bmad-method 6.0.0-alpha.8 → 6.0.0-alpha.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (539) hide show
  1. package/.github/ISSUE_TEMPLATE/idea_submission.md +1 -1
  2. package/.github/workflows/bundle-latest.yaml +277 -0
  3. package/.github/workflows/manual-release.yaml +55 -16
  4. package/CHANGELOG.md +439 -1
  5. package/README.md +12 -4
  6. package/docs/BUNDLE_DISTRIBUTION_SETUP.md +95 -0
  7. package/docs/agent-customization-guide.md +208 -0
  8. package/docs/ide-info/crush.md +1 -1
  9. package/docs/ide-info/cursor.md +7 -7
  10. package/docs/ide-info/iflow.md +3 -3
  11. package/docs/ide-info/opencode.md +1 -1
  12. package/docs/index.md +3 -1
  13. package/docs/installers-bundlers/ide-injections.md +2 -2
  14. package/docs/installers-bundlers/installers-modules-platforms-reference.md +23 -23
  15. package/docs/v4-to-v6-upgrade.md +12 -12
  16. package/docs/web-bundles-gemini-gpt-guide.md +473 -0
  17. package/package.json +1 -1
  18. package/src/core/_module-installer/install-config.yaml +2 -1
  19. package/src/core/agents/bmad-web-orchestrator.agent.xml +1 -1
  20. package/src/core/tasks/{adv-elicit.xml → advanced-elicitation.xml} +3 -3
  21. package/src/core/tasks/workflow.xml +124 -10
  22. package/src/core/tools/shard-doc.xml +44 -0
  23. package/src/core/workflows/brainstorming/README.md +5 -15
  24. package/src/core/workflows/brainstorming/instructions.md +4 -3
  25. package/src/core/workflows/brainstorming/template.md +4 -0
  26. package/src/modules/bmb/workflows/audit-workflow/checklist.md +3 -4
  27. package/src/modules/bmb/workflows/convert-legacy/README.md +1 -1
  28. package/src/modules/bmb/workflows/convert-legacy/checklist.md +1 -1
  29. package/src/modules/bmb/workflows/convert-legacy/instructions.md +2 -2
  30. package/src/modules/bmb/workflows/create-agent/agent-architecture.md +0 -4
  31. package/src/modules/bmb/workflows/create-agent/instructions.md +13 -16
  32. package/src/modules/bmb/workflows/create-module/checklist.md +0 -9
  33. package/src/modules/bmb/workflows/create-module/instructions.md +5 -10
  34. package/src/modules/bmb/workflows/create-module/module-structure.md +3 -3
  35. package/src/modules/bmb/workflows/create-workflow/instructions.md +1 -1
  36. package/src/modules/bmb/workflows/create-workflow/workflow-creation-guide.md +0 -2
  37. package/src/modules/bmb/workflows/module-brief/checklist.md +2 -2
  38. package/src/modules/bmgd/_module-installer/install-config.yaml +4 -17
  39. package/src/modules/bmgd/agents/game-architect.agent.yaml +2 -2
  40. package/src/modules/bmgd/agents/game-designer.agent.yaml +2 -2
  41. package/src/modules/bmgd/agents/game-dev.agent.yaml +2 -2
  42. package/src/modules/bmgd/agents/game-scrum-master.agent.yaml +2 -2
  43. package/src/modules/bmgd/workflows/2-design/gdd/instructions-gdd.md +1 -6
  44. package/src/modules/bmgd/workflows/2-design/narrative/instructions-narrative.md +0 -5
  45. package/src/modules/bmgd/workflows/3-technical/game-architecture/architecture-patterns.yaml +0 -26
  46. package/src/modules/bmgd/workflows/3-technical/game-architecture/checklist.md +2 -6
  47. package/src/modules/bmgd/workflows/3-technical/game-architecture/instructions.md +1 -6
  48. package/src/modules/bmgd/workflows/4-production/code-review/instructions.md +21 -43
  49. package/src/modules/bmgd/workflows/4-production/code-review/workflow.yaml +11 -21
  50. package/src/modules/bmgd/workflows/4-production/correct-course/instructions.md +5 -0
  51. package/src/modules/bmgd/workflows/4-production/correct-course/workflow.yaml +29 -22
  52. package/src/modules/bmgd/workflows/4-production/create-story/instructions.md +18 -45
  53. package/src/modules/bmgd/workflows/4-production/create-story/workflow.yaml +14 -22
  54. package/src/modules/bmgd/workflows/4-production/dev-story/instructions.md +6 -1
  55. package/src/modules/bmgd/workflows/4-production/dev-story/workflow.yaml +28 -3
  56. package/src/modules/bmgd/workflows/4-production/epic-tech-context/instructions.md +8 -33
  57. package/src/modules/bmgd/workflows/4-production/epic-tech-context/workflow.yaml +14 -22
  58. package/src/modules/bmgd/workflows/4-production/retrospective/instructions.md +16 -34
  59. package/src/modules/bmgd/workflows/4-production/retrospective/workflow.yaml +13 -34
  60. package/src/modules/bmgd/workflows/4-production/sprint-planning/instructions.md +9 -13
  61. package/src/modules/bmgd/workflows/4-production/sprint-planning/sprint-status-template.yaml +1 -1
  62. package/src/modules/bmgd/workflows/4-production/sprint-planning/workflow.yaml +6 -5
  63. package/src/modules/bmgd/workflows/4-production/story-context/instructions.md +18 -43
  64. package/src/modules/bmgd/workflows/4-production/story-context/workflow.yaml +13 -15
  65. package/src/modules/bmgd/workflows/4-production/story-done/workflow.yaml +3 -2
  66. package/src/modules/bmgd/workflows/4-production/story-ready/instructions.md +5 -5
  67. package/src/modules/bmgd/workflows/4-production/story-ready/workflow.yaml +3 -5
  68. package/src/modules/bmm/_module-installer/install-config.yaml +3 -8
  69. package/src/modules/bmm/_module-installer/installer.js +2 -2
  70. package/src/modules/bmm/agents/analyst.agent.yaml +2 -2
  71. package/src/modules/bmm/agents/architect.agent.yaml +2 -2
  72. package/src/modules/bmm/agents/pm.agent.yaml +2 -2
  73. package/src/modules/bmm/agents/sm.agent.yaml +2 -2
  74. package/src/modules/bmm/agents/tea.agent.yaml +2 -2
  75. package/src/modules/bmm/agents/tech-writer.agent.yaml +3 -3
  76. package/src/modules/bmm/agents/ux-designer.agent.yaml +2 -2
  77. package/src/modules/bmm/workflows/1-analysis/domain-research/workflow.yaml +0 -13
  78. package/src/modules/bmm/workflows/1-analysis/product-brief/instructions.md +9 -11
  79. package/src/modules/bmm/workflows/1-analysis/product-brief/workflow.yaml +4 -0
  80. package/src/modules/bmm/workflows/1-analysis/research/checklist-deep-prompt.md +2 -2
  81. package/src/modules/bmm/workflows/1-analysis/research/checklist-technical.md +2 -2
  82. package/src/modules/bmm/workflows/1-analysis/research/checklist.md +2 -2
  83. package/src/modules/bmm/workflows/1-analysis/research/instructions-deep-prompt.md +0 -2
  84. package/src/modules/bmm/workflows/1-analysis/research/instructions-market.md +1 -6
  85. package/src/modules/bmm/workflows/1-analysis/research/instructions-technical.md +0 -5
  86. package/src/modules/bmm/workflows/2-plan-workflows/create-ux-design/instructions.md +6 -1
  87. package/src/modules/bmm/workflows/2-plan-workflows/create-ux-design/workflow.yaml +6 -0
  88. package/src/modules/bmm/workflows/2-plan-workflows/prd/checklist.md +8 -12
  89. package/src/modules/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/epics-template.md +28 -0
  90. package/src/modules/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/instructions.md +145 -22
  91. package/src/modules/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/workflow.yaml +1 -3
  92. package/src/modules/bmm/workflows/2-plan-workflows/prd/instructions.md +151 -34
  93. package/src/modules/bmm/workflows/2-plan-workflows/prd/prd-template.md +2 -2
  94. package/src/modules/bmm/workflows/2-plan-workflows/prd/workflow.yaml +6 -2
  95. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/checklist.md +12 -9
  96. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/epics-template.md +0 -6
  97. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/instructions-generate-stories.md +434 -0
  98. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/instructions.md +128 -265
  99. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/workflow.yaml +13 -35
  100. package/src/modules/bmm/workflows/3-solutioning/architecture/architecture-patterns.yaml +0 -26
  101. package/src/modules/bmm/workflows/3-solutioning/architecture/checklist.md +3 -7
  102. package/src/modules/bmm/workflows/3-solutioning/architecture/instructions.md +29 -37
  103. package/src/modules/bmm/workflows/3-solutioning/architecture/workflow.yaml +9 -27
  104. package/src/modules/bmm/workflows/3-solutioning/solutioning-gate-check/checklist.md +7 -13
  105. package/src/modules/bmm/workflows/3-solutioning/solutioning-gate-check/instructions.md +55 -58
  106. package/src/modules/bmm/workflows/3-solutioning/solutioning-gate-check/workflow.yaml +8 -8
  107. package/src/modules/bmm/workflows/4-implementation/code-review/instructions.md +10 -32
  108. package/src/modules/bmm/workflows/4-implementation/code-review/workflow.yaml +11 -13
  109. package/src/modules/bmm/workflows/4-implementation/correct-course/instructions.md +5 -0
  110. package/src/modules/bmm/workflows/4-implementation/correct-course/workflow.yaml +29 -22
  111. package/src/modules/bmm/workflows/4-implementation/create-story/instructions.md +12 -37
  112. package/src/modules/bmm/workflows/4-implementation/create-story/workflow.yaml +12 -7
  113. package/src/modules/bmm/workflows/4-implementation/dev-story/instructions.md +6 -1
  114. package/src/modules/bmm/workflows/4-implementation/dev-story/workflow.yaml +28 -3
  115. package/src/modules/bmm/workflows/4-implementation/epic-tech-context/instructions.md +7 -30
  116. package/src/modules/bmm/workflows/4-implementation/epic-tech-context/workflow.yaml +13 -9
  117. package/src/modules/bmm/workflows/4-implementation/retrospective/instructions.md +8 -26
  118. package/src/modules/bmm/workflows/4-implementation/retrospective/workflow.yaml +13 -31
  119. package/src/modules/bmm/workflows/4-implementation/sprint-planning/instructions.md +5 -0
  120. package/src/modules/bmm/workflows/4-implementation/sprint-planning/sprint-status-template.yaml +1 -1
  121. package/src/modules/bmm/workflows/4-implementation/sprint-planning/workflow.yaml +6 -6
  122. package/src/modules/bmm/workflows/4-implementation/story-context/instructions.md +12 -36
  123. package/src/modules/bmm/workflows/4-implementation/story-context/workflow.yaml +12 -6
  124. package/src/modules/bmm/workflows/4-implementation/story-done/workflow.yaml +3 -2
  125. package/src/modules/bmm/workflows/4-implementation/story-ready/instructions.md +5 -5
  126. package/src/modules/bmm/workflows/4-implementation/story-ready/workflow.yaml +3 -5
  127. package/src/modules/bmm/workflows/document-project/checklist.md +1 -1
  128. package/src/modules/bmm/workflows/document-project/workflows/deep-dive-instructions.md +4 -4
  129. package/src/modules/bmm/workflows/document-project/workflows/full-scan-instructions.md +13 -13
  130. package/src/modules/bmm/workflows/testarch/ci/checklist.md +4 -4
  131. package/src/modules/bmm/workflows/testarch/framework/checklist.md +4 -4
  132. package/src/modules/bmm/workflows/testarch/test-design/checklist.md +4 -4
  133. package/src/modules/bmm/workflows/testarch/test-design/instructions.md +173 -12
  134. package/src/modules/bmm/workflows/testarch/test-design/test-design-template.md +3 -3
  135. package/src/modules/bmm/workflows/testarch/test-design/workflow.yaml +5 -1
  136. package/src/modules/bmm/workflows/workflow-status/init/instructions.md +9 -9
  137. package/src/modules/bmm/workflows/workflow-status/init/workflow.yaml +1 -1
  138. package/src/modules/bmm/workflows/workflow-status/paths/enterprise-brownfield.yaml +9 -16
  139. package/src/modules/bmm/workflows/workflow-status/paths/enterprise-greenfield.yaml +11 -18
  140. package/src/modules/bmm/workflows/workflow-status/paths/method-brownfield.yaml +8 -1
  141. package/src/modules/bmm/workflows/workflow-status/paths/method-greenfield.yaml +9 -2
  142. package/src/modules/bmm/workflows/workflow-status/workflow-status-template.yaml +2 -9
  143. package/src/modules/cis/agents/brainstorming-coach.agent.yaml +2 -2
  144. package/src/modules/cis/agents/creative-problem-solver.agent.yaml +2 -2
  145. package/src/modules/cis/agents/design-thinking-coach.agent.yaml +2 -2
  146. package/src/modules/cis/agents/innovation-strategist.agent.yaml +2 -2
  147. package/src/modules/cis/agents/storyteller.agent.yaml +2 -2
  148. package/tools/cli/README.md +50 -32
  149. package/tools/cli/bundlers/web-bundler.js +1 -1
  150. package/tools/cli/installers/lib/core/installer.js +17 -10
  151. package/tools/cli/lib/ui.js +14 -4
  152. package/tools/cli/lib/yaml-xml-builder.js +20 -2
  153. package/.bmad/_cfg/agent-manifest.csv +0 -11
  154. package/.bmad/_cfg/agents/bmb-bmad-builder.customize.yaml +0 -42
  155. package/.bmad/_cfg/agents/bmm-analyst.customize.yaml +0 -42
  156. package/.bmad/_cfg/agents/bmm-architect.customize.yaml +0 -42
  157. package/.bmad/_cfg/agents/bmm-dev.customize.yaml +0 -42
  158. package/.bmad/_cfg/agents/bmm-pm.customize.yaml +0 -42
  159. package/.bmad/_cfg/agents/bmm-sm.customize.yaml +0 -42
  160. package/.bmad/_cfg/agents/bmm-tea.customize.yaml +0 -42
  161. package/.bmad/_cfg/agents/bmm-tech-writer.customize.yaml +0 -42
  162. package/.bmad/_cfg/agents/bmm-ux-designer.customize.yaml +0 -42
  163. package/.bmad/_cfg/agents/core-bmad-master.customize.yaml +0 -42
  164. package/.bmad/_cfg/files-manifest.csv +0 -289
  165. package/.bmad/_cfg/ides/claude-code.yaml +0 -7
  166. package/.bmad/_cfg/manifest.yaml +0 -10
  167. package/.bmad/_cfg/task-manifest.csv +0 -6
  168. package/.bmad/_cfg/tool-manifest.csv +0 -2
  169. package/.bmad/_cfg/workflow-manifest.csv +0 -44
  170. package/.bmad/bmb/README.md +0 -194
  171. package/.bmad/bmb/agents/bmad-builder.md +0 -70
  172. package/.bmad/bmb/config.yaml +0 -16
  173. package/.bmad/bmb/workflows/audit-workflow/checklist.md +0 -143
  174. package/.bmad/bmb/workflows/audit-workflow/instructions.md +0 -341
  175. package/.bmad/bmb/workflows/audit-workflow/template.md +0 -118
  176. package/.bmad/bmb/workflows/audit-workflow/workflow.yaml +0 -23
  177. package/.bmad/bmb/workflows/convert-legacy/README.md +0 -262
  178. package/.bmad/bmb/workflows/convert-legacy/checklist.md +0 -205
  179. package/.bmad/bmb/workflows/convert-legacy/instructions.md +0 -377
  180. package/.bmad/bmb/workflows/convert-legacy/workflow.yaml +0 -32
  181. package/.bmad/bmb/workflows/create-agent/README.md +0 -203
  182. package/.bmad/bmb/workflows/create-agent/agent-architecture.md +0 -419
  183. package/.bmad/bmb/workflows/create-agent/agent-command-patterns.md +0 -759
  184. package/.bmad/bmb/workflows/create-agent/agent-types.md +0 -292
  185. package/.bmad/bmb/workflows/create-agent/brainstorm-context.md +0 -174
  186. package/.bmad/bmb/workflows/create-agent/checklist.md +0 -62
  187. package/.bmad/bmb/workflows/create-agent/communication-styles.md +0 -202
  188. package/.bmad/bmb/workflows/create-agent/instructions.md +0 -459
  189. package/.bmad/bmb/workflows/create-agent/workflow.yaml +0 -37
  190. package/.bmad/bmb/workflows/create-module/README.md +0 -229
  191. package/.bmad/bmb/workflows/create-module/brainstorm-context.md +0 -137
  192. package/.bmad/bmb/workflows/create-module/checklist.md +0 -244
  193. package/.bmad/bmb/workflows/create-module/installer-templates/install-config.yaml +0 -92
  194. package/.bmad/bmb/workflows/create-module/installer-templates/installer.js +0 -231
  195. package/.bmad/bmb/workflows/create-module/instructions.md +0 -581
  196. package/.bmad/bmb/workflows/create-module/module-structure.md +0 -400
  197. package/.bmad/bmb/workflows/create-module/workflow.yaml +0 -42
  198. package/.bmad/bmb/workflows/create-workflow/README.md +0 -277
  199. package/.bmad/bmb/workflows/create-workflow/brainstorm-context.md +0 -197
  200. package/.bmad/bmb/workflows/create-workflow/checklist.md +0 -94
  201. package/.bmad/bmb/workflows/create-workflow/instructions.md +0 -724
  202. package/.bmad/bmb/workflows/create-workflow/workflow-creation-guide.md +0 -1308
  203. package/.bmad/bmb/workflows/create-workflow/workflow-template/checklist.md +0 -24
  204. package/.bmad/bmb/workflows/create-workflow/workflow-template/instructions.md +0 -13
  205. package/.bmad/bmb/workflows/create-workflow/workflow-template/template.md +0 -9
  206. package/.bmad/bmb/workflows/create-workflow/workflow-template/workflow.yaml +0 -39
  207. package/.bmad/bmb/workflows/create-workflow/workflow.yaml +0 -40
  208. package/.bmad/bmb/workflows/edit-agent/README.md +0 -112
  209. package/.bmad/bmb/workflows/edit-agent/checklist.md +0 -112
  210. package/.bmad/bmb/workflows/edit-agent/instructions.md +0 -290
  211. package/.bmad/bmb/workflows/edit-agent/workflow.yaml +0 -33
  212. package/.bmad/bmb/workflows/edit-module/README.md +0 -187
  213. package/.bmad/bmb/workflows/edit-module/checklist.md +0 -165
  214. package/.bmad/bmb/workflows/edit-module/instructions.md +0 -339
  215. package/.bmad/bmb/workflows/edit-module/workflow.yaml +0 -34
  216. package/.bmad/bmb/workflows/edit-workflow/README.md +0 -119
  217. package/.bmad/bmb/workflows/edit-workflow/checklist.md +0 -70
  218. package/.bmad/bmb/workflows/edit-workflow/instructions.md +0 -342
  219. package/.bmad/bmb/workflows/edit-workflow/workflow.yaml +0 -27
  220. package/.bmad/bmb/workflows/module-brief/README.md +0 -264
  221. package/.bmad/bmb/workflows/module-brief/checklist.md +0 -116
  222. package/.bmad/bmb/workflows/module-brief/instructions.md +0 -267
  223. package/.bmad/bmb/workflows/module-brief/template.md +0 -275
  224. package/.bmad/bmb/workflows/module-brief/workflow.yaml +0 -29
  225. package/.bmad/bmb/workflows/redoc/README.md +0 -87
  226. package/.bmad/bmb/workflows/redoc/checklist.md +0 -99
  227. package/.bmad/bmb/workflows/redoc/instructions.md +0 -265
  228. package/.bmad/bmb/workflows/redoc/workflow.yaml +0 -32
  229. package/.bmad/bmm/README.md +0 -128
  230. package/.bmad/bmm/agents/analyst.md +0 -75
  231. package/.bmad/bmm/agents/architect.md +0 -80
  232. package/.bmad/bmm/agents/dev.md +0 -69
  233. package/.bmad/bmm/agents/pm.md +0 -84
  234. package/.bmad/bmm/agents/sm.md +0 -93
  235. package/.bmad/bmm/agents/tea.md +0 -80
  236. package/.bmad/bmm/agents/tech-writer.md +0 -90
  237. package/.bmad/bmm/agents/ux-designer.md +0 -79
  238. package/.bmad/bmm/config.yaml +0 -18
  239. package/.bmad/bmm/docs/README.md +0 -235
  240. package/.bmad/bmm/docs/agents-guide.md +0 -1056
  241. package/.bmad/bmm/docs/brownfield-guide.md +0 -754
  242. package/.bmad/bmm/docs/enterprise-agentic-development.md +0 -680
  243. package/.bmad/bmm/docs/faq.md +0 -587
  244. package/.bmad/bmm/docs/glossary.md +0 -320
  245. package/.bmad/bmm/docs/party-mode.md +0 -224
  246. package/.bmad/bmm/docs/quick-spec-flow.md +0 -652
  247. package/.bmad/bmm/docs/quick-start.md +0 -366
  248. package/.bmad/bmm/docs/scale-adaptive-system.md +0 -599
  249. package/.bmad/bmm/docs/test-architecture.md +0 -394
  250. package/.bmad/bmm/docs/workflow-architecture-reference.md +0 -371
  251. package/.bmad/bmm/docs/workflow-document-project-reference.md +0 -487
  252. package/.bmad/bmm/docs/workflows-analysis.md +0 -370
  253. package/.bmad/bmm/docs/workflows-implementation.md +0 -284
  254. package/.bmad/bmm/docs/workflows-planning.md +0 -601
  255. package/.bmad/bmm/docs/workflows-solutioning.md +0 -501
  256. package/.bmad/bmm/tasks/daily-standup.xml +0 -85
  257. package/.bmad/bmm/teams/default-party.csv +0 -19
  258. package/.bmad/bmm/teams/team-fullstack.yaml +0 -12
  259. package/.bmad/bmm/testarch/knowledge/ci-burn-in.md +0 -675
  260. package/.bmad/bmm/testarch/knowledge/component-tdd.md +0 -486
  261. package/.bmad/bmm/testarch/knowledge/contract-testing.md +0 -957
  262. package/.bmad/bmm/testarch/knowledge/data-factories.md +0 -500
  263. package/.bmad/bmm/testarch/knowledge/email-auth.md +0 -721
  264. package/.bmad/bmm/testarch/knowledge/error-handling.md +0 -725
  265. package/.bmad/bmm/testarch/knowledge/feature-flags.md +0 -750
  266. package/.bmad/bmm/testarch/knowledge/fixture-architecture.md +0 -401
  267. package/.bmad/bmm/testarch/knowledge/network-first.md +0 -486
  268. package/.bmad/bmm/testarch/knowledge/nfr-criteria.md +0 -670
  269. package/.bmad/bmm/testarch/knowledge/playwright-config.md +0 -730
  270. package/.bmad/bmm/testarch/knowledge/probability-impact.md +0 -601
  271. package/.bmad/bmm/testarch/knowledge/risk-governance.md +0 -615
  272. package/.bmad/bmm/testarch/knowledge/selective-testing.md +0 -732
  273. package/.bmad/bmm/testarch/knowledge/selector-resilience.md +0 -527
  274. package/.bmad/bmm/testarch/knowledge/test-healing-patterns.md +0 -644
  275. package/.bmad/bmm/testarch/knowledge/test-levels-framework.md +0 -473
  276. package/.bmad/bmm/testarch/knowledge/test-priorities-matrix.md +0 -373
  277. package/.bmad/bmm/testarch/knowledge/test-quality.md +0 -664
  278. package/.bmad/bmm/testarch/knowledge/timing-debugging.md +0 -372
  279. package/.bmad/bmm/testarch/knowledge/visual-debugging.md +0 -524
  280. package/.bmad/bmm/testarch/tea-index.csv +0 -22
  281. package/.bmad/bmm/workflows/1-analysis/brainstorm-project/instructions.md +0 -110
  282. package/.bmad/bmm/workflows/1-analysis/brainstorm-project/project-context.md +0 -25
  283. package/.bmad/bmm/workflows/1-analysis/brainstorm-project/workflow.yaml +0 -26
  284. package/.bmad/bmm/workflows/1-analysis/domain-research/instructions.md +0 -423
  285. package/.bmad/bmm/workflows/1-analysis/domain-research/template.md +0 -180
  286. package/.bmad/bmm/workflows/1-analysis/domain-research/workflow.yaml +0 -40
  287. package/.bmad/bmm/workflows/1-analysis/product-brief/checklist.md +0 -115
  288. package/.bmad/bmm/workflows/1-analysis/product-brief/instructions.md +0 -524
  289. package/.bmad/bmm/workflows/1-analysis/product-brief/template.md +0 -181
  290. package/.bmad/bmm/workflows/1-analysis/product-brief/workflow.yaml +0 -45
  291. package/.bmad/bmm/workflows/1-analysis/research/checklist-deep-prompt.md +0 -144
  292. package/.bmad/bmm/workflows/1-analysis/research/checklist-technical.md +0 -249
  293. package/.bmad/bmm/workflows/1-analysis/research/checklist.md +0 -299
  294. package/.bmad/bmm/workflows/1-analysis/research/claude-code/injections.yaml +0 -114
  295. package/.bmad/bmm/workflows/1-analysis/research/instructions-deep-prompt.md +0 -439
  296. package/.bmad/bmm/workflows/1-analysis/research/instructions-market.md +0 -679
  297. package/.bmad/bmm/workflows/1-analysis/research/instructions-router.md +0 -133
  298. package/.bmad/bmm/workflows/1-analysis/research/instructions-technical.md +0 -538
  299. package/.bmad/bmm/workflows/1-analysis/research/template-deep-prompt.md +0 -94
  300. package/.bmad/bmm/workflows/1-analysis/research/template-market.md +0 -347
  301. package/.bmad/bmm/workflows/1-analysis/research/template-technical.md +0 -245
  302. package/.bmad/bmm/workflows/1-analysis/research/workflow.yaml +0 -44
  303. package/.bmad/bmm/workflows/2-plan-workflows/create-ux-design/checklist.md +0 -310
  304. package/.bmad/bmm/workflows/2-plan-workflows/create-ux-design/instructions.md +0 -1301
  305. package/.bmad/bmm/workflows/2-plan-workflows/create-ux-design/ux-design-template.md +0 -145
  306. package/.bmad/bmm/workflows/2-plan-workflows/create-ux-design/workflow.yaml +0 -60
  307. package/.bmad/bmm/workflows/2-plan-workflows/prd/checklist.md +0 -350
  308. package/.bmad/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/epics-template.md +0 -52
  309. package/.bmad/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/instructions.md +0 -169
  310. package/.bmad/bmm/workflows/2-plan-workflows/prd/create-epics-and-stories/workflow.yaml +0 -45
  311. package/.bmad/bmm/workflows/2-plan-workflows/prd/domain-complexity.csv +0 -13
  312. package/.bmad/bmm/workflows/2-plan-workflows/prd/instructions.md +0 -408
  313. package/.bmad/bmm/workflows/2-plan-workflows/prd/prd-template.md +0 -237
  314. package/.bmad/bmm/workflows/2-plan-workflows/prd/project-types.csv +0 -11
  315. package/.bmad/bmm/workflows/2-plan-workflows/prd/workflow.yaml +0 -46
  316. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/checklist.md +0 -214
  317. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/epics-template.md +0 -80
  318. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/instructions-level0-story.md +0 -200
  319. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/instructions-level1-stories.md +0 -451
  320. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/instructions.md +0 -1115
  321. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/tech-spec-template.md +0 -181
  322. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/user-story-template.md +0 -90
  323. package/.bmad/bmm/workflows/2-plan-workflows/tech-spec/workflow.yaml +0 -60
  324. package/.bmad/bmm/workflows/3-solutioning/architecture/architecture-patterns.yaml +0 -347
  325. package/.bmad/bmm/workflows/3-solutioning/architecture/architecture-template.md +0 -103
  326. package/.bmad/bmm/workflows/3-solutioning/architecture/checklist.md +0 -244
  327. package/.bmad/bmm/workflows/3-solutioning/architecture/decision-catalog.yaml +0 -222
  328. package/.bmad/bmm/workflows/3-solutioning/architecture/instructions.md +0 -704
  329. package/.bmad/bmm/workflows/3-solutioning/architecture/pattern-categories.csv +0 -13
  330. package/.bmad/bmm/workflows/3-solutioning/architecture/workflow.yaml +0 -68
  331. package/.bmad/bmm/workflows/3-solutioning/solutioning-gate-check/checklist.md +0 -175
  332. package/.bmad/bmm/workflows/3-solutioning/solutioning-gate-check/instructions.md +0 -305
  333. package/.bmad/bmm/workflows/3-solutioning/solutioning-gate-check/template.md +0 -146
  334. package/.bmad/bmm/workflows/3-solutioning/solutioning-gate-check/validation-criteria.yaml +0 -189
  335. package/.bmad/bmm/workflows/3-solutioning/solutioning-gate-check/workflow.yaml +0 -64
  336. package/.bmad/bmm/workflows/4-implementation/code-review/backlog_template.md +0 -12
  337. package/.bmad/bmm/workflows/4-implementation/code-review/checklist.md +0 -22
  338. package/.bmad/bmm/workflows/4-implementation/code-review/instructions.md +0 -420
  339. package/.bmad/bmm/workflows/4-implementation/code-review/workflow.yaml +0 -65
  340. package/.bmad/bmm/workflows/4-implementation/correct-course/checklist.md +0 -279
  341. package/.bmad/bmm/workflows/4-implementation/correct-course/instructions.md +0 -201
  342. package/.bmad/bmm/workflows/4-implementation/correct-course/workflow.yaml +0 -43
  343. package/.bmad/bmm/workflows/4-implementation/create-story/checklist.md +0 -240
  344. package/.bmad/bmm/workflows/4-implementation/create-story/instructions.md +0 -283
  345. package/.bmad/bmm/workflows/4-implementation/create-story/template.md +0 -51
  346. package/.bmad/bmm/workflows/4-implementation/create-story/workflow.yaml +0 -74
  347. package/.bmad/bmm/workflows/4-implementation/dev-story/AUDIT-REPORT.md +0 -367
  348. package/.bmad/bmm/workflows/4-implementation/dev-story/checklist.md +0 -38
  349. package/.bmad/bmm/workflows/4-implementation/dev-story/instructions.md +0 -262
  350. package/.bmad/bmm/workflows/4-implementation/dev-story/workflow.yaml +0 -26
  351. package/.bmad/bmm/workflows/4-implementation/epic-tech-context/checklist.md +0 -17
  352. package/.bmad/bmm/workflows/4-implementation/epic-tech-context/instructions.md +0 -189
  353. package/.bmad/bmm/workflows/4-implementation/epic-tech-context/template.md +0 -76
  354. package/.bmad/bmm/workflows/4-implementation/epic-tech-context/workflow.yaml +0 -58
  355. package/.bmad/bmm/workflows/4-implementation/retrospective/instructions.md +0 -1460
  356. package/.bmad/bmm/workflows/4-implementation/retrospective/workflow.yaml +0 -71
  357. package/.bmad/bmm/workflows/4-implementation/sprint-planning/checklist.md +0 -33
  358. package/.bmad/bmm/workflows/4-implementation/sprint-planning/instructions.md +0 -238
  359. package/.bmad/bmm/workflows/4-implementation/sprint-planning/sprint-status-template.yaml +0 -55
  360. package/.bmad/bmm/workflows/4-implementation/sprint-planning/workflow.yaml +0 -47
  361. package/.bmad/bmm/workflows/4-implementation/story-context/checklist.md +0 -16
  362. package/.bmad/bmm/workflows/4-implementation/story-context/context-template.xml +0 -34
  363. package/.bmad/bmm/workflows/4-implementation/story-context/instructions.md +0 -234
  364. package/.bmad/bmm/workflows/4-implementation/story-context/workflow.yaml +0 -57
  365. package/.bmad/bmm/workflows/4-implementation/story-done/instructions.md +0 -111
  366. package/.bmad/bmm/workflows/4-implementation/story-done/workflow.yaml +0 -25
  367. package/.bmad/bmm/workflows/4-implementation/story-ready/instructions.md +0 -117
  368. package/.bmad/bmm/workflows/4-implementation/story-ready/workflow.yaml +0 -25
  369. package/.bmad/bmm/workflows/document-project/checklist.md +0 -245
  370. package/.bmad/bmm/workflows/document-project/documentation-requirements.csv +0 -12
  371. package/.bmad/bmm/workflows/document-project/instructions.md +0 -222
  372. package/.bmad/bmm/workflows/document-project/templates/deep-dive-template.md +0 -345
  373. package/.bmad/bmm/workflows/document-project/templates/index-template.md +0 -169
  374. package/.bmad/bmm/workflows/document-project/templates/project-overview-template.md +0 -103
  375. package/.bmad/bmm/workflows/document-project/templates/project-scan-report-schema.json +0 -160
  376. package/.bmad/bmm/workflows/document-project/templates/source-tree-template.md +0 -135
  377. package/.bmad/bmm/workflows/document-project/workflow.yaml +0 -34
  378. package/.bmad/bmm/workflows/document-project/workflows/deep-dive-instructions.md +0 -298
  379. package/.bmad/bmm/workflows/document-project/workflows/deep-dive.yaml +0 -31
  380. package/.bmad/bmm/workflows/document-project/workflows/full-scan-instructions.md +0 -1106
  381. package/.bmad/bmm/workflows/document-project/workflows/full-scan.yaml +0 -31
  382. package/.bmad/bmm/workflows/techdoc/documentation-standards.md +0 -262
  383. package/.bmad/bmm/workflows/testarch/atdd/atdd-checklist-template.md +0 -363
  384. package/.bmad/bmm/workflows/testarch/atdd/checklist.md +0 -373
  385. package/.bmad/bmm/workflows/testarch/atdd/instructions.md +0 -785
  386. package/.bmad/bmm/workflows/testarch/atdd/workflow.yaml +0 -52
  387. package/.bmad/bmm/workflows/testarch/automate/checklist.md +0 -580
  388. package/.bmad/bmm/workflows/testarch/automate/instructions.md +0 -1303
  389. package/.bmad/bmm/workflows/testarch/automate/workflow.yaml +0 -61
  390. package/.bmad/bmm/workflows/testarch/ci/checklist.md +0 -246
  391. package/.bmad/bmm/workflows/testarch/ci/github-actions-template.yaml +0 -165
  392. package/.bmad/bmm/workflows/testarch/ci/gitlab-ci-template.yaml +0 -128
  393. package/.bmad/bmm/workflows/testarch/ci/instructions.md +0 -517
  394. package/.bmad/bmm/workflows/testarch/ci/workflow.yaml +0 -53
  395. package/.bmad/bmm/workflows/testarch/framework/checklist.md +0 -321
  396. package/.bmad/bmm/workflows/testarch/framework/instructions.md +0 -455
  397. package/.bmad/bmm/workflows/testarch/framework/workflow.yaml +0 -53
  398. package/.bmad/bmm/workflows/testarch/nfr-assess/checklist.md +0 -405
  399. package/.bmad/bmm/workflows/testarch/nfr-assess/instructions.md +0 -722
  400. package/.bmad/bmm/workflows/testarch/nfr-assess/nfr-report-template.md +0 -443
  401. package/.bmad/bmm/workflows/testarch/nfr-assess/workflow.yaml +0 -56
  402. package/.bmad/bmm/workflows/testarch/test-design/checklist.md +0 -234
  403. package/.bmad/bmm/workflows/testarch/test-design/instructions.md +0 -621
  404. package/.bmad/bmm/workflows/testarch/test-design/test-design-template.md +0 -285
  405. package/.bmad/bmm/workflows/testarch/test-design/workflow.yaml +0 -52
  406. package/.bmad/bmm/workflows/testarch/test-review/checklist.md +0 -470
  407. package/.bmad/bmm/workflows/testarch/test-review/instructions.md +0 -608
  408. package/.bmad/bmm/workflows/testarch/test-review/test-review-template.md +0 -388
  409. package/.bmad/bmm/workflows/testarch/test-review/workflow.yaml +0 -53
  410. package/.bmad/bmm/workflows/testarch/trace/checklist.md +0 -654
  411. package/.bmad/bmm/workflows/testarch/trace/instructions.md +0 -1045
  412. package/.bmad/bmm/workflows/testarch/trace/trace-template.md +0 -673
  413. package/.bmad/bmm/workflows/testarch/trace/workflow.yaml +0 -66
  414. package/.bmad/bmm/workflows/workflow-status/init/instructions.md +0 -822
  415. package/.bmad/bmm/workflows/workflow-status/init/workflow.yaml +0 -27
  416. package/.bmad/bmm/workflows/workflow-status/instructions.md +0 -387
  417. package/.bmad/bmm/workflows/workflow-status/paths/enterprise-brownfield.yaml +0 -127
  418. package/.bmad/bmm/workflows/workflow-status/paths/enterprise-greenfield.yaml +0 -115
  419. package/.bmad/bmm/workflows/workflow-status/paths/game-design.yaml +0 -52
  420. package/.bmad/bmm/workflows/workflow-status/paths/method-brownfield.yaml +0 -97
  421. package/.bmad/bmm/workflows/workflow-status/paths/method-greenfield.yaml +0 -88
  422. package/.bmad/bmm/workflows/workflow-status/paths/quick-flow-brownfield.yaml +0 -58
  423. package/.bmad/bmm/workflows/workflow-status/paths/quick-flow-greenfield.yaml +0 -47
  424. package/.bmad/bmm/workflows/workflow-status/project-levels.yaml +0 -59
  425. package/.bmad/bmm/workflows/workflow-status/sample-level-3-workflow.yaml +0 -49
  426. package/.bmad/bmm/workflows/workflow-status/workflow-status-template.yaml +0 -31
  427. package/.bmad/bmm/workflows/workflow-status/workflow.yaml +0 -28
  428. package/.bmad/core/agents/bmad-master.md +0 -71
  429. package/.bmad/core/agents/bmad-web-orchestrator.agent.xml +0 -113
  430. package/.bmad/core/config.yaml +0 -11
  431. package/.bmad/core/tasks/adv-elicit-methods.csv +0 -39
  432. package/.bmad/core/tasks/adv-elicit.xml +0 -106
  433. package/.bmad/core/tasks/index-docs.xml +0 -65
  434. package/.bmad/core/tasks/validate-workflow.xml +0 -89
  435. package/.bmad/core/tasks/workflow.xml +0 -156
  436. package/.bmad/core/tools/shard-doc.xml +0 -65
  437. package/.bmad/core/workflows/brainstorming/README.md +0 -271
  438. package/.bmad/core/workflows/brainstorming/brain-methods.csv +0 -36
  439. package/.bmad/core/workflows/brainstorming/instructions.md +0 -314
  440. package/.bmad/core/workflows/brainstorming/template.md +0 -102
  441. package/.bmad/core/workflows/brainstorming/workflow.yaml +0 -43
  442. package/.bmad/core/workflows/party-mode/instructions.md +0 -183
  443. package/.bmad/core/workflows/party-mode/workflow.yaml +0 -27
  444. package/.bmad/docs/claude-code-instructions.md +0 -25
  445. package/.claude/commands/bmad/bmb/agents/bmad-builder.md +0 -70
  446. package/.claude/commands/bmad/bmb/workflows/audit-workflow.md +0 -15
  447. package/.claude/commands/bmad/bmb/workflows/convert-legacy.md +0 -15
  448. package/.claude/commands/bmad/bmb/workflows/create-agent.md +0 -15
  449. package/.claude/commands/bmad/bmb/workflows/create-module.md +0 -15
  450. package/.claude/commands/bmad/bmb/workflows/create-workflow.md +0 -15
  451. package/.claude/commands/bmad/bmb/workflows/edit-agent.md +0 -15
  452. package/.claude/commands/bmad/bmb/workflows/edit-module.md +0 -15
  453. package/.claude/commands/bmad/bmb/workflows/edit-workflow.md +0 -15
  454. package/.claude/commands/bmad/bmb/workflows/module-brief.md +0 -15
  455. package/.claude/commands/bmad/bmb/workflows/redoc.md +0 -15
  456. package/.claude/commands/bmad/bmm/agents/analyst.md +0 -75
  457. package/.claude/commands/bmad/bmm/agents/architect.md +0 -80
  458. package/.claude/commands/bmad/bmm/agents/dev.md +0 -69
  459. package/.claude/commands/bmad/bmm/agents/pm.md +0 -84
  460. package/.claude/commands/bmad/bmm/agents/sm.md +0 -93
  461. package/.claude/commands/bmad/bmm/agents/tea.md +0 -80
  462. package/.claude/commands/bmad/bmm/agents/tech-writer.md +0 -90
  463. package/.claude/commands/bmad/bmm/agents/ux-designer.md +0 -79
  464. package/.claude/commands/bmad/bmm/workflows/architecture.md +0 -15
  465. package/.claude/commands/bmad/bmm/workflows/brainstorm-project.md +0 -15
  466. package/.claude/commands/bmad/bmm/workflows/code-review.md +0 -15
  467. package/.claude/commands/bmad/bmm/workflows/correct-course.md +0 -15
  468. package/.claude/commands/bmad/bmm/workflows/create-epics-and-stories.md +0 -15
  469. package/.claude/commands/bmad/bmm/workflows/create-story.md +0 -15
  470. package/.claude/commands/bmad/bmm/workflows/create-ux-design.md +0 -15
  471. package/.claude/commands/bmad/bmm/workflows/dev-story.md +0 -15
  472. package/.claude/commands/bmad/bmm/workflows/document-project.md +0 -15
  473. package/.claude/commands/bmad/bmm/workflows/domain-research.md +0 -15
  474. package/.claude/commands/bmad/bmm/workflows/epic-tech-context.md +0 -15
  475. package/.claude/commands/bmad/bmm/workflows/prd.md +0 -15
  476. package/.claude/commands/bmad/bmm/workflows/product-brief.md +0 -15
  477. package/.claude/commands/bmad/bmm/workflows/research.md +0 -15
  478. package/.claude/commands/bmad/bmm/workflows/retrospective.md +0 -15
  479. package/.claude/commands/bmad/bmm/workflows/solutioning-gate-check.md +0 -15
  480. package/.claude/commands/bmad/bmm/workflows/sprint-planning.md +0 -15
  481. package/.claude/commands/bmad/bmm/workflows/story-context.md +0 -15
  482. package/.claude/commands/bmad/bmm/workflows/story-done.md +0 -15
  483. package/.claude/commands/bmad/bmm/workflows/story-ready.md +0 -15
  484. package/.claude/commands/bmad/bmm/workflows/tech-spec.md +0 -15
  485. package/.claude/commands/bmad/bmm/workflows/workflow-init.md +0 -15
  486. package/.claude/commands/bmad/bmm/workflows/workflow-status.md +0 -15
  487. package/.claude/commands/bmad/core/agents/bmad-master.md +0 -71
  488. package/.claude/commands/bmad/core/tasks/adv-elicit.md +0 -9
  489. package/.claude/commands/bmad/core/tasks/index-docs.md +0 -9
  490. package/.claude/commands/bmad/core/tools/shard-doc.md +0 -9
  491. package/.claude/commands/bmad/core/workflows/brainstorming.md +0 -15
  492. package/.claude/commands/bmad/core/workflows/party-mode.md +0 -15
  493. package/.claude/settings.local.json +0 -16
  494. package/src/modules/bmgd/workflows/4-production/dev-story/AUDIT-REPORT.md +0 -367
  495. package/src/modules/bmm/sub-modules/claude-code/README.md +0 -87
  496. package/src/modules/bmm/sub-modules/claude-code/config.yaml +0 -5
  497. package/src/modules/bmm/sub-modules/claude-code/injections.yaml +0 -242
  498. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-analysis/api-documenter.md +0 -102
  499. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-analysis/codebase-analyzer.md +0 -82
  500. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-analysis/data-analyst.md +0 -101
  501. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-analysis/pattern-detector.md +0 -84
  502. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/dependency-mapper.md +0 -83
  503. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/epic-optimizer.md +0 -81
  504. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/requirements-analyst.md +0 -61
  505. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/technical-decisions-curator.md +0 -168
  506. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/trend-spotter.md +0 -115
  507. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/user-journey-mapper.md +0 -123
  508. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-planning/user-researcher.md +0 -72
  509. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-research/market-researcher.md +0 -51
  510. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-research/tech-debt-auditor.md +0 -106
  511. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-review/document-reviewer.md +0 -102
  512. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-review/technical-evaluator.md +0 -68
  513. package/src/modules/bmm/sub-modules/claude-code/sub-agents/bmad-review/test-coverage-analyzer.md +0 -108
  514. package/src/modules/bmm/tasks/daily-standup.xml +0 -85
  515. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/instructions-level0-story.md +0 -200
  516. package/src/modules/bmm/workflows/2-plan-workflows/tech-spec/instructions-level1-stories.md +0 -451
  517. package/src/modules/bmm/workflows/3-solutioning/solutioning-gate-check/validation-criteria.yaml +0 -189
  518. package/src/modules/bmm/workflows/4-implementation/dev-story/AUDIT-REPORT.md +0 -367
  519. package/src/modules/bmm/workflows/workflow-status/sample-level-3-workflow.yaml +0 -49
  520. package/web-bundles/bmgd/agents/game-architect.xml +0 -664
  521. package/web-bundles/bmgd/agents/game-designer.xml +0 -5489
  522. package/web-bundles/bmgd/agents/game-dev.xml +0 -595
  523. package/web-bundles/bmgd/agents/game-scrum-master.xml +0 -699
  524. package/web-bundles/bmgd/teams/team-gamedev.xml +0 -6588
  525. package/web-bundles/bmm/agents/analyst.xml +0 -5263
  526. package/web-bundles/bmm/agents/architect.xml +0 -2378
  527. package/web-bundles/bmm/agents/dev.xml +0 -248
  528. package/web-bundles/bmm/agents/pm.xml +0 -4137
  529. package/web-bundles/bmm/agents/sm.xml +0 -708
  530. package/web-bundles/bmm/agents/tea.xml +0 -759
  531. package/web-bundles/bmm/agents/tech-writer.xml +0 -624
  532. package/web-bundles/bmm/agents/ux-designer.xml +0 -2492
  533. package/web-bundles/bmm/teams/team-fullstack.xml +0 -12369
  534. package/web-bundles/cis/agents/brainstorming-coach.xml +0 -1069
  535. package/web-bundles/cis/agents/creative-problem-solver.xml +0 -1060
  536. package/web-bundles/cis/agents/design-thinking-coach.xml +0 -955
  537. package/web-bundles/cis/agents/innovation-strategist.xml +0 -1108
  538. package/web-bundles/cis/agents/storyteller.xml +0 -598
  539. package/web-bundles/cis/teams/creative-squad.xml +0 -3449
