@polymorphism-tech/morph-spec 8.34.2 → 8.35.0

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 (325) hide show
  1. package/CLAUDE.md +20 -3
  2. package/README.md +2 -2
  3. package/bin/morph-spec.js +18 -4
  4. package/bin/validate.js +379 -379
  5. package/claude-plugin.json +1 -1
  6. package/docs/CHEATSHEET.md +5 -4
  7. package/docs/QUICKSTART.md +1 -1
  8. package/framework/MORPH.md +16 -17
  9. package/framework/agents.json +197 -44
  10. package/framework/ai-pin.json +22 -0
  11. package/framework/commands/morph-media.md +45 -0
  12. package/framework/docs/CLI.md +234 -9
  13. package/framework/evals/proof-rubrics/README.md +76 -0
  14. package/framework/evals/proof-rubrics/eval-de-modelo.md +64 -0
  15. package/framework/evals/proof-rubrics/fiacao.md +54 -0
  16. package/framework/evals/proof-rubrics/guard-cego.md +52 -0
  17. package/framework/evals/proof-rubrics/media-claims.md +109 -0
  18. package/framework/evals/proof-rubrics/mutation-proof.md +77 -0
  19. package/framework/evals/proof-rubrics/observabilidade-genai.md +119 -0
  20. package/framework/evals/proof-rubrics/verde-nao-e-coberto.md +48 -0
  21. package/framework/evals/rubrics/architecture.md +30 -0
  22. package/framework/evals/rubrics/code-quality.md +26 -0
  23. package/framework/evals/rubrics/test-coverage.md +20 -0
  24. package/framework/hooks/claude-code/core/protect-spec-files.js +41 -4
  25. package/framework/hooks/claude-code/statusline.sh +11 -11
  26. package/framework/hooks/git/commit-msg/conventional-commits.sh +33 -33
  27. package/framework/hooks/git/pre-commit/agents.sh +25 -25
  28. package/framework/hooks/git/pre-commit/orchestrator.sh +64 -64
  29. package/framework/hooks/git/pre-commit/specs.sh +50 -50
  30. package/framework/hooks/git/pre-push/run-tests.sh +44 -44
  31. package/framework/hooks/shared/e2e-check.js +135 -22
  32. package/framework/hooks/shared/stdin-reader.js +26 -26
  33. package/framework/rules/ai-agents-standards.md +14 -2
  34. package/framework/schemas/ai-pin.schema.json +97 -0
  35. package/framework/schemas/config.schema.json +107 -0
  36. package/framework/schemas/feature.schema.json +23 -4
  37. package/framework/skills/core/create-umbraco-lp/SKILL.md +1 -1
  38. package/framework/skills/core/migrate-lp-to-umbraco/SKILL.md +1 -1
  39. package/framework/skills/core/morph-apply/SKILL.md +26 -5
  40. package/framework/skills/core/morph-brainstorming/SKILL.md +1 -1
  41. package/framework/skills/core/morph-eval/SKILL.md +1 -1
  42. package/framework/skills/core/morph-hotfix/SKILL.md +2 -2
  43. package/framework/skills/core/morph-implement/SKILL.md +18 -2
  44. package/framework/skills/core/morph-media/SKILL.md +215 -0
  45. package/framework/skills/core/morph-plan/SKILL.md +33 -2
  46. package/framework/skills/core/morph-proposal/SKILL.md +1 -1
  47. package/framework/skills/core/morph-review/SKILL.md +166 -9
  48. package/framework/skills/core/morph-stack-scan/SKILL.md +1 -1
  49. package/framework/skills/core/morph-standards/SKILL.md +1 -1
  50. package/framework/skills/core/morph-uiux/SKILL.md +1 -1
  51. package/framework/standards/PROVENANCE.json +81 -3
  52. package/framework/standards/STANDARDS.json +1483 -839
  53. package/framework/standards/ai-agents/agent-archetypes.md +160 -0
  54. package/framework/standards/ai-agents/agent-session.md +164 -68
  55. package/framework/standards/ai-agents/agent-spec.md +196 -0
  56. package/framework/standards/ai-agents/batching.md +61 -37
  57. package/framework/standards/ai-agents/context-providers.md +97 -24
  58. package/framework/standards/ai-agents/conversational-agent-with-phases.md +239 -0
  59. package/framework/standards/ai-agents/cost-and-budget.md +256 -0
  60. package/framework/standards/ai-agents/durable-workflows-hitl.md +98 -5
  61. package/framework/standards/ai-agents/evals-with-cache.md +289 -0
  62. package/framework/standards/ai-agents/guardrails.md +222 -0
  63. package/framework/standards/ai-agents/llm-runtime-defaults.md +226 -0
  64. package/framework/standards/ai-agents/mcp-server.md +119 -18
  65. package/framework/standards/ai-agents/mcp-tools.md +85 -32
  66. package/framework/standards/ai-agents/media-pipeline.md +352 -0
  67. package/framework/standards/ai-agents/media-video.md +267 -0
  68. package/framework/standards/ai-agents/middleware-patterns.md +39 -5
  69. package/framework/standards/ai-agents/modalities-image-gen.md +354 -105
  70. package/framework/standards/ai-agents/modalities-speech-to-text.md +8 -2
  71. package/framework/standards/ai-agents/modalities-text-to-speech.md +10 -2
  72. package/framework/standards/ai-agents/modalities-vision.md +6 -2
  73. package/framework/standards/ai-agents/multi-agent-patterns.md +61 -5
  74. package/framework/standards/ai-agents/observability-patterns.md +227 -17
  75. package/framework/standards/ai-agents/production.md +38 -9
  76. package/framework/standards/ai-agents/prompt-sources.md +389 -0
  77. package/framework/standards/ai-agents/providers/model-registry.md +174 -39
  78. package/framework/standards/ai-agents/rag-custom-pgvector.md +69 -4
  79. package/framework/standards/ai-agents/service-tier-flex.md +27 -19
  80. package/framework/standards/ai-agents/setup.md +166 -50
  81. package/framework/standards/ai-agents/structured-output.md +34 -3
  82. package/framework/standards/ai-agents/sweet-spot.md +23 -3
  83. package/framework/standards/ai-agents/testing-ai.md +236 -0
  84. package/framework/standards/ai-agents/vector-data-extensions.md +50 -20
  85. package/framework/standards/ai-agents/workflows.md +27 -7
  86. package/framework/standards/frontend/design-system/ai-image-generation.md +12 -0
  87. package/framework/standards/frontend/design-system/ai-video-generation.md +13 -0
  88. package/framework/standards/infrastructure/docker/local-compose-isolation.md +3 -1
  89. package/framework/templates/.idea/morph-templates.xml +92 -0
  90. package/framework/templates/.vscode/morph-templates.code-snippets +186 -0
  91. package/framework/templates/IDE-SNIPPETS.md +262 -262
  92. package/framework/templates/REGISTRY.json +13 -0
  93. package/framework/templates/code/dotnet/abstractions/api-endpoint.cs +7 -7
  94. package/framework/templates/code/dotnet/ai-agents/AgentBootstrap.cs.template +39 -39
  95. package/framework/templates/code/dotnet/ai-agents/EmbeddingService.cs.template +68 -68
  96. package/framework/templates/code/dotnet/ai-agents/ModelRegistry.cs.template +117 -117
  97. package/framework/templates/code/dotnet/ai-agents/PromptRepository.cs.template +1 -1
  98. package/framework/templates/code/dotnet/ai-agents/ResilientToolMiddleware.cs.template +61 -61
  99. package/framework/templates/code/dotnet/ai-agents/VectorSearchTool.cs.template +107 -107
  100. package/framework/templates/code/dotnet/ai-agents/model-registry.json.template +58 -58
  101. package/framework/templates/code/dotnet/contracts/contracts-vsa.cs +281 -281
  102. package/framework/templates/code/dotnet/database/migration.cs +83 -83
  103. package/framework/templates/code/dotnet/feature/endpoint.cs.hbs +21 -21
  104. package/framework/templates/code/dotnet/feature/request.cs.hbs +4 -4
  105. package/framework/templates/code/dotnet/feature/response.cs.hbs +4 -4
  106. package/framework/templates/code/dotnet/feature/validator.cs.hbs +15 -15
  107. package/framework/templates/code/sql/ai-agents/agent-prompts-migration.sql.template +1 -1
  108. package/framework/templates/code/sql/ai-agents/pgvector-embeddings-migration.sql.template +91 -91
  109. package/framework/templates/code/typescript/contracts.ts +167 -167
  110. package/framework/templates/docs/clarifications.md +253 -253
  111. package/framework/templates/docs/schema-analysis.md +119 -119
  112. package/framework/templates/docs/ui-components.md +52 -52
  113. package/framework/templates/docs/ui-design-system.md +76 -76
  114. package/framework/templates/docs/ui-flows.md +167 -167
  115. package/framework/templates/docs/ui-mockups.md +98 -98
  116. package/framework/templates/dotnet/ai-kit/Directory.Build.props +25 -0
  117. package/framework/templates/dotnet/ai-kit/Directory.Packages.props +26 -0
  118. package/framework/templates/dotnet/ai-kit/Morph.AiKit.sln +56 -0
  119. package/framework/templates/dotnet/ai-kit/NuGet.config +12 -0
  120. package/framework/templates/dotnet/ai-kit/README.md +128 -0
  121. package/framework/templates/dotnet/ai-kit/global.json +9 -0
  122. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Agents/AgentApi.cs +65 -0
  123. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Agents/AgentFactory.cs +289 -0
  124. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Agents/AgentFactoryOptions.cs +91 -0
  125. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Agents/AgentSpec.cs +91 -0
  126. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Agents/AgentSpecOptions.cs +181 -0
  127. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/AiKitAssemblyMarker.cs +14 -0
  128. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Conversation/ConversationStore.cs +174 -0
  129. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Conversation/IConversationStore.cs +54 -0
  130. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Conversation/InMemoryConversationStore.cs +75 -0
  131. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/CountingChatClient.cs +71 -0
  132. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalAssertion.cs +246 -0
  133. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalCacheMissException.cs +57 -0
  134. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalCacheOptions.cs +78 -0
  135. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalCacheStamp.cs +225 -0
  136. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalFixture.cs +463 -0
  137. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalMode.cs +32 -0
  138. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalQualityEvaluators.cs +49 -0
  139. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalScenario.cs +214 -0
  140. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/EvalSummary.cs +168 -0
  141. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/OfflineChatClient.cs +142 -0
  142. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Evals/ShortPathResponseCache.cs +349 -0
  143. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/IMediaGenerator.cs +42 -0
  144. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/IMediaProvider.cs +77 -0
  145. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaArtifact.cs +28 -0
  146. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaDisclosure.cs +107 -0
  147. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaGenerator.cs +253 -0
  148. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaIdempotencyKey.cs +103 -0
  149. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaJob.cs +259 -0
  150. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaJobId.cs +21 -0
  151. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaJobState.cs +47 -0
  152. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaPricing.cs +102 -0
  153. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaProvenance.cs +44 -0
  154. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaRequest.cs +192 -0
  155. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaResult.cs +94 -0
  156. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaReview.cs +99 -0
  157. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaSeams.cs +97 -0
  158. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MediaStore.cs +133 -0
  159. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/MorphMedia.cs +93 -0
  160. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/Providers/GoogleImageProvider.cs +112 -0
  161. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/Providers/OpenAIImageProvider.cs +288 -0
  162. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Media/Providers/VeoVideoProvider.cs +158 -0
  163. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Middleware/IUsageCostSink.cs +29 -0
  164. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Middleware/UsageCostMiddleware.cs +208 -0
  165. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Middleware/UsageCostRecord.cs +95 -0
  166. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Morph.AiKit.csproj +38 -0
  167. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Observability/MorphOpenTelemetryExtensions.cs +119 -0
  168. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Observability/MorphTelemetryOptions.cs +82 -0
  169. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Providers/IProviderClientFactory.cs +33 -0
  170. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Providers/ModelAlias.cs +267 -0
  171. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Providers/ModelRegistry.cs +474 -0
  172. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Providers/model-registry.v2.json +87 -0
  173. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Rag/DeltaIngest.cs +169 -0
  174. package/framework/templates/dotnet/ai-kit/src/Morph.AiKit/Rag/DeltaPlan.cs +49 -0
  175. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/AgentFactoryTests.cs +495 -0
  176. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/AgentSpecTests.cs +260 -0
  177. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/ConversationStoreTests.cs +405 -0
  178. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/DeltaIngestTests.cs +379 -0
  179. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalAssertionTests.cs +197 -0
  180. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalCacheMissTests.cs +139 -0
  181. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalCacheStampTests.cs +157 -0
  182. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalFailuresTests.cs +178 -0
  183. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalFixtureTests.cs +153 -0
  184. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalRefreshTests.cs +194 -0
  185. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/EvalWorkspace.cs +86 -0
  186. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/KitEvals.cs +213 -0
  187. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Evals/OfflineChatClientTests.cs +95 -0
  188. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeChatClient.cs +225 -0
  189. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeChatClientTests.cs +215 -0
  190. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeClock.cs +33 -0
  191. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeMediaProvider.cs +89 -0
  192. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeProviderClientFactory.cs +55 -0
  193. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/FakeUsageCostSink.cs +60 -0
  194. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Fakes/InMemoryMediaStore.cs +131 -0
  195. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaAccessibilityTests.cs +133 -0
  196. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaAliasIsNotAnAgentTests.cs +127 -0
  197. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaDisclosureTests.cs +216 -0
  198. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaGeneratorTests.cs +264 -0
  199. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaIdempotencyKeyTests.cs +148 -0
  200. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaJobStateTests.cs +184 -0
  201. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaReviewTests.cs +89 -0
  202. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/MediaStoreTests.cs +98 -0
  203. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/ModelRegistryTests.cs +451 -0
  204. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/Morph.AiKit.Tests.csproj +76 -0
  205. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/SkeletonSmokeTests.cs +33 -0
  206. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/TelemetryTests.cs +261 -0
  207. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/UsageCostMiddlewareTests.cs +374 -0
  208. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/.morph-eval-cache.json +12 -0
  209. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/orcamento.acme.a-resposta-estruturada/1/CF70A7CE27BBD66A/contents.data +13 -0
  210. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/orcamento.acme.a-resposta-estruturada/1/CF70A7CE27BBD66A/entry.json +7 -0
  211. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.acme.a-saudacao/1/19F631228C6E00BA/contents.data +13 -0
  212. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.acme.a-saudacao/1/19F631228C6E00BA/entry.json +7 -0
  213. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.acme.b-escalonamento/1/A24A7C9BDD8239D8/contents.data +13 -0
  214. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.acme.b-escalonamento/1/A24A7C9BDD8239D8/entry.json +7 -0
  215. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.globex.a-saudacao/1/E38CD37DF003EDB7/contents.data +13 -0
  216. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-cache/cache/triagem.globex.a-saudacao/1/E38CD37DF003EDB7/entry.json +7 -0
  217. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-datasets/orcamento/acme/a-resposta-estruturada.json +24 -0
  218. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-datasets/triagem/acme/a-saudacao.json +23 -0
  219. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-datasets/triagem/acme/b-escalonamento.json +24 -0
  220. package/framework/templates/dotnet/ai-kit/tests/Morph.AiKit.Tests/eval-datasets/triagem/globex/a-saudacao.json +23 -0
  221. package/framework/templates/feature/decisions.md +122 -122
  222. package/framework/templates/frontend/nextjs/Dockerfile.nextjs.hbs +43 -43
  223. package/framework/templates/frontend/nextjs/client-component.tsx.hbs +26 -26
  224. package/framework/templates/frontend/nextjs/env.mjs.hbs +32 -32
  225. package/framework/templates/frontend/nextjs/feature-form.tsx.hbs +56 -56
  226. package/framework/templates/frontend/nextjs/page.tsx.hbs +22 -22
  227. package/framework/templates/frontend/nextjs/tsconfig.json.hbs +26 -26
  228. package/framework/templates/frontend/nextjs/use-feature.ts.hbs +54 -54
  229. package/framework/templates/infrastructure/docker/Dockerfile.template +58 -58
  230. package/framework/templates/infrastructure/docker/dockerfile-api.dockerfile +38 -38
  231. package/framework/templates/infrastructure/docker/dockerfile-web.dockerfile +48 -48
  232. package/framework/templates/infrastructure/github/README.md +56 -56
  233. package/framework/templates/infrastructure/github/actions/docker-build-push/action.yml.hbs +45 -45
  234. package/framework/templates/infrastructure/github/actions/health-check/action.yml.hbs +27 -27
  235. package/framework/templates/infrastructure/github/workflows/docker-build-push.yml.hbs +59 -59
  236. package/framework/templates/infrastructure/github/workflows/dotnet-build.yml.hbs +39 -39
  237. package/framework/templates/integrations/asaas-client.cs +387 -387
  238. package/framework/templates/integrations/asaas-webhook.cs +351 -351
  239. package/framework/templates/meta-prompts/fusion/fusion-agent.md +76 -76
  240. package/framework/templates/meta-prompts/fusion/fusion-aggregator.md +100 -100
  241. package/framework/templates/meta-prompts/validators/pre-commit-validator.md +95 -95
  242. package/framework/templates/project/validate.js +120 -120
  243. package/framework/templates/state.template.json +17 -17
  244. package/framework/templates/ui/design-system.css +226 -226
  245. package/package.json +3 -3
  246. package/src/commands/dashboard/dashboard.js +53 -53
  247. package/src/commands/e2e/e2e.js +15 -2
  248. package/src/commands/index.js +13 -13
  249. package/src/commands/project/checkpoint.js +209 -209
  250. package/src/commands/project/doctor.js +140 -5
  251. package/src/commands/project/update.js +469 -153
  252. package/src/commands/project/worktree.js +8 -1
  253. package/src/commands/state/advance.js +24 -2
  254. package/src/commands/state/approve.js +33 -1
  255. package/src/commands/state/create.js +72 -11
  256. package/src/commands/state/finish.js +333 -21
  257. package/src/commands/state/gate-check.js +190 -6
  258. package/src/commands/state/score.js +36 -1
  259. package/src/commands/validation/verify.js +134 -25
  260. package/src/core/state/phase-state-machine.js +197 -197
  261. package/src/core/state/state-manager.js +9 -1
  262. package/src/core/templates/template-renderer.js +477 -477
  263. package/src/dashboard/app/components/DetailPanel.jsx +11 -11
  264. package/src/dashboard/app/components/FlowGraph.jsx +17 -17
  265. package/src/dashboard/app/components/SearchFilter.jsx +22 -22
  266. package/src/dashboard/app/hooks/useDetailPanel.js +15 -15
  267. package/src/dashboard/app/main.jsx +13 -13
  268. package/src/dashboard/app/pages/AgentMap.jsx +370 -370
  269. package/src/dashboard/app/pages/PhasePipeline.jsx +408 -408
  270. package/src/dashboard/app/pages/RulesMap.jsx +273 -273
  271. package/src/dashboard/app/pages/SkillsLibrary.jsx +366 -366
  272. package/src/dashboard/app/pages/Standards.jsx +332 -332
  273. package/src/dashboard/app/styles/index.css +47 -47
  274. package/src/dashboard/index.html +12 -12
  275. package/src/dashboard/package.json +24 -24
  276. package/src/dashboard/scanner/phases-scanner.js +15 -15
  277. package/src/dashboard/scanner/rubrics-scanner.js +12 -12
  278. package/src/dashboard/scanner/rules-scanner.js +37 -37
  279. package/src/dashboard/scanner/skills-scanner.js +43 -43
  280. package/src/dashboard/scanner/squads-scanner.js +13 -13
  281. package/src/dashboard/vite-plugin-morph-data.js +17 -17
  282. package/src/dashboard/vite.config.js +24 -24
  283. package/src/lib/ai/ai-checks.js +182 -0
  284. package/src/lib/ai/ai-project-scan.js +347 -0
  285. package/src/lib/ai/code-audit.js +181 -0
  286. package/src/lib/ai/comment-stripper.js +184 -0
  287. package/src/lib/ai/pin-drift.js +138 -0
  288. package/src/lib/ai/registry-audit.js +285 -0
  289. package/src/lib/detectors/design-system-detector.js +188 -188
  290. package/src/lib/detectors/index.js +217 -217
  291. package/src/lib/e2e/compose-env.js +50 -4
  292. package/src/lib/evaluator-report.js +269 -15
  293. package/src/lib/generators/design-system-generator.js +508 -508
  294. package/src/lib/generators/settings-generator.js +209 -209
  295. package/src/lib/git/default-branch.js +92 -4
  296. package/src/lib/hooks/hook-executor.js +167 -167
  297. package/src/lib/installers/effects.js +193 -0
  298. package/src/lib/installers/mcp-installer.js +719 -719
  299. package/src/lib/installers/templates-reconcile.js +3 -3
  300. package/src/lib/risk-detector.js +284 -0
  301. package/src/lib/standards/verified-against.js +276 -0
  302. package/src/lib/tasks/eval-node.js +485 -0
  303. package/src/lib/tasks/linux-runner.js +297 -0
  304. package/src/lib/tasks/task-classifier.js +30 -30
  305. package/src/lib/tasks/task-parser.js +209 -209
  306. package/src/lib/tasks/test-nodes.js +486 -0
  307. package/src/lib/tasks/test-runner.js +410 -33
  308. package/src/lib/validators/checkpoint-persistence.js +39 -39
  309. package/src/lib/validators/css/css-validator.js +340 -340
  310. package/src/lib/validators/shared/emit-validator-dispatch.js +14 -14
  311. package/src/lib/validators/shared/issue-counter.js +14 -14
  312. package/src/lib/validators/verify-runner.js +583 -28
  313. package/src/lib/worktree/docker-audit.js +287 -0
  314. package/src/lib/worktree/env-allocator.js +24 -0
  315. package/src/lib/worktree/worktree-audit.js +30 -1
  316. package/src/scripts/setup-infra.js +24 -11
  317. package/src/utils/agent-id-mapper.js +11 -11
  318. package/src/utils/agents-installer.js +18 -8
  319. package/src/utils/claude-md-injector.js +10 -5
  320. package/src/utils/claude-settings-manager.js +300 -300
  321. package/src/utils/file-copier.js +11 -4
  322. package/src/utils/hooks-installer.js +29 -26
  323. package/src/utils/skills-installer.js +36 -29
  324. package/src/utils/version-checker.js +68 -3
  325. package/framework/standards/ai-agents/prompts-in-db.md +0 -214
@@ -0,0 +1,226 @@
1
+ # LLM Runtime Defaults — timeout, retry, strict, amostragem e o pin do SDK
2
+
3
+ > **Scope:** stacks=["dotnet"]
4
+ > **Layer:** 1 (on-keyword)
5
+ > **Keywords:** llm defaults, runtime defaults, timeout llm, retry llm, strict json schema, temperature reasoning, capability por alias, network timeout, pin de sdk
6
+ > **Read by Claude in:** implement (ao configurar cliente, alias ou opções de chamada) e troubleshoot (chamada pendurada, 400 recorrente, quebra binária)
7
+
8
+ **Verified against:** Microsoft.Extensions.AI 10.9.0 + Microsoft.Agents.AI 1.20.0 + OpenAI 2.13.0 (ai-pin 2026-09-08); provado por `templates/dotnet/ai-kit/src/Morph.AiKit/Providers/ModelAlias.cs` e `.../Providers/ModelRegistry.cs` (alias, `api:`, e limite por alias com procedência obrigatória). A superfície do SDK citada aqui — `ChatOptions`, `ChatResponseFormatJson`, `ReasoningEffort`, `OpenAIClientOptions` — foi **medida por reflexão sobre as assemblies do pin** em 2026-09-08. O timeout é **provado por** `.../Agents/AgentSpecOptions.cs` e `.../Agents/AgentFactory.cs`, que o kit compila **por spec** (`TimeoutSeconds` vira um cliente de timeout no pipeline) — e **não** por alias: a allowlist de alias do registry não tem chave de timeout (medido). Os valores default do retry do `System.ClientModel` 1.15.0 são **verificação documental** — essa assembly está fora do conjunto que o probe carrega. Last-verified: 2026-09-08.
9
+
10
+ ---
11
+
12
+ ## Fronteira com o Model Registry
13
+
14
+ `ai-agents-providers-model-registry` é **Layer 0** (sempre carregado) e continua dono do **schema**:
15
+ o formato do documento, `defaultAlias`, o fallback e a tabela de providers. **Este** standard é dono
16
+ dos **valores e dos botões de runtime**: timeout, retry, strict, amostragem, esforço de raciocínio e
17
+ o pin de versão do SDK.
18
+
19
+ Sem esta fronteira escrita, o par vira **duas verdades sobre o mesmo JSON** — e a segunda verdade é
20
+ sempre a que alguém encontra primeiro.
21
+
22
+ Complemento: `ai-agents-agent-spec` é dono da **forma** do agente e da regra "nulo = não envia";
23
+ `ai-agents-cost-and-budget` é dono de `pricing`. Aqui não se repete nenhum dos três.
24
+
25
+ ---
26
+
27
+ ## Retry herdado
28
+
29
+ **Não escreva um loop de retry sobre chamada de LLM.** A pilha do `System.ClientModel` — a base dos
30
+ clientes gerados da OpenAI — já traz uma política de retry, e ela é aplicada por padrão.
31
+
32
+ O que a assembly `System.ClientModel` 1.15.0 (a restaurada junto com o pin) carrega nos metadados,
33
+ **medido por leitura de literal em 2026-09-08**: `ClientRetryPolicy`, `ClientPipelineOptions`,
34
+ `RetryPolicy`, `MaxRetries`, `DefaultMaxRetries`, `DefaultInitialDelay`, `ShouldRetry`,
35
+ `GetNextDelay`. Isto prova que os pontos de extensão existem e como se chamam.
36
+
37
+ **Verificação documental** (fonte primária: o fonte de `ClientRetryPolicy` em
38
+ `Azure/azure-sdk-for-net`, lido em 2026-09-08), e por isso escrita como valor a **conferir** antes de
39
+ depender dela: 3 tentativas de retry, atraso inicial de 0,8 s, backoff exponencial na forma
40
+ `(1 << (tryCount - 1)) * initialDelay`, e o cabeçalho de espera do servidor respeitado quando ele
41
+ pede mais tempo do que o backoff calculado.
42
+
43
+ **A regra:** herde. Se precisar de outro número, **substitua a política** (`RetryPolicy` nas opções
44
+ do cliente), não empilhe um `for` por cima. Duas camadas de retry multiplicam: 3 × 3 = 9 chamadas
45
+ pagas para um incidente que o operador vê como "uma".
46
+
47
+ Prática de campo alinhada, com a razão escrita no próprio código: *"não adicionamos loop próprio"*.
48
+
49
+ ---
50
+
51
+ ## Timeout explícito
52
+
53
+ **Retry sobre uma chamada que nunca expira é o pior dos dois mundos.** A política tenta de novo o
54
+ que ainda não desistiu, e o incidente aparece como latência infinita em vez de erro.
55
+
56
+ Dois fatos medidos por reflexão sobre as assemblies do pin, em 2026-09-08:
57
+
58
+ 1. **`Microsoft.Extensions.AI.ChatOptions` não tem propriedade de timeout.** As 20 propriedades
59
+ declaradas são de conteúdo da chamada (`Temperature`, `TopP`, `TopK`, `MaxOutputTokens`,
60
+ `ResponseFormat`, `Tools`, `ToolMode`, `Reasoning`, `Seed`, `StopSequences`, `Instructions`,
61
+ `ModelId`, `ConversationId`, `AdditionalProperties`, …). A abstração **não sabe expressar**
62
+ timeout — logo, ele não é um botão por chamada nesse nível.
63
+ 2. **`OpenAI.OpenAIClientOptions` (OpenAI 2.13.0) declara apenas** `Endpoint`, `OrganizationId`,
64
+ `ProjectId` e `UserAgentApplicationId`. O botão de timeout **não é dele**: ele vem da base,
65
+ `System.ClientModel.Primitives.ClientPipelineOptions`, cuja assembly carrega os nomes
66
+ `NetworkTimeout` e `get_NetworkTimeout` (medido por literal na mesma data). A declaração está
67
+ fora do conjunto de assemblies que o probe carrega, então este ponto é **documental**.
68
+
69
+ **A regra, em três partes:**
70
+
71
+ - **Configure o timeout explicitamente**, e escolha conscientemente a camada. O exemplar do kit o faz **por spec de agente** (`AgentSpecOptions.TimeoutSeconds` → um cliente de timeout no pipeline), porque a allowlist de alias do registry **não tem** chave de timeout — medido. Por alias exige abrir essa allowlist, o que é mudança de `.cs`. Alias
72
+ de raciocínio pesado e alias de resposta curta não têm o mesmo tempo aceitável.
73
+ - **`CancellationToken` de turno não é timeout de chamada.** Ele cancela quando *alguém* desiste
74
+ (o usuário fechou a aba, o job foi abortado). Uma chamada pendurada sem ninguém para desistir
75
+ fica pendurada.
76
+ - **Timeout curto sem retry é fragilidade; retry sem timeout é vazamento.** Os dois andam juntos.
77
+
78
+ Medições que motivam a regra: um projeto do acervo tem **apenas** o `CancellationToken` do turno,
79
+ sem nenhum timeout de chamada. Outro tem uma biblioteca de resiliência declarada no `.csproj`
80
+ **sem aplicá-la à camada de IA**, e nenhum timeout de `HttpClient` nem handler de resiliência
81
+ padrão registrado.
82
+
83
+ > **Correção explícita de premissa.** A formulação "timeout é herdado do SDK, como o retry" é
84
+ > **falsa** nas duas pontas medidas: o retry é herdado, o timeout precisa ser **decidido**. Herdar
85
+ > o que não existe é como se descobre que uma chamada roda até o processo morrer.
86
+
87
+ ---
88
+
89
+ ## Strict JSON schema por alias
90
+
91
+ O identificador **`StrictJsonSchema` não existe**. Medição, 2026-09-08: uma varredura por reflexão
92
+ sobre as **14 assemblies** dos pacotes do pin e das pontes (`Microsoft.Agents.AI` e derivados,
93
+ `Microsoft.Extensions.AI` e derivados, `OpenAI`, `Google.GenAI`, `ModelContextProtocol` e derivados,
94
+ `Microsoft.Extensions.VectorData.Abstractions`) devolve **zero** tipos exportados cujo nome contenha
95
+ `Strict`.
96
+
97
+ E `Microsoft.Extensions.AI.ChatResponseFormatJson` declara exatamente três propriedades — `Schema`,
98
+ `SchemaDescription`, `SchemaName` — e **nenhum campo `strict`**, também medido por reflexão. A
99
+ abstração não sabe expressar strict.
100
+
101
+ O mecanismo real é **uma chave em `ChatOptions.AdditionalProperties`**, lida pela ponte do provider,
102
+ que transforma o schema antes de enviá-lo (proibir propriedades adicionais, converter schemas
103
+ booleanos). Isso significa três coisas para o desenho:
104
+
105
+ - **Strict é decisão por chamada / por alias**, porque é onde `ChatOptions` vive.
106
+ - **Suporte a strict é capacidade do modelo**, e o registry já sabe o provider e o modelo de cada
107
+ alias. Logo o lugar do "este alias suporta strict" é o **alias**.
108
+ - **Nunca uma flag global de processo.**
109
+
110
+ ### O anti-padrão, com o nome real do campo
111
+
112
+ Medido em produção no acervo: um par `StrictJsonSchemaSupported` (propriedade de configuração) +
113
+ `volatile bool _strictUnsupported` (campo estático de processo). Ao receber um `400` de qualquer
114
+ chamada, o campo é ligado e **todas as chamadas seguintes do processo** passam a ser enviadas sem
115
+ strict. A frase do próprio diagnóstico do projeto: *"um 400 em qualquer ponto degrada todas as
116
+ chamadas seguintes"*.
117
+
118
+ O efeito prático: um modelo local em desenvolvimento, que legitimamente não suporta strict, rebaixa
119
+ as chamadas de **produção** do mesmo processo. Capacidade é do alias; degradação global é um bug
120
+ disfarçado de resiliência.
121
+
122
+ O kit compila a forma correta dessa ideia: limites conhecidos de um alias vivem num record de
123
+ `Constraints` **por alias**, e um limite **sem procedência escrita é recusado na carga do
124
+ registry** — para que ninguém consiga gravar um "todo mundo sabe que" sem dizer de onde tirou.
125
+
126
+ ---
127
+
128
+ ## Temperature e reasoning
129
+
130
+ **Modelo de raciocínio e amostragem não se misturam.** A regra prática: `Temperature` só faz sentido
131
+ em modelo sem raciocínio; em modelo de raciocínio o botão é o **esforço**.
132
+
133
+ O que está **medido por reflexão** sobre `Microsoft.Extensions.AI.Abstractions` 10.9.0, em
134
+ 2026-09-08:
135
+
136
+ - `ChatOptions.Temperature` (`float?`) e `ChatOptions.Reasoning` (`ReasoningOptions`) são
137
+ propriedades **distintas** e independentes.
138
+ - `ReasoningOptions` declara `Effort` e `Output`.
139
+ - `ReasoningEffort` é um **enum de primeira classe** com exatamente cinco valores:
140
+ `None = 0`, `Low = 1`, `Medium = 2`, `High = 3`, `ExtraHigh = 4`.
141
+
142
+ Esforço de raciocínio, portanto, é **tipado** — não é string, e não precisa de convenção de projeto.
143
+
144
+ A **medição de campo** que sustenta o limite prático (dois modelos de raciocínio que rejeitam
145
+ `Temperature != 1` quando há tools na chamada) é de `ai-agents-providers-model-registry` — Layer 0,
146
+ sempre carregado, e dono dela desde a re-verificação anterior. **Não é repetida aqui**: uma segunda
147
+ cópia da mesma medição é a segunda verdade que a seção de fronteira acima existe para evitar. O que
148
+ este standard acrescenta é onde o limite mora e o que ele governa.
149
+
150
+ **Contra-evidência, e ela é instrutiva:** outro projeto do acervo **não configura parâmetro de
151
+ amostragem nenhum** e roda no default do SDK. Não configurar é uma escolha válida, e mais honesta
152
+ que configurar errado. A regra final é: **configure quando você mediu que precisa; caso contrário,
153
+ não envie** (`ai-agents-agent-spec`, "nulo = não envia").
154
+
155
+ Onde o limite mora: no **alias**, como `Constraints` com procedência — a mesma forma que o kit
156
+ compila para `ToolCallingRequiresReasoningEffortNone` e `TemperatureUnsupported`. Um limite por
157
+ alias é verificável antes da chamada; um limite espalhado em `if`s só é verificável depois do 400.
158
+
159
+ ---
160
+
161
+ ## Pin de SDK e compatibilidade binária
162
+
163
+ **Faixa flutuante em SDK de IA custa dinheiro.** Não é uma preferência de estilo: é um incidente
164
+ medido.
165
+
166
+ O caso, do acervo: um projeto referenciava o SDK da OpenAI numa faixa `2.*`. O NuGet resolveu para
167
+ uma versão menor mais nova, um membro de conteúdo de resposta **mudou de assinatura**, e a chamada
168
+ estourou `MissingMethodException` **depois de a requisição já ter sido paga** — o dinheiro saiu, a
169
+ resposta não chegou ao domínio. A correção foi pinar a versão exata, com oito linhas de comentário
170
+ explicando por quê.
171
+
172
+ **As três regras:**
173
+
174
+ 1. **Pin exato** (`[2.13.0]`, não `2.*`) para todo pacote de IA. Neste framework a fonte única é
175
+ `framework/ai-pin.json`, e nenhum standard escreve versão à mão.
176
+ 2. **A faixa e o pacote de ponte andam juntos.** `Microsoft.Extensions.AI.OpenAI` referencia uma
177
+ versão do `OpenAI`; carregar outra em runtime é uma quebra binária esperando um caminho de código
178
+ pouco exercitado.
179
+ 3. **Teste de compatibilidade binária como rede de segurança** — comparar a versão do assembly
180
+ carregado com a que a ponte referencia, e conferir a **assinatura** do membro que já quebrou uma
181
+ vez. A técnica está em `ai-agents-testing-ai`.
182
+
183
+ ---
184
+
185
+ ## Anti-patterns
186
+
187
+ | Anti-pattern | Por quê é problema | Solução |
188
+ |---|---|---|
189
+ | Loop de retry próprio sobre a chamada de LLM | Multiplica com o retry do SDK: 3 × 3 = 9 chamadas pagas por incidente | Herde; para outro número, substitua a política |
190
+ | Chamada de LLM sem timeout | Retry sobre o que nunca expira; o incidente vira latência infinita | Timeout explícito — por spec de agente (o exemplar do kit) ou por alias, se a allowlist foi aberta |
191
+ | `CancellationToken` de turno usado como timeout | Só cancela quando alguém desiste; ninguém desiste de um job noturno | Timeout explícito, além do token |
192
+ | Flag global de processo para strict | Um 400 em dev rebaixa produção no mesmo processo | Capacidade por alias, em `Constraints` com procedência |
193
+ | `Temperature` em modelo de raciocínio | Erro do provider, ou pior: silenciosamente ignorado | Esforço tipado (`ReasoningEffort`) para raciocínio; amostragem só sem raciocínio |
194
+ | Parâmetro de amostragem configurado "por garantia" | Envia valor que ninguém mediu, e some no default do provider | Nulo = não envia |
195
+ | Faixa flutuante (`2.*`) em pacote de IA | Quebra binária depois da chamada paga | Pin exato, a partir de `framework/ai-pin.json` |
196
+ | Limite de alias escrito como regra universal em C# | Vira folclore sem procedência, e ninguém sabe revogá-lo | Campo do alias, com procedência obrigatória |
197
+
198
+ ---
199
+
200
+ ## Checklist (verifiable by morph-eval)
201
+
202
+ - [ ] Nenhum loop de retry escrito à mão em volta de uma chamada de LLM
203
+ - [ ] Há timeout explícito (por spec de agente, como o exemplar do kit, ou por alias se a allowlist foi aberta), e ele **não** é o `CancellationToken` do turno
204
+ - [ ] Nenhuma flag estática de processo governa strict ou qualquer outra capacidade
205
+ - [ ] Capacidade e limite são campos do **alias**, com procedência escrita
206
+ - [ ] Nenhuma ocorrência de um tipo chamado `StrictJsonSchema` (ele não existe em nenhum pacote do pin)
207
+ - [ ] Esforço de raciocínio usa o enum `ReasoningEffort`, não string
208
+ - [ ] `Temperature` não é enviada junto com esforço de raciocínio
209
+ - [ ] Todo pacote de IA está pinado em versão exata, derivada de `framework/ai-pin.json`
210
+ - [ ] Existe um teste de compatibilidade binária cobrindo o par SDK × ponte
211
+
212
+ ---
213
+
214
+ ## References
215
+
216
+ - `ai-agents-providers-model-registry` — Layer 0: o **schema** do documento, `defaultAlias`, fallback
217
+ e a tabela de providers. Este standard não repete nada disso
218
+ - `ai-agents-agent-spec` — a forma do agente e a regra "nulo = não envia"
219
+ - `ai-agents-cost-and-budget` — `pricing` por alias, cálculo e teto de gasto
220
+ - `ai-agents-testing-ai` — o teste de compatibilidade binária, e como exercitar opções sem rede
221
+ - `ai-agents-structured-output` — o schema da saída, cujo strict este standard governa
222
+ - `framework/ai-pin.json` — a fonte única das versões; nenhuma versão é digitada num standard
223
+
224
+ ---
225
+
226
+ *MORPH-SPEC by Polymorphism Tech — ai-agents/llm-runtime-defaults.md v1.0 (2026-09-08)*
@@ -2,10 +2,10 @@
2
2
 
3
3
  > **Scope:** stacks=["dotnet"]
4
4
  > **Layer:** 2 (on-keyword)
5
- > **Keywords:** mcp server, expose mcp, build mcp server, mcp host, publish tools, McpServerTool, AddMcpServer
5
+ > **Keywords:** mcp server, expose mcp, build mcp server, mcp host, publish tools, McpServerTool, AddMcpServer, request filters, stateless, spec 2026-07-28
6
6
  > **Read by Claude in:** implement (quando um projeto expõe capacidades como MCP server para consumo externo)
7
7
 
8
- **Verified against:** MAF 1.0 GA + ModelContextProtocol C# SDK server-side (`[McpServerToolType]`/`[McpServerTool]`, `WithStdioServerTransport`/`WithHttpTransport`, `ModelContextProtocol.AspNetCore`). Last-verified: 2026-05-19.
8
+ **Verified against:** ModelContextProtocol 2.2.0 + ModelContextProtocol.AspNetCore 2.2.0 (ai-pin 2026-09-08; o `.AspNetCore` não está no pin — versão apurada no nuget.org em 2026-09-08) + revisão de spec MCP **2026-07-28** (modelcontextprotocol.io/specification/versioning, lido 2026-09-08). **Verificação documental — o ai-kit não exercita MCP**, e por isso este standard NÃO carimba `provado por`. Os nomes de tipo, os defaults e os avisos de obsolescência abaixo foram **medidos por reflexão sobre as assemblies 2.2.0** em 2026-09-08. Last-verified: 2026-09-08.
9
9
 
10
10
  ---
11
11
 
@@ -30,26 +30,63 @@ Crie um MCP server quando você quer **expor capacidades do projeto** de forma p
30
30
 
31
31
  ## A API
32
32
 
33
+ ### Não existe "MCP 2.0" como revisão de especificação
34
+
35
+ A confusão vale ser desfeita antes de qualquer código, porque ela muda o que se procura na documentação:
36
+
37
+ | Coisa | Como é versionada | Valor corrente (2026-09-08) |
38
+ |---|---|---|
39
+ | **A especificação MCP** | por **data** | revisão **`2026-07-28`** (sucede `2025-11-25`) |
40
+ | **O SDK C# `ModelContextProtocol`** | SemVer | **2.2.0**, publicado 2026-08-13 |
41
+
42
+ "MCP 2.0" é a **major do SDK**, nunca uma revisão de spec. Fonte: modelcontextprotocol.io/specification/versioning e o changelog da revisão `2026-07-28`, lidos em 2026-09-08.
43
+
44
+ ### O que a revisão `2026-07-28` mudou para quem escreve servidor
45
+
46
+ - **Sessões removidas** — o cabeçalho `Mcp-Session-Id` deixou de existir (**SEP-2567**).
47
+ - **`initialize` / `notifications/initialized` removidos** — versão e capacidades viajam em `_meta` **por request** (**SEP-2575**).
48
+ - Novo RPC **`server/discover`**.
49
+ - **`ping`, `logging/setLevel` e `notifications/roots/list_changed` removidos.**
50
+ - **Roots, Sampling e Logging deprecados** (**SEP-2577**).
51
+ - **Tasks** (long-running) saíram do core para a extensão `io.modelcontextprotocol/tasks`.
52
+ - **Elicitation/sampling substituídos por MRTR** — `InputRequiredResult` + `InputRequest.ForElicitation(...)` (**SEP-2322**).
53
+ - **Resultado cacheável** — `ICacheableResult` com `TimeToLive` e `CacheScope` (**SEP-2549**).
54
+ - **HTTP+SSE formalmente Deprecated** (Streamable HTTP é o transporte).
55
+
56
+ > **Duas dessas afirmações não dependem do changelog: elas estão gravadas na assembly.** Medido em `ModelContextProtocol.AspNetCore` 2.2.0 e `ModelContextProtocol.Core` 2.2.0, no texto do `[Obsolete]` de cada membro:
57
+ > - `HttpServerTransportOptions.EventStreamStore`/`IdleTimeout`/`MaxIdleSessionCount`/`PerSessionExecutionContext`/`SessionMigrationHandler` — *"Stateful Streamable HTTP mode is a back-compat-only escape hatch for 2025-11-25 protocol revision clients and earlier. Set `HttpServerTransportOptions.SessionMode = HttpServerSessionMode.Stateless` (**the default as of the 2026-07-28 protocol revision**) for new code. See SEP-2567."*
58
+ > - `McpServerOptions.MaxSamplingOutputTokens` — *"The Sampling feature is deprecated as of specification version 2026-07-28 … See SEP-2577."*
59
+ > - `HttpServerTransportOptions.EnableLegacySse` — obsoleto: *"…Use Streamable HTTP instead."*
60
+
61
+ ### A API C# de servidor NÃO mudou de nome
62
+
63
+ `AddMcpServer()`, `WithStdioServerTransport()`, `WithHttpTransport(...)`, `WithToolsFromAssembly()`, `WithTools([...])`, `[McpServerToolType]`, `[McpServerTool]`, `McpServerTool.Create(...)` e `app.MapMcp()` continuam iguais. **O que mudou é o default**, não a grafia.
64
+
33
65
  **Packages:**
