oh-my-opencode 5.1.51 → 5.1.54
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agents/atlas/agent.d.ts +5 -5
- package/dist/agents/dynamic-agent-core-sections.d.ts +0 -1
- package/dist/agents/dynamic-agent-prompt-builder.d.ts +1 -1
- package/dist/agents/gpt-apply-patch-guard.d.ts +0 -1
- package/dist/agents/hephaestus/agent.d.ts +3 -7
- package/dist/agents/hephaestus/model-support.d.ts +6 -0
- package/dist/agents/metis.d.ts +0 -15
- package/dist/agents/native-model-prompt.d.ts +9 -0
- package/dist/agents/native-prompt-frame.d.ts +20 -0
- package/dist/agents/native-tool-snippet.d.ts +6 -0
- package/dist/agents/sisyphus/default.d.ts +0 -1
- package/dist/agents/sisyphus-agent-factory.d.ts +2 -11
- package/dist/agents/sisyphus-junior/agent.d.ts +2 -20
- package/dist/agents/sisyphus-junior/index.d.ts +1 -11
- package/dist/agents/sisyphus-runtime-prompt-reconciler.d.ts +6 -0
- package/dist/agents/types.d.ts +2 -2
- package/dist/cli/index.js +1160 -391
- package/dist/cli/service-auth/credential-lock.d.ts +11 -0
- package/dist/cli/service-auth/credential-owner.d.ts +10 -0
- package/dist/cli/service-auth/index.d.ts +3 -1
- package/dist/cli/service-auth/keystore.d.ts +8 -1
- package/dist/cli/service-auth/owned-refresh.d.ts +21 -0
- package/dist/cli/service-auth/protocol-v2.d.ts +27 -0
- package/dist/cli/service-auth/protocol.d.ts +26 -2
- package/dist/cli/service-auth/recovery-clock.d.ts +7 -0
- package/dist/cli/service-auth/refresh-attempt.d.ts +34 -0
- package/dist/cli/service-auth/session.d.ts +9 -2
- package/dist/cli-node/index.js +1160 -391
- package/dist/hooks/native-edition-nudge/hook.d.ts +3 -4
- package/dist/index.js +15519 -8807
- package/dist/plugin/session-tool-permissions.d.ts +10 -0
- package/dist/plugin/system-transform.d.ts +2 -1
- package/dist/plugin/tool-definition.d.ts +1 -0
- package/dist/shared/bun-ffi-shim.d.ts +29 -0
- package/dist/shared/json-file-cache-store.d.ts +11 -0
- package/dist/skills/browser/runtime/omowright/index.js +24 -33
- package/dist/skills/browser/runtime/omowright/manifest.json +3 -3
- package/dist/skills/frontend/ATTRIBUTION.md +104 -1
- package/dist/skills/frontend/SKILL.md +7 -3
- package/dist/skills/frontend/references/design/design-system-architecture.md +3 -3
- package/dist/skills/frontend/references/perfection/craft-floor.md +59 -0
- package/dist/skills/frontend/references/perfection/detect.md +52 -0
- package/dist/skills/frontend/scripts/detect/cli.ts +70 -0
- package/dist/skills/frontend/scripts/detect/config.test.ts +26 -0
- package/dist/skills/frontend/scripts/detect/config.ts +53 -0
- package/dist/skills/frontend/scripts/detect/core/characters.ts +2 -0
- package/dist/skills/frontend/scripts/detect/core/color.test.ts +29 -0
- package/dist/skills/frontend/scripts/detect/core/color.ts +150 -0
- package/dist/skills/frontend/scripts/detect/core/page.ts +84 -0
- package/dist/skills/frontend/scripts/detect/core/shadow.ts +40 -0
- package/dist/skills/frontend/scripts/detect/core/source.ts +33 -0
- package/dist/skills/frontend/scripts/detect/detect.ts +77 -0
- package/dist/skills/frontend/scripts/detect/index.ts +23 -0
- package/dist/skills/frontend/scripts/detect/lint.test.ts +27 -0
- package/dist/skills/frontend/scripts/detect/lint.ts +98 -0
- package/dist/skills/frontend/scripts/detect/render/probe-placement.test.ts +19 -0
- package/dist/skills/frontend/scripts/detect/render/probe-placement.ts +50 -0
- package/dist/skills/frontend/scripts/detect/render/renderer.ts +37 -0
- package/dist/skills/frontend/scripts/detect/render/webview.ts +71 -0
- package/dist/skills/frontend/scripts/detect/report.ts +29 -0
- package/dist/skills/frontend/scripts/detect/rule.ts +42 -0
- package/dist/skills/frontend/scripts/detect/rules/color/ai-color-palette.test.ts +74 -0
- package/dist/skills/frontend/scripts/detect/rules/color/ai-color-palette.ts +83 -0
- package/dist/skills/frontend/scripts/detect/rules/color/cream-palette.test.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/color/cream-palette.ts +35 -0
- package/dist/skills/frontend/scripts/detect/rules/color/dark-glow.test.ts +47 -0
- package/dist/skills/frontend/scripts/detect/rules/color/dark-glow.ts +44 -0
- package/dist/skills/frontend/scripts/detect/rules/color/design-system-color.test.ts +26 -0
- package/dist/skills/frontend/scripts/detect/rules/color/design-system-color.ts +35 -0
- package/dist/skills/frontend/scripts/detect/rules/color/gradient-text.test.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/color/gradient-text.ts +59 -0
- package/dist/skills/frontend/scripts/detect/rules/color/gray-on-color.test.ts +39 -0
- package/dist/skills/frontend/scripts/detect/rules/color/gray-on-color.ts +38 -0
- package/dist/skills/frontend/scripts/detect/rules/color/index.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/color/low-contrast.test.ts +209 -0
- package/dist/skills/frontend/scripts/detect/rules/color/low-contrast.ts +57 -0
- package/dist/skills/frontend/scripts/detect/rules/color/placeholder-contrast.test.ts +62 -0
- package/dist/skills/frontend/scripts/detect/rules/color/radial-halo.test.ts +40 -0
- package/dist/skills/frontend/scripts/detect/rules/color/radial-halo.ts +31 -0
- package/dist/skills/frontend/scripts/detect/rules/color/radial-spotlight-glow.test.ts +27 -0
- package/dist/skills/frontend/scripts/detect/rules/color/radial-spotlight-glow.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/animation-opacity.ts +78 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/color-path.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/contrast-pairs.ts +54 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/contrast-role.ts +76 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/glow-forms.ts +56 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/gradient-samples.ts +134 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/gradients.ts +91 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/mockup-roots.ts +63 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/page-ignore.ts +7 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/painted-text.ts +141 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/palette-roles.ts +58 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/placeholder-contrast.ts +25 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/stock-accent.ts +31 -0
- package/dist/skills/frontend/scripts/detect/rules/color/support/text-colors.ts +80 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/aphoristic-cadence.test.ts +18 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/aphoristic-cadence.ts +20 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/broken-image.test.ts +25 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/broken-image.ts +17 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/em-dash-overuse.test.ts +39 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/em-dash-overuse.ts +46 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/index.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/marketing-buzzword.test.ts +18 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/marketing-buzzword.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/numbered-section-labels.test.ts +58 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/numbered-section-labels.ts +34 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/repeated-container-text.test.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/repeated-container-text.ts +56 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/script-error.test.ts +48 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/script-error.ts +38 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/skipped-heading.test.ts +49 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/skipped-heading.ts +81 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/support/numbered-label.ts +94 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/support/page-text.ts +37 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/theater-slop-phrase.test.ts +17 -0
- package/dist/skills/frontend/scripts/detect/rules/copy/theater-slop-phrase.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/blinking-cursor.test.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/blinking-cursor.ts +48 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/border-accent-on-rounded.test.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/border-accent-on-rounded.ts +14 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/bounce-easing.test.ts +72 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/bounce-easing.ts +83 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/buried-raster.test.ts +95 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/buried-raster.ts +72 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/codex-grid-background.test.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/codex-grid-background.ts +34 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/design-system-radius.test.ts +37 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/design-system-radius.ts +31 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/gpt-thin-border-wide-shadow.test.ts +59 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/gpt-thin-border-wide-shadow.ts +66 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/hard-offset-shadow.test.ts +45 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/hard-offset-shadow.ts +31 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/hero-eyebrow-chip.test.ts +76 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/hero-eyebrow-chip.ts +19 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/icon-tile-stack.test.ts +67 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/icon-tile-stack.ts +92 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/index.ts +38 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/kicker-above-heading.test.ts +126 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/kicker-above-heading.ts +69 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/marquee.test.ts +63 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/marquee.ts +51 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/organic-clip-path.test.ts +67 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/organic-clip-path.ts +41 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/pulsing-dot.test.ts +58 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/pulsing-dot.ts +72 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/repeating-stripes-gradient.test.ts +26 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/repeating-stripes-gradient.ts +25 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/shape-assembled-illustration.test.ts +59 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/shape-assembled-illustration.ts +58 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/side-tab.test.ts +91 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/side-tab.ts +17 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/appearance.ts +110 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/assert-cases.ts +25 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/borders.ts +150 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/clip-geometry.ts +151 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/css-candidates.ts +66 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/curve-samples.ts +55 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/gradient-pattern.ts +40 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/keyframes.ts +134 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/labels.ts +85 -0
- package/dist/skills/frontend/scripts/detect/rules/decoration/support/raster-state.ts +51 -0
- package/dist/skills/frontend/scripts/detect/rules/index.ts +16 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/body-text-viewport-edge.test.ts +64 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/body-text-viewport-edge.ts +62 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/clipped-overflow-container.test.ts +40 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/clipped-overflow-container.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/content-hidden-at-rest.test.ts +62 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/content-hidden-at-rest.ts +63 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/cramped-padding.test.ts +61 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/cramped-padding.ts +97 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/edge-flush-cards.test.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/edge-flush-cards.ts +47 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/first-viewport-column-overflow.test.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/first-viewport-column-overflow.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/heading-rhythm.test.ts +67 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/heading-rhythm.ts +30 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/index.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/monotonous-spacing.test.ts +19 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/monotonous-spacing.ts +32 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/nested-cards.test.ts +60 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/nested-cards.ts +38 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/straggler.test.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/straggler.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/cards.ts +114 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/clipping.ts +71 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/declared-mockups.ts +46 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/geometry.ts +73 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/hidden-interface.ts +35 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/layout-cases.ts +23 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/line-breaks.ts +32 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/motion.ts +77 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/padding.ts +93 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/support/rhythm.ts +161 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/text-occlusion.test.ts +37 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/text-occlusion.ts +84 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/text-overflow.test.ts +83 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/text-overflow.ts +72 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/unbalanced-heading.test.ts +22 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/unbalanced-heading.ts +22 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/viewport-reflow.test.ts +34 -0
- package/dist/skills/frontend/scripts/detect/rules/layout/viewport-reflow.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/source/ai-color-palette.test.ts +13 -0
- package/dist/skills/frontend/scripts/detect/rules/source/ai-color-palette.ts +11 -0
- package/dist/skills/frontend/scripts/detect/rules/source/aphoristic-cadence.test.ts +12 -0
- package/dist/skills/frontend/scripts/detect/rules/source/aphoristic-cadence.ts +14 -0
- package/dist/skills/frontend/scripts/detect/rules/source/border-accent-on-rounded.test.ts +14 -0
- package/dist/skills/frontend/scripts/detect/rules/source/border-accent-on-rounded.ts +20 -0
- package/dist/skills/frontend/scripts/detect/rules/source/bounce-easing.test.ts +19 -0
- package/dist/skills/frontend/scripts/detect/rules/source/bounce-easing.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/source/broken-image.test.ts +27 -0
- package/dist/skills/frontend/scripts/detect/rules/source/broken-image.ts +16 -0
- package/dist/skills/frontend/scripts/detect/rules/source/codex-grid-background.test.ts +11 -0
- package/dist/skills/frontend/scripts/detect/rules/source/codex-grid-background.ts +18 -0
- package/dist/skills/frontend/scripts/detect/rules/source/dark-glow.test.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/source/dark-glow.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/source/em-dash-overuse.test.ts +13 -0
- package/dist/skills/frontend/scripts/detect/rules/source/em-dash-overuse.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/source/gradient-text.test.ts +12 -0
- package/dist/skills/frontend/scripts/detect/rules/source/gradient-text.ts +11 -0
- package/dist/skills/frontend/scripts/detect/rules/source/gray-on-color.test.ts +20 -0
- package/dist/skills/frontend/scripts/detect/rules/source/gray-on-color.ts +13 -0
- package/dist/skills/frontend/scripts/detect/rules/source/index.ts +19 -0
- package/dist/skills/frontend/scripts/detect/rules/source/marketing-buzzword.test.ts +12 -0
- package/dist/skills/frontend/scripts/detect/rules/source/marketing-buzzword.ts +17 -0
- package/dist/skills/frontend/scripts/detect/rules/source/marquee.test.ts +12 -0
- package/dist/skills/frontend/scripts/detect/rules/source/marquee.ts +12 -0
- package/dist/skills/frontend/scripts/detect/rules/source/monotonous-spacing.test.ts +13 -0
- package/dist/skills/frontend/scripts/detect/rules/source/monotonous-spacing.ts +22 -0
- package/dist/skills/frontend/scripts/detect/rules/source/overused-font.test.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/source/overused-font.ts +16 -0
- package/dist/skills/frontend/scripts/detect/rules/source/radial-halo.test.ts +16 -0
- package/dist/skills/frontend/scripts/detect/rules/source/radial-halo.ts +14 -0
- package/dist/skills/frontend/scripts/detect/rules/source/side-tab.test.ts +29 -0
- package/dist/skills/frontend/scripts/detect/rules/source/side-tab.ts +58 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/accent-scans.ts +78 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/check-source.ts +6 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/corners.ts +105 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/css-effects.ts +81 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/css-scopes.ts +131 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/image-tags.ts +113 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/js-punctuation.ts +34 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/markup-scope.ts +44 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/source-color.ts +42 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/source-shadow.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/source/support/source-text.ts +110 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/all-caps-body.test.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/all-caps-body.ts +15 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/design-system-font-size.test.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/design-system-font-size.ts +23 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/design-system-font.test.ts +22 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/design-system-font.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/extreme-negative-tracking.test.ts +23 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/extreme-negative-tracking.ts +18 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/flat-type-hierarchy.test.ts +33 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/flat-type-hierarchy.ts +26 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/index.ts +21 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/italic-serif-display.test.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/italic-serif-display.ts +24 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/justified-text.test.ts +31 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/justified-text.ts +32 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/line-length.test.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/line-length.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/oversized-h1.test.ts +26 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/oversized-h1.ts +20 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/overused-font.test.ts +35 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/overused-font.ts +45 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/drawn-enlargement.ts +48 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/fading-text.ts +48 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/flex-runs.ts +16 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/font-family.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/painted-text.test.ts +63 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/painted-text.ts +81 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/svg-size.ts +57 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/text-context.ts +112 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/text-lines.ts +43 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/support/type-hierarchy.ts +48 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/tight-leading.test.ts +54 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/tight-leading.ts +47 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/tiny-text.test.ts +60 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/tiny-text.ts +23 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/undersized-ui-text.test.ts +98 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/undersized-ui-text.ts +28 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/wide-tracking.test.ts +26 -0
- package/dist/skills/frontend/scripts/detect/rules/typography/wide-tracking.ts +26 -0
- package/dist/skills/frontend/scripts/detect/snapshot/collect.ts +158 -0
- package/dist/skills/frontend/scripts/detect/snapshot/style-props.ts +25 -0
- package/dist/skills/frontend/scripts/detect/testing/build-snapshot.ts +78 -0
- package/dist/skills/frontend/scripts/detect/tsconfig.json +19 -0
- package/dist/skills/frontend/scripts/detect/types.ts +124 -0
- package/dist/skills/programming/SKILL.md +15 -74
- package/dist/skills/programming/references/go/README.md +1 -1
- package/dist/skills/programming/references/go/bootstrap.md +2 -2
- package/dist/skills/programming/references/python/README.md +4 -4
- package/dist/skills/programming/references/python/one-liners.md +5 -5
- package/dist/skills/programming/references/testing/README.md +82 -0
- package/dist/skills/programming/references/testing/junk-classes.md +56 -0
- package/dist/skills/programming/references/typescript/README.md +1 -2
- package/dist/skills/programming/scripts/go/new-project.ts +197 -0
- package/dist/skills/programming/scripts/python/new-project.ts +231 -0
- package/dist/skills/programming/scripts/python/new-script.ts +134 -0
- package/dist/skills/programming/scripts/rust/new-project.ts +215 -0
- package/dist/skills/programming/scripts/scaffolders.test.ts +96 -0
- package/dist/skills/programming/scripts/shared/run-tool.ts +19 -0
- package/dist/skills/visual-qa/SKILL.md +12 -1
- package/dist/tui.js +128 -39
- package/package.json +20 -19
- package/packages/lsp-core/src/lsp/config-loader.ts +18 -2
- package/packages/lsp-core/src/lsp/host-js-runtime.test.ts +150 -0
- package/packages/lsp-core/src/lsp/host-js-runtime.ts +57 -0
- package/packages/lsp-core/src/lsp/server-definitions.ts +10 -0
- package/packages/lsp-core/src/lsp/server-resolution.ts +9 -1
- package/packages/lsp-core/src/lsp/typescript-server-defaults.test.ts +84 -0
- package/packages/lsp-daemon/dist/cli.js +81 -15
- package/packages/lsp-daemon/dist/client.js +74 -8
- package/packages/lsp-daemon/dist/index.js +76 -10
- package/packages/lsp-tools-mcp/dist/cli.js +74 -8
- package/packages/lsp-tools-mcp/dist/mcp.js +74 -8
- package/packages/lsp-tools-mcp/dist/tools.js +74 -8
- package/packages/omo-codex/plugin/.codex-plugin/plugin.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/dist/cli.js +20 -4
- package/packages/omo-codex/plugin/components/bootstrap/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/package.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/package.json +1 -1
- package/packages/omo-codex/plugin/components/git-bash/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/git-bash/package.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/package.json +1 -1
- package/packages/omo-codex/plugin/components/lsp/dist/.omo-runtime-manifest.json +3 -3
- package/packages/omo-codex/plugin/components/lsp/dist/cli.js +77 -13
- package/packages/omo-codex/plugin/components/lsp/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/lsp/package.json +1 -1
- package/packages/omo-codex/plugin/components/rules/hooks/hooks.json +4 -4
- package/packages/omo-codex/plugin/components/rules/package.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/package.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/dist/cli.js +34 -2
- package/packages/omo-codex/plugin/components/telemetry/dist/posthog.js +34 -2
- package/packages/omo-codex/plugin/components/telemetry/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/package.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/test/codex-hook.test.ts +14 -1
- package/packages/omo-codex/plugin/components/ultrawork/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/package.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-execute-continuation/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-execute-continuation/package.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/hooks/hooks.json +5 -5
- package/packages/omo-codex/plugin/components/ulw-loop/package.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-git-bash-mcp-reminder.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-lsp-diagnostics-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-project-rule-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-comments.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-lsp-diagnostics.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-thread-title-hygiene.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-matching-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-recording-spawn-admission.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-enforcing-unlimited-goal-budget.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-guarding-ulw-loop-spawns.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-recommending-git-bash-mcp.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-auto-update.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-bootstrap-provisioning.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-recording-session-telemetry.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-execute-continuation.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-loop-resume.json +1 -1
- package/packages/omo-codex/plugin/hooks/subagent-stop-verifying-lazycodex-executor-evidence.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ultrawork-trigger.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ulw-loop-steering.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/package-lock.json +12 -12
- package/packages/omo-codex/plugin/package.json +1 -1
- package/packages/omo-codex/plugin/scripts/auto-update-plan.mjs +16 -1
- package/packages/omo-codex/plugin/skills/browser/runtime/omowright/index.js +24 -33
- package/packages/omo-codex/plugin/skills/browser/runtime/omowright/manifest.json +3 -3
- package/packages/omo-codex/plugin/skills/frontend/ATTRIBUTION.md +104 -1
- package/packages/omo-codex/plugin/skills/frontend/SKILL.md +7 -3
- package/packages/omo-codex/plugin/skills/frontend/references/design/design-system-architecture.md +3 -3
- package/packages/omo-codex/plugin/skills/frontend/references/perfection/craft-floor.md +59 -0
- package/packages/omo-codex/plugin/skills/frontend/references/perfection/detect.md +52 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/cli.ts +70 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/config.ts +53 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/core/characters.ts +2 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/core/color.ts +150 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/core/page.ts +84 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/core/shadow.ts +40 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/core/source.ts +33 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/detect.ts +77 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/index.ts +23 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/lint.ts +98 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/render/probe-placement.ts +50 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/render/renderer.ts +37 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/render/webview.ts +71 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/report.ts +29 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rule.ts +42 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/ai-color-palette.ts +83 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/cream-palette.ts +35 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/dark-glow.ts +44 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/design-system-color.ts +35 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/gradient-text.ts +59 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/gray-on-color.ts +38 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/index.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/low-contrast.ts +57 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/radial-halo.ts +31 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/radial-spotlight-glow.ts +33 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/animation-opacity.ts +78 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/color-path.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/contrast-pairs.ts +54 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/contrast-role.ts +76 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/glow-forms.ts +56 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/gradient-samples.ts +134 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/gradients.ts +91 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/mockup-roots.ts +63 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/page-ignore.ts +7 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/painted-text.ts +141 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/palette-roles.ts +58 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/placeholder-contrast.ts +25 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/stock-accent.ts +31 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/color/support/text-colors.ts +80 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/aphoristic-cadence.ts +20 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/broken-image.ts +17 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/em-dash-overuse.ts +46 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/index.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/marketing-buzzword.ts +33 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/numbered-section-labels.ts +34 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/repeated-container-text.ts +56 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/script-error.ts +38 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/skipped-heading.ts +81 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/support/numbered-label.ts +94 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/support/page-text.ts +37 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/copy/theater-slop-phrase.ts +21 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/blinking-cursor.ts +48 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/border-accent-on-rounded.ts +14 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/bounce-easing.ts +83 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/buried-raster.ts +72 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/codex-grid-background.ts +34 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/design-system-radius.ts +31 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/gpt-thin-border-wide-shadow.ts +66 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/hard-offset-shadow.ts +31 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/hero-eyebrow-chip.ts +19 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/icon-tile-stack.ts +92 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/index.ts +38 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/kicker-above-heading.ts +69 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/marquee.ts +51 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/organic-clip-path.ts +41 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/pulsing-dot.ts +72 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/repeating-stripes-gradient.ts +25 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/shape-assembled-illustration.ts +58 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/side-tab.ts +17 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/appearance.ts +110 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/assert-cases.ts +25 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/borders.ts +150 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/clip-geometry.ts +151 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/css-candidates.ts +66 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/curve-samples.ts +55 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/gradient-pattern.ts +40 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/keyframes.ts +134 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/labels.ts +85 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/decoration/support/raster-state.ts +51 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/index.ts +16 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/body-text-viewport-edge.ts +62 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/clipped-overflow-container.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/content-hidden-at-rest.ts +63 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/cramped-padding.ts +97 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/edge-flush-cards.ts +47 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/first-viewport-column-overflow.ts +43 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/heading-rhythm.ts +30 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/index.ts +21 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/monotonous-spacing.ts +32 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/nested-cards.ts +38 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/straggler.ts +28 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/cards.ts +114 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/clipping.ts +71 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/declared-mockups.ts +46 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/geometry.ts +73 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/hidden-interface.ts +35 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/layout-cases.ts +23 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/line-breaks.ts +32 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/motion.ts +77 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/padding.ts +93 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/support/rhythm.ts +161 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/text-occlusion.ts +84 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/text-overflow.ts +72 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/unbalanced-heading.ts +22 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/layout/viewport-reflow.ts +33 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/ai-color-palette.ts +11 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/aphoristic-cadence.ts +14 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/border-accent-on-rounded.ts +20 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/bounce-easing.ts +21 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/broken-image.ts +16 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/codex-grid-background.ts +18 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/dark-glow.ts +21 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/em-dash-overuse.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/gradient-text.ts +11 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/gray-on-color.ts +13 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/index.ts +19 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/marketing-buzzword.ts +17 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/marquee.ts +12 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/monotonous-spacing.ts +22 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/overused-font.ts +16 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/radial-halo.ts +14 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/side-tab.ts +58 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/accent-scans.ts +78 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/check-source.ts +6 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/corners.ts +105 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/css-effects.ts +81 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/css-scopes.ts +131 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/image-tags.ts +113 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/js-punctuation.ts +34 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/markup-scope.ts +44 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/source-color.ts +42 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/source-shadow.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/source/support/source-text.ts +110 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/all-caps-body.ts +15 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/design-system-font-size.ts +23 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/design-system-font.ts +24 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/extreme-negative-tracking.ts +18 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/flat-type-hierarchy.ts +26 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/index.ts +21 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/italic-serif-display.ts +24 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/justified-text.ts +32 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/line-length.ts +28 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/oversized-h1.ts +20 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/overused-font.ts +45 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/drawn-enlargement.ts +48 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/fading-text.ts +48 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/flex-runs.ts +16 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/font-family.ts +28 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/painted-text.ts +81 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/svg-size.ts +57 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/text-context.ts +112 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/text-lines.ts +43 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/support/type-hierarchy.ts +48 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/tight-leading.ts +47 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/tiny-text.ts +23 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/undersized-ui-text.ts +28 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/rules/typography/wide-tracking.ts +26 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/snapshot/collect.ts +158 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/snapshot/style-props.ts +25 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/testing/build-snapshot.ts +78 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/tsconfig.json +19 -0
- package/packages/omo-codex/plugin/skills/frontend/scripts/detect/types.ts +124 -0
- package/packages/omo-codex/plugin/skills/programming/SKILL.md +15 -74
- package/packages/omo-codex/plugin/skills/programming/references/go/README.md +1 -1
- package/packages/omo-codex/plugin/skills/programming/references/go/bootstrap.md +2 -2
- package/packages/omo-codex/plugin/skills/programming/references/python/README.md +4 -4
- package/packages/omo-codex/plugin/skills/programming/references/python/one-liners.md +5 -5
- package/packages/omo-codex/plugin/skills/programming/references/testing/README.md +82 -0
- package/packages/omo-codex/plugin/skills/programming/references/testing/junk-classes.md +56 -0
- package/packages/omo-codex/plugin/skills/programming/references/typescript/README.md +1 -2
- package/packages/omo-codex/plugin/skills/programming/scripts/go/new-project.ts +197 -0
- package/packages/omo-codex/plugin/skills/programming/scripts/python/new-project.ts +231 -0
- package/packages/omo-codex/plugin/skills/programming/scripts/python/new-script.ts +134 -0
- package/packages/omo-codex/plugin/skills/programming/scripts/rust/new-project.ts +215 -0
- package/packages/omo-codex/plugin/skills/programming/scripts/shared/run-tool.ts +19 -0
- package/packages/omo-codex/plugin/skills/visual-qa/SKILL.md +12 -1
- package/packages/omo-codex/plugin/test/auto-update.test.mjs +62 -0
- package/packages/omo-codex/plugin/test/payload-equivalence.test.mjs +12 -2
- package/packages/omo-codex/scripts/install-dist/install-local.mjs +77 -10
- package/packages/shared-skills/skills/browser/runtime/omowright/index.js +24 -33
- package/packages/shared-skills/skills/browser/runtime/omowright/manifest.json +3 -3
- package/packages/shared-skills/skills/frontend/ATTRIBUTION.md +104 -1
- package/packages/shared-skills/skills/frontend/SKILL.md +7 -3
- package/packages/shared-skills/skills/frontend/references/design/design-system-architecture.md +3 -3
- package/packages/shared-skills/skills/frontend/references/perfection/craft-floor.md +59 -0
- package/packages/shared-skills/skills/frontend/references/perfection/detect.md +52 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/cli.ts +70 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/config.test.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/config.ts +53 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/characters.ts +2 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/color.test.ts +29 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/color.ts +150 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/page.ts +84 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/shadow.ts +40 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/core/source.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/detect.ts +77 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/index.ts +23 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/lint.test.ts +27 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/lint.ts +98 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/render/probe-placement.test.ts +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/render/probe-placement.ts +50 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/render/renderer.ts +37 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/render/webview.ts +71 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/report.ts +29 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rule.ts +42 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/ai-color-palette.test.ts +74 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/ai-color-palette.ts +83 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/cream-palette.test.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/cream-palette.ts +35 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/dark-glow.test.ts +47 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/dark-glow.ts +44 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/design-system-color.test.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/design-system-color.ts +35 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/gradient-text.test.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/gradient-text.ts +59 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/gray-on-color.test.ts +39 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/gray-on-color.ts +38 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/index.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/low-contrast.test.ts +209 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/low-contrast.ts +57 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/placeholder-contrast.test.ts +62 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/radial-halo.test.ts +40 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/radial-halo.ts +31 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/radial-spotlight-glow.test.ts +27 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/radial-spotlight-glow.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/animation-opacity.ts +78 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/color-path.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/contrast-pairs.ts +54 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/contrast-role.ts +76 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/glow-forms.ts +56 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/gradient-samples.ts +134 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/gradients.ts +91 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/mockup-roots.ts +63 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/page-ignore.ts +7 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/painted-text.ts +141 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/palette-roles.ts +58 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/placeholder-contrast.ts +25 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/stock-accent.ts +31 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/color/support/text-colors.ts +80 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/aphoristic-cadence.test.ts +18 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/aphoristic-cadence.ts +20 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/broken-image.test.ts +25 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/broken-image.ts +17 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/em-dash-overuse.test.ts +39 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/em-dash-overuse.ts +46 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/index.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/marketing-buzzword.test.ts +18 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/marketing-buzzword.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/numbered-section-labels.test.ts +58 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/numbered-section-labels.ts +34 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/repeated-container-text.test.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/repeated-container-text.ts +56 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/script-error.test.ts +48 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/script-error.ts +38 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/skipped-heading.test.ts +49 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/skipped-heading.ts +81 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/support/numbered-label.ts +94 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/support/page-text.ts +37 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/theater-slop-phrase.test.ts +17 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/copy/theater-slop-phrase.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/blinking-cursor.test.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/blinking-cursor.ts +48 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/border-accent-on-rounded.test.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/border-accent-on-rounded.ts +14 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/bounce-easing.test.ts +72 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/bounce-easing.ts +83 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/buried-raster.test.ts +95 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/buried-raster.ts +72 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/codex-grid-background.test.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/codex-grid-background.ts +34 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/design-system-radius.test.ts +37 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/design-system-radius.ts +31 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/gpt-thin-border-wide-shadow.test.ts +59 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/gpt-thin-border-wide-shadow.ts +66 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/hard-offset-shadow.test.ts +45 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/hard-offset-shadow.ts +31 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/hero-eyebrow-chip.test.ts +76 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/hero-eyebrow-chip.ts +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/icon-tile-stack.test.ts +67 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/icon-tile-stack.ts +92 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/index.ts +38 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/kicker-above-heading.test.ts +126 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/kicker-above-heading.ts +69 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/marquee.test.ts +63 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/marquee.ts +51 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/organic-clip-path.test.ts +67 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/organic-clip-path.ts +41 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/pulsing-dot.test.ts +58 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/pulsing-dot.ts +72 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/repeating-stripes-gradient.test.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/repeating-stripes-gradient.ts +25 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/shape-assembled-illustration.test.ts +59 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/shape-assembled-illustration.ts +58 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/side-tab.test.ts +91 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/side-tab.ts +17 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/appearance.ts +110 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/assert-cases.ts +25 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/borders.ts +150 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/clip-geometry.ts +151 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/css-candidates.ts +66 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/curve-samples.ts +55 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/gradient-pattern.ts +40 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/keyframes.ts +134 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/labels.ts +85 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/decoration/support/raster-state.ts +51 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/index.ts +16 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/body-text-viewport-edge.test.ts +64 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/body-text-viewport-edge.ts +62 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/clipped-overflow-container.test.ts +40 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/clipped-overflow-container.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/content-hidden-at-rest.test.ts +62 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/content-hidden-at-rest.ts +63 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/cramped-padding.test.ts +61 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/cramped-padding.ts +97 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/edge-flush-cards.test.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/edge-flush-cards.ts +47 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/first-viewport-column-overflow.test.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/first-viewport-column-overflow.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/heading-rhythm.test.ts +67 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/heading-rhythm.ts +30 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/index.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/monotonous-spacing.test.ts +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/monotonous-spacing.ts +32 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/nested-cards.test.ts +60 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/nested-cards.ts +38 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/straggler.test.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/straggler.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/cards.ts +114 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/clipping.ts +71 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/declared-mockups.ts +46 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/geometry.ts +73 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/hidden-interface.ts +35 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/layout-cases.ts +23 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/line-breaks.ts +32 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/motion.ts +77 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/padding.ts +93 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/support/rhythm.ts +161 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/text-occlusion.test.ts +37 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/text-occlusion.ts +84 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/text-overflow.test.ts +83 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/text-overflow.ts +72 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/unbalanced-heading.test.ts +22 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/unbalanced-heading.ts +22 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/viewport-reflow.test.ts +34 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/layout/viewport-reflow.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/ai-color-palette.test.ts +13 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/ai-color-palette.ts +11 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/aphoristic-cadence.test.ts +12 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/aphoristic-cadence.ts +14 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/border-accent-on-rounded.test.ts +14 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/border-accent-on-rounded.ts +20 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/bounce-easing.test.ts +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/bounce-easing.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/broken-image.test.ts +27 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/broken-image.ts +16 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/codex-grid-background.test.ts +11 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/codex-grid-background.ts +18 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/dark-glow.test.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/dark-glow.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/em-dash-overuse.test.ts +13 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/em-dash-overuse.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/gradient-text.test.ts +12 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/gradient-text.ts +11 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/gray-on-color.test.ts +20 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/gray-on-color.ts +13 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/index.ts +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/marketing-buzzword.test.ts +12 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/marketing-buzzword.ts +17 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/marquee.test.ts +12 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/marquee.ts +12 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/monotonous-spacing.test.ts +13 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/monotonous-spacing.ts +22 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/overused-font.test.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/overused-font.ts +16 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/radial-halo.test.ts +16 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/radial-halo.ts +14 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/side-tab.test.ts +29 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/side-tab.ts +58 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/accent-scans.ts +78 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/check-source.ts +6 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/corners.ts +105 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/css-effects.ts +81 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/css-scopes.ts +131 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/image-tags.ts +113 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/js-punctuation.ts +34 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/markup-scope.ts +44 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/source-color.ts +42 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/source-shadow.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/source/support/source-text.ts +110 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/all-caps-body.test.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/all-caps-body.ts +15 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/design-system-font-size.test.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/design-system-font-size.ts +23 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/design-system-font.test.ts +22 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/design-system-font.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/extreme-negative-tracking.test.ts +23 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/extreme-negative-tracking.ts +18 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/flat-type-hierarchy.test.ts +33 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/flat-type-hierarchy.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/index.ts +21 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/italic-serif-display.test.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/italic-serif-display.ts +24 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/justified-text.test.ts +31 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/justified-text.ts +32 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/line-length.test.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/line-length.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/oversized-h1.test.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/oversized-h1.ts +20 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/overused-font.test.ts +35 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/overused-font.ts +45 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/drawn-enlargement.ts +48 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/fading-text.ts +48 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/flex-runs.ts +16 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/font-family.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/painted-text.test.ts +63 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/painted-text.ts +81 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/svg-size.ts +57 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/text-context.ts +112 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/text-lines.ts +43 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/support/type-hierarchy.ts +48 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/tight-leading.test.ts +54 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/tight-leading.ts +47 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/tiny-text.test.ts +60 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/tiny-text.ts +23 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/undersized-ui-text.test.ts +98 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/undersized-ui-text.ts +28 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/wide-tracking.test.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/rules/typography/wide-tracking.ts +26 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/snapshot/collect.ts +158 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/snapshot/style-props.ts +25 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/testing/build-snapshot.ts +78 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/tsconfig.json +19 -0
- package/packages/shared-skills/skills/frontend/scripts/detect/types.ts +124 -0
- package/packages/shared-skills/skills/programming/SKILL.md +15 -74
- package/packages/shared-skills/skills/programming/references/go/README.md +1 -1
- package/packages/shared-skills/skills/programming/references/go/bootstrap.md +2 -2
- package/packages/shared-skills/skills/programming/references/python/README.md +4 -4
- package/packages/shared-skills/skills/programming/references/python/one-liners.md +5 -5
- package/packages/shared-skills/skills/programming/references/testing/README.md +82 -0
- package/packages/shared-skills/skills/programming/references/testing/junk-classes.md +56 -0
- package/packages/shared-skills/skills/programming/references/typescript/README.md +1 -2
- package/packages/shared-skills/skills/programming/scripts/go/new-project.ts +197 -0
- package/packages/shared-skills/skills/programming/scripts/python/new-project.ts +231 -0
- package/packages/shared-skills/skills/programming/scripts/python/new-script.ts +134 -0
- package/packages/shared-skills/skills/programming/scripts/rust/new-project.ts +215 -0
- package/packages/shared-skills/skills/programming/scripts/scaffolders.test.ts +96 -0
- package/packages/shared-skills/skills/programming/scripts/shared/run-tool.ts +19 -0
- package/packages/shared-skills/skills/visual-qa/SKILL.md +12 -1
- package/dist/agents/gpt-prompt-identity.d.ts +0 -3
- package/dist/agents/hephaestus/gpt-5-4.d.ts +0 -24
- package/dist/agents/hephaestus/gpt-5-5.d.ts +0 -2
- package/dist/agents/hephaestus/gpt-5-6.d.ts +0 -2
- package/dist/agents/kimi-tool-loop-guard.d.ts +0 -1
- package/dist/agents/sisyphus/claude-fable-5.d.ts +0 -19
- package/dist/agents/sisyphus/claude-opus-4-7.d.ts +0 -22
- package/dist/agents/sisyphus/claude-opus-4-8.d.ts +0 -19
- package/dist/agents/sisyphus/claude-opus-5.d.ts +0 -33
- package/dist/agents/sisyphus/gemini.d.ts +0 -20
- package/dist/agents/sisyphus/glm-5-2.d.ts +0 -4
- package/dist/agents/sisyphus/gpt-5-4.d.ts +0 -26
- package/dist/agents/sisyphus/gpt-5-5.d.ts +0 -6
- package/dist/agents/sisyphus/gpt-task-system-guide.d.ts +0 -1
- package/dist/agents/sisyphus/grok-4.d.ts +0 -21
- package/dist/agents/sisyphus/index.d.ts +0 -31
- package/dist/agents/sisyphus/kimi-k2-6.d.ts +0 -32
- package/dist/agents/sisyphus/kimi-k2-7.d.ts +0 -17
- package/dist/agents/sisyphus/kimi-k3-1.d.ts +0 -9
- package/dist/agents/sisyphus/kimi-k3.d.ts +0 -19
- package/dist/agents/sisyphus-dynamic-prompt-builder.d.ts +0 -2
- package/dist/agents/sisyphus-dynamic-prompt-execution.d.ts +0 -2
- package/dist/agents/sisyphus-dynamic-prompt-exploration.d.ts +0 -2
- package/dist/agents/sisyphus-dynamic-prompt-role.d.ts +0 -2
- package/dist/agents/sisyphus-dynamic-prompt-sections.d.ts +0 -18
- package/dist/agents/sisyphus-dynamic-prompt-style.d.ts +0 -2
- package/dist/agents/sisyphus-dynamic-prompt.d.ts +0 -3
- package/dist/agents/sisyphus-gemini-fallback-overrides.d.ts +0 -1
- package/dist/agents/sisyphus-junior/gemini.d.ts +0 -10
- package/dist/agents/sisyphus-junior/glm-5-2.d.ts +0 -1
- package/dist/agents/sisyphus-junior/gpt-5-4.d.ts +0 -11
- package/dist/agents/sisyphus-junior/gpt-5-5.d.ts +0 -5
- package/dist/agents/sisyphus-junior/gpt.d.ts +0 -9
- package/dist/agents/sisyphus-junior/kimi-k2-6.d.ts +0 -13
- package/dist/agents/sisyphus-junior/kimi-k2-7.d.ts +0 -11
- package/dist/agents/sisyphus-junior/kimi-k3-1.d.ts +0 -6
- package/dist/agents/sisyphus-junior/kimi-k3.d.ts +0 -12
- package/dist/features/claude-code-agent-loader/opencode-config-agents-reader.d.ts +0 -1
- package/dist/features/claude-code-command-loader/loader-cache.d.ts +0 -1
- package/dist/features/claude-code-command-loader/loader.d.ts +0 -1
- package/dist/features/opencode-skill-loader/config-source-discovery.d.ts +0 -1
- package/dist/features/opencode-skill-loader/merger/config-skill-entry-loader.d.ts +0 -1
- package/dist/features/opencode-skill-loader/opencode-config-skills-reader.d.ts +0 -1
- package/dist/features/team-mode/team-layout-tmux/resolve-caller-tmux-session.d.ts +0 -1
- package/dist/features/team-mode/team-registry/team-spec-input-normalizer.d.ts +0 -1
- package/dist/shared/git-worktree/collect-git-diff-stats.d.ts +0 -1
- package/dist/shared/git-worktree/parse-status-porcelain-line.d.ts +0 -1
- package/dist/shared/migration/agent-names.d.ts +0 -1
- package/dist/shared/migration/migrations-sidecar.d.ts +0 -1
- package/dist/shared/skill-path-resolver.d.ts +0 -1
- package/dist/shared/zip-entry-listing/powershell-zip-entry-listing.d.ts +0 -1
- package/dist/shared/zip-entry-listing/zipinfo-zip-entry-listing.d.ts +0 -1
- package/dist/skills/programming/scripts/go/new-project.py +0 -138
- package/dist/skills/programming/scripts/python/new-project.py +0 -172
- package/dist/skills/programming/scripts/python/new-script.py +0 -116
- package/dist/skills/programming/scripts/rust/new-project.py +0 -178
- package/packages/omo-codex/plugin/skills/programming/scripts/go/new-project.py +0 -138
- package/packages/omo-codex/plugin/skills/programming/scripts/python/new-project.py +0 -172
- package/packages/omo-codex/plugin/skills/programming/scripts/python/new-script.py +0 -116
- package/packages/omo-codex/plugin/skills/programming/scripts/rust/new-project.py +0 -178
- package/packages/shared-skills/skills/programming/scripts/go/new-project.py +0 -138
- package/packages/shared-skills/skills/programming/scripts/python/new-project.py +0 -172
- package/packages/shared-skills/skills/programming/scripts/python/new-script.py +0 -116
- package/packages/shared-skills/skills/programming/scripts/rust/new-project.py +0 -178
package/dist/cli/index.js
CHANGED
|
@@ -2132,7 +2132,7 @@ var package_default;
|
|
|
2132
2132
|
var init_package = __esm(() => {
|
|
2133
2133
|
package_default = {
|
|
2134
2134
|
name: "oh-my-opencode",
|
|
2135
|
-
version: "5.1.
|
|
2135
|
+
version: "5.1.54",
|
|
2136
2136
|
description: "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
|
|
2137
2137
|
main: "./dist/index.js",
|
|
2138
2138
|
types: "dist/index.d.ts",
|
|
@@ -2274,14 +2274,15 @@ var init_package = __esm(() => {
|
|
|
2274
2274
|
prepublishOnly: "bun run clean && bun run build:lsp-tools-mcp && bun run build:lsp-daemon && bun run build",
|
|
2275
2275
|
"test:model-capabilities": "bun test --timeout 20000 packages/model-core/src/model-capability-aliases.test.ts packages/model-core/src/model-capability-guardrails.test.ts packages/model-core/src/model-capabilities.test.ts packages/omo-opencode/src/cli/doctor/checks/model-resolution.test.ts --bail",
|
|
2276
2276
|
"check:copy": "bun script/check-copy.ts",
|
|
2277
|
-
typecheck: "bun run check:copy &&
|
|
2278
|
-
"typecheck:
|
|
2279
|
-
"typecheck:
|
|
2277
|
+
typecheck: "bun run check:copy && bun check --no-script --all -p tsconfig.json && bun run typecheck:script && bun run typecheck:packages && bun run typecheck:skill-scripts",
|
|
2278
|
+
"typecheck:skill-scripts": "bun check --no-script --all -p packages/shared-skills/skills/frontend/scripts/detect/tsconfig.json",
|
|
2279
|
+
"typecheck:packages": "bun check --no-script --all -p packages/rules-engine/tsconfig.json && bun check --no-script --all -p packages/delegate-core/tsconfig.json && bun check --no-script --all -p packages/mcp-stdio-core/tsconfig.json && bun check --no-script --all -p packages/mcp-client-core/tsconfig.json && bun check --no-script --all -p packages/git-bash-mcp/tsconfig.json && bun check --no-script --all -p packages/ast-grep-mcp/tsconfig.json && bun check --no-script --all -p packages/lsp-core/tsconfig.json && bun check --no-script --all -p packages/utils/tsconfig.json && bun check --no-script --all -p packages/model-core/tsconfig.json && bun check --no-script --all -p packages/omo-config-core/tsconfig.json && bun check --no-script --all -p packages/prompts-core/tsconfig.json && bun check --no-script --all -p packages/comment-checker-core/tsconfig.json && bun check --no-script --all -p packages/hashline-core/tsconfig.json && bun check --no-script --all -p packages/tmux-core/tsconfig.json && bun check --no-script --all -p packages/team-core/tsconfig.json && bun check --no-script --all -p packages/openclaw-core/tsconfig.json && bun check --no-script --all -p packages/boulder-state/tsconfig.json && bun check --no-script --all -p packages/isolation-core/tsconfig.json && bun check --no-script --all -p packages/memory-core/tsconfig.json && bun check --no-script --all -p packages/telemetry-core/tsconfig.json && bun check --no-script --all -p packages/claude-code-compat-core/tsconfig.json && bun check --no-script --all -p packages/skills-loader-core/tsconfig.json && bun check --no-script --all -p packages/agents-md-core/tsconfig.json && bun check --no-script --all -p packages/omo-codex/plugin/shared/tsconfig.json && bun check --no-script --all -p packages/omo-codex/tsconfig.json && bun check --no-script --all -p packages/omo-senpi/tsconfig.json && bun check --no-script --all -p packages/senpi-task/tsconfig.json && bun check --no-script --all -p packages/omo-opencode/tsconfig.json && bun check --no-script --all -p packages/omo-native/tsconfig.json && bun check --no-script --all -p packages/senpi-desktop-protocol/tsconfig.json && bun check --no-script --all -p packages/senpi-desktop-engine/tsconfig.json && bun check --no-script --all -p packages/senpi-desktop-prelude/tsconfig.json && bun check --no-script --all -p packages/senpi-desktop-service/tsconfig.json && bun check --no-script --all -p packages/senpi-desktop-tool/tsconfig.json",
|
|
2280
|
+
"typecheck:script": "bun check --no-script --all -p script/tsconfig.json",
|
|
2280
2281
|
test: "bun test --timeout 20000",
|
|
2281
2282
|
"changelog:section": "bun script/changelog-section.ts",
|
|
2282
2283
|
"test:codex": "bun run build:codex-install && bun run build:git-bash-mcp && bun run build:lsp-tools-mcp && bun run build:lsp-daemon && npm --prefix packages/lsp-tools-mcp test && npm --prefix packages/omo-codex/plugin ci && npm --prefix packages/omo-codex/plugin/components/ulw-loop test && bun run --cwd packages/omo-codex/plugin build && node scripts/check-third-party-notices.mjs --ship && bun test --timeout 20000 packages/omo-opencode/src/cli/cli-installer.platform.test.ts packages/omo-codex/src/install/codex-cache.test.ts packages/omo-codex/src/install/codex-cleanup.test.ts packages/omo-codex/src/install/codex-config-agent-cleanup.test.ts packages/omo-codex/src/install/codex-config-autonomous-features.test.ts packages/omo-codex/src/install/codex-config-reasoning.test.ts packages/omo-codex/src/install/codex-config-toml.test.ts packages/omo-codex/src/install/codex-project-local-cleanup.test.ts packages/omo-codex/src/install/install-codex-project-local-cleanup.test.ts packages/omo-codex/src/install/install-codex.test.ts packages/omo-codex/src/install/install-codex-packaged.test.ts packages/omo-codex/src/install/link-cached-plugin-agents.test.ts packages/omo-codex/src/**/*.test.ts packages/utils/src/jsonc-parser.test.ts packages/utils/src/frontmatter.test.ts packages/hashline-core/src/hash-computation.test.ts packages/hashline-core/src/smoke-untested-modules.test.ts packages/rules-engine/src/index.test.ts packages/rules-engine/src/security-boundary.test.ts packages/agents-md-core/src/injector.test.ts packages/omo-codex/plugin/components/lsp/test/package-smoke.test.ts && node --test packages/omo-codex/plugin/test/*.test.mjs packages/omo-codex/scripts/install-cache-copy.test.mjs packages/omo-codex/scripts/install-cli-args.test.mjs packages/omo-codex/scripts/install-delegated-command.test.mjs packages/omo-codex/scripts/install-config-autonomous-features.test.mjs packages/omo-codex/scripts/install-config-autonomous.test.mjs packages/omo-codex/scripts/install-config-reasoning.test.mjs packages/omo-codex/scripts/install-config.test.mjs packages/omo-codex/scripts/install-hook-targets.test.mjs packages/omo-codex/scripts/install-project-local-cleanup.test.mjs packages/omo-codex/scripts/install-lazycodex-version-stamp.test.mjs packages/omo-codex/scripts/install-local-entrypoint.test.mjs packages/omo-codex/scripts/install-local-git-bash-preflight.test.mjs packages/omo-codex/scripts/install-local.test.mjs packages/omo-codex/scripts/install-marketplace-cache.test.mjs packages/omo-codex/scripts/install-mcp-context7-runtime.test.mjs packages/omo-codex/scripts/install-mcp-runtime.test.mjs packages/omo-codex/scripts/install-packaged-local.test.mjs packages/omo-codex/scripts/install-generated-bundle.test.mjs packages/omo-codex/scripts/install-agent-links.test.mjs packages/omo-codex/scripts/install-bin-links.test.mjs",
|
|
2283
2284
|
"test:fast": "bun run script/test-fast.ts",
|
|
2284
|
-
"test:senpi": "bun run build:senpi-plugin &&
|
|
2285
|
+
"test:senpi": "bun run build:senpi-plugin && bun check --no-script --all -p packages/omo-senpi/tsconfig.json && bun test --timeout 20000 packages/omo-senpi && bun test ./.agents/skills/senpi-qa/scripts/resolve-evidence-dir.test.mjs",
|
|
2285
2286
|
"test:windows-codex": "bun run test:codex",
|
|
2286
2287
|
"build:git-bash-mcp": "bun run --cwd packages/git-bash-mcp build",
|
|
2287
2288
|
"build:ast-grep-mcp": "bun run --cwd packages/ast-grep-mcp build",
|
|
@@ -2317,7 +2318,7 @@ var init_package = __esm(() => {
|
|
|
2317
2318
|
},
|
|
2318
2319
|
devDependencies: {
|
|
2319
2320
|
"@clack/prompts": "^1.8.1",
|
|
2320
|
-
"@code-yeongyu/senpi": "2026.10.
|
|
2321
|
+
"@code-yeongyu/senpi": "2026.10.30-1",
|
|
2321
2322
|
"@modelcontextprotocol/sdk": "^1.30.0",
|
|
2322
2323
|
"@oh-my-opencode/agents-md-core": "workspace:*",
|
|
2323
2324
|
"@oh-my-opencode/ast-grep-mcp": "workspace:*",
|
|
@@ -2371,7 +2372,7 @@ var init_package = __esm(() => {
|
|
|
2371
2372
|
"jsonc-parser": "^3.3.1",
|
|
2372
2373
|
knip: "6.43.0",
|
|
2373
2374
|
"node-pty": "^1.1.0",
|
|
2374
|
-
omowright: "github:code-yeongyu/omowright#
|
|
2375
|
+
omowright: "github:code-yeongyu/omowright#c06d20337ad942b09dea8757a45f6c848008a68d",
|
|
2375
2376
|
"oxc-parser": "0.148.0",
|
|
2376
2377
|
oxlint: "1.89.0",
|
|
2377
2378
|
picocolors: "^1.1.1",
|
|
@@ -2381,18 +2382,18 @@ var init_package = __esm(() => {
|
|
|
2381
2382
|
typescript: "^7.0.2"
|
|
2382
2383
|
},
|
|
2383
2384
|
optionalDependencies: {
|
|
2384
|
-
"oh-my-opencode-darwin-arm64": "5.1.
|
|
2385
|
-
"oh-my-opencode-darwin-x64": "5.1.
|
|
2386
|
-
"oh-my-opencode-darwin-x64-baseline": "5.1.
|
|
2387
|
-
"oh-my-opencode-linux-arm64": "5.1.
|
|
2388
|
-
"oh-my-opencode-linux-arm64-musl": "5.1.
|
|
2389
|
-
"oh-my-opencode-linux-x64": "5.1.
|
|
2390
|
-
"oh-my-opencode-linux-x64-baseline": "5.1.
|
|
2391
|
-
"oh-my-opencode-linux-x64-musl": "5.1.
|
|
2392
|
-
"oh-my-opencode-linux-x64-musl-baseline": "5.1.
|
|
2393
|
-
"oh-my-opencode-windows-arm64": "5.1.
|
|
2394
|
-
"oh-my-opencode-windows-x64": "5.1.
|
|
2395
|
-
"oh-my-opencode-windows-x64-baseline": "5.1.
|
|
2385
|
+
"oh-my-opencode-darwin-arm64": "5.1.54",
|
|
2386
|
+
"oh-my-opencode-darwin-x64": "5.1.54",
|
|
2387
|
+
"oh-my-opencode-darwin-x64-baseline": "5.1.54",
|
|
2388
|
+
"oh-my-opencode-linux-arm64": "5.1.54",
|
|
2389
|
+
"oh-my-opencode-linux-arm64-musl": "5.1.54",
|
|
2390
|
+
"oh-my-opencode-linux-x64": "5.1.54",
|
|
2391
|
+
"oh-my-opencode-linux-x64-baseline": "5.1.54",
|
|
2392
|
+
"oh-my-opencode-linux-x64-musl": "5.1.54",
|
|
2393
|
+
"oh-my-opencode-linux-x64-musl-baseline": "5.1.54",
|
|
2394
|
+
"oh-my-opencode-windows-arm64": "5.1.54",
|
|
2395
|
+
"oh-my-opencode-windows-x64": "5.1.54",
|
|
2396
|
+
"oh-my-opencode-windows-x64-baseline": "5.1.54"
|
|
2396
2397
|
},
|
|
2397
2398
|
overrides: {
|
|
2398
2399
|
hono: "^4.13.8",
|
|
@@ -8055,7 +8056,8 @@ var init_latest_models = __esm(() => {
|
|
|
8055
8056
|
gptLunaFast: "gpt-6-luna-fast",
|
|
8056
8057
|
glm: "glm-5.3",
|
|
8057
8058
|
glmFlash: "glm-5.3-flash",
|
|
8058
|
-
kimi: "kimi-k3",
|
|
8059
|
+
kimi: "kimi-k3.1-pro",
|
|
8060
|
+
kimiK3: "kimi-k3",
|
|
8059
8061
|
geminiPro: "gemini-4-argon"
|
|
8060
8062
|
};
|
|
8061
8063
|
});
|
|
@@ -9378,9 +9380,13 @@ var init_agent_model_requirements = __esm(() => {
|
|
|
9378
9380
|
variant: "max"
|
|
9379
9381
|
},
|
|
9380
9382
|
{
|
|
9381
|
-
providers: ["opencode-go", "kimi-for-coding", "moonshotai", "
|
|
9383
|
+
providers: ["opencode-go", "kimi-for-coding", "moonshotai", "moonshotai-cn"],
|
|
9382
9384
|
model: LATEST_MODEL_BY_FAMILY.kimi
|
|
9383
9385
|
},
|
|
9386
|
+
{
|
|
9387
|
+
providers: ["opencode", "bailian-coding-plan", "firmware", "ollama-cloud", "aihubmix"],
|
|
9388
|
+
model: LATEST_MODEL_BY_FAMILY.kimiK3
|
|
9389
|
+
},
|
|
9384
9390
|
{
|
|
9385
9391
|
providers: ["openai", "chatgpt-subscription", "github-copilot", "opencode"],
|
|
9386
9392
|
model: "gpt-5.6-sol",
|
|
@@ -9475,10 +9481,11 @@ var init_agent_model_requirements = __esm(() => {
|
|
|
9475
9481
|
variant: "max"
|
|
9476
9482
|
},
|
|
9477
9483
|
{
|
|
9478
|
-
providers: ["opencode-go", "kimi-for-coding", "moonshotai"
|
|
9484
|
+
providers: ["opencode-go", "kimi-for-coding", "moonshotai"],
|
|
9479
9485
|
model: LATEST_MODEL_BY_FAMILY.kimi,
|
|
9480
9486
|
variant: "max"
|
|
9481
|
-
}
|
|
9487
|
+
},
|
|
9488
|
+
{ providers: ["opencode"], model: LATEST_MODEL_BY_FAMILY.kimiK3, variant: "max" }
|
|
9482
9489
|
])
|
|
9483
9490
|
},
|
|
9484
9491
|
metis: {
|
|
@@ -9499,10 +9506,11 @@ var init_agent_model_requirements = __esm(() => {
|
|
|
9499
9506
|
variant: "max"
|
|
9500
9507
|
},
|
|
9501
9508
|
{
|
|
9502
|
-
providers: ["opencode-go", "kimi-for-coding", "moonshotai"
|
|
9509
|
+
providers: ["opencode-go", "kimi-for-coding", "moonshotai"],
|
|
9503
9510
|
model: LATEST_MODEL_BY_FAMILY.kimi,
|
|
9504
9511
|
variant: "max"
|
|
9505
|
-
}
|
|
9512
|
+
},
|
|
9513
|
+
{ providers: ["opencode"], model: LATEST_MODEL_BY_FAMILY.kimiK3, variant: "max" }
|
|
9506
9514
|
])
|
|
9507
9515
|
},
|
|
9508
9516
|
momus: {
|
|
@@ -9585,10 +9593,11 @@ var init_category_model_requirements = __esm(() => {
|
|
|
9585
9593
|
variant: "max"
|
|
9586
9594
|
},
|
|
9587
9595
|
{
|
|
9588
|
-
providers: ["kimi-for-coding", "moonshotai", "opencode-go"
|
|
9596
|
+
providers: ["kimi-for-coding", "moonshotai", "opencode-go"],
|
|
9589
9597
|
model: LATEST_MODEL_BY_FAMILY.kimi,
|
|
9590
9598
|
variant: "max"
|
|
9591
|
-
}
|
|
9599
|
+
},
|
|
9600
|
+
{ providers: ["opencode"], model: LATEST_MODEL_BY_FAMILY.kimiK3, variant: "max" }
|
|
9592
9601
|
])
|
|
9593
9602
|
},
|
|
9594
9603
|
ultrabrain: {
|
|
@@ -9640,10 +9649,11 @@ var init_category_model_requirements = __esm(() => {
|
|
|
9640
9649
|
variant: "max"
|
|
9641
9650
|
},
|
|
9642
9651
|
{
|
|
9643
|
-
providers: ["kimi-for-coding", "moonshotai", "opencode-go"
|
|
9652
|
+
providers: ["kimi-for-coding", "moonshotai", "opencode-go"],
|
|
9644
9653
|
model: LATEST_MODEL_BY_FAMILY.kimi,
|
|
9645
9654
|
variant: "max"
|
|
9646
|
-
}
|
|
9655
|
+
},
|
|
9656
|
+
{ providers: ["opencode"], model: LATEST_MODEL_BY_FAMILY.kimiK3, variant: "max" }
|
|
9647
9657
|
])
|
|
9648
9658
|
},
|
|
9649
9659
|
quick: {
|
|
@@ -9706,10 +9716,11 @@ var init_category_model_requirements = __esm(() => {
|
|
|
9706
9716
|
},
|
|
9707
9717
|
{ providers: ["zai-coding-plan", "opencode-go"], model: LATEST_MODEL_BY_FAMILY.glm, variant: "max" },
|
|
9708
9718
|
{
|
|
9709
|
-
providers: ["kimi-for-coding", "moonshotai", "opencode-go"
|
|
9719
|
+
providers: ["kimi-for-coding", "moonshotai", "opencode-go"],
|
|
9710
9720
|
model: LATEST_MODEL_BY_FAMILY.kimi,
|
|
9711
9721
|
variant: "max"
|
|
9712
|
-
}
|
|
9722
|
+
},
|
|
9723
|
+
{ providers: ["opencode"], model: LATEST_MODEL_BY_FAMILY.kimiK3, variant: "max" }
|
|
9713
9724
|
]
|
|
9714
9725
|
},
|
|
9715
9726
|
writing: {
|
|
@@ -10273,7 +10284,7 @@ function transformModelForProviderDisplay(provider, model) {
|
|
|
10273
10284
|
var CLAUDE_VERSION_DOT, GEMINI_31_PRO_PREVIEW, GEMINI_3_FLASH_PREVIEW;
|
|
10274
10285
|
var init_provider_model_id_transform = __esm(() => {
|
|
10275
10286
|
CLAUDE_VERSION_DOT = /claude-(\w+)-(\d+)-(\d+)/g;
|
|
10276
|
-
GEMINI_31_PRO_PREVIEW = /gemini-3\.1-pro(?!-)/g;
|
|
10287
|
+
GEMINI_31_PRO_PREVIEW = /(?<!antigravity-)gemini-3\.1-pro(?!-)/g;
|
|
10277
10288
|
GEMINI_3_FLASH_PREVIEW = /(?<!antigravity-)gemini-3-flash(?!-)/g;
|
|
10278
10289
|
});
|
|
10279
10290
|
|
|
@@ -10347,6 +10358,36 @@ var init_supplemental_entries = __esm(() => {
|
|
|
10347
10358
|
output: 262144
|
|
10348
10359
|
}
|
|
10349
10360
|
},
|
|
10361
|
+
"kimi-k3.1-pro": {
|
|
10362
|
+
id: "kimi-k3.1-pro",
|
|
10363
|
+
family: "kimi",
|
|
10364
|
+
reasoning: true,
|
|
10365
|
+
temperature: true,
|
|
10366
|
+
toolCall: true,
|
|
10367
|
+
modalities: {
|
|
10368
|
+
input: ["text", "image", "video"],
|
|
10369
|
+
output: ["text"]
|
|
10370
|
+
},
|
|
10371
|
+
limit: {
|
|
10372
|
+
context: 1048576,
|
|
10373
|
+
output: 1048576
|
|
10374
|
+
}
|
|
10375
|
+
},
|
|
10376
|
+
"kimi-k3.1-pro-highspeed": {
|
|
10377
|
+
id: "kimi-k3.1-pro-highspeed",
|
|
10378
|
+
family: "kimi",
|
|
10379
|
+
reasoning: true,
|
|
10380
|
+
temperature: true,
|
|
10381
|
+
toolCall: true,
|
|
10382
|
+
modalities: {
|
|
10383
|
+
input: ["text", "image", "video"],
|
|
10384
|
+
output: ["text"]
|
|
10385
|
+
},
|
|
10386
|
+
limit: {
|
|
10387
|
+
context: 1048576,
|
|
10388
|
+
output: 1048576
|
|
10389
|
+
}
|
|
10390
|
+
},
|
|
10350
10391
|
"kimi-k2.6": {
|
|
10351
10392
|
id: "kimi-k2.6",
|
|
10352
10393
|
family: "kimi",
|
|
@@ -12431,6 +12472,33 @@ function createJsonFileCacheStore(options) {
|
|
|
12431
12472
|
});
|
|
12432
12473
|
}
|
|
12433
12474
|
}
|
|
12475
|
+
function writeIfChanged(value) {
|
|
12476
|
+
ensureCacheDir();
|
|
12477
|
+
const cacheFile = getCacheFilePath();
|
|
12478
|
+
const serialized = options.serialize?.(value) ?? JSON.stringify(value, null, 2);
|
|
12479
|
+
try {
|
|
12480
|
+
const existing = existsSync10(cacheFile) ? readFileSync3(cacheFile, "utf-8") : undefined;
|
|
12481
|
+
const unchanged = existing !== undefined && (existing === serialized || options.comparable !== undefined && JSON.stringify(options.comparable(JSON.parse(existing))) === JSON.stringify(options.comparable(value)));
|
|
12482
|
+
if (unchanged) {
|
|
12483
|
+
memoryValue = value;
|
|
12484
|
+
writtenInCurrentProcess = true;
|
|
12485
|
+
log2(`[${options.logPrefix}] ${options.cacheLabel} unchanged; skipped write`, options.describe(value));
|
|
12486
|
+
return false;
|
|
12487
|
+
}
|
|
12488
|
+
} catch {}
|
|
12489
|
+
try {
|
|
12490
|
+
writeFileSync4(cacheFile, serialized);
|
|
12491
|
+
memoryValue = value;
|
|
12492
|
+
writtenInCurrentProcess = true;
|
|
12493
|
+
log2(`[${options.logPrefix}] ${options.cacheLabel} written`, options.describe(value));
|
|
12494
|
+
return true;
|
|
12495
|
+
} catch (error) {
|
|
12496
|
+
log2(`[${options.logPrefix}] Error writing ${toLogLabel(options.cacheLabel)}`, {
|
|
12497
|
+
error: String(error)
|
|
12498
|
+
});
|
|
12499
|
+
return false;
|
|
12500
|
+
}
|
|
12501
|
+
}
|
|
12434
12502
|
function resetMemory() {
|
|
12435
12503
|
memoryValue = undefined;
|
|
12436
12504
|
writtenInCurrentProcess = false;
|
|
@@ -12439,6 +12507,7 @@ function createJsonFileCacheStore(options) {
|
|
|
12439
12507
|
read,
|
|
12440
12508
|
has,
|
|
12441
12509
|
write,
|
|
12510
|
+
writeIfChanged,
|
|
12442
12511
|
resetMemory
|
|
12443
12512
|
};
|
|
12444
12513
|
}
|
|
@@ -67503,7 +67572,8 @@ function createModelCapabilitiesCacheStore(getCacheDir = getOmoOpenCodeCacheDir)
|
|
|
67503
67572
|
generatedAt: snapshot.generatedAt
|
|
67504
67573
|
}),
|
|
67505
67574
|
serialize: (snapshot) => `${JSON.stringify(snapshot, null, 2)}
|
|
67506
|
-
|
|
67575
|
+
`,
|
|
67576
|
+
comparable: ({ generatedAt: _generatedAt, ...catalog }) => catalog
|
|
67507
67577
|
});
|
|
67508
67578
|
function readModelCapabilitiesCache() {
|
|
67509
67579
|
return snapshotCacheStore.read();
|
|
@@ -67516,7 +67586,7 @@ function createModelCapabilitiesCacheStore(getCacheDir = getOmoOpenCodeCacheDir)
|
|
|
67516
67586
|
}
|
|
67517
67587
|
async function refreshModelCapabilitiesCache(args = {}) {
|
|
67518
67588
|
const snapshot = await fetchModelCapabilitiesSnapshot(args);
|
|
67519
|
-
|
|
67589
|
+
snapshotCacheStore.writeIfChanged(snapshot);
|
|
67520
67590
|
return snapshot;
|
|
67521
67591
|
}
|
|
67522
67592
|
return {
|
|
@@ -77153,8 +77223,8 @@ var init_memory = __esm(() => {
|
|
|
77153
77223
|
enabled: boolean2().optional()
|
|
77154
77224
|
}).strict();
|
|
77155
77225
|
OmoMemoryProjectionSchema = object({
|
|
77156
|
-
max_entries_per_directory: number2().int().min(0).default(
|
|
77157
|
-
max_bytes: number2().int().min(0).default(
|
|
77226
|
+
max_entries_per_directory: number2().int().min(0).default(0),
|
|
77227
|
+
max_bytes: number2().int().min(0).default(40960)
|
|
77158
77228
|
}).strict();
|
|
77159
77229
|
OmoMemoryProjectionLayerSchema = object({
|
|
77160
77230
|
max_entries_per_directory: number2().int().min(0).optional(),
|
|
@@ -77218,7 +77288,7 @@ var init_memory = __esm(() => {
|
|
|
77218
77288
|
query_expansion: false
|
|
77219
77289
|
}),
|
|
77220
77290
|
project_scope: OmoMemoryProjectScopeSchema.default({ nudge: true, recall: true }),
|
|
77221
|
-
projection: OmoMemoryProjectionSchema.default({ max_entries_per_directory:
|
|
77291
|
+
projection: OmoMemoryProjectionSchema.default({ max_entries_per_directory: 0, max_bytes: 40960 }),
|
|
77222
77292
|
compile_warn_tokens: number2().int().positive().default(30000),
|
|
77223
77293
|
agents: record(string2(), OmoMemoryAgentOverridesSchema).default({})
|
|
77224
77294
|
}).strict();
|
|
@@ -77266,6 +77336,21 @@ var init_model_catalog = __esm(() => {
|
|
|
77266
77336
|
OmoModelCatalogLayerSchema = record(string2(), OmoModelCatalogEntryLayerSchema);
|
|
77267
77337
|
});
|
|
77268
77338
|
|
|
77339
|
+
// packages/omo-config-core/src/schema/model-pad.ts
|
|
77340
|
+
var OmoModelPadLabelsSchema, OmoModelPadSchema;
|
|
77341
|
+
var init_model_pad = __esm(() => {
|
|
77342
|
+
init_zod();
|
|
77343
|
+
OmoModelPadLabelsSchema = object({
|
|
77344
|
+
daily: string2().optional(),
|
|
77345
|
+
geeky: string2().optional(),
|
|
77346
|
+
normal: string2().optional(),
|
|
77347
|
+
heavy: string2().optional()
|
|
77348
|
+
}).strict();
|
|
77349
|
+
OmoModelPadSchema = object({
|
|
77350
|
+
labels: OmoModelPadLabelsSchema.optional()
|
|
77351
|
+
}).strict();
|
|
77352
|
+
});
|
|
77353
|
+
|
|
77269
77354
|
// packages/omo-config-core/src/schema/model-profile.ts
|
|
77270
77355
|
function isRecord8(value) {
|
|
77271
77356
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
@@ -77586,6 +77671,7 @@ var init_config = __esm(() => {
|
|
|
77586
77671
|
init_git_master();
|
|
77587
77672
|
init_memory();
|
|
77588
77673
|
init_model_catalog();
|
|
77674
|
+
init_model_pad();
|
|
77589
77675
|
init_model_profile();
|
|
77590
77676
|
init_side_panel();
|
|
77591
77677
|
init_task();
|
|
@@ -77607,6 +77693,7 @@ var init_config = __esm(() => {
|
|
|
77607
77693
|
models: OmoModelCatalogLayerSchema.optional(),
|
|
77608
77694
|
model_profiles: OmoModelProfilesLayerSchema.optional(),
|
|
77609
77695
|
model_profile: string2().optional(),
|
|
77696
|
+
model_pad: OmoModelPadSchema.optional(),
|
|
77610
77697
|
memory: OmoMemorySettingsLayerSchema.optional(),
|
|
77611
77698
|
telemetry: OmoTelemetrySettingsLayerSchema.optional(),
|
|
77612
77699
|
side_panel: OmoSidePanelSettingsLayerSchema.optional(),
|
|
@@ -77625,6 +77712,7 @@ var init_config = __esm(() => {
|
|
|
77625
77712
|
models: OmoModelCatalogLayerSchema.optional(),
|
|
77626
77713
|
model_profiles: OmoModelProfilesLayerSchema.optional(),
|
|
77627
77714
|
model_profile: string2().optional(),
|
|
77715
|
+
model_pad: OmoModelPadSchema.optional(),
|
|
77628
77716
|
memory: OmoMemorySettingsLayerSchema.optional(),
|
|
77629
77717
|
telemetry: OmoTelemetrySettingsLayerSchema.optional(),
|
|
77630
77718
|
side_panel: OmoSidePanelSettingsLayerSchema.optional(),
|
|
@@ -77648,6 +77736,7 @@ var init_config = __esm(() => {
|
|
|
77648
77736
|
models: OmoModelCatalogSchema.optional(),
|
|
77649
77737
|
model_profiles: OmoModelProfilesSchema.optional(),
|
|
77650
77738
|
model_profile: string2().optional(),
|
|
77739
|
+
model_pad: OmoModelPadSchema.optional(),
|
|
77651
77740
|
memory: OmoMemorySettingsSchema.optional(),
|
|
77652
77741
|
telemetry: OmoTelemetrySettingsSchema.optional(),
|
|
77653
77742
|
side_panel: OmoSidePanelSettingsSchema.optional(),
|
|
@@ -77674,6 +77763,7 @@ var init_config = __esm(() => {
|
|
|
77674
77763
|
models: OmoModelCatalogLayerSchema.optional(),
|
|
77675
77764
|
model_profiles: OmoModelProfilesLayerSchema.optional(),
|
|
77676
77765
|
model_profile: string2().optional(),
|
|
77766
|
+
model_pad: OmoModelPadSchema.optional(),
|
|
77677
77767
|
memory: OmoMemorySettingsLayerSchema.optional(),
|
|
77678
77768
|
telemetry: OmoTelemetrySettingsLayerSchema.optional(),
|
|
77679
77769
|
side_panel: OmoSidePanelSettingsLayerSchema.optional(),
|
|
@@ -77819,6 +77909,7 @@ var init_schema = __esm(() => {
|
|
|
77819
77909
|
init_legacy_harness_names();
|
|
77820
77910
|
init_memory();
|
|
77821
77911
|
init_model_catalog();
|
|
77912
|
+
init_model_pad();
|
|
77822
77913
|
init_model_profile();
|
|
77823
77914
|
init_model_ref();
|
|
77824
77915
|
init_provenance();
|
|
@@ -82839,6 +82930,37 @@ function getDefaultTelemetryOsProvider() {
|
|
|
82839
82930
|
}
|
|
82840
82931
|
var init_machine_id = () => {};
|
|
82841
82932
|
|
|
82933
|
+
// packages/telemetry-core/src/terminal-program.ts
|
|
82934
|
+
function isKnownTerminalProgram(value) {
|
|
82935
|
+
return KNOWN_TERMINAL_PROGRAMS.some((known) => known === value);
|
|
82936
|
+
}
|
|
82937
|
+
function toTelemetryTerminalProgram(termProgram) {
|
|
82938
|
+
if (termProgram === undefined || termProgram === "")
|
|
82939
|
+
return;
|
|
82940
|
+
return isKnownTerminalProgram(termProgram) ? termProgram : "other";
|
|
82941
|
+
}
|
|
82942
|
+
var KNOWN_TERMINAL_PROGRAMS;
|
|
82943
|
+
var init_terminal_program = __esm(() => {
|
|
82944
|
+
KNOWN_TERMINAL_PROGRAMS = [
|
|
82945
|
+
"Apple_Terminal",
|
|
82946
|
+
"iTerm.app",
|
|
82947
|
+
"vscode",
|
|
82948
|
+
"cursor",
|
|
82949
|
+
"windsurf",
|
|
82950
|
+
"zed",
|
|
82951
|
+
"WezTerm",
|
|
82952
|
+
"ghostty",
|
|
82953
|
+
"tmux",
|
|
82954
|
+
"Hyper",
|
|
82955
|
+
"WarpTerminal",
|
|
82956
|
+
"kitty",
|
|
82957
|
+
"alacritty",
|
|
82958
|
+
"Tabby",
|
|
82959
|
+
"rio",
|
|
82960
|
+
"mintty"
|
|
82961
|
+
];
|
|
82962
|
+
});
|
|
82963
|
+
|
|
82842
82964
|
// packages/telemetry-core/src/injected-client.ts
|
|
82843
82965
|
function isTelemetryClientEnabled(input) {
|
|
82844
82966
|
const env = input.env ?? process.env;
|
|
@@ -82941,12 +83063,16 @@ function getSharedProperties(input) {
|
|
|
82941
83063
|
total_memory_gb: Math.round(osProvider.totalmem() / 1024 / 1024 / 1024),
|
|
82942
83064
|
locale: Intl.DateTimeFormat().resolvedOptions().locale,
|
|
82943
83065
|
timezone: Intl.DateTimeFormat().resolvedOptions().timeZone,
|
|
82944
|
-
shell: process.env.SHELL,
|
|
83066
|
+
shell: getShellName(process.env.SHELL),
|
|
82945
83067
|
ci: Boolean(process.env.CI),
|
|
82946
|
-
terminal: process.env.TERM_PROGRAM,
|
|
83068
|
+
terminal: toTelemetryTerminalProgram(process.env.TERM_PROGRAM),
|
|
82947
83069
|
...input.product.additionalProperties
|
|
82948
83070
|
};
|
|
82949
83071
|
}
|
|
83072
|
+
function getShellName(shellPath) {
|
|
83073
|
+
const name = shellPath?.split(/[\\/]/).pop()?.replace(/\.exe$/i, "");
|
|
83074
|
+
return name ? name : undefined;
|
|
83075
|
+
}
|
|
82950
83076
|
function getSafeCpuInfo(osProvider, input) {
|
|
82951
83077
|
try {
|
|
82952
83078
|
const cpuInfo = osProvider.cpus();
|
|
@@ -82971,6 +83097,7 @@ var NO_OP_CLIENT;
|
|
|
82971
83097
|
var init_injected_client = __esm(() => {
|
|
82972
83098
|
init_env();
|
|
82973
83099
|
init_machine_id();
|
|
83100
|
+
init_terminal_program();
|
|
82974
83101
|
NO_OP_CLIENT = {
|
|
82975
83102
|
enabled: false,
|
|
82976
83103
|
trackActive: () => {
|
|
@@ -92550,7 +92677,7 @@ var package_default2;
|
|
|
92550
92677
|
var init_package2 = __esm(() => {
|
|
92551
92678
|
package_default2 = {
|
|
92552
92679
|
name: "@oh-my-opencode/omo-codex",
|
|
92553
|
-
version: "5.1.
|
|
92680
|
+
version: "5.1.54",
|
|
92554
92681
|
type: "module",
|
|
92555
92682
|
private: true,
|
|
92556
92683
|
description: "Codex harness adapter for oh-my-openagent. Vendored Codex plugin namespace (omo) + TypeScript installer + telemetry.",
|
|
@@ -93758,11 +93885,22 @@ init_commander();
|
|
|
93758
93885
|
// packages/omo-opencode/src/cli/install.ts
|
|
93759
93886
|
init_package();
|
|
93760
93887
|
|
|
93888
|
+
// packages/omo-opencode/src/cli/cli-installer.ts
|
|
93889
|
+
import { createInterface as createInterface2 } from "readline/promises";
|
|
93890
|
+
|
|
93891
|
+
// packages/telemetry-core/src/install-disclosure.ts
|
|
93892
|
+
var TELEMETRY_PRIVACY_POLICY_URL = "https://github.com/code-yeongyu/oh-my-openagent/blob/dev/docs/legal/privacy-policy.md";
|
|
93893
|
+
var TELEMETRY_INSTALL_DISCLOSURE_LINES = [
|
|
93894
|
+
"OmO sends anonymous usage telemetry (no prompts, code, file paths, or account data) to improve the product.",
|
|
93895
|
+
"The data goes to PostHog in the United States.",
|
|
93896
|
+
"Turn it off with DO_NOT_TRACK=1 (or OMO_DISABLE_TELEMETRY=1).",
|
|
93897
|
+
`Details: ${TELEMETRY_PRIVACY_POLICY_URL}`
|
|
93898
|
+
];
|
|
93899
|
+
|
|
93761
93900
|
// packages/omo-opencode/src/cli/cli-installer.ts
|
|
93762
93901
|
init_shared();
|
|
93763
93902
|
init_config_manager();
|
|
93764
93903
|
var import_picocolors3 = __toESM(require_picocolors(), 1);
|
|
93765
|
-
import { createInterface as createInterface2 } from "readline/promises";
|
|
93766
93904
|
|
|
93767
93905
|
// packages/omo-opencode/src/cli/install-validators.ts
|
|
93768
93906
|
var import_picocolors = __toESM(require_picocolors(), 1);
|
|
@@ -99923,6 +100061,7 @@ var REQUIRED_PLUGIN_ARTIFACTS = [
|
|
|
99923
100061
|
join66("extensions", "omo-thread-client.js"),
|
|
99924
100062
|
join66("extensions", "omo-telemetry-recovery.js"),
|
|
99925
100063
|
join66("extensions", "omo-feedback.js"),
|
|
100064
|
+
join66("extensions", "omo-desktop-toolkit.js"),
|
|
99926
100065
|
join66("extensions", "omo-claim-receipt.js"),
|
|
99927
100066
|
join66("extensions", "assets.generated.json"),
|
|
99928
100067
|
join66("extensions", "omo-member.js"),
|
|
@@ -101201,8 +101340,8 @@ async function runCliInstaller(args, version) {
|
|
|
101201
101340
|
}
|
|
101202
101341
|
console.log();
|
|
101203
101342
|
}
|
|
101204
|
-
|
|
101205
|
-
|
|
101343
|
+
for (const line of TELEMETRY_INSTALL_DISCLOSURE_LINES)
|
|
101344
|
+
printInfo(line);
|
|
101206
101345
|
console.log();
|
|
101207
101346
|
printBox(`${import_picocolors3.default.bold("Pro Tip:")} Include ${import_picocolors3.default.cyan("ultrawork")} (or ${import_picocolors3.default.cyan("ulw")}) in your prompt.
|
|
101208
101347
|
` + `All features work like magic-parallel agents, background tasks,
|
|
@@ -102498,7 +102637,7 @@ async function promptInstallConfig(detected, platform, codexAutonomousOverride)
|
|
|
102498
102637
|
message: "Do you have a Kimi For Coding subscription?",
|
|
102499
102638
|
options: [
|
|
102500
102639
|
{ value: "no", label: "No", hint: "Will use other configured providers" },
|
|
102501
|
-
{ value: "yes", label: "Yes", hint: "Kimi K3 for Sisyphus/Prometheus fallback" }
|
|
102640
|
+
{ value: "yes", label: "Yes", hint: "Kimi K3.1 Pro for Sisyphus/Prometheus fallback" }
|
|
102502
102641
|
],
|
|
102503
102642
|
initialValue: initial.kimiForCoding
|
|
102504
102643
|
});
|
|
@@ -102757,8 +102896,8 @@ async function runTuiInstaller(args, version) {
|
|
|
102757
102896
|
if (config.hasOpenCode) {
|
|
102758
102897
|
log4.message(`Run ${import_picocolors4.default.cyan("opencode")} to start!`);
|
|
102759
102898
|
}
|
|
102760
|
-
log4.info(
|
|
102761
|
-
|
|
102899
|
+
log4.info(TELEMETRY_INSTALL_DISCLOSURE_LINES.join(`
|
|
102900
|
+
`));
|
|
102762
102901
|
note(`Include ${import_picocolors4.default.cyan("ultrawork")} (or ${import_picocolors4.default.cyan("ulw")}) in your prompt.
|
|
102763
102902
|
` + `All features work like magic-parallel agents, background tasks,
|
|
102764
102903
|
` + `deep exploration, and relentless execution until completion.`, "The Magic Word");
|
|
@@ -109295,6 +109434,8 @@ var package_default3 = {
|
|
|
109295
109434
|
},
|
|
109296
109435
|
dependencies: {
|
|
109297
109436
|
"@clack/prompts": "^1.8.1",
|
|
109437
|
+
"@code-yeongyu/senpi": "2026.10.30-1",
|
|
109438
|
+
"@earendil-works/pi-ai": "npm:@code-yeongyu/senpi-ai@2026.10.30-1",
|
|
109298
109439
|
"@modelcontextprotocol/sdk": "^1.30.0",
|
|
109299
109440
|
"@oh-my-opencode/agents-md-core": "workspace:*",
|
|
109300
109441
|
"@oh-my-opencode/boulder-state": "workspace:*",
|
|
@@ -110603,6 +110744,8 @@ function isOAuthTokenData(value) {
|
|
|
110603
110744
|
if (typeof value !== "object" || value === null || Array.isArray(value))
|
|
110604
110745
|
return false;
|
|
110605
110746
|
const record = value;
|
|
110747
|
+
if (record["issuer"] !== undefined && typeof record["issuer"] !== "string")
|
|
110748
|
+
return false;
|
|
110606
110749
|
if (typeof record["accessToken"] !== "string")
|
|
110607
110750
|
return false;
|
|
110608
110751
|
const refreshToken = record["refreshToken"];
|
|
@@ -110617,6 +110760,8 @@ function isOAuthTokenData(value) {
|
|
|
110617
110760
|
if (typeof clientInfo !== "object" || clientInfo === null || Array.isArray(clientInfo))
|
|
110618
110761
|
return false;
|
|
110619
110762
|
const clientRecord = clientInfo;
|
|
110763
|
+
if (clientRecord["issuer"] !== undefined && typeof clientRecord["issuer"] !== "string")
|
|
110764
|
+
return false;
|
|
110620
110765
|
if (typeof clientRecord["clientId"] !== "string")
|
|
110621
110766
|
return false;
|
|
110622
110767
|
const clientSecret = clientRecord["clientSecret"];
|
|
@@ -110685,7 +110830,9 @@ function deleteToken(serverHost, resource) {
|
|
|
110685
110830
|
return deleteLegacyToken(serverHost, resource);
|
|
110686
110831
|
try {
|
|
110687
110832
|
unlinkSync9(filePath);
|
|
110688
|
-
|
|
110833
|
+
const indexDeleted = deleteTokenIndexEntry(getMcpOauthStorageDir(), getMcpOauthServerHash(serverHost, resource));
|
|
110834
|
+
const legacyDeleted = deleteLegacyToken(serverHost, resource);
|
|
110835
|
+
return indexDeleted && legacyDeleted;
|
|
110689
110836
|
} catch (deleteError) {
|
|
110690
110837
|
if (!(deleteError instanceof Error))
|
|
110691
110838
|
throw deleteError;
|
|
@@ -110795,19 +110942,26 @@ async function fetchMetadata(url) {
|
|
|
110795
110942
|
}
|
|
110796
110943
|
return { ok: true, json };
|
|
110797
110944
|
}
|
|
110798
|
-
function parseMetadataFields(json, resource) {
|
|
110945
|
+
function parseMetadataFields(json, resource, expectedIssuer) {
|
|
110946
|
+
const issuer = readStringField(json, "issuer");
|
|
110947
|
+
parseHttpsUrl(issuer, "issuer");
|
|
110948
|
+
if (issuer !== expectedIssuer) {
|
|
110949
|
+
throw new Error("OAuth metadata issuer mismatch");
|
|
110950
|
+
}
|
|
110799
110951
|
const authorizationEndpoint = parseHttpsUrl(readStringField(json, "authorization_endpoint"), "authorization_endpoint").toString();
|
|
110800
110952
|
const tokenEndpoint = parseHttpsUrl(readStringField(json, "token_endpoint"), "token_endpoint").toString();
|
|
110801
110953
|
const registrationEndpointValue = json.registration_endpoint;
|
|
110802
110954
|
const registrationEndpoint = typeof registrationEndpointValue === "string" && registrationEndpointValue.length > 0 ? parseHttpsUrl(registrationEndpointValue, "registration_endpoint").toString() : undefined;
|
|
110803
110955
|
return {
|
|
110956
|
+
issuer,
|
|
110957
|
+
...json.authorization_response_iss_parameter_supported === true ? { authorizationResponseIssParameterSupported: true } : {},
|
|
110804
110958
|
authorizationEndpoint,
|
|
110805
110959
|
tokenEndpoint,
|
|
110806
110960
|
registrationEndpoint,
|
|
110807
110961
|
resource
|
|
110808
110962
|
};
|
|
110809
110963
|
}
|
|
110810
|
-
async function fetchAuthorizationServerMetadata(issuer, resource) {
|
|
110964
|
+
async function fetchAuthorizationServerMetadata(issuer, resource, allowOriginFallback = false) {
|
|
110811
110965
|
const issuerUrl = parseHttpsUrl(issuer, "Authorization server URL");
|
|
110812
110966
|
const issuerPath = issuerUrl.pathname.replace(/\/+$/, "");
|
|
110813
110967
|
const metadataUrl = new URL(`/.well-known/oauth-authorization-server${issuerPath}`, issuerUrl).toString();
|
|
@@ -110817,7 +110971,7 @@ async function fetchAuthorizationServerMetadata(issuer, resource) {
|
|
|
110817
110971
|
const rootMetadataUrl = new URL("/.well-known/oauth-authorization-server", issuerUrl).toString();
|
|
110818
110972
|
const rootMetadata = await fetchMetadata(rootMetadataUrl);
|
|
110819
110973
|
if (rootMetadata.ok) {
|
|
110820
|
-
return parseMetadataFields(rootMetadata.json, resource);
|
|
110974
|
+
return parseMetadataFields(rootMetadata.json, resource, allowOriginFallback ? issuerUrl.origin : issuer);
|
|
110821
110975
|
}
|
|
110822
110976
|
}
|
|
110823
110977
|
if (metadata.status === 404) {
|
|
@@ -110825,7 +110979,7 @@ async function fetchAuthorizationServerMetadata(issuer, resource) {
|
|
|
110825
110979
|
}
|
|
110826
110980
|
throw new Error(`OAuth authorization server metadata fetch failed (${metadata.status})`);
|
|
110827
110981
|
}
|
|
110828
|
-
return parseMetadataFields(metadata.json, resource);
|
|
110982
|
+
return parseMetadataFields(metadata.json, resource, issuer);
|
|
110829
110983
|
}
|
|
110830
110984
|
function parseAuthorizationServers(metadata) {
|
|
110831
110985
|
const servers = metadata.authorization_servers;
|
|
@@ -110833,11 +110987,11 @@ function parseAuthorizationServers(metadata) {
|
|
|
110833
110987
|
return [];
|
|
110834
110988
|
return servers.filter((server) => typeof server === "string" && server.length > 0);
|
|
110835
110989
|
}
|
|
110836
|
-
async function discoverOAuthServerMetadata(resource) {
|
|
110990
|
+
async function discoverOAuthServerMetadata(resource, forceRefresh = false) {
|
|
110837
110991
|
const resourceUrl = parseHttpsUrl(resource, "Resource server URL");
|
|
110838
110992
|
const resourceKey = resourceUrl.toString();
|
|
110839
110993
|
const cached = discoveryCache.get(resourceKey);
|
|
110840
|
-
if (cached)
|
|
110994
|
+
if (cached && !forceRefresh)
|
|
110841
110995
|
return cached;
|
|
110842
110996
|
const pending = pendingDiscovery.get(resourceKey);
|
|
110843
110997
|
if (pending)
|
|
@@ -110855,7 +111009,7 @@ async function discoverOAuthServerMetadata(resource) {
|
|
|
110855
111009
|
if (prmResponse.status !== 404) {
|
|
110856
111010
|
throw new Error(`OAuth protected resource metadata fetch failed (${prmResponse.status})`);
|
|
110857
111011
|
}
|
|
110858
|
-
return fetchAuthorizationServerMetadata(
|
|
111012
|
+
return fetchAuthorizationServerMetadata(resource.replace(/\/+$/, ""), resource, true);
|
|
110859
111013
|
})();
|
|
110860
111014
|
pendingDiscovery.set(resourceKey, discoveryPromise);
|
|
110861
111015
|
try {
|
|
@@ -110879,6 +111033,10 @@ async function getOrRegisterClient(options) {
|
|
|
110879
111033
|
}
|
|
110880
111034
|
const fetchImpl = options.fetch ?? globalThis.fetch;
|
|
110881
111035
|
const request = {
|
|
111036
|
+
application_type: options.redirectUris.some((uri) => {
|
|
111037
|
+
const url = new URL(uri);
|
|
111038
|
+
return (url.protocol === "http:" || url.protocol === "https:") && !["127.0.0.1", "localhost", "[::1]"].includes(url.hostname);
|
|
111039
|
+
}) ? "web" : "native",
|
|
110882
111040
|
redirect_uris: options.redirectUris,
|
|
110883
111041
|
client_name: options.clientName,
|
|
110884
111042
|
grant_types: ["authorization_code", "refresh_token"],
|
|
@@ -110955,12 +111113,20 @@ function buildAuthorizationUrl(authorizationEndpoint, options) {
|
|
|
110955
111113
|
return url.toString();
|
|
110956
111114
|
}
|
|
110957
111115
|
var CALLBACK_TIMEOUT_MS = 5 * 60 * 1000;
|
|
110958
|
-
function startCallbackServer(port) {
|
|
111116
|
+
function startCallbackServer(port, validation) {
|
|
110959
111117
|
return new Promise((resolve, reject) => {
|
|
110960
111118
|
let timeoutId;
|
|
110961
111119
|
const server = createServer2((request, response) => {
|
|
110962
111120
|
clearTimeout(timeoutId);
|
|
110963
111121
|
const requestUrl = new URL(request.url ?? "/", `http://localhost:${port}`);
|
|
111122
|
+
const issuer = requestUrl.searchParams.get("iss");
|
|
111123
|
+
if (validation && (issuer !== null && issuer !== validation.issuer || issuer === null && validation.authorizationResponseIssParameterSupported)) {
|
|
111124
|
+
response.writeHead(400, { "content-type": "text/html" });
|
|
111125
|
+
response.end("<html><body><h1>Authorization failed</h1></body></html>");
|
|
111126
|
+
server.close();
|
|
111127
|
+
reject(new Error("OAuth authorization response issuer mismatch or missing issuer"));
|
|
111128
|
+
return;
|
|
111129
|
+
}
|
|
110964
111130
|
const code = requestUrl.searchParams.get("code");
|
|
110965
111131
|
const state = requestUrl.searchParams.get("state");
|
|
110966
111132
|
const error = requestUrl.searchParams.get("error");
|
|
@@ -111030,7 +111196,7 @@ async function runAuthorizationCodeRedirect(options) {
|
|
|
111030
111196
|
scopes: options.scopes,
|
|
111031
111197
|
resource: options.resource
|
|
111032
111198
|
});
|
|
111033
|
-
const callbackPromise = startCallbackServer(options.callbackPort);
|
|
111199
|
+
const callbackPromise = startCallbackServer(options.callbackPort, options);
|
|
111034
111200
|
openBrowser(authorizationUrl);
|
|
111035
111201
|
const result = await callbackPromise;
|
|
111036
111202
|
if (result.state !== state) {
|
|
@@ -111065,10 +111231,12 @@ function buildOAuthTokenData(tokenData, clientInfo, fallbackRefreshToken) {
|
|
|
111065
111231
|
throw new Error("Token response missing access_token");
|
|
111066
111232
|
}
|
|
111067
111233
|
return {
|
|
111234
|
+
...clientInfo.issuer ? { issuer: clientInfo.issuer } : {},
|
|
111068
111235
|
accessToken,
|
|
111069
111236
|
refreshToken: typeof tokenData["refresh_token"] === "string" ? tokenData["refresh_token"] : fallbackRefreshToken,
|
|
111070
111237
|
expiresAt: typeof tokenData["expires_in"] === "number" ? Math.floor(Date.now() / 1000) + tokenData["expires_in"] : undefined,
|
|
111071
111238
|
clientInfo: {
|
|
111239
|
+
...clientInfo.issuer ? { issuer: clientInfo.issuer } : {},
|
|
111072
111240
|
clientId: clientInfo.clientId,
|
|
111073
111241
|
...clientInfo.clientSecret ? { clientSecret: clientInfo.clientSecret } : {}
|
|
111074
111242
|
}
|
|
@@ -111082,6 +111250,7 @@ class McpOAuthProvider {
|
|
|
111082
111250
|
storedCodeVerifier = null;
|
|
111083
111251
|
storedClientInfo = null;
|
|
111084
111252
|
callbackPort = null;
|
|
111253
|
+
issuer;
|
|
111085
111254
|
constructor(options) {
|
|
111086
111255
|
this.serverUrl = options.serverUrl;
|
|
111087
111256
|
this.configClientId = options.clientId;
|
|
@@ -111091,7 +111260,32 @@ class McpOAuthProvider {
|
|
|
111091
111260
|
return loadToken(this.serverUrl, this.serverUrl);
|
|
111092
111261
|
}
|
|
111093
111262
|
saveTokens(tokenData) {
|
|
111094
|
-
|
|
111263
|
+
const issuer = tokenData.issuer ?? this.issuer;
|
|
111264
|
+
return saveToken(this.serverUrl, this.serverUrl, issuer ? {
|
|
111265
|
+
...tokenData,
|
|
111266
|
+
issuer,
|
|
111267
|
+
...tokenData.clientInfo ? { clientInfo: { ...tokenData.clientInfo, issuer: tokenData.clientInfo.issuer ?? issuer } } : {}
|
|
111268
|
+
} : tokenData);
|
|
111269
|
+
}
|
|
111270
|
+
bindIssuer(issuer) {
|
|
111271
|
+
const token = this.tokens();
|
|
111272
|
+
const stamps = [token?.issuer, token?.clientInfo?.issuer, this.storedClientInfo?.issuer, this.issuer];
|
|
111273
|
+
const changed = stamps.some((stamp) => stamp !== undefined && stamp !== issuer);
|
|
111274
|
+
if (changed) {
|
|
111275
|
+
this.storedClientInfo = null;
|
|
111276
|
+
this.storedCodeVerifier = null;
|
|
111277
|
+
if (!deleteToken(this.serverUrl, this.serverUrl)) {
|
|
111278
|
+
throw new Error("Unable to discard credentials for the previous OAuth issuer");
|
|
111279
|
+
}
|
|
111280
|
+
}
|
|
111281
|
+
this.issuer = issuer;
|
|
111282
|
+
if (!changed && token && !this.saveTokens(token)) {
|
|
111283
|
+
throw new Error("Unable to stamp stored OAuth credentials with their issuer");
|
|
111284
|
+
}
|
|
111285
|
+
const clientInfo = this.clientInformation();
|
|
111286
|
+
if (clientInfo)
|
|
111287
|
+
this.storedClientInfo = { ...clientInfo, issuer };
|
|
111288
|
+
return changed;
|
|
111095
111289
|
}
|
|
111096
111290
|
clientInformation() {
|
|
111097
111291
|
if (this.storedClientInfo)
|
|
@@ -111121,6 +111315,8 @@ class McpOAuthProvider {
|
|
|
111121
111315
|
this.callbackPort = await findAvailablePort2();
|
|
111122
111316
|
}
|
|
111123
111317
|
const result = await runAuthorizationCodeRedirect({
|
|
111318
|
+
issuer: metadata.issuer,
|
|
111319
|
+
authorizationResponseIssParameterSupported: metadata.authorizationResponseIssParameterSupported,
|
|
111124
111320
|
authorizationEndpoint: metadata.authorizationEndpoint,
|
|
111125
111321
|
callbackPort: this.callbackPort,
|
|
111126
111322
|
clientId: clientInfo.clientId,
|
|
@@ -111132,16 +111328,19 @@ class McpOAuthProvider {
|
|
|
111132
111328
|
return { code: result.code };
|
|
111133
111329
|
}
|
|
111134
111330
|
async login() {
|
|
111135
|
-
const metadata = await discoverOAuthServerMetadata(this.serverUrl);
|
|
111331
|
+
const metadata = await discoverOAuthServerMetadata(this.serverUrl, true);
|
|
111332
|
+
this.bindIssuer(metadata.issuer);
|
|
111333
|
+
if (this.callbackPort === null)
|
|
111334
|
+
this.callbackPort = await findAvailablePort2();
|
|
111136
111335
|
const clientRegistrationStorage = {
|
|
111137
111336
|
getClientRegistration: () => this.storedClientInfo,
|
|
111138
111337
|
setClientRegistration: (_serverIdentifier, credentials) => {
|
|
111139
|
-
this.storedClientInfo = credentials;
|
|
111338
|
+
this.storedClientInfo = { ...credentials, issuer: metadata.issuer };
|
|
111140
111339
|
}
|
|
111141
111340
|
};
|
|
111142
111341
|
const clientInfo = await getOrRegisterClient({
|
|
111143
111342
|
...metadata.registrationEndpoint ? { registrationEndpoint: metadata.registrationEndpoint } : {},
|
|
111144
|
-
serverIdentifier:
|
|
111343
|
+
serverIdentifier: metadata.issuer,
|
|
111145
111344
|
clientName: PLUGIN_NAME4,
|
|
111146
111345
|
redirectUris: [this.redirectUrl()],
|
|
111147
111346
|
tokenEndpointAuthMethod: "none",
|
|
@@ -111151,7 +111350,7 @@ class McpOAuthProvider {
|
|
|
111151
111350
|
if (!clientInfo) {
|
|
111152
111351
|
throw new Error("Failed to obtain client credentials. Provide a clientId or ensure the server supports DCR.");
|
|
111153
111352
|
}
|
|
111154
|
-
this.storedClientInfo = clientInfo;
|
|
111353
|
+
this.storedClientInfo = { ...clientInfo, issuer: metadata.issuer };
|
|
111155
111354
|
const { code } = await this.redirectToAuthorization(metadata);
|
|
111156
111355
|
const verifier = this.codeVerifier();
|
|
111157
111356
|
if (!verifier) {
|
|
@@ -111170,12 +111369,14 @@ class McpOAuthProvider {
|
|
|
111170
111369
|
}).toString()
|
|
111171
111370
|
});
|
|
111172
111371
|
const tokenData = await parseTokenResponse(tokenResponse);
|
|
111173
|
-
const oauthTokenData = buildOAuthTokenData(tokenData, clientInfo);
|
|
111372
|
+
const oauthTokenData = buildOAuthTokenData(tokenData, { ...clientInfo, issuer: metadata.issuer });
|
|
111174
111373
|
this.saveTokens(oauthTokenData);
|
|
111175
111374
|
return oauthTokenData;
|
|
111176
111375
|
}
|
|
111177
111376
|
async refresh(refreshToken) {
|
|
111178
|
-
const metadata = await discoverOAuthServerMetadata(this.serverUrl);
|
|
111377
|
+
const metadata = await discoverOAuthServerMetadata(this.serverUrl, true);
|
|
111378
|
+
if (this.bindIssuer(metadata.issuer))
|
|
111379
|
+
return this.login();
|
|
111179
111380
|
const clientInfo = this.clientInformation();
|
|
111180
111381
|
const clientId = clientInfo?.clientId ?? this.configClientId;
|
|
111181
111382
|
if (!clientId) {
|
|
@@ -111195,6 +111396,7 @@ class McpOAuthProvider {
|
|
|
111195
111396
|
const tokenData = await parseTokenResponse(tokenResponse);
|
|
111196
111397
|
const oauthTokenData = buildOAuthTokenData(tokenData, {
|
|
111197
111398
|
clientId,
|
|
111399
|
+
issuer: metadata.issuer,
|
|
111198
111400
|
...clientInfo?.clientSecret ? { clientSecret: clientInfo.clientSecret } : {}
|
|
111199
111401
|
}, refreshToken);
|
|
111200
111402
|
this.saveTokens(oauthTokenData);
|
|
@@ -112042,6 +112244,17 @@ import { hostname } from "os";
|
|
|
112042
112244
|
// packages/omo-opencode/src/cli/service-auth/protocol.ts
|
|
112043
112245
|
init_zod();
|
|
112044
112246
|
|
|
112247
|
+
// packages/omo-opencode/src/cli/service-auth/credential-owner.ts
|
|
112248
|
+
init_zod();
|
|
112249
|
+
var identity = string2().regex(/^[A-Za-z0-9_-]{1,128}$/);
|
|
112250
|
+
var credentialOwnerSchema = object({
|
|
112251
|
+
accountId: identity,
|
|
112252
|
+
deviceId: identity,
|
|
112253
|
+
familyId: identity,
|
|
112254
|
+
generation: number2().int().positive().safe(),
|
|
112255
|
+
ownerHandle: string2().regex(/^[\x21-\x7e]{1,4096}$/)
|
|
112256
|
+
});
|
|
112257
|
+
|
|
112045
112258
|
// packages/omo-opencode/src/cli/service-auth/terminal-text.ts
|
|
112046
112259
|
import { stripVTControlCharacters as stripVTControlCharacters4 } from "util";
|
|
112047
112260
|
function terminalText(value) {
|
|
@@ -112060,9 +112273,19 @@ class SignInError extends Error {
|
|
|
112060
112273
|
|
|
112061
112274
|
class RequestFailure extends SignInError {
|
|
112062
112275
|
notSent;
|
|
112063
|
-
|
|
112276
|
+
responseStatus;
|
|
112277
|
+
constructor(notSent, responseStatus) {
|
|
112064
112278
|
super("Unable to complete the service request. Check the connection and retry.", true);
|
|
112065
112279
|
this.notSent = notSent;
|
|
112280
|
+
this.responseStatus = responseStatus;
|
|
112281
|
+
}
|
|
112282
|
+
}
|
|
112283
|
+
|
|
112284
|
+
class InvalidApiResponse extends SignInError {
|
|
112285
|
+
status;
|
|
112286
|
+
constructor(status) {
|
|
112287
|
+
super("The service returned an invalid error response.");
|
|
112288
|
+
this.status = status;
|
|
112066
112289
|
}
|
|
112067
112290
|
}
|
|
112068
112291
|
var platformSchema = _enum(["macos", "linux", "windows"]);
|
|
@@ -112075,12 +112298,18 @@ var tokenSchema = object({
|
|
|
112075
112298
|
});
|
|
112076
112299
|
var grantSchema = tokenSchema.extend({
|
|
112077
112300
|
device: object({ id: nonempty, name: nonempty }),
|
|
112078
|
-
offlineGrant: nonempty.optional()
|
|
112301
|
+
offlineGrant: nonempty.optional(),
|
|
112302
|
+
owner: credentialOwnerSchema.optional(),
|
|
112303
|
+
writerFloor: union([literal(1), literal(2)]).optional(),
|
|
112304
|
+
freshAuthorizationProof: nonempty.optional()
|
|
112079
112305
|
});
|
|
112080
112306
|
var credentialSchema = grantSchema.extend({
|
|
112081
112307
|
signingPrivateKey: nonempty,
|
|
112082
112308
|
sealingPrivateKey: nonempty,
|
|
112083
|
-
refreshState: literal("uncertain").optional()
|
|
112309
|
+
refreshState: literal("uncertain").optional(),
|
|
112310
|
+
credentialGeneration: nonempty.optional(),
|
|
112311
|
+
accountId: nonempty.optional(),
|
|
112312
|
+
refreshAttempt: unknown().optional()
|
|
112084
112313
|
});
|
|
112085
112314
|
var deviceCodeSchema = object({
|
|
112086
112315
|
deviceCode: string2().regex(/^dc\.[A-Za-z0-9_-]{43}$/),
|
|
@@ -112108,6 +112337,9 @@ var limitSchema = object({
|
|
|
112108
112337
|
var deviceListSchema = object({
|
|
112109
112338
|
devices: array(object({ id: nonempty, name: nonempty, revokedAt: timestamp.nullable() }))
|
|
112110
112339
|
});
|
|
112340
|
+
var currentDeviceListSchema = object({
|
|
112341
|
+
devices: array(object({ id: nonempty, current: boolean2(), revokedAt: timestamp.nullable() }))
|
|
112342
|
+
});
|
|
112111
112343
|
var REFUSAL_CODES = [
|
|
112112
112344
|
"unauthorized",
|
|
112113
112345
|
"account_deleted",
|
|
@@ -112124,7 +112356,11 @@ var REFUSAL_CODES = [
|
|
|
112124
112356
|
"unavailable",
|
|
112125
112357
|
"forbidden",
|
|
112126
112358
|
"invalid_request",
|
|
112127
|
-
"not_found"
|
|
112359
|
+
"not_found",
|
|
112360
|
+
"client_upgrade_required",
|
|
112361
|
+
"writer_floor_mismatch",
|
|
112362
|
+
"service_upgrade_required",
|
|
112363
|
+
"refresh_recovery_expired"
|
|
112128
112364
|
];
|
|
112129
112365
|
var isKnownRefusal = (code) => REFUSAL_CODES.includes(code);
|
|
112130
112366
|
function refusalGuidance(code, status) {
|
|
@@ -112151,6 +112387,10 @@ function refusalGuidance(code, status) {
|
|
|
112151
112387
|
case "access_denied":
|
|
112152
112388
|
case "authorization_pending":
|
|
112153
112389
|
return "account_refused";
|
|
112390
|
+
case "client_upgrade_required":
|
|
112391
|
+
case "writer_floor_mismatch":
|
|
112392
|
+
case "service_upgrade_required":
|
|
112393
|
+
case "refresh_recovery_expired":
|
|
112154
112394
|
case "unknown":
|
|
112155
112395
|
if (status === 401)
|
|
112156
112396
|
return "sign_in_again";
|
|
@@ -112261,13 +112501,13 @@ async function requestApi(api, path, init, signal) {
|
|
|
112261
112501
|
try {
|
|
112262
112502
|
body = await response.json();
|
|
112263
112503
|
} catch {
|
|
112264
|
-
throw new RequestFailure(false);
|
|
112504
|
+
throw new RequestFailure(false, response.status);
|
|
112265
112505
|
}
|
|
112266
112506
|
if (response.ok)
|
|
112267
112507
|
return body;
|
|
112268
112508
|
const envelope = envelopeSchema.safeParse(body);
|
|
112269
112509
|
if (!envelope.success)
|
|
112270
|
-
throw new
|
|
112510
|
+
throw new InvalidApiResponse(response.status);
|
|
112271
112511
|
const error = envelope.data.error;
|
|
112272
112512
|
const detail = limitSchema.safeParse(error.detail);
|
|
112273
112513
|
throw new ApiRefusal(error.code, response.status, error.code === "entitlement_required" && detail.success ? detail.data : undefined, response.headers.get("retry-after"));
|
|
@@ -112371,7 +112611,7 @@ async function loginDevice(session, options) {
|
|
|
112371
112611
|
}
|
|
112372
112612
|
|
|
112373
112613
|
// packages/omo-opencode/src/cli/service-auth/keystore.ts
|
|
112374
|
-
import { createHash as
|
|
112614
|
+
import { createHash as createHash12, randomUUID as randomUUID7 } from "crypto";
|
|
112375
112615
|
import { basename as basename15 } from "path";
|
|
112376
112616
|
|
|
112377
112617
|
// packages/omo-opencode/src/cli/service-auth/secret-service-lock.ts
|
|
@@ -112415,289 +112655,490 @@ var probeSecretServiceLock = () => new Promise((resolve) => {
|
|
|
112415
112655
|
});
|
|
112416
112656
|
});
|
|
112417
112657
|
|
|
112418
|
-
// packages/omo-opencode/src/cli/service-auth/
|
|
112419
|
-
|
|
112420
|
-
}
|
|
112658
|
+
// packages/omo-opencode/src/cli/service-auth/credential-lock.ts
|
|
112659
|
+
import { AsyncLocalStorage as AsyncLocalStorage3 } from "async_hooks";
|
|
112660
|
+
import { createHash as createHash11 } from "crypto";
|
|
112661
|
+
import { mkdir as mkdir11 } from "fs/promises";
|
|
112662
|
+
import { homedir as homedir31 } from "os";
|
|
112663
|
+
import { join as join106 } from "path";
|
|
112421
112664
|
|
|
112422
|
-
|
|
112665
|
+
// packages/team-core/src/team-state-store/lock-publish.ts
|
|
112666
|
+
import { access as access4, open as open3, unlink as unlink3 } from "fs/promises";
|
|
112667
|
+
import { dirname as dirname42 } from "path";
|
|
112668
|
+
|
|
112669
|
+
// packages/team-core/src/team-state-store/lock-record.ts
|
|
112670
|
+
import { randomUUID as randomUUID6 } from "crypto";
|
|
112671
|
+
import { readFile as readFile34, stat as stat9 } from "fs/promises";
|
|
112672
|
+
|
|
112673
|
+
// packages/memory-core/src/locks/process-identity.ts
|
|
112674
|
+
import { execFile as execFile7 } from "child_process";
|
|
112675
|
+
|
|
112676
|
+
// packages/memory-core/src/fs/resilient.ts
|
|
112677
|
+
import * as fsSync from "fs";
|
|
112678
|
+
import * as fsp from "fs/promises";
|
|
112679
|
+
|
|
112680
|
+
// packages/memory-core/src/fs/retry.ts
|
|
112681
|
+
var EINTR_RETRY_CAP = 128;
|
|
112682
|
+
function fsErrorCode(error) {
|
|
112683
|
+
if (!(error instanceof Error) || !("code" in error))
|
|
112684
|
+
return;
|
|
112685
|
+
return typeof error.code === "string" ? error.code : undefined;
|
|
112423
112686
|
}
|
|
112424
|
-
|
|
112687
|
+
async function retryOnEintr(operation) {
|
|
112688
|
+
for (let attempt = 0;; attempt += 1) {
|
|
112689
|
+
try {
|
|
112690
|
+
return await operation();
|
|
112691
|
+
} catch (error) {
|
|
112692
|
+
if (fsErrorCode(error) !== "EINTR" || attempt >= EINTR_RETRY_CAP)
|
|
112693
|
+
throw error;
|
|
112694
|
+
}
|
|
112695
|
+
}
|
|
112696
|
+
}
|
|
112697
|
+
function retryOnEintrSync(operation) {
|
|
112698
|
+
for (let attempt = 0;; attempt += 1) {
|
|
112699
|
+
try {
|
|
112700
|
+
return operation();
|
|
112701
|
+
} catch (error) {
|
|
112702
|
+
if (fsErrorCode(error) !== "EINTR" || attempt >= EINTR_RETRY_CAP)
|
|
112703
|
+
throw error;
|
|
112704
|
+
}
|
|
112705
|
+
}
|
|
112425
112706
|
}
|
|
112426
112707
|
|
|
112427
|
-
|
|
112708
|
+
// packages/memory-core/src/fs/rename-contention.ts
|
|
112709
|
+
var CONTENTION_CODES = new Set(["EPERM", "EBUSY", "EACCES"]);
|
|
112710
|
+
|
|
112711
|
+
// packages/memory-core/src/fs/resilient.ts
|
|
112712
|
+
function isFunction2(value) {
|
|
112713
|
+
return typeof value === "function";
|
|
112428
112714
|
}
|
|
112429
|
-
|
|
112430
|
-
|
|
112431
|
-
|
|
112432
|
-
|
|
112433
|
-
|
|
112434
|
-
|
|
112435
|
-
|
|
112436
|
-
|
|
112437
|
-
|
|
112438
|
-
|
|
112439
|
-
|
|
112440
|
-
|
|
112441
|
-
|
|
112715
|
+
function withAsyncRetry(operation) {
|
|
112716
|
+
return (...args) => retryOnEintr(async () => operation(...args));
|
|
112717
|
+
}
|
|
112718
|
+
function withSyncRetry(operation) {
|
|
112719
|
+
return (...args) => retryOnEintrSync(() => operation(...args));
|
|
112720
|
+
}
|
|
112721
|
+
function resilientNamespace(namespace, kind) {
|
|
112722
|
+
const wrapFunction = kind === "async" ? withAsyncRetry : withSyncRetry;
|
|
112723
|
+
const cache = new Map;
|
|
112724
|
+
return new Proxy(namespace, {
|
|
112725
|
+
get(target, property) {
|
|
112726
|
+
if (cache.has(property))
|
|
112727
|
+
return cache.get(property);
|
|
112728
|
+
const value = Reflect.get(target, property);
|
|
112729
|
+
if (!isFunction2(value))
|
|
112730
|
+
return value;
|
|
112731
|
+
const wrapped = wrapFunction(value);
|
|
112732
|
+
const native = Reflect.get(value, "native");
|
|
112733
|
+
if (isFunction2(native))
|
|
112734
|
+
Object.assign(wrapped, { native: wrapFunction(native) });
|
|
112735
|
+
cache.set(property, wrapped);
|
|
112736
|
+
return wrapped;
|
|
112737
|
+
}
|
|
112738
|
+
});
|
|
112739
|
+
}
|
|
112740
|
+
var IDEMPOTENT_HANDLE_METHODS = new Set(["stat", "sync", "datasync", "chmod", "chown", "utimes", "truncate"]);
|
|
112741
|
+
var promises = resilientNamespace(fsp, "async");
|
|
112742
|
+
var sync = resilientNamespace(fsSync, "sync");
|
|
112743
|
+
var {
|
|
112744
|
+
access: access3,
|
|
112745
|
+
chmod: chmod2,
|
|
112746
|
+
copyFile: copyFile4,
|
|
112747
|
+
cp: cp5,
|
|
112748
|
+
link,
|
|
112749
|
+
lstat: lstat18,
|
|
112750
|
+
mkdir: mkdir10,
|
|
112751
|
+
mkdtemp: mkdtemp2,
|
|
112752
|
+
readFile: readFile33,
|
|
112753
|
+
readdir: readdir17,
|
|
112754
|
+
readlink: readlink7,
|
|
112755
|
+
realpath: realpath2,
|
|
112756
|
+
rm: rm16,
|
|
112757
|
+
rmdir: rmdir2,
|
|
112758
|
+
stat: stat8,
|
|
112759
|
+
statfs,
|
|
112760
|
+
unlink: unlink2
|
|
112761
|
+
} = promises;
|
|
112762
|
+
var {
|
|
112763
|
+
accessSync: accessSync5,
|
|
112764
|
+
chmodSync: chmodSync7,
|
|
112765
|
+
fsyncSync: fsyncSync3,
|
|
112766
|
+
linkSync,
|
|
112767
|
+
lstatSync: lstatSync5,
|
|
112768
|
+
mkdirSync: mkdirSync19,
|
|
112769
|
+
readFileSync: readFileSync44,
|
|
112770
|
+
readdirSync: readdirSync14,
|
|
112771
|
+
realpathSync: realpathSync13,
|
|
112772
|
+
statSync: statSync8,
|
|
112773
|
+
unlinkSync: unlinkSync10,
|
|
112774
|
+
writeFileSync: writeFileSync17,
|
|
112775
|
+
writeSync
|
|
112776
|
+
} = sync;
|
|
112777
|
+
|
|
112778
|
+
// packages/memory-core/src/locks/process-start-time.ts
|
|
112779
|
+
var PROC_PIDTBSDINFO = 3;
|
|
112780
|
+
var PROC_BSDINFO_SIZE = 136;
|
|
112781
|
+
var START_TVSEC_OFFSET = 120;
|
|
112782
|
+
var procPidInfoLookup = null;
|
|
112783
|
+
async function openProcPidInfo() {
|
|
112784
|
+
if (process.platform !== "darwin")
|
|
112785
|
+
return null;
|
|
112786
|
+
try {
|
|
112787
|
+
const { dlopen, FFIType } = await import("bun:ffi");
|
|
112788
|
+
const library = dlopen("/usr/lib/libSystem.B.dylib", {
|
|
112789
|
+
proc_pidinfo: {
|
|
112790
|
+
args: [FFIType.i32, FFIType.i32, FFIType.u64, FFIType.ptr, FFIType.i32],
|
|
112791
|
+
returns: FFIType.i32
|
|
112792
|
+
}
|
|
112793
|
+
});
|
|
112794
|
+
return (pid, flavor, arg, buffer, size) => Number(library.symbols.proc_pidinfo(pid, flavor, arg, buffer, size));
|
|
112795
|
+
} catch {
|
|
112796
|
+
return null;
|
|
112797
|
+
}
|
|
112798
|
+
}
|
|
112799
|
+
function loadProcPidInfo() {
|
|
112800
|
+
procPidInfoLookup ??= openProcPidInfo();
|
|
112801
|
+
return procPidInfoLookup;
|
|
112802
|
+
}
|
|
112803
|
+
async function readDarwinProcessStartSeconds(pid) {
|
|
112804
|
+
if (process.platform !== "darwin")
|
|
112805
|
+
return null;
|
|
112806
|
+
if (!Number.isSafeInteger(pid) || pid <= 0)
|
|
112807
|
+
return null;
|
|
112808
|
+
const procPidInfo = await loadProcPidInfo();
|
|
112809
|
+
if (procPidInfo === null)
|
|
112810
|
+
return null;
|
|
112811
|
+
const buffer = new Uint8Array(PROC_BSDINFO_SIZE);
|
|
112812
|
+
let written = 0;
|
|
112813
|
+
try {
|
|
112814
|
+
written = procPidInfo(pid, PROC_PIDTBSDINFO, 0n, buffer, PROC_BSDINFO_SIZE);
|
|
112815
|
+
} catch {
|
|
112816
|
+
return null;
|
|
112817
|
+
}
|
|
112818
|
+
if (written !== PROC_BSDINFO_SIZE)
|
|
112819
|
+
return null;
|
|
112820
|
+
const view = new DataView(buffer.buffer, buffer.byteOffset, buffer.byteLength);
|
|
112821
|
+
const startSeconds = Number(view.getBigUint64(START_TVSEC_OFFSET, true));
|
|
112822
|
+
return startSeconds > 0 ? startSeconds : null;
|
|
112823
|
+
}
|
|
112824
|
+
var PROCESS_QUERY_LIMITED_INFORMATION = 4096;
|
|
112825
|
+
var kernel32Lookup = null;
|
|
112826
|
+
async function openKernel32() {
|
|
112827
|
+
if (process.platform !== "win32")
|
|
112828
|
+
return null;
|
|
112829
|
+
try {
|
|
112830
|
+
const { dlopen, FFIType } = await import("bun:ffi");
|
|
112831
|
+
const library = dlopen("kernel32.dll", {
|
|
112832
|
+
OpenProcess: { args: [FFIType.u32, FFIType.i32, FFIType.u32], returns: FFIType.ptr },
|
|
112833
|
+
GetProcessTimes: { args: [FFIType.ptr, FFIType.ptr, FFIType.ptr, FFIType.ptr, FFIType.ptr], returns: FFIType.i32 },
|
|
112834
|
+
CloseHandle: { args: [FFIType.ptr], returns: FFIType.i32 }
|
|
112835
|
+
});
|
|
112836
|
+
return library.symbols;
|
|
112837
|
+
} catch {
|
|
112838
|
+
return null;
|
|
112839
|
+
}
|
|
112840
|
+
}
|
|
112841
|
+
async function readWin32ProcessCreationFiletime(pid) {
|
|
112842
|
+
if (process.platform !== "win32")
|
|
112843
|
+
return null;
|
|
112844
|
+
if (!Number.isSafeInteger(pid) || pid <= 0)
|
|
112845
|
+
return null;
|
|
112846
|
+
kernel32Lookup ??= openKernel32();
|
|
112847
|
+
const kernel32 = await kernel32Lookup;
|
|
112848
|
+
if (kernel32 === null)
|
|
112849
|
+
return null;
|
|
112850
|
+
const handle = kernel32.OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, 0, pid);
|
|
112851
|
+
if (handle === null || handle === 0 || handle === 0n)
|
|
112852
|
+
return null;
|
|
112853
|
+
try {
|
|
112854
|
+
const creation = new BigUint64Array(1);
|
|
112855
|
+
const ok = kernel32.GetProcessTimes(handle, creation, new BigUint64Array(1), new BigUint64Array(1), new BigUint64Array(1));
|
|
112856
|
+
const filetime = creation[0] ?? 0n;
|
|
112857
|
+
return ok === 0 || filetime === 0n ? null : filetime;
|
|
112858
|
+
} finally {
|
|
112859
|
+
kernel32.CloseHandle(handle);
|
|
112860
|
+
}
|
|
112861
|
+
}
|
|
112862
|
+
|
|
112863
|
+
// packages/memory-core/src/locks/process-identity.ts
|
|
112864
|
+
function errorCode(error) {
|
|
112865
|
+
if (!(error instanceof Error) || !("code" in error))
|
|
112442
112866
|
return;
|
|
112443
|
-
|
|
112444
|
-
process.stderr.write(`${message}
|
|
112445
|
-
`);
|
|
112446
|
-
};
|
|
112447
|
-
var isLocked = (error) => error instanceof Error && (LOCKED.test(error.message) || LOCKED.test(String(error.code ?? "")));
|
|
112448
|
-
function credentialId(api) {
|
|
112449
|
-
return createHash10("sha256").update(serviceOrigin(api)).digest("hex");
|
|
112867
|
+
return typeof error.code === "string" ? error.code : undefined;
|
|
112450
112868
|
}
|
|
112451
|
-
function
|
|
112452
|
-
return
|
|
112869
|
+
async function execFileText(command, args) {
|
|
112870
|
+
return await new Promise((resolve) => {
|
|
112871
|
+
execFile7(command, args, { encoding: "utf8", timeout: 2000, windowsHide: true }, (error, stdout) => {
|
|
112872
|
+
if (error !== null) {
|
|
112873
|
+
resolve(null);
|
|
112874
|
+
return;
|
|
112875
|
+
}
|
|
112876
|
+
const value = stdout.trim();
|
|
112877
|
+
resolve(value.length > 0 ? value : null);
|
|
112878
|
+
});
|
|
112879
|
+
});
|
|
112453
112880
|
}
|
|
112454
|
-
function
|
|
112455
|
-
|
|
112456
|
-
|
|
112457
|
-
|
|
112458
|
-
|
|
112459
|
-
|
|
112460
|
-
|
|
112461
|
-
|
|
112462
|
-
|
|
112463
|
-
|
|
112464
|
-
|
|
112465
|
-
|
|
112466
|
-
|
|
112467
|
-
|
|
112468
|
-
|
|
112469
|
-
return
|
|
112470
|
-
|
|
112471
|
-
|
|
112472
|
-
|
|
112473
|
-
|
|
112474
|
-
|
|
112475
|
-
|
|
112476
|
-
|
|
112477
|
-
|
|
112478
|
-
|
|
112479
|
-
|
|
112480
|
-
|
|
112481
|
-
|
|
112482
|
-
|
|
112483
|
-
|
|
112484
|
-
|
|
112485
|
-
|
|
112486
|
-
|
|
112881
|
+
async function readLinuxStartIdentity(pid) {
|
|
112882
|
+
try {
|
|
112883
|
+
const stat = await readFile33(`/proc/${pid}/stat`, "utf8");
|
|
112884
|
+
const commandEnd = stat.lastIndexOf(")");
|
|
112885
|
+
if (commandEnd < 0)
|
|
112886
|
+
return null;
|
|
112887
|
+
const fieldsAfterCommand = stat.slice(commandEnd + 2).trim().split(/\s+/);
|
|
112888
|
+
const startTicks = fieldsAfterCommand[19];
|
|
112889
|
+
return startTicks === undefined ? null : `linux-proc-start-ticks:${startTicks}`;
|
|
112890
|
+
} catch {
|
|
112891
|
+
return null;
|
|
112892
|
+
}
|
|
112893
|
+
}
|
|
112894
|
+
async function readWin32StartIdentity(pid) {
|
|
112895
|
+
if (getPidLiveness(pid) === "dead")
|
|
112896
|
+
return null;
|
|
112897
|
+
const creationFiletime = await readWin32ProcessCreationFiletime(pid);
|
|
112898
|
+
if (creationFiletime !== null)
|
|
112899
|
+
return `win32-creation-filetime:${creationFiletime}`;
|
|
112900
|
+
const value = await execFileText("powershell.exe", [
|
|
112901
|
+
"-NoProfile",
|
|
112902
|
+
"-Command",
|
|
112903
|
+
`(Get-Process -Id ${pid} -ErrorAction SilentlyContinue).StartTime.ToUniversalTime().ToString('o')`
|
|
112904
|
+
]);
|
|
112905
|
+
return value === null ? null : `win32-creation-date:${value}`;
|
|
112906
|
+
}
|
|
112907
|
+
function createProcessStartIdentityReader(read, ownPid) {
|
|
112908
|
+
let ownIdentity;
|
|
112909
|
+
return (pid) => {
|
|
112910
|
+
if (pid !== ownPid)
|
|
112911
|
+
return read(pid);
|
|
112912
|
+
ownIdentity ??= read(pid).then((identity) => {
|
|
112913
|
+
if (identity === null)
|
|
112914
|
+
ownIdentity = undefined;
|
|
112915
|
+
return identity;
|
|
112916
|
+
}, (error) => {
|
|
112917
|
+
ownIdentity = undefined;
|
|
112918
|
+
throw error;
|
|
112919
|
+
});
|
|
112920
|
+
return ownIdentity;
|
|
112487
112921
|
};
|
|
112488
|
-
|
|
112489
|
-
|
|
112490
|
-
|
|
112491
|
-
|
|
112492
|
-
|
|
112493
|
-
|
|
112494
|
-
|
|
112495
|
-
|
|
112496
|
-
|
|
112497
|
-
|
|
112498
|
-
|
|
112499
|
-
|
|
112500
|
-
|
|
112501
|
-
|
|
112502
|
-
|
|
112503
|
-
|
|
112922
|
+
}
|
|
112923
|
+
var getProcessStartIdentity = createProcessStartIdentityReader(readProcessStartIdentity, process.pid);
|
|
112924
|
+
async function readProcessStartIdentity(pid) {
|
|
112925
|
+
if (process.platform === "linux")
|
|
112926
|
+
return await readLinuxStartIdentity(pid);
|
|
112927
|
+
if (process.platform === "darwin" || process.platform === "freebsd") {
|
|
112928
|
+
if (getPidLiveness(pid) === "dead")
|
|
112929
|
+
return null;
|
|
112930
|
+
const startSeconds = await readDarwinProcessStartSeconds(pid);
|
|
112931
|
+
if (startSeconds !== null)
|
|
112932
|
+
return `proc-start-epoch:${startSeconds}`;
|
|
112933
|
+
const value = await execFileText("/bin/ps", ["-o", "lstart=", "-p", String(pid)]);
|
|
112934
|
+
return value === null ? null : `ps-lstart:${value.replace(/\s+/g, " ")}`;
|
|
112935
|
+
}
|
|
112936
|
+
if (process.platform === "win32")
|
|
112937
|
+
return await readWin32StartIdentity(pid);
|
|
112938
|
+
return null;
|
|
112939
|
+
}
|
|
112940
|
+
function identityScheme(identity) {
|
|
112941
|
+
const separator = identity.indexOf(":");
|
|
112942
|
+
return separator <= 0 ? null : identity.slice(0, separator);
|
|
112943
|
+
}
|
|
112944
|
+
function startIdentitiesConflict(recorded, actual) {
|
|
112945
|
+
const recordedScheme = identityScheme(recorded);
|
|
112946
|
+
if (recordedScheme === null || recordedScheme !== identityScheme(actual))
|
|
112947
|
+
return false;
|
|
112948
|
+
return recorded !== actual;
|
|
112949
|
+
}
|
|
112950
|
+
function getPidLiveness(pid) {
|
|
112951
|
+
try {
|
|
112952
|
+
process.kill(pid, 0);
|
|
112953
|
+
return "alive";
|
|
112954
|
+
} catch (error) {
|
|
112955
|
+
const code = errorCode(error);
|
|
112956
|
+
if (code === "ESRCH")
|
|
112957
|
+
return "dead";
|
|
112958
|
+
if (code === "EPERM")
|
|
112959
|
+
return "alive";
|
|
112960
|
+
return "unknown";
|
|
112961
|
+
}
|
|
112962
|
+
}
|
|
112963
|
+
|
|
112964
|
+
// packages/team-core/src/team-state-store/lock-worker-lifetime.ts
|
|
112965
|
+
init_zod();
|
|
112966
|
+
import { randomUUID as randomUUID5 } from "crypto";
|
|
112967
|
+
import { BroadcastChannel, parentPort, threadId } from "worker_threads";
|
|
112968
|
+
var Registration = object({
|
|
112969
|
+
kind: literal("omo-team-lock-register-v1"),
|
|
112970
|
+
incarnation: string2(),
|
|
112971
|
+
challenge: string2()
|
|
112972
|
+
});
|
|
112973
|
+
var Message = discriminatedUnion("kind", [
|
|
112974
|
+
object({ kind: literal("query"), id: string2(), incarnation: string2(), record: string2() }),
|
|
112975
|
+
object({ kind: literal("answer"), id: string2(), released: boolean2() }),
|
|
112976
|
+
object({ kind: literal("hello"), threadId: number2() }),
|
|
112977
|
+
object({ kind: literal("register"), threadId: number2(), challenge: string2() })
|
|
112978
|
+
]);
|
|
112979
|
+
function createState() {
|
|
112980
|
+
const channel = new BroadcastChannel(`omo-team-lock-lifetime-v1-${process.pid}`);
|
|
112981
|
+
channel.unref();
|
|
112982
|
+
const state = {
|
|
112983
|
+
incarnation: randomUUID5(),
|
|
112984
|
+
records: new Map,
|
|
112985
|
+
exited: new Set,
|
|
112986
|
+
observed: new WeakSet,
|
|
112987
|
+
observing: new Map,
|
|
112988
|
+
pending: new Map,
|
|
112989
|
+
channel,
|
|
112990
|
+
installed: false,
|
|
112991
|
+
registered: parentPort === null,
|
|
112992
|
+
registration: undefined,
|
|
112993
|
+
onRegistered: undefined
|
|
112504
112994
|
};
|
|
112505
|
-
|
|
112506
|
-
|
|
112507
|
-
|
|
112508
|
-
const assertUsable = async () => {
|
|
112509
|
-
if (platform !== "linux" || Date.now() < unlockedUntil)
|
|
112510
|
-
return;
|
|
112511
|
-
const lock = await lockProbe();
|
|
112512
|
-
if (lock === "locked")
|
|
112513
|
-
throw new KeychainLockedError(`${platformName} is locked. Unlock it, then try again. Credentials are never saved to a file.`);
|
|
112514
|
-
if (lock === "unlocked") {
|
|
112515
|
-
unlockedUntil = Date.now() + UNLOCKED_REUSE_MS;
|
|
112995
|
+
channel.onmessage = (event) => {
|
|
112996
|
+
const parsed = Message.safeParse(event.data);
|
|
112997
|
+
if (!parsed.success)
|
|
112516
112998
|
return;
|
|
112517
|
-
|
|
112518
|
-
|
|
112519
|
-
|
|
112520
|
-
|
|
112521
|
-
|
|
112522
|
-
|
|
112523
|
-
|
|
112524
|
-
|
|
112525
|
-
await assertUsable();
|
|
112526
|
-
let value;
|
|
112527
|
-
try {
|
|
112528
|
-
value = await answered(secrets);
|
|
112529
|
-
} catch (error) {
|
|
112530
|
-
if (error instanceof KeychainApprovalPendingError)
|
|
112531
|
-
throw error;
|
|
112532
|
-
throw unavailable(error);
|
|
112533
|
-
}
|
|
112534
|
-
if (value === null)
|
|
112535
|
-
return null;
|
|
112536
|
-
try {
|
|
112537
|
-
return schema.parse(JSON.parse(value));
|
|
112538
|
-
} catch {
|
|
112539
|
-
throw new InvalidCredentialState(signInRoute() === "cli" ? "Stored sign-in data is invalid. Run omo logout, then omo login." : "The OmO sign-in saved on this computer can't be read, and it can't be reset from the terminal yet.");
|
|
112999
|
+
const message = parsed.data;
|
|
113000
|
+
switch (message.kind) {
|
|
113001
|
+
case "hello": {
|
|
113002
|
+
const observed = state.observing.get(message.threadId);
|
|
113003
|
+
if (observed !== undefined) {
|
|
113004
|
+
channel.postMessage({ kind: "register", threadId: message.threadId, challenge: observed.challenge });
|
|
113005
|
+
}
|
|
113006
|
+
return;
|
|
112540
113007
|
}
|
|
112541
|
-
|
|
112542
|
-
|
|
112543
|
-
|
|
112544
|
-
|
|
112545
|
-
|
|
112546
|
-
|
|
112547
|
-
|
|
113008
|
+
case "register":
|
|
113009
|
+
if (message.threadId === threadId) {
|
|
113010
|
+
parentPort?.postMessage({
|
|
113011
|
+
kind: "omo-team-lock-register-v1",
|
|
113012
|
+
incarnation: state.incarnation,
|
|
113013
|
+
challenge: message.challenge
|
|
113014
|
+
});
|
|
113015
|
+
state.registered = true;
|
|
113016
|
+
state.onRegistered?.();
|
|
113017
|
+
}
|
|
113018
|
+
return;
|
|
113019
|
+
case "answer":
|
|
113020
|
+
state.pending.get(message.id)?.(message.released);
|
|
113021
|
+
return;
|
|
113022
|
+
case "query": {
|
|
113023
|
+
const status = message.incarnation === state.incarnation ? state.records.get(message.record) : undefined;
|
|
113024
|
+
if (status !== undefined || state.exited.has(message.incarnation)) {
|
|
113025
|
+
channel.postMessage({
|
|
113026
|
+
kind: "answer",
|
|
113027
|
+
id: message.id,
|
|
113028
|
+
released: status === "released" || state.exited.has(message.incarnation)
|
|
113029
|
+
});
|
|
113030
|
+
}
|
|
113031
|
+
return;
|
|
112548
113032
|
}
|
|
112549
|
-
|
|
112550
|
-
|
|
112551
|
-
|
|
112552
|
-
await assertUsable();
|
|
112553
|
-
try {
|
|
112554
|
-
await secrets.delete(key);
|
|
112555
|
-
} catch (error) {
|
|
112556
|
-
throw unavailable(error);
|
|
113033
|
+
default: {
|
|
113034
|
+
const unexpected = message;
|
|
113035
|
+
throw new Error(`Unexpected lock lifetime message: ${unexpected}`);
|
|
112557
113036
|
}
|
|
112558
|
-
forget(secrets);
|
|
112559
113037
|
}
|
|
112560
113038
|
};
|
|
113039
|
+
return state;
|
|
112561
113040
|
}
|
|
112562
|
-
|
|
112563
|
-
|
|
112564
|
-
|
|
112565
|
-
|
|
112566
|
-
|
|
112567
|
-
|
|
112568
|
-
|
|
112569
|
-
const
|
|
112570
|
-
|
|
112571
|
-
const
|
|
112572
|
-
|
|
112573
|
-
|
|
112574
|
-
|
|
112575
|
-
|
|
112576
|
-
response.setHeader("cache-control", "no-store");
|
|
112577
|
-
response.setHeader("referrer-policy", "no-referrer");
|
|
112578
|
-
response.setHeader("content-type", "text/plain; charset=utf-8");
|
|
112579
|
-
const url = new URL(request.url ?? "/", origin);
|
|
112580
|
-
if (request.method !== "GET" || request.headers.host !== new URL(origin).host || url.origin !== origin || url.pathname !== "/callback" || request.headers.forwarded || request.headers["x-forwarded-for"]) {
|
|
112581
|
-
response.writeHead(404).end("Not found");
|
|
112582
|
-
return;
|
|
112583
|
-
}
|
|
112584
|
-
const code = url.searchParams.get("code");
|
|
112585
|
-
const suppliedState = Buffer.from(url.searchParams.get("state") ?? "");
|
|
112586
|
-
const expectedState = Buffer.from(state);
|
|
112587
|
-
if (accepted || url.searchParams.getAll("state").length !== 1 || suppliedState.length !== expectedState.length || !timingSafeEqual(suppliedState, expectedState) || url.searchParams.getAll("code").length !== 1 || !code) {
|
|
112588
|
-
response.writeHead(400).end("Invalid sign-in response");
|
|
113041
|
+
var state2 = globalThis.__omoTeamLockLifetimeV1 ??= createState();
|
|
113042
|
+
var lockOwnerInstanceId = state2.incarnation;
|
|
113043
|
+
function attachWorker(worker) {
|
|
113044
|
+
if (state2.observed.has(worker))
|
|
113045
|
+
return;
|
|
113046
|
+
state2.observed.add(worker);
|
|
113047
|
+
const id = worker.threadId;
|
|
113048
|
+
const challenge = randomUUID5();
|
|
113049
|
+
state2.observing.set(id, { worker, challenge });
|
|
113050
|
+
const incarnations = new Set;
|
|
113051
|
+
let exited = false;
|
|
113052
|
+
worker.on("message", (message) => {
|
|
113053
|
+
const parsed = Registration.safeParse(message);
|
|
113054
|
+
if (!parsed.success || parsed.data.challenge !== challenge)
|
|
112589
113055
|
return;
|
|
112590
|
-
|
|
112591
|
-
|
|
112592
|
-
|
|
112593
|
-
answer.resolve(code);
|
|
113056
|
+
incarnations.add(parsed.data.incarnation);
|
|
113057
|
+
if (exited)
|
|
113058
|
+
state2.exited.add(parsed.data.incarnation);
|
|
112594
113059
|
});
|
|
112595
|
-
|
|
112596
|
-
|
|
112597
|
-
|
|
112598
|
-
|
|
112599
|
-
|
|
112600
|
-
|
|
112601
|
-
|
|
112602
|
-
|
|
112603
|
-
|
|
112604
|
-
|
|
112605
|
-
|
|
112606
|
-
|
|
112607
|
-
|
|
112608
|
-
|
|
112609
|
-
|
|
112610
|
-
|
|
112611
|
-
|
|
112612
|
-
|
|
112613
|
-
|
|
112614
|
-
|
|
112615
|
-
|
|
112616
|
-
try {
|
|
112617
|
-
options.signal?.throwIfAborted();
|
|
112618
|
-
const openerFailed = () => {
|
|
112619
|
-
if (!accepted)
|
|
112620
|
-
throw new BrowserUnavailable("No browser is available; use device sign-in.");
|
|
112621
|
-
};
|
|
112622
|
-
const [code] = await Promise.all([
|
|
112623
|
-
answer.promise,
|
|
112624
|
-
options.open(url.href).then((opened) => {
|
|
112625
|
-
if (!opened)
|
|
112626
|
-
openerFailed();
|
|
112627
|
-
}, openerFailed)
|
|
112628
|
-
]);
|
|
112629
|
-
return { code, codeVerifier: verifier };
|
|
112630
|
-
} finally {
|
|
113060
|
+
worker.once("exit", () => {
|
|
113061
|
+
exited = true;
|
|
113062
|
+
if (state2.observing.get(id)?.worker === worker)
|
|
113063
|
+
state2.observing.delete(id);
|
|
113064
|
+
for (const incarnation of incarnations)
|
|
113065
|
+
state2.exited.add(incarnation);
|
|
113066
|
+
});
|
|
113067
|
+
}
|
|
113068
|
+
function installLockWorkerObserver() {
|
|
113069
|
+
if (state2.installed)
|
|
113070
|
+
return;
|
|
113071
|
+
state2.installed = true;
|
|
113072
|
+
process.on("worker", attachWorker);
|
|
113073
|
+
state2.channel.postMessage({ kind: "hello", threadId });
|
|
113074
|
+
}
|
|
113075
|
+
installLockWorkerObserver();
|
|
113076
|
+
async function registerLockWorker() {
|
|
113077
|
+
if (state2.registered)
|
|
113078
|
+
return;
|
|
113079
|
+
state2.registration ??= new Promise((resolve) => {
|
|
113080
|
+
const finish = () => {
|
|
112631
113081
|
clearTimeout(timer);
|
|
112632
|
-
|
|
112633
|
-
|
|
112634
|
-
|
|
112635
|
-
|
|
112636
|
-
|
|
112637
|
-
|
|
113082
|
+
state2.onRegistered = undefined;
|
|
113083
|
+
resolve();
|
|
113084
|
+
};
|
|
113085
|
+
const timer = setTimeout(finish, 250);
|
|
113086
|
+
state2.onRegistered = finish;
|
|
113087
|
+
state2.channel.postMessage({ kind: "hello", threadId });
|
|
113088
|
+
});
|
|
113089
|
+
await state2.registration;
|
|
112638
113090
|
}
|
|
112639
|
-
|
|
112640
|
-
|
|
112641
|
-
|
|
112642
|
-
|
|
112643
|
-
|
|
112644
|
-
|
|
112645
|
-
|
|
112646
|
-
|
|
112647
|
-
|
|
112648
|
-
|
|
112649
|
-
|
|
112650
|
-
|
|
112651
|
-
|
|
112652
|
-
|
|
112653
|
-
|
|
112654
|
-
|
|
112655
|
-
|
|
112656
|
-
|
|
112657
|
-
|
|
112658
|
-
|
|
112659
|
-
|
|
113091
|
+
function markLockRecordHeld(record) {
|
|
113092
|
+
state2.records.set(record, "held");
|
|
113093
|
+
}
|
|
113094
|
+
function markLockRecordReleased(record) {
|
|
113095
|
+
if (state2.records.has(record))
|
|
113096
|
+
state2.records.set(record, "released");
|
|
113097
|
+
}
|
|
113098
|
+
function forgetLockRecord(record) {
|
|
113099
|
+
state2.records.delete(record);
|
|
113100
|
+
}
|
|
113101
|
+
async function isWorkerLockReleased(incarnation, record) {
|
|
113102
|
+
if (state2.exited.has(incarnation))
|
|
113103
|
+
return true;
|
|
113104
|
+
if (incarnation === state2.incarnation)
|
|
113105
|
+
return state2.records.get(record) === "released";
|
|
113106
|
+
const id = randomUUID5();
|
|
113107
|
+
return await new Promise((resolve) => {
|
|
113108
|
+
const finish = (released) => {
|
|
113109
|
+
clearTimeout(timer);
|
|
113110
|
+
state2.pending.delete(id);
|
|
113111
|
+
resolve(released);
|
|
113112
|
+
};
|
|
113113
|
+
const timer = setTimeout(() => finish(false), 250);
|
|
113114
|
+
state2.pending.set(id, finish);
|
|
113115
|
+
state2.channel.postMessage({ kind: "query", id, incarnation, record });
|
|
113116
|
+
});
|
|
112660
113117
|
}
|
|
112661
|
-
|
|
112662
|
-
// packages/omo-opencode/src/cli/service-auth/session.ts
|
|
112663
|
-
import { mkdir as mkdir11 } from "fs/promises";
|
|
112664
|
-
import { homedir as homedir31 } from "os";
|
|
112665
|
-
import { join as join107 } from "path";
|
|
112666
|
-
|
|
112667
|
-
// packages/team-core/src/team-state-store/lock-publish.ts
|
|
112668
|
-
import { access as access3, open as open2, unlink as unlink2 } from "fs/promises";
|
|
112669
|
-
import { dirname as dirname42 } from "path";
|
|
112670
113118
|
|
|
112671
113119
|
// packages/team-core/src/team-state-store/lock-record.ts
|
|
112672
|
-
|
|
112673
|
-
|
|
112674
|
-
|
|
112675
|
-
|
|
112676
|
-
function buildLockRecord(ownerTag) {
|
|
112677
|
-
return `${ownerTag} ${randomUUID5()}
|
|
113120
|
+
async function buildLockRecord(ownerTag) {
|
|
113121
|
+
await registerLockWorker();
|
|
113122
|
+
const processStart = await getProcessStartIdentity(process.pid);
|
|
113123
|
+
return `${ownerTag} ${randomUUID6()}
|
|
112678
113124
|
${process.pid}
|
|
112679
113125
|
${Date.now()}
|
|
112680
113126
|
${lockOwnerInstanceId}
|
|
113127
|
+
${processStart ?? "unavailable"}
|
|
112681
113128
|
`;
|
|
112682
113129
|
}
|
|
112683
|
-
function
|
|
112684
|
-
heldLockRecords.add(content);
|
|
112685
|
-
}
|
|
112686
|
-
function markLockRecordReleased(content) {
|
|
112687
|
-
heldLockRecords.delete(content);
|
|
112688
|
-
}
|
|
112689
|
-
function errorCode(error) {
|
|
113130
|
+
function errorCode2(error) {
|
|
112690
113131
|
if (!(error instanceof Error) || !("code" in error))
|
|
112691
113132
|
return null;
|
|
112692
113133
|
return typeof error.code === "string" ? error.code : null;
|
|
112693
113134
|
}
|
|
112694
113135
|
function isPathAbsenceError(error) {
|
|
112695
|
-
const code =
|
|
113136
|
+
const code = errorCode2(error);
|
|
112696
113137
|
return code === "ENOENT" || code === "ENOTDIR";
|
|
112697
113138
|
}
|
|
112698
113139
|
function parseLockOwner(content) {
|
|
112699
113140
|
const lines = content.split(/\r?\n/).filter((line) => line.length > 0);
|
|
112700
|
-
if (lines.length !== 3 && lines.length !== 4)
|
|
113141
|
+
if (lines.length !== 3 && lines.length !== 4 && lines.length !== 5)
|
|
112701
113142
|
return null;
|
|
112702
113143
|
const ownerPid = Number.parseInt(lines[1] ?? "", 10);
|
|
112703
113144
|
const acquiredAtEpochMs = Number.parseInt(lines[2] ?? "", 10);
|
|
@@ -112708,24 +113149,14 @@ function parseLockOwner(content) {
|
|
|
112708
113149
|
return {
|
|
112709
113150
|
ownerPid,
|
|
112710
113151
|
acquiredAtEpochMs,
|
|
112711
|
-
instanceId: lines
|
|
113152
|
+
instanceId: lines[3] ?? null,
|
|
113153
|
+
processStart: lines[4] ?? null
|
|
112712
113154
|
};
|
|
112713
113155
|
}
|
|
112714
|
-
function isPidAlive(pid) {
|
|
112715
|
-
try {
|
|
112716
|
-
process.kill(pid, 0);
|
|
112717
|
-
return true;
|
|
112718
|
-
} catch (error) {
|
|
112719
|
-
if (!(error instanceof Error)) {
|
|
112720
|
-
throw error;
|
|
112721
|
-
}
|
|
112722
|
-
return false;
|
|
112723
|
-
}
|
|
112724
|
-
}
|
|
112725
113156
|
async function readLockRecord(lockPath) {
|
|
112726
113157
|
try {
|
|
112727
|
-
const content = await
|
|
112728
|
-
const { mtimeMs } = await
|
|
113158
|
+
const content = await readFile34(lockPath, "utf8");
|
|
113159
|
+
const { mtimeMs } = await stat9(lockPath);
|
|
112729
113160
|
return { content, modifiedAtEpochMs: mtimeMs };
|
|
112730
113161
|
} catch (error) {
|
|
112731
113162
|
if (!(error instanceof Error))
|
|
@@ -112733,23 +113164,30 @@ async function readLockRecord(lockPath) {
|
|
|
112733
113164
|
return null;
|
|
112734
113165
|
}
|
|
112735
113166
|
}
|
|
112736
|
-
function isLockRecordStale(record, staleAfterMs) {
|
|
113167
|
+
async function isLockRecordStale(record, staleAfterMs) {
|
|
112737
113168
|
const owner = parseLockOwner(record.content);
|
|
112738
113169
|
if (owner === null)
|
|
112739
113170
|
return Date.now() - record.modifiedAtEpochMs > staleAfterMs;
|
|
112740
|
-
|
|
112741
|
-
|
|
113171
|
+
const liveness = getPidLiveness(owner.ownerPid);
|
|
113172
|
+
if (liveness === "dead") {
|
|
113173
|
+
return owner.instanceId !== null || Date.now() - owner.acquiredAtEpochMs > staleAfterMs;
|
|
112742
113174
|
}
|
|
112743
|
-
if (
|
|
113175
|
+
if (liveness === "unknown")
|
|
112744
113176
|
return false;
|
|
112745
|
-
if (owner.
|
|
112746
|
-
|
|
112747
|
-
|
|
113177
|
+
if (owner.processStart !== null) {
|
|
113178
|
+
const actual = await getProcessStartIdentity(owner.ownerPid);
|
|
113179
|
+
if (actual !== null && startIdentitiesConflict(owner.processStart, actual))
|
|
113180
|
+
return true;
|
|
113181
|
+
}
|
|
113182
|
+
if (owner.instanceId !== null && owner.ownerPid === process.pid) {
|
|
113183
|
+
return await isWorkerLockReleased(owner.instanceId, record.content);
|
|
113184
|
+
}
|
|
113185
|
+
return false;
|
|
112748
113186
|
}
|
|
112749
113187
|
|
|
112750
113188
|
// packages/team-core/src/team-state-store/lock-publish.ts
|
|
112751
113189
|
async function pathMayExist(path, deps = {}) {
|
|
112752
|
-
const accessPath = deps.access ??
|
|
113190
|
+
const accessPath = deps.access ?? access4;
|
|
112753
113191
|
try {
|
|
112754
113192
|
await accessPath(path);
|
|
112755
113193
|
return true;
|
|
@@ -112760,7 +113198,7 @@ async function pathMayExist(path, deps = {}) {
|
|
|
112760
113198
|
}
|
|
112761
113199
|
}
|
|
112762
113200
|
async function assertRetryableLockOpenError(lockPath, error, deps) {
|
|
112763
|
-
const code =
|
|
113201
|
+
const code = errorCode2(error);
|
|
112764
113202
|
if (code === "EEXIST")
|
|
112765
113203
|
return;
|
|
112766
113204
|
if (code === "EPERM") {
|
|
@@ -112775,9 +113213,9 @@ async function publishLockRecord(lockPath, record) {
|
|
|
112775
113213
|
markLockRecordHeld(record);
|
|
112776
113214
|
let fileHandle;
|
|
112777
113215
|
try {
|
|
112778
|
-
fileHandle = await
|
|
113216
|
+
fileHandle = await open3(lockPath, "wx");
|
|
112779
113217
|
} catch (error) {
|
|
112780
|
-
|
|
113218
|
+
forgetLockRecord(record);
|
|
112781
113219
|
await assertRetryableLockOpenError(lockPath, error);
|
|
112782
113220
|
return false;
|
|
112783
113221
|
}
|
|
@@ -112786,7 +113224,7 @@ async function publishLockRecord(lockPath, record) {
|
|
|
112786
113224
|
} catch (error) {
|
|
112787
113225
|
markLockRecordReleased(record);
|
|
112788
113226
|
await fileHandle.close();
|
|
112789
|
-
await
|
|
113227
|
+
await unlink3(lockPath).catch(() => {
|
|
112790
113228
|
return;
|
|
112791
113229
|
});
|
|
112792
113230
|
throw error;
|
|
@@ -112796,8 +113234,8 @@ async function publishLockRecord(lockPath, record) {
|
|
|
112796
113234
|
}
|
|
112797
113235
|
|
|
112798
113236
|
// packages/team-core/src/team-state-store/lock-reclaim.ts
|
|
112799
|
-
import { createHash as
|
|
112800
|
-
import { unlink as
|
|
113237
|
+
import { createHash as createHash10 } from "crypto";
|
|
113238
|
+
import { unlink as unlink4 } from "fs/promises";
|
|
112801
113239
|
var RECLAIM_UNLINK_ATTEMPTS = 3;
|
|
112802
113240
|
var RECLAIM_UNLINK_RETRY_MS = 25;
|
|
112803
113241
|
function delay2(ms) {
|
|
@@ -112806,11 +113244,11 @@ function delay2(ms) {
|
|
|
112806
113244
|
});
|
|
112807
113245
|
}
|
|
112808
113246
|
function reclaimGuardPath(lockPath, record) {
|
|
112809
|
-
return `${lockPath}.reclaim-${
|
|
113247
|
+
return `${lockPath}.reclaim-${createHash10("sha256").update(record).digest("hex").slice(0, 16)}`;
|
|
112810
113248
|
}
|
|
112811
113249
|
async function unlinkWithRetry(path, deps) {
|
|
112812
113250
|
const wait = deps.delay ?? delay2;
|
|
112813
|
-
const unlinkFile = deps.unlink ??
|
|
113251
|
+
const unlinkFile = deps.unlink ?? unlink4;
|
|
112814
113252
|
for (let attempt = 1;; attempt += 1) {
|
|
112815
113253
|
try {
|
|
112816
113254
|
await unlinkFile(path);
|
|
@@ -112820,7 +113258,7 @@ async function unlinkWithRetry(path, deps) {
|
|
|
112820
113258
|
throw error;
|
|
112821
113259
|
if (isPathAbsenceError(error))
|
|
112822
113260
|
return "absent";
|
|
112823
|
-
const code =
|
|
113261
|
+
const code = errorCode2(error);
|
|
112824
113262
|
if (code !== "EPERM" && code !== "EBUSY" || attempt === RECLAIM_UNLINK_ATTEMPTS)
|
|
112825
113263
|
return "stuck";
|
|
112826
113264
|
await wait(RECLAIM_UNLINK_RETRY_MS);
|
|
@@ -112829,10 +113267,10 @@ async function unlinkWithRetry(path, deps) {
|
|
|
112829
113267
|
}
|
|
112830
113268
|
async function removeLockRecordIfUnchanged(lockPath, expectedRecord, staleAfterMs, deps = {}) {
|
|
112831
113269
|
const guardPath = reclaimGuardPath(lockPath, expectedRecord);
|
|
112832
|
-
const guardRecord = buildLockRecord("lock-reclaim");
|
|
113270
|
+
const guardRecord = await buildLockRecord("lock-reclaim");
|
|
112833
113271
|
if (!await publishLockRecord(guardPath, guardRecord)) {
|
|
112834
113272
|
const guard = await readLockRecord(guardPath);
|
|
112835
|
-
if (guard !== null && isLockRecordStale(guard, staleAfterMs)) {
|
|
113273
|
+
if (guard !== null && await isLockRecordStale(guard, staleAfterMs)) {
|
|
112836
113274
|
await removeLockRecordIfUnchanged(guardPath, guard.content, staleAfterMs, deps);
|
|
112837
113275
|
}
|
|
112838
113276
|
return "busy";
|
|
@@ -112841,13 +113279,16 @@ async function removeLockRecordIfUnchanged(lockPath, expectedRecord, staleAfterM
|
|
|
112841
113279
|
const current = await readLockRecord(lockPath);
|
|
112842
113280
|
if (current === null)
|
|
112843
113281
|
return "absent";
|
|
112844
|
-
if (current.content !== expectedRecord || !isLockRecordStale(current, staleAfterMs))
|
|
113282
|
+
if (current.content !== expectedRecord || !await isLockRecordStale(current, staleAfterMs))
|
|
112845
113283
|
return "changed";
|
|
112846
113284
|
const unlinked = await unlinkWithRetry(lockPath, deps);
|
|
113285
|
+
if (unlinked !== "stuck")
|
|
113286
|
+
forgetLockRecord(expectedRecord);
|
|
112847
113287
|
return unlinked === "absent" ? "absent" : unlinked;
|
|
112848
113288
|
} finally {
|
|
112849
113289
|
markLockRecordReleased(guardRecord);
|
|
112850
|
-
await unlinkWithRetry(guardPath, deps)
|
|
113290
|
+
if (await unlinkWithRetry(guardPath, deps) !== "stuck")
|
|
113291
|
+
forgetLockRecord(guardRecord);
|
|
112851
113292
|
}
|
|
112852
113293
|
}
|
|
112853
113294
|
|
|
@@ -112866,7 +113307,7 @@ async function acquireLock(lockPath, ownerTag, staleAfterMs) {
|
|
|
112866
113307
|
if (Date.now() - startedAt > LOCK_WAIT_TIMEOUT_MS) {
|
|
112867
113308
|
throw new Error(`Timed out acquiring lock: ${lockPath}`);
|
|
112868
113309
|
}
|
|
112869
|
-
const record = buildLockRecord(ownerTag);
|
|
113310
|
+
const record = await buildLockRecord(ownerTag);
|
|
112870
113311
|
if (await publishLockRecord(lockPath, record))
|
|
112871
113312
|
return record;
|
|
112872
113313
|
const outcome = await reapStaleLock(lockPath, staleAfterMs);
|
|
@@ -112883,26 +113324,327 @@ async function withLock(lockPath, fn, opts) {
|
|
|
112883
113324
|
return await fn();
|
|
112884
113325
|
} finally {
|
|
112885
113326
|
markLockRecordReleased(record);
|
|
112886
|
-
await removeLockRecordIfUnchanged(lockPath, record, staleAfterMs);
|
|
113327
|
+
const outcome = await removeLockRecordIfUnchanged(lockPath, record, staleAfterMs);
|
|
113328
|
+
if (outcome === "removed" || outcome === "absent" || outcome === "changed")
|
|
113329
|
+
forgetLockRecord(record);
|
|
112887
113330
|
}
|
|
112888
113331
|
}
|
|
112889
113332
|
async function reapStaleLock(lockPath, staleAfterMs = DEFAULT_STALE_AFTER_MS, deps = {}) {
|
|
112890
113333
|
const observed = await readLockRecord(lockPath);
|
|
112891
113334
|
if (observed === null)
|
|
112892
113335
|
return "absent";
|
|
112893
|
-
if (!isLockRecordStale(observed, staleAfterMs))
|
|
113336
|
+
if (!await isLockRecordStale(observed, staleAfterMs))
|
|
112894
113337
|
return "changed";
|
|
112895
113338
|
return await removeLockRecordIfUnchanged(lockPath, observed.content, staleAfterMs, deps);
|
|
112896
113339
|
}
|
|
112897
113340
|
|
|
113341
|
+
// packages/omo-opencode/src/cli/service-auth/credential-lock.ts
|
|
113342
|
+
var held = new AsyncLocalStorage3;
|
|
113343
|
+
function credentialLockPaths(api, home = homedir31()) {
|
|
113344
|
+
const id = createHash11("sha256").update(serviceOrigin(api)).digest("hex");
|
|
113345
|
+
const directory = join106(home, ".omo", "session-locks");
|
|
113346
|
+
return { directory, lock: join106(directory, `${id}.lock`), desktopRecord: join106(directory, `${id}.desktop-generation.json`) };
|
|
113347
|
+
}
|
|
113348
|
+
async function withCredentialLock(api, action, home = homedir31(), ownerTag = "cli-session") {
|
|
113349
|
+
const { directory, lock } = credentialLockPaths(api, home);
|
|
113350
|
+
const owned = held.getStore();
|
|
113351
|
+
if (owned?.has(lock))
|
|
113352
|
+
return action();
|
|
113353
|
+
await mkdir11(directory, { recursive: true, mode: 448 });
|
|
113354
|
+
return withLock(lock, () => held.run(new Set([...owned ?? [], lock]), action), {
|
|
113355
|
+
ownerTag,
|
|
113356
|
+
staleAfterMs: Number.POSITIVE_INFINITY
|
|
113357
|
+
});
|
|
113358
|
+
}
|
|
113359
|
+
|
|
113360
|
+
// packages/omo-opencode/src/cli/service-auth/keystore.ts
|
|
113361
|
+
class CredentialStoreError extends SignInError {
|
|
113362
|
+
}
|
|
113363
|
+
|
|
113364
|
+
class KeychainLockedError extends CredentialStoreError {
|
|
113365
|
+
}
|
|
113366
|
+
class InvalidCredentialState extends SignInError {
|
|
113367
|
+
}
|
|
113368
|
+
|
|
113369
|
+
class CredentialIdentityChanged extends Error {
|
|
113370
|
+
constructor() {
|
|
113371
|
+
super("The stored sign-in changed; the captured account is no longer current.");
|
|
113372
|
+
}
|
|
113373
|
+
}
|
|
113374
|
+
|
|
113375
|
+
class KeychainApprovalPendingError extends CredentialStoreError {
|
|
113376
|
+
}
|
|
113377
|
+
var SESSION_READ_WAIT = { kind: "bounded", deadlineMs: 5000 };
|
|
113378
|
+
var INTERACTIVE_READ_WAIT = {
|
|
113379
|
+
kind: "interactive",
|
|
113380
|
+
noticeAfterMs: 2000,
|
|
113381
|
+
notice: (message) => process.stderr.write(`${message}
|
|
113382
|
+
`)
|
|
113383
|
+
};
|
|
113384
|
+
var processReads = new WeakMap;
|
|
113385
|
+
var LOCKED = /-25308|errSecInteractionNotAllowed|interaction is not allowed|locked collection/i;
|
|
113386
|
+
var UNLOCKED_REUSE_MS = 30000;
|
|
113387
|
+
var fallbackNoticed = false;
|
|
113388
|
+
var stderrNoticeOncePerProcess = (message) => {
|
|
113389
|
+
if (fallbackNoticed)
|
|
113390
|
+
return;
|
|
113391
|
+
fallbackNoticed = true;
|
|
113392
|
+
process.stderr.write(`${message}
|
|
113393
|
+
`);
|
|
113394
|
+
};
|
|
113395
|
+
var isLocked = (error) => error instanceof Error && (LOCKED.test(error.message) || LOCKED.test(String(error.code ?? "")));
|
|
113396
|
+
function credentialId(api) {
|
|
113397
|
+
return createHash12("sha256").update(serviceOrigin(api)).digest("hex");
|
|
113398
|
+
}
|
|
113399
|
+
function createCredentialStore(api, options = {}) {
|
|
113400
|
+
const store = createSealedStore(api, "omo-cli", credentialSchema, options.secrets, options.platform, options.lockProbe, options.notice, options.wait, (current, value) => {
|
|
113401
|
+
const sameIdentity = current !== null && current.device.id === value.device.id && current.signingPrivateKey === value.signingPrivateKey && current.sealingPrivateKey === value.sealingPrivateKey && (value.accountId === undefined || current.accountId === undefined || current.accountId === value.accountId);
|
|
113402
|
+
const accountId = value.accountId ?? (sameIdentity ? current?.accountId : undefined);
|
|
113403
|
+
return {
|
|
113404
|
+
...value,
|
|
113405
|
+
...accountId === undefined ? {} : { accountId },
|
|
113406
|
+
credentialGeneration: sameIdentity ? current?.credentialGeneration ?? randomUUID7() : randomUUID7()
|
|
113407
|
+
};
|
|
113408
|
+
});
|
|
113409
|
+
return {
|
|
113410
|
+
read: store.read,
|
|
113411
|
+
readAuthoritative: store.readAuthoritative,
|
|
113412
|
+
write: (value) => withCredentialLock(api, () => store.write(value), options.home),
|
|
113413
|
+
clear: () => withCredentialLock(api, store.clear, options.home)
|
|
113414
|
+
};
|
|
113415
|
+
}
|
|
113416
|
+
function createSealedStore(api, namespace, schema, secrets = typeof Bun === "undefined" ? null : Bun.secrets, platform = process.platform, lockProbe = probeSecretServiceLock, notice = stderrNoticeOncePerProcess, wait = SESSION_READ_WAIT, amendWrite) {
|
|
113417
|
+
if (!secrets)
|
|
113418
|
+
throw new SignInError("OmO sign-in needs Bun 1.4 or newer with OS credential storage. No file fallback is available.");
|
|
113419
|
+
const platformName = platform === "darwin" ? "macOS Keychain" : platform === "linux" ? "Linux Secret Service (libsecret and an unlocked keyring)" : platform === "win32" ? "Windows Credential Manager" : null;
|
|
113420
|
+
if (platformName === null)
|
|
113421
|
+
throw new SignInError("This platform has no supported OS credential store.");
|
|
113422
|
+
const key = { service: namespace, name: credentialId(api) };
|
|
113423
|
+
const slot = `${key.service}
|
|
113424
|
+
${key.name}`;
|
|
113425
|
+
const readsOf = (api) => {
|
|
113426
|
+
const known = processReads.get(api);
|
|
113427
|
+
if (known !== undefined)
|
|
113428
|
+
return known;
|
|
113429
|
+
const created = new Map;
|
|
113430
|
+
processReads.set(api, created);
|
|
113431
|
+
return created;
|
|
113432
|
+
};
|
|
113433
|
+
const forget = (api) => {
|
|
113434
|
+
readsOf(api).delete(slot);
|
|
113435
|
+
};
|
|
113436
|
+
const sharedRead = (api) => {
|
|
113437
|
+
const reads = readsOf(api);
|
|
113438
|
+
const pending = reads.get(slot);
|
|
113439
|
+
if (pending !== undefined)
|
|
113440
|
+
return pending;
|
|
113441
|
+
const read = Promise.resolve().then(() => api.get(key));
|
|
113442
|
+
const done = () => {
|
|
113443
|
+
if (reads.get(slot) === read)
|
|
113444
|
+
reads.delete(slot);
|
|
113445
|
+
};
|
|
113446
|
+
read.then(done, done);
|
|
113447
|
+
reads.set(slot, read);
|
|
113448
|
+
return read;
|
|
113449
|
+
};
|
|
113450
|
+
const waiting = platform === "darwin" ? `macOS Keychain is waiting for your approval: answer the "${basename15(process.execPath)} wants to access key ${namespace}" dialog ("Always Allow" stops it asking again)` : `${platformName} has not answered; it may be waiting for your approval or an unlock in a system dialog`;
|
|
113451
|
+
const answered = async (api, fresh = false) => {
|
|
113452
|
+
const read = fresh ? Promise.resolve().then(() => api.get(key)) : sharedRead(api);
|
|
113453
|
+
let timer;
|
|
113454
|
+
try {
|
|
113455
|
+
if (wait.kind === "interactive") {
|
|
113456
|
+
timer = setTimeout(() => wait.notice(`omo: ${waiting}.`), wait.noticeAfterMs);
|
|
113457
|
+
return await read;
|
|
113458
|
+
}
|
|
113459
|
+
const expired = new Promise((_, reject) => {
|
|
113460
|
+
timer = setTimeout(() => reject(new KeychainApprovalPendingError(`${waiting}, then try again. Credentials are never saved to a file.`)), wait.deadlineMs);
|
|
113461
|
+
});
|
|
113462
|
+
return await Promise.race([read, expired]);
|
|
113463
|
+
} finally {
|
|
113464
|
+
clearTimeout(timer);
|
|
113465
|
+
}
|
|
113466
|
+
};
|
|
113467
|
+
const unavailable = (error) => isLocked(error) ? new KeychainLockedError(`${platformName} is locked. Unlock it, then try again. Credentials are never saved to a file.`) : new CredentialStoreError(`Cannot access ${platformName}. Unlock or enable the OS credential store and try again. Credentials are never saved to a file.`);
|
|
113468
|
+
let unlockedUntil = 0;
|
|
113469
|
+
let noticed = false;
|
|
113470
|
+
const assertUsable = async () => {
|
|
113471
|
+
if (platform !== "linux" || Date.now() < unlockedUntil)
|
|
113472
|
+
return;
|
|
113473
|
+
const lock = await lockProbe();
|
|
113474
|
+
if (lock === "locked")
|
|
113475
|
+
throw new KeychainLockedError(`${platformName} is locked. Unlock it, then try again. Credentials are never saved to a file.`);
|
|
113476
|
+
if (lock === "unlocked") {
|
|
113477
|
+
unlockedUntil = Date.now() + UNLOCKED_REUSE_MS;
|
|
113478
|
+
return;
|
|
113479
|
+
}
|
|
113480
|
+
if (!noticed) {
|
|
113481
|
+
noticed = true;
|
|
113482
|
+
notice("omo: could not check whether the keyring is locked (gdbus or the Secret Service did not answer); using libsecret directly.");
|
|
113483
|
+
}
|
|
113484
|
+
};
|
|
113485
|
+
const parsedRead = async (fresh) => {
|
|
113486
|
+
await assertUsable();
|
|
113487
|
+
let value;
|
|
113488
|
+
try {
|
|
113489
|
+
value = await answered(secrets, fresh);
|
|
113490
|
+
} catch (error) {
|
|
113491
|
+
if (error instanceof KeychainApprovalPendingError)
|
|
113492
|
+
throw error;
|
|
113493
|
+
throw unavailable(error);
|
|
113494
|
+
}
|
|
113495
|
+
if (value === null)
|
|
113496
|
+
return null;
|
|
113497
|
+
try {
|
|
113498
|
+
return schema.parse(JSON.parse(value));
|
|
113499
|
+
} catch {
|
|
113500
|
+
throw new InvalidCredentialState(signInRoute() === "cli" ? "Stored sign-in data is invalid. Run omo account forget, then omo login." : "The OmO sign-in saved on this computer can't be read. Run omo account forget to remove it, then sign in again in the desktop app.");
|
|
113501
|
+
}
|
|
113502
|
+
};
|
|
113503
|
+
return {
|
|
113504
|
+
read: () => parsedRead(false),
|
|
113505
|
+
readAuthoritative: () => parsedRead(true),
|
|
113506
|
+
async write(value) {
|
|
113507
|
+
await assertUsable();
|
|
113508
|
+
try {
|
|
113509
|
+
let next = value;
|
|
113510
|
+
if (amendWrite !== undefined) {
|
|
113511
|
+
const raw = await answered(secrets, true);
|
|
113512
|
+
let previous = null;
|
|
113513
|
+
if (raw !== null) {
|
|
113514
|
+
try {
|
|
113515
|
+
previous = schema.parse(JSON.parse(raw));
|
|
113516
|
+
} catch {}
|
|
113517
|
+
}
|
|
113518
|
+
next = amendWrite(previous, value);
|
|
113519
|
+
}
|
|
113520
|
+
await secrets.set({ ...key, value: JSON.stringify(schema.parse(next)) });
|
|
113521
|
+
} catch (error) {
|
|
113522
|
+
throw unavailable(error);
|
|
113523
|
+
}
|
|
113524
|
+
forget(secrets);
|
|
113525
|
+
},
|
|
113526
|
+
async clear() {
|
|
113527
|
+
await assertUsable();
|
|
113528
|
+
try {
|
|
113529
|
+
await secrets.delete(key);
|
|
113530
|
+
} catch (error) {
|
|
113531
|
+
throw unavailable(error);
|
|
113532
|
+
}
|
|
113533
|
+
forget(secrets);
|
|
113534
|
+
}
|
|
113535
|
+
};
|
|
113536
|
+
}
|
|
113537
|
+
|
|
113538
|
+
// packages/omo-opencode/src/cli/service-auth/loopback.ts
|
|
113539
|
+
import { createHash as createHash13, randomBytes as randomBytes5, timingSafeEqual } from "crypto";
|
|
113540
|
+
import { createServer as createServer3 } from "http";
|
|
113541
|
+
class BrowserUnavailable extends SignInError {
|
|
113542
|
+
}
|
|
113543
|
+
async function authorize(options) {
|
|
113544
|
+
const verifier = randomBytes5(32).toString("base64url");
|
|
113545
|
+
const state = randomBytes5(32).toString("base64url");
|
|
113546
|
+
const answer = Promise.withResolvers();
|
|
113547
|
+
const abort = () => answer.reject(new SignInError("Browser sign-in cancelled or timed out."));
|
|
113548
|
+
let accepted = false;
|
|
113549
|
+
let origin = "";
|
|
113550
|
+
const server = createServer3((request, response) => {
|
|
113551
|
+
response.setHeader("cache-control", "no-store");
|
|
113552
|
+
response.setHeader("referrer-policy", "no-referrer");
|
|
113553
|
+
response.setHeader("content-type", "text/plain; charset=utf-8");
|
|
113554
|
+
const url = new URL(request.url ?? "/", origin);
|
|
113555
|
+
if (request.method !== "GET" || request.headers.host !== new URL(origin).host || url.origin !== origin || url.pathname !== "/callback" || request.headers.forwarded || request.headers["x-forwarded-for"]) {
|
|
113556
|
+
response.writeHead(404).end("Not found");
|
|
113557
|
+
return;
|
|
113558
|
+
}
|
|
113559
|
+
const code = url.searchParams.get("code");
|
|
113560
|
+
const suppliedState = Buffer.from(url.searchParams.get("state") ?? "");
|
|
113561
|
+
const expectedState = Buffer.from(state);
|
|
113562
|
+
if (accepted || url.searchParams.getAll("state").length !== 1 || suppliedState.length !== expectedState.length || !timingSafeEqual(suppliedState, expectedState) || url.searchParams.getAll("code").length !== 1 || !code) {
|
|
113563
|
+
response.writeHead(400).end("Invalid sign-in response");
|
|
113564
|
+
return;
|
|
113565
|
+
}
|
|
113566
|
+
accepted = true;
|
|
113567
|
+
response.writeHead(200).end("Return to the terminal to finish signing in.");
|
|
113568
|
+
answer.resolve(code);
|
|
113569
|
+
});
|
|
113570
|
+
try {
|
|
113571
|
+
await new Promise((resolve, reject) => {
|
|
113572
|
+
server.once("error", reject);
|
|
113573
|
+
server.listen(0, "127.0.0.1", () => {
|
|
113574
|
+
server.off("error", reject);
|
|
113575
|
+
resolve();
|
|
113576
|
+
});
|
|
113577
|
+
});
|
|
113578
|
+
const address = server.address();
|
|
113579
|
+
if (!address || typeof address === "string")
|
|
113580
|
+
throw new SignInError("Unable to start the sign-in callback.");
|
|
113581
|
+
origin = `http://127.0.0.1:${address.port}`;
|
|
113582
|
+
const url = new URL(serviceOrigin(options.accounts));
|
|
113583
|
+
url.search = new URLSearchParams({
|
|
113584
|
+
redirect_uri: `${origin}/callback`,
|
|
113585
|
+
code_challenge: createHash13("sha256").update(verifier).digest("base64url"),
|
|
113586
|
+
code_challenge_method: "S256",
|
|
113587
|
+
state
|
|
113588
|
+
}).toString();
|
|
113589
|
+
const timer = setTimeout(abort, 5 * 60000);
|
|
113590
|
+
options.signal?.addEventListener("abort", abort, { once: true });
|
|
113591
|
+
try {
|
|
113592
|
+
options.signal?.throwIfAborted();
|
|
113593
|
+
const openerFailed = () => {
|
|
113594
|
+
if (!accepted)
|
|
113595
|
+
throw new BrowserUnavailable("No browser is available; use device sign-in.");
|
|
113596
|
+
};
|
|
113597
|
+
const [code] = await Promise.all([
|
|
113598
|
+
answer.promise,
|
|
113599
|
+
options.open(url.href).then((opened) => {
|
|
113600
|
+
if (!opened)
|
|
113601
|
+
openerFailed();
|
|
113602
|
+
}, openerFailed)
|
|
113603
|
+
]);
|
|
113604
|
+
return { code, codeVerifier: verifier };
|
|
113605
|
+
} finally {
|
|
113606
|
+
clearTimeout(timer);
|
|
113607
|
+
options.signal?.removeEventListener("abort", abort);
|
|
113608
|
+
}
|
|
113609
|
+
} finally {
|
|
113610
|
+
server.closeAllConnections();
|
|
113611
|
+
await new Promise((resolve) => server.close(() => resolve()));
|
|
113612
|
+
}
|
|
113613
|
+
}
|
|
113614
|
+
async function loginLoopback(session, options) {
|
|
113615
|
+
await session.ready();
|
|
113616
|
+
const keys = generateDeviceKeys();
|
|
113617
|
+
for (;; ) {
|
|
113618
|
+
const authorization = await authorize({ accounts: options.accounts, open: options.open, signal: session.signal });
|
|
113619
|
+
try {
|
|
113620
|
+
const grant = parseReply(grantSchema, await session.request("/v1/session/exchange", jsonRequest({
|
|
113621
|
+
...authorization,
|
|
113622
|
+
kind: "cli",
|
|
113623
|
+
deviceName: options.name,
|
|
113624
|
+
platform: options.platform,
|
|
113625
|
+
...keys.public
|
|
113626
|
+
})));
|
|
113627
|
+
await session.save({ ...grant, ...keys.private });
|
|
113628
|
+
return;
|
|
113629
|
+
} catch (error) {
|
|
113630
|
+
if (await session.removeForLimit(error, options.chooseDevice))
|
|
113631
|
+
continue;
|
|
113632
|
+
throw new SignInError("Sign-in cancelled. No device was removed.");
|
|
113633
|
+
}
|
|
113634
|
+
}
|
|
113635
|
+
}
|
|
113636
|
+
|
|
113637
|
+
// packages/omo-opencode/src/cli/service-auth/session.ts
|
|
113638
|
+
import { homedir as homedir32 } from "os";
|
|
113639
|
+
|
|
112898
113640
|
// packages/omo-opencode/src/cli/service-auth/signed-out-marker.ts
|
|
112899
113641
|
init_zod();
|
|
112900
|
-
import { mkdir as
|
|
112901
|
-
import { dirname as dirname43, join as
|
|
113642
|
+
import { mkdir as mkdir12, readFile as readFile35, rename as rename8, rm as rm17, writeFile as writeFile17 } from "fs/promises";
|
|
113643
|
+
import { dirname as dirname43, join as join107 } from "path";
|
|
112902
113644
|
var markerSchema = object({ device: string2().nullable(), at: string2() });
|
|
112903
|
-
var signedOutMarkerPath = (home, credential) =>
|
|
113645
|
+
var signedOutMarkerPath = (home, credential) => join107(home, ".omo", "account-state", `${credential}.signed-out.json`);
|
|
112904
113646
|
async function readSignedOutMarker(path) {
|
|
112905
|
-
const text = await
|
|
113647
|
+
const text = await readFile35(path, "utf8").catch(() => null);
|
|
112906
113648
|
if (text === null)
|
|
112907
113649
|
return null;
|
|
112908
113650
|
let value;
|
|
@@ -112915,12 +113657,12 @@ async function readSignedOutMarker(path) {
|
|
|
112915
113657
|
return parsed.success ? parsed.data : null;
|
|
112916
113658
|
}
|
|
112917
113659
|
async function writeSignedOutMarker(path, device) {
|
|
112918
|
-
await
|
|
113660
|
+
await mkdir12(dirname43(path), { recursive: true, mode: 448 });
|
|
112919
113661
|
const staging = `${path}.${process.pid}.tmp`;
|
|
112920
|
-
await
|
|
112921
|
-
await
|
|
113662
|
+
await writeFile17(staging, JSON.stringify({ device, at: new Date().toISOString() }), { mode: 384 });
|
|
113663
|
+
await rename8(staging, path);
|
|
112922
113664
|
}
|
|
112923
|
-
var clearSignedOutMarker = (path) =>
|
|
113665
|
+
var clearSignedOutMarker = (path) => rm17(path, { force: true });
|
|
112924
113666
|
|
|
112925
113667
|
// packages/omo-opencode/src/cli/service-auth/session.ts
|
|
112926
113668
|
class SessionEnded extends SignInError {
|
|
@@ -112935,30 +113677,29 @@ class SessionEnded extends SignInError {
|
|
|
112935
113677
|
var DEVICE_REVOKING_REFUSALS = new Set(["account_deleted", "reauth_required", "device_revoked"]);
|
|
112936
113678
|
function createSession(options) {
|
|
112937
113679
|
const api = serviceOrigin(options.api);
|
|
113680
|
+
const now = options.now ?? Date.now;
|
|
112938
113681
|
const { store, signal } = options;
|
|
112939
|
-
const
|
|
112940
|
-
const lockPath = join107(directory, `${credentialId(api)}.lock`);
|
|
112941
|
-
const markerPath = signedOutMarkerPath(options.home ?? homedir31(), credentialId(api));
|
|
113682
|
+
const markerPath = signedOutMarkerPath(options.home ?? homedir32(), credentialId(api));
|
|
112942
113683
|
async function locked(action) {
|
|
112943
|
-
await mkdir11(directory, { recursive: true, mode: 448 });
|
|
112944
113684
|
signal?.throwIfAborted();
|
|
112945
|
-
return
|
|
113685
|
+
return withCredentialLock(api, async () => {
|
|
112946
113686
|
signal?.throwIfAborted();
|
|
112947
113687
|
return action();
|
|
112948
|
-
},
|
|
113688
|
+
}, options.home);
|
|
112949
113689
|
}
|
|
112950
113690
|
const request = (path, init) => requestApi(api, path, init, signal);
|
|
112951
|
-
|
|
112952
|
-
|
|
112953
|
-
|
|
112954
|
-
|
|
112955
|
-
if (Date.parse(current.accessTokenExpiresAt) >
|
|
112956
|
-
return current
|
|
113691
|
+
async function refreshed(current) {
|
|
113692
|
+
if (current.refreshState === "uncertain" || current.refreshAttempt !== undefined) {
|
|
113693
|
+
throw new SessionEnded(`Refresh recovery can no longer be proved safe. ${signInHint("again")}`, false, "refresh_recovery_expired");
|
|
113694
|
+
}
|
|
113695
|
+
if (Date.parse(current.accessTokenExpiresAt) > now() + 30000)
|
|
113696
|
+
return current;
|
|
112957
113697
|
await store.write({ ...current, refreshState: "uncertain" });
|
|
112958
113698
|
try {
|
|
112959
113699
|
const tokens = parseReply(tokenSchema, await request("/v1/session/refresh", jsonRequest({ refreshToken: current.refreshToken })));
|
|
112960
|
-
|
|
112961
|
-
|
|
113700
|
+
const successor = { ...current, ...tokens };
|
|
113701
|
+
await store.write(successor);
|
|
113702
|
+
return successor;
|
|
112962
113703
|
} catch (error) {
|
|
112963
113704
|
if (error instanceof CredentialStoreError)
|
|
112964
113705
|
throw error;
|
|
@@ -112970,12 +113711,19 @@ function createSession(options) {
|
|
|
112970
113711
|
await store.write(current);
|
|
112971
113712
|
throw error;
|
|
112972
113713
|
}
|
|
112973
|
-
throw
|
|
113714
|
+
throw new SessionEnded(`The refresh outcome is unknown. Saved credentials and keys were retained. ${signInHint("again")}`, false, "refresh_recovery_expired");
|
|
112974
113715
|
}
|
|
112975
113716
|
}
|
|
113717
|
+
async function snapshot() {
|
|
113718
|
+
return locked(async () => {
|
|
113719
|
+
const current = await store.read();
|
|
113720
|
+
return current === null ? null : refreshed(current);
|
|
113721
|
+
});
|
|
113722
|
+
}
|
|
112976
113723
|
return {
|
|
112977
113724
|
request,
|
|
112978
113725
|
signal,
|
|
113726
|
+
transaction: locked,
|
|
112979
113727
|
async ready() {
|
|
112980
113728
|
await store.read();
|
|
112981
113729
|
},
|
|
@@ -112987,18 +113735,32 @@ function createSession(options) {
|
|
|
112987
113735
|
},
|
|
112988
113736
|
signedOutMarker: () => readSignedOutMarker(markerPath),
|
|
112989
113737
|
clearSignedOutMarker: () => clearSignedOutMarker(markerPath),
|
|
112990
|
-
async update(action) {
|
|
112991
|
-
return locked(async () =>
|
|
113738
|
+
async update(action, options = {}) {
|
|
113739
|
+
return locked(async () => {
|
|
113740
|
+
let current;
|
|
113741
|
+
try {
|
|
113742
|
+
current = await store.readAuthoritative();
|
|
113743
|
+
} catch (error) {
|
|
113744
|
+
if (!options.replaceInvalid || !(error instanceof InvalidCredentialState))
|
|
113745
|
+
throw error;
|
|
113746
|
+
current = null;
|
|
113747
|
+
}
|
|
113748
|
+
return action(current);
|
|
113749
|
+
});
|
|
112992
113750
|
},
|
|
113751
|
+
async forget() {
|
|
113752
|
+
await locked(() => store.clear());
|
|
113753
|
+
},
|
|
113754
|
+
accessSnapshot: snapshot,
|
|
112993
113755
|
async logout() {
|
|
112994
113756
|
return locked(async () => {
|
|
112995
113757
|
let current = null;
|
|
112996
113758
|
try {
|
|
112997
|
-
current = await store.
|
|
113759
|
+
current = await store.readAuthoritative();
|
|
112998
113760
|
if (current !== null) {
|
|
112999
113761
|
if (current.refreshState === "uncertain")
|
|
113000
113762
|
return false;
|
|
113001
|
-
const access = Date.parse(current.accessTokenExpiresAt) <=
|
|
113763
|
+
const access = Date.parse(current.accessTokenExpiresAt) <= now() ? (await refreshed(current)).accessToken : current.accessToken;
|
|
113002
113764
|
await request(`/v1/devices/${encodeURIComponent(current.device.id)}`, {
|
|
113003
113765
|
method: "DELETE",
|
|
113004
113766
|
headers: { authorization: `Bearer ${access}` }
|
|
@@ -113017,12 +113779,19 @@ function createSession(options) {
|
|
|
113017
113779
|
}
|
|
113018
113780
|
});
|
|
113019
113781
|
},
|
|
113020
|
-
async accessToken() {
|
|
113782
|
+
async accessToken(expect) {
|
|
113783
|
+
signal?.throwIfAborted();
|
|
113784
|
+
const snapshot = await store.read();
|
|
113785
|
+
signal?.throwIfAborted();
|
|
113786
|
+
if (snapshot !== null && snapshot.refreshState !== "uncertain" && snapshot.refreshAttempt === undefined && Date.parse(snapshot.accessTokenExpiresAt) > now() + 30000 && (expect === undefined || expect(snapshot)))
|
|
113787
|
+
return snapshot.accessToken;
|
|
113021
113788
|
return locked(async () => {
|
|
113022
|
-
const current = await store.
|
|
113789
|
+
const current = await store.readAuthoritative();
|
|
113023
113790
|
if (current === null)
|
|
113024
113791
|
throw new SignInError(`Not signed in. ${signInHint("first")}`);
|
|
113025
|
-
|
|
113792
|
+
if (expect !== undefined && !expect(current))
|
|
113793
|
+
throw new CredentialIdentityChanged;
|
|
113794
|
+
return (await refreshed(current)).accessToken;
|
|
113026
113795
|
});
|
|
113027
113796
|
},
|
|
113028
113797
|
async removeForLimit(error, choose) {
|
|
@@ -113351,12 +114120,12 @@ async function boulder(options) {
|
|
|
113351
114120
|
}
|
|
113352
114121
|
// packages/omo-opencode/src/cli/codex-ulw-loop.ts
|
|
113353
114122
|
import { spawn as spawn6 } from "child_process";
|
|
113354
|
-
import { existsSync as existsSync67, readFileSync as
|
|
113355
|
-
import { homedir as
|
|
114123
|
+
import { existsSync as existsSync67, readFileSync as readFileSync45, realpathSync as realpathSync14 } from "fs";
|
|
114124
|
+
import { homedir as homedir33 } from "os";
|
|
113356
114125
|
var ULW_LOOP_DELEGATION_SENTINEL = "OMO_ULW_LOOP_DELEGATED";
|
|
113357
114126
|
function resolveCodexUlwLoopCommand(input = {}) {
|
|
113358
114127
|
const env = input.env ?? process.env;
|
|
113359
|
-
const homeDir = input.homeDir ??
|
|
114128
|
+
const homeDir = input.homeDir ?? homedir33();
|
|
113360
114129
|
const localComponentBin = resolveLocalUlwLoopBin(env, homeDir);
|
|
113361
114130
|
if (localComponentBin !== null)
|
|
113362
114131
|
return { executable: localComponentBin, argsPrefix: [] };
|
|
@@ -113401,7 +114170,7 @@ function resolveLegacyLocalOmoBin(env, homeDir, currentExecutablePaths) {
|
|
|
113401
114170
|
}
|
|
113402
114171
|
function isGeneratedRuntimeWrapper(candidate) {
|
|
113403
114172
|
try {
|
|
113404
|
-
return
|
|
114173
|
+
return readFileSync45(candidate, "utf8").includes(RUNTIME_WRAPPER_MARKER);
|
|
113405
114174
|
} catch (error) {
|
|
113406
114175
|
if (error instanceof Error)
|
|
113407
114176
|
return false;
|
|
@@ -113414,7 +114183,7 @@ function isCurrentExecutable(candidate, currentExecutablePaths) {
|
|
|
113414
114183
|
}
|
|
113415
114184
|
function realpathOrSelf2(path) {
|
|
113416
114185
|
try {
|
|
113417
|
-
return
|
|
114186
|
+
return realpathSync14(path);
|
|
113418
114187
|
} catch (error) {
|
|
113419
114188
|
if (error instanceof Error)
|
|
113420
114189
|
return path;
|
|
@@ -113599,7 +114368,7 @@ function linkedWorktrees(records) {
|
|
|
113599
114368
|
}
|
|
113600
114369
|
// packages/omo-opencode/src/cli/worktree-sweep/sweep.ts
|
|
113601
114370
|
import { existsSync as existsSync68 } from "fs";
|
|
113602
|
-
import { stat as
|
|
114371
|
+
import { stat as stat10 } from "fs/promises";
|
|
113603
114372
|
import os7 from "os";
|
|
113604
114373
|
import { normalize as normalize2 } from "path";
|
|
113605
114374
|
|
|
@@ -113682,7 +114451,7 @@ async function isOlderThan(worktreePath, days, now) {
|
|
|
113682
114451
|
if (days <= 0)
|
|
113683
114452
|
return false;
|
|
113684
114453
|
try {
|
|
113685
|
-
const stats = await
|
|
114454
|
+
const stats = await stat10(worktreePath);
|
|
113686
114455
|
return now - stats.mtimeMs > days * DAY_MS;
|
|
113687
114456
|
} catch {
|
|
113688
114457
|
return false;
|
|
@@ -113929,7 +114698,7 @@ Model Providers (Priority: Native > Copilot > OpenCode Zen > Z.ai > Kimi > Baili
|
|
|
113929
114698
|
Copilot github-copilot/ models (fallback)
|
|
113930
114699
|
OpenCode Zen opencode/ models (opencode/claude-opus-5, etc.)
|
|
113931
114700
|
Z.ai zai-coding-plan/glm-5.2 (visual-engineering fallback)
|
|
113932
|
-
Kimi kimi-for-coding/kimi-k3 (Sisyphus/Prometheus fallback)
|
|
114701
|
+
Kimi kimi-for-coding/kimi-k3.1-pro (Sisyphus/Prometheus fallback)
|
|
113933
114702
|
Bailian bailian-coding-plan/ models (Qwen, GLM, Kimi fallback)
|
|
113934
114703
|
MiniMax minimax-coding-plan/MiniMax-M3 (utility fallback)
|
|
113935
114704
|
MiniMax CN minimax-cn-coding-plan/MiniMax-M3 (utility fallback)
|