mirror of
https://github.com/expo/code-review-cli.git
synced 2026-11-13 20:28:06 -10:00
Compare commits
1
Commits
main
...
ecr-ref-coverage
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
fbcc822c2a |
No files matched your search
@@ -226,6 +226,28 @@ test("extensionless citations count only when they name something real", async (
|
||||
expect(tokens.some((problem) => problem.includes(`${REF} infrastructure/finops/ —`))).toBe(true);
|
||||
});
|
||||
|
||||
test("the ref the message suggests silences the citation it was suggested for", async () => {
|
||||
// A scoped prompt names an app by its directory basename; the ref that pins it is
|
||||
// the root-relative path. Coverage has to connect the two, or the suggested fix is
|
||||
// not a fix. Both the plain and the glob form of that path must count.
|
||||
const files = (pin: string): Record<string, string> => ({
|
||||
"infrastructure/cert-manager/kustomization.yaml": "resources: []\n",
|
||||
"infrastructure/.expo-code-review/config.jsonc": "{}\n",
|
||||
"infrastructure/.expo-code-review/agents/k8s.md": `${pin}\n\nApps: \`cert-manager\`.\n`,
|
||||
});
|
||||
|
||||
const unpinned = await checkConfigRefs({ root: await makeRepo(files("")) });
|
||||
expect(unpinned.problems).toHaveLength(1);
|
||||
expect(unpinned.problems[0]!.problem).toContain(`${REF} infrastructure/cert-manager/ —`);
|
||||
|
||||
for (const pin of [
|
||||
`<!-- ${REF} infrastructure/cert-manager/ — the app -->`,
|
||||
`<!-- ${REF} glob:infrastructure/cert-manager/** — the app -->`,
|
||||
]) {
|
||||
expect((await checkConfigRefs({ root: await makeRepo(files(pin)) })).problems).toEqual([]);
|
||||
}
|
||||
});
|
||||
|
||||
test("a scope-relative annotated ref is broken, and names the root-relative fix", async () => {
|
||||
const root = await makeRepo({
|
||||
"infrastructure/general-central/module/main.tf": "resource {}\n",
|
||||
|
||||
+13
-9
@@ -762,7 +762,19 @@ export async function checkConfigRefs(options: CheckConfigRefsOptions): Promise<
|
||||
}
|
||||
|
||||
for (const { line, token } of findProseCitations(text)) {
|
||||
const forms = citationForms(token);
|
||||
// Extension or wildcard tail ⇒ a citation on shape alone. Otherwise it only
|
||||
// counts if it names something real: `eas-build-worker/terraform` and
|
||||
// `general-central/{module,production}` are paths, `anthropic/claude-opus-5`
|
||||
// is shaped identically and is not.
|
||||
const named = isCodeCitation(token) ? null : await namedPath(token, scopeRoot);
|
||||
if (!isCodeCitation(token) && !named) {
|
||||
continue;
|
||||
}
|
||||
// Coverage must accept the path the token RESOLVED to, not just the token as
|
||||
// written: a prompt says `cert-manager` and the ref that pins it is
|
||||
// `infrastructure/cert-manager/`. Without this, the fix the message suggests
|
||||
// does not silence the citation it was suggested for.
|
||||
const forms = [...citationForms(token), ...(named ? coveringForms(named) : [])];
|
||||
if (
|
||||
ignored.has(token) ||
|
||||
forms.some((form) => covered.has(form)) ||
|
||||
@@ -772,14 +784,6 @@ export async function checkConfigRefs(options: CheckConfigRefsOptions): Promise<
|
||||
) {
|
||||
continue;
|
||||
}
|
||||
// Extension or wildcard tail ⇒ a citation on shape alone. Otherwise it only
|
||||
// counts if it names something real: `eas-build-worker/terraform` and
|
||||
// `general-central/{module,production}` are paths, `anthropic/claude-opus-5`
|
||||
// is shaped identically and is not.
|
||||
const named = isCodeCitation(token) ? null : await namedPath(token, scopeRoot);
|
||||
if (!isCodeCitation(token) && !named) {
|
||||
continue;
|
||||
}
|
||||
const lineCitation = LINE_CITATION_RE.exec(token);
|
||||
// For an extensionless token the suggestion is the path that actually resolved,
|
||||
// which is also how a scope-relative citation learns its root-relative form.
|
||||
|
||||
Reference in new issue
Block a user