功能修改

This commit is contained in:
npc0-hue
2026-07-20 16:42:33 +08:00
parent 48b8ad8d6c
commit a0e69417db
224 changed files with 22015 additions and 884 deletions
@@ -0,0 +1,2 @@
schema: spec-driven
created: 2026-07-18
@@ -0,0 +1,80 @@
## Context
Item 9 made the console truthful about API-backed operational state, current-session operations, and safe projections. The remaining production gap is not another dashboard facade; it is durable governance: admission control under capacity pressure, alert lifecycle closure, complete plugin lifecycle state, and real provider-backed AI assistance. The implementation must reuse Platform as the authority and Run as a channelized executor while keeping plugin pages and browser code away from raw secrets, direct sockets, host paths, and provider transport details.
## Goals / Non-Goals
**Goals:**
- Govern server and Run capacity through Platform admission checks, safe endpoint capacity reports, queued/retrying jobs, and explicit capacity-denied responses.
- Persist alerts with source, severity, state, acknowledgement, scoped retry, resolution, suppression windows, audit links, and safe diagnostic text.
- Model complete plugin lifecycle state and compatibility gates in Platform, and drive lifecycle jobs through the existing job channel.
- Add real AI Provider invocation through a provider client that uses Platform-stored key/base URL material and never returns raw credentials or transport details.
- Require AI-generated config changes to produce a diff/recommendation that must be approved before any run-side write job is dispatched.
- Surface governance, alerts, lifecycle, and AI states in existing first-party pages without replacing the visual system or full-width management surfaces.
- Extend Run capacity/lifecycle contracts with bounded metadata only, preserving channel isolation and priority.
**Non-Goals:**
- No billing, cloud host sales, cloud/agent provider marketplace, or SaaS marketplace expansion.
- No arbitrary shell, direct Run socket/endpoint, host path projection, raw PID/socket/DSN/RCON, or raw credential/token/key/base URL exposure.
- No browser/plugin storage of provider secrets.
- No replacement of the five required first-party areas or the black-mecha/magical-girl theme system.
## Decisions
### Decision 1: Platform owns production admission decisions
Run heartbeats report bounded capacity metadata. Platform combines that with server bindings, queued/running job pressure, endpoint capability availability, and configured limits before accepting lifecycle, dependency, backup, update, and plugin jobs. Rejected work returns a safe capacity or compatibility reason and records audit/alert evidence.
Alternative considered: let Run reject after claim. Rejected because operators need immediate Platform feedback, and Run-only rejection creates noisy retry loops.
### Decision 2: Alerts are durable state, not transient UI messages
Capacity pressure, failed lifecycle work, stale endpoints, AI provider failures, plugin compatibility failures, and unsafe request denials create or update durable alert records. Alerts have explicit acknowledgement and resolution transitions with actor and audit metadata. Current-session UI operations remain separate and cannot close durable alerts by themselves.
Alternative considered: derive alerts only from latest jobs/metrics. Rejected because acknowledgement, suppression, and resolution are production workflows that must survive restart.
### Decision 3: Plugin lifecycle state is managed by Platform
Marketplace enablement remains a catalog state, while lifecycle operations track installed plugin version, target server compatibility, dependency status, desired state, current state, upgrade/rollback availability, linked job IDs, and audit/alert summaries. Plugin manifests and bridge calls declare capabilities and purposes, but Platform authorizes and dispatches all jobs.
Alternative considered: plugin pages manage lifecycle locally through bridge state. Rejected because that would bypass durable authorization and job/audit truth.
### Decision 4: Real AI Provider calls use a redacted provider client
Platform selects an active provider, decrypts key/base URL material inside the service boundary, sends bounded requests through a provider client, and returns only safe recommendation/diff/usage metadata. Tests and local mode can still use deterministic clients, but production code must support a real HTTP provider path with redacted failures.
Alternative considered: expose base URLs or keys to plugin pages for direct calls. Rejected by the repository AI Provider rules and secret boundary.
### Decision 5: AI config changes are two-step
AI can suggest a structured diff for configuration or lifecycle inputs. Platform stores the diff preview and requires explicit approval before dispatching a run-side config write job. Approval is scoped to actor/server/plugin/config revision and stale approvals are denied.
Alternative considered: dispatch config writes directly after AI completion. Rejected because AI suggestions must be reviewable before mutation.
### Decision 6: Run receives bounded lifecycle and capacity metadata only
Run protocol additions are limited to safe capacity dimensions, pressure reasons, lifecycle capability names, and logical job inputs. They do not carry raw host paths, process IDs, sockets, credentials, provider configuration, or browser/plugin transport material.
Alternative considered: add a general operations channel. Rejected because existing control/job/log/artifact/game-client channels already define the isolation model.
## Risks / Trade-offs
- [Risk] Alert deduplication can hide repeated incidents. Mitigation: keep occurrence counts, last-seen timestamps, state transitions, and audit references.
- [Risk] Capacity admission can reject recoverable work too early. Mitigation: use explicit retry-after hints, scoped retry, and distinguish hard compatibility failures from temporary pressure.
- [Risk] Real provider calls can leak transport errors. Mitigation: redact provider failures and validate every response before returning it.
- [Risk] Lifecycle state overlaps existing marketplace state. Mitigation: keep marketplace catalog state separate from server/plugin lifecycle installations.
- [Risk] Broad verification may be expensive. Mitigation: add focused unit tests first, then run full platform_web, plugins, platform, run, structure, OpenSpec, diff, and browser checks before completion.
## Migration Plan
1. Add OpenSpec artifacts and validate strictly before implementation.
2. Add shared Platform domain/DTO/validator/model/repo/service support for capacity governance, alerts, plugin lifecycle, and AI diff approvals.
3. Add Platform API routes and route docs with named DTOs and OpenAPI-style handler comments.
4. Extend plugin manifest/SDK/bridge contracts and examples with lifecycle and mediated AI purpose metadata.
5. Extend Run protocol/runtime capacity and lifecycle metadata without crossing channel boundaries.
6. Update platform_web contracts/pages/theme/tests to surface capacity, alerts, lifecycle, and AI diff approval using existing first-party surfaces.
7. Run full verification and record evidence in this change's tasks.
Rollback is additive: remove the new governance/lifecycle/alert/AI diff approval routes and UI panels, while preserving existing item 9 console behavior and earlier durable job/channel mechanics.
@@ -0,0 +1,30 @@
## Why
The platform now has a real API-backed operations console and durable Run channels, but production operators still need stronger capacity governance, alert closure, full plugin lifecycle state, and a non-mock Platform-mediated AI Provider path. These areas were intentionally left as future work in prior changes and now need to become first-class, durable workflows without weakening the existing browser, plugin, Run, and secret boundaries.
## What Changes
- Add production capacity governance for Run endpoints and server instances: safe capacity reports, admission decisions, pressure alerts, and bounded retry/reconciliation.
- Add durable alert rules/events with acknowledgement, scoped retry, resolution, audit evidence, and UI surfacing across overview, server detail, maintenance, and operation history.
- Complete plugin lifecycle beyond marketplace state: install, enable, disable, upgrade, rollback, retire, dependency checks, compatibility gates, lifecycle jobs, and durable audit/alert hooks.
- Replace mock-only AI invocation with a real provider-client integration path that keeps keys and base URLs in Platform, validates plugin purposes, returns redacted recommendations, and requires reviewable diff approval before config writes.
- Extend Run channel contracts only with bounded capacity and lifecycle metadata; do not add direct browser-to-Run access or plugin-owned transports.
- Preserve the required first-party areas and the black-mecha / magical-girl crystal-moonlight operations console style.
## Capabilities
### New Capabilities
- `production-operations-governance`: Platform-owned capacity governance, alert closure, complete plugin lifecycle, and real mediated AI Provider operations.
### Modified Capabilities
None.
## Impact
- Affects `platform/` domain, DTOs, validators, repositories, services, API routes, tests, and docs.
- Affects `platform_web/` API contracts, page contracts, first-party pages, shared operation components, theme styles, browser acceptance, and tests.
- Affects `plugins/` manifest schema, SDK/bridge contracts, examples, validation tests, and docs.
- Affects the independent `run/` protocol/runtime with bounded capacity/lifecycle metadata and tests.
- Does not add billing, cloud host sales, cloud/agent provider marketplace, arbitrary shell, direct Run socket/endpoint exposure, or raw credential projection.
@@ -0,0 +1,109 @@
## ADDED Requirements
### Requirement: Platform governs production capacity
Platform SHALL make admission and scheduling decisions using persisted server bindings, endpoint capability support, current Run capacity reports, durable job pressure, and configured safety limits before dispatching production lifecycle work.
#### Scenario: Capacity accepts bounded work
- **WHEN** an authorized operator requests a plugin lifecycle, dependency, backup, update, or server lifecycle operation and an assigned endpoint is online with matching capabilities and available capacity
- **THEN** Platform MUST create one durable job with safe capacity metadata, audit the admission decision, and expose a safe job projection
#### Scenario: Capacity denies pressure safely
- **WHEN** the assigned endpoint is offline, stale, missing capability support, over its configured running/queued limits, or under log/artifact/backlog pressure
- **THEN** Platform MUST reject or defer the request with a safe retry-after/capacity reason, MUST NOT fabricate success, and MUST NOT expose raw endpoint addresses, sockets, paths, credentials, leases, or session tokens
### Requirement: Run reports bounded capacity without blocking priority channels
Run SHALL report only bounded capacity dimensions on control heartbeat and job claim metadata, and SHALL keep control, job lifecycle, log ingest, artifact transfer, and optional game-client bridge channels independent.
#### Scenario: Artifact backlog exists during heartbeat
- **WHEN** artifact or component transfer backlog is present
- **THEN** Run MUST continue sending control heartbeat and job ack/result/cancel/reconcile metadata without embedding artifact chunks, host paths, local file names, credentials, sockets, or provider configuration
#### Scenario: Capacity report is sanitized
- **WHEN** Platform or browser views Run endpoint capacity
- **THEN** visible capacity MUST include only logical counts, percentages, pressure codes, and timestamps, never raw host paths, PIDs, sockets, DSNs, RCON values, secrets, leases, or direct endpoint URLs
### Requirement: Alerts are durable and closeable
Platform SHALL persist alert records for production incidents including capacity pressure, endpoint staleness, failed jobs, lifecycle failures, plugin compatibility failures, unsafe request denials, and AI provider failures.
#### Scenario: Alert is acknowledged and resolved
- **WHEN** an authorized operator acknowledges and later resolves an active alert
- **THEN** Platform MUST update durable alert state, actor, timestamps, audit references, and safe resolution notes without mutating unrelated alerts
#### Scenario: Alert retry remains scoped
- **WHEN** an operator retries a failed alert source such as endpoint capacity refresh, plugin lifecycle check, or AI provider test
- **THEN** only that source is retried, busy state prevents duplicate submission, and success/failure is reflected from Platform responses rather than local timers
### Requirement: Plugin lifecycle is complete and platform-mediated
Platform SHALL manage plugin lifecycle installations separately from marketplace catalog state, including install, enable, disable, upgrade, rollback, retire, dependency checks, compatibility gates, desired/current state, job linkage, audit history, and alert integration.
#### Scenario: Plugin upgrade is approved
- **WHEN** an authorized operator approves an upgrade for a server-bound plugin installation with a compatible target version, satisfied dependency checks, and endpoint capability support
- **THEN** Platform MUST create a durable lifecycle job and transition state only from job results or reconciliation evidence
#### Scenario: Plugin rollback is repeated
- **WHEN** rollback is retried with the same idempotency key and immutable inputs
- **THEN** Platform MUST return the original lifecycle/job result and MUST reject the same key with different immutable inputs
#### Scenario: Unsafe lifecycle input is rejected
- **WHEN** plugin lifecycle metadata, manifest actions, bridge requests, or job inputs contain arbitrary shell, raw credentials, direct Run endpoints, host paths, PIDs, sockets, DSNs, RCON data, unknown capabilities, or undeclared AI purposes
- **THEN** validation MUST reject the request before registration or dispatch
### Requirement: Plugins request AI only through Platform-mediated capability
Plugin manifests, SDK calls, and platform-hosted plugin pages SHALL request AI assistance only through typed Platform bridge/API contracts that declare purpose, request ID, scoped input, and context references.
#### Scenario: Declared AI purpose is invoked
- **WHEN** a plugin invokes a declared AI purpose through the Platform bridge
- **THEN** Platform MUST validate plugin installation state, route permission, server scope, purpose, payload bounds, provider availability, and unsafe text before invoking a provider client
#### Scenario: Undeclared AI purpose is denied
- **WHEN** a plugin invokes an undeclared or currently unauthorized AI purpose
- **THEN** Platform MUST deny the request with a safe error and MUST NOT call a provider client
### Requirement: Real AI Provider integration stays inside Platform
Platform SHALL support a real provider client path that reads provider keys and base URL material only inside Platform service boundaries, invokes enabled providers with bounded requests, and returns redacted responses.
#### Scenario: Real provider returns recommendation
- **WHEN** an enabled provider is selected and the provider client succeeds
- **THEN** Platform MUST return safe recommendation, model, usage, request ID, and optional diff preview metadata without raw API keys, bearer tokens, base URL secrets, transport headers, storage material, host paths, sockets, or credentials
#### Scenario: Provider fails
- **WHEN** provider transport, authentication, rate limit, or model invocation fails
- **THEN** Platform MUST persist a safe audit/alert, return a redacted failure, and MUST NOT expose raw provider URL, headers, keys, request body secrets, or stack traces
### Requirement: AI config changes require reviewable diff approval
AI-generated configuration changes SHALL be persisted as reviewable recommendations or diff previews and SHALL require separate operator approval before Platform dispatches any run-side config write job.
#### Scenario: Diff is approved
- **WHEN** an authorized operator approves a current, matching AI config diff preview for the same server, plugin, actor scope, and config revision
- **THEN** Platform MUST dispatch one bounded config write job and link the job, approval, audit event, and source AI request
#### Scenario: Diff is stale or cancelled
- **WHEN** the config revision changes, the approval is cancelled, or the preview has expired
- **THEN** Platform MUST reject dispatch, preserve the recommendation for review history, and avoid run-side mutation
### Requirement: Console surfaces governance without changing visual direction
platform_web SHALL surface capacity governance, alert closure, plugin lifecycle, and AI diff approval in the existing first-party operations console using real Platform APIs, permissions, confirmation, busy state, scoped retry, and failure recovery.
#### Scenario: Operator closes alert in the console
- **WHEN** an authorized operator acknowledges or resolves an alert
- **THEN** the UI MUST dispatch one Platform request, block duplicate submission while pending, refresh from persisted response, and show failure recovery without claiming local success
#### Scenario: Narrow viewport renders governance surfaces
- **WHEN** the console is rendered at 390px in black-mecha or magical-girl theme
- **THEN** capacity, alerts, lifecycle, AI diff review, confirmations, and operation rows MUST remain readable, bounded, and theme-consistent without page-local global decoration
### Requirement: Verification covers production governance boundaries
The change SHALL include platform tests, run tests, plugin typecheck/tests/manifest validation, platform_web typecheck/tests/build, browser acceptance evidence, structure validation, strict OpenSpec validation, two-repository diff whitespace checks, and forbidden-field scans before tasks are marked complete.
#### Scenario: Verification evidence is recorded
- **WHEN** implementation tasks are completed
- **THEN** `tasks.md` MUST record real command/browser evidence and MUST NOT mark verification complete until those checks pass
@@ -0,0 +1,57 @@
## 1. OpenSpec and Architecture
- [x] 1.1 Create proposal, design, spec, and task artifacts for production operations governance.
- [x] 1.2 Run `openspec validate implement-production-operations-governance --strict` before implementation.
## 2. Platform Capacity, Alerts, and Lifecycle
- [x] 2.1 Add domain/DTO/validator/model/repo/service support for production capacity governance and safe admission decisions.
- [x] 2.2 Add durable alert records with acknowledge, resolve, scoped retry, audit linkage, deduplication, and safe diagnostic text.
- [x] 2.3 Add complete plugin lifecycle installation state, compatibility gates, idempotency fences, upgrade/rollback/retire operations, and job/audit/alert integration.
- [x] 2.4 Add real AI Provider client integration plus redacted provider failure handling and alert/audit evidence.
- [x] 2.5 Add AI config diff preview/approval persistence and dispatch gating before run-side config write jobs.
- [x] 2.6 Update Platform API routes, route docs, protocol docs, and tests.
## 3. Plugin SDK and Bridge
- [x] 3.1 Extend manifest schema and examples with production lifecycle and AI purpose declarations.
- [x] 3.2 Extend SDK/bridge contracts to request lifecycle/AI through Platform-mediated capabilities only.
- [x] 3.3 Add validation/typecheck/tests proving unsafe lifecycle input and raw credential/direct Run fields are rejected.
## 4. Run Protocol and Runtime
- [x] 4.1 Extend Run protocol capacity reports and job metadata with bounded pressure/lifecycle fields only.
- [x] 4.2 Update Run runtime capacity reporting and lifecycle handling without blocking control/job/log/artifact channels.
- [x] 4.3 Add Run tests for capacity sanitization, channel isolation under backlog, and lifecycle metadata validation.
## 5. platform_web Console
- [x] 5.1 Add typed API/contracts for capacity governance, alerts, plugin lifecycle, AI diff preview, and approval.
- [x] 5.2 Surface alerts and capacity on overview, server detail, maintenance, and operation history with confirmation, busy state, scoped retry, persisted responses, and failure recovery.
- [x] 5.3 Surface full plugin lifecycle and AI diff approval in existing first-party pages using shared themed surfaces.
- [x] 5.4 Add tests for permissions, duplicate prevention, failed recovery, forbidden-field omission, and 390px theme-safe rendering.
## 6. Verification
- [x] 6.1 Run platform Go tests.
- [x] 6.2 Run independent Run Go tests.
- [x] 6.3 Run plugins typecheck, tests, and manifest validation.
- [x] 6.4 Run platform_web typecheck, tests, and production build.
- [x] 6.5 Run browser acceptance for the five first-party areas, server detail, alerts, plugin lifecycle, AI diff approval, desktop and 390px, black-mecha and magical-girl.
- [x] 6.6 Scan rendered outputs for raw key/token/secret/base URL secret/path/PID/socket/credential/DSN/RCON/direct Run endpoint fragments.
- [x] 6.7 Run `scripts/check-structure.sh`, `openspec validate implement-production-operations-governance --strict`, and both repository `git diff --check`.
- [x] 6.8 Record real verification evidence in this file before marking verification tasks complete.
## Verification Evidence
- 2026-07-18 19:02 CST: `cd platform && go test ./...` passed for all Platform packages; `cd /Users/tasia/Desktop/code/run && go test ./...` passed for the independent Run repository.
- `cd plugins && npm run typecheck`, `npm test -- --run`, and `npm run validate:manifest` passed: 1 test file / 19 tests and all three example manifests validated. The manifest command was rerun outside the filesystem sandbox because `tsx` requires a local IPC pipe.
- `cd platform_web && npm run typecheck`, `npm test -- --run`, and `npm run build` passed: 26 test files / 135 tests, 1,829 production modules transformed, and the production bundle completed successfully.
- `scripts/local-debug-smoke.sh` and `npm --prefix platform_web run acceptance:browser` passed against the real local Platform and independent Run stack rooted at `/private/tmp/browser-local-debug-acceptance-10o`. `node --check platform_web/acceptance/browser-acceptance.mjs` and `bash -n scripts/local-debug-env.sh scripts/local-debug-smoke.sh scripts/local-debug-start.sh` also passed.
- Capacity evidence recorded a persisted `denied` admission with bounded `queue.limit` and `capability.missing` pressure codes plus a linked durable alert and audit event. Alert cancellation preserved `active`; confirmed acknowledgement persisted `acknowledged`, actor, timestamp, and audit linkage.
- Plugin lifecycle install and enable each produced durable Platform jobs. The persisted installation reached the requested enabled state with linked job and audit IDs; browser scans passed after the lifecycle interactions.
- AI diff cancellation preserved `pending`; explicit approval persisted `approved` and dispatched exactly one `config.write` job. Independent Run completed that job as `succeeded` with a safe `file.write` result at version 2 and an `atomic compare-and-swap file write` audit summary; Platform configuration advanced from version 1 to 2 before the subsequent real `process.stop` request.
- Browser acceptance covered 首页、服务器管理、插件市场、用户管理、AI 提供商管理, server detail, maintenance/operation history, alert closure, plugin lifecycle, and AI diff approval in four scenarios: 1440x960 and 390x844 for `mecha-black` and `magical-girl`. All 38 route/interaction checks reported zero horizontal overflow, zero overlapping controls, and no tiny visible text boxes.
- API and rendered-output scans passed for raw key/token/secret/base URL secret, host path, PID, socket, credential, DSN, RCON, session/direct Run endpoint, and plugin-owned transport fragments. Confirm/cancel, busy duplicate prevention, persisted terminal state, real failure recovery, and scoped retry evidence are included in the structured artifact.
- `scripts/check-structure.sh`, `openspec validate implement-production-operations-governance --strict`, the main repository `git diff --check`, and the independent Run repository `git diff --check` passed. These gates were rerun after recording this evidence.
- Structured browser evidence: `/private/tmp/browser-local-debug-acceptance-10o/browser-acceptance/browser-acceptance-evidence.json` and `/private/tmp/browser-local-debug-acceptance-10o/browser-acceptance/item-10-evidence.json`. Durable Platform/Run result snapshot: `/private/tmp/browser-local-debug-acceptance-10o/platform/metadata.json`.