Skip to content

Instantly share code, notes, and snippets.

@andreasRedeker
Last active July 27, 2024 19:41
Show Gist options
  • Save andreasRedeker/693a7ce8e81d4739d6864fcfa4606141 to your computer and use it in GitHub Desktop.
Save andreasRedeker/693a7ce8e81d4739d6864fcfa4606141 to your computer and use it in GitHub Desktop.
Parqet iOS Scriptable Widget
// Variables used by Scriptable.
// These must be at the very top of the file. Do not edit.
// icon-color: teal; icon-glyph: chart-line;
// Script by Andreas Redeker <hello@andreasredeker.de>
let portfolioId;
const TIMEFRAME = {
'max': "seit Kauf",
'ytd': "seit Jahresbeginn",
'mtd': "seit Monatsbeginn",
'today': "heute",
'7d': "1 Woche",
'1m': "1 Monat",
'3m': "3 Monate",
'6m': "6 Monate",
'1y': "1 Jahr",
'3y': "3 Jahre",
'5y': "5 Jahre"
};
let defaultTimeframe = 'max';
const apiUrl = (portfolioId, timeframe) => `https://api.parqet.com/v1/portfolios/${portfolioId}?timeframe=${timeframe}&useInclude=true`;
const backgroundColor = Color.dynamic(Color.white(), new Color("374151"));
const titleColor = Color.gray();
const titleFont = Font.mediumSystemFont(10);
const titleMinimumScaleFactor = 1;
const valueFont = Font.boldSystemFont(16);
const valueMinimumScaleFactor = 0.8;
if (config.runsInWidget && args.widgetParameter) {
portfolioId = args.widgetParameter;
} else if (config.runsInWidget && !args.widgetParameter) {
throw Error("Bitte Portfolio-Id in den Widget Parametern eintragen");
}
if (config.runsInApp) {
portfolioId = "637793772999856f62ee6578"; // parqet demo portfolio for testing
}
const portfolio = await getPortfolio(portfolioId, defaultTimeframe);
async function getPortfolio(portfolioId, timeframe) {
const data = await new Request(apiUrl(portfolioId, timeframe)).loadJSON();
if (data.statusCode == 401) {
throw Error("Portfolio ist nicht öffentlich");
}
const obj = {
name: data.portfolio.name,
currency: data.portfolio.currency,
value: data.performance.portfolioValue,
gainGrossValue: data.performance.unrealized.gainGross,
returnGrossPercent: data.performance.unrealized.returnGross,
dividendsGainNet: data.performance.dividends.gainNet,
public: data.portfolio.public,
timeframe: data.interval.timeframe
};
return obj;
}
let widget = await createWidget();
async function createWidget() {
let w = new ListWidget();
w.url = 'parqetapp://';
w.backgroundColor = backgroundColor;
let portfolioName = w.addText(portfolio.name);
portfolioName.font = titleFont;
portfolioName.textColor = titleColor;
portfolioName.minimumScaleFactor = titleMinimumScaleFactor;
let portfolioValue = w.addText(toLocaleCurrencyString(portfolio.value));
portfolioValue.font = Font.boldSystemFont(20);
portfolioValue.minimumScaleFactor = 0.9;
w.addSpacer();
let gainTitle = w.addText(`Kursgewinn ${TIMEFRAME[portfolio.timeframe]}`);
gainTitle.font = titleFont;
gainTitle.textColor = titleColor;
gainTitle.minimumScaleFactor = valueMinimumScaleFactor;
let gainGross = w.addText(toLocaleCurrencyString(portfolio.gainGrossValue));
gainGross.textColor = portfolio.returnGrossPercent > 0 ? Color.green() : Color.red();
gainGross.font = valueFont;
gainGross.minimumScaleFactor = valueMinimumScaleFactor;
let returnNet = w.addText(
portfolio.returnGrossPercent.toLocaleString() + " %"
);
returnNet.textColor = portfolio.gainGrossValue > 0 ? Color.green() : Color.red();
returnNet.font = valueFont;
returnNet.minimumScaleFactor = valueMinimumScaleFactor;
w.addSpacer();
let dividendsTitle = w.addText("Erhaltene Dividenden");
dividendsTitle.font = titleFont;
dividendsTitle.textColor = titleColor;
dividendsTitle.minimumScaleFactor = titleMinimumScaleFactor;
let dividends = w.addText(toLocaleCurrencyString(portfolio.dividendsGainNet));
dividends.font = valueFont;
dividends.minimumScaleFactor = valueMinimumScaleFactor;
w.addSpacer();
let updateTimestamp = w.addText(
"Stand " + new Date().toLocaleTimeString().slice(0, 5)
);
updateTimestamp.textColor = titleColor;
updateTimestamp.font = Font.mediumSystemFont(8);
updateTimestamp.centerAlignText();
return w;
}
function toLocaleCurrencyString(value) {
return value.toLocaleString("de-DE", {
style: "currency",
currency: portfolio.currency,
});
}
if (config.runsInApp) {
await widget.presentSmall();
}
Script.setWidget(widget);
Script.complete();
@LeRaffl
Copy link

LeRaffl commented Jul 2, 2024

Ziemlich geil. Würde gerne den Part unten mit den erhaltenen Dividenen ersetzen durch den internen Zinsfuß, aber ich tu mich schwer weil ich keinen Plan hab wie die ganzen Variablen heißen. Kannst du da weiterhelfen?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment