Skip to content

feat(docs-sync): open per-surface docs PRs, rank reviewers, and cover the cloud product surfaces - #14093

Merged
iscekic merged 1 commit into
mainfrom
kwf/docs-sync-cloud-surfaces-v2-de1e
Sep 14, 2026
Merged

iscekic merged 1 commit into
mainfrom
kwf/docs-sync-cloud-surfaces-v2-de1e

Conversation

@iscekic

@iscekic iscekic commented Sep 13, 2026 •

Copy link
Copy Markdown
Collaborator

Changelog for users

  • A docs change for a cloud product now opens its own sync pull request for that product instead of the shared catch-all.
  • Cloud pages route to their product: mobile to cloud-mobile, collaborate pages to cloud-web, and cloud-agent pages to cloud-agent.
  • The job leaves the old dated docs/auto-sync-<date> pull requests alone: it no longer comments on or closes them, reads them as learning targets, or rewrites their bodies.
  • If the cloud history cannot be read, the cloud surface still opens its pull request and uses the other reviewers; the run does not fail.

Changelog for maintainers

  • .github/docs-sync/learn.mjs:455 — Accepted: the learnings query had no head filter, so a legacy dated PR could be read and have its body rewritten. The loop now skips any head that is not a docs/auto-sync/<surface> branch, and selftest case 26 covers it.
  • .github/docs-sync/learn.mjs:945 — Accepted: one failed marker PATCH aborted the loop and left the later targets stale. Each target now logs a warning on failure and the remaining targets still publish, and selftest case 27 covers it.
  • sources entries now accept { "repo": "...", "prefix": "..." }; a bare string still means this repository, so the committed map needs no rewrite.
  • Cloud surfaces rank reviewers from the named repository's commit history and check write access there; the workflow needs secret DOCS_SYNC_CLOUD_TOKEN (contents: read on Kilo-Org/cloud), read as CLOUD_REPO_TOKEN. An unreachable history or missing token returns the fixed other pair (fallback: true), still opens the surface pull request, and exits 0.
  • isSurfaceBranch and surfaceNameFromBranch accept only docs/auto-sync/<name>; the bare integration ref and dated docs/auto-sync-<date> refs are rejected.
  • The prepare step no longer comments on or closes legacy rolling pull requests, but still deletes a lingering bare docs/auto-sync ref because a ref cannot be a path prefix of another.
  • Learnings read every open per-surface PR, union their watermark tips, and refresh the processed-through and learned-through markers on skipped surface PRs; the watermark query now sorts by updated-desc.
  • Review surfaces.mjs and reviewers.mjs first; the cloud token and fallback path and the skipped-surface marker refresh are the risky parts.

Computed surface map:

cli, vscode, jetbrains, gateway, web, cloud-mobile, cloud-web, cloud-extension, cloud-agent, other

cloud-mobile    <- Kilo-Org/cloud:apps/mobile/                  docs: packages/kilo-docs/pages/code-with-ai/platforms/mobile.md
cloud-web       <- Kilo-Org/cloud:apps/web/                     docs: packages/kilo-docs/pages/collaborate/
cloud-extension <- Kilo-Org/cloud:apps/extension/               docs: none
cloud-agent     <- Kilo-Org/cloud:packages/cloud-agent-sdk/, Kilo-Org/cloud:packages/cloud-agent-profile/
                                                                docs: packages/kilo-docs/pages/code-with-ai/platforms/cloud-agent.md

E2E proof — log excerpts

offline proof: `.github/docs-sync/selftest.mjs` (repository entry point; rc=0)
case 1: Defect A (mergeOrFallback)
dated branch docs/auto-sync-2026-09-13 does not exist on origin yet; will create it on push
  ok: case1_mergeOrFallback
case 2: Defect B (edit.mjs stderr-on-exit-0)
  ok: case2_defectB
case 2b: AC4a (--auto on every docs-sync kilo run)
  ok: case2b_autoFlag
case 2c: unconditional kilo-stderr-*.log
  ok: case2c_stderrLogAlways
case 2d: redact env secrets from kilo stderr capture
  ok: case2d_redactEnvSecrets
case 2e: prefix-secret ordering (longer value redacted first)
  ok: case2e_prefixSecretOrdering
case 2f: redact env secrets from kilo stdout (triage-raw)
  ok: case2f_redactStdout
case 2g: redact-stream.mjs stdin filter
  ok: case2g_redactStream
case 2h: pending cause has no ANSI escapes
  ok: case2h_pendingCauseIsReadable
case 2i: triage/edit budgets fit at least two units
  ok: case2i_budgetsFitWork
case 3: watermark invariant
  ok: case3_watermark
case 4: routing and round trip
  ok: case4_routing
case 5: re-collection closes the loop
  ok: case5_recollection
case 6: budgets
  ok: case6_budgets
case 7: applyCap
  ok: case7_cap
case 8: triage pass outputs
  ok: case8_triage
case 9: revert interception
  ok: case9_reverts
case 10: learnings
  10a — three commit classes
  10rz — timestamp correlation
  10b — watermark suppression
  10c — rerun idempotency
  10d — contradiction replacement
  10e — prompt injection
  10f — failure path
  10g — general-rule check
  10h — comment trust
  10i — draft gate
  10j — no --auto on extraction call
  10k — hand-mangled file
  10l — empty file fallback
  10m — empty delta marker advance
  10n — non-empty delta marker route
  10o — deleted-in-window rejection
  10p — resolveLearnedThrough + anti-drift
  10q — dry run no live write
  10s — prompt artifacts survive an API failure
  10t — marker PATCH preserves a concurrent body edit
  10u — duplicates inside one delta
  10 — promptBlock format
  10 — parseLearnedThrough
  10 — renderLearnings deterministic order
  ok: case10_learnings
case 11 — per-surface assignee and reviewer calls
  ok: case11_prOwner
case 12 — per-surface segmentation
  ok: case12_surfaceSegmentation
case 13 — one surface's failure is isolated
  ok: case13_surfaceFailureIsolated
case 14 — prepare-branch merges surface branches without a ref collision
  ok: case14_prepareBranchSurfaces
case 15 — updating an open surface PR preserves human commits
  ok: case15_surfaceUpdate
case 16 — a deleted doc file reaches its surface PR
Owner request

