diff --git a/apps.html b/apps.html index 16c56d2e..bac7697c 100644 --- a/apps.html +++ b/apps.html @@ -80,6 +80,8 @@

All Apps

@@ -833,9 +835,9 @@

Chaos - Stranger Missions

const count = document.getElementById('finder-count'); const empty = document.getElementById('finder-empty'); const groups = { - 'quick-games': ['blur','instant-judge','nodo','brain-burst','snap-judge','daily-duel','percent-pulse','two-truths','key-clash','flinch','tier-rank-me'], + 'quick-games': ['blur','instant-judge','nodo','brain-burst','snap-judge','daily-duel','percent-pulse','two-truths','key-clash','tier-rank-me'], habits: ['true-me','future-me','water-reminder','gratitude-log','gratitude-challenge','mood-log','sleep-prep','eye-break','stretch-reminder','win-log'], - decisions: ['food-roulette','movie-roulette','date-roulette','dinner-home-roulette','trip-roulette','study-roulette','what-to-do','pickwhirl','truth-roulette','quick-local-food'], + decisions: ['food-roulette','movie-roulette','date-roulette','dinner-home-roulette','trip-roulette','study-roulette','what-to-do','chore-roulette','truth-roulette','quick-local-food'], ai: ['debate-me','voice-memo','future-me','date-pilot','global-news','pantry-ai','name-maker','idea-market','life-trace'] }; const clean = value => value.normalize('NFKC').toLocaleLowerCase().trim(); diff --git a/docs/APP_DISCOVERY_GROWTH_RELEASE_2026-10-27.md b/docs/APP_DISCOVERY_GROWTH_RELEASE_2026-10-27.md index b5a452e9..3c4f4d87 100644 --- a/docs/APP_DISCOVERY_GROWTH_RELEASE_2026-10-27.md +++ b/docs/APP_DISCOVERY_GROWTH_RELEASE_2026-10-27.md @@ -13,12 +13,12 @@ From a **fresh main** checkout of this site repository, after checking working t ```bash git pull --ff-only bash scripts/publish_app_discovery.sh --dry-run -# Review the four changed destination paths. Never pass --delete. +# Review the eleven specified destination paths. Never pass --delete. bash scripts/publish_app_discovery.sh --apply bash scripts/check_app_discovery_live.sh ``` -Only these files transfer: `index.html`, `apps.html`, `sitemap.xml`, `robots.txt`, `guides/quick-games/index.html`, `guides/daily-habits/index.html`, `support/brain-burst/index.html`, `support/snaplingo/index.html`, `support/face-reaction-battle/index.html`. The homepage links are tracked with `discovery_nav_click` and let visitors reach the search or guides without scrolling 92 cards. Every other VPS file, including privacy, support, policy, payment and ads assets, stays untouched. To override environment use `APP_SITE_DEPLOY_HOST` and `APP_SITE_DEPLOY_ROOT` with a known-safe absolute path. The script refuses unknown flags/invalid targets. +Only these files transfer: `index.html`, `apps.html`, `sitemap.xml`, `robots.txt`, `guides/quick-games/index.html`, `guides/daily-habits/index.html`, `guides/decision-helpers/index.html`, `guides/ai-tools/index.html`, `support/brain-burst/index.html`, `support/snaplingo/index.html`, `support/face-reaction-battle/index.html`. The homepage links are tracked with `discovery_nav_click` and let visitors reach the search or guides without scrolling 92 cards. Every other VPS file, including privacy, support, policy, payment and ads assets, stays untouched. To override environment use `APP_SITE_DEPLOY_HOST` and `APP_SITE_DEPLOY_ROOT` with a known-safe absolute path. The script refuses unknown flags/invalid targets. **Publish gate:** a dry-run is not publication. Only mark live once `check_app_discovery_live.sh` reports HTTP 200 and matches the homepage `discovery-links`, `id="find-app"`, both guide canonical URLs, guide click event and sitemap entries. After manual publication consider Google Search Console URL inspection and sitemap submission if the `appdevelopsk.com` property is available. @@ -63,4 +63,12 @@ A **restricted 3-day finalized GSC window (Oct 22–24)** was available, so do n - Preserve Google Play Install Referrer on each CTA. `download_click` adds `app` and `placement` so support hero CTA and page-details CTA can be compared; avoid raw visitor search content. - New `tests/search-landing-growth.test.mjs` and GitHub CI prevent catalog/product mismatches, fabricated ratings, missing store links, and missing live-check assertions. -After shipping the updated **nine** files from a fresh main checkout, run `bash scripts/check_app_discovery_live.sh`. Record the deploy timestamp, then compare **landing impressions/CTR**, **support CTA clicks by placement**, **Play visitors/install**, and **first completed app action** after enough data accumulates. The early data is directional only. +After shipping the updated **eleven** files from a fresh main checkout, run `bash scripts/check_app_discovery_live.sh`. Record the deploy timestamp, then compare **landing impressions/CTR**, **support CTA clicks by placement**, **Play visitors/install**, and **first completed app action** after enough data accumulates. The early data is directional only. + +## Additional organic discovery paths — 2026-10-27 + +- Two additional editorial choice guides: `/guides/decision-helpers/` and `/guides/ai-tools/`. Each includes four **non-hidden** apps from the local catalog, canonical metadata, truthful first-party publisher attribution, and per-app Play campaign links. +- Add both to homepage and searchable catalog discovery navigation, plus sitemap and VPS deployment/production checks. +- The catalog filter previously included stale app identifiers `flinch` (the published app is `daily-duel`) and `pickwhirl` (published app is `chore-roulette`). Removed stale names and used real catalog identifiers. +- A CI regression now checks every filter slug against the published catalog, including renamed apps, to prevent silent zero-result filters after future renames or delistings. The total listed app count is taken from `site_counts.json`, not a stale hardcoded 92. +- This does **not** create new Google Play installs on its own; the VPS must be updated and the customer conversion funnel measured. diff --git a/guides/ai-tools/index.html b/guides/ai-tools/index.html new file mode 100644 index 00000000..ff55d1f8 --- /dev/null +++ b/guides/ai-tools/index.html @@ -0,0 +1,85 @@ + + + + +AI apps for debate practice, voice notes and ideas | SK Apps + + + + + + + + + + + + +
+ +

