mirror of
https://github.com/diegosouzapw/OmniRoute.git
synced 2026-08-02 21:32:10 +03:00
* feat(oauth): add Kiro long-lived API key auth (#6587) New /api/oauth/kiro/api-key route + KiroService.validateApiKey let a Kiro account be linked with a long-lived AWS CodeWhisperer/Kiro API key instead of the interactive OAuth device flow, with live per-account model discovery (ListAvailableModels, 5-minute cache) layered over the existing static registry fallback. Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> * fix(changelog): re-restore #6587 bullet after release sync Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> * fix(merge): restore #6126 clinepass files reverted by release auto-resolve + baseline re-merge The release sync's auto-resolve reverted sibling PR #6126's clinepass work (registry, catalog, oauth constants, clineAuth.ts, token-refresh case, tests) and the file-size baseline — all outside this PR's scope. Restored to the release versions, re-applied only this PR's own baseline entries, restored the #6126 CHANGELOG bullet (re-inserting only this PR's own). Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> * chore(quality): freeze public-creds FP — AWS region default in validateApiKey signature Same class as the existing minimax fn-param FPs: CRED_KEY_RE matches the apiKey: param annotation and captures the region default "us-east-1", which is not a credential. Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> * fix(kiro): keep hard-failure reject semantics + kill public-creds fn-param FP at the source - getKiroUsage: exhausted non-auth attempts now REJECT with the last HTTP-status failure in the pre-#6587 format (usage-service-hardening relies on it); auth failures keep the soft social-auth message. - validateApiKey: region default moved out of the parameter list (the check-public-creds CRED_KEY_RE matches the apiKey: annotation and flags any literal in the signature); drops the brittle line-keyed allowlist entry. Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> --------- Co-authored-by: strangersp <strangersp@users.noreply.github.com> Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com> Co-authored-by: Diego Rodrigues de Sa e Souza <diegosouza.pw@gmail.com>
39 lines
1.6 KiB
TypeScript
39 lines
1.6 KiB
TypeScript
import test from "node:test";
|
|
import assert from "node:assert/strict";
|
|
|
|
import {
|
|
buildKiroApiKeyConnectionName,
|
|
isKiroApiKeyImportClientError,
|
|
} from "../../src/app/api/oauth/kiro/api-key/helpers.ts";
|
|
|
|
test("Kiro API key connection names differ for different keys in the same region", () => {
|
|
const first = buildKiroApiKeyConnectionName("kiro", "us-east-1", "ksk_first_key");
|
|
const second = buildKiroApiKeyConnectionName("kiro", "us-east-1", "ksk_second_key");
|
|
|
|
assert.match(first, /^Kiro API Key \(us-east-1, [a-f0-9]{8}\)$/);
|
|
assert.match(second, /^Kiro API Key \(us-east-1, [a-f0-9]{8}\)$/);
|
|
assert.notEqual(first, second);
|
|
});
|
|
|
|
test("Kiro API key connection names are stable for the same trimmed key", () => {
|
|
const first = buildKiroApiKeyConnectionName("amazon-q", "eu-west-1", " ksk_same_key ");
|
|
const second = buildKiroApiKeyConnectionName("amazon-q", "eu-west-1", "ksk_same_key");
|
|
|
|
assert.equal(first, second);
|
|
assert.match(first, /^Amazon Q API Key \(eu-west-1, [a-f0-9]{8}\)$/);
|
|
});
|
|
|
|
test("Kiro API key import classifies client validation failures as 400-class", () => {
|
|
assert.equal(isKiroApiKeyImportClientError(new Error("API key is required")), true);
|
|
assert.equal(isKiroApiKeyImportClientError(new Error("Invalid region")), true);
|
|
assert.equal(
|
|
isKiroApiKeyImportClientError(new Error("Failed to list profiles: Invalid API key")),
|
|
true
|
|
);
|
|
});
|
|
|
|
test("Kiro API key import leaves network/server failures as 500-class", () => {
|
|
assert.equal(isKiroApiKeyImportClientError(new Error("fetch failed")), false);
|
|
assert.equal(isKiroApiKeyImportClientError(new Error("ECONNRESET")), false);
|
|
});
|