Repository navigation
feat(cli): sync-fork --repository-url for the dedicated sync-fork key - #169
Merged
Merged
Conversation
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…-url Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
7 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
osc admin sync-forkalways started with a catalog lookup (GET catalog.svc.<env>/service/<serviceId>) using the platform API key. A caller that holds only the dedicated maker-manager keyAPI_KEY_SYNC_FORKgotinvalid authorization headerand the command exited 0 without syncing.This adds
--repository-url <url>and makes<serviceId>optional ([serviceId]).<serviceId>or--repository-urlis required. Neither or both prints an error and exits 1.https://github.com/<owner>/<repo>[.git]only (no other host, no http, no extra path, query, port or credentials). It is passed on unmodified because maker-manager matches registered repos on the exact string.<serviceId>and no--repository-urlkeep their flow, output and exit codes unchanged (including the existingwaitForOrderremake wait andconsole.log+ exit 0 error handling).--repository-urlpath every failure (sync failed, request error, failed order, timeout) exits non-zero.--waitwith--repository-urlwaitForOrderpollsGET /maker/<orderId>, which the narrow key is rejected on (maker-managerapi_maker.ts: the dedicated key passes auth only forGET /makerwithrepositoryUrlas the sole query parameter). So on this path--waitpollsGET /maker?repositoryUrl=<url>instead (newwaitForRemakeByRepositoryUrlinsyncfork.ts), mirroring client-core semantics: poll every 5s, NEW/PENDING/RUNNING are non-terminal, a 60s grace period (REMAKE_GRACE_MS) to find the order, counted from the moment the sync job is seen as finished. DONE is success; any other terminal phase exits 1.Stale-order handling: the order list is snapshotted (orderId to phase) before the sync is triggered. After the sync an order is accepted only if its orderId is not in the snapshot, or it is in an active phase, or its phase differs from the snapshot. A stale earlier DONE order is therefore never accepted (see the grace heuristic below). The phase comparison is needed because maker-manager rebuilds an existing order under the same orderId (DONE to PENDING). Once an order is accepted, only that orderId is tracked to a terminal phase.
No-change runs: 60s grace heuristic (flagged)
The sync status has no "changed" flag, so the CLI cannot tell "nothing to merge, no remake will follow" from "remake coming". If no new or changed order appears within 60s after the sync job has succeeded,
--waitprintsSync fork succeeded; no remake order appeared within 60s (fork was likely already up to date)and exits 0, so a no-change run does not turn a workflow red. False-success risk: a remake order that only appears after 60s is not waited for. Sync failure and request errors still exit 1.Evidence: HTTP calls on the
--repository-urlpathVerified against
Eyevinn/osaas-maker-manager(src/api_maker.ts,src/sync_fork_key.ts,src/api_sync_fork_scoped.ts).POST maker.svc.<env>/sync-forktriggerSyncForkGET maker.svc.<env>/sync-fork/by-repo?repositoryUrl=getSyncForkStatus,waitForSyncForkGET maker.svc.<env>/maker?repositoryUrl=(sole query param)No catalog call.
GET /maker/<orderId>is not called on this path (asserted in tests). Fields read from the trimmed/makerresponse[{order:{orderId,status:{phase}}}]:order.orderIdandorder.status.phase, both present. An unregistered repository returns 403, which now exits 1 with the message.Platformconstruction (packages/core/src/platform.ts) only readsOSC_API_KEYand throws if missing; it makes no network call, no token or PAT exchange and does not readOSC_ACCESS_TOKEN.Tests
New
packages/cli/src/admin/cmd.syncfork.test.ts(mockscreateFetch, fake timers): catalog skipped with--repository-url; serviceId path still calls catalog; neither/both rejected; invalid URLs rejected (other host, http, missing repo, extra path, lookalike host, query string, not a URL); valid URLs (with and without.git) accepted;--waitpassing path (new order PENDING, RUNNING, DONE, exit 0); rebuild reusing the orderId; failed phase exits 1; no-change run (only stale DONE order) exits 0 after exactly the 60s grace and stops polling; order appearing late inside the grace is waited to DONE; order appearing and failing inside the grace exits 1; sync-fork failure exits 1; request error exits 1; noGET /maker/<id>call. Existing admin tests pass.tsc(admin files) and eslint are clean and prettier was run on the changed files only.Lessons
The by-repo response has no changed flag (status comes only from the K8s Job counters,
osaas-maker-managerprepare_service/provider.ts:846-866) and the remake order is created outside maker-manager, so no-change vs changed is undecidable and the 60s grace is a heuristic.waitForOrderusesGET /maker/<id>, a route outside the dedicated key's scope, so reusing the existing remake wait would have synced and then failed silently (error printed viaconsole.log, exit 0). A rebuild reuses the orderId, so "a new orderId" alone cannot identify the remake order; the phase has to be compared with a pre-trigger snapshot.What a human does next
Release a new
@osaas/cliversion, then inEyevinn/open-livebump the@osaas/clipin in the sync-fork workflow and switch its step toosc --env prod admin sync-fork --repository-url <url> --wait(withOSC_API_KEYset to the dedicated sync-fork key).🤖 Generated with Claude Code
Co-Authored-By: Claude Sonnet 5.5 noreply@anthropic.com