AI apps for debate practice, voice notes and ideas

An AI app is useful when it helps with a specific task. Choose based on the input you have and the outcome you want: practice an argument, reflect by voice, track food at home or brainstorm names.

+
+
+

Choose for your situation

  1. Choose the task first. Debate practice and voice journaling are different activities, even though both may use AI. Pick one outcome to test.
  2. +
  3. Review generated material. AI text can be imperfect. Review suggestions before you rely on them, especially for important decisions.
  4. +
  5. Check current permissions and pricing. Visit each Google Play page for the latest feature, privacy and purchase details. Avoid entering confidential personal information into any app until you understand its controls.
+
+

Apps to explore

+

These are apps published by SK Apps. They are not third-party rankings. The Play listing is the source for current availability, device compatibility and purchase options.

+
+Debate Me - AI Debate Practice app icon +

Practise an argument

Debate Me - AI Debate Practice

+

A structured way to improve your reasoning through AI-assisted debate practice. AI debate practice to sharpen your arguments and win any discussion.

+See on Google Play +
+
+Speakly - AI Voice Diary app icon +

Reflect with voice

Speakly - AI Voice Diary

+

For speaking a journal entry instead of typing a daily note. Voice diary with AI — record, transcribe and track your mood by speaking.

+See on Google Play +
+
+Pantry AI - Smart Food Manager app icon +

Organise food at home

Pantry AI - Smart Food Manager

+

For tracking ingredients and expiry dates rather than remembering everything. Pantry tracker & food inventory: cut waste, track expiry dates, plan meals.

+See on Google Play +
+
+NameCraft app icon +

Brainstorm names

NameCraft

+

For generating naming ideas for a character, pet, business or project. AI name generator for baby, character, pet, business & username ideas.

+See on Google Play +
+
+

Not sure what to pick?

+