34
66
 
35
67
  ```xml
36
- <!-- SDK cliente+servidor do protocolo MCP -->
37
- <PackageReference Include="ModelContextProtocol" Version="0.1.*" />
68
+ <!-- SDK cliente+servidor do protocolo MCP — no ai-pin.json -->
69
+ <PackageReference Include="ModelContextProtocol" Version="2.2.0" />
38
70
 
39
- <!-- Pacote base MAF (para AsAIAgent, AsAIFunction) -->
40
- <PackageReference Include="Microsoft.Agents.AI" Version="1.0.*" />
71
+ <!-- Pacote base MAF (para AsAIAgent, AsAIFunction) — no ai-pin.json -->
72
+ <PackageReference Include="Microsoft.Agents.AI" Version="1.20.0" />
41
73
 
42
- <!-- Apenas se o transporte for HTTP (server-side) -->
43
- <PackageReference Include="ModelContextProtocol.AspNetCore" Version="0.1.*" />
74
+ <!-- Apenas se o transporte for HTTP (server-side).
75
+ NÃO está no ai-pin.json; versão apurada no nuget.org em 2026-09-08. -->
76
+ <PackageReference Include="ModelContextProtocol.AspNetCore" Version="2.2.0" />
44
77
  ```
45
78
 
46
- > `ModelContextProtocol` versão 0.1.* (preview) — GA previsto. Verifique versão corrente no NuGet antes de travar.
79
+ ### Stateless é o DEFAULT, não uma escolha
80
+
81
+ Medido em `ModelContextProtocol.AspNetCore` 2.2.0, instanciando `HttpServerTransportOptions` e lendo os valores iniciais: **`SessionMode == HttpServerSessionMode.Stateless`** e `Stateless == true`. Os valores de `HttpServerSessionMode` são `Stateless` (0), `Stateful` (1) e `StatefulForInitializeClients` (2).
82
+
83
+ Escrever `o.Stateless = true` hoje é redundante; escrever `o.SessionMode = HttpServerSessionMode.Stateful` é **optar por um escape hatch de compatibilidade** com clientes da revisão `2025-11-25` e anteriores — e é isso que a mensagem de obsolescência diz. A versão anterior deste standard apresentava stateless como uma decisão de escala do autor; o protocolo já a tomou.
47
84
 
