From c6bab4b8b25d28059865f70a432fe356811c4374 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 15:52:54 +0200 Subject: [PATCH 01/15] Update directory structure for Zensible --- .github/workflows/docs.yml | 29 +++ docs.11tydata.js | 12 -- {api => docs/api}/api-query-from-insight.md | 0 {api => docs/api}/api-run-query.md | 0 {api => docs/api}/api-token.md | 0 {api => docs/api}/api.json | 0 {api => docs/api}/insights-reference.md | 0 {api => docs/api}/signals-reference.md | 0 .../articles}/anonymization-how-it-works.md | 0 .../articles}/app-privacy-report.md | 0 .../articles}/app-tracking-transparency.md | 0 .../articles}/apple-app-privacy.md | 0 {articles => docs/articles}/articles.json | 0 ...-if-users-upgrade-to-latest-app-version.md | 0 .../articles}/create-custom-dashboards.md | 0 .../articles}/decide-to-drop-ios-version.md | 0 {articles => docs/articles}/documentation.md | 0 .../articles}/duration-signals.md | 0 {articles => docs/articles}/grand-rename.md | 0 .../articles}/hosting-solutions.md | 0 .../articles}/how-to-funnel-insights.md | 0 .../articles}/insights-about-daily-users.md | 0 .../articles}/insights-about-monthly-users.md | 0 .../articles}/insights-about-referrers.md | 0 .../insights-about-system-version.md | 0 {articles => docs/articles}/insights.md | 0 .../invite-members-to-organization.md | 0 {articles => docs/articles}/login-options.md | 0 {articles => docs/articles}/making-account.md | 0 {articles => docs/articles}/namespaces.md | 0 .../articles}/navigation-signals.md | 0 {articles => docs/articles}/notebooks.md | 0 {articles => docs/articles}/preset-errors.md | 0 .../articles}/preset-purchases.md | 0 .../articles}/set-up-filters-insights.md | 0 .../articles}/signal-type-naming.md | 0 .../articles}/telemetry-client.md | 0 {articles => docs/articles}/test-mode.md | 0 {articles => docs/articles}/update-package.md | 0 {basics => docs/basics}/acquisition.md | 0 {basics => docs/basics}/activation.md | 0 {basics => docs/basics}/basics.json | 0 {basics => docs/basics}/index.md | 0 {basics => docs/basics}/metrics.md | 0 {basics => docs/basics}/pirate-metrics.md | 0 {basics => docs/basics}/retention.md | 0 glossary.md => docs/glossary.md | 0 {guides => docs/guides}/android-setup.md | 0 {guides => docs/guides}/flutter-setup.md | 0 {guides => docs/guides}/guides.json | 0 {guides => docs/guides}/javascript-setup.md | 0 {guides => docs/guides}/objective-c-setup.md | 0 {guides => docs/guides}/privacy-faq.md | 0 {guides => docs/guides}/react-setup.md | 0 {guides => docs/guides}/swift-setup.md | 0 {guides => docs/guides}/vue-setup.md | 0 {guides => docs/guides}/web-setup.md | 0 docs/index.md | 181 ++++++++++++++++++ index.njk => docs/index.njk | 0 {ingest => docs/ingest}/default-parameters.md | 0 {ingest => docs/ingest}/ingest.json | 0 {ingest => docs/ingest}/v1.md | 0 {ingest => docs/ingest}/v2.md | 0 .../integrations}/integrations.json | 0 .../integrations}/revenuecat.md | 0 .../integrations}/superwall.md | 0 .../web-setup-google-tag-manager.md | 0 docs/markdown.md | 111 +++++++++++ .../recipes}/averagaging-numbers.md | 0 {recipes => docs/recipes}/listing-events.md | 0 {recipes => docs/recipes}/recipes.json | 0 .../recipes}/views-per-purchase-example.md | 0 {tql => docs/tql}/aggregators.md | 0 {tql => docs/tql}/baseFilters.md | 0 {tql => docs/tql}/descending.md | 0 {tql => docs/tql}/dimensionSpec.md | 0 {tql => docs/tql}/experiment.md | 0 {tql => docs/tql}/extractionFunction.md | 0 {tql => docs/tql}/filters.md | 0 {tql => docs/tql}/firstGuideline.md | 0 {tql => docs/tql}/funnel.md | 0 {tql => docs/tql}/funnels.md | 0 {tql => docs/tql}/granularity.md | 0 {tql => docs/tql}/groupBy.md | 0 {tql => docs/tql}/post-aggregators.md | 0 {tql => docs/tql}/query.md | 0 {tql => docs/tql}/queryContext.md | 0 {tql => docs/tql}/queryType.md | 0 {tql => docs/tql}/retention.md | 0 {tql => docs/tql}/scan.md | 0 {tql => docs/tql}/time-intervals.md | 0 {tql => docs/tql}/timeseries.md | 0 {tql => docs/tql}/topN.md | 0 {tql => docs/tql}/topNMetricSpec.md | 0 {tql => docs/tql}/tql.json | 0 {tql => docs/tql}/valueFormatter.md | 0 96 files changed, 321 insertions(+), 12 deletions(-) create mode 100644 .github/workflows/docs.yml delete mode 100644 docs.11tydata.js rename {api => docs/api}/api-query-from-insight.md (100%) rename {api => docs/api}/api-run-query.md (100%) rename {api => docs/api}/api-token.md (100%) rename {api => docs/api}/api.json (100%) rename {api => docs/api}/insights-reference.md (100%) rename {api => docs/api}/signals-reference.md (100%) rename {articles => docs/articles}/anonymization-how-it-works.md (100%) rename {articles => docs/articles}/app-privacy-report.md (100%) rename {articles => docs/articles}/app-tracking-transparency.md (100%) rename {articles => docs/articles}/apple-app-privacy.md (100%) rename {articles => docs/articles}/articles.json (100%) rename {articles => docs/articles}/check-if-users-upgrade-to-latest-app-version.md (100%) rename {articles => docs/articles}/create-custom-dashboards.md (100%) rename {articles => docs/articles}/decide-to-drop-ios-version.md (100%) rename {articles => docs/articles}/documentation.md (100%) rename {articles => docs/articles}/duration-signals.md (100%) rename {articles => docs/articles}/grand-rename.md (100%) rename {articles => docs/articles}/hosting-solutions.md (100%) rename {articles => docs/articles}/how-to-funnel-insights.md (100%) rename {articles => docs/articles}/insights-about-daily-users.md (100%) rename {articles => docs/articles}/insights-about-monthly-users.md (100%) rename {articles => docs/articles}/insights-about-referrers.md (100%) rename {articles => docs/articles}/insights-about-system-version.md (100%) rename {articles => docs/articles}/insights.md (100%) rename {articles => docs/articles}/invite-members-to-organization.md (100%) rename {articles => docs/articles}/login-options.md (100%) rename {articles => docs/articles}/making-account.md (100%) rename {articles => docs/articles}/namespaces.md (100%) rename {articles => docs/articles}/navigation-signals.md (100%) rename {articles => docs/articles}/notebooks.md (100%) rename {articles => docs/articles}/preset-errors.md (100%) rename {articles => docs/articles}/preset-purchases.md (100%) rename {articles => docs/articles}/set-up-filters-insights.md (100%) rename {articles => docs/articles}/signal-type-naming.md (100%) rename {articles => docs/articles}/telemetry-client.md (100%) rename {articles => docs/articles}/test-mode.md (100%) rename {articles => docs/articles}/update-package.md (100%) rename {basics => docs/basics}/acquisition.md (100%) rename {basics => docs/basics}/activation.md (100%) rename {basics => docs/basics}/basics.json (100%) rename {basics => docs/basics}/index.md (100%) rename {basics => docs/basics}/metrics.md (100%) rename {basics => docs/basics}/pirate-metrics.md (100%) rename {basics => docs/basics}/retention.md (100%) rename glossary.md => docs/glossary.md (100%) rename {guides => docs/guides}/android-setup.md (100%) rename {guides => docs/guides}/flutter-setup.md (100%) rename {guides => docs/guides}/guides.json (100%) rename {guides => docs/guides}/javascript-setup.md (100%) rename {guides => docs/guides}/objective-c-setup.md (100%) rename {guides => docs/guides}/privacy-faq.md (100%) rename {guides => docs/guides}/react-setup.md (100%) rename {guides => docs/guides}/swift-setup.md (100%) rename {guides => docs/guides}/vue-setup.md (100%) rename {guides => docs/guides}/web-setup.md (100%) create mode 100644 docs/index.md rename index.njk => docs/index.njk (100%) rename {ingest => docs/ingest}/default-parameters.md (100%) rename {ingest => docs/ingest}/ingest.json (100%) rename {ingest => docs/ingest}/v1.md (100%) rename {ingest => docs/ingest}/v2.md (100%) rename {integrations => docs/integrations}/integrations.json (100%) rename {integrations => docs/integrations}/revenuecat.md (100%) rename {integrations => docs/integrations}/superwall.md (100%) rename {integrations => docs/integrations}/web-setup-google-tag-manager.md (100%) create mode 100644 docs/markdown.md rename {recipes => docs/recipes}/averagaging-numbers.md (100%) rename {recipes => docs/recipes}/listing-events.md (100%) rename {recipes => docs/recipes}/recipes.json (100%) rename {recipes => docs/recipes}/views-per-purchase-example.md (100%) rename {tql => docs/tql}/aggregators.md (100%) rename {tql => docs/tql}/baseFilters.md (100%) rename {tql => docs/tql}/descending.md (100%) rename {tql => docs/tql}/dimensionSpec.md (100%) rename {tql => docs/tql}/experiment.md (100%) rename {tql => docs/tql}/extractionFunction.md (100%) rename {tql => docs/tql}/filters.md (100%) rename {tql => docs/tql}/firstGuideline.md (100%) rename {tql => docs/tql}/funnel.md (100%) rename {tql => docs/tql}/funnels.md (100%) rename {tql => docs/tql}/granularity.md (100%) rename {tql => docs/tql}/groupBy.md (100%) rename {tql => docs/tql}/post-aggregators.md (100%) rename {tql => docs/tql}/query.md (100%) rename {tql => docs/tql}/queryContext.md (100%) rename {tql => docs/tql}/queryType.md (100%) rename {tql => docs/tql}/retention.md (100%) rename {tql => docs/tql}/scan.md (100%) rename {tql => docs/tql}/time-intervals.md (100%) rename {tql => docs/tql}/timeseries.md (100%) rename {tql => docs/tql}/topN.md (100%) rename {tql => docs/tql}/topNMetricSpec.md (100%) rename {tql => docs/tql}/tql.json (100%) rename {tql => docs/tql}/valueFormatter.md (100%) diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml new file mode 100644 index 0000000..47ee722 --- /dev/null +++ b/.github/workflows/docs.yml @@ -0,0 +1,29 @@ +name: Documentation +on: + push: + branches: + - master + - main +permissions: + contents: read + pages: write + id-token: write +jobs: + deploy: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + runs-on: ubuntu-latest + steps: + - uses: actions/configure-pages@v6 + - uses: actions/checkout@v6 + - uses: actions/setup-python@v6 + with: + python-version: 3.x + - run: pip install zensical + - run: zensical build --clean + - uses: actions/upload-pages-artifact@v5 + with: + path: site + - uses: actions/deploy-pages@v5 + id: deployment diff --git a/docs.11tydata.js b/docs.11tydata.js deleted file mode 100644 index e10251a..0000000 --- a/docs.11tydata.js +++ /dev/null @@ -1,12 +0,0 @@ -let data = { - layout: "docs/docpage.njk", - tags: "docs", - sitemapchangefrequency: "daily", - sitemappriority: "0.7", -}; - -// if(process.env.NODE_ENV === "production") { -data.date = "git Last Modified"; -// } - -module.exports = data; diff --git a/api/api-query-from-insight.md b/docs/api/api-query-from-insight.md similarity index 100% rename from api/api-query-from-insight.md rename to docs/api/api-query-from-insight.md diff --git a/api/api-run-query.md b/docs/api/api-run-query.md similarity index 100% rename from api/api-run-query.md rename to docs/api/api-run-query.md diff --git a/api/api-token.md b/docs/api/api-token.md similarity index 100% rename from api/api-token.md rename to docs/api/api-token.md diff --git a/api/api.json b/docs/api/api.json similarity index 100% rename from api/api.json rename to docs/api/api.json diff --git a/api/insights-reference.md b/docs/api/insights-reference.md similarity index 100% rename from api/insights-reference.md rename to docs/api/insights-reference.md diff --git a/api/signals-reference.md b/docs/api/signals-reference.md similarity index 100% rename from api/signals-reference.md rename to docs/api/signals-reference.md diff --git a/articles/anonymization-how-it-works.md b/docs/articles/anonymization-how-it-works.md similarity index 100% rename from articles/anonymization-how-it-works.md rename to docs/articles/anonymization-how-it-works.md diff --git a/articles/app-privacy-report.md b/docs/articles/app-privacy-report.md similarity index 100% rename from articles/app-privacy-report.md rename to docs/articles/app-privacy-report.md diff --git a/articles/app-tracking-transparency.md b/docs/articles/app-tracking-transparency.md similarity index 100% rename from articles/app-tracking-transparency.md rename to docs/articles/app-tracking-transparency.md diff --git a/articles/apple-app-privacy.md b/docs/articles/apple-app-privacy.md similarity index 100% rename from articles/apple-app-privacy.md rename to docs/articles/apple-app-privacy.md diff --git a/articles/articles.json b/docs/articles/articles.json similarity index 100% rename from articles/articles.json rename to docs/articles/articles.json diff --git a/articles/check-if-users-upgrade-to-latest-app-version.md b/docs/articles/check-if-users-upgrade-to-latest-app-version.md similarity index 100% rename from articles/check-if-users-upgrade-to-latest-app-version.md rename to docs/articles/check-if-users-upgrade-to-latest-app-version.md diff --git a/articles/create-custom-dashboards.md b/docs/articles/create-custom-dashboards.md similarity index 100% rename from articles/create-custom-dashboards.md rename to docs/articles/create-custom-dashboards.md diff --git a/articles/decide-to-drop-ios-version.md b/docs/articles/decide-to-drop-ios-version.md similarity index 100% rename from articles/decide-to-drop-ios-version.md rename to docs/articles/decide-to-drop-ios-version.md diff --git a/articles/documentation.md b/docs/articles/documentation.md similarity index 100% rename from articles/documentation.md rename to docs/articles/documentation.md diff --git a/articles/duration-signals.md b/docs/articles/duration-signals.md similarity index 100% rename from articles/duration-signals.md rename to docs/articles/duration-signals.md diff --git a/articles/grand-rename.md b/docs/articles/grand-rename.md similarity index 100% rename from articles/grand-rename.md rename to docs/articles/grand-rename.md diff --git a/articles/hosting-solutions.md b/docs/articles/hosting-solutions.md similarity index 100% rename from articles/hosting-solutions.md rename to docs/articles/hosting-solutions.md diff --git a/articles/how-to-funnel-insights.md b/docs/articles/how-to-funnel-insights.md similarity index 100% rename from articles/how-to-funnel-insights.md rename to docs/articles/how-to-funnel-insights.md diff --git a/articles/insights-about-daily-users.md b/docs/articles/insights-about-daily-users.md similarity index 100% rename from articles/insights-about-daily-users.md rename to docs/articles/insights-about-daily-users.md diff --git a/articles/insights-about-monthly-users.md b/docs/articles/insights-about-monthly-users.md similarity index 100% rename from articles/insights-about-monthly-users.md rename to docs/articles/insights-about-monthly-users.md diff --git a/articles/insights-about-referrers.md b/docs/articles/insights-about-referrers.md similarity index 100% rename from articles/insights-about-referrers.md rename to docs/articles/insights-about-referrers.md diff --git a/articles/insights-about-system-version.md b/docs/articles/insights-about-system-version.md similarity index 100% rename from articles/insights-about-system-version.md rename to docs/articles/insights-about-system-version.md diff --git a/articles/insights.md b/docs/articles/insights.md similarity index 100% rename from articles/insights.md rename to docs/articles/insights.md diff --git a/articles/invite-members-to-organization.md b/docs/articles/invite-members-to-organization.md similarity index 100% rename from articles/invite-members-to-organization.md rename to docs/articles/invite-members-to-organization.md diff --git a/articles/login-options.md b/docs/articles/login-options.md similarity index 100% rename from articles/login-options.md rename to docs/articles/login-options.md diff --git a/articles/making-account.md b/docs/articles/making-account.md similarity index 100% rename from articles/making-account.md rename to docs/articles/making-account.md diff --git a/articles/namespaces.md b/docs/articles/namespaces.md similarity index 100% rename from articles/namespaces.md rename to docs/articles/namespaces.md diff --git a/articles/navigation-signals.md b/docs/articles/navigation-signals.md similarity index 100% rename from articles/navigation-signals.md rename to docs/articles/navigation-signals.md diff --git a/articles/notebooks.md b/docs/articles/notebooks.md similarity index 100% rename from articles/notebooks.md rename to docs/articles/notebooks.md diff --git a/articles/preset-errors.md b/docs/articles/preset-errors.md similarity index 100% rename from articles/preset-errors.md rename to docs/articles/preset-errors.md diff --git a/articles/preset-purchases.md b/docs/articles/preset-purchases.md similarity index 100% rename from articles/preset-purchases.md rename to docs/articles/preset-purchases.md diff --git a/articles/set-up-filters-insights.md b/docs/articles/set-up-filters-insights.md similarity index 100% rename from articles/set-up-filters-insights.md rename to docs/articles/set-up-filters-insights.md diff --git a/articles/signal-type-naming.md b/docs/articles/signal-type-naming.md similarity index 100% rename from articles/signal-type-naming.md rename to docs/articles/signal-type-naming.md diff --git a/articles/telemetry-client.md b/docs/articles/telemetry-client.md similarity index 100% rename from articles/telemetry-client.md rename to docs/articles/telemetry-client.md diff --git a/articles/test-mode.md b/docs/articles/test-mode.md similarity index 100% rename from articles/test-mode.md rename to docs/articles/test-mode.md diff --git a/articles/update-package.md b/docs/articles/update-package.md similarity index 100% rename from articles/update-package.md rename to docs/articles/update-package.md diff --git a/basics/acquisition.md b/docs/basics/acquisition.md similarity index 100% rename from basics/acquisition.md rename to docs/basics/acquisition.md diff --git a/basics/activation.md b/docs/basics/activation.md similarity index 100% rename from basics/activation.md rename to docs/basics/activation.md diff --git a/basics/basics.json b/docs/basics/basics.json similarity index 100% rename from basics/basics.json rename to docs/basics/basics.json diff --git a/basics/index.md b/docs/basics/index.md similarity index 100% rename from basics/index.md rename to docs/basics/index.md diff --git a/basics/metrics.md b/docs/basics/metrics.md similarity index 100% rename from basics/metrics.md rename to docs/basics/metrics.md diff --git a/basics/pirate-metrics.md b/docs/basics/pirate-metrics.md similarity index 100% rename from basics/pirate-metrics.md rename to docs/basics/pirate-metrics.md diff --git a/basics/retention.md b/docs/basics/retention.md similarity index 100% rename from basics/retention.md rename to docs/basics/retention.md diff --git a/glossary.md b/docs/glossary.md similarity index 100% rename from glossary.md rename to docs/glossary.md diff --git a/guides/android-setup.md b/docs/guides/android-setup.md similarity index 100% rename from guides/android-setup.md rename to docs/guides/android-setup.md diff --git a/guides/flutter-setup.md b/docs/guides/flutter-setup.md similarity index 100% rename from guides/flutter-setup.md rename to docs/guides/flutter-setup.md diff --git a/guides/guides.json b/docs/guides/guides.json similarity index 100% rename from guides/guides.json rename to docs/guides/guides.json diff --git a/guides/javascript-setup.md b/docs/guides/javascript-setup.md similarity index 100% rename from guides/javascript-setup.md rename to docs/guides/javascript-setup.md diff --git a/guides/objective-c-setup.md b/docs/guides/objective-c-setup.md similarity index 100% rename from guides/objective-c-setup.md rename to docs/guides/objective-c-setup.md diff --git a/guides/privacy-faq.md b/docs/guides/privacy-faq.md similarity index 100% rename from guides/privacy-faq.md rename to docs/guides/privacy-faq.md diff --git a/guides/react-setup.md b/docs/guides/react-setup.md similarity index 100% rename from guides/react-setup.md rename to docs/guides/react-setup.md diff --git a/guides/swift-setup.md b/docs/guides/swift-setup.md similarity index 100% rename from guides/swift-setup.md rename to docs/guides/swift-setup.md diff --git a/guides/vue-setup.md b/docs/guides/vue-setup.md similarity index 100% rename from guides/vue-setup.md rename to docs/guides/vue-setup.md diff --git a/guides/web-setup.md b/docs/guides/web-setup.md similarity index 100% rename from guides/web-setup.md rename to docs/guides/web-setup.md diff --git a/docs/index.md b/docs/index.md new file mode 100644 index 0000000..b50d7a1 --- /dev/null +++ b/docs/index.md @@ -0,0 +1,181 @@ +--- +icon: lucide/rocket +--- + +!!! warning + + This is a test for a new documentation system. Trust nothing and no one. The original TelemetryDeck + documentation still lives at https://telemetrydeck.com/docs/ for now. + + +---- + +# Get started + +For full documentation visit [zensical.org](https://zensical.org/docs/). + +## Commands + +* [`zensical new`][new] - Create a new project +* [`zensical serve`][serve] - Start local web server +* [`zensical build`][build] - Build your site + + [new]: https://zensical.org/docs/usage/new/ + [serve]: https://zensical.org/docs/usage/preview/ + [build]: https://zensical.org/docs/usage/build/ + +## Examples + +### Admonitions + +> Go to [documentation](https://zensical.org/docs/authoring/admonitions/) + +!!! note + + This is a **note** admonition. Use it to provide helpful information. + +!!! warning + + This is a **warning** admonition. Be careful! + +### Details + +> Go to [documentation](https://zensical.org/docs/authoring/admonitions/#collapsible-blocks) + +??? info "Click to expand for more info" + + This content is hidden until you click to expand it. + Great for FAQs or long explanations. + +## Code Blocks + +> Go to [documentation](https://zensical.org/docs/authoring/code-blocks/) + +``` python hl_lines="2" title="Code blocks" +def greet(name): + print(f"Hello, {name}!") # (1)! + +greet("Python") +``` + +1. > Go to [documentation](https://zensical.org/docs/authoring/code-blocks/#code-annotations) + + Code annotations allow to attach notes to lines of code. + +Code can also be highlighted inline: `#!python print("Hello, Python!")`. + +## Content tabs + +> Go to [documentation](https://zensical.org/docs/authoring/content-tabs/) + +=== "Python" + + ``` python + print("Hello from Python!") + ``` + +=== "Rust" + + ``` rs + println!("Hello from Rust!"); + ``` + +## Diagrams + +> Go to [documentation](https://zensical.org/docs/authoring/diagrams/) + +``` mermaid +graph LR + A[Start] --> B{Error?}; + B -->|Yes| C[Hmm...]; + C --> D[Debug]; + D --> B; + B ---->|No| E[Yay!]; +``` + +## Footnotes + +> Go to [documentation](https://zensical.org/docs/authoring/footnotes/) + +Here's a sentence with a footnote.[^1] + +Hover it, to see a tooltip. + +[^1]: This is the footnote. + + +## Formatting + +> Go to [documentation](https://zensical.org/docs/authoring/formatting/) + +- ==This was marked (highlight)== +- ^^This was inserted (underline)^^ +- ~~This was deleted (strikethrough)~~ +- H~2~O +- A^T^A +- ++ctrl+alt+del++ + +## Icons, Emojis + +> Go to [documentation](https://zensical.org/docs/authoring/icons-emojis/) + +* :sparkles: `:sparkles:` +* :rocket: `:rocket:` +* :tada: `:tada:` +* :memo: `:memo:` +* :eyes: `:eyes:` + +## Maths + +> Go to [documentation](https://zensical.org/docs/authoring/math/) + +$$ +\cos x=\sum_{k=0}^{\infty}\frac{(-1)^k}{(2k)!}x^{2k} +$$ + +!!! warning "Needs configuration" + Note that MathJax is included via a `script` tag on this page and is not + configured in the generated default configuration to avoid including it + in a pages that do not need it. See the documentation for details on how + to configure it on all your pages if they are more Maths-heavy than these + simple starter pages. + + + + +## Task Lists + +> Go to [documentation](https://zensical.org/docs/authoring/lists/#using-task-lists) + +* [x] Install Zensical +* [x] Configure `zensical.toml` +* [x] Write amazing documentation +* [ ] Deploy anywhere + +## Tooltips + +> Go to [documentation](https://zensical.org/docs/authoring/tooltips/) + +[Hover me][example] + + [example]: https://example.com "I'm a tooltip!" diff --git a/index.njk b/docs/index.njk similarity index 100% rename from index.njk rename to docs/index.njk diff --git a/ingest/default-parameters.md b/docs/ingest/default-parameters.md similarity index 100% rename from ingest/default-parameters.md rename to docs/ingest/default-parameters.md diff --git a/ingest/ingest.json b/docs/ingest/ingest.json similarity index 100% rename from ingest/ingest.json rename to docs/ingest/ingest.json diff --git a/ingest/v1.md b/docs/ingest/v1.md similarity index 100% rename from ingest/v1.md rename to docs/ingest/v1.md diff --git a/ingest/v2.md b/docs/ingest/v2.md similarity index 100% rename from ingest/v2.md rename to docs/ingest/v2.md diff --git a/integrations/integrations.json b/docs/integrations/integrations.json similarity index 100% rename from integrations/integrations.json rename to docs/integrations/integrations.json diff --git a/integrations/revenuecat.md b/docs/integrations/revenuecat.md similarity index 100% rename from integrations/revenuecat.md rename to docs/integrations/revenuecat.md diff --git a/integrations/superwall.md b/docs/integrations/superwall.md similarity index 100% rename from integrations/superwall.md rename to docs/integrations/superwall.md diff --git a/integrations/web-setup-google-tag-manager.md b/docs/integrations/web-setup-google-tag-manager.md similarity index 100% rename from integrations/web-setup-google-tag-manager.md rename to docs/integrations/web-setup-google-tag-manager.md diff --git a/docs/markdown.md b/docs/markdown.md new file mode 100644 index 0000000..e2da6dc --- /dev/null +++ b/docs/markdown.md @@ -0,0 +1,111 @@ +--- +icon: simple/markdown +--- + +# Markdown in 5min + +## Headers + +``` +# H1 Header +## H2 Header +### H3 Header +#### H4 Header +##### H5 Header +###### H6 Header +``` + +## Text formatting + +``` +**bold text** +*italic text* +***bold and italic*** +~~strikethrough~~ +`inline code` +``` + +## Links and images + +``` +[Link text](https://example.com) +[Link with title](https://example.com "Hover title") +![Alt text](image.jpg) +![Image with title](image.jpg "Image title") +``` + +## Lists + +``` +Unordered: + +- Item 1 +- Item 2 + - Nested item + +Ordered: + +1. First item +2. Second item +3. Third item +``` + +## Blockquotes + +``` +> This is a blockquote +> Multiple lines +>> Nested quote +``` + +## Code blocks + +```` +```javascript +function hello() { + console.log("Hello, world!"); +} +``` +```` + +## Tables + +``` +| Header 1 | Header 2 | Header 3 | +|----------|----------|----------| +| Row 1 | Data | Data | +| Row 2 | Data | Data | +``` + +## Horizontal rule + +``` +--- +or +*** +or +___ +``` + +## Task lists + +``` +- [x] Completed task +- [ ] Incomplete task +- [ ] Another task +``` + +## Escaping characters + +``` +Use backslash to escape: \* \_ \# \` +``` + +## Line breaks + +``` +End a line with two spaces +to create a line break. + +Or use a blank line for a new paragraph. +``` \ No newline at end of file diff --git a/recipes/averagaging-numbers.md b/docs/recipes/averagaging-numbers.md similarity index 100% rename from recipes/averagaging-numbers.md rename to docs/recipes/averagaging-numbers.md diff --git a/recipes/listing-events.md b/docs/recipes/listing-events.md similarity index 100% rename from recipes/listing-events.md rename to docs/recipes/listing-events.md diff --git a/recipes/recipes.json b/docs/recipes/recipes.json similarity index 100% rename from recipes/recipes.json rename to docs/recipes/recipes.json diff --git a/recipes/views-per-purchase-example.md b/docs/recipes/views-per-purchase-example.md similarity index 100% rename from recipes/views-per-purchase-example.md rename to docs/recipes/views-per-purchase-example.md diff --git a/tql/aggregators.md b/docs/tql/aggregators.md similarity index 100% rename from tql/aggregators.md rename to docs/tql/aggregators.md diff --git a/tql/baseFilters.md b/docs/tql/baseFilters.md similarity index 100% rename from tql/baseFilters.md rename to docs/tql/baseFilters.md diff --git a/tql/descending.md b/docs/tql/descending.md similarity index 100% rename from tql/descending.md rename to docs/tql/descending.md diff --git a/tql/dimensionSpec.md b/docs/tql/dimensionSpec.md similarity index 100% rename from tql/dimensionSpec.md rename to docs/tql/dimensionSpec.md diff --git a/tql/experiment.md b/docs/tql/experiment.md similarity index 100% rename from tql/experiment.md rename to docs/tql/experiment.md diff --git a/tql/extractionFunction.md b/docs/tql/extractionFunction.md similarity index 100% rename from tql/extractionFunction.md rename to docs/tql/extractionFunction.md diff --git a/tql/filters.md b/docs/tql/filters.md similarity index 100% rename from tql/filters.md rename to docs/tql/filters.md diff --git a/tql/firstGuideline.md b/docs/tql/firstGuideline.md similarity index 100% rename from tql/firstGuideline.md rename to docs/tql/firstGuideline.md diff --git a/tql/funnel.md b/docs/tql/funnel.md similarity index 100% rename from tql/funnel.md rename to docs/tql/funnel.md diff --git a/tql/funnels.md b/docs/tql/funnels.md similarity index 100% rename from tql/funnels.md rename to docs/tql/funnels.md diff --git a/tql/granularity.md b/docs/tql/granularity.md similarity index 100% rename from tql/granularity.md rename to docs/tql/granularity.md diff --git a/tql/groupBy.md b/docs/tql/groupBy.md similarity index 100% rename from tql/groupBy.md rename to docs/tql/groupBy.md diff --git a/tql/post-aggregators.md b/docs/tql/post-aggregators.md similarity index 100% rename from tql/post-aggregators.md rename to docs/tql/post-aggregators.md diff --git a/tql/query.md b/docs/tql/query.md similarity index 100% rename from tql/query.md rename to docs/tql/query.md diff --git a/tql/queryContext.md b/docs/tql/queryContext.md similarity index 100% rename from tql/queryContext.md rename to docs/tql/queryContext.md diff --git a/tql/queryType.md b/docs/tql/queryType.md similarity index 100% rename from tql/queryType.md rename to docs/tql/queryType.md diff --git a/tql/retention.md b/docs/tql/retention.md similarity index 100% rename from tql/retention.md rename to docs/tql/retention.md diff --git a/tql/scan.md b/docs/tql/scan.md similarity index 100% rename from tql/scan.md rename to docs/tql/scan.md diff --git a/tql/time-intervals.md b/docs/tql/time-intervals.md similarity index 100% rename from tql/time-intervals.md rename to docs/tql/time-intervals.md diff --git a/tql/timeseries.md b/docs/tql/timeseries.md similarity index 100% rename from tql/timeseries.md rename to docs/tql/timeseries.md diff --git a/tql/topN.md b/docs/tql/topN.md similarity index 100% rename from tql/topN.md rename to docs/tql/topN.md diff --git a/tql/topNMetricSpec.md b/docs/tql/topNMetricSpec.md similarity index 100% rename from tql/topNMetricSpec.md rename to docs/tql/topNMetricSpec.md diff --git a/tql/tql.json b/docs/tql/tql.json similarity index 100% rename from tql/tql.json rename to docs/tql/tql.json diff --git a/tql/valueFormatter.md b/docs/tql/valueFormatter.md similarity index 100% rename from tql/valueFormatter.md rename to docs/tql/valueFormatter.md From 40676077deaaee77efda9a8362cf72d9e3a1dee6 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 15:53:05 +0200 Subject: [PATCH 02/15] Add rudimentary zensible configuration file --- zensical.toml | 349 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 349 insertions(+) create mode 100644 zensical.toml diff --git a/zensical.toml b/zensical.toml new file mode 100644 index 0000000..be1233c --- /dev/null +++ b/zensical.toml @@ -0,0 +1,349 @@ +# ============================================================================ +# +# The configuration produced by default is meant to highlight the features +# that Zensical provides and to serve as a starting point for your own +# projects. +# +# ============================================================================ + +[project] + +# The site_name is shown in the page header and the browser window title +# +# Read more: https://zensical.org/docs/setup/basics/#site_name +site_name = "TelemetryDeck Documentation" + +# The site_description is included in the HTML head and should contain a +# meaningful description of the site content for use by search engines. +# +# Read more: https://zensical.org/docs/setup/basics/#site_description +site_description = "Documentation for the installation and usage of TelemetryDeck, a privacy first usage analytics service." + +# The site_author attribute. This is used in the HTML head element. +# +# Read more: https://zensical.org/docs/setup/basics/#site_author +site_author = "TelemetryDeck Docs Team" + +# The site_url is the canonical URL for your site. When building online +# documentation you should set this. +# Read more: https://zensical.org/docs/setup/basics/#site_url +#site_url = "https://docs.telemetrydeck.com/" + +# The copyright notice appears in the page footer and can contain an HTML +# fragment. +# +# Read more: https://zensical.org/docs/setup/basics/#copyright +copyright = """ +Copyright © 2026 TelemetryDeck GmbH +""" + +# Zensical supports both implicit navigation and explicitly defined navigation. +# If you decide not to define a navigation here then Zensical will simply +# derive the navigation structure from the directory structure of your +# "docs_dir". The definition below demonstrates how a navigation structure +# can be defined using TOML syntax. +# +# Read more: https://zensical.org/docs/setup/navigation/ +# nav = [ +# { "Get started" = "index.md" }, +# { "Markdown in 5min" = "markdown.md" }, +# ] + +# With the "extra_css" option you can add your own CSS styling to customize +# your Zensical project according to your needs. You can add any number of +# CSS files. +# +# The path provided should be relative to the "docs_dir". +# +# Read more: https://zensical.org/docs/customization/#additional-css +# +#extra_css = ["stylesheets/extra.css"] + +# With the `extra_javascript` option you can add your own JavaScript to your +# project to customize the behavior according to your needs. +# +# The path provided should be relative to the "docs_dir". +# +# Read more: https://zensical.org/docs/customization/#additional-javascript +#extra_javascript = ["javascripts/extra.js"] + +# ---------------------------------------------------------------------------- +# Section for configuring theme options +# ---------------------------------------------------------------------------- +[project.theme] + +# change this to "classic" to use the traditional Material for MkDocs look. +#variant = "classic" + +# Zensical allows you to override specific blocks, partials, or whole +# templates as well as to define your own templates. To do this, uncomment +# the custom_dir setting below and set it to a directory in which you +# keep your template overrides. +# +# Read more: +# - https://zensical.org/docs/customization/#extending-the-theme +# +#custom_dir = "overrides" + +# With the "favicon" option you can set your own image to use as the icon +# browsers will use in the browser title bar or tab bar. The path provided +# must be relative to the "docs_dir". +# +# Read more: +# - https://zensical.org/docs/setup/logo-and-icons/#favicon +# - https://developer.mozilla.org/en-US/docs/Glossary/Favicon +# +#favicon = "images/favicon.png" + +# Zensical supports more than 60 different languages. This means that the +# labels and tooltips that Zensical's templates produce are translated. +# The "language" option allows you to set the language used. This language +# is also indicated in the HTML head element to help with accessibility +# and guide search engines and translation tools. +# +# The default language is "en" (English). It is possible to create +# sites with multiple languages and configure a language selector. See +# the documentation for details. +# +# Read more: +# - https://zensical.org/docs/setup/language/ +# +language = "en" + +# Zensical provides a number of feature toggles that change the behavior +# of the documentation site. +features = [ + # Zensical includes an announcement bar. This feature allows users to + # dismiss it when they have read the announcement. + # https://zensical.org/docs/setup/header/#announcement-bar + "announce.dismiss", + + # If you have a repository configured and turn on this feature, Zensical + # will generate an edit button for the page. This works for common + # repository hosting services. + # https://zensical.org/docs/setup/repository/#content-actions + #"content.action.edit", + + # If you have a repository configured and turn on this feature, Zensical + # will generate a button that allows the user to view the Markdown + # code for the current page. + # https://zensical.org/docs/setup/repository/#content-actions + #"content.action.view", + + # Code annotations allow you to add an icon with a tooltip to your + # code blocks to provide explanations at crucial points. + # https://zensical.org/docs/authoring/code-blocks/#code-annotations + "content.code.annotate", + + # This feature turns on a button in code blocks that allow users to + # copy the content to their clipboard without first selecting it. + # https://zensical.org/docs/authoring/code-blocks/#code-copy-button + "content.code.copy", + + # Code blocks can include a button to allow for the selection of line + # ranges by the user. + # https://zensical.org/docs/authoring/code-blocks/#code-selection-button + "content.code.select", + + # Zensical can render footnotes as inline tooltips, so the user can read + # the footnote without leaving the context of the document. + # https://zensical.org/docs/authoring/footnotes/#footnote-tooltips + "content.footnote.tooltips", + + # If you have many content tabs that have the same titles (e.g., "Python", + # "JavaScript", "Cobol"), this feature causes all of them to switch to + # at the same time when the user chooses their language in one. + # https://zensical.org/docs/authoring/content-tabs/#linked-content-tabs + "content.tabs.link", + + # With this feature enabled users can add tooltips to links that will be + # displayed when the mouse pointer hovers the link. + # https://zensical.org/docs/authoring/tooltips/#improved-tooltips + "content.tooltips", + + # With this feature enabled, Zensical will automatically hide parts + # of the header when the user scrolls past a certain point. + # https://zensical.org/docs/setup/header/#automatic-hiding + # "header.autohide", + + # Turn on this feature to expand all collapsible sections in the + # navigation sidebar by default. + # https://zensical.org/docs/setup/navigation/#navigation-expansion + # "navigation.expand", + + # This feature turns on navigation elements in the footer that allow the + # user to navigate to a next or previous page. + # https://zensical.org/docs/setup/footer/#navigation + "navigation.footer", + + # When section index pages are enabled, documents can be directly attached + # to sections, which is particularly useful for providing overview pages. + # https://zensical.org/docs/setup/navigation/#section-index-pages + "navigation.indexes", + + # When instant navigation is enabled, clicks on all internal links will be + # intercepted and dispatched via XHR without fully reloading the page. + # https://zensical.org/docs/setup/navigation/#instant-navigation + "navigation.instant", + + # With instant prefetching, your site will start to fetch a page once the + # user hovers over a link. This will reduce the perceived loading time + # for the user. + # https://zensical.org/docs/setup/navigation/#instant-prefetching + "navigation.instant.prefetch", + + # In order to provide a better user experience on slow connections when + # using instant navigation, a progress indicator can be enabled. + # https://zensical.org/docs/setup/navigation/#progress-indicator + #"navigation.instant.progress", + + # When navigation paths are activated, a breadcrumb navigation is rendered + # above the title of each page + # https://zensical.org/docs/setup/navigation/#navigation-path + "navigation.path", + + # When pruning is enabled, only the visible navigation items are included + # in the rendered HTML, reducing the size of the built site by 33% or more. + # https://zensical.org/docs/setup/navigation/#navigation-pruning + #"navigation.prune", + + # When sections are enabled, top-level sections are rendered as groups in + # the sidebar for viewports above 1220px, but remain as-is on mobile. + # https://zensical.org/docs/setup/navigation/#navigation-sections + "navigation.sections", + + # When tabs are enabled, top-level sections are rendered in a menu layer + # below the header for viewports above 1220px, but remain as-is on mobile. + # https://zensical.org/docs/setup/navigation/#navigation-tabs + #"navigation.tabs", + + # When sticky tabs are enabled, navigation tabs will lock below the header + # and always remain visible when scrolling down. + # https://zensical.org/docs/setup/navigation/#sticky-navigation-tabs + #"navigation.tabs.sticky", + + # A back-to-top button can be shown when the user, after scrolling down, + # starts to scroll up again. + # https://zensical.org/docs/setup/navigation/#back-to-top-button + "navigation.top", + + # When anchor tracking is enabled, the URL in the address bar is + # automatically updated with the active anchor as highlighted in the table + # of contents. + # https://zensical.org/docs/setup/navigation/#anchor-tracking + "navigation.tracking", + + # When search highlighting is enabled and a user clicks on a search result, + # Zensical will highlight all occurrences after following the link. + # https://zensical.org/docs/setup/search/#search-highlighting + "search.highlight", + + # When anchor following for the table of contents is enabled, the sidebar + # is automatically scrolled so that the active anchor is always visible. + # https://zensical.org/docs/setup/navigation/#anchor-following + # "toc.follow", + + # When navigation integration for the table of contents is enabled, it is + # always rendered as part of the navigation sidebar on the left. + # https://zensical.org/docs/setup/navigation/#navigation-integration + #"toc.integrate", +] + +# ---------------------------------------------------------------------------- +# You can configure your own logo to be shown in the header using the "logo" +# option in the "theme" subsection. The logo must be a relative path to a file +# in your "docs_dir", e.g., to use `docs/assets/logo.png` you would set: +# ---------------------------------------------------------------------------- +#logo = "assets/logo.png" + +# ---------------------------------------------------------------------------- +# If you don't have a dedicated project logo, you can use a built-in icon from +# the icon sets shipped in Zensical. Please note that the setting lives in a +# different subsection, and that the above take precedence over the icon. +# +# Read more: +# - https://zensical.org/docs/setup/logo-and-icons +# - https://github.com/zensical/ui/tree/master/dist/.icons +# ---------------------------------------------------------------------------- +#[project.theme.icon] +#logo = "lucide/smile" + +# ---------------------------------------------------------------------------- +# In the "font" subsection you can configure the fonts used. By default, fonts +# are loaded from Google Fonts, giving you a wide range of choices from a set +# of suitably licensed fonts. There are options for a normal text font and for +# a monospaced font used in code blocks. +# ---------------------------------------------------------------------------- +#[project.theme.font] +#text = "Inter" +#code = "Jetbrains Mono" + +# ---------------------------------------------------------------------------- +# In the "palette" subsection you can configure options for the color scheme. +# You can configure different color schemes, e.g., to turn on dark mode, +# that the user can switch between. Each color scheme can be further +# customized. +# +# Read more: +# - https://zensical.org/docs/setup/colors/ +# ---------------------------------------------------------------------------- +[[project.theme.palette]] +scheme = "default" +toggle.icon = "lucide/sun" +toggle.name = "Switch to dark mode" + +[[project.theme.palette]] +scheme = "slate" +toggle.icon = "lucide/moon" +toggle.name = "Switch to light mode" + +# ---------------------------------------------------------------------------- +# The "extra" section contains miscellaneous settings. +# ---------------------------------------------------------------------------- +#[[project.extra.social]] +#icon = "fontawesome/brands/github" +#link = "https://github.com/user/repo" + +# ---------------------------------------------------------------------------- +# In this section you can configure the Markdown extensions that are used when +# rendering your documentation. We enable the most useful extensions by default, +# but you can customize this list to your needs. +# +# Read more: +# - https://zensical.org/docs/setup/extensions/ +# ---------------------------------------------------------------------------- +[project.markdown_extensions.abbr] +[project.markdown_extensions.admonition] +[project.markdown_extensions.attr_list] +[project.markdown_extensions.def_list] +[project.markdown_extensions.footnotes] +[project.markdown_extensions.md_in_html] +[project.markdown_extensions.toc] +permalink = true +[project.markdown_extensions.pymdownx.arithmatex] +generic = true +[project.markdown_extensions.pymdownx.betterem] +[project.markdown_extensions.pymdownx.caret] +[project.markdown_extensions.pymdownx.details] +[project.markdown_extensions.pymdownx.emoji] +emoji_generator = "zensical.extensions.emoji.to_svg" +emoji_index = "zensical.extensions.emoji.twemoji" +[project.markdown_extensions.pymdownx.highlight] +anchor_linenums = true +line_spans = "__span" +pygments_lang_class = true +[project.markdown_extensions.pymdownx.inlinehilite] +[project.markdown_extensions.pymdownx.keys] +[project.markdown_extensions.pymdownx.magiclink] +[project.markdown_extensions.pymdownx.mark] +[project.markdown_extensions.pymdownx.smartsymbols] +[project.markdown_extensions.pymdownx.superfences] +custom_fences = [ + { name = "mermaid", class = "mermaid", format = "pymdownx.superfences.fence_code_format" } +] +[project.markdown_extensions.pymdownx.tabbed] +alternate_style = true +combine_header_slug = true +[project.markdown_extensions.pymdownx.tasklist] +custom_checkbox = true +[project.markdown_extensions.pymdownx.tilde] From 2d5a284156f20732d60c7df8b205d935ae07a1c3 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 15:59:46 +0200 Subject: [PATCH 03/15] ci: add Azure Static Web Apps workflow file on-behalf-of: @Azure opensource@microsoft.com --- ...-static-web-apps-purple-bush-012fe8010.yml | 46 +++++++++++++++++++ 1 file changed, 46 insertions(+) create mode 100644 .github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml diff --git a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml new file mode 100644 index 0000000..5c2cec7 --- /dev/null +++ b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml @@ -0,0 +1,46 @@ +name: Azure Static Web Apps CI/CD + +on: + push: + branches: + - feature/zensible + pull_request: + types: [opened, synchronize, reopened, closed] + branches: + - feature/zensible + +jobs: + build_and_deploy_job: + if: github.event_name == 'push' || (github.event_name == 'pull_request' && github.event.action != 'closed') + runs-on: ubuntu-latest + name: Build and Deploy Job + steps: + - uses: actions/checkout@v3 + with: + submodules: true + lfs: false + - name: Build And Deploy + id: builddeploy + uses: Azure/static-web-apps-deploy@v1 + with: + azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} + repo_token: ${{ secrets.GITHUB_TOKEN }} # Used for Github integrations (i.e. PR comments) + action: "upload" + ###### Repository/Build Configurations - These values can be configured to match your app requirements. ###### + # For more information regarding Static Web App workflow configurations, please visit: https://aka.ms/swaworkflowconfig + app_location: "/" # App source code path + api_location: "" # Api source code path - optional + output_location: "" # Built app content directory - optional + ###### End of Repository/Build Configurations ###### + + close_pull_request_job: + if: github.event_name == 'pull_request' && github.event.action == 'closed' + runs-on: ubuntu-latest + name: Close Pull Request Job + steps: + - name: Close Pull Request + id: closepullrequest + uses: Azure/static-web-apps-deploy@v1 + with: + azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} + action: "close" From f063923f469973f347d56acb770de4f305ff0e36 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 16:01:41 +0200 Subject: [PATCH 04/15] Update CI for SWA --- ...-static-web-apps-purple-bush-012fe8010.yml | 99 ++++++++++--------- 1 file changed, 53 insertions(+), 46 deletions(-) diff --git a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml index 5c2cec7..78f595d 100644 --- a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml +++ b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml @@ -1,46 +1,53 @@ -name: Azure Static Web Apps CI/CD - -on: - push: - branches: - - feature/zensible - pull_request: - types: [opened, synchronize, reopened, closed] - branches: - - feature/zensible - -jobs: - build_and_deploy_job: - if: github.event_name == 'push' || (github.event_name == 'pull_request' && github.event.action != 'closed') - runs-on: ubuntu-latest - name: Build and Deploy Job - steps: - - uses: actions/checkout@v3 - with: - submodules: true - lfs: false - - name: Build And Deploy - id: builddeploy - uses: Azure/static-web-apps-deploy@v1 - with: - azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} - repo_token: ${{ secrets.GITHUB_TOKEN }} # Used for Github integrations (i.e. PR comments) - action: "upload" - ###### Repository/Build Configurations - These values can be configured to match your app requirements. ###### - # For more information regarding Static Web App workflow configurations, please visit: https://aka.ms/swaworkflowconfig - app_location: "/" # App source code path - api_location: "" # Api source code path - optional - output_location: "" # Built app content directory - optional - ###### End of Repository/Build Configurations ###### - - close_pull_request_job: - if: github.event_name == 'pull_request' && github.event.action == 'closed' - runs-on: ubuntu-latest - name: Close Pull Request Job - steps: - - name: Close Pull Request - id: closepullrequest - uses: Azure/static-web-apps-deploy@v1 - with: - azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} - action: "close" +name: Azure Static Web Apps CI/CD + +on: + push: + branches: + - feature/zensible + pull_request: + types: [opened, synchronize, reopened, closed] + branches: + - feature/zensible + +jobs: + build_and_deploy_job: + if: github.event_name == 'push' || (github.event_name == 'pull_request' && github.event.action != 'closed') + runs-on: ubuntu-latest + name: Build and Deploy Job + steps: + - uses: actions/checkout@v3 + with: + submodules: true + lfs: false + - uses: actions/setup-python@v6 + with: + python-version: 3.x + - run: pip install zensical + - run: zensical build --clean + - name: Build And Deploy + id: builddeploy + uses: Azure/static-web-apps-deploy@v1 + with: + azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} + repo_token: ${{ secrets.GITHUB_TOKEN }} # Used for Github integrations (i.e. PR comments) + action: "upload" + ###### Repository/Build Configurations - These values can be configured to match your app requirements. ###### + # For more information regarding Static Web App workflow configurations, please visit: https://aka.ms/swaworkflowconfig + app_location: "site" + api_location: "" + skip_app_build: true + skip_api_build: true + output_location: "" + ###### End of Repository/Build Configurations ###### + + close_pull_request_job: + if: github.event_name == 'pull_request' && github.event.action == 'closed' + runs-on: ubuntu-latest + name: Close Pull Request Job + steps: + - name: Close Pull Request + id: closepullrequest + uses: Azure/static-web-apps-deploy@v1 + with: + azure_static_web_apps_api_token: ${{ secrets.AZURE_STATIC_WEB_APPS_API_TOKEN_PURPLE_BUSH_012FE8010 }} + action: "close" From 1f6d3a652de8f90401db4ab8ac7989cf9b4c1e10 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 16:13:10 +0200 Subject: [PATCH 05/15] Move content from index.njk to index.md --- docs/index.md | 32 +++++++++++++++++++++++++++++ docs/index.njk | 56 -------------------------------------------------- 2 files changed, 32 insertions(+), 56 deletions(-) delete mode 100644 docs/index.njk diff --git a/docs/index.md b/docs/index.md index b50d7a1..80b4bc4 100644 --- a/docs/index.md +++ b/docs/index.md @@ -8,6 +8,38 @@ icon: lucide/rocket documentation still lives at https://telemetrydeck.com/docs/ for now. +--- + +## Welcome to TelemetryDeck + +TelemetryDeck helps you understand how users interact with your application through privacy-focused analytics. With just an SDK integration, you'll get valuable insights automatically – no complex configuration required. + +### Getting Started in 2 simple steps + + +- **Choose and install** the SDK for your platform from the guides below +- **Deploy your app** to start collecting data + +Once your updated app is in users' hands, TelemetryDeck will begin collecting data. It may take some time before you see meaningful insights, depending on your app's usage. + +### What's next after setup? + +After setting up the SDK and deploying your app, your most important next step is to learn how to use the dashboard to analyze your data: + +- [Analytics Walkthrough](/basics) - Learn how to navigate TelemetryDeck, interpret insights, and use analytics to make data-driven decisions that improve your app and grow your user base. + + +### Documentation Feedback + +If you find an error or feel like the documentation could be improved somewhat, we'd love +to hear from you! Either directly submit a change request with the buttons on each page, +or open an issue in our Docs GitHub Repository. + +The [documentation guide](/articles/documentation) explains all markdown and +additional features you can use while writing documentation for TelemetryDeck. + + + ---- # Get started diff --git a/docs/index.njk b/docs/index.njk deleted file mode 100644 index 398e42f..0000000 --- a/docs/index.njk +++ /dev/null @@ -1,56 +0,0 @@ ----json -{ -"title": "Quick Start Guide", -"lead": "Set up TelemetryDeck in minutes and start gaining insights into your app's performance", -"tags": "intro", -"categoryOrder": -9000, -"searchEngineDescription":"With this Quick Start Guide, you can set up TelemetryDeck's app analytics in minutes and start gaining insights into your app's performance." -} ---- - -

