Commit f6b09b9
authored
Introduce skill to help answering Perseus history questions (archaeology) (#3775)
## Summary:
This PR introduces a skill that basically embeds the knowledge in our [Perseus Github History](https://khanacademy.atlassian.net/wiki/spaces/LC/pages/4370696155/Perseus+GitHub+History) document. It enables an AI agent to answer questions about why Perseus is built the way it is.
The skill stitches together the Perseus git history timeline, which spans several repos, so that the agent can authoritatively answer these questions, complete with git commit IDs and pull request details.
Although Phabricator was used earlier in Perseus development, this skill does not source Phabricator info into its research. If it finds related Phabricator Diff IDs, it will include them in the response, but the user will need to open those Phabricator urls.
<details>
<summary>
Example usage
</summary>
```
❯ Why does the PerseusDependencies exist and what is it for?
⏺ Skill(archaeology)
⎿ Successfully loaded skill
Searched for 3 patterns, read 2 files (ctrl+o to expand)
⏺ I have the current picture. Now let me trace the history.
... a bunch of AI research ...
⏺ I have the full trail. Here's the answer.
Short answer
PerseusDependencies exists to decouple Perseus from Khan Academy's webapp via dependency injection — it's the bag of host-provided
implementations (KaTeX/TeX rendering, logging, JIPT translation, URL helpers, locale/env flags) that Perseus needs but cannot import
directly, because those things live in webapp. It was created in 2021–2022 specifically to prepare Perseus for extraction from the webapp
monorepo into its own standalone package, so Perseus code could stop reaching into webapp internals and instead receive them from whoever
embeds it. That's also why dependencies.ts's error message still says "Make sure Perseus is being imported from
javascript/perseus/perseus.js" — a fossil of its webapp home.
It comes in two generations: the original PerseusDependencies (a global singleton set via setDependencies, used in non-React contexts) and
the newer, preferred PerseusDependenciesV2 (delivered through React's DependenciesContext). The type's own doc-comment now tells you to
stop adding to the V1 singleton and shrink its footprint.
The trail (newest → oldest)
- now · Khan/perseus · packages/perseus/src/dependencies.ts + types.ts:324 — V1 PerseusDependencies singleton (get/setDependencies)
coexists with PerseusDependenciesV2 via DependenciesContext; V1's doc-comment warns "avoid adding new dependencies here… it was a quick
fix… Aim to shrink the footprint."
- 2024-Nov-04 · Khan/perseus · 486e4cd #1793 — "move useVideo to v2 deps" — migrating individual deps off the V1 singleton onto the V2
context, per the shrink-the-footprint goal.
- 2023-Jul-06 · Khan/perseus · dd800c2 #600 — "[Analytics] 1. Introduce DependenciesContext" — births PerseusDependenciesV2/the React
context as the modern replacement for the global singleton.
- 2022-Apr-26 · Khan/perseus · afeec15 #136 — "FEI-3758.0: Copy over perseus-all-package…" — the file arrives in the current repo
unchanged; the concept predates this repo entirely.
- 2022-Feb-25 · Khan/webapp · a9c6b7e7e9 #3846 — "FEI-4234.2: Create dependencies singleton and use it for KaTeX deps" — establishes the
singleton in earnest and adds an ESLint rule blocking katex-package imports inside the perseus packages, explicitly "prevent all imports
from webapp inside of the perseus packages we're planning to extract." This is the "why."
- 2021-Nov-08 · Khan/webapp · f497b8f9b5 #2136 (FEI-3863) — "Add a 'dependencies' attribute to APIOptions, to prepare the way for
dependency injection" — the seed: creates the canonical webapp-dependencies.js (real impl) and test-dependencies.js (test impl) that get
injected.
Interpretation
The two-tier design is a half-finished migration, not an intentional dual API. V1 was, in the author's own words, "a quick fix" for
dependencies needed where neither APIOptions nor a React context reach (e.g. module-level singletons like the TeX component and JIPT label
stores). V2 (React context) is the destination; deps are being moved over one at a time (e.g. useVideo in #1793), and staticUrl is
already @deprecated in favor of PerseusDependenciesV2.generateUrl. So when you encounter it: prefer
useDependencies()/PerseusDependenciesV2 for new work, and treat the V1 singleton as legacy surface to drain, not extend.
✻ Worked for 7m 16s · 2 shells still running
⏺ Background command "cd ~/khan/webapp
echo "=== birth of webapp-dependencies.js (follow) ==="
git -c core.hooksPath=/dev/null log --diff-filter=A --follow --date=short --format='%h %ad %an | %s' --all --
services/static/javascript/perseus/webapp-dependencies.js 2>/dev/null | tail -3
git log --diff-filter=A --follow --date=short --format='%h %ad %an | %s' --all --
services/static/javascript/perseus-all-package/webapp-dependencies.js 2>/dev/null | tail -3
echo
echo "=== look for earlier 'perseus-dependencies' or setDependencies introduction ==="
git log --all --date=short --format='%h %ad | %s' -S 'setDependencies' 2>/dev/null | tail -5" completed (exit code 0)
⏺ The investigation is complete — that background task's output was already captured and incorporated into the answer above. No further
action needed.
✻ Cogitated for 1s · 1 shell still running
⏺ Background command "cd ~/khan/webapp
echo "=== prototype #3049 ==="
git -c core.hooksPath=/dev/null log --all --oneline --grep='#3049' | head -3
git log --all --date=short --format='%h %ad %an | %s%n%b' -S 'getDependencies' 2>/dev/null | grep -iE '3049|prototype|dependency
injection|extract' | head -5" completed (exit code 0)
⏺ Both background tasks have completed and their output was already folded into the answer above. The archaeology is done — see the answer
for why PerseusDependencies exists (decoupling Perseus from webapp for extraction) and its V1→V2 migration story.
✻ Churned for 2s
```
</details>
Issue: "none"
## Test plan:
Try the skill out! Ask it your hardest question! :D
Author: jeremywiebe
Reviewers: benchristel, Myranae, jeremywiebe, nishasy, mark-fitzgerald, handeyeco, catandthemachines, anakaren-rojas
Required Reviewers:
Approved By: benchristel, Myranae
Checks: ✅ 11 checks were successful, ⏭️ 1 check has been skipped
Pull Request URL: #37751 parent df41413 commit f6b09b9
2 files changed
Lines changed: 203 additions & 0 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
| 26 | + | |
| 27 | + | |
| 28 | + | |
| 29 | + | |
| 30 | + | |
| 31 | + | |
| 32 | + | |
| 33 | + | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
| 47 | + | |
| 48 | + | |
| 49 | + | |
| 50 | + | |
| 51 | + | |
| 52 | + | |
| 53 | + | |
| 54 | + | |
| 55 | + | |
| 56 | + | |
| 57 | + | |
| 58 | + | |
| 59 | + | |
| 60 | + | |
| 61 | + | |
| 62 | + | |
| 63 | + | |
| 64 | + | |
| 65 | + | |
| 66 | + | |
| 67 | + | |
| 68 | + | |
| 69 | + | |
| 70 | + | |
| 71 | + | |
| 72 | + | |
| 73 | + | |
| 74 | + | |
| 75 | + | |
| 76 | + | |
| 77 | + | |
| 78 | + | |
| 79 | + | |
| 80 | + | |
| 81 | + | |
| 82 | + | |
| 83 | + | |
| 84 | + | |
| 85 | + | |
| 86 | + | |
| 87 | + | |
| 88 | + | |
| 89 | + | |
| 90 | + | |
| 91 | + | |
| 92 | + | |
| 93 | + | |
| 94 | + | |
| 95 | + | |
| 96 | + | |
| 97 | + | |
| 98 | + | |
| 99 | + | |
| 100 | + | |
| 101 | + | |
| 102 | + | |
| 103 | + | |
| 104 | + | |
| 105 | + | |
| 106 | + | |
| 107 | + | |
| 108 | + | |
| 109 | + | |
| 110 | + | |
| 111 | + | |
| 112 | + | |
| 113 | + | |
| 114 | + | |
| 115 | + | |
| 116 | + | |
| 117 | + | |
| 118 | + | |
| 119 | + | |
| 120 | + | |
| 121 | + | |
| 122 | + | |
| 123 | + | |
| 124 | + | |
| 125 | + | |
| 126 | + | |
| 127 | + | |
| 128 | + | |
| 129 | + | |
| 130 | + | |
| 131 | + | |
| 132 | + | |
| 133 | + | |
| 134 | + | |
| 135 | + | |
| 136 | + | |
| 137 | + | |
| 138 | + | |
| 139 | + | |
| 140 | + | |
| 141 | + | |
| 142 | + | |
| 143 | + | |
| 144 | + | |
| 145 | + | |
| 146 | + | |
| 147 | + | |
| 148 | + | |
| 149 | + | |
| 150 | + | |
| 151 | + | |
| 152 | + | |
| 153 | + | |
| 154 | + | |
| 155 | + | |
| 156 | + | |
| 157 | + | |
| 158 | + | |
| 159 | + | |
| 160 | + | |
| 161 | + | |
| 162 | + | |
| 163 | + | |
| 164 | + | |
| 165 | + | |
| 166 | + | |
| 167 | + | |
| 168 | + | |
| 169 | + | |
| 170 | + | |
| 171 | + | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
| 188 | + | |
| 189 | + | |
| 190 | + | |
| 191 | + | |
| 192 | + | |
| 193 | + | |
| 194 | + | |
| 195 | + | |
| 196 | + | |
| 197 | + | |
| 198 | + | |
| 199 | + | |
| 200 | + | |
| 201 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
0 commit comments