48
85
  **Dois jeitos de declarar tools:**
49
86
 
50
87
  | Padrão | Quando usar |
51
88
  |--------|-------------|
52
- | Atributos `[McpServerToolType]` + `[McpServerTool]` | Tools são métodos estáticos do projeto — padrão canônico do SDK. Descoberta automática via `WithToolsFromAssembly()`. |
89
+ | Atributos `[McpServerToolType]` + `[McpServerTool]` | Tools são métodos do projeto — padrão canônico do SDK. Descoberta automática via `WithToolsFromAssembly()`. |
53
90
  | `McpServerTool.Create(...)` | Embrulhar um agente MAF (`agent.AsAIFunction()`) ou um `AIFunction` construído em runtime como tool. |
54
91
 
55
92
  **Padrão de servidor (stdio):**
@@ -63,7 +100,7 @@ Tools ([McpServerTool] ou McpServerTool.Create)
63
100
  → Host.Build().RunAsync() // sobe o servidor
64
101
  ```
65
102
 
66
- **Transport stdio** é o padrão para servidores locais (subprocessos, Claude Code tools). **HTTP server-side** usa o pacote `ModelContextProtocol.AspNetCore`: troque `WithStdioServerTransport()` por `WithHttpTransport(o => o.Stateless = true)` e exponha o endpoint com `app.MapMcp()` num `WebApplication`.
103
+ **Transport stdio** é o padrão para servidores locais (subprocessos, Claude Code tools). **HTTP server-side** usa o pacote `ModelContextProtocol.AspNetCore`: troque `WithStdioServerTransport()` por `WithHttpTransport()` e exponha o endpoint com `app.MapMcp()` num `WebApplication`.
67
104
 
68
105
  ---
69
106
 
@@ -148,7 +185,7 @@ var builder = WebApplication.CreateBuilder(args);
148
185
 
149
186
  builder.Services
150
187
  .AddMcpServer()
151
- .WithHttpTransport(options => options.Stateless = true) // stateless: escalável
188
+ .WithHttpTransport() // SessionMode = Stateless já é o default (medido em 2.2.0)
152
189
  .WithToolsFromAssembly();
153
190
 
154
191
  var app = builder.Build();
@@ -157,9 +194,64 @@ app.MapMcp(); // expõe o endpoint MCP (Streamable HTTP)
157
194
  app.Run();
158
195
  ```
159
196
 
160
- > `Stateless = true` é recomendado para servidores que não precisam de requests server-to-client
161
- > (sampling/elicitation) — escala melhor e dispensa gestão de sessão. Para HTTP em produção,
162
- > proteja `MapMcp()` com autenticação — ver seção Segurança.
197
+ > Não escreva `options.Stateless = true`: é redundante desde a revisão `2026-07-28`. Se você
198
+ > precisar de `SessionMode = HttpServerSessionMode.Stateful`, saiba que está optando por um
199
+ > **escape hatch de compatibilidade** com clientes antigos — o próprio SDK diz isso no
200
+ > `[Obsolete]`. Para HTTP em produção, proteja `MapMcp()` com autenticação — ver seção Segurança.
201
+
202
+ ---
203
+
204
+ ## Filtros de request — listar não é poder chamar
205
+
206
+ Este é o mecanismo que permite **um servidor MCP servir vários tenants** sem um processo por tenant. A API foi medida em `ModelContextProtocol` 2.2.0 (`McpRequestFilterBuilderExtensions`) e `ModelContextProtocol.AspNetCore` 2.2.0 (`HttpMcpServerBuilderExtensions`).
207
+
208
+ ```csharp
209
+ services.AddMcpServer()
210
+ .WithListToolsHandler(async (context, ct) => new ListToolsResult { Tools = GetTools() })
211
+ .WithRequestFilters(f =>
212
+ {
213
+ // (1) Poda a LISTAGEM — o cliente não vê a tool.
214
+ f.AddListToolsFilter(next => async (context, ct) =>
215
+ {
216
+ var result = await next(context, ct);
217
+ result.Tools = [.. result.Tools.Where(t => AllowedFor(context.User, t))];
218
+ return result;
219
+ });
220
+
221
+ // (2) Bloqueia a CHAMADA — sem isto, quem souber o nome chama assim mesmo.
222
+ f.AddCallToolFilter(next => async (context, ct) =>
223
+ {
224
+ if (!AllowedFor(context.User, context.Params!.Name)) // ClaimsPrincipal por request
225
+ throw new McpException("tool not available for this principal");
226
+ return await next(context, ct);
227
+ });
228
+ })
229
+ .AddAuthorizationFilters(); // a ORDEM importa — ver abaixo
230
+ ```
231
+
232
+ **Duas regras que este standard existe para gravar:**
233
+
234
+ 1. **São DOIS filtros, não um.** `AddListToolsFilter` **esconde** a tool; só `AddCallToolFilter` **impede chamá-la**. Um cliente que já conhece o nome — porque leu a lista antes, porque outro tenant tem a mesma tool, ou porque adivinhou — chama direto. Poda de listagem é ergonomia, não autorização.
235
+ 2. **Cliente já conectado não relê a lista até reconectar.** Revogar acesso podando a listagem não revoga nada para quem já está dentro. A revogação real é o filtro de `CallTool`.
236
+
237
+ **A ordem do encadeamento é semântica:** um filtro registrado **antes** de `AddAuthorizationFilters()` roda com a lista **completa** — vê todas as tools, inclusive as que a autorização removeria. Se a intenção é filtrar o que já passou pela autorização, registre depois.
238
+
239
+ Filtros disponíveis (medidos): `AddListToolsFilter`, `AddCallToolFilter`, `AddListPromptsFilter`, `AddGetPromptFilter`, `AddListResourcesFilter`, `AddReadResourceFilter`, `AddListResourceTemplatesFilter`, `AddCompleteFilter`, `AddSubscribeToResourcesFilter`, `AddUnsubscribeFromResourcesFilter`, `AddSetLoggingLevelFilter`.
240
+
241
+ ### Identidade por request
242
+
243
+ - **`context.User`** é o `ClaimsPrincipal` do request, disponível dentro do filtro.
244
+ - Uma tool pode receber por **injeção de parâmetro**: `ClaimsPrincipal`, `RequestContext<T>`, `McpServer` e `IProgress<T>`. O escopo de DI é **por request** — `McpServerOptions.ScopeRequests` tem default **`true`** (medido). `[FromKeyedServices]` funciona.
245
+ - **`HttpServerTransportOptions.ConfigureSessionOptions`** permite montar o `ToolCollection` a partir do `HttpContext.User` — poda no nascimento da sessão, complementar (não substituta) ao filtro de `CallTool`.
246
+
247
+ ### Argumento de tool é input NÃO confiável
248
+
249
+ O que chega nos argumentos foi escrito por um modelo, a partir de texto que um humano digitou. Trate como entrada hostil:
250
+
251
+ - **Allow-list** de valores onde houver conjunto finito; nunca `switch` com `default:` permissivo.
252
+ - **Limite de tamanho** em toda string antes de tocar I/O.
253
+ - **Query parametrizada**, sempre — nunca concatenação com o argumento.
254
+ - **Id de tenant vem da closure ou da credencial, NUNCA do modelo.** Uma tool que aceita `tenantId` como parâmetro é uma tool que qualquer prompt injection reaponta para outro cliente.
163
255
 