Welcome to TelemetryDeck

- -

TelemetryDeck helps you understand how users interact with your application through privacy-focused analytics. With just an SDK integration, you'll get valuable insights automatically – no complex configuration required.

- -

Getting Started in 2 simple steps

- -
    -
  1. Choose and install the SDK for your platform from the guides below
  2. -
  3. Deploy your app to start collecting data
  4. -
- -

Once your updated app is in users' hands, TelemetryDeck will begin collecting data. It may take some time before you see meaningful insights, depending on your app's usage.

- -{% include "docs/featured.njk" %} - -

What's next after setup?

- -

After setting up the SDK and deploying your app, your most important next step is to learn how to use the dashboard to analyze your data:

- -
-
-
- -
-

- - πŸ“Š Analytics Walkthrough -

-

Learn how to navigate TelemetryDeck, interpret insights, and use analytics to make data-driven decisions that improve your app and grow your user base.

-

- Start here to get real value from your analytics - β†’ -

-
-
-
-
- -

Documentation Feedback

- -

If you find an error or feel like the documentation could be improved somewhat, we'd love -to hear from you! Either directly submit a change request with the buttons on each page, -or open an issue in our Docs GitHub Repository.

- -

The documentation guide explains all markdown and -additional features you can use while writing documentation for TelemetryDeck.