Pick one thing you want to finish today. If you need more choices, search all published apps or explore daily habit apps.

+
+ + + + diff --git a/guides/decision-helpers/index.html b/guides/decision-helpers/index.html new file mode 100644 index 00000000..f3938f34 --- /dev/null +++ b/guides/decision-helpers/index.html @@ -0,0 +1,85 @@ + + + + +Decision helper apps for choosing food, movies and activities | SK Apps + + + + + + + + + + + + +
+ +

Decision helper apps for choosing food, movies and activities

When choosing takes longer than doing, start with the kind of choice you need to make. These four SK Apps tools focus on different situations, from picking a restaurant to deciding what to do next.

+
+
+

Choose for your situation

  1. Start with your context. A restaurant picker is useful when your decision depends on nearby places. A movie picker is better when you already plan to watch something.
  2. +
  3. Agree on boundaries first. Set a time limit, budget or preferred category before you spin. Picking faster is only helpful if the option fits your situation.
  4. +
  5. Avoid comparing unrelated tools. A choice wheel will not verify local restaurant hours; a food finder will not tell you which movie fits your mood. Open the store description for current capabilities.
+
+

Apps to explore

+

These are apps published by SK Apps. They are not third-party rankings. The Play listing is the source for current availability, device compatibility and purchase options.

+
+Food Roulette app icon +

Where to eat

Food Roulette

+

When you need a nearby restaurant suggestion rather than another list to compare. What to eat? Spin the food roulette to pick a nearby restaurant in seconds.

+See on Google Play +
+
+Movie Roulette: Film Picker app icon +

What to watch

Movie Roulette: Film Picker

+

When the evening decision is about a film and you already know your mood. Movie picker: spin to decide what to watch by mood, genre and platform.

+See on Google Play +
+
+What To Do: Activity Picker app icon +

What to do right now

What To Do: Activity Picker

+

When you have free time but cannot decide on an activity. Activity picker to beat boredom — spin and decide what to do right now.

+See on Google Play +
+
+PickWhirl: Spin to Decide app icon +

Which option to pick

PickWhirl: Spin to Decide

+

When you want to spin among everyday possibilities, including chores and plans. Can't decide? Spin to pick chores, dinner, movies & more in one tap..

+See on Google Play +
+
+

Not sure what to pick?

+

Pick one thing you want to finish today. If you need more choices, search all published apps or explore quick mobile games.

+
+ + + + diff --git a/index.html b/index.html index 3ef2b845..6f7332e3 100644 --- a/index.html +++ b/index.html @@ -436,6 +436,8 @@

Featured Apps

