Skip to content

Commit

Permalink
Add PlacePage donations
Browse files Browse the repository at this point in the history
  • Loading branch information
rtsisyk committed Nov 26, 2024
1 parent ea524dc commit ea6f4d6
Show file tree
Hide file tree
Showing 10 changed files with 326 additions and 4 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
dist/
.wrangler/
# Autogenerated by esbuild.
workers-site/index.js
node_modules/
Expand Down
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,10 @@ npm i

Use `npx wrangler dev` for localhost development and for testing using Cloudflare dev tools.

```
curl -H "X-OM-DataVersion: 241001" -H "X-OM-AppVersion: 2024.10.22-10-Google" -H 'Accept-Language: fr-FR' http://localhost:8787/maps
```

## Update node dependencies to their major versions

```bash
Expand Down
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@
"scripts": {
"build": "esbuild src/index.ts --bundle --outfile=dist/index.js",
"test": "jest",
"format": "prettier --write '{src,test}/**/*.{ts,tsx}' '*.json' '*.toml' '.github/**/*.yml'",
"format:ci": "prettier --check '{src,test}/**/*.{ts,tsx}' '*.json' '*.toml' '.github/**/*.yml'",
"format": "prettier --write '{src,test}/**/*.{ts,tsx,json}' '*.json' '*.toml' '.github/**/*.yml'",
"format:ci": "prettier --check '{src,test}/**/*.{ts,tsx,json}' '*.json' '*.toml' '.github/**/*.yml'",
"upgrade": "npx npm-check-updates -u && npm install",
"logs": "npx wrangler tail --env prod --format json"
},
Expand Down
44 changes: 44 additions & 0 deletions src/locales.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
{
"en": {
"placePagePrompt": "Organic Maps app is free for everyone, thanks to your donations. No ads. No trackers. Open source.",
"perMonth": "/month",
"perYear": "/year",
"otherAmount": "Other"
},
"de": {
"placePagePrompt": "Organic Maps ist dank deiner Spenden für alle kostenlos. Keine Werbung. Keine Tracker. Open Source.",
"perMonth": "/Monat",
"perYear": "/Jahr",
"otherAmount": "Andere"
},
"fr": {
"placePagePrompt": "L'application Organic Maps est gratuite pour tout le monde grâce à vos dons. Pas de publicité. Pas de trackers. Open-source.",
"perMonth": "/mois",
"perYear": "/an",
"otherAmount": "Autre"
},
"nl": {
"placePagePrompt": "De Organic Maps app is gratis voor iedereen dankzij jullie donaties. Geen advertenties. Geen trackers. Open-source.",
"perMonth": "/maand",
"perYear": "/jaar",
"otherAmount": "Ander"
},
"it": {
"placePagePrompt": "L'app Organic Maps è gratuita per tutti grazie alle vostre donazioni. Nessuna pubblicità. Nessun tracker. Open-source.",
"perMonth": "/mese",
"perYear": "/anno",
"otherAmount": "Altro"
},
"es": {
"placePagePrompt": "Organic Maps es gratis para todos gracias a sus donaciones. Sin anuncios. Sin rastreadores. Código abierto.",
"perMonth": "/mes",
"perYear": "/año",
"otherAmount": "Otro"
},
"pt": {
"placePagePrompt": "O app Organic Maps é gratuito para todos graças às suas doações. Sem anúncios. Sem rastreadores. Código aberto.",
"perMonth": "/mês",
"perYear": "/ano",
"otherAmount": "Outro"
}
}
15 changes: 15 additions & 0 deletions src/locales.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import LOCALES_JSON from './locales.json';

export interface Locale {
placePagePrompt: string;
perMonth: string;
perYear: string;
otherAmount: string;
}

export interface Locales {
[key: string]: Locale;
}

const LOCALES = LOCALES_JSON as Locales;
export default LOCALES;
198 changes: 198 additions & 0 deletions src/products.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,198 @@
{
"FR": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"DE": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"NL": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"IT": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"ES": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"PT": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"BE": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"AT": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"LU": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"MC": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"AD": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"SM": [
{
"title": "4,99€$per_month",
"link": "https://donate.stripe.com/6oEg2912f2c81r200j"
},
{
"title": "34,99€$per_year",
"link": "https://donate.stripe.com/eVa2bjdP19EA0mY6oI"
},
{
"title": "$other",
"link": "https://donate.stripe.com/28odU16mzg2Yc5GfYY"
}
],
"GB": [
{
"title": "£4.99$per_month",
"link": "https://donate.stripe.com/8wMg29fX98Awd9K28u"
},
{
"title": "£34.99$per_year",
"link": "https://donate.stripe.com/eVabLT9yL2c89Xy7sP"
},
{
"title": "$other",
"link": "https://donate.stripe.com/6oE7vD26j3gc2v69AC"
}
],
"US": [
{
"title": "$5.49$per_month",
"link": "https://donate.stripe.com/00g3fncKXcQMedO5kL"
},
{
"title": "$36.99$per_year",
"link": "https://donate.stripe.com/bIY6rz5ivcQM9XyaF6"
},
{
"title": "$other",
"link": "https://donate.stripe.com/7sIcPX5ivg2Y2v6145"
}
]
}
40 changes: 40 additions & 0 deletions src/products.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import LOCALES from './locales';
import PRODUCTS_JSON from './products.json';

export interface Product {
title: string;
link: string;
}

const PRODUCTS = PRODUCTS_JSON as Record<string, Product[]>;

export interface ProductsConfig {
placePagePrompt: string;
products: Product[];
}

export function getProducts(locale: string | null): ProductsConfig | undefined {
if (!locale) {
return undefined;
}
const parts = locale.split(/[-_]/);
const language = parts[0].toLowerCase();
const country = parts[1] ? parts[1].toUpperCase() : '';

const products = PRODUCTS[country];
const trans = LOCALES[language];
if (products === undefined || trans === undefined) {
return undefined;
}

return {
placePagePrompt: trans.placePagePrompt,
products: products.map((product) => ({
...product,
title: product.title
.replace('$other', trans.otherAmount)
.replace('$per_month', trans.perMonth)
.replace('$per_year', trans.perYear),
})),
};
}
9 changes: 7 additions & 2 deletions src/servers.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { parseDataVersion, parseAppVersion } from './versions';
import { getProducts, ProductsConfig } from './products';

export const DATA_VERSIONS = [
210529, //
Expand Down Expand Up @@ -125,7 +126,7 @@ export async function getServersList(request: Request) {
if (dataVersion === null) {
// Older clients download from the archive.
servers = [SERVER.backblaze];
} else if (dataVersion == 240702 && abusedVersions.includes(request.headers.get('x-om-appversion'))) {
} else if (dataVersion == 240702 && abusedVersions.includes(request.headers.get('x-om-appversion') || 'unknown')) {
// Redirect https://apps.apple.com/us/app/mapxplorer-navigation-radar/id6463052823
// who abuses our servers to a slow download "trap" node.
return new Response('["https://cdn-fi2.organicmaps.app/"]', {
Expand Down Expand Up @@ -176,6 +177,7 @@ export async function getServersList(request: Request) {
DonateUrl?: string;
NY?: string;
};
productsConfig?: ProductsConfig;
} = {
servers: servers,
};
Expand Down Expand Up @@ -203,11 +205,14 @@ export async function getServersList(request: Request) {

if (donatesEnabled) {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore workarounds error TS2339: Property 'country' does not exist on type 'IncomingRequestCfProperties<unknown>'.
response.settings = {
DonateUrl: DONATE_URL,
NY: 'false', // Must be `string` instead of `bool`, otherwise clients will crash
};
if (appVersion.code >= 241022) {
const locale = request.headers.get('accept-language');
response.productsConfig = getProducts(locale);
}
}

return new Response(JSON.stringify(response), {
Expand Down
14 changes: 14 additions & 0 deletions test/products.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { describe, expect, test } from '@jest/globals';
import { getProducts } from '../src/products';

describe('getProducts', () => {
test('fr-FR', () => {
const fr_FR = getProducts('fr-FR');
expect(fr_FR).toBeDefined();
if (!fr_FR) return;
expect(fr_FR.placePagePrompt).toBe(
"L'application Organic Maps est gratuite pour tout le monde grâce à vos dons. Pas de publicité. Pas de trackers. Open-source.",
);
expect(fr_FR.products[fr_FR.products.length - 1].title).toEqual('Autre');
});
});
1 change: 1 addition & 0 deletions tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
"preserveConstEnums": true,
"sourceMap": true,
"esModuleInterop": true,
"resolveJsonModule": true,
"types": ["@cloudflare/workers-types"]
},
"include": ["src/"],
Expand Down

0 comments on commit ea6f4d6

Please sign in to comment.