From f897f27f92da63df84b2da484bd8ec6830c0846e Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 16:15:40 +0200 Subject: [PATCH 06/15] Update Repo URL --- zensical.toml | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/zensical.toml b/zensical.toml index be1233c..c0743a8 100644 --- a/zensical.toml +++ b/zensical.toml @@ -8,6 +8,9 @@ [project] + +repo_url = "https://github.com/TelemetryDeck/docs" + # The site_name is shown in the page header and the browser window title # # Read more: https://zensical.org/docs/setup/basics/#site_name @@ -122,13 +125,13 @@ features = [ # will generate an edit button for the page. This works for common # repository hosting services. # https://zensical.org/docs/setup/repository/#content-actions - #"content.action.edit", + "content.action.edit", # If you have a repository configured and turn on this feature, Zensical # will generate a button that allows the user to view the Markdown # code for the current page. # https://zensical.org/docs/setup/repository/#content-actions - #"content.action.view", + "content.action.view", # Code annotations allow you to add an icon with a tooltip to your # code blocks to provide explanations at crucial points. From eb2ae3a07a83ffdc08948fbbb3864ce1645f5918 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 16:21:53 +0200 Subject: [PATCH 07/15] Rudimentary Color scheme --- zensical.toml | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/zensical.toml b/zensical.toml index c0743a8..3ffba6d 100644 --- a/zensical.toml +++ b/zensical.toml @@ -291,14 +291,25 @@ features = [ # - https://zensical.org/docs/setup/colors/ # ---------------------------------------------------------------------------- [[project.theme.palette]] +media = "(prefers-color-scheme)" +toggle.icon = "lucide/sun-moon" +toggle.name = "Switch to light mode" + +[[project.theme.palette]] +media = "(prefers-color-scheme: light)" scheme = "default" toggle.icon = "lucide/sun" toggle.name = "Switch to dark mode" +primary = "deep orange" +accent = "orange" [[project.theme.palette]] +media = "(prefers-color-scheme: dark)" scheme = "slate" toggle.icon = "lucide/moon" -toggle.name = "Switch to light mode" +toggle.name = "Switch to system preference" +primary = "orange" +accent = "deep orange" # ---------------------------------------------------------------------------- # The "extra" section contains miscellaneous settings. From b9dececeb3c6095b5213c949ca7438058c7552db Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 17:19:35 +0200 Subject: [PATCH 08/15] Add TelemetryDeck App Analytics --- .../azure-static-web-apps-purple-bush-012fe8010.yml | 5 +++++ overrides/partials/integrations/analytics/telemetrydeck.html | 4 ++++ zensical.toml | 5 ++++- 3 files changed, 13 insertions(+), 1 deletion(-) create mode 100644 overrides/partials/integrations/analytics/telemetrydeck.html diff --git a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml index 78f595d..593baec 100644 --- a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml +++ b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml @@ -19,6 +19,11 @@ jobs: with: submodules: true lfs: false + - name: Replace TelemetryDeck App ID + env: + TELEMETRYDECK_APP_ID: ${{ secrets.TELEMETRYDECK_APP_ID }} + run: | + sed -i "s|#TELEMETRYDECK_APP_ID#|${TELEMETRYDECK_APP_ID}|g" overrides/partials/integrations/analytics/telemetrydeck.html - uses: actions/setup-python@v6 with: python-version: 3.x diff --git a/overrides/partials/integrations/analytics/telemetrydeck.html b/overrides/partials/integrations/analytics/telemetrydeck.html new file mode 100644 index 0000000..3ec627d --- /dev/null +++ b/overrides/partials/integrations/analytics/telemetrydeck.html @@ -0,0 +1,4 @@ + diff --git a/zensical.toml b/zensical.toml index 3ffba6d..01736c1 100644 --- a/zensical.toml +++ b/zensical.toml @@ -86,7 +86,7 @@ Copyright © 2026 TelemetryDeck GmbH # Read more: # - https://zensical.org/docs/customization/#extending-the-theme # -#custom_dir = "overrides" +custom_dir = "overrides" # With the "favicon" option you can set your own image to use as the icon # browsers will use in the browser title bar or tab bar. The path provided @@ -318,6 +318,9 @@ accent = "deep orange" #icon = "fontawesome/brands/github" #link = "https://github.com/user/repo" +[project.extra.analytics] +provider = "telemetrydeck" + # ---------------------------------------------------------------------------- # In this section you can configure the Markdown extensions that are used when # rendering your documentation. We enable the most useful extensions by default, From 82c9e077515a1682d661c8934cd19defa15d83cc Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 17:35:32 +0200 Subject: [PATCH 09/15] Convert warnings with regex --- docs/api/api-query-from-insight.md | 6 ++---- docs/api/api-run-query.md | 6 ++---- docs/api/api-token.md | 6 ++---- docs/guides/javascript-setup.md | 11 ++++------- docs/ingest/v1.md | 6 ++---- docs/integrations/revenuecat.md | 6 ++---- docs/tql/aggregators.md | 6 ++---- docs/tql/dimensionSpec.md | 6 ++---- docs/tql/funnels.md | 6 ++---- 9 files changed, 20 insertions(+), 39 deletions(-) diff --git a/docs/api/api-query-from-insight.md b/docs/api/api-query-from-insight.md index 543927d..36b58b0 100644 --- a/docs/api/api-query-from-insight.md +++ b/docs/api/api-query-from-insight.md @@ -6,11 +6,9 @@ description: Using the TelemetryDeck API, you can retrieve the query that is use lead: Using the TelemetryDeck API, you can retrieve the query that is used in an insight --- -{% notewarning "Paid plans only" %} +!!! warning "Paid plans only" -API access β€” including retrieving an insight's query β€” is available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and you'll be able to generate a personal access token and use the API. - -{% endnotewarning %} + API access β€” including retrieving an insight's query β€” is available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and you'll be able to generate a personal access token and use the API. ## Authorization diff --git a/docs/api/api-run-query.md b/docs/api/api-run-query.md index f7e6c04..c4d61de 100644 --- a/docs/api/api-run-query.md +++ b/docs/api/api-run-query.md @@ -7,11 +7,9 @@ lead: Using the TelemetryDeck API, you can run a query and retrieve its results order: 2 --- -{% notewarning "Paid plans only" %} +!!! warning "Paid plans only" -API access β€” including running queries β€” is available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and you'll be able to generate a personal access token and run queries. - -{% endnotewarning %} + API access β€” including running queries β€” is available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and you'll be able to generate a personal access token and run queries. ## Authorization diff --git a/docs/api/api-token.md b/docs/api/api-token.md index a13152c..c062aeb 100644 --- a/docs/api/api-token.md +++ b/docs/api/api-token.md @@ -7,11 +7,9 @@ lead: To interact with the TelemetryDeck API, you need a personal access token ( order: 1 --- -{% notewarning "Paid plans only" %} +!!! warning "Paid plans only" -Personal access tokens are available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and the feature will become available in the dashboard. - -{% endnotewarning %} + Personal access tokens are available on TelemetryDeck's paid plans. If your organization is on the free plan, upgrade your plan first and the feature will become available in the dashboard. ## Generating a Personal Access Token diff --git a/docs/guides/javascript-setup.md b/docs/guides/javascript-setup.md index e896f9b..cfa7060 100644 --- a/docs/guides/javascript-setup.md +++ b/docs/guides/javascript-setup.md @@ -87,14 +87,11 @@ If can't specify a user identifier at initialization, you can set it later by se Please note that `td.signal` is an async function that returns a promise. -{% notewarning "Special treatment for frameworks" %} +!!! warning "Special treatment for frameworks" -Some frameworks, like Svelte, don't need `crypto` and node.js. Here are some tips on how to implement TelemetryDeck when using some of these special frameworks: - -- The initialization should happen once, and the TD object should be passed around in a service or singleton. -- The `td.send` function should be used to send signals, either automatically in a router-like object or on a per-feature basis. - -{% endnotewarning %} + Some frameworks, like Svelte, don't need `crypto` and node.js. Here are some tips on how to implement TelemetryDeck when using some of these special frameworks: + - The initialization should happen once, and the TD object should be passed around in a service or singleton. + - The `td.send` function should be used to send signals, either automatically in a router-like object or on a per-feature basis. ### Advanced initialization options diff --git a/docs/ingest/v1.md b/docs/ingest/v1.md index 8a79b77..913b9c3 100644 --- a/docs/ingest/v1.md +++ b/docs/ingest/v1.md @@ -6,11 +6,9 @@ order: 99999 searchEngineDescription: A reference of all properties of the Signal Ingestion API. Note -- We’re continuing to host ingest v1, but officially deprecating it and recommending using v2. --- -{% notewarning "Deprecated" %} +!!! warning "Deprecated" -While we're continuing to host ingest v1, we're officially deprecating it and recommending our customers to use the [v2 API](/docs/ingest/v2/) instead. The v2 API is more flexible, has better support for custom data, and is more future proof. - -{% endnotewarning %} + While we're continuing to host ingest v1, we're officially deprecating it and recommending our customers to use the [v2 API](/docs/ingest/v2/) instead. The v2 API is more flexible, has better support for custom data, and is more future proof. This article will first show the minimal structure needed for a signal to send, and then talk about some of the optional extensions. diff --git a/docs/integrations/revenuecat.md b/docs/integrations/revenuecat.md index bf80a5a..427f6ed 100644 --- a/docs/integrations/revenuecat.md +++ b/docs/integrations/revenuecat.md @@ -84,11 +84,9 @@ Here's what's going on in the above example 2. We then manually set a default user for TelemetryDeck. This allows us to later retrieve a hashed version of the user identifier. 3. Finally, we configure RevenueCat and set up the necessary user attributes. -{% notewarning "You need to keep user identifiers in sync" %} +!!! warning "You need to keep user identifiers in sync" -Whenever you update your TelemetryDeck user identifier, you'll also need to update the user identifier in RevenueCat's `$telemetryDeckUserId` user attribute. - -{% endnotewarning %} + Whenever you update your TelemetryDeck user identifier, you'll also need to update the user identifier in RevenueCat's `$telemetryDeckUserId` user attribute. ## Setting up RevenueCat's TelemetryDeck Integration diff --git a/docs/tql/aggregators.md b/docs/tql/aggregators.md index fddc53d..818d02d 100644 --- a/docs/tql/aggregators.md +++ b/docs/tql/aggregators.md @@ -117,11 +117,9 @@ Also, you can use post aggregators to do union, intersection or difference on sk `cardinality` computes the cardinality of a dimension. -{% notewarning "Deprecated" %} +!!! warning "Deprecated" -This aggregator is deprecated. Use `thetaSketch` instead. - -{% endnotewarning %} + This aggregator is deprecated. Use `thetaSketch` instead. ```json { diff --git a/docs/tql/dimensionSpec.md b/docs/tql/dimensionSpec.md index 28cd830..1f8b1af 100644 --- a/docs/tql/dimensionSpec.md +++ b/docs/tql/dimensionSpec.md @@ -9,11 +9,9 @@ The default DimensionSpec returns dimension values as is and optionally renames If an extraction function is set, it returns dimension values transformed using the given extraction function. -{% notewarning "What is a dimension?" %} +!!! warning "What is a dimension?" -TelemetryDecks Query Language is based on Apache Druid. In Druid, a dimension is a named field in your data used for filtering, grouping, or joining - typically string or categorical values. - -{% endnotewarning %} + TelemetryDecks Query Language is based on Apache Druid. In Druid, a dimension is a named field in your data used for filtering, grouping, or joining - typically string or categorical values. ## Default DimensionSpec diff --git a/docs/tql/funnels.md b/docs/tql/funnels.md index 5b7d9b5..b92d15c 100644 --- a/docs/tql/funnels.md +++ b/docs/tql/funnels.md @@ -13,11 +13,9 @@ searchEngineDescription: This is a quick overview on how to create funnels, or c order: 1000 --- -{% notewarning "Deprecated" %} +!!! warning "Deprecated" -The content below is deprecated and will be removed in the future. Please refer to the [new documentation](/docs/tql/funnel/) instead. - -{% endnotewarning %} + The content below is deprecated and will be removed in the future. Please refer to the [new documentation](/docs/tql/funnel/) instead. This article explains the thought process on how to create funnel-type queries; scroll to the bottom for a complete example. From 99f7b35d60322cf2829b5bc75d8f7911fd23d78b Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 17:36:51 +0200 Subject: [PATCH 10/15] Convert infos with regex --- docs/articles/apple-app-privacy.md | 10 ++++------ docs/articles/documentation.md | 14 ++++++-------- docs/guides/javascript-setup.md | 16 +++++++--------- docs/guides/web-setup.md | 10 ++++------ docs/integrations/revenuecat.md | 14 +++++--------- docs/tql/aggregators.md | 8 +++----- docs/tql/funnels.md | 6 ++---- docs/tql/query.md | 8 +++----- 8 files changed, 34 insertions(+), 52 deletions(-) diff --git a/docs/articles/apple-app-privacy.md b/docs/articles/apple-app-privacy.md index 88c4cb1..3b4b959 100644 --- a/docs/articles/apple-app-privacy.md +++ b/docs/articles/apple-app-privacy.md @@ -34,14 +34,12 @@ In the second screen, scroll down until you see the **Identifiers** section. In TelemetryDeck's **default mode**, with no user identifier specified, check the **Device ID** checkmark. This is what identifies individual users to TelemetryDeck. -{% noteinfo "Other Types of Identifiers" %} +!!! warning "Other Types of Identifiers" -In case you use TelemetryDeck in a more advanced way where you supply a custom user identifier, you'll need to think about this for a second: + In case you use TelemetryDeck in a more advanced way where you supply a custom user identifier, you'll need to think about this for a second: -- If you instead specify a User Identifier such as email address or username to TelemetryDeck, check instead the **User ID** checkmark. The identifier is only transmitted as a hash, but it still counts as a user identifier. -- If you instead are purposefully disabling user tracking by handing the same string to TelemetryDeck for each user, you don't need to check any of the checkboxes in the **Identifiers** section. - -{% endnoteinfo %} + - If you instead specify a User Identifier such as email address or username to TelemetryDeck, check instead the **User ID** checkmark. The identifier is only transmitted as a hash, but it still counts as a user identifier. + - If you instead are purposefully disabling user tracking by handing the same string to TelemetryDeck for each user, you don't need to check any of the checkboxes in the **Identifiers** section. ### Usage Data diff --git a/docs/articles/documentation.md b/docs/articles/documentation.md index 8428599..ef8a8c0 100644 --- a/docs/articles/documentation.md +++ b/docs/articles/documentation.md @@ -79,16 +79,14 @@ Organizational tags like `docs` and `guides` are automatically applied. Use the - The experience level of the reader (`beginner`, `intermediate`, `advanced`) - The type of query (`filter`, `cohorts`, etc.) -{% noteinfo "You don't need to add 'docs' and 'articles' as tags" %} +!!! warning "You don't need to add 'docs' and 'articles' as tags" -All markdown files in the `docs` repository automatically get the `docs` tag applied to them (by `docs.11tydata.js`). In addition, the respective directories apply their own tags as well: + All markdown files in the `docs` repository automatically get the `docs` tag applied to them (by `docs.11tydata.js`). In addition, the respective directories apply their own tags as well: -- Files in the `intro` directory get the `intro` tag applied. -- Files in the `guides` directory get the `guides` tag applied. -- Files in the `articles` directory get the `articles` tag applied. -- Files in the `api` directory get the `api` tag applied. - -{% endnoteinfo %} + - Files in the `intro` directory get the `intro` tag applied. + - Files in the `guides` directory get the `guides` tag applied. + - Files in the `articles` directory get the `articles` tag applied. + - Files in the `api` directory get the `api` tag applied. ### Order diff --git a/docs/guides/javascript-setup.md b/docs/guides/javascript-setup.md index cfa7060..691a19a 100644 --- a/docs/guides/javascript-setup.md +++ b/docs/guides/javascript-setup.md @@ -14,17 +14,15 @@ order: 300 The TelemetryDeck SDK has no dependencies and supports **modern evergreen browsers** and **modern versions of Node.js** with support for [cryptography](https://caniuse.com/cryptography). -{% noteinfo "There are multiple ways of adding TelemetryDeck to a web site" %} +!!! warning "There are multiple ways of adding TelemetryDeck to a web site" -There are different tutorials you should read depending on your use case. + There are different tutorials you should read depending on your use case. -- The [TelemetryDeck Web SDK](/docs/guides/web-setup) is a quick and easy way to include web analytics into your website. This is fantastic for blogs, landing pages, static websites, and content-driven websites. - -- If you are building a JavaScript application – a Progressive Web App written in React, Vue, Angular, Svelte, Ember, or mobile or desktop apps written with React Native, Electron, Ionic, and so on, you should read this guide. - -[Our blog post](/blog/js-sdk-2-0/) explains the differences between the two SDKs in more detail. - -{% endnoteinfo %} + - The [TelemetryDeck Web SDK](/docs/guides/web-setup) is a quick and easy way to include web analytics into your website. This is fantastic for blogs, landing pages, static websites, and content-driven websites. + + - If you are building a JavaScript application – a Progressive Web App written in React, Vue, Angular, Svelte, Ember, or mobile or desktop apps written with React Native, Electron, Ionic, and so on, you should read this guide. + + [Our blog post](/blog/js-sdk-2-0/) explains the differences between the two SDKs in more detail. ## Set up diff --git a/docs/guides/web-setup.md b/docs/guides/web-setup.md index 0a97303..42ee7e9 100644 --- a/docs/guides/web-setup.md +++ b/docs/guides/web-setup.md @@ -109,14 +109,12 @@ This means that the Web SDK will recognize recurring users on the same day on th ## If you're a developer -{% noteinfo "There are multiple ways of adding TelemetryDeck to a web site" %} +!!! warning "There are multiple ways of adding TelemetryDeck to a web site" -There are different tutorials you should read depending on your use case. + There are different tutorials you should read depending on your use case. -- If you are building a **JavaScript application or PWA using node package manager**, you should read the [Node Package Setup Guide](/docs/guides/javascript-setup). -- If you are building a **website or blog**, and want to include TelemetryDeck with a simple script tag similar to Google Analytics or Plausible Analytics, you should read this guide. - -{% endnoteinfo %} + - If you are building a **JavaScript application or PWA using node package manager**, you should read the [Node Package Setup Guide](/docs/guides/javascript-setup). + - If you are building a **website or blog**, and want to include TelemetryDeck with a simple script tag similar to Google Analytics or Plausible Analytics, you should read this guide. ## What to do next diff --git a/docs/integrations/revenuecat.md b/docs/integrations/revenuecat.md index 427f6ed..8a4e73b 100644 --- a/docs/integrations/revenuecat.md +++ b/docs/integrations/revenuecat.md @@ -15,11 +15,9 @@ RevenueCat pairs excellently with TelemetryDeck – use TelemetryDeck to improv With this integration, you can import your RevenueCat events into TelemetryDeck, and see everything on one dashboard. We'll be using RevenueCat's _Webhooks_ feature to pass on their data to TelemetryDeck. -{% noteinfo "Read the announcement" %} +!!! warning "Read the announcement" -Our [announcement blog post](https://telemetrydeck.com/blog/revenuecat-integration/) shows you what to expect, how to use the new revenue dashboard, and gives examples on what to do with your revenue data. - -{% endnoteinfo %} + Our [announcement blog post](https://telemetrydeck.com/blog/revenuecat-integration/) shows you what to expect, how to use the new revenue dashboard, and gives examples on what to do with your revenue data. ## Installing RevenueCat and TelemetryDeck @@ -35,13 +33,11 @@ RevenueCat has a concept of **user attributes**. Our goal is to set two new user - `$telemetryDeckAppId`: This attribute should be set to your TelemetryDeck App ID, the same one you pass into the TelemetryDeck SDK for initialization. - `$telemetryDeckUserId`: This attribute needs to be the **already-hashed user identifier** that TelemetryDeck is using. -{% noteinfo "RevenueCat gets the hashed version of the TelemetryDeck User Identifier" %} - -While the TelemetryDeck SDK usually takes care of hashing for you, you'll need to extract the identifier after it's been hashed and pass that on to RevenueCat. Only then will the final identifiers in your TelemetryDeck dashboard match up. +!!! warning "RevenueCat gets the hashed version of the TelemetryDeck User Identifier" -If your version of the TelemetryDeck SDK does not expose a function to vend the hashed user identifier, you can hash it yourself using something like `SHA256(user_id + salt)`. + While the TelemetryDeck SDK usually takes care of hashing for you, you'll need to extract the identifier after it's been hashed and pass that on to RevenueCat. Only then will the final identifiers in your TelemetryDeck dashboard match up. -{% endnoteinfo %} + If your version of the TelemetryDeck SDK does not expose a function to vend the hashed user identifier, you can hash it yourself using something like `SHA256(user_id + salt)`. ### iOS diff --git a/docs/tql/aggregators.md b/docs/tql/aggregators.md index 818d02d..5be6e2b 100644 --- a/docs/tql/aggregators.md +++ b/docs/tql/aggregators.md @@ -97,13 +97,11 @@ A theta sketch gives you the number of unique values that a dimension has in you Theta sketches are a probabilistic data structure used for the [count-distinct problem](https://en.wikipedia.org/wiki/Count-distinct_problem). They allow us to quickly count elements in sets, such as the set of users in the aggregation buckets -{% noteinfo "More on ThetaSketches" %} +!!! warning "More on ThetaSketches" -A Theta sketch object can be thought of as a Set data structure. At query time, sketches are read and aggregated (set unioned) together. By default, you receive the estimate of the number of unique entries in the sketch object. + A Theta sketch object can be thought of as a Set data structure. At query time, sketches are read and aggregated (set unioned) together. By default, you receive the estimate of the number of unique entries in the sketch object. -Also, you can use post aggregators to do union, intersection or difference on sketch columns in the same row. This means you can create distinct sets of users and compare them against each other. This is necessary for retention and funnel queries. - -{% endnoteinfo %} + Also, you can use post aggregators to do union, intersection or difference on sketch columns in the same row. This means you can create distinct sets of users and compare them against each other. This is necessary for retention and funnel queries. ```json { diff --git a/docs/tql/funnels.md b/docs/tql/funnels.md index b92d15c..2aca4ad 100644 --- a/docs/tql/funnels.md +++ b/docs/tql/funnels.md @@ -112,11 +112,9 @@ For our filters, we want to grab all signals that might be relevant for the funn We're going to use aggregations to split up (or aggregate) the signals into different buckets, and count them by `clientUser` which is the field for TelemetryDeck's user identifier. We're using Theta Sketches to count the number of different users for the funnel stage. -{% noteinfo "What's a theta sketch?" %} +!!! warning "What's a theta sketch?" -A theta sketch is a probabilistic data structure used for the [count-distinct problem](https://en.wikipedia.org/wiki/Count-distinct_problem). It allows us to quickly count elements in sets, such as the set of users in the aggregation buckets. - -{% endnoteinfo %} + A theta sketch is a probabilistic data structure used for the [count-distinct problem](https://en.wikipedia.org/wiki/Count-distinct_problem). It allows us to quickly count elements in sets, such as the set of users in the aggregation buckets. ```json [ diff --git a/docs/tql/query.md b/docs/tql/query.md index 292ad82..2119a4e 100644 --- a/docs/tql/query.md +++ b/docs/tql/query.md @@ -11,13 +11,11 @@ Most queries for TelemetryDeck can be constructed using the regular Insight Edit You can use the TQL Query Builder to construct your query, or you can write it by hand. The minimum required properties are `granularity`, `dataSource` and `queryType`. The following sections describe the properties of the query object. -{% noteinfo "This looks curiously familiar" %} +!!! warning "This looks curiously familiar" -If you've ever worked with [Apache Druid](https://druid.apache.org), you'll notice a lot of similarities between TQL and Druid's native query language. This is because TQL is a superset of Druid's native query language, and TQL queries are compiled down into Druid queries before they're executed. + If you've ever worked with [Apache Druid](https://druid.apache.org), you'll notice a lot of similarities between TQL and Druid's native query language. This is because TQL is a superset of Druid's native query language, and TQL queries are compiled down into Druid queries before they're executed. -Druid queries can do various things that TQL queries can't do for security and privacy reasons, and Druid queries are also more verbose. To get into the fine details of Druid's query language, please check the [Apache Druid Documentation](https://druid.apache.org/docs/latest/querying/). - -{% endnoteinfo %} + Druid queries can do various things that TQL queries can't do for security and privacy reasons, and Druid queries are also more verbose. To get into the fine details of Druid's query language, please check the [Apache Druid Documentation](https://druid.apache.org/docs/latest/querying/). This example timeseries query returns the number of users per week: From 44173b82c54b6762ac2ae9c425ef701a1b4e2b12 Mon Sep 17 00:00:00 2001 From: Daniel Jilg Date: Mon, 4 May 2026 17:43:37 +0200 Subject: [PATCH 11/15] Update logo and favicon --- {images => docs/assets}/MAU_1.png | Bin {images => docs/assets}/MAU_2.png | Bin {images => docs/assets}/MAU_3.png | Bin {images => docs/assets}/MAU_4.png | Bin {images => docs/assets}/MAU_5.png | Bin .../assets}/Notebooks-Overview.png | Bin .../assets}/Notebooks-TQL-Live-Preview.png | Bin .../assets}/Peerigon_Logo_RGB_no_padding.svg | 0 {images => docs/assets}/Referrers_1.png | Bin {images => docs/assets}/Referrers_2.png | Bin {images => docs/assets}/Referrers_3a.png | Bin {images => docs/assets}/Referrers_3b.png | Bin {images => docs/assets}/Referrers_4.png | Bin {images => docs/assets}/Referrers_5.png | Bin .../assets}/Screenshot_SystemVersion.png | Bin {images => docs/assets}/aarrr-framework.png | Bin .../assets}/acquisition-active-vs-new.png | Bin .../acquisition-by-time-last-weeks.png | Bin .../assets}/acquisition-by-time.png | Bin .../acquisition-device-distribution.png | Bin .../acquisition-geographic-distribution.png | Bin .../assets}/acquisition-new-users.png | Bin .../assets}/activation-activated-users.png | Bin .../assets}/activation-by-time.png | Bin .../activation-device-distribution.png | Bin .../activation-geographic-distribution.png | Bin .../assets}/anonymization-display-image.jpg | Bin {images => docs/assets}/bar-chart.PNG | Bin {images => docs/assets}/compact_wide_mode.PNG | Bin .../assets}/create-new-insight.png | Bin .../assets}/daily-active-users-example.png | Bin .../assets}/dashboard-acquisition.png | Bin {images => docs/assets}/dashboard-custom.png | Bin .../assets}/dashboard-exploring-details.png | Bin .../assets}/dashboard-filtering-data.png | Bin .../assets}/dashboard-main-nav.png | Bin .../assets}/dashboard-notebooks.png | Bin .../assets}/dashboard-overview.png | Bin .../assets}/dashboard-signal-types.png | Bin {images => docs/assets}/display_mode.PNG | Bin {images => docs/assets}/donut-chart.PNG | Bin .../assets}/duration-signal-01.png | Bin .../assets}/duration-signal-02.png | Bin .../assets}/duration-signal-03.png | Bin .../assets}/edit-dashboard-name.png | Bin {images => docs/assets}/faq.jpg | Bin docs/assets/favicon.svg | 1 + {images => docs/assets}/filter_example.png | Bin {images => docs/assets}/filter_location.png | Bin {images => docs/assets}/funnel_type.PNG | Bin {images => docs/assets}/funnels_example.png | Bin .../assets}/funnels_set_filters.jpg | Bin {images => docs/assets}/line-chart.PNG | Bin .../assets}/location-create-dashboard.png | Bin .../assets}/location-edit-group.PNG | Bin .../assets}/location-edit-insight.png | Bin {images => docs/assets}/login-mask.png | Bin docs/assets/logo.svg | 31 ++++++++++++++++++ .../assets}/metrics-accessibility.png | Bin {images => docs/assets}/metrics-devices.png | Bin {images => docs/assets}/metrics-errors.png | Bin .../assets}/metrics-localization.png | Bin {images => docs/assets}/metrics-versions.png | Bin .../assets}/notebooks-video-thumbnail.png | Bin {images => docs/assets}/privacy-overview.png | Bin .../assets}/purchases-privacy-box.png | Bin {images => docs/assets}/rc-td-1.png | Bin {images => docs/assets}/rc-td-2.png | Bin {images => docs/assets}/retention-by-time.png | Bin .../assets}/retention-device-distribution.png | Bin .../retention-geographic-distribution.png | Bin .../assets}/retention-returning-users.png | Bin .../assets}/revenuecat_webhook_config.png | Bin .../assets}/system-versions-example.png | Bin {images => docs/assets}/table-chart.PNG | Bin {images => docs/assets}/test_mode.png | Bin {images => docs/assets}/typedigital.png | Bin .../assets}/update_next_major_version.png | Bin {images => docs/assets}/update_package.png | Bin .../assets}/xcode-swift-package.png | Bin .../assets}/xcode-swift-package1.png | Bin .../assets}/xcode-swift-package2.png | Bin {images => docs/assets}/yt-4-minute-setup.png | Bin {images => docs/assets}/yt-app-analytics.png | Bin .../assets}/yt-app-store-connect.png | Bin .../assets}/yt-built-in-charts.png | Bin {images => docs/assets}/yt-custom-charts.png | Bin zensical.toml | 4 +-- 88 files changed, 34 insertions(+), 2 deletions(-) rename {images => docs/assets}/MAU_1.png (100%) rename {images => docs/assets}/MAU_2.png (100%) rename {images => docs/assets}/MAU_3.png (100%) rename {images => docs/assets}/MAU_4.png (100%) rename {images => docs/assets}/MAU_5.png (100%) rename {images => docs/assets}/Notebooks-Overview.png (100%) rename {images => docs/assets}/Notebooks-TQL-Live-Preview.png (100%) rename {images => docs/assets}/Peerigon_Logo_RGB_no_padding.svg (100%) rename {images => docs/assets}/Referrers_1.png (100%) rename {images => docs/assets}/Referrers_2.png (100%) rename {images => docs/assets}/Referrers_3a.png (100%) rename {images => docs/assets}/Referrers_3b.png (100%) rename {images => docs/assets}/Referrers_4.png (100%) rename {images => docs/assets}/Referrers_5.png (100%) rename {images => docs/assets}/Screenshot_SystemVersion.png (100%) rename {images => docs/assets}/aarrr-framework.png (100%) rename {images => docs/assets}/acquisition-active-vs-new.png (100%) rename {images => docs/assets}/acquisition-by-time-last-weeks.png (100%) rename {images => docs/assets}/acquisition-by-time.png (100%) rename {images => docs/assets}/acquisition-device-distribution.png (100%) rename {images => docs/assets}/acquisition-geographic-distribution.png (100%) rename {images => docs/assets}/acquisition-new-users.png (100%) rename {images => docs/assets}/activation-activated-users.png (100%) rename {images => docs/assets}/activation-by-time.png (100%) rename {images => docs/assets}/activation-device-distribution.png (100%) rename {images => docs/assets}/activation-geographic-distribution.png (100%) rename {images => docs/assets}/anonymization-display-image.jpg (100%) rename {images => docs/assets}/bar-chart.PNG (100%) rename {images => docs/assets}/compact_wide_mode.PNG (100%) rename {images => docs/assets}/create-new-insight.png (100%) rename {images => docs/assets}/daily-active-users-example.png (100%) rename {images => docs/assets}/dashboard-acquisition.png (100%) rename {images => docs/assets}/dashboard-custom.png (100%) rename {images => docs/assets}/dashboard-exploring-details.png (100%) rename {images => docs/assets}/dashboard-filtering-data.png (100%) rename {images => docs/assets}/dashboard-main-nav.png (100%) rename {images => docs/assets}/dashboard-notebooks.png (100%) rename {images => docs/assets}/dashboard-overview.png (100%) rename {images => docs/assets}/dashboard-signal-types.png (100%) rename {images => docs/assets}/display_mode.PNG (100%) rename {images => docs/assets}/donut-chart.PNG (100%) rename {images => docs/assets}/duration-signal-01.png (100%) rename {images => docs/assets}/duration-signal-02.png (100%) rename {images => docs/assets}/duration-signal-03.png (100%) rename {images => docs/assets}/edit-dashboard-name.png (100%) rename {images => docs/assets}/faq.jpg (100%) create mode 100644 docs/assets/favicon.svg rename {images => docs/assets}/filter_example.png (100%) rename {images => docs/assets}/filter_location.png (100%) rename {images => docs/assets}/funnel_type.PNG (100%) rename {images => docs/assets}/funnels_example.png (100%) rename {images => docs/assets}/funnels_set_filters.jpg (100%) rename {images => docs/assets}/line-chart.PNG (100%) rename {images => docs/assets}/location-create-dashboard.png (100%) rename {images => docs/assets}/location-edit-group.PNG (100%) rename {images => docs/assets}/location-edit-insight.png (100%) rename {images => docs/assets}/login-mask.png (100%) create mode 100644 docs/assets/logo.svg rename {images => docs/assets}/metrics-accessibility.png (100%) rename {images => docs/assets}/metrics-devices.png (100%) rename {images => docs/assets}/metrics-errors.png (100%) rename {images => docs/assets}/metrics-localization.png (100%) rename {images => docs/assets}/metrics-versions.png (100%) rename {images => docs/assets}/notebooks-video-thumbnail.png (100%) rename {images => docs/assets}/privacy-overview.png (100%) rename {images => docs/assets}/purchases-privacy-box.png (100%) rename {images => docs/assets}/rc-td-1.png (100%) rename {images => docs/assets}/rc-td-2.png (100%) rename {images => docs/assets}/retention-by-time.png (100%) rename {images => docs/assets}/retention-device-distribution.png (100%) rename {images => docs/assets}/retention-geographic-distribution.png (100%) rename {images => docs/assets}/retention-returning-users.png (100%) rename {images => docs/assets}/revenuecat_webhook_config.png (100%) rename {images => docs/assets}/system-versions-example.png (100%) rename {images => docs/assets}/table-chart.PNG (100%) rename {images => docs/assets}/test_mode.png (100%) rename {images => docs/assets}/typedigital.png (100%) rename {images => docs/assets}/update_next_major_version.png (100%) rename {images => docs/assets}/update_package.png (100%) rename {images => docs/assets}/xcode-swift-package.png (100%) rename {images => docs/assets}/xcode-swift-package1.png (100%) rename {images => docs/assets}/xcode-swift-package2.png (100%) rename {images => docs/assets}/yt-4-minute-setup.png (100%) rename {images => docs/assets}/yt-app-analytics.png (100%) rename {images => docs/assets}/yt-app-store-connect.png (100%) rename {images => docs/assets}/yt-built-in-charts.png (100%) rename {images => docs/assets}/yt-custom-charts.png (100%) diff --git a/images/MAU_1.png b/docs/assets/MAU_1.png similarity index 100% rename from images/MAU_1.png rename to docs/assets/MAU_1.png diff --git a/images/MAU_2.png b/docs/assets/MAU_2.png similarity index 100% rename from images/MAU_2.png rename to docs/assets/MAU_2.png diff --git a/images/MAU_3.png b/docs/assets/MAU_3.png similarity index 100% rename from images/MAU_3.png rename to docs/assets/MAU_3.png diff --git a/images/MAU_4.png b/docs/assets/MAU_4.png similarity index 100% rename from images/MAU_4.png rename to docs/assets/MAU_4.png diff --git a/images/MAU_5.png b/docs/assets/MAU_5.png similarity index 100% rename from images/MAU_5.png rename to docs/assets/MAU_5.png diff --git a/images/Notebooks-Overview.png b/docs/assets/Notebooks-Overview.png similarity index 100% rename from images/Notebooks-Overview.png rename to docs/assets/Notebooks-Overview.png diff --git a/images/Notebooks-TQL-Live-Preview.png b/docs/assets/Notebooks-TQL-Live-Preview.png similarity index 100% rename from images/Notebooks-TQL-Live-Preview.png rename to docs/assets/Notebooks-TQL-Live-Preview.png diff --git a/images/Peerigon_Logo_RGB_no_padding.svg b/docs/assets/Peerigon_Logo_RGB_no_padding.svg similarity index 100% rename from images/Peerigon_Logo_RGB_no_padding.svg rename to docs/assets/Peerigon_Logo_RGB_no_padding.svg diff --git a/images/Referrers_1.png b/docs/assets/Referrers_1.png similarity index 100% rename from images/Referrers_1.png rename to docs/assets/Referrers_1.png diff --git a/images/Referrers_2.png b/docs/assets/Referrers_2.png similarity index 100% rename from images/Referrers_2.png rename to docs/assets/Referrers_2.png diff --git a/images/Referrers_3a.png b/docs/assets/Referrers_3a.png similarity index 100% rename from images/Referrers_3a.png rename to docs/assets/Referrers_3a.png diff --git a/images/Referrers_3b.png b/docs/assets/Referrers_3b.png similarity index 100% rename from images/Referrers_3b.png rename to docs/assets/Referrers_3b.png diff --git a/images/Referrers_4.png b/docs/assets/Referrers_4.png similarity index 100% rename from images/Referrers_4.png rename to docs/assets/Referrers_4.png diff --git a/images/Referrers_5.png b/docs/assets/Referrers_5.png similarity index 100% rename from images/Referrers_5.png rename to docs/assets/Referrers_5.png diff --git a/images/Screenshot_SystemVersion.png b/docs/assets/Screenshot_SystemVersion.png similarity index 100% rename from images/Screenshot_SystemVersion.png rename to docs/assets/Screenshot_SystemVersion.png diff --git a/images/aarrr-framework.png b/docs/assets/aarrr-framework.png similarity index 100% rename from images/aarrr-framework.png rename to docs/assets/aarrr-framework.png diff --git a/images/acquisition-active-vs-new.png b/docs/assets/acquisition-active-vs-new.png similarity index 100% rename from images/acquisition-active-vs-new.png rename to docs/assets/acquisition-active-vs-new.png diff --git a/images/acquisition-by-time-last-weeks.png b/docs/assets/acquisition-by-time-last-weeks.png similarity index 100% rename from images/acquisition-by-time-last-weeks.png rename to docs/assets/acquisition-by-time-last-weeks.png diff --git a/images/acquisition-by-time.png b/docs/assets/acquisition-by-time.png similarity index 100% rename from images/acquisition-by-time.png rename to docs/assets/acquisition-by-time.png diff --git a/images/acquisition-device-distribution.png b/docs/assets/acquisition-device-distribution.png similarity index 100% rename from images/acquisition-device-distribution.png rename to docs/assets/acquisition-device-distribution.png diff --git a/images/acquisition-geographic-distribution.png b/docs/assets/acquisition-geographic-distribution.png similarity index 100% rename from images/acquisition-geographic-distribution.png rename to docs/assets/acquisition-geographic-distribution.png diff --git a/images/acquisition-new-users.png b/docs/assets/acquisition-new-users.png similarity index 100% rename from images/acquisition-new-users.png rename to docs/assets/acquisition-new-users.png diff --git a/images/activation-activated-users.png b/docs/assets/activation-activated-users.png similarity index 100% rename from images/activation-activated-users.png rename to docs/assets/activation-activated-users.png diff --git a/images/activation-by-time.png b/docs/assets/activation-by-time.png similarity index 100% rename from images/activation-by-time.png rename to docs/assets/activation-by-time.png diff --git a/images/activation-device-distribution.png b/docs/assets/activation-device-distribution.png similarity index 100% rename from images/activation-device-distribution.png rename to docs/assets/activation-device-distribution.png diff --git a/images/activation-geographic-distribution.png b/docs/assets/activation-geographic-distribution.png similarity index 100% rename from images/activation-geographic-distribution.png rename to docs/assets/activation-geographic-distribution.png diff --git a/images/anonymization-display-image.jpg b/docs/assets/anonymization-display-image.jpg similarity index 100% rename from images/anonymization-display-image.jpg rename to docs/assets/anonymization-display-image.jpg diff --git a/images/bar-chart.PNG b/docs/assets/bar-chart.PNG similarity index 100% rename from images/bar-chart.PNG rename to docs/assets/bar-chart.PNG diff --git a/images/compact_wide_mode.PNG b/docs/assets/compact_wide_mode.PNG similarity index 100% rename from images/compact_wide_mode.PNG rename to docs/assets/compact_wide_mode.PNG diff --git a/images/create-new-insight.png b/docs/assets/create-new-insight.png similarity index 100% rename from images/create-new-insight.png rename to docs/assets/create-new-insight.png diff --git a/images/daily-active-users-example.png b/docs/assets/daily-active-users-example.png similarity index 100% rename from images/daily-active-users-example.png rename to docs/assets/daily-active-users-example.png diff --git a/images/dashboard-acquisition.png b/docs/assets/dashboard-acquisition.png similarity index 100% rename from images/dashboard-acquisition.png rename to docs/assets/dashboard-acquisition.png diff --git a/images/dashboard-custom.png b/docs/assets/dashboard-custom.png similarity index 100% rename from images/dashboard-custom.png rename to docs/assets/dashboard-custom.png diff --git a/images/dashboard-exploring-details.png b/docs/assets/dashboard-exploring-details.png similarity index 100% rename from images/dashboard-exploring-details.png rename to docs/assets/dashboard-exploring-details.png diff --git a/images/dashboard-filtering-data.png b/docs/assets/dashboard-filtering-data.png similarity index 100% rename from images/dashboard-filtering-data.png rename to docs/assets/dashboard-filtering-data.png diff --git a/images/dashboard-main-nav.png b/docs/assets/dashboard-main-nav.png similarity index 100% rename from images/dashboard-main-nav.png rename to docs/assets/dashboard-main-nav.png diff --git a/images/dashboard-notebooks.png b/docs/assets/dashboard-notebooks.png similarity index 100% rename from images/dashboard-notebooks.png rename to docs/assets/dashboard-notebooks.png diff --git a/images/dashboard-overview.png b/docs/assets/dashboard-overview.png similarity index 100% rename from images/dashboard-overview.png rename to docs/assets/dashboard-overview.png diff --git a/images/dashboard-signal-types.png b/docs/assets/dashboard-signal-types.png similarity index 100% rename from images/dashboard-signal-types.png rename to docs/assets/dashboard-signal-types.png diff --git a/images/display_mode.PNG b/docs/assets/display_mode.PNG similarity index 100% rename from images/display_mode.PNG rename to docs/assets/display_mode.PNG diff --git a/images/donut-chart.PNG b/docs/assets/donut-chart.PNG similarity index 100% rename from images/donut-chart.PNG rename to docs/assets/donut-chart.PNG diff --git a/images/duration-signal-01.png b/docs/assets/duration-signal-01.png similarity index 100% rename from images/duration-signal-01.png rename to docs/assets/duration-signal-01.png diff --git a/images/duration-signal-02.png b/docs/assets/duration-signal-02.png similarity index 100% rename from images/duration-signal-02.png rename to docs/assets/duration-signal-02.png diff --git a/images/duration-signal-03.png b/docs/assets/duration-signal-03.png similarity index 100% rename from images/duration-signal-03.png rename to docs/assets/duration-signal-03.png diff --git a/images/edit-dashboard-name.png b/docs/assets/edit-dashboard-name.png similarity index 100% rename from images/edit-dashboard-name.png rename to docs/assets/edit-dashboard-name.png diff --git a/images/faq.jpg b/docs/assets/faq.jpg similarity index 100% rename from images/faq.jpg rename to docs/assets/faq.jpg diff --git a/docs/assets/favicon.svg b/docs/assets/favicon.svg new file mode 100644 index 0000000..dc4a92c --- /dev/null +++ b/docs/assets/favicon.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/images/filter_example.png b/docs/assets/filter_example.png similarity index 100% rename from images/filter_example.png rename to docs/assets/filter_example.png diff --git a/images/filter_location.png b/docs/assets/filter_location.png similarity index 100% rename from images/filter_location.png rename to docs/assets/filter_location.png diff --git a/images/funnel_type.PNG b/docs/assets/funnel_type.PNG similarity index 100% rename from images/funnel_type.PNG rename to docs/assets/funnel_type.PNG diff --git a/images/funnels_example.png b/docs/assets/funnels_example.png similarity index 100% rename from images/funnels_example.png rename to docs/assets/funnels_example.png diff --git a/images/funnels_set_filters.jpg b/docs/assets/funnels_set_filters.jpg similarity index 100% rename from images/funnels_set_filters.jpg rename to docs/assets/funnels_set_filters.jpg diff --git a/images/line-chart.PNG b/docs/assets/line-chart.PNG similarity index 100% rename from images/line-chart.PNG rename to docs/assets/line-chart.PNG diff --git a/images/location-create-dashboard.png b/docs/assets/location-create-dashboard.png similarity index 100% rename from images/location-create-dashboard.png rename to docs/assets/location-create-dashboard.png diff --git a/images/location-edit-group.PNG b/docs/assets/location-edit-group.PNG similarity index 100% rename from images/location-edit-group.PNG rename to docs/assets/location-edit-group.PNG diff --git a/images/location-edit-insight.png b/docs/assets/location-edit-insight.png similarity index 100% rename from images/location-edit-insight.png rename to docs/assets/location-edit-insight.png diff --git a/images/login-mask.png b/docs/assets/login-mask.png similarity index 100% rename from images/login-mask.png rename to docs/assets/login-mask.png diff --git a/docs/assets/logo.svg b/docs/assets/logo.svg new file mode 100644 index 0000000..ae16198 --- /dev/null +++ b/docs/assets/logo.svg @@ -0,0 +1,31 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/images/metrics-accessibility.png b/docs/assets/metrics-accessibility.png similarity index 100% rename from images/metrics-accessibility.png rename to docs/assets/metrics-accessibility.png diff --git a/images/metrics-devices.png b/docs/assets/metrics-devices.png similarity index 100% rename from images/metrics-devices.png rename to docs/assets/metrics-devices.png diff --git a/images/metrics-errors.png b/docs/assets/metrics-errors.png similarity index 100% rename from images/metrics-errors.png rename to docs/assets/metrics-errors.png diff --git a/images/metrics-localization.png b/docs/assets/metrics-localization.png similarity index 100% rename from images/metrics-localization.png rename to docs/assets/metrics-localization.png diff --git a/images/metrics-versions.png b/docs/assets/metrics-versions.png similarity index 100% rename from images/metrics-versions.png rename to docs/assets/metrics-versions.png diff --git a/images/notebooks-video-thumbnail.png b/docs/assets/notebooks-video-thumbnail.png similarity index 100% rename from images/notebooks-video-thumbnail.png rename to docs/assets/notebooks-video-thumbnail.png diff --git a/images/privacy-overview.png b/docs/assets/privacy-overview.png similarity index 100% rename from images/privacy-overview.png rename to docs/assets/privacy-overview.png diff --git a/images/purchases-privacy-box.png b/docs/assets/purchases-privacy-box.png similarity index 100% rename from images/purchases-privacy-box.png rename to docs/assets/purchases-privacy-box.png diff --git a/images/rc-td-1.png b/docs/assets/rc-td-1.png similarity index 100% rename from images/rc-td-1.png rename to docs/assets/rc-td-1.png diff --git a/images/rc-td-2.png b/docs/assets/rc-td-2.png similarity index 100% rename from images/rc-td-2.png rename to docs/assets/rc-td-2.png diff --git a/images/retention-by-time.png b/docs/assets/retention-by-time.png similarity index 100% rename from images/retention-by-time.png rename to docs/assets/retention-by-time.png diff --git a/images/retention-device-distribution.png b/docs/assets/retention-device-distribution.png similarity index 100% rename from images/retention-device-distribution.png rename to docs/assets/retention-device-distribution.png diff --git a/images/retention-geographic-distribution.png b/docs/assets/retention-geographic-distribution.png similarity index 100% rename from images/retention-geographic-distribution.png rename to docs/assets/retention-geographic-distribution.png diff --git a/images/retention-returning-users.png b/docs/assets/retention-returning-users.png similarity index 100% rename from images/retention-returning-users.png rename to docs/assets/retention-returning-users.png diff --git a/images/revenuecat_webhook_config.png b/docs/assets/revenuecat_webhook_config.png similarity index 100% rename from images/revenuecat_webhook_config.png rename to docs/assets/revenuecat_webhook_config.png diff --git a/images/system-versions-example.png b/docs/assets/system-versions-example.png similarity index 100% rename from images/system-versions-example.png rename to docs/assets/system-versions-example.png diff --git a/images/table-chart.PNG b/docs/assets/table-chart.PNG similarity index 100% rename from images/table-chart.PNG rename to docs/assets/table-chart.PNG diff --git a/images/test_mode.png b/docs/assets/test_mode.png similarity index 100% rename from images/test_mode.png rename to docs/assets/test_mode.png diff --git a/images/typedigital.png b/docs/assets/typedigital.png similarity index 100% rename from images/typedigital.png rename to docs/assets/typedigital.png diff --git a/images/update_next_major_version.png b/docs/assets/update_next_major_version.png similarity index 100% rename from images/update_next_major_version.png rename to docs/assets/update_next_major_version.png diff --git a/images/update_package.png b/docs/assets/update_package.png similarity index 100% rename from images/update_package.png rename to docs/assets/update_package.png diff --git a/images/xcode-swift-package.png b/docs/assets/xcode-swift-package.png similarity index 100% rename from images/xcode-swift-package.png rename to docs/assets/xcode-swift-package.png diff --git a/images/xcode-swift-package1.png b/docs/assets/xcode-swift-package1.png similarity index 100% rename from images/xcode-swift-package1.png rename to docs/assets/xcode-swift-package1.png diff --git a/images/xcode-swift-package2.png b/docs/assets/xcode-swift-package2.png similarity index 100% rename from images/xcode-swift-package2.png rename to docs/assets/xcode-swift-package2.png diff --git a/images/yt-4-minute-setup.png b/docs/assets/yt-4-minute-setup.png similarity index 100% rename from images/yt-4-minute-setup.png rename to docs/assets/yt-4-minute-setup.png diff --git a/images/yt-app-analytics.png b/docs/assets/yt-app-analytics.png similarity index 100% rename from images/yt-app-analytics.png rename to docs/assets/yt-app-analytics.png diff --git a/images/yt-app-store-connect.png b/docs/assets/yt-app-store-connect.png similarity index 100% rename from images/yt-app-store-connect.png rename to docs/assets/yt-app-store-connect.png diff --git a/images/yt-built-in-charts.png b/docs/assets/yt-built-in-charts.png similarity index 100% rename from images/yt-built-in-charts.png rename to docs/assets/yt-built-in-charts.png diff --git a/images/yt-custom-charts.png b/docs/assets/yt-custom-charts.png similarity index 100% rename from images/yt-custom-charts.png rename to docs/assets/yt-custom-charts.png diff --git a/zensical.toml b/zensical.toml index 01736c1..22920b5 100644 --- a/zensical.toml +++ b/zensical.toml @@ -96,7 +96,7 @@ custom_dir = "overrides" # - https://zensical.org/docs/setup/logo-and-icons/#favicon # - https://developer.mozilla.org/en-US/docs/Glossary/Favicon # -#favicon = "images/favicon.png" +favicon = "assets/favicon.png" # Zensical supports more than 60 different languages. This means that the # labels and tooltips that Zensical's templates produce are translated. @@ -257,7 +257,7 @@ features = [ # option in the "theme" subsection. The logo must be a relative path to a file # in your "docs_dir", e.g., to use `docs/assets/logo.png` you would set: # ---------------------------------------------------------------------------- -#logo = "assets/logo.png" +logo = "assets/logo.svg" # ---------------------------------------------------------------------------- # If you don't have a dedicated project logo, you can use a built-in icon from From 0743d6545153624c3445c25d3d38795027a8b66b Mon Sep 17 00:00:00 2001 From: Konstantin Kostov Date: Sun, 10 May 2026 11:57:09 +0200 Subject: [PATCH 12/15] docs: update README with local dev instructions --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index 292768f..4ca93c3 100644 --- a/README.md +++ b/README.md @@ -5,3 +5,10 @@ Welcome to the public documentation for TelemetryDeck. The output of these pages We're incredibly grateful for pull requests or issues that improve things or let us know about errata and missing or unclear bits of information! <3 Check out `articles/documentation.md` for an overview of how documentation pages are formatted. + + +## Local Development + +We use Python `pip`. You can follow the setups at https://zensical.org/docs/get-started/#installation for the initial setup. + +Note: Make sure the Python version is recent e.g. 3.14 or later (`python3 --version`). From 53eac2d68fa9fce2f3aea8423517712a7daedd80 Mon Sep 17 00:00:00 2001 From: Konstantin Kostov Date: Sun, 10 May 2026 12:16:56 +0200 Subject: [PATCH 13/15] feat: fix image references --- docs/articles/anonymization-how-it-works.md | 6 +++--- docs/articles/apple-app-privacy.md | 2 +- docs/articles/create-custom-dashboards.md | 8 ++++---- docs/articles/decide-to-drop-ios-version.md | 2 +- docs/articles/documentation.md | 14 +++++++------- docs/articles/duration-signals.md | 6 +++--- docs/articles/how-to-funnel-insights.md | 6 +++--- docs/articles/insights-about-daily-users.md | 2 +- docs/articles/insights-about-monthly-users.md | 10 +++++----- docs/articles/insights-about-referrers.md | 12 ++++++------ docs/articles/insights-about-system-version.md | 2 +- docs/articles/insights.md | 18 +++++++++--------- docs/articles/login-options.md | 2 +- docs/articles/notebooks.md | 6 +++--- docs/articles/preset-purchases.md | 2 +- docs/articles/set-up-filters-insights.md | 4 ++-- docs/articles/test-mode.md | 2 +- docs/articles/update-package.md | 4 ++-- docs/basics/acquisition.md | 12 ++++++------ docs/basics/activation.md | 8 ++++---- docs/basics/index.md | 18 +++++++++--------- docs/basics/metrics.md | 10 +++++----- docs/basics/pirate-metrics.md | 2 +- docs/basics/retention.md | 8 ++++---- docs/guides/objective-c-setup.md | 2 +- docs/guides/privacy-faq.md | 2 +- docs/guides/react-setup.md | 2 +- docs/guides/swift-setup.md | 6 +++--- docs/guides/vue-setup.md | 2 +- docs/integrations/revenuecat.md | 4 ++-- 30 files changed, 92 insertions(+), 92 deletions(-) diff --git a/docs/articles/anonymization-how-it-works.md b/docs/articles/anonymization-how-it-works.md index 5f74634..ab589f2 100644 --- a/docs/articles/anonymization-how-it-works.md +++ b/docs/articles/anonymization-how-it-works.md @@ -8,7 +8,7 @@ description: TelemetryDeck anonymizes user data, by double salting and hashing I lead: We take user privacy seriously. To ensure the privacy of our users, we use various techniques to anonymize user data. One of the ways we do this is by using a double hashing technique to anonymize user identifiers. searchEngineTitle: How TelemetryDeck anonymizes user data privacy-friendly searchEngineDescription: TelemetryDeck anonymizes user data, by double hashing and salting IDs, to ensure anonymity and protect user privacy while still providing valuable insights. -headerImage: /docs/images/anonymization-display-image.jpg +headerImage: /assets/anonymization-display-image.jpg --- ## Methodology @@ -19,7 +19,7 @@ At TelemetryDeck, we even go a step further: the β€œidentification date” is no **Check out why [App Store Connect is not enough](https://www.youtube.com/watch?v=4_WqJGPzgmY) to protect user data!** -[![Compare TelemetryDeck and App Store Connect for Analytics](/docs/images/yt-app-store-connect.png)](https://www.youtube.com/watch?v=4_WqJGPzgmY) +[![Compare TelemetryDeck and App Store Connect for Analytics](/assets/yt-app-store-connect.png)](https://www.youtube.com/watch?v=4_WqJGPzgmY) ## User identifiers @@ -35,7 +35,7 @@ If you use the same (custom) salt and provide the same original identifier, you **Check out our [YouTube Channel](https://www.youtube.com/watch?v=4sQcZoi21nU) for a deeper dive into our anonymization process!** -[![The Benefits of TelemetryDeck For Privacy Focused App Analytics](/docs/images/yt-app-analytics.png)](https://www.youtube.com/watch?v=4sQcZoi21nU) +[![The Benefits of TelemetryDeck For Privacy Focused App Analytics](/assets/yt-app-analytics.png)](https://www.youtube.com/watch?v=4sQcZoi21nU) ## Conclusion diff --git a/docs/articles/apple-app-privacy.md b/docs/articles/apple-app-privacy.md index 3b4b959..267bfa3 100644 --- a/docs/articles/apple-app-privacy.md +++ b/docs/articles/apple-app-privacy.md @@ -16,7 +16,7 @@ Since TelemetryDeck's analytics are private by default, you can include this inf This means your app will get an excellent privacy rating. -![A screenshot of Apple's Privacy Overview](/docs/images/privacy-overview.png) +![A screenshot of Apple's Privacy Overview](/assets/privacy-overview.png) ## How do I start? diff --git a/docs/articles/create-custom-dashboards.md b/docs/articles/create-custom-dashboards.md index 0aadfae..8216dc8 100644 --- a/docs/articles/create-custom-dashboards.md +++ b/docs/articles/create-custom-dashboards.md @@ -16,7 +16,7 @@ order: To create a dashboard for your insights, go to your [TelemetryDeck dashboard](https://dashboard.telemetrydeck.com/), navigate to `Dashboards` and look at the left sidebar. Here you can find the `New Dashboard` button. Create a _New Dashboard_, give your dashboard a name and then click _Create_. You now have a new insight dashboard in your sidebar! -![Location of the "Create New Dashboard" Button](/docs/images/location-create-dashboard.png) +![Location of the "Create New Dashboard" Button](/assets/location-create-dashboard.png) ## Share your dashboards with your organization @@ -31,20 +31,20 @@ You can also share specific dashboards with the members of your organization. To Now let's **create** an insight. While in your newly created dashboard, navigate to the `Actions` drop down button on the top-right side. Click the _Create new Insight_ button and give your new insight a name. Please choose from one of our convenient templates! The insight will be automagically ✨ generated for you. If needed, you can also change the display mode, title, query type, and more - even after creating it. -![Location of the "Create New Insight" Button](/docs/images/create-new-insight.png) +![Location of the "Create New Insight" Button](/assets/create-new-insight.png) You can create a bunch of insights inside your dashboards and thus, combine thematically related charts of your insights. And you're able to resize your charts to regular-sized `Compact` cards or big `Wide` cards. To **delete** insights from a dashboard, click on the insights' name. Go to `Actions` in the top right corner, just delete the current insight by clicking on "Delete Insight". -![Location of the "Delete Insight" Button](/docs/images/location-edit-insight.png) +![Location of the "Delete Insight" Button](/assets/location-edit-insight.png) ### Rename your dashboard Not happy with the name given to your dashboard? No problem - you can change it quickly! Click on the dashboard whose name you want to change. Then hover over your dashboard name, and click to edit. Save your changes after you are done editing - your dashboard now has a new name. -![Location of the "Rename Dashboard" Button](/docs/images/edit-dashboard-name.png) +![Location of the "Rename Dashboard" Button](/assets/edit-dashboard-name.png) ### Delete your dashboard diff --git a/docs/articles/decide-to-drop-ios-version.md b/docs/articles/decide-to-drop-ios-version.md index ddd9c7b..6380978 100644 --- a/docs/articles/decide-to-drop-ios-version.md +++ b/docs/articles/decide-to-drop-ios-version.md @@ -27,7 +27,7 @@ The TelemetryDeck SDK by default tries to collect data about the user's operatin To find out which percentage of your users are using a certain OS version, use a **Breakdown Insight** (also known as a **Top N Insight**). Then you'll have multiple options for the breakdown key. TelemetryDeck provides pre-built dashboards, among others the Top N Insight just described: -![Screenshot SystemVersion](/docs/images/Screenshot_SystemVersion.png) +![Screenshot SystemVersion](/assets/Screenshot_SystemVersion.png) You can switch between `majorMinorVersion` and `majorVersion` in the chart. Below we come back to the difference with recommendations what to use for this purpose. As an orientation beyond your app we also want to point out our monthly updated [surveys](https://telemetrydeck.com/survey/). Through these we provide information about [majorMinorVersions](https://telemetrydeck.com/survey/apple/iOS/minorSystemVersions/) and [majorVersions](https://telemetrydeck.com/survey/apple/iOS/majorSystemVersions/) currently used according to our data set as well as device related information regarding [iPhone models](https://telemetrydeck.com/survey/apple/iPhone/models/) for example. diff --git a/docs/articles/documentation.md b/docs/articles/documentation.md index ef8a8c0..8c841da 100644 --- a/docs/articles/documentation.md +++ b/docs/articles/documentation.md @@ -186,25 +186,25 @@ and [links](https://www.markdownguide.org/basic-syntax/#link). ## Images -To display an image in a docs article, add it to the `images` directory. You can then link it using regular markdown image syntax, adding `/docs/images/` before the images' name. +To display an image in a docs article, add it to the `assets` directory. You can then link it using regular markdown image syntax, adding `/assets/` before the image's name. -Example: You just added the file `privacy-overview.png` to the `images` folder. You can now display that image like so: +Example: You just added the file `privacy-overview.png` to the `assets` folder. You can now display that image like so: ```markdown -![A screenshot of Apple's Privacy Overview](/docs/images/privacy-overview.png) +![A screenshot of Apple's Privacy Overview](/assets/privacy-overview.png) ``` -The first part is the image's alt text. The second part is the path (`/docs/images/`) and the image file name `privacy-overview.png`. +The first part is the image's alt text. The second part is the path (`/assets/`) and the image file name `privacy-overview.png`. Here's what it looks like: -![A screenshot of Apple's Privacy Overview](/docs/images/privacy-overview.png) +![A screenshot of Apple's Privacy Overview](/assets/privacy-overview.png) {% notewarning "Image File Locations" %} -Image files need to live in the `images` directory at the root of the `docs` repository. Image files that are elsewhere in the file hierarchy will be ignored. +Image files need to live in the `assets` directory inside `docs/`. Image files elsewhere in the file hierarchy will be ignored. -You need to prefix `/docs/images/` to the path when linking to the image, since the Docs repository lives inside a `/docs` folder on deployment. +Prefix `/assets/` to the path when linking to the image β€” the path is resolved against the docs site root. {% endnotewarning %} ## Code Blocks diff --git a/docs/articles/duration-signals.md b/docs/articles/duration-signals.md index 3cc9440..6ec2bbf 100644 --- a/docs/articles/duration-signals.md +++ b/docs/articles/duration-signals.md @@ -84,11 +84,11 @@ The histogram aggregation type is perfect for visualizing the distribution of du 1. Create a new insight of type "Advanced Query", then open the "JSON Editor": - ![A screenshot of the Query Creator dialog](/docs/images/duration-signal-01.png) + ![A screenshot of the Query Creator dialog](/assets/duration-signal-01.png) 2. Copy & paste the following histogram aggregation query and adjust `` to your needs: - ![A screenshot of the JSON Editor text field](/docs/images/duration-signal-02.png) + ![A screenshot of the JSON Editor text field](/assets/duration-signal-02.png) ```json { @@ -125,7 +125,7 @@ The histogram aggregation type is perfect for visualizing the distribution of du 3. Set the chart type to be a bar chart in the UI via the insight's top right segmented control: - ![A screenshot of the insight set to be a bar chart](/docs/images/duration-signal-03.png) + ![A screenshot of the insight set to be a bar chart](/assets/duration-signal-03.png) 4. You might also want to adjust the `splitPoints` array based on the expected duration of your activity, for example: - **Short interactions** (button clicks): `[0, 0.05, 0.1, 0.15, 0.2, 0.3, 0.5, 1, 2, 5]` diff --git a/docs/articles/how-to-funnel-insights.md b/docs/articles/how-to-funnel-insights.md index 236a704..8a15ccd 100644 --- a/docs/articles/how-to-funnel-insights.md +++ b/docs/articles/how-to-funnel-insights.md @@ -16,9 +16,9 @@ Sometimes they go directly to their goal, do not pass Go, and do not collect 200 These goals are often your goals, too. As the app owner, you want them to spend time in your app, find the new feature, and order that new product. -![Screenshot of a funnel called "Log in Journey" with 4 decreasing steps, going from "user login", to "show group view", to "show insight", and finally to "widget setup"](/docs/images/funnels_example.png) +![Screenshot of a funnel called "Log in Journey" with 4 decreasing steps, going from "user login", to "show group view", to "show insight", and finally to "widget setup"](/assets/funnels_example.png) -![Screenshot of the funnel steps with set filters for "Log in Journey"](/docs/images/funnels_set_filters.jpg) +![Screenshot of the funnel steps with set filters for "Log in Journey"](/assets/funnels_set_filters.jpg) Funnels are a great way to show this kind of behavior. What funnels do at heart is display **when** a user **ends the process**. For example, it is possible to showcase each page of an app - from opening the home page to the final checkout page. If you have 100 users going through that process, and all of them finish it, all steps should show 100 users. If there happens to be some confusion during the process, and users cancel it before the checkout, you will see that the page causing that issue will leave a drop in users afterward. The checkout page will probably show fewer than 100 users at the end. @@ -28,7 +28,7 @@ Let's have a look at how to use funnels in TelemetryDeck. ## How to use funnels Imagine you want to track how many users turn into customers. You can use funnels to track this conversion process. Since a funnel filters your insights by conditions, you must set up filters in your TelemetryDeck dashboard with the **filter editor**. These filters help you track how many users complete each funnel step, leading to a great visualization of your app's conversion. To create a **funnel chart**, just set the chart type to funnel and the query type to **funnel query** - or use our handy template to create an empty funnel! -![Screenshot of the selected funnel query and chart type](/docs/images/funnel_type.PNG) +![Screenshot of the selected funnel query and chart type](/assets/funnel_type.PNG) For example, let's say your funnel has three steps: diff --git a/docs/articles/insights-about-daily-users.md b/docs/articles/insights-about-daily-users.md index c777a80..c55a4ea 100644 --- a/docs/articles/insights-about-daily-users.md +++ b/docs/articles/insights-about-daily-users.md @@ -19,7 +19,7 @@ Insights of daily active users are the best way to see how your app is doing. Yo We will help you set up your insight so you can track your users right away, privacy-friendly and anonymized! -![Bar chart example of daily active users](/docs/images/daily-active-users-example.png) +![Bar chart example of daily active users](/assets/daily-active-users-example.png) ## Navigate to your app diff --git a/docs/articles/insights-about-monthly-users.md b/docs/articles/insights-about-monthly-users.md index 2e6bcff..94597de 100644 --- a/docs/articles/insights-about-monthly-users.md +++ b/docs/articles/insights-about-monthly-users.md @@ -18,21 +18,21 @@ order: Follow these steps to get an insight of your monthly active users (MAU) within a couple of minutes: 1. Go to the dashboard and create a New Insight. - ![Create a new insight](/docs/images/MAU_1.png) + ![Create a new insight](/assets/MAU_1.png) 2. In the next step select "I don’t know, show me some examples" and then choose "Monthly Users". 3. Now you are already getting results! Unfortunately, you probably still do not find the chart that helpful since only data of the last 30 days is included and that contradicts a chart with granularity set to "Month". - ![Standard insight](/docs/images/MAU_2.png) + ![Standard insight](/assets/MAU_2.png) **A quick fix** is changing the included data from "Last 30 Days" to "This Year" in the respective dropdown at the top of the page. - ![Insight current year](/docs/images/MAU_3.png) + ![Insight current year](/assets/MAU_3.png) 4. An issue is that you do not want to constantly change the time interval manually every time you use TelemetryDeck for this query to work. To resolve this: - While editing the query click on the **Query Type** button and choose **Advanced Query**. This will cause that you stop editing the query, but once you click on "Edit" that same query again you can now use the Visual Editor. - In the Metadata section add an item for Relative Intervals - At beginningDate choose `month`, `-12` and `beginning` to start the time interval 12 months ago and for **endDate** choose `month`, `0` and `end` to end the time interval at the current time. - ![Set relative interval](/docs/images/MAU_4.png) + ![Set relative interval](/assets/MAU_4.png) The query is now working as required although the dropdown at the top is changed back to "Last 30 Days". -![Final insight](/docs/images/MAU_5.png) +![Final insight](/assets/MAU_5.png) diff --git a/docs/articles/insights-about-referrers.md b/docs/articles/insights-about-referrers.md index f922729..30eb3f6 100644 --- a/docs/articles/insights-about-referrers.md +++ b/docs/articles/insights-about-referrers.md @@ -16,10 +16,10 @@ order: --- To begin with, add a new insight in the dashboard of your choice and select **Advanced Query** so that you can proceed using the **Visual Editor**. -![Create a new advanced query](/docs/images/Referrers_1.png) +![Create a new advanced query](/assets/Referrers_1.png) 1. In the first section of the Visual Editor, **Metadata**, choose a `topN query` - we propose granularity `all` so that you can display the information in a donut chart in the end. - ![Metadata](/docs/images/Referrers_2.png) + ![Metadata](/assets/Referrers_2.png) 2. In the next step you can choose which **Data to Include**. To get started, add `thisApp` as well as the respective App ID. @@ -27,15 +27,15 @@ To begin with, add a new insight in the dashboard of your choice and select **Ad To achieve that add a `regex` filter with dimension `referrer` and domain as well as top-level-domain of your website separated by a `\`: `referrer~yourDomain\.com`. Please be aware that this is a rather basic regex filter as the purpose here is to show the creation of the query. More elements can be added to the filter of course. Once you have entered the information for the filter click on the field again and select `Negate (Wrap in "not" condition)` - ![Data to Include_1](/docs/images/Referrers_3a.png) + ![Data to Include_1](/assets/Referrers_3a.png) When you are finished, the filter in **Data to Include** section should look as follows: - ![Data to Include_2](/docs/images/Referrers_3b.png) + ![Data to Include_2](/assets/Referrers_3b.png) Additionally, feel free to add further information in the regex filter in case you want to exclude search engines besides your own website as referrers for example. This could be used in the `regex` filter of the Visual Editor to expand the filter: `(yourDomain\.com|google\.|bing\.|search\.brave|yandex\.|kagi\.|duckduckgo\.)`. 4. The following section are **topN Options**. In the first part regarding the dimension, select type `default` and type in `referrer` two times. Furthermore, choose a `numeric` metric and add `count`. To wrap this section up choose the number of topN results to be returned, i.e. the threshold. - ![topN Options](/docs/images/Referrers_4.png) + ![topN Options](/assets/Referrers_4.png) 5. Finally, add a `longSum`-aggregator for the **Aggregations** and type in `count` in the two respective fields. - ![Aggregations](/docs/images/Referrers_5.png) + ![Aggregations](/assets/Referrers_5.png) To wrap the creation of the insight up we recommend using a `Donut Chart` to display topN of the query results. diff --git a/docs/articles/insights-about-system-version.md b/docs/articles/insights-about-system-version.md index 038fd8e..a826808 100644 --- a/docs/articles/insights-about-system-version.md +++ b/docs/articles/insights-about-system-version.md @@ -34,7 +34,7 @@ Click on _+ Create new Insight_ and give it a name. Now you can either build you You can directly see how many users are using your app from a specific operating system. By default, the versions are grouped by minor versions (displayed as `15.x.x`). -![Donut chart example of system versions](/docs/images/system-versions-example.png) +![Donut chart example of system versions](/assets/system-versions-example.png) ## Step four: Configure your insights diff --git a/docs/articles/insights.md b/docs/articles/insights.md index 4fc8c23..53e7fe6 100644 --- a/docs/articles/insights.md +++ b/docs/articles/insights.md @@ -21,7 +21,7 @@ The query is used to retrieve data from the TelemetryDeck API, and the display m **Check out our [YouTube Channel](https://www.youtube.com/watch?v=x0eZoQDnAPA) to learn how our built-in charts work!** -[![Understanding TelemetryDeck's built-in charts](/docs/images/yt-built-in-charts.png)](https://www.youtube.com/watch?v=x0eZoQDnAPA) +[![Understanding TelemetryDeck's built-in charts](/assets/yt-built-in-charts.png)](https://www.youtube.com/watch?v=x0eZoQDnAPA) ### Versatile and adjustable @@ -53,12 +53,12 @@ The title is displayed on top of any insight card. Example: "Daily Active Users" **Compact and wide mode** You can choose between "Compact" and "Wide". If "Wide" is active, the insight will be displayed in a larger frame. This allows you to see your most important insight with extra detail. -![buttons for the compact mode](/docs/images/compact_wide_mode.PNG) +![buttons for the compact mode](/assets/compact_wide_mode.PNG) **Display Mode** Here, you can choose the most suitable chart type for your insight. Learn more about the chart types in the section [Chart Types](#chart-types). -![icons for the display mode](/docs/images/display_mode.PNG) +![icons for the display mode](/assets/display_mode.PNG) **Counting** If "Count Signals" is checked, an insight will count all signals by their type. If "Count Users" is checked, each user will only get counted once. Only the newest is selected if the set of signals counted by the insight contains multiple signals from the same user. This is great for counting users, for example, "How many users are using feature x?" @@ -106,7 +106,7 @@ There is no going back from here. If you later decide that there is no custom qu **Check out our [YouTube Channel](https://www.youtube.com/watch?v=PYWO3017_Ho) on how to create custom charts!** -[![Creating Custom Charts in TelemetryDeck – Conversion Tracking Tutorial](/docs/images/yt-custom-charts.png)](https://www.youtube.com/watch?v=PYWO3017_Ho) +[![Creating Custom Charts in TelemetryDeck – Conversion Tracking Tutorial](/assets/yt-custom-charts.png)](https://www.youtube.com/watch?v=PYWO3017_Ho) ## Chart Types @@ -119,7 +119,7 @@ The TelemetryDeck dashboard will show time zones of your users in **their browse --- -![An example of a table chart](/docs/images/table-chart.PNG) +![An example of a table chart](/assets/table-chart.PNG) **Table** @@ -129,7 +129,7 @@ If only one line of data is returned, that line will be displayed in large type. --- -![An example of a bar chart](/docs/images/bar-chart.PNG) +![An example of a bar chart](/assets/bar-chart.PNG) **Bar Chart** @@ -137,7 +137,7 @@ It displays the query result as a vertical bar chart, one bar per line of data. --- -![An example of a line chart](/docs/images/line-chart.PNG) +![An example of a line chart](/assets/line-chart.PNG) **Line Chart** @@ -145,7 +145,7 @@ This chart shows the query result as a line chart, one bar per line of data. Thi --- -![An example of a donut chart](/docs/images/donut-chart.PNG) +![An example of a donut chart](/assets/donut-chart.PNG) **Donut Chart** @@ -153,7 +153,7 @@ A pie/donut type chart that will sort the rows of data by number and visually sh --- -![An example of a funnel chart](/docs/images/funnels_example.png) +![An example of a funnel chart](/assets/funnels_example.png) **Funnel Chart** diff --git a/docs/articles/login-options.md b/docs/articles/login-options.md index 0ab72c4..746a8b6 100644 --- a/docs/articles/login-options.md +++ b/docs/articles/login-options.md @@ -18,7 +18,7 @@ To login into the TelemetryDeck dashboard you can use any of these options: * Okta (for our enterprise customers, on request) -![Login mask](/docs/images/login-mask.png) +![Login mask](/assets/login-mask.png) ## Frequently Asked Questions **Does TemeletryDeck support 2FA?** diff --git a/docs/articles/notebooks.md b/docs/articles/notebooks.md index f193311..043d6b8 100644 --- a/docs/articles/notebooks.md +++ b/docs/articles/notebooks.md @@ -16,7 +16,7 @@ searchEngineDescription: Learn how to effectively use TelemetryDeck Notebooks to Notebooks are your analytics lab notebook – a place where you can document your findings, share insights with your team, and maintain context throughout your investigations. Let's explore how to use them effectively. {% noteinfo "See Notebooks in action" %} -[![Notebooks Feature Demo - Learn how to combine live charts with markdown text for better analytics insights](/docs/images/notebooks-video-thumbnail.png)](https://www.youtube.com/watch?v=WAa2BRIaVGE) +[![Notebooks Feature Demo - Learn how to combine live charts with markdown text for better analytics insights](/assets/notebooks-video-thumbnail.png)](https://www.youtube.com/watch?v=WAa2BRIaVGE) *Watch the [Notebooks Walkthrough](https://www.youtube.com/watch?v=WAa2BRIaVGE) on our YouTube channel* {% endnoteinfo %} @@ -32,7 +32,7 @@ Notebooks are your analytics lab notebook – a place where you can document you Starting with a clear question or hypothesis helps focus your analysis and makes it easier to structure your notebook. It also makes it easier to share your findings with others later. {% endnoteinfo %} -![A screenshot of the Notebooks overview tab, showing a list of notebooks](/docs/images/Notebooks-Overview.png) +![A screenshot of the Notebooks overview tab, showing a list of notebooks](/assets/Notebooks-Overview.png) ### Adding charts to your notebook @@ -62,7 +62,7 @@ You can customize how your data is displayed using the `displayMode` value in yo - `raw` - Ideal for detailed breakdowns - `funnelChart` - Essential for conversion analysis -![A screenshot showing the markdown editor with TQL code, and the live chart preview in a notebook](/docs/images/Notebooks-TQL-Live-Preview.png) +![A screenshot showing the markdown editor with TQL code, and the live chart preview in a notebook](/assets/Notebooks-TQL-Live-Preview.png) ### Using Markdown effectively diff --git a/docs/articles/preset-purchases.md b/docs/articles/preset-purchases.md index fbeb9cd..9f2256f 100644 --- a/docs/articles/preset-purchases.md +++ b/docs/articles/preset-purchases.md @@ -109,4 +109,4 @@ You can answer all subsequent questions with "No" because we neither link collec When all is configured your "Purchases" entry in your App Privacy page should end up looking like this: -![Purchases entry with only 'Used for Analytics' in the box](/docs/images/purchases-privacy-box.png) +![Purchases entry with only 'Used for Analytics' in the box](/assets/purchases-privacy-box.png) diff --git a/docs/articles/set-up-filters-insights.md b/docs/articles/set-up-filters-insights.md index b48ad8b..c467918 100644 --- a/docs/articles/set-up-filters-insights.md +++ b/docs/articles/set-up-filters-insights.md @@ -16,7 +16,7 @@ With filters, you can create custom views of your insights and organize the info Navigate to the [dashboard](https://dashboard.telemetrydeck.com), and select your app. You can find the filter editor in your insight group, while editing an insight. Either create a new insight or edit an existing one to see the editor just below the chart itself. -![Screenshot of the filter location in the dashboard](/docs/images/filter_location.png) +![Screenshot of the filter location in the dashboard](/assets/filter_location.png) In your insight group, you can add filters to any insight you want. With advanced filter options available, you can add multiple filters to obtain the desired query results. Nesting filters and combining them with boolean operations can help you refine your query and achieve even more accurate insights. @@ -28,7 +28,7 @@ You can use analytics filters to refine your data and obtain precise insights. W - The **Selector** filter lets you compare any _payload key_ (also known as a dimension) to a value. For instance, if you send a `shouldUseHealthKit` parameter as part of your payload in signals, you can filter for `shouldUseHealthKit = β€œtrue”`. - Additionally, you can use **Regular Expressions** (RegEx) to filter data based on _complex patterns or strings of text_. Sometimes it is not possible to match a value exactly, and in such cases, regular expressions can be incredibly useful to obtain more accurate and specific insights into user behavior. A good example for using RegEx is filtering by device type, locale, or anything else you would like a more precise view on! -![Screenshot of how adding a condition changes the output. Adding that only iOS versions should be shown, and then wrapping the condition inside a NOT so that everything but iOS versions is shown.](/docs/images/filter_example.png) +![Screenshot of how adding a condition changes the output. Adding that only iOS versions should be shown, and then wrapping the condition inside a NOT so that everything but iOS versions is shown.](/assets/filter_example.png) ## Query construction diff --git a/docs/articles/test-mode.md b/docs/articles/test-mode.md index 528b77b..7c67e95 100644 --- a/docs/articles/test-mode.md +++ b/docs/articles/test-mode.md @@ -28,7 +28,7 @@ Each sent signal has a `isTestMode` parameter, which can either be `true` or `fa Navigate to your TelemetryDeck [dashboard](https://dashboard.telemetrydeck.com/), where you will find the Test Mode toggle on the top left side, just above the sidebar. You can toggle it to show your signals either in `isTestMode == true` or `isTestMode == false`. While toggled to `true`, you will see a banner at the top displaying **Test Data** to remind you that you are currently in Test Mode, and all signals get sent in said mode. All charts will display test data only while in Test Mode. -![Screenshot of the dashboard showing the Test Mode toggle in the upper left corner.](/docs/images/test_mode.png) +![Screenshot of the dashboard showing the Test Mode toggle in the upper left corner.](/assets/test_mode.png) ## Sending Signals in Test Mode diff --git a/docs/articles/update-package.md b/docs/articles/update-package.md index b0ceba9..4a6d60e 100644 --- a/docs/articles/update-package.md +++ b/docs/articles/update-package.md @@ -25,7 +25,7 @@ With that in mind, here's how to manually update a Swift package using Xcode: ## How to update a Swift Package in Xcode -![Screenshot of the left sidebar in Xcode 14, with the TelemetryDeck Swift Package highlighted](/docs/images/update_package.png) +![Screenshot of the left sidebar in Xcode 14, with the TelemetryDeck Swift Package highlighted](/assets/update_package.png) Updating packages in Xcode can be done using one of two ways. If you want to just update a single package individually – which we recommend by the way – do this: @@ -45,7 +45,7 @@ By default, Xcode and Swift Package Manager will not update the Major version of If you want to update to the next major version of a package, you can do this by manually changing the version requirement in the Xcode project. To do that, navigate to the project, select "Package Dependencies" and manually update the minimum version requirement to the next major version. -![Screenshot of the left sidebar in Xcode 14, with the TelemetryDeck Swift Package highlighted](/docs/images/update_next_major_version.png) +![Screenshot of the left sidebar in Xcode 14, with the TelemetryDeck Swift Package highlighted](/assets/update_next_major_version.png) For example, if you have a package that is currently at version `1.2.3`, and you want to update to version `2.0.0`, you can change the version requirement in the Xcode project to `2.0.0`. This will tell the Swift Package Manager to download the newest version of the package that is greater than `2.0.0`, but less than `3.0.0`. When a `2.0.1` comes out, you can update to that version by following the steps above. diff --git a/docs/basics/acquisition.md b/docs/basics/acquisition.md index 2e61e7e..454707b 100644 --- a/docs/basics/acquisition.md +++ b/docs/basics/acquisition.md @@ -30,7 +30,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - Are there patterns in my acquisition rate? - How effective are my marketing campaigns? -![Daily, Weekly, and Monthly New Users](/docs/images/acquisition-new-users.png) +![Daily, Weekly, and Monthly New Users](/assets/acquisition-new-users.png) **How to interpret the charts:** - **Consistent upward trend**: Your app is steadily gaining users – investigate what's working and double down @@ -47,7 +47,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - Is my app primarily attracting new users or maintaining existing ones? - How does acquisition compare to retention? -![Active vs New Users Ratio](/docs/images/acquisition-active-vs-new.png) +![Active vs New Users Ratio](/assets/acquisition-active-vs-new.png) **How to interpret the chart:** - **High ratio (>0.5)**: Many new users compared to your active base - suggesting strong acquisition but possibly weak retention @@ -63,7 +63,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - Which days of the week see the most new installations? - Do weekdays significantly outperform weekends for user acquisition? -![Acquisition Time Patterns](/docs/images/acquisition-by-time.png) +![Acquisition Time Patterns](/assets/acquisition-by-time.png) **How to interpret the charts:** - **Hour of day peaks**: Show prime discovery times (user-local) @@ -79,7 +79,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - Have specific events or campaigns created temporary spikes? - How can I differentiate between one-off events and genuine trends? -![Recent Acquisition Time Patterns](/docs/images/acquisition-by-time-last-weeks.png) +![Recent Acquisition Time Patterns](/assets/acquisition-by-time-last-weeks.png) **How to interpret the charts:** - **Four-week hourly view**: Identifies specific days with unusual activity @@ -95,7 +95,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - Should I prioritize specific hardware or screen sizes? - When can I safely drop support for older devices? -![New Users by Device Type](/docs/images/acquisition-device-distribution.png) +![New Users by Device Type](/assets/acquisition-device-distribution.png) **How to interpret the chart:** - **Top device models**: Prioritize testing and optimization for these devices @@ -111,7 +111,7 @@ New users are detected by the `TelemetryDeck.Acquisition.newInstallDetected` sig - What languages do my users speak? - Which markets should I prioritize for expansion? -![New Users by Country and Language](/docs/images/acquisition-geographic-distribution.png) +![New Users by Country and Language](/assets/acquisition-geographic-distribution.png) **How to interpret the charts:** - **Dominant regions**: Countries with the largest segments indicate your strongest markets diff --git a/docs/basics/activation.md b/docs/basics/activation.md index 4642b96..d17191e 100644 --- a/docs/basics/activation.md +++ b/docs/basics/activation.md @@ -31,7 +31,7 @@ Activated users are those with at least 5 minutes accumulated total usage time w - How effective is my onboarding experience? - What are the immediate activation patterns in the last 24 hours? -![Hourly, Daily, Weekly, and Monthly Activated Users](/docs/images/activation-activated-users.png) +![Hourly, Daily, Weekly, and Monthly Activated Users](/assets/activation-activated-users.png) **How to interpret the charts:** - **Hourly (last 24h)**: Shows recent activation activity and immediate trends – useful for spotting issues or validating recent changes @@ -49,7 +49,7 @@ Activated users are those with at least 5 minutes accumulated total usage time w - Do weekdays or weekends provide better conditions for user activation? - Are recent activation patterns consistent with long-term trends? -![Activation Time Patterns](/docs/images/activation-by-time.png) +![Activation Time Patterns](/assets/activation-by-time.png) **How to interpret the charts:** - **Hour of day patterns**: Show when users have time to properly explore your app (user-local timezone) @@ -66,7 +66,7 @@ Activated users are those with at least 5 minutes accumulated total usage time w - Should I optimize my Onboarding for specific hardware or screen sizes? - Are there platform-specific activation barriers? -![Activated Users by Device Type](/docs/images/activation-device-distribution.png) +![Activated Users by Device Type](/assets/activation-device-distribution.png) **How to interpret the chart:** - **Top-performing devices**: These provide the best activation experience – understand why @@ -83,7 +83,7 @@ Several other models follow at about 5.71% each. This fairly even split suggests - What languages correlate with higher activation rates? - Which markets provide the strongest foundation for growth? -![Activated Users by Country and Language](/docs/images/activation-geographic-distribution.png) +![Activated Users by Country and Language](/assets/activation-geographic-distribution.png) **How to interpret the charts:** - **Strong activation regions**: Countries where users consistently experience your app's value diff --git a/docs/basics/index.md b/docs/basics/index.md index eb880ad..1791928 100644 --- a/docs/basics/index.md +++ b/docs/basics/index.md @@ -16,7 +16,7 @@ order: 10 After integrating the TelemetryDeck SDK into your app, your data will start appearing in the TelemetryDeck dashboard. The main navigation tabs help you find different types of insights: -![TelemetryDeck Main Navigation](/docs/images/dashboard-main-nav.png) +![TelemetryDeck Main Navigation](/assets/dashboard-main-nav.png) Let's explore what you'll find in each section: @@ -24,7 +24,7 @@ Let's explore what you'll find in each section: The Overview tab provides a high-level summary of your app's performance, showing key metrics like daily active users, total users, user retention, app version distribution, and system version distribution: -![Overview Dashboard](/docs/images/dashboard-overview.png) +![Overview Dashboard](/assets/dashboard-overview.png) This view gives you immediate answers to: "How is my app performing right now?" and "Are my users upgrading to new versions?" @@ -32,7 +32,7 @@ This view gives you immediate answers to: "How is my app performing right now?" The Customers section organizes your user data according to the journey users take with your app, from discovery to monetization: -![Acquisition Dashboard](/docs/images/dashboard-acquisition.png) +![Acquisition Dashboard](/assets/dashboard-acquisition.png) Each tab focuses on a different stage of the user journey: @@ -110,7 +110,7 @@ TelemetryDeck also provides built-in presets for tracking purchases and revenue The Metrics section provides essential technical insights about your app across different devices and platforms: -![Metrics Dashboard - Devices](/docs/images/metrics-devices.png) +![Metrics Dashboard - Devices](/assets/metrics-devices.png) **Key metrics include:** @@ -139,7 +139,7 @@ The Metrics section provides essential technical insights about your app across The Explore section gives you direct access to your raw event data through multiple views: -![Explore Dashboard - Signal Types](/docs/images/dashboard-signal-types.png) +![Explore Dashboard - Signal Types](/assets/dashboard-signal-types.png) Here you can examine all signal types your app has sent, explore parameters attached to your events, view recent events chronologically, and use the query playground to experiment with data analysis. This section is particularly useful for debugging, understanding user behavior sequences, and diving deeper into specific user actions. @@ -162,7 +162,7 @@ Here you can examine all signal types your app has sent, explore parameters atta The Dashboards section allows you to create and organize custom visualizations: -![Custom Dashboards](/docs/images/dashboard-custom.png) +![Custom Dashboards](/assets/dashboard-custom.png) You can build insights using either the visual editor (for simple queries) or TelemetryDeck Query Language (TQL) for more complex analysis. Common dashboard setups include: @@ -223,7 +223,7 @@ Each insight can be organized into groups (displayed in the sidebar) to keep rel The Notebooks tab lets you combine live charts and markdown text in a single place, so you can document your questions, structure your investigations, and share insights with your team. Perfect for keeping context during long-running analyses, preparing presentations, or leaving notes for your future self. For example, here's an excerpt of a notebook: -![Sample Notebook investigating Onboarding issues with Explanations](/docs/images/dashboard-notebooks.png) +![Sample Notebook investigating Onboarding issues with Explanations](/assets/dashboard-notebooks.png) You can use Notebooks to: - Document your hypotheses and findings alongside live data @@ -253,7 +253,7 @@ See Notebooks in action in our [feature demo video](https://www.youtube.com/watc At the top of most dashboard pages, you'll find time filters that let you focus on specific periods: -![Filtering Data](/docs/images/dashboard-filtering-data.png) +![Filtering Data](/assets/dashboard-filtering-data.png) - **Last 30 Days** (default) – Shows data from the past month - **Test Mode** – Toggle to see data from development builds (when your app is run directly from your IDE) @@ -277,7 +277,7 @@ At the top of most dashboard pages, you'll find time filters that let you focus Many visualizations have interactive elements: -![Exploring Details](/docs/images/dashboard-exploring-details.png) +![Exploring Details](/assets/dashboard-exploring-details.png) - Hover over chart elements to see detailed values and source info - Use the "…" menu in the top right of cards for additional options diff --git a/docs/basics/metrics.md b/docs/basics/metrics.md index f5c438a..04e3d00 100644 --- a/docs/basics/metrics.md +++ b/docs/basics/metrics.md @@ -26,7 +26,7 @@ With TelemetryDeck's Metrics dashboard, these insights are automatically collect - Which platforms should I prioritize for development and testing? - When can I safely drop support for older devices? -![Device and Platform Distribution](/docs/images/metrics-devices.png) +![Device and Platform Distribution](/assets/metrics-devices.png) **How to interpret the charts:** - **Models**: Shows specific device models being used, helping prioritize testing @@ -44,7 +44,7 @@ With TelemetryDeck's Metrics dashboard, these insights are automatically collect - Are there patterns in build adoption? - Which SDK versions are in use across your user base? -![Version Analytics](/docs/images/metrics-versions.png) +![Version Analytics](/assets/metrics-versions.png) **How to interpret the charts:** - **App Versions**: Tracks adoption of your app releases over time @@ -61,7 +61,7 @@ With TelemetryDeck's Metrics dashboard, these insights are automatically collect - Which errors should I prioritize fixing? - Are errors occurring on specific devices or platforms? -![Error Monitoring](/docs/images/metrics-errors.png) +![Error Monitoring](/assets/metrics-errors.png) **How to interpret the charts:** - **Most Frequent Errors**: Ranks issues by occurrence count and percentage @@ -98,7 +98,7 @@ TelemetryDeck offers built-in presets for error tracking that require some confi - Should I invest in additional localizations? - Are users using my app in the same language as their device? -![Localization Insights](/docs/images/metrics-localization.png) +![Localization Insights](/assets/metrics-localization.png) **How to interpret the charts:** - **Preferred Language**: Shows user device language settings @@ -116,7 +116,7 @@ TelemetryDeck offers built-in presets for error tracking that require some confi - Does my app need better accessibility support? - How would design changes impact users with accessibility needs? -![Accessibility Usage](/docs/images/metrics-accessibility.png) +![Accessibility Usage](/assets/metrics-accessibility.png) **How to interpret the charts:** - **Preferred Content Size**: Shows text size preferences (88.43% use default size "L") diff --git a/docs/basics/pirate-metrics.md b/docs/basics/pirate-metrics.md index 01b179b..6436068 100644 --- a/docs/basics/pirate-metrics.md +++ b/docs/basics/pirate-metrics.md @@ -18,7 +18,7 @@ Pirate Metrics, also known as the AARRR framework, was created by venture capita This framework breaks down the complete user journey into five key stages that form a natural progression: -![AARRR Framework Chart](/docs/images/aarrr-framework.png) +![AARRR Framework Chart](/assets/aarrr-framework.png) 1. **Acquisition**: How users discover and install your app 2. **Activation**: How users experience your app for the first time diff --git a/docs/basics/retention.md b/docs/basics/retention.md index 7e83c31..6abd1d7 100644 --- a/docs/basics/retention.md +++ b/docs/basics/retention.md @@ -31,7 +31,7 @@ Returning users are those who have used your app for more than 5 sessions. - What are the immediate retention patterns in the last 24 hours? - How do retention trends compare across different time periods? -![Hourly, Daily, Weekly, and Monthly Returning Users](/docs/images/retention-returning-users.png) +![Hourly, Daily, Weekly, and Monthly Returning Users](/assets/retention-returning-users.png) **How to interpret the charts:** - **Hourly (last 24h)**: Shows recent returning user activity – useful for immediate validation of retention initiatives @@ -49,7 +49,7 @@ Returning users are those who have used your app for more than 5 sessions. - Do returning users prefer weekdays or weekends for app usage? - Are retention patterns changing over recent weeks? -![Retention Time Patterns](/docs/images/retention-by-time.png) +![Retention Time Patterns](/assets/retention-by-time.png) **How to interpret the charts:** - **Hour of day patterns**: Show when returning users are most active (user-local timezone) @@ -66,7 +66,7 @@ Returning users are those who have used your app for more than 5 sessions. - Are there platform-specific retention challenges? - Should I prioritize retention improvements for specific hardware? -![Returning Users by Device Type](/docs/images/retention-device-distribution.png) +![Returning Users by Device Type](/assets/retention-device-distribution.png) **How to interpret the charts:** - **Top-retention devices**: These provide the best long-term user experience @@ -82,7 +82,7 @@ Returning users are those who have used your app for more than 5 sessions. - What languages correlate with higher long-term engagement? - Are there cultural or regional patterns in user retention? -![Returning Users by Country and Language](/docs/images/retention-geographic-distribution.png) +![Returning Users by Country and Language](/assets/retention-geographic-distribution.png) **How to interpret the charts:** - **High-retention regions**: Countries where users consistently return to your app diff --git a/docs/guides/objective-c-setup.md b/docs/guides/objective-c-setup.md index 3693579..5258698 100644 --- a/docs/guides/objective-c-setup.md +++ b/docs/guides/objective-c-setup.md @@ -27,7 +27,7 @@ The TelemetryDeck Swift package uses Swift Package Manager. 1. Set the Dependency Rule to Up to Next Major Version. 1. Click Add Package. -![A screenshot of Xcode adding the TelemetryDeck Package](/docs/images/xcode-swift-package.png) +![A screenshot of Xcode adding the TelemetryDeck Package](/assets/xcode-swift-package.png) This will include the TelemetryDeck Swift Client into your app by downloading the source code. Feel free to browse the client's source code. It's tiny and you'll see for yourself how TelemetryDeck is hashing user identifiers before they ever reach the server. Privacy, yay! diff --git a/docs/guides/privacy-faq.md b/docs/guides/privacy-faq.md index 975e825..347089b 100644 --- a/docs/guides/privacy-faq.md +++ b/docs/guides/privacy-faq.md @@ -7,7 +7,7 @@ featured: true description: Frequently asked questions about TelemetryDeck's Privacy Policy lead: This FAQ answers the most common questions about our Privacy Policy and how to answer your users' questions. order: 10000 -headerImage: /docs/images/faq.jpg +headerImage: /assets/faq.jpg --- The TelemetryDeck SDK was developed from the ground up with privacy in mind. An important principle of TelemetryDeck is to store only the minimum amount of data necessary to identify specific user behaviors. diff --git a/docs/guides/react-setup.md b/docs/guides/react-setup.md index 5ff1982..c7d851e 100644 --- a/docs/guides/react-setup.md +++ b/docs/guides/react-setup.md @@ -161,7 +161,7 @@ Now that you've integrated TelemetryDeck, learn how to use the analytics platfor ## Sponsors -[](https://typedigital.de) +[](https://typedigital.de) The development of the TelemetryDeck React SDK was graciously provided by our friends at Augsburg-based web development agency [typedigital](https://typedigital.de). Thanks a lot, and check them out for your web application development needs. 🧑 diff --git a/docs/guides/swift-setup.md b/docs/guides/swift-setup.md index 9af5d71..5e96b6d 100644 --- a/docs/guides/swift-setup.md +++ b/docs/guides/swift-setup.md @@ -28,19 +28,19 @@ The TelemetryDeck Swift package uses Swift Package Manager. 1. Set the Dependency Rule to Up to Next Major Version 1. Press Add Package to continue -![A screenshot of Xcode adding the TelemetryDeck Package](/docs/images/xcode-swift-package1.png) +![A screenshot of Xcode adding the TelemetryDeck Package](/assets/xcode-swift-package1.png) This will include the TelemetryDeck Swift SDK into your app by downloading the source code. Feel free to browse the client's source code, it's tiny and you'll see for yourself how TelemetryDeck is hashing user identifiers before they ever reach the server. Privacy, yay! **Watch our [Quick Start video](https://www.youtube.com/watch?v=FA71bSnK_B8) to setup TelemetryDeck in 4 Minutes!** -[![TelemetryDeck Setup in 4 Minutes – Swift SDK Integration](/docs/images/yt-4-minute-setup.png)](https://www.youtube.com/watch?v=FA71bSnK_B8) +[![TelemetryDeck Setup in 4 Minutes – Swift SDK Integration](/assets/yt-4-minute-setup.png)](https://www.youtube.com/watch?v=FA71bSnK_B8) ## Including the package in your target Xcode will ask you to link the package with your target in the next screen, titled Choose Package Products for SwiftSDK. Set the Add to target column to your app target for TelemetryDeck (not "TelemetryClient", which is deprecated) and click Add Package to complete the integration. -![A screenshot of Xcode setting the target for the TelemetryDeck library](/docs/images/xcode-swift-package2.png) +![A screenshot of Xcode setting the target for the TelemetryDeck library](/assets/xcode-swift-package2.png) {% noteinfo "Link Library with more than one Target" %} diff --git a/docs/guides/vue-setup.md b/docs/guides/vue-setup.md index 6d58dc8..dba9fd7 100644 --- a/docs/guides/vue-setup.md +++ b/docs/guides/vue-setup.md @@ -153,7 +153,7 @@ Now that you've integrated TelemetryDeck, learn how to use the analytics platfor ## Sponsors -[](https://www.peerigon.com) +[](https://www.peerigon.com) The development of the TelemetryDeck Vue SDK was graciously provided by our friends at Augsburg-based bespoke software development company [Peerigon](https://www.peerigon.com). Thanks a lot, and check them out for your application development needs. 🧑 diff --git a/docs/integrations/revenuecat.md b/docs/integrations/revenuecat.md index 8a4e73b..022d834 100644 --- a/docs/integrations/revenuecat.md +++ b/docs/integrations/revenuecat.md @@ -93,7 +93,7 @@ Now we need to tell RevenueCat to send copies of all events over to TelemetryDec - Select **TelemetryDeck** - Click **Add Integration** to confirm -![A screenshot of RevenueCat's TelemetryDeck Integration](/docs/images/rc-td-1.png) -![A screenshot of RevenueCat's TelemetryDeck Integration](/docs/images/rc-td-2.png) +![A screenshot of RevenueCat's TelemetryDeck Integration](/assets/rc-td-1.png) +![A screenshot of RevenueCat's TelemetryDeck Integration](/assets/rc-td-2.png) And you're done. RevenueCat events should now arrive and be mixed in with your TelemetryDeck signals πŸ₯³ From 4af87ee328384f22889e3b3d1d86b5950a5ff04c Mon Sep 17 00:00:00 2001 From: Konstantin Kostov Date: Sun, 10 May 2026 12:37:37 +0200 Subject: [PATCH 14/15] feat: try grouping sections --- zensical.toml | 130 ++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 121 insertions(+), 9 deletions(-) diff --git a/zensical.toml b/zensical.toml index 22920b5..cd9a34a 100644 --- a/zensical.toml +++ b/zensical.toml @@ -41,16 +41,128 @@ Copyright © 2026 TelemetryDeck GmbH """ # Zensical supports both implicit navigation and explicitly defined navigation. -# If you decide not to define a navigation here then Zensical will simply -# derive the navigation structure from the directory structure of your -# "docs_dir". The definition below demonstrates how a navigation structure -# can be defined using TOML syntax. +# Pages are grouped thematically below; group titles map to TOML inline tables, +# and a value can be either a path (single page) or an array (collapsible group). # # Read more: https://zensical.org/docs/setup/navigation/ -# nav = [ -# { "Get started" = "index.md" }, -# { "Markdown in 5min" = "markdown.md" }, -# ] +nav = [ + { "Welcome" = "index.md" }, + { "SDK Setup" = [ + { "Swift" = "guides/swift-setup.md" }, + { "Android (Kotlin)" = "guides/android-setup.md" }, + { "Flutter" = "guides/flutter-setup.md" }, + { "JavaScript" = "guides/javascript-setup.md" }, + { "React" = "guides/react-setup.md" }, + { "Vue" = "guides/vue-setup.md" }, + { "Web" = "guides/web-setup.md" }, + { "Objective-C" = "guides/objective-c-setup.md" }, + { "Privacy FAQ" = "guides/privacy-faq.md" }, + ] }, + { "Analytics Basics" = [ + { "Overview" = "basics/index.md" }, + { "Acquisition" = "basics/acquisition.md" }, + { "Activation" = "basics/activation.md" }, + { "Retention" = "basics/retention.md" }, + { "Metrics" = "basics/metrics.md" }, + { "Pirate Metrics (AARRR)" = "basics/pirate-metrics.md" }, + { "Built-in Presets" = [ + { "Purchases" = "articles/preset-purchases.md" }, + { "Errors" = "articles/preset-errors.md" }, + { "Navigation signals" = "articles/navigation-signals.md" }, + { "Duration signals" = "articles/duration-signals.md" }, + ] }, + ] }, + { "Insights & Dashboards" = [ + { "Insights overview" = "articles/insights.md" }, + { "Daily active users" = "articles/insights-about-daily-users.md" }, + { "Monthly active users" = "articles/insights-about-monthly-users.md" }, + { "Referrers" = "articles/insights-about-referrers.md" }, + { "System version distribution" = "articles/insights-about-system-version.md" }, + { "Latest version adoption" = "articles/check-if-users-upgrade-to-latest-app-version.md" }, + { "Funnel insights" = "articles/how-to-funnel-insights.md" }, + { "Filter setup" = "articles/set-up-filters-insights.md" }, + { "Custom dashboards" = "articles/create-custom-dashboards.md" }, + { "Notebooks" = "articles/notebooks.md" }, + ] }, + { "Signal Concepts" = [ + { "Namespaces" = "articles/namespaces.md" }, + { "Signal type naming" = "articles/signal-type-naming.md" }, + { "Test mode" = "articles/test-mode.md" }, + { "Updating the SDK" = "articles/update-package.md" }, + { "The Grand Rename" = "articles/grand-rename.md" }, + { "TelemetryClient (legacy)" = "articles/telemetry-client.md" }, + ] }, + { "Privacy & Compliance" = [ + { "How anonymization works" = "articles/anonymization-how-it-works.md" }, + { "Apple App Privacy" = "articles/apple-app-privacy.md" }, + { "App Privacy Report" = "articles/app-privacy-report.md" }, + { "App Tracking Transparency" = "articles/app-tracking-transparency.md" }, + { "Hosting solutions" = "articles/hosting-solutions.md" }, + ] }, + { "Account & Organization" = [ + { "Make an account" = "articles/making-account.md" }, + { "Invite members" = "articles/invite-members-to-organization.md" }, + { "Login options" = "articles/login-options.md" }, + ] }, + { "Recipes" = [ + { "Averaging numbers" = "recipes/averagaging-numbers.md" }, + { "Listing events" = "recipes/listing-events.md" }, + { "Views per purchase" = "recipes/views-per-purchase-example.md" }, + ] }, + { "Integrations" = [ + { "RevenueCat" = "integrations/revenuecat.md" }, + { "Superwall" = "integrations/superwall.md" }, + { "Google Tag Manager" = "integrations/web-setup-google-tag-manager.md" }, + ] }, + { "Server-side Ingest" = [ + { "Default parameters" = "ingest/default-parameters.md" }, + { "Ingest API v2" = "ingest/v2.md" }, + { "Ingest API v1 (legacy)" = "ingest/v1.md" }, + ] }, + { "Reference" = [ + { "Signals API" = [ + { "Signals reference" = "api/signals-reference.md" }, + { "Insights reference" = "api/insights-reference.md" }, + { "Run a query" = "api/api-run-query.md" }, + { "Query from insight" = "api/api-query-from-insight.md" }, + { "API tokens" = "api/api-token.md" }, + ] }, + { "TQL" = [ + { "TQL guidelines" = "tql/firstGuideline.md" }, + { "TQL query reference" = "tql/query.md" }, + { "Query context" = "tql/queryContext.md" }, + { "Query type" = "tql/queryType.md" }, + { "Query types" = [ + { "Timeseries" = "tql/timeseries.md" }, + { "Top N" = "tql/topN.md" }, + { "Group By" = "tql/groupBy.md" }, + { "Scan" = "tql/scan.md" }, + { "Funnel" = "tql/funnel.md" }, + { "Retention" = "tql/retention.md" }, + { "Experiment" = "tql/experiment.md" }, + { "Funnels (deprecated)" = "tql/funnels.md" }, + ] }, + { "Filters & time" = [ + { "Filters" = "tql/filters.md" }, + { "Base filters" = "tql/baseFilters.md" }, + { "Time intervals" = "tql/time-intervals.md" }, + ] }, + { "Aggregators" = [ + { "Aggregators" = "tql/aggregators.md" }, + { "Post-aggregators" = "tql/post-aggregators.md" }, + ] }, + { "Specs & helpers" = [ + { "Dimension spec" = "tql/dimensionSpec.md" }, + { "Extraction function" = "tql/extractionFunction.md" }, + { "Granularity" = "tql/granularity.md" }, + { "TopN metric spec" = "tql/topNMetricSpec.md" }, + { "Value formatter" = "tql/valueFormatter.md" }, + { "Descending" = "tql/descending.md" }, + ] }, + ] }, + ] }, + { "Glossary" = "glossary.md" }, +] # With the "extra_css" option you can add your own CSS styling to customize # your Zensical project according to your needs. You can add any number of @@ -213,7 +325,7 @@ features = [ # When sections are enabled, top-level sections are rendered as groups in # the sidebar for viewports above 1220px, but remain as-is on mobile. # https://zensical.org/docs/setup/navigation/#navigation-sections - "navigation.sections", + #"navigation.sections", # When tabs are enabled, top-level sections are rendered in a menu layer # below the header for viewports above 1220px, but remain as-is on mobile. From 5e8671b123ef0404e55185b2ed561d8dd1f8126e Mon Sep 17 00:00:00 2001 From: Konstantin Kostov Date: Sun, 10 May 2026 12:46:18 +0200 Subject: [PATCH 15/15] feat: try serving markdown --- ...-static-web-apps-purple-bush-012fe8010.yml | 2 + .github/workflows/docs.yml | 2 + README.md | 10 + scripts/build_llms.py | 255 ++++++++++++++++++ staticwebapp.config.json | 6 + 5 files changed, 275 insertions(+) create mode 100644 scripts/build_llms.py create mode 100644 staticwebapp.config.json diff --git a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml index 593baec..1518d01 100644 --- a/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml +++ b/.github/workflows/azure-static-web-apps-purple-bush-012fe8010.yml @@ -29,6 +29,8 @@ jobs: python-version: 3.x - run: pip install zensical - run: zensical build --clean + - name: Generate llms.txt and ship raw markdown + run: python3 scripts/build_llms.py - name: Build And Deploy id: builddeploy uses: Azure/static-web-apps-deploy@v1 diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index 47ee722..70ed450 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -22,6 +22,8 @@ jobs: python-version: 3.x - run: pip install zensical - run: zensical build --clean + - name: Generate llms.txt and ship raw markdown + run: python3 scripts/build_llms.py - uses: actions/upload-pages-artifact@v5 with: path: site diff --git a/README.md b/README.md index 4ca93c3..6de2adb 100644 --- a/README.md +++ b/README.md @@ -12,3 +12,13 @@ Check out `articles/documentation.md` for an overview of how documentation pages We use Python `pip`. You can follow the setups at https://zensical.org/docs/get-started/#installation for the initial setup. Note: Make sure the Python version is recent e.g. 3.14 or later (`python3 --version`). + +## LLM and agent friendly output + +Every page is also published as raw Markdown alongside the rendered HTML. After `zensical build`, run `python3 scripts/build_llms.py` to: + +- copy each source `.md` from `docs/` into the corresponding location in `site/` (so `https://docs.telemetrydeck.com/articles/insights.md` returns the source for `/articles/insights/`), +- write `site/llms.txt` following the [llms.txt](https://llmstxt.org) convention, +- write `site/llms-full.txt` containing every page concatenated for one-shot ingestion. + +Both deploy workflows run this step automatically after the Zensical build. diff --git a/scripts/build_llms.py b/scripts/build_llms.py new file mode 100644 index 0000000..97a4da0 --- /dev/null +++ b/scripts/build_llms.py @@ -0,0 +1,255 @@ +"""Generate llms.txt, llms-full.txt, and ship raw .md sources alongside the +rendered HTML so coding agents and LLMs can consume the documentation. + +Run after `zensical build`. Reads: + - zensical.toml (for site metadata and navigation) + - docs/ (source markdown) + +Writes into the existing site/ directory: + - site/.md for every source page (preserves directory layout) + - site/llms.txt structured index per https://llmstxt.org + - site/llms-full.txt all page content concatenated for one-shot consumption +""" + +from __future__ import annotations + +import re +import shutil +import sys +import tomllib +from dataclasses import dataclass +from pathlib import Path +from typing import Iterable + +ROOT = Path(__file__).resolve().parent.parent +CONFIG_PATH = ROOT / "zensical.toml" +DOCS_DIR = ROOT / "docs" +SITE_DIR = ROOT / "site" +STATIC_WEB_APP_CONFIG = ROOT / "staticwebapp.config.json" +DEFAULT_SITE_URL = "https://docs.telemetrydeck.com" + +FRONTMATTER_RE = re.compile(r"^---\n(.*?)\n---\n", re.DOTALL) + + +@dataclass +class Page: + rel_path: str + title: str + description: str + + +def load_config() -> dict: + with CONFIG_PATH.open("rb") as f: + return tomllib.load(f) + + +def parse_frontmatter(text: str) -> tuple[dict, str]: + """Extract YAML-ish frontmatter without pulling in PyYAML. + + Only top-level scalar key/value pairs are read β€” that is all we need + (title, description, lead). Lists and nested maps are skipped. + """ + match = FRONTMATTER_RE.match(text) + if not match: + return {}, text + data: dict[str, str] = {} + current_key: str | None = None + for line in match.group(1).splitlines(): + if not line.strip() or line.lstrip().startswith("#"): + continue + if line.startswith(" ") or line.startswith("\t"): + current_key = None + continue + if ":" not in line: + continue + key, _, value = line.partition(":") + key = key.strip() + value = value.strip().strip('"').strip("'") + current_key = key + data[key] = value + body = text[match.end():] + return data, body + + +def page_for(rel_path: str, fallback: str | None = None) -> Page | None: + src = DOCS_DIR / rel_path + if not src.is_file(): + print(f"warning: missing source page {rel_path}", file=sys.stderr) + return None + text = src.read_text(encoding="utf-8") + fm, _ = parse_frontmatter(text) + title = fm.get("title") or fallback or fallback_title(rel_path) + description = fm.get("description") or fm.get("lead", "") + return Page(rel_path=rel_path, title=title, description=description) + + +def fallback_title(rel_path: str) -> str: + stem = Path(rel_path).stem + if stem == "index": + stem = Path(rel_path).parent.name or "Home" + return stem.replace("-", " ").replace("_", " ").title() + + +def md_url(rel_path: str, base_url: str) -> str: + return f"{base_url.rstrip('/')}/{rel_path}" + + +def copy_source_markdown(rel_paths: Iterable[str]) -> int: + count = 0 + for rel_path in rel_paths: + src = DOCS_DIR / rel_path + dst = SITE_DIR / rel_path + if not src.is_file(): + continue + dst.parent.mkdir(parents=True, exist_ok=True) + shutil.copy2(src, dst) + count += 1 + return count + + +def collect_nav_pages( + nav: list, prefix: tuple[str, ...] = () +) -> list[tuple[tuple[str, ...], str, str]]: + """Walk the nav structure and yield (section_path, page_rel_path, label) tuples.""" + pages: list[tuple[tuple[str, ...], str, str]] = [] + for entry in nav: + if not isinstance(entry, dict) or len(entry) != 1: + continue + label, value = next(iter(entry.items())) + if isinstance(value, str): + pages.append((prefix, value, label)) + elif isinstance(value, list): + pages.extend(collect_nav_pages(value, prefix + (label,))) + return pages + + +def all_source_pages() -> list[str]: + return sorted( + str(p.relative_to(DOCS_DIR)).replace("\\", "/") + for p in DOCS_DIR.rglob("*.md") + ) + + +def render_llms_txt(config: dict, base_url: str) -> str: + project = config.get("project", {}) + site_name = project.get("site_name", "Documentation") + site_description = project.get("site_description", "") + nav = project.get("nav", []) + + nav_pages = collect_nav_pages(nav) + seen: set[str] = set() + + lines: list[str] = [f"# {site_name}", ""] + if site_description: + lines += [f"> {site_description}", ""] + lines += [ + "Every documentation page is also available as Markdown by visiting", + "the same URL with a `.md` suffix (for example `/articles/insights.md`).", + "A single concatenated copy of all pages lives at `/llms-full.txt`.", + "", + ] + + sections: dict[tuple[str, ...], list[Page]] = {} + for section_path, rel_path, label in nav_pages: + if rel_path in seen: + continue + seen.add(rel_path) + page = page_for(rel_path, fallback=label) + if page is None: + continue + sections.setdefault(section_path, []).append(page) + + for section_path, pages in sections.items(): + heading = " / ".join(section_path) if section_path else "Overview" + lines.append(f"## {heading}") + lines.append("") + for page in pages: + url = md_url(page.rel_path, base_url) + entry = f"- [{page.title}]({url})" + if page.description: + entry += f": {page.description}" + lines.append(entry) + lines.append("") + + extras = sorted( + rel_path for rel_path in all_source_pages() if rel_path not in seen + ) + if extras: + lines.append("## Optional") + lines.append("") + for rel_path in extras: + page = page_for(rel_path) + if page is None: + continue + url = md_url(rel_path, base_url) + entry = f"- [{page.title}]({url})" + if page.description: + entry += f": {page.description}" + lines.append(entry) + lines.append("") + + return "\n".join(lines).rstrip() + "\n" + + +def render_llms_full_txt(config: dict, base_url: str) -> str: + project = config.get("project", {}) + site_name = project.get("site_name", "Documentation") + + parts: list[str] = [ + f"# {site_name} (full text)", + "", + "Concatenated source for every documentation page. Pages are separated", + "by horizontal rules and labelled with their canonical URL.", + "", + ] + + for rel_path in all_source_pages(): + page = page_for(rel_path) + if page is None: + continue + url = md_url(rel_path, base_url) + text = (DOCS_DIR / rel_path).read_text(encoding="utf-8") + parts += [ + "---", + "", + f"# {page.title}", + "", + f"Source: {url}", + "", + text.rstrip(), + "", + ] + + return "\n".join(parts).rstrip() + "\n" + + +def main() -> int: + if not SITE_DIR.is_dir(): + print(f"error: site directory not found at {SITE_DIR}", file=sys.stderr) + print("run `zensical build` before this script", file=sys.stderr) + return 1 + + config = load_config() + site_url = config.get("project", {}).get("site_url") or DEFAULT_SITE_URL + base_url = site_url.rstrip("/") + + rel_paths = all_source_pages() + copied = copy_source_markdown(rel_paths) + print(f"copied {copied} markdown sources into {SITE_DIR}") + + if STATIC_WEB_APP_CONFIG.is_file(): + shutil.copy2(STATIC_WEB_APP_CONFIG, SITE_DIR / STATIC_WEB_APP_CONFIG.name) + print(f"copied {STATIC_WEB_APP_CONFIG.name} into {SITE_DIR}") + + llms_txt = render_llms_txt(config, base_url) + (SITE_DIR / "llms.txt").write_text(llms_txt, encoding="utf-8") + print(f"wrote {SITE_DIR / 'llms.txt'}") + + llms_full_txt = render_llms_full_txt(config, base_url) + (SITE_DIR / "llms-full.txt").write_text(llms_full_txt, encoding="utf-8") + print(f"wrote {SITE_DIR / 'llms-full.txt'}") + return 0 + + +if __name__ == "__main__": + sys.exit(main()) diff --git a/staticwebapp.config.json b/staticwebapp.config.json new file mode 100644 index 0000000..d69301a --- /dev/null +++ b/staticwebapp.config.json @@ -0,0 +1,6 @@ +{ + "mimeTypes": { + ".md": "text/markdown; charset=utf-8", + ".txt": "text/plain; charset=utf-8" + } +}