mirror of
https://github.com/tiennm99/miti99bot-js.git
synced 2026-08-24 09:33:33 +00:00
chore(plans): drop orphan reports tied to no active plan
Removed reports that documented work already shipped and not tied to any archived plan dir: - docs-manager-260420-2151-documentation-audit.md (one-off doc audit) - researcher-260421-0845-leaguepedia-api-verification.md (lolschedule research) - researcher-260421-0909-leaguepedia-auth-token.md (lolschedule research) The lolschedule module is in src/modules/lolschedule/ but never had a discrete plan dir. Findings from the leaguepedia reports are reflected in the live module code; the markdown is no longer load-bearing. plans/reports/ now contains only the 6 Atlas migration reports for the active plan.
This commit is contained in:
@@ -1,143 +0,0 @@
|
||||
# Documentation Audit Report
|
||||
|
||||
## Summary
|
||||
|
||||
Audited 12 documentation files covering architecture, module setup, deployment, code standards, and module READMEs. Found **3 major stale sections** related to module implementation status (wordle/loldle described as stubs when now fully implemented) and **1 test count discrepancy**. No broken links detected. Modular architecture docs are accurate.
|
||||
|
||||
## Doc Files Inventory
|
||||
|
||||
| File | Purpose | Status |
|
||||
|------|---------|--------|
|
||||
| README.md | Top-level overview, setup, deploy, troubleshooting | **MAJOR-DRIFT** |
|
||||
| CLAUDE.md | Dev guidance, commands, module contract, testing | **FRESH** |
|
||||
| docs/architecture.md | Deep dive: cold-start, registry, storage, crons, deploy | **MINOR-DRIFT** |
|
||||
| docs/adding-a-module.md | Step-by-step module authoring guide | **FRESH** |
|
||||
| docs/code-standards.md | Formatting, JSDoc, file org, naming, testing | **FRESH** |
|
||||
| docs/codebase-summary.md | Tech stack, active modules table, data flows | **MAJOR-DRIFT** |
|
||||
| docs/deployment-guide.md | CF setup, KV, D1, secrets, deploy steps, rollback | **FRESH** |
|
||||
| docs/using-d1.md | When to use D1 vs KV, SQL API, migration examples | **FRESH** |
|
||||
| docs/using-cron.md | Cron syntax, handler signature, examples | **FRESH** |
|
||||
| src/modules/wordle/README.md | Commands, architecture, KV schema | **FRESH** |
|
||||
| src/modules/loldle/README.md | Commands, architecture, KV schema | **MAJOR-DRIFT** |
|
||||
| src/modules/misc/README.md | Commands, KV demo, schema | **FRESH** |
|
||||
|
||||
## Detailed Findings
|
||||
|
||||
### 1. README.md — MAJOR-DRIFT
|
||||
|
||||
**Lines 14, 67-68: Test count and module status discrepancies**
|
||||
|
||||
- **Line 14 claim:** "105+ vitest unit tests"
|
||||
- **Actual:** 200 tests (verified: `npm test` output shows "Tests 200 passed")
|
||||
- **Fix:** Update to "200+ vitest unit tests"
|
||||
|
||||
- **Line 67 claim:** "wordle/ # stub — proves plugin system"
|
||||
- **Line 68 claim:** "loldle/ # stub"
|
||||
- **Actual:** Both are now full implementations:
|
||||
- Wordle: 4 commands (guessing game, new round, giveup, stats) with KV state, render, daily word, compare logic
|
||||
- Loldle: 4 commands (guessing game, new round, giveup, stats) with KV state, champions data, compare logic
|
||||
- Commit 8a9a6af: "feat(wordle): port classic 5-letter guessing game"
|
||||
- **Fix:** Change line 67 to "wordle/ # Classic 5-letter word guessing game (full impl)" and line 68 to "loldle/ # League of Legends champion guessing game (full impl)"
|
||||
|
||||
### 2. docs/codebase-summary.md — MAJOR-DRIFT
|
||||
|
||||
**Lines 25-26: Module status table outdated**
|
||||
|
||||
| Row | Claim | Actual |
|
||||
|-----|-------|--------|
|
||||
| `wordle` | "Status: Stub" | Full implementation: `/wordle`, `/wordle_new`, `/wordle_giveup`, `/wordle_stats` |
|
||||
| `wordle` | "Commands: `/wordle`, `/wstats`, `/konami`" | Wrong commands listed; actual: `/wordle`, `/wordle_new`, `/wordle_giveup`, `/wordle_stats` (all public) |
|
||||
| `wordle` | "Storage: —" | Uses KV (see src/modules/wordle/README.md) |
|
||||
| `loldle` | "Status: Stub" | Full implementation: `/loldle`, `/loldle_new`, `/loldle_giveup`, `/loldle_stats` |
|
||||
| `loldle` | "Commands: `/loldle`, `/ggwp`" | Missing 3 commands; actual: `/loldle`, `/loldle_new`, `/loldle_giveup`, `/loldle_stats` |
|
||||
| `loldle` | "Storage: —" | Uses KV (see src/modules/loldle/index.js lines 10, 16) |
|
||||
|
||||
**Fix:** Update the "Active Modules" table rows for wordle and loldle with actual command counts, visibility, and KV storage.
|
||||
|
||||
### 3. docs/architecture.md — MINOR-DRIFT
|
||||
|
||||
**Line 33: Module classification outdated**
|
||||
|
||||
- **Line 33 claim:** "wordle/ loldle/ — stub modules proving the plugin system"
|
||||
- **Actual:** Both are now production implementations with full game logic
|
||||
- **Fix:** Update to "wordle/ loldle/ — classic word/champion guessing games (full implementations)" or remove stub reference
|
||||
|
||||
**Line 362: Test count**
|
||||
|
||||
- **Line 362 claim:** "105 tests run in ~500ms"
|
||||
- **Actual:** 200 tests run in ~2.26s (from `npm test`)
|
||||
- **Fix:** Update to "200 tests run in ~2.26s"
|
||||
|
||||
### 4. src/modules/loldle/README.md — MAJOR-DRIFT
|
||||
|
||||
**Lines 1-3: Module described as stub**
|
||||
|
||||
- **Current claim:** "League of Legends guessing game — currently a stub proving the plugin system."
|
||||
- **Actual:** Full implementation with handlers imported (line 8: `import { handleGiveup, handleLoldle, handleNew, handleStats } from "./handlers.js"`), 4 commands, KV state (lines 10-17)
|
||||
- **Fix:** Rewrite to match wordle/README.md pattern: describe the 4 commands, handlers, architecture (handlers.js, compare.js, lookup.js, daily.js, render.js, state.js, champions-data.js), and KV schema
|
||||
|
||||
**Line 15: "No KV usage currently"**
|
||||
|
||||
- **Actual:** Module has `init` hook and KV state management (lines 14-17)
|
||||
- **Fix:** Document the `loldle:` namespace and game/stats keys (same pattern as wordle)
|
||||
|
||||
**Lines 6-16: Commands are stubs with stub responses**
|
||||
|
||||
- **Actual:** Commands have real handler implementations (handlers.js exists with 400+ LOC)
|
||||
- **Fix:** Remove "stub" references, document actual commands and their behavior
|
||||
|
||||
### 5. Cross-Reference Checks
|
||||
|
||||
**Internal links verified:**
|
||||
|
||||
- `README.md` → `docs/adding-a-module.md` ✓ (exists, correct relative path)
|
||||
- `README.md` → `docs/architecture.md` ✓
|
||||
- `README.md` → `docs/using-d1.md` ✓
|
||||
- `README.md` → `docs/using-cron.md` ✓
|
||||
- `README.md` → `docs/deployment-guide.md` ✓
|
||||
- `docs/architecture.md` → `src/modules/<name>/README.md` ✓ (pattern reference, not broken link)
|
||||
- All plan references in README.md reference existing directories ✓
|
||||
|
||||
**No broken links found.**
|
||||
|
||||
### 6. Missing Documentation
|
||||
|
||||
None. All required docs exist:
|
||||
|
||||
- ✓ Top-level README with setup, deploy, troubleshooting
|
||||
- ✓ Architecture deep-dive
|
||||
- ✓ Adding a module guide
|
||||
- ✓ Code standards
|
||||
- ✓ Codebase summary
|
||||
- ✓ Deployment guide (KV + D1)
|
||||
- ✓ D1 usage guide
|
||||
- ✓ Cron usage guide
|
||||
- ✓ Per-module READMEs (wordle, loldle, misc, trading, util)
|
||||
|
||||
Note: `docs/todo.md` exists but appears to be an internal tracking doc, not user-facing documentation.
|
||||
|
||||
---
|
||||
|
||||
## Prioritized Fix List
|
||||
|
||||
### Immediate (blocking user confusion)
|
||||
|
||||
1. **README.md line 14:** Update "105+ vitest" → "200+" (test count)
|
||||
2. **README.md lines 67-68:** Remove "stub" label from wordle/loldle in architecture snapshot
|
||||
3. **docs/codebase-summary.md lines 25-26:** Update module status table (wordle/loldle to "Complete", fix commands, add KV storage)
|
||||
4. **src/modules/loldle/README.md:** Full rewrite to describe actual implementation (4 commands, handlers, KV schema) not stub
|
||||
|
||||
### Secondary (clarity improvement)
|
||||
|
||||
5. **docs/architecture.md line 33:** Remove "stub" reference from module list description
|
||||
6. **docs/architecture.md line 362:** Update test count from "105" → "200" and runtime from "~500ms" → "~2.26s"
|
||||
|
||||
---
|
||||
|
||||
## Notes
|
||||
|
||||
- Loldle module is fully implemented (files: handlers.js, compare.js, lookup.js, daily.js, render.js, state.js, champions-data.js, champions.json) but its README still describes it as a stub — this is the most glaring discrepancy.
|
||||
- Wordle module is correctly documented in its own README but incorrectly labeled "stub" in architecture snapshot and codebase summary.
|
||||
- Test count increased from 105 to 200 (likely due to additional trading module tests or recent test additions) — this is a growth metric worth celebrating.
|
||||
- All module-specific README files are accurate except loldle.
|
||||
- No architectural issues, just stale descriptive text that contradicts code reality.
|
||||
@@ -1,80 +0,0 @@
|
||||
# Leaguepedia API — Verification Report
|
||||
|
||||
**Date:** 2026-04-21
|
||||
**Purpose:** Verify the Leaguepedia MediaWiki/Cargo API can provide today / this-week LoL matches for a miti99bot module. No implementation, verification only.
|
||||
**Verdict:** **YES — usable.** Endpoint is public, no auth, returns structured JSON. One caveat on `where=` clauses needs rechecking from Cloudflare Workers egress.
|
||||
|
||||
---
|
||||
|
||||
## Endpoint
|
||||
|
||||
- Base: `https://lol.fandom.com/api.php`
|
||||
- Action: `cargoquery` (MediaWiki Cargo extension)
|
||||
- Auth: none
|
||||
- Format: `format=json` → clean `{cargoquery:[{title:{…}}]}` payload
|
||||
- Related `mw.Api` JS wrapper (doc-wikimedia link) works the same; for a Worker we use plain `fetch`, not `mw.Api`
|
||||
|
||||
## Relevant table: `MatchSchedule`
|
||||
|
||||
Primary table for both upcoming and played matches. Confirmed fields (live API, 2026-04-21):
|
||||
|
||||
| Field | Type | Example |
|
||||
|---|---|---|
|
||||
| `DateTime_UTC` | datetime | `"2026-06-14 09:00:00"` |
|
||||
| `Team1`, `Team2` | string | `"T1"`, `"TBD"` |
|
||||
| `Tournament` | string | Tournament name/slug |
|
||||
| `BestOf` | int | |
|
||||
| `Winner` | string | empty until played |
|
||||
| `OverviewPage` | string | wiki page for tournament |
|
||||
| `_pageName` | string | wiki row page |
|
||||
|
||||
Complementary tables: `Tournaments` (metadata), `ScoreboardGames` (per-game stats), `Teams`.
|
||||
|
||||
## Query syntax (verified working)
|
||||
|
||||
Use **table + field aliases** — the bare form `fields=MatchSchedule.DateTime_UTC` hits an `MWException`. Alias form is the idiomatic Leaguepedia convention:
|
||||
|
||||
```
|
||||
tables=MatchSchedule=MS
|
||||
fields=MS.DateTime_UTC=DateTime, MS.Team1=T1, MS.Team2=T2, MS.Tournament=Tournament
|
||||
order_by=MS.DateTime_UTC ASC
|
||||
limit=20
|
||||
```
|
||||
|
||||
Live sample (no where-filter) returned real rows. Ordering, limit, and aliasing all confirmed working.
|
||||
|
||||
Intended week-window query (to be re-verified from CF Worker egress):
|
||||
|
||||
```
|
||||
where=MS.DateTime_UTC >= "2026-04-21 00:00:00"
|
||||
AND MS.DateTime_UTC < "2026-04-28 00:00:00"
|
||||
```
|
||||
|
||||
## Limitations & operational notes
|
||||
|
||||
- **Strict anonymous rate limit.** From a single shared egress IP the API throttled after 1–2 req/min with `ratelimited`. Mitigations for Workers:
|
||||
- Use Worker's distributed egress (many IPs) — in practice won't hit the same bucket
|
||||
- Cache responses in KV (e.g. 60–300 s for upcoming schedule, 5–15 min for results)
|
||||
- Use `cf: { cacheTtl, cacheEverything: true }` on `fetch`
|
||||
- **User-Agent required.** Fandom's policy expects a contact UA, e.g. `miti99bot/0.1 (https://t.me/miti99bot; minhtienit99@gmail.com)`.
|
||||
- **Help page is Cloudflare-challenged.** `https://lol.fandom.com/wiki/Help:Leaguepedia_API` returns 403 to non-browser UAs — consult it from a browser, not from `fetch` code.
|
||||
- **No official JS SDK.** MediaWiki's `mw.Api` is on-wiki JS only. Community Python wrapper (`mwrogue` / `leaguepedia_parser`) is the reference implementation — we port the query shape, not the lib.
|
||||
- **`where=` clause returned MWException from this verification IP** even on trivial filters (`MS.Team1="T1"`). Likely an upstream filter on the shared egress, not a protocol limitation — the exact form is documented and heavily used. **Needs one confirmation curl from a CF Worker before building on it.**
|
||||
|
||||
## Feasibility verdict
|
||||
|
||||
| Requirement | Feasible? | Notes |
|
||||
|---|---|---|
|
||||
| Fetch today's matches | ✅ | `DateTime_UTC >= today AND < tomorrow` |
|
||||
| Fetch this week's matches | ✅ | 7-day window on `DateTime_UTC` |
|
||||
| Filter by region/league | ✅ | `Tournament LIKE "LCK%"` or `OverviewPage` |
|
||||
| Include results/winners | ✅ | `Winner`, `BestOf` already on row |
|
||||
| Run from Cloudflare Worker | ✅ | plain `fetch` + JSON; add UA + KV cache |
|
||||
| Scheduled daily digest | ✅ | fits existing `cron-dispatcher.js` pattern |
|
||||
|
||||
## Unresolved questions
|
||||
|
||||
1. Does `where=` with comparison operators (`>=`, `<`) work from CF Worker egress, or do we need to alternate filter form (`HOLDS`, `LIKE`, full-table-scan + client-side filter)?
|
||||
2. Timezone UX — show UTC, VN time (UTC+7), or let the `/matches` command take a region arg?
|
||||
3. Caching window — ~60 s for "live today" vs ~5 min for week-view; confirm TTL with a real command spec before implementing.
|
||||
4. Do we want the command to also surface `Winner`/score once a match has finished, or keep it schedule-only?
|
||||
@@ -1,55 +0,0 @@
|
||||
# Leaguepedia / Fandom API — Auth Token Verification
|
||||
|
||||
**Date:** 2026-04-21
|
||||
**Follow-up to:** `researcher-260421-0845-leaguepedia-api-verification.md`
|
||||
**Question:** Can we register and use a token to avoid the rate limit?
|
||||
**Verdict:** **No useful token available. Caching + CF Worker egress is the right answer.**
|
||||
|
||||
---
|
||||
|
||||
## What's NOT available on Fandom
|
||||
|
||||
| Mechanism | Status | Evidence |
|
||||
|---|---|---|
|
||||
| `Special:BotPasswords` | Disabled | 403 CF + disabled in UCP platform (documented in Fandom community) |
|
||||
| OAuth 1.0a / 2.0 (`Special:OAuthConsumerRegistration`) | Not offered | 403; Fandom never enabled the OAuth extension |
|
||||
| `action=clientlogin` (MW native login) | Disabled | `authmanagerinfo` returns only `RememberMeAuthenticationRequest`, no password field |
|
||||
| WMF-style API-key header | N/A | MediaWiki has no such thing; Fandom has none either |
|
||||
|
||||
```bash
|
||||
# Live probe
|
||||
curl '.../api.php?action=query&meta=authmanagerinfo&amirequestsfor=login&format=json'
|
||||
# → only returns RememberMeAuthenticationRequest — native login is off
|
||||
```
|
||||
|
||||
## What Fandom *does* expose
|
||||
|
||||
- **Helios SSO** at `services.fandom.com/mobile-fandom-app/fandom-auth/login`
|
||||
- POST `username` + `password` → `access_token` cookie
|
||||
- Used by Leaguepedia's official `mwcleric` Python lib (`LoginCredentials`)
|
||||
- Cookie is carried on subsequent `api.php` requests from same session
|
||||
|
||||
## Does an authenticated cookie lift the rate limit?
|
||||
|
||||
**No, not meaningfully.**
|
||||
|
||||
- MediaWiki's `noratelimit` right only belongs to specific wiki groups (`sysop`, `bot`). Regular logged-in users have the same API limits as anonymous.
|
||||
- Joining the `bot` group on Leaguepedia requires wiki-admin (Leaguepedia staff) approval — not practical for a side project.
|
||||
- The throttling we hit earlier is **Fandom's Cloudflare-edge IP rate limit**, which is session-agnostic. Auth cookies don't bypass it.
|
||||
- `siprop=ratelimits` is stripped on Fandom (`Unrecognized value`) — we can't even enumerate the limits.
|
||||
|
||||
## Right answer for miti99bot (Cloudflare Worker)
|
||||
|
||||
No token registration needed. Mitigate via:
|
||||
|
||||
1. **Edge caching** — `fetch(url, { cf: { cacheTtl: 60, cacheEverything: true } })`. Many bot users share one cached response.
|
||||
2. **KV result cache** — wrap the query in `create-store.js`, key = `matches:{from}:{to}`, TTL 60 s for "today", 5 min for "week".
|
||||
3. **Cron pre-warm** — add a module cron (existing `cron-dispatcher.js` pattern) that refreshes the week window every 15 min. Telegram `/matches` then reads pre-warmed cache.
|
||||
4. **CF Worker egress diversity** — Worker outbound IPs are many; per-IP buckets rarely hit 429 in practice.
|
||||
5. **Honor `Retry-After`** on 429 and surface "data momentarily unavailable" to the user instead of stalling.
|
||||
6. **Proper UA** — `miti99bot/0.1 (https://t.me/miti99bot; minhtienit99@gmail.com)` (already planned). Missing UA is itself a throttle signal on Fandom.
|
||||
|
||||
## Unresolved questions
|
||||
|
||||
1. Do CF Worker-origin fetches hit the same 429 as this shared egress does? (low risk — worth one real test before shipping)
|
||||
2. Is the module's read pattern bursty or steady? If steady, cron pre-warm + long TTL removes all pressure. If bursty (many users hit `/matches` at game time), KV cache is still the lever.
|
||||
Reference in New Issue
Block a user