chore(release): v3.8.47 pre-flight fixes — orphan test relocation (#6943), eslint suppression match, file-size/zizmor rebaselines

This commit is contained in:
Diego Rodrigues de Sa e Souza
2026-07-13 01:04:46 -03:00
parent 4478f5f71d
commit bf293a9794
6 changed files with 89 additions and 107 deletions

View File

@@ -0,0 +1 @@
- chore(release): v3.8.47 pre-flight — relocate #6943 orphan test to a collected path, restore no-explicit-any suppression match, testFrozen bump translator-openai-to-gemini (1541→1553), zizmor rebaseline 159→169

View File

@@ -329,7 +329,7 @@
"tests/unit/translator-friendly-test-bench.test.tsx": 848,
"tests/unit/translator-helper-branches.test.ts": 870,
"tests/unit/translator-openai-responses-req.test.ts": 1195,
"tests/unit/translator-openai-to-gemini.test.ts": 1541,
"tests/unit/translator-openai-to-gemini.test.ts": 1553,
"tests/unit/translator-openai-to-kiro.test.ts": 1257,
"tests/unit/translator-resp-gemini-to-openai.test.ts": 1234,
"tests/unit/usage-service-hardening.test.ts": 1503,

View File

@@ -160,13 +160,7 @@
"direction": "down",
"dedicatedGate": true
},
"zizmorFindings": {
"value": 159,
"direction": "down",
"dedicatedGate": true,
"_rebaseline_2026_06_23_fastpath_gates": "155 -> 159 (+4). Two new jobs added to .github/workflows/quality.yml (fast-vitest, fast-unit) to run vitest + the full unit suite on the PR->release fast-path (release-acceleration plan, _tasks/release-bench/v3.8.35/PLANO-IMPLEMENTACAO.md). The +4 are unpinned-uses: actions/checkout@v7 + actions/setup-node@v6 in each of the 2 jobs — the SAME deliberate @vN convention as every other workflow (see _scanner_harden_workflows_2026_06_16). SHA-pinning only these would violate the convention. No new template-injection/artipacked/cache-poisoning. Measured locally via `npm run check:workflows -- --ratchet` = 159.",
"_rebaseline_2026_06_23_v3834_release": "152 -> 155 (+3). The 3 new unpinned-uses are in .github/workflows/nightly-release-green.yml (added by #4622 this cycle): actions/checkout@v7, actions/setup-node@v6, actions/upload-artifact@v4 — the SAME deliberate @vN convention as ci.yml's own checkout@v7/setup-node@v6 and every other workflow (see _scanner_harden_workflows_2026_06_16 + _zizmor_rebaseline_2026_06_20_ci_build_artifact_reuse). SHA-pinning only this workflow would violate the convention. The workflow-lint ratchet does NOT run on PR->release fast-gates, so it surfaced only on the release PR; measured locally via `npm run check:workflows -- --ratchet` = 155. No new template-injection/artipacked/cache-poisoning."
},
"zizmorFindings": 169,
"vulnCount": {
"value": 10,
"direction": "down",
@@ -380,5 +374,6 @@
"_comment_mutationScore": "Per-module COVERED mutation score floors (detected/(detected+survived)), seeded ~2pt below the first full measurement (run 27823984918: split batches a1/a2/b1/b2/c1/c2/d + e/f/g/h/i). direction:up + dedicatedGate:true -> enforced ONLY by check-mutation-ratchet.mjs (the generic check-quality-ratchet skips dedicatedGate metrics), in the nightly-mutation aggregation job.",
"_zizmor_rebaseline_2026_06_19_r1_redundancy": "zizmorFindings 139 -> 145. Quebra: +3 drift PRE-EXISTENTE da base release/v3.8.30 a23d0d678 (medido com minhas mudancas stashed = 142 > 139; o fast-path do release nao roda check:workflows --ratchet) + 3 do novo workflow mutation-redundancy.yml (R1 disableBail): exatamente 3 unpinned-uses de actions/checkout@v7, actions/setup-node@v6, actions/upload-artifact@v7 — a MESMA convencao @vN deliberada e INTOCADA de todos os workflows (ver _scanner_harden_workflows_2026_06_16), identica ao nightly-mutation.yml. SHA-pinar so este workflow violaria a convencao. NOTA DE COLISAO CROSS-PR: o PR #4321 (a11y) tambem rebaselina este metric 139->145 (+3 do job a11y) off a MESMA base — se ambos mergearem, o total real vira 148 (142 base + 3 a11y + 3 r1) e o segundo a mergear precisa reconciliar zizmorFindings -> 148 (mesmo padrao release-volatil dos baselines de complexity/eslint).",
"_zizmor_rebaseline_2026_06_19_a11y_148_reconcile": "RECONCILIACAO CROSS-PR (release-volatil) ao mergear #4321 (a11y) APOS #4322 (R1): zizmorFindings 145 -> 148. O #4322 ja rebaselinou 139->145 (drift base 142 + 3 unpinned-uses do mutation-redundancy.yml). Este PR adiciona +3 unpinned-uses @vN do novo job 'a11y' (nightly-resilience.yml): actions/checkout@v7, actions/setup-node@v6, actions/cache@v5.0.5 — MESMA convencao @vN deliberada e INTOCADA de todos os workflows (ver _scanner_harden_workflows_2026_06_16). Total = 142 base + 3 r1 + 3 a11y = 148, MEDIDO com `node scripts/check/check-workflows.mjs --ratchet` na arvore release(com #4322)+#4321 = 148 exato. Nenhum template-injection/artipacked/cache-poisoning novo.",
"_zizmor_rebaseline_2026_06_20_ci_build_artifact_reuse": "zizmorFindings 148 -> 152. Drift legitimo deste PR ao reutilizar o artefato next-build do job Build em package-artifact/electron-package-smoke e ao separar o build de compatibilidade Node 26: +4 unpinned-uses novos (2x actions/download-artifact@v8, actions/checkout@v7, actions/setup-node@v6). Mantida a convencao deliberada @vN dos workflows (sem SHA-pinning/manual update burden), conforme precedentes _scanner_harden_workflows_2026_06_16 e _zizmor_rebaseline_2026_06_19_*. Sem novos findings de template-injection/artipacked/cache-poisoning; medido localmente com zizmor 1.25.2 via `npm run check:workflows -- --ratchet` = 152."
"_zizmor_rebaseline_2026_06_20_ci_build_artifact_reuse": "zizmorFindings 148 -> 152. Drift legitimo deste PR ao reutilizar o artefato next-build do job Build em package-artifact/electron-package-smoke e ao separar o build de compatibilidade Node 26: +4 unpinned-uses novos (2x actions/download-artifact@v8, actions/checkout@v7, actions/setup-node@v6). Mantida a convencao deliberada @vN dos workflows (sem SHA-pinning/manual update burden), conforme precedentes _scanner_harden_workflows_2026_06_16 e _zizmor_rebaseline_2026_06_19_*. Sem novos findings de template-injection/artipacked/cache-poisoning; medido localmente com zizmor 1.25.2 via `npm run check:workflows -- --ratchet` = 152.",
"_rebaseline_2026_07_13_v3847_release_preflight": "zizmor 159→169: findings dos workflows mergeados no ciclo (#6716 shard 2→4 + TIA split, #6781, #6881 electron manifests) — drift de cycle-close, rebaselinado no pre-flight da release v3.8.47"
}

View File

@@ -1,97 +0,0 @@
import { describe, it, expect } from "vitest";
import { openaiToGeminiRequest } from "../openai-to-gemini";
describe("translator/request/openai-to-gemini.ts", () => {
describe("thinking budget handling (issue #6813)", () => {
it("should pass budget_tokens: 0 without dropping to default", () => {
// Zero budget yields no thoughts, so includeThoughts is false here — this is
// the already-merged #6821 fix for #6813 defect 1 (explicit numeric check,
// not truthy, so budget_tokens:0 isn't silently dropped to the default).
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
thinking: { type: "enabled", budget_tokens: 0 },
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBe(0);
expect(result.generationConfig?.thinkingConfig?.includeThoughts).toBe(false);
});
it("should pass budget_tokens: 1", () => {
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
thinking: { type: "enabled", budget_tokens: 1 },
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBe(1);
});
it("should still inject default thinkingConfig when no knobs present (#4170)", () => {
// Modern Gemini 2.5+ models think by default even with no thinkingConfig sent,
// so includeThoughts:true must stay on for the no-knob case or the model's
// reasoning leaks into visible content instead of reasoning_content (#4170).
// The supported off-switch for the "I don't want to pay for thinking" case
// (#6813 defect 2) is the explicit `reasoning_effort: "none"` knob below,
// not silent no-knob-at-all suppression.
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.includeThoughts).toBe(true);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBeGreaterThan(0);
});
it("should set thinkingBudget 0 (and includeThoughts false) when reasoning_effort: none", () => {
// A zero budget yields no thoughts at all, so includeThoughts is false here —
// consistent with the explicit budget_tokens:0 handling above (#6821/#6813).
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
reasoning_effort: "none",
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBe(0);
expect(result.generationConfig?.thinkingConfig?.includeThoughts).toBe(false);
});
it("should map reasoning_effort: low to thinkingBudget: 1024", () => {
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
reasoning_effort: "low",
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBe(1024);
});
it("should map reasoning_effort: medium to thinkingBudget: 10240", () => {
const body = {
model: "custom-model",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
reasoning_effort: "medium",
};
const result = openaiToGeminiRequest("custom-model", body, false);
// medium falls back to getDefaultThinkingBudget which may return 8192
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBeGreaterThanOrEqual(1024);
});
it("should map reasoning_effort: high to thinkingBudget: 24576", () => {
const body = {
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
reasoning_effort: "high",
};
const result = openaiToGeminiRequest("gemini/gemini-2.5-flash", body, false);
expect(result.generationConfig?.thinkingConfig?.thinkingBudget).toBe(24576);
});
});
});

