Add affiliate links feature#146
Open
wtfloris wants to merge 13 commits into
Open
Conversation
Owner
Author
Prod migrationThese tables aren't auto-migrated — run this against the prod DB before deploying (mirrors BEGIN;
CREATE TABLE hestia.affiliate_categories (
id int4 GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
slug varchar NOT NULL,
name_en varchar NOT NULL,
name_nl varchar NOT NULL,
icon varchar NULL,
sort_order int4 DEFAULT 0 NOT NULL,
enabled bool DEFAULT true NOT NULL,
CONSTRAINT affiliate_categories_slug_key UNIQUE (slug)
);
CREATE TABLE hestia.affiliate_links (
id int4 GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
category_id int4 NOT NULL REFERENCES hestia.affiliate_categories(id),
provider varchar NOT NULL,
url varchar NOT NULL,
title_en varchar NULL,
title_nl varchar NULL,
blurb_en varchar NULL,
blurb_nl varchar NULL,
logo varchar NULL,
sort_order int4 DEFAULT 0 NOT NULL,
enabled bool DEFAULT true NOT NULL,
click_count int4 DEFAULT 0 NOT NULL,
created_at timestamptz DEFAULT CURRENT_TIMESTAMP NOT NULL,
updated_at timestamptz DEFAULT CURRENT_TIMESTAMP NOT NULL
);
CREATE INDEX affiliate_links_category_idx ON hestia.affiliate_links USING btree (category_id);
-- Grants: bot/scraper read via the `hestia` role; web reads + increments click_count via `svc_hestia_web`.
GRANT SELECT, INSERT, UPDATE, DELETE ON hestia.affiliate_categories, hestia.affiliate_links TO hestia, svc_hestia_web;
COMMIT;Notes:
|
Adds affiliate_categories/affiliate_links tables, /api/affiliate-links and /go/<id> redirect with click tracking, and bot /support (/steun) command. Donation system unchanged; /support referenced in start/stop and weekly reminder messages. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Renders /api/affiliate-links below the settings panel: permanent on desktop, collapsible accordion on mobile. Localized via i18n, re-renders on language toggle, links route through /go/<id>. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Move the Friday thanks/reminder into strings.py (en+nl) and send each subscriber their language via get_user_lang. Leads with /support, Tikkie as the alternative. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Rewrite EN/NL affiliate intro text and render the paragraph break. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Rewrite start/stop/support/weekly_reminder copy, fix MarkdownV2 escaping, make affiliate link title nullable + optional in /support, update tests. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Align web panel, /support and weekly reminder copy (small bonus, ~1 week, €79/mo). Move cost overview to an info icon, drop donation subtext from the modal. Add a swappable 'comparison' affiliate entry surfaced as a Pro tip on web and in /support; update tests. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2a09047 to
e9b3875
Compare
# Conflicts: # web/static/base.js
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Adds an affiliate-links framework so users can support Hestia by signing up for services (energy, internet, etc.) through partner links, as an alternative to donating. Surfaces on the Telegram bot and web dashboard; the API is ready for the iOS app.
What's included
Data model (
misc/hestia.ddl)affiliate_categories(slug, localizedname_en/name_nl, icon, ordering, enabled)affiliate_links(provider, realurl, optional localizedtitle/blurb,logo, ordering, enabled,click_count) —title_*are nullable; rendering skips them when unsettargetsare handledBackend / API (
web/hestia_web/app.py)GET /api/affiliate-links?lang=en|nl— auth via session cookie orX-Device-Id(same as the other app APIs). Returns categories→links with ago_url; the raw affiliateurlis never exposedGET /go/<id>— public 302 redirect to the real URL with server-side click counting; rejects non-http(s) schemes, 404s unknown/disabled linksTelegram bot (
hestia/bot.py,strings.py)/support+/steuncommands, fully localized (en/nl)/start,/stop,/help, and the weekly reminder broadcast (which is now localized per-subscriber viaget_user_lang)Web dashboard (
templates/dashboard.html,static/)/api/affiliate-links, localized, re-renders on language toggle, opens links via/go/<id>Notes
CREATE TABLEs + grants run (they're not auto-migrated).https://hestia.bot/go/<id>(hardcodedHESTIA_BASE_URL); the web derives the host from the request.go_urlin the user's default browser (UIApplication.open), not an in-appSFSafariViewController, so affiliate attribution cookies land in the real browser.🤖 Generated with Claude Code