@@ -1,721 +0,0 @@
1
- # Email-Based Authentication Testing
2
-
3
- ## Principle
4
-
5
- Email-based authentication (magic links, one-time codes, passwordless login) requires specialized testing with email capture services like Mailosaur or Ethereal. Extract magic links via HTML parsing or use built-in link extraction, preserve browser storage (local/session/cookies) when processing links, cache email payloads to avoid exhausting inbox quotas, and cover negative cases (expired links, reused links, multiple rapid requests). Log email IDs and links for troubleshooting, but scrub PII before committing artifacts.
6
-
7
- ## Rationale
8
-
9
- Email authentication introduces unique challenges: asynchronous email delivery, quota limits (AWS Cognito: 50/day), cost per email, and complex state management (session preservation across link clicks). Without proper patterns, tests become slow (wait for email each time), expensive (quota exhaustion), and brittle (timing issues, missing state). Using email capture services + session caching + state preservation patterns makes email auth tests fast, reliable, and cost-effective.
10
-
11
- ## Pattern Examples
12
-
13
- ### Example 1: Magic Link Extraction with Mailosaur
14
-
15
- **Context**: Passwordless login flow where user receives magic link via email, clicks it, and is authenticated.
16
-
17
- **Implementation**:
18
-
19
- ```typescript
20
- // tests/e2e/magic-link-auth.spec.ts
21
- import { test, expect } from '@playwright/test';
22
-
23
- /**
24
- * Magic Link Authentication Flow
25
- * 1. User enters email
26
- * 2. Backend sends magic link
27
- * 3. Test retrieves email via Mailosaur
28
- * 4. Extract and visit magic link
29
- * 5. Verify user is authenticated
30
- */
31
-
32
- // Mailosaur configuration
33
- const MAILOSAUR_API_KEY = process.env.MAILOSAUR_API_KEY!;
34
- const MAILOSAUR_SERVER_ID = process.env.MAILOSAUR_SERVER_ID!;
35
-
36
- /**
37
- * Extract href from HTML email body
38
- * DOMParser provides XML/HTML parsing in Node.js
39
- */
40
- function extractMagicLink(htmlString: string): string | null {
41
- const { JSDOM } = require('jsdom');
42
- const dom = new JSDOM(htmlString);
43
- const link = dom.window.document.querySelector('#magic-link-button');
44
- return link ? (link as HTMLAnchorElement).href : null;
45
- }
46
-
47
- /**
48
- * Alternative: Use Mailosaur's built-in link extraction
49
- * Mailosaur automatically parses links - no regex needed!
50
- */
51
- async function getMagicLinkFromEmail(email: string): Promise<string> {
52
- const MailosaurClient = require('mailosaur');
53
- const mailosaur = new MailosaurClient(MAILOSAUR_API_KEY);
54
-
55
- // Wait for email (timeout: 30 seconds)
56
- const message = await mailosaur.messages.get(
57
- MAILOSAUR_SERVER_ID,
58
- {
59
- sentTo: email,
60
- },
61
- {
62
- timeout: 30000, // 30 seconds
63
- },
64
- );
65
-
66
- // Mailosaur extracts links automatically - no parsing needed!
67
- const magicLink = message.html?.links?.[0]?.href;
68
-
69
- if (!magicLink) {
70
- throw new Error(`Magic link not found in email to ${email}`);
71
- }
72
-
73
- console.log(`📧 Email received. Magic link extracted: ${magicLink}`);
74
- return magicLink;
75
- }
76
-
77
- test.describe('Magic Link Authentication', () => {
78
- test('should authenticate user via magic link', async ({ page, context }) => {
79
- // Arrange: Generate unique test email
80
- const randomId = Math.floor(Math.random() * 1000000);
81
- const testEmail = `user-${randomId}@${MAILOSAUR_SERVER_ID}.mailosaur.net`;
82
-
83
- // Act: Request magic link
84
- await page.goto('/login');
85
- await page.getByTestId('email-input').fill(testEmail);
86
- await page.getByTestId('send-magic-link').click();
87
-
88
- // Assert: Success message
89
- await expect(page.getByTestId('check-email-message')).toBeVisible();
90
- await expect(page.getByTestId('check-email-message')).toContainText('Check your email');
91
-
92
- // Retrieve magic link from email
93
- const magicLink = await getMagicLinkFromEmail(testEmail);
94
-
95
- // Visit magic link
96
- await page.goto(magicLink);
97
-
98
- // Assert: User is authenticated
99
- await expect(page.getByTestId('user-menu')).toBeVisible();
100
- await expect(page.getByTestId('user-email')).toContainText(testEmail);
101
-
102
- // Verify session storage preserved
103
- const localStorage = await page.evaluate(() => JSON.stringify(window.localStorage));
104
- expect(localStorage).toContain('authToken');
105
- });
106
-
107
- test('should handle expired magic link', async ({ page }) => {
108
- // Use pre-expired link (older than 15 minutes)
109
- const expiredLink = 'http://localhost:3000/auth/verify?token=expired-token-123';
110
-
111
- await page.goto(expiredLink);
112
-
113
- // Assert: Error message displayed
114
- await expect(page.getByTestId('error-message')).toBeVisible();
115
- await expect(page.getByTestId('error-message')).toContainText('link has expired');
116
-
117
- // Assert: User NOT authenticated
118
- await expect(page.getByTestId('user-menu')).not.toBeVisible();
119
- });
120
-
121
- test('should prevent reusing magic link', async ({ page }) => {
122
- const randomId = Math.floor(Math.random() * 1000000);
123
- const testEmail = `user-${randomId}@${MAILOSAUR_SERVER_ID}.mailosaur.net`;
124
-
125
- // Request magic link
126
- await page.goto('/login');
127
- await page.getByTestId('email-input').fill(testEmail);
128
- await page.getByTestId('send-magic-link').click();
129
-
130
- const magicLink = await getMagicLinkFromEmail(testEmail);
131
-
132
- // Visit link first time (success)
133
- await page.goto(magicLink);
134
- await expect(page.getByTestId('user-menu')).toBeVisible();
135
-
136
- // Sign out
137
- await page.getByTestId('sign-out').click();
138
-
139
- // Try to reuse same link (should fail)
140
- await page.goto(magicLink);
141
- await expect(page.getByTestId('error-message')).toBeVisible();
142
- await expect(page.getByTestId('error-message')).toContainText('link has already been used');
143
- });
144
- });
145
- ```
146
-
147
- **Cypress equivalent with Mailosaur plugin**:
148
-
149
- ```javascript
150
- // cypress/e2e/magic-link-auth.cy.ts
151
- describe('Magic Link Authentication', () => {
152
- it('should authenticate user via magic link', () => {
153
- const serverId = Cypress.env('MAILOSAUR_SERVERID');
154
- const randomId = Cypress._.random(1e6);
155
- const testEmail = `user-${randomId}@${serverId}.mailosaur.net`;
156
-
157
- // Request magic link
158
- cy.visit('/login');
159
- cy.get('[data-cy="email-input"]').type(testEmail);
160
- cy.get('[data-cy="send-magic-link"]').click();
161
- cy.get('[data-cy="check-email-message"]').should('be.visible');
162
-
163
- // Retrieve and visit magic link
164
- cy.mailosaurGetMessage(serverId, { sentTo: testEmail })
165
- .its('html.links.0.href') // Mailosaur extracts links automatically!
166
- .should('exist')
167
- .then((magicLink) => {
168
- cy.log(`Magic link: ${magicLink}`);
169
- cy.visit(magicLink);
170
- });
171
-
172
- // Verify authenticated
173
- cy.get('[data-cy="user-menu"]').should('be.visible');
174
- cy.get('[data-cy="user-email"]').should('contain', testEmail);
175
- });
176
- });
177
- ```
178
-
179
- **Key Points**:
180
-
181
- - **Mailosaur auto-extraction**: `html.links[0].href` or `html.codes[0].value`
182
- - **Unique emails**: Random ID prevents collisions
183
- - **Negative testing**: Expired and reused links tested
184
- - **State verification**: localStorage/session checked
185
- - **Fast email retrieval**: 30 second timeout typical
186
-
187
- ---
188
-
189
- ### Example 2: State Preservation Pattern with cy.session / Playwright storageState
190
-
191
- **Context**: Cache authenticated session to avoid requesting magic link on every test.
192
-
193
- **Implementation**:
194
-
195
- ```typescript
196
- // playwright/fixtures/email-auth-fixture.ts
197
- import { test as base } from '@playwright/test';
198
- import { getMagicLinkFromEmail } from '../support/mailosaur-helpers';
199
-
200
- type EmailAuthFixture = {
201
- authenticatedUser: { email: string; token: string };
202
- };
203
-
204
- export const test = base.extend<EmailAuthFixture>({
205
- authenticatedUser: async ({ page, context }, use) => {
206
- const randomId = Math.floor(Math.random() * 1000000);
207
- const testEmail = `user-${randomId}@${process.env.MAILOSAUR_SERVER_ID}.mailosaur.net`;
208
-
209
- // Check if we have cached auth state for this email
210
- const storageStatePath = `./test-results/auth-state-${testEmail}.json`;
211
-
212
- try {
213
- // Try to reuse existing session
214
- await context.storageState({ path: storageStatePath });
215
- await page.goto('/dashboard');
216
-
217
- // Validate session is still valid
218
- const isAuthenticated = await page.getByTestId('user-menu').isVisible({ timeout: 2000 });
219
-
220
- if (isAuthenticated) {
221
- console.log(`✅ Reusing cached session for ${testEmail}`);
222
- await use({ email: testEmail, token: 'cached' });
223
- return;
224
- }
225
- } catch (error) {
226
- console.log(`📧 No cached session, requesting magic link for ${testEmail}`);
227
- }
228
-
229
- // Request new magic link
230
- await page.goto('/login');
231
- await page.getByTestId('email-input').fill(testEmail);
232
- await page.getByTestId('send-magic-link').click();
233
-
234
- // Get magic link from email
235
- const magicLink = await getMagicLinkFromEmail(testEmail);
236
-
237
- // Visit link and authenticate
238
- await page.goto(magicLink);
239
- await expect(page.getByTestId('user-menu')).toBeVisible();
240
-
241
- // Extract auth token from localStorage
242
- const authToken = await page.evaluate(() => localStorage.getItem('authToken'));
243
-
244
- // Save session state for reuse
245
- await context.storageState({ path: storageStatePath });
246
-
247
- console.log(`💾 Cached session for ${testEmail}`);
248
-
249
- await use({ email: testEmail, token: authToken || '' });
250
- },
251
- });
252
- ```
253
-
254
- **Cypress equivalent with cy.session + data-session**:
255
-
256
- ```javascript
257
- // cypress/support/commands/email-auth.js
258
- import { dataSession } from 'cypress-data-session';
259
-
260
- /**
261
- * Authenticate via magic link with session caching
262
- * - First run: Requests email, extracts link, authenticates
263
- * - Subsequent runs: Reuses cached session (no email)
264
- */
265
- Cypress.Commands.add('authViaMagicLink', (email) => {
266
- return dataSession({
267
- name: `magic-link-${email}`,
268
-
269
- // First-time setup: Request and process magic link
270
- setup: () => {
271
- cy.visit('/login');
272
- cy.get('[data-cy="email-input"]').type(email);
273
- cy.get('[data-cy="send-magic-link"]').click();
274
-
275
- // Get magic link from Mailosaur
276
- cy.mailosaurGetMessage(Cypress.env('MAILOSAUR_SERVERID'), {
277
- sentTo: email,
278
- })
279
- .its('html.links.0.href')
280
- .should('exist')
281
- .then((magicLink) => {
282
- cy.visit(magicLink);
283
- });
284
-
285
- // Wait for authentication
286
- cy.get('[data-cy="user-menu"]', { timeout: 10000 }).should('be.visible');
287
-
288
- // Preserve authentication state
289
- return cy.getAllLocalStorage().then((storage) => {
290
- return { storage, email };
291
- });
292
- },
293
-
294
- // Validate cached session is still valid
295
- validate: (cached) => {
296
- return cy.wrap(Boolean(cached?.storage));
297
- },
298
-
299
- // Recreate session from cache (no email needed)
300
- recreate: (cached) => {
301
- // Restore localStorage
302
- cy.setLocalStorage(cached.storage);
303
- cy.visit('/dashboard');
304
- cy.get('[data-cy="user-menu"]', { timeout: 5000 }).should('be.visible');
305
- },
306
-
307
- shareAcrossSpecs: true, // Share session across all tests
308
- });
309
- });
310
- ```
311
-
312
- **Usage in tests**:
313
-
314
- ```javascript
315
- // cypress/e2e/dashboard.cy.ts
316
- describe('Dashboard', () => {
317
- const serverId = Cypress.env('MAILOSAUR_SERVERID');
318
- const testEmail = `test-user@${serverId}.mailosaur.net`;
319
-
320
- beforeEach(() => {
321
- // First test: Requests magic link
322
- // Subsequent tests: Reuses cached session (no email!)
323
- cy.authViaMagicLink(testEmail);
324
- });
325
-
326
- it('should display user dashboard', () => {
327
- cy.get('[data-cy="dashboard-content"]').should('be.visible');
328
- });
329
-
330
- it('should show user profile', () => {
331
- cy.get('[data-cy="user-email"]').should('contain', testEmail);
332
- });
333
-
334
- // Both tests share same session - only 1 email consumed!
335
- });
336
- ```
337
-
338
- **Key Points**:
339
-
340
- - **Session caching**: First test requests email, rest reuse session
341
- - **State preservation**: localStorage/cookies saved and restored
342
- - **Validation**: Check cached session is still valid
343
- - **Quota optimization**: Massive reduction in email consumption
344
- - **Fast tests**: Cached auth takes seconds vs. minutes
345
-
346
- ---
347
-
348
- ### Example 3: Negative Flow Tests (Expired, Invalid, Reused Links)
349
-
350
- **Context**: Comprehensive negative testing for email authentication edge cases.
351
-
352
- **Implementation**:
353
-
354
- ```typescript
355
- // tests/e2e/email-auth-negative.spec.ts
356
- import { test, expect } from '@playwright/test';
357
- import { getMagicLinkFromEmail } from '../support/mailosaur-helpers';
358
-
359
- const MAILOSAUR_SERVER_ID = process.env.MAILOSAUR_SERVER_ID!;
360
-
361
- test.describe('Email Auth Negative Flows', () => {
362
- test('should reject expired magic link', async ({ page }) => {
363
- // Generate expired link (simulate 24 hours ago)
364
- const expiredToken = Buffer.from(
365
- JSON.stringify({
366
- email: 'test@example.com',
367
- exp: Date.now() - 24 * 60 * 60 * 1000, // 24 hours ago
368
- }),
369
- ).toString('base64');
370
-
371
- const expiredLink = `http://localhost:3000/auth/verify?token=${expiredToken}`;
372
-
373
- // Visit expired link
374
- await page.goto(expiredLink);
375
-
376
- // Assert: Error displayed
377
- await expect(page.getByTestId('error-message')).toBeVisible();
378
- await expect(page.getByTestId('error-message')).toContainText(/link.*expired|expired.*link/i);
379
-
380
- // Assert: Link to request new one
381
- await expect(page.getByTestId('request-new-link')).toBeVisible();
382
-
383
- // Assert: User NOT authenticated
384
- await expect(page.getByTestId('user-menu')).not.toBeVisible();
385
- });
386
-
387
- test('should reject invalid magic link token', async ({ page }) => {
388
- const invalidLink = 'http://localhost:3000/auth/verify?token=invalid-garbage';
389
-
390
- await page.goto(invalidLink);
391
-
392
- // Assert: Error displayed
393
- await expect(page.getByTestId('error-message')).toBeVisible();
394
- await expect(page.getByTestId('error-message')).toContainText(/invalid.*link|link.*invalid/i);
395
-
396
- // Assert: User not authenticated
397
- await expect(page.getByTestId('user-menu')).not.toBeVisible();
398
- });
399
-
400
- test('should reject already-used magic link', async ({ page, context }) => {
401
- const randomId = Math.floor(Math.random() * 1000000);
402
- const testEmail = `user-${randomId}@${MAILOSAUR_SERVER_ID}.mailosaur.net`;
403
-
404
- // Request magic link
405
- await page.goto('/login');
406
- await page.getByTestId('email-input').fill(testEmail);
407
- await page.getByTestId('send-magic-link').click();
408
-
409
- const magicLink = await getMagicLinkFromEmail(testEmail);
410
-
411
- // Visit link FIRST time (success)
412
- await page.goto(magicLink);
413
- await expect(page.getByTestId('user-menu')).toBeVisible();
414
-
415
- // Sign out
416
- await page.getByTestId('user-menu').click();
417
- await page.getByTestId('sign-out').click();
418
- await expect(page.getByTestId('user-menu')).not.toBeVisible();
419
-
420
- // Try to reuse SAME link (should fail)
421
- await page.goto(magicLink);
422
-
423
- // Assert: Link already used error
424
- await expect(page.getByTestId('error-message')).toBeVisible();
425
- await expect(page.getByTestId('error-message')).toContainText(/already.*used|link.*used/i);
426
-
427
- // Assert: User not authenticated
428
- await expect(page.getByTestId('user-menu')).not.toBeVisible();
429
- });
430
-
431
- test('should handle rapid successive link requests', async ({ page }) => {
432
- const randomId = Math.floor(Math.random() * 1000000);
433
- const testEmail = `user-${randomId}@${MAILOSAUR_SERVER_ID}.mailosaur.net`;
434
-
435
- // Request magic link 3 times rapidly
436
- for (let i = 0; i < 3; i++) {
437
- await page.goto('/login');
438
- await page.getByTestId('email-input').fill(testEmail);
439
- await page.getByTestId('send-magic-link').click();
440
- await expect(page.getByTestId('check-email-message')).toBeVisible();
441
- }
442
-
443
- // Only the LATEST link should work
444
- const MailosaurClient = require('mailosaur');
445
- const mailosaur = new MailosaurClient(process.env.MAILOSAUR_API_KEY);
446
-
447
- const messages = await mailosaur.messages.list(MAILOSAUR_SERVER_ID, {
448
- sentTo: testEmail,
449
- });
450
-
451
- // Should receive 3 emails
452
- expect(messages.items.length).toBeGreaterThanOrEqual(3);
453
-
454
- // Get the LATEST magic link
455
- const latestMessage = messages.items[0]; // Most recent first
456
- const latestLink = latestMessage.html.links[0].href;
457
-
458
- // Latest link works
459
- await page.goto(latestLink);
460
- await expect(page.getByTestId('user-menu')).toBeVisible();
461
-
462
- // Older links should NOT work (if backend invalidates previous)
463
- await page.getByTestId('sign-out').click();
464
- const olderLink = messages.items[1].html.links[0].href;
465
-
466
- await page.goto(olderLink);
467
- await expect(page.getByTestId('error-message')).toBeVisible();
468
- });
469
-
470
- test('should rate-limit excessive magic link requests', async ({ page }) => {
471
- const randomId = Math.floor(Math.random() * 1000000);
472
- const testEmail = `user-${randomId}@${MAILOSAUR_SERVER_ID}.mailosaur.net`;
473
-
474
- // Request magic link 10 times rapidly (should hit rate limit)
475
- for (let i = 0; i < 10; i++) {
476
- await page.goto('/login');
477
- await page.getByTestId('email-input').fill(testEmail);
478
- await page.getByTestId('send-magic-link').click();
479
-
480
- // After N requests, should show rate limit error
481
- const errorVisible = await page
482
- .getByTestId('rate-limit-error')
483
- .isVisible({ timeout: 1000 })
484
- .catch(() => false);
485
-
486
- if (errorVisible) {
487
- console.log(`Rate limit hit after ${i + 1} requests`);
488
- await expect(page.getByTestId('rate-limit-error')).toContainText(/too many.*requests|rate.*limit/i);
489
- return;
490
- }
491
- }
492
-
493
- // If no rate limit after 10 requests, log warning
494
- console.warn('⚠️ No rate limit detected after 10 requests');
495
- });
496
- });
497
- ```
498
-
499
- **Key Points**:
500
-
501
- - **Expired links**: Test 24+ hour old tokens
502
- - **Invalid tokens**: Malformed or garbage tokens rejected
503
- - **Reuse prevention**: Same link can't be used twice
504
- - **Rapid requests**: Multiple requests handled gracefully
505
- - **Rate limiting**: Excessive requests blocked
506
-
507
- ---
508
-
509
- ### Example 4: Caching Strategy with cypress-data-session / Playwright Projects
510
-
511
- **Context**: Minimize email consumption by sharing authentication state across tests and specs.
512
-
513
- **Implementation**:
514
-
515
- ```javascript
516
- // cypress/support/commands/register-and-sign-in.js
517
- import { dataSession } from 'cypress-data-session';
518
-
519
- /**
520
- * Email Authentication Caching Strategy
521
- * - One email per test run (not per spec, not per test)
522
- * - First spec: Full registration flow (form → email → code → sign in)
523
- * - Subsequent specs: Only sign in (reuse user)
524
- * - Subsequent tests in same spec: Session already active (no sign in)
525
- */
526
-
527
- // Helper: Fill registration form
528
- function fillRegistrationForm({ fullName, userName, email, password }) {
529
- cy.intercept('POST', 'https://cognito-idp*').as('cognito');
530
- cy.contains('Register').click();
531
- cy.get('#reg-dialog-form').should('be.visible');
532
- cy.get('#first-name').type(fullName, { delay: 0 });
533
- cy.get('#last-name').type(lastName, { delay: 0 });
534
- cy.get('#email').type(email, { delay: 0 });
535
- cy.get('#username').type(userName, { delay: 0 });
536
- cy.get('#password').type(password, { delay: 0 });
537
- cy.contains('button', 'Create an account').click();
538
- cy.wait('@cognito').its('response.statusCode').should('equal', 200);
539
- }
540
-
541
- // Helper: Confirm registration with email code
542
- function confirmRegistration(email) {
543
- return cy
544
- .mailosaurGetMessage(Cypress.env('MAILOSAUR_SERVERID'), { sentTo: email })
545
- .its('html.codes.0.value') // Mailosaur auto-extracts codes!
546
- .then((code) => {
547
- cy.intercept('POST', 'https://cognito-idp*').as('cognito');
548
- cy.get('#verification-code').type(code, { delay: 0 });
549
- cy.contains('button', 'Confirm registration').click();
550
- cy.wait('@cognito');
551
- cy.contains('You are now registered!').should('be.visible');
552
- cy.contains('button', /ok/i).click();
553
- return cy.wrap(code); // Return code for reference
554
- });
555
- }
556
-
557
- // Helper: Full registration (form + email)
558
- function register({ fullName, userName, email, password }) {
559
- fillRegistrationForm({ fullName, userName, email, password });
560
- return confirmRegistration(email);
561
- }
562
-
563
- // Helper: Sign in
564
- function signIn({ userName, password }) {
565
- cy.intercept('POST', 'https://cognito-idp*').as('cognito');
566
- cy.contains('Sign in').click();
567
- cy.get('#sign-in-username').type(userName, { delay: 0 });
568
- cy.get('#sign-in-password').type(password, { delay: 0 });
569
- cy.contains('button', 'Sign in').click();
570
- cy.wait('@cognito');
571
- cy.contains('Sign out').should('be.visible');
572
- }
573
-
574
- /**
575
- * Register and sign in with email caching
576
- * ONE EMAIL PER MACHINE (cypress run or cypress open)
577
- */
578
- Cypress.Commands.add('registerAndSignIn', ({ fullName, userName, email, password }) => {
579
- return dataSession({
580
- name: email, // Unique session per email
581
-
582
- // First time: Full registration (form → email → code)
583
- init: () => register({ fullName, userName, email, password }),
584
-
585
- // Subsequent specs: Just check email exists (code already used)
586
- setup: () => confirmRegistration(email),
587
-
588
- // Always runs after init/setup: Sign in
589
- recreate: () => signIn({ userName, password }),
590
-
591
- // Share across ALL specs (one email for entire test run)
592
- shareAcrossSpecs: true,
593
- });
594
- });
595
- ```
596
-
597
- **Usage across multiple specs**:
598
-
599
- ```javascript
600
- // cypress/e2e/place-order.cy.ts
601
- describe('Place Order', () => {
602
- beforeEach(() => {
603
- cy.visit('/');
604
- cy.registerAndSignIn({
605
- fullName: Cypress.env('fullName'), // From cypress.config
606
- userName: Cypress.env('userName'),
607
- email: Cypress.env('email'), // SAME email across all specs
608
- password: Cypress.env('password'),
609
- });
610
- });
611
-
612
- it('should place order', () => {
613
- /* ... */
614
- });
615
- it('should view order history', () => {
616
- /* ... */
617
- });
618
- });
619
-
620
- // cypress/e2e/profile.cy.ts
621
- describe('User Profile', () => {
622
- beforeEach(() => {
623
- cy.visit('/');
624
- cy.registerAndSignIn({
625
- fullName: Cypress.env('fullName'),
626
- userName: Cypress.env('userName'),
627
- email: Cypress.env('email'), // SAME email - no new email sent!
628
- password: Cypress.env('password'),
629
- });
630
- });
631
-
632
- it('should update profile', () => {
633
- /* ... */
634
- });
635
- });
636
- ```
637
-
638
- **Playwright equivalent with storageState**:
639
-
640
- ```typescript
641
- // playwright.config.ts
642
- import { defineConfig } from '@playwright/test';
643
-
644
- export default defineConfig({
645
- projects: [
646
- {
647
- name: 'setup',
648
- testMatch: /global-setup\.ts/,
649
- },
650
- {
651
- name: 'authenticated',
652
- testMatch: /.*\.spec\.ts/,
653
- dependencies: ['setup'],
654
- use: {
655
- storageState: '.auth/user-session.json', // Reuse auth state
656
- },
657
- },
658
- ],
659
- });
660
- ```
661
-
662
- ```typescript
663
- // tests/global-setup.ts (runs once)
664
- import { test as setup } from '@playwright/test';
665
- import { getMagicLinkFromEmail } from './support/mailosaur-helpers';
666
-
667
- const authFile = '.auth/user-session.json';
668
-
669
- setup('authenticate via magic link', async ({ page }) => {
670
- const testEmail = process.env.TEST_USER_EMAIL!;
671
-
672
- // Request magic link
673
- await page.goto('/login');
674
- await page.getByTestId('email-input').fill(testEmail);
675
- await page.getByTestId('send-magic-link').click();
676
-
677
- // Get and visit magic link
678
- const magicLink = await getMagicLinkFromEmail(testEmail);
679
- await page.goto(magicLink);
680
-
681
- // Verify authenticated
682
- await expect(page.getByTestId('user-menu')).toBeVisible();
683
-
684
- // Save authenticated state (ONE TIME for all tests)
685
- await page.context().storageState({ path: authFile });
686
-
687
- console.log('✅ Authentication state saved to', authFile);
688
- });
689
- ```
690
-
691
- **Key Points**:
692
-
693
- - **One email per run**: Global setup authenticates once
694
- - **State reuse**: All tests use cached storageState
695
- - **cypress-data-session**: Intelligently manages cache lifecycle
696
- - **shareAcrossSpecs**: Session shared across all spec files
697
- - **Massive savings**: 500 tests = 1 email (not 500!)
698
-
699
- ---
700
-
701
- ## Email Authentication Testing Checklist
702
-
703
- Before implementing email auth tests, verify:
704
-
705
- - [ ] **Email service**: Mailosaur/Ethereal/MailHog configured with API keys
706
- - [ ] **Link extraction**: Use built-in parsing (html.links[0].href) over regex
707
- - [ ] **State preservation**: localStorage/session/cookies saved and restored
708
- - [ ] **Session caching**: cypress-data-session or storageState prevents redundant emails
709
- - [ ] **Negative flows**: Expired, invalid, reused, rapid requests tested
710
- - [ ] **Quota awareness**: One email per run (not per test)
711
- - [ ] **PII scrubbing**: Email IDs logged for debug, but scrubbed from artifacts
712
- - [ ] **Timeout handling**: 30 second email retrieval timeout configured
713
-
714
- ## Integration Points
715
-
716
- - Used in workflows: `*framework` (email auth setup), `*automate` (email auth test generation)
717
- - Related fragments: `fixture-architecture.md`, `test-quality.md`
718
- - Email services: Mailosaur (recommended), Ethereal (free), MailHog (self-hosted)
719
- - Plugins: cypress-mailosaur, cypress-data-session
720
-
721
- _Source: Email authentication blog, Murat testing toolkit, Mailosaur documentation_