Surface: the docs sync GitHub Action (.github/docs-sync/**).

Before you start: reconcile your base

Your branch's declared base is kwf/docs-sync-surface-prs-34e3 (PR 14085) and
GitHub reports your base PR 14089 as CONFLICTING against it. Merge the base
branch into your worktree and resolve the conflicts BEFORE you add anything.
The stack must read mergeable when you are done. Do not open, close or comment
on any pull request: the driver publishes.

Addition 1: the cloud repo's products are surfaces too

The surface map .github/docs-sync/surfaces.json covers only packages in THIS
repository. The company also ships products from Kilo-Org/cloud, and their
documentation lives in this repository under packages/kilo-docs/pages/. Today
every one of those pages falls to the other catch-all, so a mobile or web
docs change is assigned to the other reviewer pair instead of the people who
own the product.

Derive the cloud surfaces the same way the existing map was derived, from the
repository layout. Kilo-Org/cloud is NOT checked out on this machine and must
not be cloned: read its layout through the GitHub API with the gh CLI, which
is already authenticated. Its products are apps/mobile, apps/web,
apps/extension, and the cloud-agent packages under packages/.

Exclusions, by owner policy: Kilo Claw and Kilo Chat are not product surfaces
for this map. Do not add, change or touch any kiloclaw path, any kilo-chat
path, or the kiloclaw docs pages.

Two things make a cloud surface different from a kilocode surface. Handle both:

  1. A source prefix must name its repository. A kilocode surface ranks reviewers
    from this repo's local git history; a cloud surface must rank from the
    Kilo-Org/cloud history, which is only reachable through the GitHub API
    (gh api repos/Kilo-Org/cloud/commits?path=<prefix> or the equivalent
    GraphQL query). Extend the sources entry shape so a prefix carries its
    repo, and keep the existing bare-string entries working as "this repo" so
    the committed map does not have to be rewritten. Keep the existing
    write-access and bot filters for the ranked people.
  2. The job runs in a GitHub Action in this repository and cannot read a private
    sibling repo without a token that grants it. State in the PR body exactly
    which token or permission the workflow needs and where it is set. If the
    cloud history is unreachable at run time, the surface must still get its own
    PR and fall back to the fixed other reviewer pair. It must never fail the
    run and never silently assign the wrong people.

Addition 2: ignore every legacy docs-sync pull request

The previous design opened one rolling PR on a dated branch. Two are still
open: 14043 on docs/auto-sync-2026-09-11 and 13989 on
docs/auto-sync-2026-09-10. The owner will clean these up and no new ones will
be opened.

The job must disregard them completely. It must not comment on them, must not
close them, must not treat one as an integration base, and must not count one
as an existing PR for any surface. Today the job does close and comment on the
previous rolling PR; remove that behaviour.

Only a branch that starts with docs/auto-sync/ (note the trailing slash, the
SURFACE_BRANCH_PREFIX in surfaces.mjs) is one of this job's own PRs. A
dated branch like docs/auto-sync-2026-09-11 shares a prefix up to the
separator, so a startsWith("docs/auto-sync") test matches it by accident.
Prove the distinction in a test.

Acceptance

  • A selftest case maps a docs page for a cloud product to that product's
    surface, not to other, and ranks its reviewers from cloud-repo history.
  • A selftest case proves an unreachable cloud history still opens the surface
    PR with the other reviewer pair and exits 0.
  • A selftest case proves a dated docs/auto-sync-<date> branch and its PR are
    ignored: not commented on, not closed, not reused as a base, not counted.
  • A selftest case proves docs/auto-sync/<surface> is still recognized.
  • node .github/docs-sync/selftest.mjs, surfaces.test.mjs and
    scope.test.mjs all pass, and the PR body quotes the computed surface map
    including the new cloud surfaces.

Comment thread .github/docs-sync/learn.mjs
Comment thread .github/docs-sync/learn.mjs Outdated
@kilo-code-bot

kilo-code-bot Bot commented Sep 13, 2026 •

Copy link
Copy Markdown
Contributor

Code Review Summary

Status: No Issues Found | Recommendation: Merge

Both findings from the previous review are resolved at HEAD, and the incremental diff (.github/docs-sync/learn.mjs, .github/docs-sync/selftest.mjs) adds no new issues.

  • .github/docs-sync/learn.mjs:461-467 — the learnings query now skips any open auto-docs PR whose head is not a docs/auto-sync/<surface> branch, so legacy dated rolling PRs are neither read as targets nor PATCHed. Selftest case 26 covers it.
  • .github/docs-sync/learn.mjs:954-965 — the per-target marker PATCH is wrapped in its own try/catch and warns on failure, so one failed PATCH no longer aborts the remaining targets. Selftest case 27 covers it.
Files Reviewed (2 files)
  • .github/docs-sync/learn.mjs
  • .github/docs-sync/selftest.mjs
Previous Review Summary (commit 989262c)

Current summary above is authoritative. Previous snapshots are kept for context only.

Previous review (commit 989262c)

Status: 2 Issues Found | Recommendation: Address before merge

Overview

Severity Count
CRITICAL 1
WARNING 0
SUGGESTION 1
Issue Details (click to expand)

CRITICAL

File Line Issue
.github/docs-sync/learn.mjs 455 learn.mjs resolves every open auto-docs PR with no docs/auto-sync/<surface> filter, so legacy rolling PRs (e.g. #14043, head docs/auto-sync-2026-09-11) become learning targets and get their bodies PATCHed — defeating the PR's "ignore legacy auto-sync PRs" requirement.

SUGGESTION

File Line Issue
.github/docs-sync/learn.mjs 945 The multi-target marker PATCH loop has no per-target error isolation; one failure aborts the rest, leaving stale markers.
Files Reviewed (11 files)
  • .github/docs-sync/learn.mjs - 2 issues
  • .github/docs-sync/lib.mjs
  • .github/docs-sync/prepare-branch.mjs
  • .github/docs-sync/reviewers.mjs
  • .github/docs-sync/selftest.mjs
  • .github/docs-sync/surfaces.json
  • .github/docs-sync/surfaces.mjs
  • .github/docs-sync/surfaces.test.mjs
  • .github/docs-sync/upsert-pr.mjs
  • .github/docs-sync/watermark.mjs
  • .github/workflows/docs-sync.yml

Fix these issues in Kilo Cloud


Reviewed by deepseek-v4.1-flash · Input: 0 · Output: 0 · Cached: 0

Review guidance: REVIEW.md from base branch main

@iscekic
iscekic changed the base branch from kwf/docs-sync-scope-and-proof-07b7 to main September 13, 2026 18:07
@iscekic iscekic changed the title feat(docs-sync): add cloud product surfaces and ignore legacy auto-sync PRs feat(docs-sync): open per-surface docs PRs, rank reviewers, and cover the cloud product surfaces Sep 13, 2026
@iscekic
iscekic marked this pull request as draft September 13, 2026 18:14
iscekic added a commit that referenced this pull request Sep 13, 2026
@iscekic
iscekic force-pushed the kwf/docs-sync-cloud-surfaces-v2-de1e branch from 989262c to 7374ffa Compare September 13, 2026 18:30
@iscekic
iscekic force-pushed the kwf/docs-sync-cloud-surfaces-v2-de1e branch from 7374ffa to 4e0e56a Compare September 13, 2026 18:33
@iscekic
iscekic marked this pull request as ready for review September 13, 2026 18:40
@iscekic iscekic added the human-ready PR is ready for a human review. label Sep 13, 2026
@iscekic iscekic self-assigned this Sep 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants