diff --git a/.planning/phases/19.1-chat-satellites/19.1-01-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-01-PLAN.md index 8c211393..e60b861d 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-01-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-01-PLAN.md @@ -49,6 +49,7 @@ estimate: raw_tokens: 200000 tasks: 3 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand inside this plan. must_haves: truths: - "D-01: module git.golem15.com/golem15/sm-userfriends-plugin, package userfriends, plugin ID golem15.userfriends, Requires golem15.user only; frozen PHP userfriends 182b514." diff --git a/.planning/phases/19.1-chat-satellites/19.1-02-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-02-PLAN.md index 62da8234..c14478f8 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-02-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-02-PLAN.md @@ -3,7 +3,9 @@ phase: 19.1-chat-satellites plan: 02 type: execute wave: 2 +# Scheduler grouping only: D-17 Render/Purify is an external summercms.go /msd-quick gate (CONTEXT deferred; not a 19.1 plan id). depends_on: [] +# Empty on purpose: no 19.1 plan predecessor and no files_modified overlap with 19.1-01. D-17 is asserted on Task 1 verify and the tracer precondition. files_modified: - .planning/notes/2026-10-18-bluemonday-forum-policy.md - ../sm-forum-plugin/.gitignore @@ -39,13 +41,14 @@ files_modified: - ../sm-forum-plugin/harness_test.go - ../sm-forum-plugin/fixture_plugin_test.go - ../sm-forum-plugin/http_tracer_test.go -autonomous: true +autonomous: false requirements: [SC-19.1-1, D-01, D-02, D-03, D-04, D-05, D-08, D-16, D-17, D-18] estimate: tokens: 200000 raw_tokens: 200000 - tasks: 3 + tasks: 4 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand. The fourth task is the identifier checkpoint, not a scope split. must_haves: truths: - "D-17: forum execution starts only after a summercms.go module exports Render(markdown) and Purify(html); sm-forum-plugin go.mod never requires bluemonday or goldmark." @@ -174,15 +177,45 @@ Then assert D-17: a summercms.go package exports Render and Purify (grep modules The forum-policy note exists and D-17 Render/Purify are importable. + + Task 2: Confirm D-02 forum baseline id and D-05 prefix before the new repo exists + .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md (D-02, D-05), .planning/phases/19.1-chat-satellites/19.1-01-PLAN.md (Task 1 remote reply) + Print a short identifier sheet, then stop. Do not create ../sm-forum-plugin. The sheet lists: module git.golem15.com/golem15/sm-forum-plugin, package forum, PluginID golem15.forum, migration id 202610180001_create_golem15_forum_baseline, published prefix /_forum/api/v1. Remote policy follows the plan 01 Task 1 reply (tea-create only on proceed-and-push). D-17 Render/Purify remains the external gate already asserted in Task 1. + Lock D-02 baseline id 202610180001_create_golem15_forum_baseline and D-05 prefix /_forum/api/v1, then implement? + These names land in every adopting app's database and in published clients. Changing the migration id or prefix after an app migrates needs a new migration and a client change. + + + + + Reply proceed or abort. + + test -f .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && grep -q "D-05" .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && echo forum-ids-ready + non-zero exit or "forum-ids-ready" absent + + + - SUMMARY records the reply verbatim. + - After abort, ../sm-forum-plugin does not exist. + + The human confirmed the forum baseline id and published prefix before any forum repo file was written. + + - Task 2: End-to-end forum post — category, thread, GFM table, no script element + Task 3: End-to-end forum post — category, thread, GFM table, no script element D-02 forum baseline id and D-05 /_forum/api/v1 become the shared contract. - D-17 exports Render and Purify (Task 1 printed d17-ready). ../sm-forum-plugin does not already exist as a foreign module. + Task 2 reply is proceed. D-17 exports Render and Purify (Task 1 printed d17-ready; external /msd-quick gate, not a 19.1 plan). ../sm-forum-plugin does not already exist as a foreign module. ../sm-forum-plugin/go.mod, ../sm-forum-plugin/go.work, ../sm-forum-plugin/go.sum, ../sm-forum-plugin/.gitignore, ../sm-forum-plugin/README.md, ../sm-forum-plugin/plugin.go, ../sm-forum-plugin/boot.go, ../sm-forum-plugin/routes.go, ../sm-forum-plugin/config/config.yaml, ../sm-forum-plugin/lang/en/lang.yaml, ../sm-forum-plugin/lang/pl/lang.yaml, ../sm-forum-plugin/contracts/access_resolver.go, ../sm-forum-plugin/classes/deny_all.go, ../sm-forum-plugin/classes/forum_service.go, ../sm-forum-plugin/models/category.go, ../sm-forum-plugin/models/thread.go, ../sm-forum-plugin/models/post.go, ../sm-forum-plugin/models/thread_read.go, ../sm-forum-plugin/models/registry.go, ../sm-forum-plugin/api/auth.go, ../sm-forum-plugin/api/errors.go, ../sm-forum-plugin/api/json.go, ../sm-forum-plugin/api/categories.go, ../sm-forum-plugin/api/threads.go, ../sm-forum-plugin/api/posts.go, ../sm-forum-plugin/updates/registry.go, ../sm-forum-plugin/updates/202610180001_create_golem15_forum_baseline.go, ../sm-forum-plugin/updates/baseline_test.go, ../sm-forum-plugin/testmain_test.go, ../sm-forum-plugin/harness_test.go, ../sm-forum-plugin/fixture_plugin_test.go, ../sm-forum-plugin/http_tracer_test.go ../sm-chatchannels-plugin/plugin.go, ../sm-chatchannels-plugin/contracts/access_resolver.go, ../sm-chatchannels-plugin/classes/deny_all.go, ../sm-chatchannels-plugin/boot.go, ../sm-chatchannels-plugin/routes.go, ../sm-chat-plugin/go.mod, ../sm-chat-plugin/http_tracer_test.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/classes/ForumService.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/classes/DenyAllForumAccessResolver.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/updates/, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/tests/security/ForumMarkdownRenderTest.php Per D-01 and D-02, create ../sm-forum-plugin as a sibling. Analog go.mod pins; replace summercms => ../summercms.go; go.work replaces sm-user-plugin. go.mod stays on analog pins plus the user plugin. Consume D-17 from summercms; do not add markdown libraries or the friends module. -plugin.go: package forum, PluginID golem15.forum, Requires golem15.user, HasRoutes, BucketProvider, HasCommands (rewrite lands in Task 3). README H1 Forum; plugin.name Forum / Forum. SetAccessResolver analog chatchannels. +plugin.go: package forum, PluginID golem15.forum, Requires golem15.user, HasRoutes, BucketProvider, HasCommands (rewrite lands in Task 4). README H1 Forum, one-sentence summary, import line, **Name:** mnemonic, standard sections; names only acme / blog; plugin.name Forum / Forum. Per D-03 / PATTERNS Docs/README, production sources, comments, lang and README never contain QuestStream, family, parent, child, Wavepath, or Fonoteka; copy TestFixtureAbsentFromProduction (retired-token grep) from the chat analog. SetAccessResolver analog chatchannels. Baseline 202610180001_create_golem15_forum_baseline: four PHP v1.1.0 tables from RESEARCH. categories.context_type NOT NULL, no FK; unique (context_type, context_id, slug); threads.user_id and posts.user_id nullable SET NULL; deletion_reason varchar check self|moderator or null. TestBaseline greps the four table names. @@ -212,7 +245,7 @@ Remote policy follows plan 01 Task 1: tea-create only on proceed-and-push; other - Task 3: DeleteContext, morph rewrite, remaining routes, GDPR null authorship + Task 4: DeleteContext, morph rewrite, remaining routes, GDPR null authorship forum:rewrite-context-types changes stored context_type rows; PHP cannot resolve rewritten aliases. ../sm-forum-plugin/classes/forum_service.go, ../sm-forum-plugin/console/rewrite_context_types.go, ../sm-forum-plugin/api/categories.go, ../sm-forum-plugin/api/threads.go, ../sm-forum-plugin/api/posts.go, ../sm-forum-plugin/routes.go, ../sm-forum-plugin/boot.go, ../sm-forum-plugin/plugin.go, ../sm-forum-plugin/README.md ../sm-forum-plugin/classes/forum_service.go, ../sm-chat-plugin/console/rewrite_context_types.go, ../sm-chat-plugin/classes/writes.go, ../sm-chatchannels-plugin/boot.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/forum/classes/ForumService.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/controllers/api/CommunityForumController.php diff --git a/.planning/phases/19.1-chat-satellites/19.1-03-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-03-PLAN.md index 8208f6f7..a877a347 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-03-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-03-PLAN.md @@ -35,13 +35,14 @@ files_modified: - ../sm-chatbots-plugin/harness_test.go - ../sm-chatbots-plugin/fixture_plugin_test.go - ../sm-chatbots-plugin/http_tracer_test.go -autonomous: true +autonomous: false requirements: [SC-19.1-1, SC-19.1-2, D-01, D-02, D-03, D-04, D-05] estimate: tokens: 160000 raw_tokens: 160000 - tasks: 2 + tasks: 3 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand inside this plan. must_haves: truths: - "D-01 / SC-19.1-2: module git.golem15.com/golem15/sm-chatbots-plugin, package chatbots, PluginID golem15.chatbots, Requires golem15.chat and golem15.user; go.mod never requires the AI plugin." @@ -134,15 +135,45 @@ Analog: + + Task 1: Confirm D-02 chatbots baseline id and D-05 prefix before the new repo exists + .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md (D-02, D-05), .planning/phases/19.1-chat-satellites/19.1-01-PLAN.md (Task 1 remote reply) + Print a short identifier sheet, then stop. Do not create ../sm-chatbots-plugin. The sheet lists: module git.golem15.com/golem15/sm-chatbots-plugin, package chatbots, PluginID golem15.chatbots, migration id 202610180001_create_golem15_chatbots_baseline, published prefix /_chatbots/api/v1. Remote policy follows the plan 01 Task 1 reply (tea-create only on proceed-and-push). + Lock D-02 baseline id 202610180001_create_golem15_chatbots_baseline and D-05 prefix /_chatbots/api/v1, then implement? + These names land in every adopting app's database and in published clients. Changing the migration id or prefix after an app migrates needs a new migration and a client change. + + + + + Reply proceed or abort. + + test -f .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && grep -q "D-05" .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && echo chatbots-ids-ready + non-zero exit or "chatbots-ids-ready" absent + + + - SUMMARY records the reply verbatim. + - After abort, ../sm-chatbots-plugin does not exist. + + The human confirmed the chatbots baseline id and published prefix before any chatbots repo file was written. + + - Task 1: End-to-end /ping — registry, dispatcher, JWT actor, ephemeral, /help + Task 2: End-to-end /ping — registry, dispatcher, JWT actor, ephemeral, /help D-02 bot_flags baseline and D-05 /_chatbots/api/v1 become the shared contract. - ../sm-chat-plugin exists (Phase 19) and ../sm-chatbots-plugin does not already exist as a foreign module. + Task 1 reply is proceed. ../sm-chat-plugin exists (Phase 19) and ../sm-chatbots-plugin does not already exist as a foreign module. ../sm-chatbots-plugin/go.mod, ../sm-chatbots-plugin/go.work, ../sm-chatbots-plugin/go.sum, ../sm-chatbots-plugin/.gitignore, ../sm-chatbots-plugin/README.md, ../sm-chatbots-plugin/plugin.go, ../sm-chatbots-plugin/boot.go, ../sm-chatbots-plugin/routes.go, ../sm-chatbots-plugin/config/config.yaml, ../sm-chatbots-plugin/lang/en/lang.yaml, ../sm-chatbots-plugin/lang/pl/lang.yaml, ../sm-chatbots-plugin/contracts/slash_command.go, ../sm-chatbots-plugin/contracts/bot_auth_resolver.go, ../sm-chatbots-plugin/classes/deny_all.go, ../sm-chatbots-plugin/classes/registry.go, ../sm-chatbots-plugin/classes/dispatcher.go, ../sm-chatbots-plugin/classes/help.go, ../sm-chatbots-plugin/models/bot_flag.go, ../sm-chatbots-plugin/models/registry.go, ../sm-chatbots-plugin/api/auth.go, ../sm-chatbots-plugin/api/errors.go, ../sm-chatbots-plugin/api/json.go, ../sm-chatbots-plugin/api/commands.go, ../sm-chatbots-plugin/updates/registry.go, ../sm-chatbots-plugin/updates/202610180001_create_golem15_chatbots_baseline.go, ../sm-chatbots-plugin/updates/baseline_test.go, ../sm-chatbots-plugin/testmain_test.go, ../sm-chatbots-plugin/harness_test.go, ../sm-chatbots-plugin/fixture_plugin_test.go, ../sm-chatbots-plugin/http_tracer_test.go ../sm-chatchannels-plugin/plugin.go, ../sm-chatchannels-plugin/go.work, ../sm-chatchannels-plugin/classes/deny_all.go, ../sm-chat-plugin/contracts/registry.go, ../sm-chat-plugin/api/auth.go, ../sm-chat-plugin/http_tracer_test.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/classes/SlashCommandRegistry.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/classes/CommandDispatcher.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/classes/CommandResult.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/classes/commands/HelpCommand.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/contracts/SlashCommand.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/contracts/BotAuthResolver.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/updates/create_bot_flags_table.php Per D-01 and D-02, create ../sm-chatbots-plugin. Analog pins; replace summercms => ../summercms.go; go.work replaces sm-user-plugin and sm-chat-plugin. Require sm-chat-plugin. Do not require the AI plugin module (SC-19.1-2). -plugin.go: package chatbots, PluginID golem15.chatbots, Requires golem15.chat and golem15.user. README H1 Chat bots; plugin.name Chat bots. SetBotAuthResolver analog SetAccessResolver. +plugin.go: package chatbots, PluginID golem15.chatbots, Requires golem15.chat and golem15.user. README H1 Chat bots, one-sentence summary, import line, **Name:** mnemonic, standard sections; names only acme / blog; plugin.name Chat bots / Boty czatu. Per D-03 / PATTERNS Docs/README, production sources, comments, lang and README never contain QuestStream, family, parent, child, Wavepath, or Fonoteka; copy TestFixtureAbsentFromProduction (retired-token grep) from the chat analog. SetBotAuthResolver analog SetAccessResolver. Baseline 202610180001_create_golem15_chatbots_baseline: golem15_chatbots_bot_flags (id, user_id unique chatbots_bot_flags_user_unique, is_bot bool default true, timestamps, FK user_id cascade). TestBaseline greps that table. @@ -173,7 +204,7 @@ Remote: stay local unless plan 01 already chose proceed-and-push and tea is avai - Task 2: GDPR bot_flags delete and catalog/auth expansion + Task 3: GDPR bot_flags delete and catalog/auth expansion ../sm-chatbots-plugin/boot.go, ../sm-chatbots-plugin/classes/registry.go, ../sm-chatbots-plugin/api/commands.go, ../sm-chatbots-plugin/README.md ../sm-chatbots-plugin/boot.go, ../sm-chat-plugin/boot.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatbots/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/controllers/api/CommunityCommandController.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/controllers/api/BotRestController.php Per D-03, Listen user.Deleting and delete golem15_chatbots_bot_flags for that user_id inside ev.Tx. diff --git a/.planning/phases/19.1-chat-satellites/19.1-04-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-04-PLAN.md index 37495983..103d608b 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-04-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-04-PLAN.md @@ -38,13 +38,14 @@ files_modified: - ../sm-herald-plugin/harness_test.go - ../sm-herald-plugin/fixture_plugin_test.go - ../sm-herald-plugin/http_tracer_test.go -autonomous: true +autonomous: false requirements: [SC-19.1-1, SC-19.1-2, D-04, D-05, D-06, D-09, D-10, D-11, D-12] estimate: tokens: 200000 raw_tokens: 200000 - tasks: 3 + tasks: 4 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand. The fourth task is the identifier checkpoint, not a scope split. must_haves: truths: - "D-09 / SC-19.1-2: .planning/notes/2026-10-18-webpush-go.md exists and names github.com/SherClockHolmes/webpush-go v1.4.0, jwt/v5 share, Options.HTTPClient = *fetchguard.Client Do, and does not name the in-tree Web Push module as the sender." @@ -164,15 +165,45 @@ Analog: The decision note exists and no herald go.mod yet requires webpush-go. + + Task 2: Confirm D-02 herald baseline id and D-05 prefix before the new repo exists + .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md (D-02, D-05, D-06), .planning/phases/19.1-chat-satellites/19.1-01-PLAN.md (Task 1 remote reply) + Print a short identifier sheet, then stop. Do not create ../sm-herald-plugin. The sheet lists: module git.golem15.com/golem15/sm-herald-plugin, package herald, PluginID golem15.herald, migration id 202610180001_create_golem15_herald_baseline, published prefix /_herald/api/v1. Remote policy follows the plan 01 Task 1 reply (tea-create only on proceed-and-push). + Lock D-02 baseline id 202610180001_create_golem15_herald_baseline and D-05 prefix /_herald/api/v1, then implement? + These names land in every adopting app's database and in published clients. D-06 also publishes routes PHP did not ship. Changing the migration id or prefix after an app migrates needs a new migration and a client change. + + + + + Reply proceed or abort. + + test -f .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && grep -q "D-05" .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && echo herald-ids-ready + non-zero exit or "herald-ids-ready" absent + + + - SUMMARY records the reply verbatim. + - After abort, ../sm-herald-plugin does not exist. + + The human confirmed the herald baseline id and published prefix before any herald repo file was written. + + - Task 2: End-to-end push — subscribe https, SendUnconditional after commit, 410 prune, rollback sends 0 + Task 3: End-to-end push — subscribe https, SendUnconditional after commit, 410 prune, rollback sends 0 D-02 herald baseline and D-05 /_herald/api/v1 become the shared contract; D-06 publishes routes PHP did not ship. - Task 1 printed webpush-note-ready. ../sm-herald-plugin does not already exist as a foreign module. + Task 2 reply is proceed. Task 1 printed webpush-note-ready. ../sm-herald-plugin does not already exist as a foreign module. ../sm-herald-plugin/go.mod, ../sm-herald-plugin/go.work, ../sm-herald-plugin/go.sum, ../sm-herald-plugin/.gitignore, ../sm-herald-plugin/README.md, ../sm-herald-plugin/plugin.go, ../sm-herald-plugin/boot.go, ../sm-herald-plugin/routes.go, ../sm-herald-plugin/config/config.yaml, ../sm-herald-plugin/lang/en/lang.yaml, ../sm-herald-plugin/lang/pl/lang.yaml, ../sm-herald-plugin/classes/subscription_service.go, ../sm-herald-plugin/classes/sender.go, ../sm-herald-plugin/jobs/send.go, ../sm-herald-plugin/models/subscription.go, ../sm-herald-plugin/models/registry.go, ../sm-herald-plugin/api/auth.go, ../sm-herald-plugin/api/errors.go, ../sm-herald-plugin/api/json.go, ../sm-herald-plugin/api/push.go, ../sm-herald-plugin/updates/registry.go, ../sm-herald-plugin/updates/202610180001_create_golem15_herald_baseline.go, ../sm-herald-plugin/updates/baseline_test.go, ../sm-herald-plugin/testmain_test.go, ../sm-herald-plugin/harness_test.go, ../sm-herald-plugin/fixture_plugin_test.go, ../sm-herald-plugin/http_tracer_test.go ../sm-chat-plugin/plugin.go, ../sm-chat-plugin/jobs/maintain_thread_summary.go, ../sm-chat-plugin/classes/service.go, ../sm-chat-plugin/http_tracer_test.go, modules/fetchguard/client.go, modules/fetchguard/policy.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/classes/PushSender.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/classes/services/SubscriptionService.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/updates/create_push_subscriptions_table.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/config/herald.php, .planning/notes/2026-10-18-webpush-go.md Only after the note exists, create ../sm-herald-plugin and go get github.com/SherClockHolmes/webpush-go@v1.4.0. Analog pins; replace summercms => ../summercms.go. Requires() empty. Do not import user models. Do not import the in-tree Web Push module. -plugin.go: package herald, PluginID golem15.herald, HasJobs, HasRoutes, HasCommands (command in Task 3), BucketProvider. README H1 Herald; rewrite the PHP reuse contract around the generic API (D-06). +plugin.go: package herald, PluginID golem15.herald, HasJobs, HasRoutes, HasCommands (command in Task 4), BucketProvider. README H1 Herald, one-sentence summary, import line, **Name:** mnemonic, standard sections; names only acme / blog; plugin.name Herald / Herald. Per D-03 / PATTERNS Docs/README, production sources, comments, lang and README never contain QuestStream, family, parent, child, Wavepath, or Fonoteka; copy TestFixtureAbsentFromProduction (retired-token grep) from the chat analog. Rewrite the PHP reuse contract around the generic API (D-06). Baseline 202610180001_create_golem15_herald_baseline: golem15_herald_push_subscriptions (endpoint varchar 500, keys text JSON p256dh/auth, unique (user_id, endpoint) herald_push_user_endpoint_unique, FK user_id cascade because the test host has users). TestBaseline greps the table. @@ -201,7 +232,7 @@ Remote: stay local unless plan 01 chose proceed-and-push; never force-push. - Task 3: PresenceGate, NeutralHeraldProfile, vapid-generate, remaining push routes + Task 4: PresenceGate, NeutralHeraldProfile, vapid-generate, remaining push routes ../sm-herald-plugin/contracts/herald_profile.go, ../sm-herald-plugin/contracts/presence_gate.go, ../sm-herald-plugin/classes/deny_all.go, ../sm-herald-plugin/classes/neutral_profile.go, ../sm-herald-plugin/classes/sender.go, ../sm-herald-plugin/console/vapid_generate.go, ../sm-herald-plugin/api/push.go, ../sm-herald-plugin/routes.go, ../sm-herald-plugin/boot.go, ../sm-herald-plugin/plugin.go, ../sm-herald-plugin/config/config.yaml, ../sm-herald-plugin/README.md ../sm-herald-plugin/classes/sender.go, ../sm-chatchannels-plugin/classes/deny_all.go, ../sm-chat-plugin/console/rewrite_context_types.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/classes/DenyAllPresenceGate.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/classes/NeutralHeraldProfile.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/console/GenerateVapidKeys.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/herald/config/herald.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/controllers/api/PushSubscriptionController.php Per D-03, PresenceGate default DenyAll ShouldSend always false; SetPresenceGate; Boot Warn while DenyAll is active. HeraldProfile default NeutralHeraldProfile (app name only) — no Warn for the profile. diff --git a/.planning/phases/19.1-chat-satellites/19.1-05-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-05-PLAN.md index 62a8fe97..de0aaec6 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-05-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-05-PLAN.md @@ -3,7 +3,9 @@ phase: 19.1-chat-satellites plan: 05 type: execute wave: 2 +# Scheduler grouping only: sm-chat-plugin (Phase 19) is already shipped. Not a 19.1 plan edge. depends_on: [] +# Empty on purpose: Phase 19 chat is a prior-phase artifact, asserted on the tracer precondition. No 19.1 plan predecessor. files_modified: - .planning/notes/2026-10-18-livekit-server-sdk-go.md - ../sm-chatvideo-plugin/.gitignore @@ -39,18 +41,20 @@ files_modified: - ../sm-chatvideo-plugin/harness_test.go - ../sm-chatvideo-plugin/fixture_plugin_test.go - ../sm-chatvideo-plugin/http_tracer_test.go -autonomous: true + - ../sm-chatvideo-plugin/reconcile_test.go +autonomous: false requirements: [SC-19.1-1, SC-19.1-2, D-04, D-05, D-07, D-13, D-14, D-15] estimate: tokens: 200000 raw_tokens: 200000 - tasks: 3 + tasks: 4 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand. The fourth task is the identifier checkpoint, not a scope split. must_haves: truths: - "D-13 / SC-19.1-2: .planning/notes/2026-10-18-livekit-server-sdk-go.md names github.com/livekit/server-sdk-go/v2 v2.19.0, flags pion/media-sdk/buildkit, RoomAPI interface, TrustedMode for the operator URL, and jwt/v5 MapClaims if SDK grant JSON differs." - - "D-02: baseline 202610180001_create_golem15_chatvideo_baseline creates golem15_chatvideo_sessions (unique active_conversation_id, join_code, no updated_at, CREATED_AT=started_at) and participants; demo-seed v1.0.1 is a comment." - - "D-05 / D-15: paths /_chatvideo/api/v1/conversations/{id}/video/{start,join,leave,end,status} and /call-links/{code}; video-initiate 5/min on start only; authorizer splits segment 2 of video:session:{id} and never uses the segment-1 helper; capabilities prs." + - "D-02 / D-15: baseline 202610180001_create_golem15_chatvideo_baseline creates golem15_chatvideo_sessions (unique active_conversation_id, join_code, card_message_id nullable uint, no updated_at, CREATED_AT=started_at) and participants; demo-seed v1.0.1 is a comment." + - "D-05 / D-15: paths /_chatvideo/api/v1/conversations/{id}/video/{start,join,leave,end,status} and /call-links/{code}; video-initiate 5/min on start only; authorizer splits segment 2 of video:session:{id} and never uses the segment-1 helper; capabilities prs; sessions.card_message_id is a nullable uint that carries over from PHP." - "D-14: summer chatvideo:reconcile-sessions plus conga Kind golem15.chatvideo.reconcile_sessions MaxAttempts 1 every 5 minutes; generic only (empty/gone room or max_duration); no GuestCall, call cards, or CallNotifier." - "D-13 token golden: HS256, iss API key, sub user id string, name, iat/nbf/exp token_ttl 900, video grant room/roomJoin/canPublish/canSubscribe, optional metadata JSON avatar." artifacts: @@ -184,17 +188,47 @@ Analog: The LiveKit note exists and no chatvideo go.mod yet requires the SDK. + + Task 2: Confirm D-02 chatvideo baseline id and D-05 prefix before the new repo exists + .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md (D-02, D-05, D-15), .planning/phases/19.1-chat-satellites/19.1-01-PLAN.md (Task 1 remote reply) + Print a short identifier sheet, then stop. Do not create ../sm-chatvideo-plugin. The sheet lists: module git.golem15.com/golem15/sm-chatvideo-plugin, package chatvideo, PluginID golem15.chatvideo, migration id 202610180001_create_golem15_chatvideo_baseline, published prefix /_chatvideo/api/v1, sessions.card_message_id nullable uint (D-15). Remote policy follows the plan 01 Task 1 reply (tea-create only on proceed-and-push). Phase 19 sm-chat-plugin is already shipped and is an external precondition, not a 19.1 plan edge. + Lock D-02 baseline id 202610180001_create_golem15_chatvideo_baseline and D-05 prefix /_chatvideo/api/v1, then implement? + These names land in every adopting app's database and in published clients. Changing the migration id or prefix after an app migrates needs a new migration and a client change. + + + + + Reply proceed or abort. + + test -f .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && grep -q "D-15" .planning/phases/19.1-chat-satellites/19.1-CONTEXT.md && echo chatvideo-ids-ready + non-zero exit or "chatvideo-ids-ready" absent + + + - SUMMARY records the reply verbatim. + - After abort, ../sm-chatvideo-plugin does not exist. + + The human confirmed the chatvideo baseline id and published prefix before any chatvideo repo file was written. + + - Task 2: End-to-end video start — unique active session, token golden, authorizer stranger deny + Task 3: End-to-end video start — unique active session, token golden, authorizer stranger deny D-02 chatvideo baseline and D-05 /_chatvideo/api/v1 become the shared contract. - Task 1 printed livekit-note-ready. ../sm-chat-plugin exists. ../sm-chatvideo-plugin does not already exist as a foreign module. + Task 2 reply is proceed. Task 1 printed livekit-note-ready. ../sm-chat-plugin exists (Phase 19 already shipped). ../sm-chatvideo-plugin does not already exist as a foreign module. ../sm-chatvideo-plugin/go.mod, ../sm-chatvideo-plugin/go.work, ../sm-chatvideo-plugin/go.sum, ../sm-chatvideo-plugin/.gitignore, ../sm-chatvideo-plugin/README.md, ../sm-chatvideo-plugin/plugin.go, ../sm-chatvideo-plugin/boot.go, ../sm-chatvideo-plugin/routes.go, ../sm-chatvideo-plugin/config/config.yaml, ../sm-chatvideo-plugin/lang/en/lang.yaml, ../sm-chatvideo-plugin/lang/pl/lang.yaml, ../sm-chatvideo-plugin/classes/livekit.go, ../sm-chatvideo-plugin/classes/authorizer.go, ../sm-chatvideo-plugin/classes/video_service.go, ../sm-chatvideo-plugin/models/session.go, ../sm-chatvideo-plugin/models/participant.go, ../sm-chatvideo-plugin/models/registry.go, ../sm-chatvideo-plugin/api/auth.go, ../sm-chatvideo-plugin/api/errors.go, ../sm-chatvideo-plugin/api/json.go, ../sm-chatvideo-plugin/api/video.go, ../sm-chatvideo-plugin/updates/registry.go, ../sm-chatvideo-plugin/updates/202610180001_create_golem15_chatvideo_baseline.go, ../sm-chatvideo-plugin/updates/baseline_test.go, ../sm-chatvideo-plugin/testmain_test.go, ../sm-chatvideo-plugin/harness_test.go, ../sm-chatvideo-plugin/fixture_plugin_test.go, ../sm-chatvideo-plugin/http_tracer_test.go ../sm-chat-plugin/classes/authorizer.go, ../sm-chat-plugin/boot.go, ../sm-chat-plugin/routes.go, ../sm-chat-plugin/http_tracer_test.go, modules/lighthouse/channel.go, modules/fetchguard/policy.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/Plugin.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/classes/LiveKitService.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/classes/VideoChannelAuthorizer.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/models/VideoSession.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/updates/, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/config/config.php, .planning/notes/2026-10-18-livekit-server-sdk-go.md Only after the note exists, create ../sm-chatvideo-plugin and go get github.com/livekit/server-sdk-go/v2@v2.19.0. Analog pins; replace summercms and sm-chat-plugin and sm-user-plugin. Requires golem15.chat. -plugin.go: package chatvideo, PluginID golem15.chatvideo, HasRoutes, HasJobs, HasCommands, HasSchedule (schedule in Task 3), BucketProvider. README H1 Chat video. +plugin.go: package chatvideo, PluginID golem15.chatvideo, HasRoutes, HasJobs, HasCommands, HasSchedule (schedule in Task 4), BucketProvider. README H1 Chat video, one-sentence summary, import line, **Name:** mnemonic, standard sections; names only acme / blog; plugin.name Chat video / Czat wideo. Per D-03 / PATTERNS Docs/README, production sources, comments, lang and README never contain QuestStream, family, parent, child, Wavepath, or Fonoteka; copy TestFixtureAbsentFromProduction (retired-token grep) from the chat analog. -Baseline 202610180001_create_golem15_chatvideo_baseline: sessions and participants from RESEARCH. unique active_conversation_id uniq_chatvideo_active_conversation; join_code varchar 12 unique; status pending|active|ended; no updated_at; comment demo-seed v1.0.1. Model CREATED_AT=started_at. TestBaseline greps both tables. +Baseline 202610180001_create_golem15_chatvideo_baseline: sessions and participants from RESEARCH. unique active_conversation_id uniq_chatvideo_active_conversation; join_code varchar 12 unique; card_message_id nullable uint (D-15 carry-over; the generic plugin stores the column and does not write call cards); status pending|active|ended; no updated_at; comment demo-seed v1.0.1. Model CREATED_AT=started_at. TestBaseline greps both tables and card_message_id. RoomAPI interface as RESEARCH. Production client: NewRoomServiceClient with HTTP through fetchguard TrustedMode (operator URL, may be loopback). Admin URL: livekit_admin_url else rewrite wss/ws to https/http. DeleteRoom swallows missing-room (D-13). ParticipantCount missing-room returns 0. Tests: in-memory fake; do not import the WebRTC stack the note flagged; do not construct the realtime room client. @@ -224,24 +258,27 @@ Remote: stay local unless plan 01 chose proceed-and-push; never force-push. - Task 3: leave/end/status/call-links, generic reconciler, realtime events - ../sm-chatvideo-plugin/classes/video_service.go, ../sm-chatvideo-plugin/classes/notifier.go, ../sm-chatvideo-plugin/jobs/reconcile.go, ../sm-chatvideo-plugin/console/reconcile.go, ../sm-chatvideo-plugin/schedule.go, ../sm-chatvideo-plugin/api/video.go, ../sm-chatvideo-plugin/api/call_links.go, ../sm-chatvideo-plugin/routes.go, ../sm-chatvideo-plugin/plugin.go, ../sm-chatvideo-plugin/boot.go, ../sm-chatvideo-plugin/README.md + Task 4: leave/end/status/call-links, generic reconciler, realtime events + ../sm-chatvideo-plugin/classes/video_service.go, ../sm-chatvideo-plugin/classes/notifier.go, ../sm-chatvideo-plugin/jobs/reconcile.go, ../sm-chatvideo-plugin/console/reconcile.go, ../sm-chatvideo-plugin/schedule.go, ../sm-chatvideo-plugin/api/video.go, ../sm-chatvideo-plugin/api/call_links.go, ../sm-chatvideo-plugin/routes.go, ../sm-chatvideo-plugin/plugin.go, ../sm-chatvideo-plugin/boot.go, ../sm-chatvideo-plugin/README.md, ../sm-chatvideo-plugin/reconcile_test.go ../sm-chatvideo-plugin/classes/video_service.go, ../sm-chat-plugin/classes/emit.go, ../sm-chat-plugin/jobs/maintain_thread_summary.go, ../sm-paymentgateway-plugin/schedule.go, /media/nvme/dev/jz/wavepath.org/plugins/golem15/chatvideo/classes/VideoCallNotifier.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/console/ReconcileVideoSessions.php, /media/nvme/dev/jz/wavepath.org/plugins/golem15/wavepath/controllers/api/CommunityVideoController.php Per D-05, add leave, end, status on /_chatvideo/api/v1/conversations/{id}/video/{leave,end,status} and GET /_chatvideo/api/v1/call-links/{code} with bucket call-link 10/min. join_code alphabet abcdefghijklmnopqrstuvwxyz0123456789 length 10. Uniform 404 for unknown codes. Per D-15, notifier publishes video:call:incoming to user:{id}; accepted/declined/ended and participant joined/left to video:session:{id}. Payload keys from RESEARCH. Publish failure is logged and not raised. Do not port host close-push extras. -Per D-14, Reconcile: if the LiveKit room is missing or empty, or started_at + max_duration elapsed, end the session, DeleteRoom (swallowed), emit video:call:ended. Command chatvideo:reconcile-sessions. Job Kind golem15.chatvideo.reconcile_sessions, MaxAttempts 1. Plugin.Schedule pact.Every(5 * time.Minute) on that command (5 minutes divides 24h). Keep only empty-or-gone room and max_duration. Drop host-only extras (guest rooms, chat cards, grace seconds) and the host command name. +Per D-14, Reconcile: if the LiveKit room is missing or empty, or started_at + max_duration elapsed, end the session, DeleteRoom (swallowed), emit video:call:ended. Command chatvideo:reconcile-sessions. Job Kind golem15.chatvideo.reconcile_sessions, MaxAttempts 1. Plugin.Schedule pact.Every(5 * time.Minute) on that command (5 minutes divides 24h). Keep only empty-or-gone room and max_duration. Drop host-only extras (guest rooms, chat cards, grace seconds) and the host command name. Add TestReconcileEmptyRoom (short, RoomAPI fake): an active session whose fake room is missing or has ParticipantCount 0 is ended; a room that is still occupied stays active. After APIs exist, note in the SUMMARY that execute should run the security-review agent (CONTEXT). Do not spawn it from this task. go -C ../sm-chatvideo-plugin vet ./... && go -C ../sm-chatvideo-plugin test -count=1 -short ./... non-zero exit or a package reports FAIL + go -C ../sm-chatvideo-plugin test -count=1 -short -run '^TestReconcileEmptyRoom$' . + non-zero exit, or TestReconcileEmptyRoom is missing, or an empty/gone room stays active - grep -n 'chatvideo:reconcile-sessions' ../sm-chatvideo-plugin/console/reconcile.go prints one line. - grep -n 'golem15.chatvideo.reconcile_sessions' ../sm-chatvideo-plugin/jobs/reconcile.go prints one line. - grep -n 'Every(5' ../sm-chatvideo-plugin/schedule.go prints one line. + - grep -n 'func TestReconcileEmptyRoom' ../sm-chatvideo-plugin/*.go prints one line. - grep -n 'GuestCall\|CallNotifier\|start_grace_seconds' ../sm-chatvideo-plugin/*.go ../sm-chatvideo-plugin/classes/*.go ../sm-chatvideo-plugin/jobs/*.go prints 0 lines. - grep -n 'call-links' ../sm-chatvideo-plugin/routes.go prints at least one line. @@ -272,7 +309,7 @@ After APIs exist, note in the SUMMARY that execute should run the security-revie -The note exists before go get. go -C ../sm-chatvideo-plugin test -short stays green including TestLiveKitTokenClaims and TestVideoAuthorizer. TestHTTPTracer proves one active session. +The note exists before go get. go -C ../sm-chatvideo-plugin test -short stays green including TestLiveKitTokenClaims, TestVideoAuthorizer, and TestReconcileEmptyRoom. TestHTTPTracer proves one active session. diff --git a/.planning/phases/19.1-chat-satellites/19.1-06-PLAN.md b/.planning/phases/19.1-chat-satellites/19.1-06-PLAN.md index 70acc0cb..8fc2ca16 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-06-PLAN.md +++ b/.planning/phases/19.1-chat-satellites/19.1-06-PLAN.md @@ -38,6 +38,7 @@ estimate: raw_tokens: 180000 tasks: 3 confidence: low +# Estimates are uncalibrated (0 phase actuals). The user locked exactly this 6-plan split; do not split further. Stay tracer-then-expand inside this plan. must_haves: truths: - "SC-19.1-4 / D-04: each plugin has testdata/PHP_METHOD_MAP.md plus TestPHPMethodMap; counts are chatbots 22, forum 25, herald 14, userfriends 31, chatvideo 0 in-plugin (Wavepath host methods mapped to generic-API Go or explicit N/A)." @@ -90,7 +91,7 @@ This plan's slice (plan 6 of 6, wave 3): unit tests last — maps, goldens, `scr ## Decisions taken in this plan (Claude's discretion) - Gate env overrides: USERFRIENDS, FORUM, CHATBOTS, HERALD, CHATVIDEO (sibling checkouts). -- Named short tests from RESEARCH/VALIDATION: TestBaseline ×5, TestHTTPTracer ×5, TestAccessResolverDefault, TestLiveKitTokenClaims, TestVideoAuthorizer, TestSubscribeEndpoint, TestNoGolem, TestNoUserfriendsImport, TestPHPMethodMap, TestFixtureAbsentFromProduction. +- Named short tests from RESEARCH/VALIDATION: TestBaseline ×5, TestHTTPTracer ×5, TestAccessResolverDefault, TestLiveKitTokenClaims, TestVideoAuthorizer, TestReconcileEmptyRoom, TestSubscribeEndpoint, TestNoGolem, TestNoUserfriendsImport, TestPHPMethodMap, TestFixtureAbsentFromProduction. - Postgres stage: tracers + TestSendEventRollback + GDPR cascades. - Decision-note paths grepped for locked module path + version. - Execute should run the security-review agent after this plan (APIs + push + tokens + HTML + GDPR all exist). This planner does not spawn it. @@ -140,7 +141,7 @@ Analog: Plans 01-05 have created the five sibling plugin roots with TestHTTPTracer and TestBaseline names. scripts/check-phase19.1.sh, ../sm-userfriends-plugin/testdata/PHP_METHOD_MAP.md, ../sm-userfriends-plugin/testdata/php_methods.txt, ../sm-userfriends-plugin/php_method_map_test.go scripts/check-phase19.sh, ../sm-chat-plugin/php_method_map_test.go, ../sm-chat-plugin/testdata/PHP_METHOD_MAP.md, .planning/phases/19.1-chat-satellites/19.1-VALIDATION.md - Copy scripts/check-phase19.sh shape into scripts/check-phase19.1.sh. Stages: self-test, plugins, docs, postgres. Sibling env USERFRIENDS / FORUM / CHATBOTS / HERALD / CHATVIDEO defaulting to $ROOT/../sm-<name>-plugin. Fail-closed: a skip, miss, red, or "no tests to run" fails. --self-test plants JSON the detectors must refuse. Named short tests from VALIDATION (TestBaseline, TestHTTPTracer, TestNoGolem, TestNoUserfriendsImport, TestSubscribeEndpoint, TestLiveKitTokenClaims, TestVideoAuthorizer, TestAccessResolverDefault, TestPHPMethodMap, TestFixtureAbsentFromProduction). Postgres: the five tracers plus TestSendEventRollback and GDPR cascade names. Docs stage greps the three note paths for SherClockHolmes/webpush-go, livekit/server-sdk-go/v2, and the forum-policy bluemonday pin. + Copy scripts/check-phase19.sh shape into scripts/check-phase19.1.sh. Stages: self-test, plugins, docs, postgres. Sibling env USERFRIENDS / FORUM / CHATBOTS / HERALD / CHATVIDEO defaulting to $ROOT/../sm-<name>-plugin. Fail-closed: a skip, miss, red, or "no tests to run" fails. --self-test plants JSON the detectors must refuse. Named short tests from VALIDATION (TestBaseline, TestHTTPTracer, TestNoGolem, TestNoUserfriendsImport, TestSubscribeEndpoint, TestLiveKitTokenClaims, TestVideoAuthorizer, TestReconcileEmptyRoom, TestAccessResolverDefault, TestPHPMethodMap, TestFixtureAbsentFromProduction). Postgres: the five tracers plus TestSendEventRollback and GDPR cascade names. Docs stage greps the three note paths for SherClockHolmes/webpush-go, livekit/server-sdk-go/v2, and the forum-policy bluemonday pin. Also write userfriends testdata/PHP_METHOD_MAP.md for all 31 PHP test methods (GroupPolicy, GroupVisibilityGate, GroupModels). Components and demo seeders are not-applicable (D-07). php_method_map_test.go copies the chat analog. This tracer proves the gate can require TestPHPMethodMap on one repo. @@ -152,6 +153,7 @@ Also write userfriends testdata/PHP_METHOD_MAP.md for all 31 PHP test methods (G - grep -n 'USERFRIENDS' scripts/check-phase19.1.sh prints at least one line. - grep -n 'TestPHPMethodMap' scripts/check-phase19.1.sh prints at least one line. + - grep -n 'TestReconcileEmptyRoom' scripts/check-phase19.1.sh prints at least one line. - wc -l ../sm-userfriends-plugin/testdata/PHP_METHOD_MAP.md is greater than 31. The phase gate self-test refuses planted failures, and userfriends TestPHPMethodMap is green. diff --git a/.planning/phases/19.1-chat-satellites/19.1-RESEARCH.md b/.planning/phases/19.1-chat-satellites/19.1-RESEARCH.md index 8f60fc19..5f9cd349 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-RESEARCH.md +++ b/.planning/phases/19.1-chat-satellites/19.1-RESEARCH.md @@ -593,29 +593,35 @@ app.Events.Listen[*userclasses.DeletingEvent](PluginID, p.onUserDeleting) | A3 | D-17 will export `Render`/`Purify` + named policy before forum execute | CONTEXT | Forum plan blocks if missing | | A4 | classify-confidence webfetch=LOW even `--verified` | seam output | Library versions are checkpoints inside locked names | -## Open Questions +## Open Questions (RESOLVED) -1. **LiveKit JWT: SDK vs jwt/v5** +1. **LiveKit JWT: SDK vs jwt/v5** (RESOLVED — plan 05) - What we know: PHP payload is explicit MapClaims [VERIFIED: LiveKitService.php:80-99]. Official Go samples use `auth.AccessToken`. - What's unclear: extra claims (`jti`, grant nesting). - Recommendation: first chatvideo task is a golden round-trip; pick mint path that matches PHP. Do not reopen D-13. + - RESOLVED: plan 05 Task 3 `TestLiveKitTokenClaims`; prefer jwt/v5 MapClaims if SDK ToJWT fails the golden. D-13 stays locked. -2. **D-17 module shape** +2. **D-17 module shape** (RESOLVED — plan 02) - What we know: not landed; must not be cabana or seaglass. - What's unclear: package name (beach-theme), whether `Purify` policies are a registry. - Recommendation: forum consumes whatever the quick task exports; document the call in the forum plan, do not specify the package name here. + - RESOLVED: plan 02 Task 1 consumes whatever the `/msd-quick` task exports (`func Render(` / `func Purify(`) and does not name the package. -3. **Morph rewrite ownership** +3. **Morph rewrite ownership** (RESOLVED — plan 02) - Discretion. Recommendation: forum owns `forum:rewrite-context-types` for `golem15_forum_categories.context_type`; chat already rewrites conversation context_type. + - RESOLVED: plan 02 Task 4 ships `forum:rewrite-context-types` for `golem15_forum_categories.context_type`. -4. **chatvideo generic addressing** +4. **chatvideo generic addressing** (RESOLVED — plan 05) - Discretion: conversation id vs context alias. Recommendation: **conversation id** as primary (`/_chatvideo/api/v1/conversations/{id}/video/...`) plus optional context lookup through chat's registry so Wavepath group-video payloads stay reproducible. + - RESOLVED: plan 05 uses conversation id as primary plus optional context lookup through chat Registry. -5. **Herald NeutralHeraldProfile vs deny-all** +5. **Herald NeutralHeraldProfile vs deny-all** (RESOLVED — plan 04) - PHP binds NeutralHeraldProfile + DenyAllPresenceGate. Go should keep both defaults. PresenceGate is the fail-closed send gate. + - RESOLVED: plan 04 Task 4 keeps both defaults; PresenceGate DenyAll is the fail-closed send gate; NeutralHeraldProfile has no Warn. -6. **OBS-01 cooldown without Laravel Cache** +6. **OBS-01 cooldown without Laravel Cache** (RESOLVED — plan 04) - PHP `Cache::add('obs:warn:herald.delivery', 1, 60)` [VERIFIED: PushSender.php:213]. Recommendation: process-local sync.Map 60s (PHP already has an in-process fallback [VERIFIED: PushSender.php:227-246]) plus optional cooler if already in the plugin test host. Do not add Redis as a herald dependency. + - RESOLVED: plan 04 Task 4 uses process-local sync.Map 60s. ## Environment Availability @@ -704,7 +710,7 @@ Five repos means a task that "finishes forum" is not evidence for herald. Nyquis ### Wave 0 Gaps -- [ ] Five repos: `go.mod` with `replace` to `../../../../summercms.go`, `plugin.go`, baseline, `harness_test.go` / `testmain_test.go` +- [ ] Five repos: `go.mod` with `replace` to `../summercms.go` (sibling checkout; live measurement `sm-chat-plugin/go.mod:147`. The older `../../../../summercms.go` path is stale — that is for an app submodule mount, not these sibling repos), `plugin.go`, baseline, `harness_test.go` / `testmain_test.go` - [ ] `testdata/goldens/` per plugin (serializers, events, LiveKit JWT, forum HTML) - [ ] `acme` fixture plugin (test files only) where a context is needed (forum, userfriends adapter) - [ ] LiveKit `RoomAPI` + push `HTTPClient` fakes diff --git a/.planning/phases/19.1-chat-satellites/19.1-VALIDATION.md b/.planning/phases/19.1-chat-satellites/19.1-VALIDATION.md index 3a2e99f7..833088b5 100644 --- a/.planning/phases/19.1-chat-satellites/19.1-VALIDATION.md +++ b/.planning/phases/19.1-chat-satellites/19.1-VALIDATION.md @@ -66,7 +66,7 @@ Task IDs assume the research-recommended 6-plan split (confirm at the plan-count ## Wave 0 Requirements -- [ ] Five repos: `go.mod` with `replace` to `../../../../summercms.go`, `plugin.go`, baseline, `harness_test.go` / `testmain_test.go` (`flag.Parse` + `testing.Short`) +- [ ] Five repos: `go.mod` with `replace` to `../summercms.go` (sibling checkout; live measurement `sm-chat-plugin/go.mod:147`. The older `../../../../summercms.go` path is stale — that is for an app submodule mount, not these sibling repos), `plugin.go`, baseline, `harness_test.go` / `testmain_test.go` (`flag.Parse` + `testing.Short`) - [ ] `testdata/goldens/` per plugin (serializers, events, LiveKit JWT, forum HTML) - [ ] `acme` fixture plugin (test files only) where a context is needed (forum, userfriends adapter) - [ ] LiveKit `RoomAPI` + push `HTTPClient` fakes