🔎 Find an app 🎮 Quick games 📅 Daily habits + 🎲 Decision helpers + ✨ AI tools
diff --git a/scripts/check_app_discovery_live.sh b/scripts/check_app_discovery_live.sh index 1609a852..2c930682 100644 --- a/scripts/check_app_discovery_live.sh +++ b/scripts/check_app_discovery_live.sh @@ -19,13 +19,13 @@ grep -Fq 'discovery_nav_click' "$tmp/index.html" || { echo 'FAIL homepage discov fetch '/apps' 'apps.html' grep -Fq 'id="find-app"' "$tmp/apps.html" || { echo 'FAIL catalog search is stale' >&2; exit 1; } grep -Fq 'catalog_store_click' "$tmp/apps.html" || { echo 'FAIL store-click attribution is stale' >&2; exit 1; } -for slug in quick-games daily-habits; do +for slug in quick-games daily-habits decision-helpers ai-tools; do fetch "/guides/$slug/" "$slug.html" grep -Fq "https://appdevelopsk.com/guides/$slug/" "$tmp/$slug.html" || { echo "FAIL guide $slug content/canonical mismatch" >&2; exit 1; } grep -Fq 'guide_store_click' "$tmp/$slug.html" || { echo "FAIL $slug click measurement missing" >&2; exit 1; } done fetch '/sitemap.xml' 'sitemap.xml' -for slug in quick-games daily-habits; do +for slug in quick-games daily-habits decision-helpers ai-tools; do grep -Fq "https://appdevelopsk.com/guides/$slug/" "$tmp/sitemap.xml" || { echo "FAIL sitemap missing $slug" >&2; exit 1; } done for slug in brain-burst snaplingo; do diff --git a/scripts/publish_app_discovery.sh b/scripts/publish_app_discovery.sh index aac41e81..5b8b6a3f 100644 --- a/scripts/publish_app_discovery.sh +++ b/scripts/publish_app_discovery.sh @@ -15,7 +15,7 @@ root="${APP_SITE_DEPLOY_ROOT:-/var/www/html}" if [[ ! "$host" =~ ^[a-zA-Z0-9_.@-]+$ || ! "$root" =~ ^/var/www/[a-zA-Z0-9_./-]+$ ]]; then echo 'Invalid APP_SITE_DEPLOY_HOST or APP_SITE_DEPLOY_ROOT' >&2; exit 2 fi -files=(index.html apps.html sitemap.xml robots.txt guides/quick-games/index.html guides/daily-habits/index.html support/brain-burst/index.html support/snaplingo/index.html support/face-reaction-battle/index.html) +files=(index.html apps.html sitemap.xml robots.txt guides/quick-games/index.html guides/daily-habits/index.html guides/decision-helpers/index.html guides/ai-tools/index.html support/brain-burst/index.html support/snaplingo/index.html support/face-reaction-battle/index.html) for file in "${files[@]}"; do [[ -s "$file" ]] || { echo "Missing source file: $file" >&2; exit 2; } done diff --git a/sitemap.xml b/sitemap.xml index 442eab10..11c2c3c9 100644 --- a/sitemap.xml +++ b/sitemap.xml @@ -325,4 +325,6 @@ https://appdevelopsk.com/csae-standards/2026-08-18yearly0.3 https://appdevelopsk.com/guides/quick-games/2026-10-27monthly0.7 https://appdevelopsk.com/guides/daily-habits/2026-10-27monthly0.7 + https://appdevelopsk.com/guides/decision-helpers/2026-10-27monthly0.7 + https://appdevelopsk.com/guides/ai-tools/2026-10-27monthly0.7 diff --git a/tests/catalog-growth.test.mjs b/tests/catalog-growth.test.mjs index 2ed62bf8..cf00e3b5 100644 --- a/tests/catalog-growth.test.mjs +++ b/tests/catalog-growth.test.mjs @@ -6,12 +6,12 @@ const read = p => readFileSync(new URL('../'+p, import.meta.url),'utf8'); const data = JSON.parse(read('apps_data.json')); const catalog = read('apps.html'); const sitemap = read('sitemap.xml'); -const guides = ['quick-games','daily-habits']; +const guides = ['quick-games','daily-habits','decision-helpers','ai-tools']; test('catalog search retains 92 real indexed store cards and passes install referrer',()=>{ const visible=data.filter(x=>!x.hidden); const tags=[...catalog.matchAll(/t[1].includes('id='+entry.pkg)),entry.app); @@ -77,3 +77,19 @@ test('homepage sends visitors to catalog and both indexable guides without a sea for (const slug of guides) assert.match(home,new RegExp('href="/guides/'+slug+'/"')); assert.match(home,/discovery_nav_click/); }); + +test('purpose filters refer only to visible current catalog slugs, not renamed app titles',()=>{ + const match=catalog.match(/const groups = (\{[\s\S]*?\});\s*const clean/); + assert.ok(match,'missing purpose filter definitions'); + const groups=runInNewContext('('+match[1]+')'); + const visible=new Set(data.filter(a=>!a.hidden).map(a=>a.app)); + for(const [goal,slugs] of Object.entries(groups)){ + assert.ok(slugs.length>=4,'too few choices for '+goal); + assert.equal(new Set(slugs).size,slugs.length,'duplicate catalog slug in '+goal); + for(const slug of slugs){ + assert.ok(visible.has(slug),'invalid or delisted catalog slug '+slug+' in '+goal); + } + } + assert.ok(groups.decisions.includes('chore-roulette')); + assert.ok(groups['quick-games'].includes('daily-duel')); +});