164
256
  **Registrar no Claude Code (`settings.json` do projeto consumidor):**
165
257
 
@@ -218,6 +310,10 @@ prefira o tipo de instância resolvido por DI a métodos estáticos com estado g
218
310
  | Expor tools sem validação de input | Agentes externos (ou alucinações de LLM) podem enviar dados malformados | Validar todos os parâmetros antes de qualquer I/O |
219
311
  | Tools sem escopo definido — expor tudo "por conveniência" | Superfície de ataque ampla; dificulta manutenção | Expor apenas o necessário; revisar a lista a cada release |
220
312
  | HTTP transport sem autenticação | Qualquer processo na rede pode invocar as tools | Bearer token / API key obrigatório em HTTP; stdio é suficiente para uso local |
313
+ | **Podar só a listagem e chamar isso de autorização** | `ListTools` filtrado esconde a tool; quem sabe o nome chama assim mesmo, e cliente conectado não relê a lista | `AddListToolsFilter` **e** `AddCallToolFilter` |
314
+ | **`tenantId` como parâmetro de tool** | O argumento é escrito pelo modelo: prompt injection reaponta para outro cliente | Tenant vem da closure ou de `context.User` |
315
+ | Escrever `options.Stateless = true` "para escalar" | Redundante desde a revisão `2026-07-28`; sugere que há uma decisão a tomar onde não há | `WithHttpTransport()` sem argumento |
316
+ | Contar com `initialize`, `Mcp-Session-Id`, `ping` ou `logging/setLevel` | Removidos na revisão `2026-07-28` | Versão/capacidades em `_meta` por request; `server/discover` |
221
317
  | Subir o MCP server no mesmo processo da aplicação principal | Acoplamento; falha no servidor MCP afeta a app | Projeto separado (`MyProject.McpServer`) com entrypoint próprio |
222
318
 
223
319
  ---
@@ -226,13 +322,16 @@ prefira o tipo de instância resolvido por DI a métodos estáticos com estado g
226
322
 
227
323
  - [ ] `ModelContextProtocol` e `Microsoft.Agents.AI` no `.csproj`; `ModelContextProtocol.AspNetCore` apenas se HTTP
228
324
  - [ ] Tools declaradas via `[McpServerToolType]` + `[McpServerTool]` (estáticas) ou `McpServerTool.Create(...)` (agente MAF / runtime)
229
- - [ ] `AddMcpServer()` com `WithStdioServerTransport()` (stdio) ou `WithHttpTransport(o => o.Stateless = true)` (HTTP)
325
+ - [ ] `AddMcpServer()` com `WithStdioServerTransport()` (stdio) ou `WithHttpTransport()` (HTTP) — sem reafirmar o default `Stateless`
230
326
  - [ ] `WithToolsFromAssembly()` para tools por atributo, ou `WithTools([...])` para tools de runtime
231
327
  - [ ] Entrypoint: `await builder.Build().RunAsync()` (stdio) ou `app.MapMcp(); app.Run()` (HTTP)
232
328
  - [ ] Agente criado via `_modelRegistry.GetChatClient("alias").AsAIAgent(...)` — provider-agnostic
233
329
  - [ ] Validação de input em todas as tools antes de executar lógica de negócio
234
330
  - [ ] Escopo mínimo: apenas tools necessárias para o consumidor externo
235
331
  - [ ] HTTP transport (se usado) protegido por autenticação
332
+ - [ ] Multi-tenant: existe `AddCallToolFilter`, e não apenas `AddListToolsFilter`
333
+ - [ ] Nenhuma tool recebe id de tenant como parâmetro
334
+ - [ ] Nenhum `PackageReference` com faixa flutuante; pacote fora do pin com data de apuração
236
335
  - [ ] Nenhum `Guid.NewGuid()` — usar `Guid.CreateVersion7()` se IDs são necessários
237
336
 
238
337
  ---
@@ -242,9 +341,11 @@ prefira o tipo de instância resolvido por DI a métodos estáticos com estado g
242
341
  - `ai-agents-setup` — pacotes base MAF, DI, quick start
243
342
  - `ai-agents-mcp-tools` — consumir MCP servers externos em um agente MAF
244
343
  - `ai-agents-production` — middleware pipeline, `ResilientToolMiddleware`, segurança
245
- - [ModelContextProtocol C# SDK](https://github.com/modelcontextprotocol/csharp-sdk)
344
+ - [ModelContextProtocol C# SDK](https://github.com/modelcontextprotocol/csharp-sdk) — `docs/concepts/filters.md`, `docs/concepts/identity/identity.md` (lidos 2026-09-08)
345
+ - [MCP — versionamento da especificação](https://modelcontextprotocol.io/specification/versioning) e o changelog da revisão `2026-07-28` (lidos 2026-09-08)
346
+ - [NuGet — ModelContextProtocol 2.2.0](https://www.nuget.org/packages/ModelContextProtocol/2.2.0) (publicado 2026-08-13)
246
347
  - [Expose Agent as MCP Server — MAF docs](https://learn.microsoft.com/en-us/agent-framework/agents/tools/local-mcp-tools)
247
348
 
248
349
  ---
249
350
 
250
- *MORPH-SPEC by Polymorphism Tech — ai-agents/mcp-server.md v1.0 (2026-05-19)*
351
+ *MORPH-SPEC by Polymorphism Tech — ai-agents/mcp-server.md v2.0 (2026-09-08)*