mirror of
https://github.com/boshu2/agentops.git
synced 2026-09-14 15:08:13 +08:00
a4c0f2d646
Wave 1 of the new-user happy-path fixes (fresh-eyes novice test,
follow-up to the [3.3 release
audit](docs/audits/release-readiness-3.3-2026-07-20.md)).
**Edge 1 — `ao gate check` in a foreign repo.** Was: ~10 blocking
UNKNOWN rows naming agentops-internal scripts, a summary that counted
none of them, exit 1 — the product's own suggested next command failed
in every repo but this one. Now: a deterministic repo marker
(`cli/go.mod` module identity) routes those checks to first-class
not-applicable SKIPs outside agentops; human output aggregates them into
one honest line and suppresses the routing-skip wall (70 lines → 5); the
summary counts UNKNOWN in its own bucket everywhere; `--json` keeps
every row. Inside agentops, a missing backing script stays fail-closed
UNKNOWN (guard pinned by test).
**Edge 2 — permanent false `fm-skills-missing` P1.** The detector's
Lstat-based scan counted the canonical `ao skills link` symlink farm as
zero skills. Now resolves symlinked skill dirs; dangling links still
count as absent.
**Edge 3 — P1 on every default dev Mac.** Benign PATH shadowing
(Homebrew git + Apple `/usr/bin/git`) raised a P1 with a broken
empty-slot remediation ("Install the missing CLI yourself — —").
Shadow-only now produces no finding; the missing-CLI template renders
only with real names.
**Process:** three scoped implementer agents (disjoint file ownership) +
fresh adversarial verifier (4× RESOLVED, incl. dangling-symlink and
genuinely-missing-CLI negative cases). **Verified:** per-fix RED→GREEN
shell repros; foreign-repo first contact now 5 lines + exit 0 with JSON
parity; 61/61 test pkgs; golangci-lint clean; `ao gate check --full`
67/67 over this range.
47 lines
1.9 KiB
Go
47 lines
1.9 KiB
Go
package gates
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
)
|
|
|
|
// agentopsCLIModulePath is the module path declared by the agentops repo's own
|
|
// CLI module. Its presence at <root>/cli/go.mod is the deterministic
|
|
// "this IS the agentops repo" marker used by NotApplicableOutsideAgentOps.
|
|
const agentopsCLIModulePath = "github.com/boshu2/agentops/cli"
|
|
|
|
// NotApplicableReason is the first-class SKIP reason emitted when an
|
|
// agentops-internal check runs in a foreign repository whose tree does not
|
|
// contain the check's backing artifact. Report aggregation keys on this exact
|
|
// string, so it is a single shared constant.
|
|
const NotApplicableReason = "not applicable: agentops-repo check; backing artifact not present in this repository"
|
|
|
|
// IsAgentOpsRepo reports whether root is the agentops repository itself.
|
|
//
|
|
// Marker: <root>/cli/go.mod whose `module` directive is exactly
|
|
// github.com/boshu2/agentops/cli. This is unambiguous (module paths are
|
|
// globally unique by convention and this one names the agentops repo),
|
|
// deterministic (a plain tracked file, present in every checkout and linked
|
|
// worktree), and cheap (one bounded file read). It deliberately does NOT use
|
|
// git metadata (remotes can be renamed or absent) or the presence of scripts/
|
|
// (which is exactly what a foreign repo may or may not have).
|
|
//
|
|
// Inside the agentops repo a missing backing script stays UNKNOWN and
|
|
// fail-closed — that guard protects agentops CI from silently losing a gate.
|
|
// Outside it, the same condition is a first-class not-applicable SKIP
|
|
// (see ScriptRunner.Run).
|
|
func IsAgentOpsRepo(root string) bool {
|
|
raw, err := os.ReadFile(filepath.Join(root, "cli", "go.mod"))
|
|
if err != nil {
|
|
return false
|
|
}
|
|
for _, line := range strings.Split(string(raw), "\n") {
|
|
line = strings.TrimSpace(line)
|
|
if rest, ok := strings.CutPrefix(line, "module "); ok {
|
|
return strings.TrimSpace(rest) == agentopsCLIModulePath
|
|
}
|
|
}
|
|
return false
|
|
}
|