@numa-tech/numa 1.22.1 → 1.23.1
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/README.md +14 -1
- package/dist/ai-registry/commands.js +5 -2
- package/dist/ai-registry/commands.js.map +1 -1
- package/dist/ai-registry/namespace.d.ts +4 -0
- package/dist/ai-registry/namespace.js +17 -3
- package/dist/ai-registry/namespace.js.map +1 -1
- package/dist/ai-registry/skill-installer.js +35 -5
- package/dist/ai-registry/skill-installer.js.map +1 -1
- package/dist/ai-registry/tui.js +15 -4
- package/dist/ai-registry/tui.js.map +1 -1
- package/dist/authorization/application-client.d.ts +808 -7
- package/dist/authorization/application-client.js +36 -8
- package/dist/authorization/application-client.js.map +1 -1
- package/dist/authorization/application-commands.d.ts +3 -1
- package/dist/authorization/application-commands.js +8 -2
- package/dist/authorization/application-commands.js.map +1 -1
- package/dist/authorization/application-schemas.d.ts +235 -14
- package/dist/authorization/application-schemas.js +76 -15
- package/dist/authorization/application-schemas.js.map +1 -1
- package/dist/authorization/environment-governance-client.d.ts +155 -0
- package/dist/authorization/environment-governance-client.js +86 -0
- package/dist/authorization/environment-governance-client.js.map +1 -0
- package/dist/authorization/environment-governance-commands.d.ts +6 -0
- package/dist/authorization/environment-governance-commands.js +58 -0
- package/dist/authorization/environment-governance-commands.js.map +1 -0
- package/dist/authorization/environment-governance-schemas.d.ts +79 -0
- package/dist/authorization/environment-governance-schemas.js +15 -0
- package/dist/authorization/environment-governance-schemas.js.map +1 -0
- package/dist/authorization/runtime-artifact-client.d.ts +36 -0
- package/dist/authorization/runtime-artifact-client.js +135 -0
- package/dist/authorization/runtime-artifact-client.js.map +1 -0
- package/dist/authorization/runtime-artifact-commands.d.ts +6 -0
- package/dist/authorization/runtime-artifact-commands.js +29 -0
- package/dist/authorization/runtime-artifact-commands.js.map +1 -0
- package/dist/command-catalog.js +254 -0
- package/dist/command-catalog.js.map +1 -1
- package/dist/compatibility/index.d.ts +1 -0
- package/dist/compatibility/index.js +3 -0
- package/dist/compatibility/index.js.map +1 -0
- package/dist/compatibility/registry-instance.d.ts +17 -0
- package/dist/compatibility/registry-instance.js +93 -0
- package/dist/compatibility/registry-instance.js.map +1 -0
- package/dist/gitops/client.d.ts +359 -0
- package/dist/gitops/client.js +164 -1
- package/dist/gitops/client.js.map +1 -1
- package/dist/gitops/commands.js +46 -3
- package/dist/gitops/commands.js.map +1 -1
- package/dist/gitops/schemas.d.ts +35 -0
- package/dist/gitops/schemas.js +23 -0
- package/dist/gitops/schemas.js.map +1 -1
- package/dist/gitops/workload-commands.d.ts +9 -0
- package/dist/gitops/workload-commands.js +190 -0
- package/dist/gitops/workload-commands.js.map +1 -0
- package/dist/gitops/workload-input.d.ts +22 -0
- package/dist/gitops/workload-input.js +125 -0
- package/dist/gitops/workload-input.js.map +1 -0
- package/dist/gitops/workload-schemas.d.ts +217 -0
- package/dist/gitops/workload-schemas.js +68 -0
- package/dist/gitops/workload-schemas.js.map +1 -0
- package/dist/interactive/prompts.d.ts +4 -2
- package/dist/interactive/prompts.js +36 -4
- package/dist/interactive/prompts.js.map +1 -1
- package/dist/interactive/registry-namespace.d.ts +7 -0
- package/dist/interactive/registry-namespace.js +51 -0
- package/dist/interactive/registry-namespace.js.map +1 -0
- package/dist/interactive/registry.js +35 -26
- package/dist/interactive/registry.js.map +1 -1
- package/docs/authorization-configuration-publication.md +4 -1
- package/docs/environment-configuration-publication.md +95 -0
- package/docs/gitops-configuration.md +122 -0
- package/package.json +7 -5
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import type { AuthConfig } from "../config.js";
|
|
2
|
+
import { type KeycloakTokenProvider } from "../oauth.js";
|
|
3
|
+
export interface EnvironmentGovernanceDependencies {
|
|
4
|
+
fetch?: typeof fetch;
|
|
5
|
+
tokenProvider?: KeycloakTokenProvider;
|
|
6
|
+
}
|
|
7
|
+
export type GovernancePagination = {
|
|
8
|
+
page?: number;
|
|
9
|
+
pageSize?: number;
|
|
10
|
+
q?: string;
|
|
11
|
+
};
|
|
12
|
+
export declare class EnvironmentGovernanceClient {
|
|
13
|
+
private readonly config;
|
|
14
|
+
private readonly dependencies;
|
|
15
|
+
constructor(config: AuthConfig, dependencies?: EnvironmentGovernanceDependencies);
|
|
16
|
+
private json;
|
|
17
|
+
identities(options?: GovernancePagination): Promise<{
|
|
18
|
+
[x: string]: unknown;
|
|
19
|
+
items: Record<string, unknown>[];
|
|
20
|
+
total: number;
|
|
21
|
+
page: number;
|
|
22
|
+
pageSize: number;
|
|
23
|
+
}>;
|
|
24
|
+
identity(id: string): Promise<{
|
|
25
|
+
[x: string]: unknown;
|
|
26
|
+
id: string;
|
|
27
|
+
code: string;
|
|
28
|
+
name: string;
|
|
29
|
+
issuerId: string;
|
|
30
|
+
status: "ACTIVE" | "DISABLED" | "DRAFT";
|
|
31
|
+
version: number;
|
|
32
|
+
clients: {
|
|
33
|
+
[x: string]: unknown;
|
|
34
|
+
applicationId: number;
|
|
35
|
+
slot: string;
|
|
36
|
+
referenceId: string;
|
|
37
|
+
instanceId: string;
|
|
38
|
+
}[];
|
|
39
|
+
environmentReferenceCount: number;
|
|
40
|
+
}>;
|
|
41
|
+
identityEnvironments(id: string, options?: GovernancePagination): Promise<{
|
|
42
|
+
[x: string]: unknown;
|
|
43
|
+
items: Record<string, unknown>[];
|
|
44
|
+
total: number;
|
|
45
|
+
page: number;
|
|
46
|
+
pageSize: number;
|
|
47
|
+
}>;
|
|
48
|
+
clientOptions(issuerId: string, applicationId: number, options?: GovernancePagination): Promise<{
|
|
49
|
+
[x: string]: unknown;
|
|
50
|
+
items: Record<string, unknown>[];
|
|
51
|
+
total: number;
|
|
52
|
+
page: number;
|
|
53
|
+
pageSize: number;
|
|
54
|
+
}>;
|
|
55
|
+
previewIdentity(input: unknown, id?: string): Promise<{
|
|
56
|
+
operation: string;
|
|
57
|
+
id: string | null;
|
|
58
|
+
current: {
|
|
59
|
+
[x: string]: unknown;
|
|
60
|
+
id: string;
|
|
61
|
+
code: string;
|
|
62
|
+
name: string;
|
|
63
|
+
issuerId: string;
|
|
64
|
+
status: "ACTIVE" | "DISABLED" | "DRAFT";
|
|
65
|
+
version: number;
|
|
66
|
+
clients: {
|
|
67
|
+
[x: string]: unknown;
|
|
68
|
+
applicationId: number;
|
|
69
|
+
slot: string;
|
|
70
|
+
referenceId: string;
|
|
71
|
+
instanceId: string;
|
|
72
|
+
}[];
|
|
73
|
+
environmentReferenceCount: number;
|
|
74
|
+
} | null;
|
|
75
|
+
desired: {
|
|
76
|
+
expectedVersion: number;
|
|
77
|
+
code: string;
|
|
78
|
+
name: string;
|
|
79
|
+
issuerId: string;
|
|
80
|
+
status: "ACTIVE" | "DISABLED" | "DRAFT";
|
|
81
|
+
clients: {
|
|
82
|
+
applicationId: number;
|
|
83
|
+
slot: string;
|
|
84
|
+
referenceId: string;
|
|
85
|
+
instanceId: string;
|
|
86
|
+
}[];
|
|
87
|
+
};
|
|
88
|
+
remoteWrites: false;
|
|
89
|
+
}>;
|
|
90
|
+
saveIdentity(input: unknown, id?: string): Promise<{
|
|
91
|
+
[x: string]: unknown;
|
|
92
|
+
id: string;
|
|
93
|
+
code: string;
|
|
94
|
+
name: string;
|
|
95
|
+
issuerId: string;
|
|
96
|
+
status: "ACTIVE" | "DISABLED" | "DRAFT";
|
|
97
|
+
version: number;
|
|
98
|
+
clients: {
|
|
99
|
+
[x: string]: unknown;
|
|
100
|
+
applicationId: number;
|
|
101
|
+
slot: string;
|
|
102
|
+
referenceId: string;
|
|
103
|
+
instanceId: string;
|
|
104
|
+
}[];
|
|
105
|
+
environmentReferenceCount: number;
|
|
106
|
+
}>;
|
|
107
|
+
binding(environmentId: number): Promise<{
|
|
108
|
+
[x: string]: unknown;
|
|
109
|
+
environmentId: number;
|
|
110
|
+
envCode: string;
|
|
111
|
+
version: number;
|
|
112
|
+
identityConfigurationId: string | null;
|
|
113
|
+
registryNamespaceId: number | null;
|
|
114
|
+
defaultGatewayId: string | null;
|
|
115
|
+
}>;
|
|
116
|
+
migrationIssues(): Promise<Record<string, unknown>[]>;
|
|
117
|
+
previewBinding(environmentId: number, input: unknown): Promise<{
|
|
118
|
+
operation: string;
|
|
119
|
+
environmentId: number;
|
|
120
|
+
current: {
|
|
121
|
+
[x: string]: unknown;
|
|
122
|
+
environmentId: number;
|
|
123
|
+
envCode: string;
|
|
124
|
+
version: number;
|
|
125
|
+
identityConfigurationId: string | null;
|
|
126
|
+
registryNamespaceId: number | null;
|
|
127
|
+
defaultGatewayId: string | null;
|
|
128
|
+
};
|
|
129
|
+
desired: {
|
|
130
|
+
expectedVersion: number;
|
|
131
|
+
identityConfigurationId: string | null;
|
|
132
|
+
registryNamespaceId: number | null;
|
|
133
|
+
defaultGatewayId: string | null;
|
|
134
|
+
};
|
|
135
|
+
remoteWrites: false;
|
|
136
|
+
}>;
|
|
137
|
+
saveBinding(environmentId: number, input: unknown): Promise<{
|
|
138
|
+
[x: string]: unknown;
|
|
139
|
+
environmentId: number;
|
|
140
|
+
envCode: string;
|
|
141
|
+
version: number;
|
|
142
|
+
identityConfigurationId: string | null;
|
|
143
|
+
registryNamespaceId: number | null;
|
|
144
|
+
defaultGatewayId: string | null;
|
|
145
|
+
}>;
|
|
146
|
+
resolved(applicationId: number, environmentId: number, slot?: string, view?: "current" | "applied"): Promise<{
|
|
147
|
+
[x: string]: unknown;
|
|
148
|
+
schemaVersion: 1;
|
|
149
|
+
applicationId: number;
|
|
150
|
+
environmentId: number;
|
|
151
|
+
envCode: string;
|
|
152
|
+
slot: string;
|
|
153
|
+
view: "applied" | "current";
|
|
154
|
+
}>;
|
|
155
|
+
}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { resolveBackendUrl } from "../backend.js";
|
|
3
|
+
import { ensureAccessToken, fetchWithKeycloakIdentity } from "../oauth.js";
|
|
4
|
+
import { AuthorizationError, authorizationHttpErrorCode } from "./errors.js";
|
|
5
|
+
import { parse, uuid, positive, environmentSlot, document } from "./application-schemas.js";
|
|
6
|
+
import * as s from "./environment-governance-schemas.js";
|
|
7
|
+
const IDENTITY = "/api/v1/admin/authorization/identity-configurations";
|
|
8
|
+
const ENV = "/api/v1/admin/environments";
|
|
9
|
+
function invalid(message) { throw new AuthorizationError(message, "authorization_input_invalid"); }
|
|
10
|
+
function mappings(value) { return value.map(v => `${v.applicationId}/${v.slot}/${v.referenceId}/${v.instanceId}`).sort().join("\n"); }
|
|
11
|
+
function scoped(valid) { if (!valid)
|
|
12
|
+
throw new AuthorizationError("Environment governance response scope mismatch.", "authorization_invalid_response"); }
|
|
13
|
+
function query(value) { return new URLSearchParams(Object.entries(value).filter(([, v]) => v !== undefined).map(([k, v]) => [k, String(v)])).toString(); }
|
|
14
|
+
export class EnvironmentGovernanceClient {
|
|
15
|
+
config;
|
|
16
|
+
dependencies;
|
|
17
|
+
constructor(config, dependencies = {}) {
|
|
18
|
+
this.config = config;
|
|
19
|
+
this.dependencies = dependencies;
|
|
20
|
+
}
|
|
21
|
+
async json(path, schema, method = "GET", body) {
|
|
22
|
+
let response;
|
|
23
|
+
try {
|
|
24
|
+
response = await fetchWithKeycloakIdentity(this.config, resolveBackendUrl(this.config, { path, method }), () => ({ method, redirect: "error", signal: AbortSignal.timeout(60000), headers: { Accept: "application/json", ...(body === undefined ? {} : { "Content-Type": "application/json" }) }, ...(body === undefined ? {} : { body: JSON.stringify(body) }) }), { fetch: this.dependencies.fetch ?? fetch, tokenProvider: this.dependencies.tokenProvider ?? ensureAccessToken, retryUnauthorized: method === "GET" });
|
|
25
|
+
}
|
|
26
|
+
catch {
|
|
27
|
+
throw new AuthorizationError("Environment governance request did not complete. Read the target before taking further action; writes are never replayed.", "authorization_api_error");
|
|
28
|
+
}
|
|
29
|
+
if (!response.ok) {
|
|
30
|
+
const raw = response.headers.get("content-type")?.includes("application/json") ? await response.json().catch(() => undefined) : undefined;
|
|
31
|
+
const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" && /^[A-Z][A-Z0-9_]{1,100}$/.test(raw.code) ? raw.code : undefined;
|
|
32
|
+
throw new AuthorizationError(`Environment governance API returned HTTP ${response.status}.`, authorizationHttpErrorCode(response.status), response.status, undefined, code);
|
|
33
|
+
}
|
|
34
|
+
const result = schema.safeParse(await response.json().catch(() => undefined));
|
|
35
|
+
if (!result.success)
|
|
36
|
+
throw new AuthorizationError("Environment governance response does not match the contract.", "authorization_invalid_response", response.status);
|
|
37
|
+
return result.data;
|
|
38
|
+
}
|
|
39
|
+
identities(options = {}) { return this.json(`${IDENTITY}?${query(parse(s.pagination, options))}`, s.page); }
|
|
40
|
+
async identity(id) { id = parse(uuid, id); const result = await this.json(`${IDENTITY}/${id}`, s.identity); scoped(result.id === id); return result; }
|
|
41
|
+
identityEnvironments(id, options = {}) { return this.json(`${IDENTITY}/${parse(uuid, id)}/environments?${query(parse(s.pagination, options))}`, s.page); }
|
|
42
|
+
clientOptions(issuerId, applicationId, options = {}) { return this.json(`${IDENTITY}/client-options?${query({ ...parse(s.pagination, options), issuerId: parse(uuid, issuerId), applicationId: parse(positive, applicationId) })}`, s.page); }
|
|
43
|
+
async previewIdentity(input, id) {
|
|
44
|
+
const desired = parse(s.identityInput, input), current = id === undefined ? null : await this.identity(id);
|
|
45
|
+
if (desired.expectedVersion !== (current?.version ?? 0))
|
|
46
|
+
invalid("Observed identity configuration version changed; read and review the complete replacement again.");
|
|
47
|
+
if (current && current.issuerId !== desired.issuerId)
|
|
48
|
+
invalid("Issuer migration is not an identity configuration update.");
|
|
49
|
+
return { operation: current ? "UPDATE" : "CREATE", id: id ?? null, current, desired, remoteWrites: false };
|
|
50
|
+
}
|
|
51
|
+
async saveIdentity(input, id) {
|
|
52
|
+
const preview = await this.previewIdentity(input, id);
|
|
53
|
+
const result = await this.json(`${IDENTITY}${id ? `/${parse(uuid, id)}` : ""}`, s.identity, id ? "PUT" : "POST", preview.desired);
|
|
54
|
+
scoped((!id || result.id === id) && result.issuerId === preview.desired.issuerId && [preview.desired.expectedVersion, preview.desired.expectedVersion + 1].includes(result.version) && result.code === preview.desired.code && result.name === preview.desired.name && result.status === preview.desired.status && mappings(result.clients) === mappings(preview.desired.clients));
|
|
55
|
+
return result;
|
|
56
|
+
}
|
|
57
|
+
async binding(environmentId) {
|
|
58
|
+
environmentId = parse(positive, environmentId);
|
|
59
|
+
const result = await this.json(`${ENV}/${environmentId}/resource-binding`, s.binding);
|
|
60
|
+
scoped(result.environmentId === environmentId);
|
|
61
|
+
return result;
|
|
62
|
+
}
|
|
63
|
+
migrationIssues() { return this.json(`${ENV}/resource-binding-migration-issues`, z.array(document)); }
|
|
64
|
+
async previewBinding(environmentId, input) {
|
|
65
|
+
const desired = parse(s.bindingInput, input), current = await this.binding(environmentId);
|
|
66
|
+
if (desired.expectedVersion !== current.version)
|
|
67
|
+
invalid("Observed environment binding version changed; read and review the complete replacement again.");
|
|
68
|
+
return { operation: "UPDATE", environmentId, current, desired, remoteWrites: false };
|
|
69
|
+
}
|
|
70
|
+
async saveBinding(environmentId, input) {
|
|
71
|
+
const preview = await this.previewBinding(environmentId, input);
|
|
72
|
+
const result = await this.json(`${ENV}/${parse(positive, environmentId)}/resource-binding`, s.binding, "PUT", preview.desired);
|
|
73
|
+
scoped(result.environmentId === environmentId && [preview.desired.expectedVersion, preview.desired.expectedVersion + 1].includes(result.version) && result.identityConfigurationId === preview.desired.identityConfigurationId && result.registryNamespaceId === preview.desired.registryNamespaceId && result.defaultGatewayId === preview.desired.defaultGatewayId);
|
|
74
|
+
return result;
|
|
75
|
+
}
|
|
76
|
+
async resolved(applicationId, environmentId, slot = "RESOURCE", view = "current") {
|
|
77
|
+
applicationId = parse(positive, applicationId);
|
|
78
|
+
environmentId = parse(positive, environmentId);
|
|
79
|
+
slot = parse(environmentSlot, slot);
|
|
80
|
+
parse(z.enum(["current", "applied"]), view);
|
|
81
|
+
const result = await this.json(`${ENV}/${environmentId}/applications/${applicationId}/resolved-configuration?${query({ slot, view })}`, s.resolved);
|
|
82
|
+
scoped(result.applicationId === applicationId && result.environmentId === environmentId && result.slot === slot && result.view === view);
|
|
83
|
+
return result;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
//# sourceMappingURL=environment-governance-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"environment-governance-client.js","sourceRoot":"","sources":["../../src/authorization/environment-governance-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import type { Command } from "commander";
|
|
2
|
+
import { EnvironmentGovernanceClient } from "./environment-governance-client.js";
|
|
3
|
+
export interface EnvironmentGovernanceCommandDependencies {
|
|
4
|
+
environmentGovernanceClientFactory?: () => EnvironmentGovernanceClient;
|
|
5
|
+
}
|
|
6
|
+
export declare function registerEnvironmentGovernanceCommands(auth: Command, dependencies?: EnvironmentGovernanceCommandDependencies): void;
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import process from "node:process";
|
|
2
|
+
import { readFile } from "node:fs/promises";
|
|
3
|
+
import { loadConfig } from "../config.js";
|
|
4
|
+
import { AuthorizationError } from "./errors.js";
|
|
5
|
+
import { safeEvidence } from "./application-schemas.js";
|
|
6
|
+
import { EnvironmentGovernanceClient } from "./environment-governance-client.js";
|
|
7
|
+
const integer = (v) => { if (typeof v !== "string" || !/^\d+$/.test(v) || !Number.isSafeInteger(Number(v)))
|
|
8
|
+
throw new AuthorizationError("Expected a safe numeric catalog ID or revision.", "authorization_input_invalid"); return Number(v); };
|
|
9
|
+
const page = (o) => ({ page: integer(o.page ?? "1"), pageSize: integer(o.size ?? "20"), q: String(o.query ?? "") });
|
|
10
|
+
function paging(c) { return c.option("--page <number>", "Page starting at 1", "1").option("--size <number>", "Page size 1-100", "20").option("--query <text>", "Search current directory"); }
|
|
11
|
+
async function input(o) { let text; try {
|
|
12
|
+
text = await readFile(String(o.file), "utf8");
|
|
13
|
+
}
|
|
14
|
+
catch {
|
|
15
|
+
throw new AuthorizationError("Cannot read governance JSON file.", "authorization_input_invalid");
|
|
16
|
+
} if (Buffer.byteLength(text) > 2 * 1024 * 1024)
|
|
17
|
+
throw new AuthorizationError("Input exceeds 2 MiB.", "authorization_input_invalid"); try {
|
|
18
|
+
return JSON.parse(text);
|
|
19
|
+
}
|
|
20
|
+
catch {
|
|
21
|
+
throw new AuthorizationError("Invalid governance JSON.", "authorization_input_invalid");
|
|
22
|
+
} }
|
|
23
|
+
export function registerEnvironmentGovernanceCommands(auth, dependencies = {}) {
|
|
24
|
+
function action(c, handler, write = false) {
|
|
25
|
+
c.action(async (...args) => {
|
|
26
|
+
const o = args.at(-2);
|
|
27
|
+
if (write && o.yes !== true)
|
|
28
|
+
throw new AuthorizationError("Review preview and supply --yes with the same complete input and expectedVersion.", "authorization_input_invalid");
|
|
29
|
+
const result = await handler(dependencies.environmentGovernanceClientFactory?.() ?? new EnvironmentGovernanceClient(loadConfig("platform")), args.slice(0, -2), o);
|
|
30
|
+
process.stdout.write(`${JSON.stringify({ ok: true, data: safeEvidence(result) }, null, 2)}\n`);
|
|
31
|
+
});
|
|
32
|
+
return c;
|
|
33
|
+
}
|
|
34
|
+
const identity = auth.command("identity-configuration").description("Ordinary registered issuer and application slot mappings; local revisioned configuration");
|
|
35
|
+
identity.addHelpText("after", "\nRequires platform ops-admin. preview is read-only; save replaces the full mapping list with expectedVersion. Publish separately using protocol 3. No secret delivery or issuer migration.\n");
|
|
36
|
+
action(paging(identity.command("list")), (c, _, o) => c.identities(page(o)));
|
|
37
|
+
action(identity.command("show <id>"), (c, [id]) => c.identity(id));
|
|
38
|
+
action(paging(identity.command("environments <id>")), (c, [id], o) => c.identityEnvironments(id, page(o)));
|
|
39
|
+
action(paging(identity.command("client-options")).requiredOption("--issuer-id <uuid>", "Exact registered issuer").requiredOption("--app <number>", "Application catalog ID"), (c, _, o) => c.clientOptions(String(o.issuerId), integer(o.app), page(o)));
|
|
40
|
+
for (const name of ["preview", "save"]) {
|
|
41
|
+
const command = identity.command(name).requiredOption("--file <path>", "Complete ConfigurationInput JSON with expectedVersion").option("--id <uuid>", "Existing identity configuration; omit only for creation");
|
|
42
|
+
if (name === "save")
|
|
43
|
+
command.option("--yes", "Confirm complete reviewed replacement");
|
|
44
|
+
action(command, async (c, _, o) => name === "preview" ? c.previewIdentity(await input(o), o.id ? String(o.id) : undefined) : c.saveIdentity(await input(o), o.id ? String(o.id) : undefined), name === "save");
|
|
45
|
+
}
|
|
46
|
+
const resources = auth.command("environment-resource").description("Numeric platform environment resource binding; distinct from application environment UUIDs");
|
|
47
|
+
resources.addHelpText("after", "\npreview performs GET and validates expectedVersion. save updates local binding only, never publishes or clears omitted fields. Include all three nullable resource pointers. current is draft composition; applied is an activated snapshot, not runtime loading proof.\n");
|
|
48
|
+
action(resources.command("show <environment-id>"), (c, [id]) => c.binding(integer(id)));
|
|
49
|
+
action(resources.command("migration-issues"), (c) => c.migrationIssues());
|
|
50
|
+
for (const name of ["preview", "save"]) {
|
|
51
|
+
const command = resources.command(`${name} <environment-id>`).requiredOption("--file <path>", "Complete BindingInput JSON with expectedVersion and all pointers");
|
|
52
|
+
if (name === "save")
|
|
53
|
+
command.option("--yes", "Confirm reviewed binding revision");
|
|
54
|
+
action(command, async (c, [id], o) => name === "preview" ? c.previewBinding(integer(id), await input(o)) : c.saveBinding(integer(id), await input(o)), name === "save");
|
|
55
|
+
}
|
|
56
|
+
action(resources.command("resolved <environment-id>").requiredOption("--app <number>", "Application catalog ID").option("--slot <slot>", "RESOURCE, CLI_LOGIN, BROWSER_LOGIN or MACHINE:<purpose>", "RESOURCE").option("--view <view>", "current or applied", "current"), (c, [id], o) => c.resolved(integer(o.app), integer(id), String(o.slot), String(o.view)));
|
|
57
|
+
}
|
|
58
|
+
//# sourceMappingURL=environment-governance-commands.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"environment-governance-commands.js","sourceRoot":"","sources":["../../src/authorization/environment-governance-commands.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
export declare const pagination: z.ZodObject<{
|
|
3
|
+
page: z.ZodDefault<z.ZodNumber>;
|
|
4
|
+
pageSize: z.ZodDefault<z.ZodNumber>;
|
|
5
|
+
q: z.ZodDefault<z.ZodString>;
|
|
6
|
+
}, z.core.$strict>;
|
|
7
|
+
export declare const page: z.ZodObject<{
|
|
8
|
+
items: z.ZodArray<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
9
|
+
total: z.ZodNumber;
|
|
10
|
+
page: z.ZodNumber;
|
|
11
|
+
pageSize: z.ZodNumber;
|
|
12
|
+
}, z.core.$loose>;
|
|
13
|
+
export declare const clientMapping: z.ZodObject<{
|
|
14
|
+
applicationId: z.ZodNumber;
|
|
15
|
+
slot: z.ZodString;
|
|
16
|
+
referenceId: z.ZodString;
|
|
17
|
+
instanceId: z.ZodString;
|
|
18
|
+
}, z.core.$strict>;
|
|
19
|
+
export declare const identityInput: z.ZodObject<{
|
|
20
|
+
expectedVersion: z.ZodNumber;
|
|
21
|
+
code: z.ZodString;
|
|
22
|
+
name: z.ZodString;
|
|
23
|
+
issuerId: z.ZodString;
|
|
24
|
+
status: z.ZodEnum<{
|
|
25
|
+
ACTIVE: "ACTIVE";
|
|
26
|
+
DISABLED: "DISABLED";
|
|
27
|
+
DRAFT: "DRAFT";
|
|
28
|
+
}>;
|
|
29
|
+
clients: z.ZodArray<z.ZodObject<{
|
|
30
|
+
applicationId: z.ZodNumber;
|
|
31
|
+
slot: z.ZodString;
|
|
32
|
+
referenceId: z.ZodString;
|
|
33
|
+
instanceId: z.ZodString;
|
|
34
|
+
}, z.core.$strict>>;
|
|
35
|
+
}, z.core.$strict>;
|
|
36
|
+
export declare const identity: z.ZodObject<{
|
|
37
|
+
id: z.ZodString;
|
|
38
|
+
code: z.ZodString;
|
|
39
|
+
name: z.ZodString;
|
|
40
|
+
issuerId: z.ZodString;
|
|
41
|
+
status: z.ZodEnum<{
|
|
42
|
+
ACTIVE: "ACTIVE";
|
|
43
|
+
DISABLED: "DISABLED";
|
|
44
|
+
DRAFT: "DRAFT";
|
|
45
|
+
}>;
|
|
46
|
+
version: z.ZodNumber;
|
|
47
|
+
clients: z.ZodArray<z.ZodObject<{
|
|
48
|
+
applicationId: z.ZodNumber;
|
|
49
|
+
slot: z.ZodString;
|
|
50
|
+
referenceId: z.ZodString;
|
|
51
|
+
instanceId: z.ZodString;
|
|
52
|
+
}, z.core.$loose>>;
|
|
53
|
+
environmentReferenceCount: z.ZodNumber;
|
|
54
|
+
}, z.core.$loose>;
|
|
55
|
+
export declare const bindingInput: z.ZodObject<{
|
|
56
|
+
expectedVersion: z.ZodNumber;
|
|
57
|
+
identityConfigurationId: z.ZodNullable<z.ZodString>;
|
|
58
|
+
registryNamespaceId: z.ZodNullable<z.ZodNumber>;
|
|
59
|
+
defaultGatewayId: z.ZodNullable<z.ZodString>;
|
|
60
|
+
}, z.core.$strict>;
|
|
61
|
+
export declare const binding: z.ZodObject<{
|
|
62
|
+
environmentId: z.ZodNumber;
|
|
63
|
+
envCode: z.ZodString;
|
|
64
|
+
version: z.ZodNumber;
|
|
65
|
+
identityConfigurationId: z.ZodNullable<z.ZodString>;
|
|
66
|
+
registryNamespaceId: z.ZodNullable<z.ZodNumber>;
|
|
67
|
+
defaultGatewayId: z.ZodNullable<z.ZodString>;
|
|
68
|
+
}, z.core.$loose>;
|
|
69
|
+
export declare const resolved: z.ZodObject<{
|
|
70
|
+
schemaVersion: z.ZodLiteral<1>;
|
|
71
|
+
applicationId: z.ZodNumber;
|
|
72
|
+
environmentId: z.ZodNumber;
|
|
73
|
+
envCode: z.ZodString;
|
|
74
|
+
slot: z.ZodString;
|
|
75
|
+
view: z.ZodEnum<{
|
|
76
|
+
applied: "applied";
|
|
77
|
+
current: "current";
|
|
78
|
+
}>;
|
|
79
|
+
}, z.core.$loose>;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import { uuid, version, positive, environmentSlot, document } from "./application-schemas.js";
|
|
3
|
+
const text = z.string().trim().min(1);
|
|
4
|
+
export const pagination = z.object({ page: positive.max(100000).default(1), pageSize: positive.max(100).default(20), q: z.string().max(100).default("") }).strict();
|
|
5
|
+
export const page = z.object({ items: z.array(document), total: version, page: positive, pageSize: positive.max(100) }).passthrough();
|
|
6
|
+
export const clientMapping = z.object({ applicationId: positive, slot: environmentSlot, referenceId: uuid, instanceId: uuid }).strict();
|
|
7
|
+
export const identityInput = z.object({ expectedVersion: version, code: z.string().regex(/^[A-Za-z0-9][A-Za-z0-9._-]{0,119}$/), name: text.max(160), issuerId: uuid,
|
|
8
|
+
status: z.enum(["DRAFT", "ACTIVE", "DISABLED"]), clients: z.array(clientMapping) }).strict().refine(v => new Set(v.clients.map(c => `${c.applicationId}/${c.slot}`)).size === v.clients.length, "Duplicate application slot");
|
|
9
|
+
export const identity = z.object({ id: uuid, code: text, name: text, issuerId: uuid, status: z.enum(["DRAFT", "ACTIVE", "DISABLED"]), version,
|
|
10
|
+
clients: z.array(clientMapping.loose()), environmentReferenceCount: version }).passthrough();
|
|
11
|
+
// PUT is a complete replacement. Require every nullable pointer so omission cannot clear it accidentally.
|
|
12
|
+
export const bindingInput = z.object({ expectedVersion: version, identityConfigurationId: uuid.nullable(), registryNamespaceId: positive.nullable(), defaultGatewayId: uuid.nullable() }).strict();
|
|
13
|
+
export const binding = z.object({ environmentId: positive, envCode: text, version, identityConfigurationId: uuid.nullable(), registryNamespaceId: positive.nullable(), defaultGatewayId: uuid.nullable() }).passthrough();
|
|
14
|
+
export const resolved = z.object({ schemaVersion: z.literal(1), applicationId: positive, environmentId: positive, envCode: text, slot: environmentSlot, view: z.enum(["current", "applied"]) }).passthrough();
|
|
15
|
+
//# sourceMappingURL=environment-governance-schemas.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"environment-governance-schemas.js","sourceRoot":"","sources":["../../src/authorization/environment-governance-schemas.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
import type { AuthConfig } from "../config.js";
|
|
3
|
+
import { type KeycloakTokenProvider } from "../oauth.js";
|
|
4
|
+
declare const selection: z.ZodObject<{
|
|
5
|
+
environmentId: z.ZodOptional<z.ZodNumber>;
|
|
6
|
+
envCode: z.ZodOptional<z.ZodString>;
|
|
7
|
+
slot: z.ZodDefault<z.ZodString>;
|
|
8
|
+
releaseId: z.ZodOptional<z.ZodString>;
|
|
9
|
+
artifactType: z.ZodDefault<z.ZodEnum<{
|
|
10
|
+
BROWSER: "BROWSER";
|
|
11
|
+
PROTECTED: "PROTECTED";
|
|
12
|
+
}>>;
|
|
13
|
+
}, z.core.$strict>;
|
|
14
|
+
export type RuntimeArtifactSelection = z.input<typeof selection>;
|
|
15
|
+
/** Java producer's canonical JSON: recursive lexical object keys, original array order. */
|
|
16
|
+
export declare function runtimeArtifactDigest(value: unknown): string;
|
|
17
|
+
export declare class RuntimeArtifactClient {
|
|
18
|
+
private readonly config;
|
|
19
|
+
private readonly applicationId;
|
|
20
|
+
private readonly dependencies;
|
|
21
|
+
constructor(config: AuthConfig, applicationId: number, dependencies?: {
|
|
22
|
+
fetch?: typeof fetch;
|
|
23
|
+
tokenProvider?: KeycloakTokenProvider;
|
|
24
|
+
});
|
|
25
|
+
download(input: RuntimeArtifactSelection, output: string): Promise<{
|
|
26
|
+
output: string;
|
|
27
|
+
contractVersion: number;
|
|
28
|
+
releaseId: string;
|
|
29
|
+
envCode: string;
|
|
30
|
+
slot: string;
|
|
31
|
+
artifactType: "BROWSER" | "PROTECTED";
|
|
32
|
+
digest: string;
|
|
33
|
+
loadingState: "UNVERIFIED";
|
|
34
|
+
}>;
|
|
35
|
+
}
|
|
36
|
+
export {};
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
import { createHash } from "node:crypto";
|
|
2
|
+
import { open, unlink } from "node:fs/promises";
|
|
3
|
+
import { resolve } from "node:path";
|
|
4
|
+
import { z } from "zod";
|
|
5
|
+
import { resolveBackendUrl } from "../backend.js";
|
|
6
|
+
import { ensureAccessToken, fetchWithKeycloakIdentity } from "../oauth.js";
|
|
7
|
+
import { AuthorizationError, authorizationHttpErrorCode } from "./errors.js";
|
|
8
|
+
const selection = z.object({
|
|
9
|
+
environmentId: z.number().int().positive().safe().optional(),
|
|
10
|
+
envCode: z.string().min(1).max(120).refine(v => v.trim() === v).optional(),
|
|
11
|
+
slot: z.string().regex(/^(BROWSER_LOGIN|CLI_LOGIN|RESOURCE|MACHINE:[A-Za-z0-9._-]+)$/).default("RESOURCE"),
|
|
12
|
+
releaseId: z.string().uuid().optional(),
|
|
13
|
+
artifactType: z.enum(["PROTECTED", "BROWSER"]).default("PROTECTED"),
|
|
14
|
+
}).strict().refine(v => (v.environmentId === undefined) !== (v.envCode === undefined))
|
|
15
|
+
.refine(v => v.artifactType !== "BROWSER" || v.slot === "BROWSER_LOGIN");
|
|
16
|
+
const artifactSchema = z.object({
|
|
17
|
+
contractVersion: z.literal(1), artifactType: z.enum(["PROTECTED", "BROWSER"]),
|
|
18
|
+
releaseId: z.string().uuid(), envCode: z.string().min(1), slot: z.string(),
|
|
19
|
+
loadingState: z.literal("UNVERIFIED"),
|
|
20
|
+
applicationId: z.number().int().positive().safe().optional(),
|
|
21
|
+
environmentId: z.number().int().positive().safe().optional(),
|
|
22
|
+
sourceDigest: z.string().regex(/^[a-f0-9]{64}$/).optional(),
|
|
23
|
+
configuration: z.record(z.string(), z.unknown()), digest: z.string().regex(/^[a-f0-9]{64}$/),
|
|
24
|
+
}).strict();
|
|
25
|
+
const browserConfiguration = z.object({
|
|
26
|
+
applicationCode: z.string().optional(), apiBaseUrl: z.string().url().optional(),
|
|
27
|
+
roleClientId: z.string().min(1).refine(v => v.trim() === v).optional(),
|
|
28
|
+
identity: z.object({ issuerUrl: z.string().url(), clientId: z.string().min(1),
|
|
29
|
+
audiences: z.array(z.object({ clientId: z.string().min(1) }).strict()).optional(),
|
|
30
|
+
}).strict(),
|
|
31
|
+
}).strict().refine(v => v.roleClientId === undefined || v.identity.audiences?.some(audience => audience.clientId === v.roleClientId) === true);
|
|
32
|
+
function invalid(response = false) {
|
|
33
|
+
throw new AuthorizationError(response ? "Runtime artifact response is invalid or does not match the requested release." : "Select exactly one numeric environment ID or environment code, a valid slot, and an optional release ID.", response ? "authorization_invalid_response" : "authorization_input_invalid");
|
|
34
|
+
}
|
|
35
|
+
/** Java producer's canonical JSON: recursive lexical object keys, original array order. */
|
|
36
|
+
export function runtimeArtifactDigest(value) {
|
|
37
|
+
const encode = (item) => {
|
|
38
|
+
if (item === null || typeof item === "string" || typeof item === "boolean")
|
|
39
|
+
return JSON.stringify(item);
|
|
40
|
+
if (typeof item === "number" && Number.isFinite(item) && (!Number.isInteger(item) || Number.isSafeInteger(item)))
|
|
41
|
+
return JSON.stringify(item);
|
|
42
|
+
if (Array.isArray(item))
|
|
43
|
+
return `[${item.map(encode).join(",")}]`;
|
|
44
|
+
if (item && typeof item === "object")
|
|
45
|
+
return `{${Object.entries(item).sort(([a], [b]) => a < b ? -1 : a > b ? 1 : 0).map(([key, child]) => `${JSON.stringify(key)}:${encode(child)}`).join(",")}}`;
|
|
46
|
+
return invalid(true);
|
|
47
|
+
};
|
|
48
|
+
return createHash("sha256").update(encode(value), "utf8").digest("hex");
|
|
49
|
+
}
|
|
50
|
+
function credentialFree(value) {
|
|
51
|
+
if (Array.isArray(value))
|
|
52
|
+
return value.every(credentialFree);
|
|
53
|
+
if (value && typeof value === "object")
|
|
54
|
+
return Object.entries(value).every(([name, item]) => {
|
|
55
|
+
const key = name.replace(/[_-]/g, "").toLowerCase();
|
|
56
|
+
const reference = /(?:ref|reference|refs|references)$/.test(key);
|
|
57
|
+
return (reference || !/(?:password|secret|token|credential|^authorization$|^cookie$)/.test(key)) && credentialFree(item);
|
|
58
|
+
});
|
|
59
|
+
return true;
|
|
60
|
+
}
|
|
61
|
+
export class RuntimeArtifactClient {
|
|
62
|
+
config;
|
|
63
|
+
applicationId;
|
|
64
|
+
dependencies;
|
|
65
|
+
constructor(config, applicationId, dependencies = {}) {
|
|
66
|
+
this.config = config;
|
|
67
|
+
this.applicationId = applicationId;
|
|
68
|
+
this.dependencies = dependencies;
|
|
69
|
+
if (!Number.isSafeInteger(applicationId) || applicationId < 1)
|
|
70
|
+
invalid();
|
|
71
|
+
}
|
|
72
|
+
async download(input, output) {
|
|
73
|
+
const parsed = selection.safeParse(input);
|
|
74
|
+
if (!parsed.success || !output.trim())
|
|
75
|
+
invalid();
|
|
76
|
+
const chosen = parsed.data;
|
|
77
|
+
const query = new URLSearchParams({ applicationId: String(this.applicationId), ...Object.fromEntries(Object.entries(chosen).map(([k, v]) => [k, String(v)])) });
|
|
78
|
+
const path = `/api/v1/admin/environments/runtime-configuration?${query}`;
|
|
79
|
+
let response;
|
|
80
|
+
try {
|
|
81
|
+
response = await fetchWithKeycloakIdentity(this.config, resolveBackendUrl(this.config, { path, method: "GET" }), () => ({ method: "GET", redirect: "error", signal: AbortSignal.timeout(60000), headers: { Accept: "application/json" } }), { fetch: this.dependencies.fetch ?? fetch, tokenProvider: this.dependencies.tokenProvider ?? ensureAccessToken, retryUnauthorized: true });
|
|
82
|
+
}
|
|
83
|
+
catch {
|
|
84
|
+
throw new AuthorizationError("Runtime artifact download did not complete.", "authorization_api_error");
|
|
85
|
+
}
|
|
86
|
+
if (!response.ok) {
|
|
87
|
+
const body = await response.json().catch(() => undefined);
|
|
88
|
+
const code = body && typeof body === "object" ? (body.code ?? body.detail) : undefined;
|
|
89
|
+
throw new AuthorizationError(`Runtime artifact API returned HTTP ${response.status}.`, authorizationHttpErrorCode(response.status), response.status, undefined, typeof code === "string" && /^[A-Z][A-Z0-9_]{1,100}$/.test(code) ? code : undefined);
|
|
90
|
+
}
|
|
91
|
+
const text = await response.text();
|
|
92
|
+
if (Buffer.byteLength(text) > 2 * 1024 * 1024)
|
|
93
|
+
invalid(true);
|
|
94
|
+
let raw;
|
|
95
|
+
try {
|
|
96
|
+
raw = JSON.parse(text);
|
|
97
|
+
}
|
|
98
|
+
catch {
|
|
99
|
+
invalid(true);
|
|
100
|
+
}
|
|
101
|
+
const result = artifactSchema.safeParse(raw);
|
|
102
|
+
if (!result.success)
|
|
103
|
+
invalid(true);
|
|
104
|
+
const artifact = result.data;
|
|
105
|
+
const { digest, ...unsigned } = artifact;
|
|
106
|
+
if (artifact.artifactType !== chosen.artifactType || artifact.slot !== chosen.slot || chosen.releaseId && artifact.releaseId !== chosen.releaseId || chosen.envCode && artifact.envCode !== chosen.envCode)
|
|
107
|
+
invalid(true);
|
|
108
|
+
if (artifact.artifactType === "PROTECTED" && (artifact.applicationId !== this.applicationId || !artifact.environmentId || !artifact.sourceDigest || chosen.environmentId && artifact.environmentId !== chosen.environmentId))
|
|
109
|
+
invalid(true);
|
|
110
|
+
if (artifact.artifactType === "BROWSER" && (artifact.environmentId !== undefined || artifact.applicationId !== undefined || !browserConfiguration.safeParse(artifact.configuration).success))
|
|
111
|
+
invalid(true);
|
|
112
|
+
if (runtimeArtifactDigest(unsigned) !== digest || !credentialFree(artifact.configuration))
|
|
113
|
+
invalid(true);
|
|
114
|
+
const destination = resolve(output);
|
|
115
|
+
let created = false;
|
|
116
|
+
try {
|
|
117
|
+
const file = await open(destination, "wx", 0o600);
|
|
118
|
+
created = true;
|
|
119
|
+
try {
|
|
120
|
+
await file.writeFile(`${JSON.stringify(artifact, null, 2)}\n`, "utf8");
|
|
121
|
+
await file.sync();
|
|
122
|
+
}
|
|
123
|
+
finally {
|
|
124
|
+
await file.close();
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
catch {
|
|
128
|
+
if (created)
|
|
129
|
+
await unlink(destination).catch(() => undefined);
|
|
130
|
+
throw new AuthorizationError("Cannot create artifact output file; choose a new writable path. Existing files are never overwritten.", "authorization_input_invalid");
|
|
131
|
+
}
|
|
132
|
+
return { output: destination, contractVersion: 1, releaseId: artifact.releaseId, envCode: artifact.envCode, slot: artifact.slot, artifactType: artifact.artifactType, digest, loadingState: artifact.loadingState };
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
//# sourceMappingURL=runtime-artifact-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runtime-artifact-client.js","sourceRoot":"","sources":["../../src/authorization/runtime-artifact-client.ts"],"names":[],"mappings":"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"}
|