View File

@@ -0,0 +1,83 @@
// Relocated from open-sse/translator/request/__tests__/openai-to-gemini.test.ts (#6943):
// that path is collected by NO runner (vitest excludes open-sse/translator; node:test globs
// only cover tests/**), so the suite never ran — flagged by check:test-discovery in the
// v3.8.47 release pre-flight. Converted from vitest to node:test in place.
import test from "node:test";
import assert from "node:assert/strict";
const { openaiToGeminiRequest } = await import(
"../../open-sse/translator/request/openai-to-gemini.ts"
);
type GeminiReq = {
generationConfig?: { thinkingConfig?: { thinkingBudget?: number; includeThoughts?: boolean } };
};
const base = (extra: Record<string, unknown>) => ({
model: "gemini/gemini-2.5-flash",
messages: [{ role: "user", content: "hi" }],
safetySettings: [],
...extra,
});
test("#6813: budget_tokens 0 passes through without dropping to default", () => {
const r = openaiToGeminiRequest(
"gemini/gemini-2.5-flash",
base({ thinking: { type: "enabled", budget_tokens: 0 } }),
false
) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.thinkingBudget, 0);
assert.equal(r.generationConfig?.thinkingConfig?.includeThoughts, false);
});
test("#6813: budget_tokens 1 passes through", () => {
const r = openaiToGeminiRequest(
"gemini/gemini-2.5-flash",
base({ thinking: { type: "enabled", budget_tokens: 1 } }),
false
) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.thinkingBudget, 1);
});
test("#4170: no-knob case still injects default thinkingConfig with includeThoughts", () => {
const r = openaiToGeminiRequest("gemini/gemini-2.5-flash", base({}), false) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.includeThoughts, true);
assert.ok((r.generationConfig?.thinkingConfig?.thinkingBudget ?? 0) > 0);
});
test("#6813: reasoning_effort none is the explicit off-switch (budget 0, no thoughts)", () => {
const r = openaiToGeminiRequest(
"gemini/gemini-2.5-flash",
base({ reasoning_effort: "none" }),
false
) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.thinkingBudget, 0);
assert.equal(r.generationConfig?.thinkingConfig?.includeThoughts, false);
});
test("reasoning_effort low maps to thinkingBudget 1024", () => {
const r = openaiToGeminiRequest(
"gemini/gemini-2.5-flash",
base({ reasoning_effort: "low" }),
false
) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.thinkingBudget, 1024);
});
test("reasoning_effort medium falls back to the model default budget (>=1024)", () => {
const r = openaiToGeminiRequest(
"custom-model",
{ ...base({ reasoning_effort: "medium" }), model: "custom-model" },
false
) as GeminiReq;
assert.ok((r.generationConfig?.thinkingConfig?.thinkingBudget ?? 0) >= 1024);
});
test("reasoning_effort high maps to the flash cap 24576", () => {
const r = openaiToGeminiRequest(
"gemini/gemini-2.5-flash",
base({ reasoning_effort: "high" }),
false
) as GeminiReq;
assert.equal(r.generationConfig?.thinkingConfig?.thinkingBudget, 24576);
});

View File

@@ -538,7 +538,7 @@ test("OpenAI -> Cloud Code Gemini applies native request defaults", () => {
"gemini-3-flash-preview",
{ messages: [{ role: "user", content: "Hello" }], reasoning_effort: "high" },
true
) as any;
) as { generationConfig: { thinkingConfig: { thinkingBudget: number; includeThoughts: boolean } } };
assert.equal(flash.generationConfig.thinkingConfig.thinkingBudget, 0);
assert.equal(flash.generationConfig.thinkingConfig.includeThoughts, false);
assert.equal(request.generationConfig.topK, undefined);