mirror of
https://github.com/whyour/qinglong.git
synced 2026-09-20 16:07:11 +08:00
feat(ql3): add unified cluster operator cli
This commit is contained in:
@@ -0,0 +1,49 @@
|
||||
'use strict';
|
||||
|
||||
const assert = require('node:assert/strict');
|
||||
const { spawnSync } = require('node:child_process');
|
||||
const path = require('node:path');
|
||||
const { test } = require('node:test');
|
||||
const {
|
||||
parseArguments,
|
||||
} = require('../../scripts/ql3-cluster-admin-product-live-contract.cjs');
|
||||
|
||||
const script = path.resolve(
|
||||
__dirname,
|
||||
'../../scripts/ql3-cluster-admin-product-live-contract.cjs',
|
||||
);
|
||||
|
||||
test('accepts one bounded image reference', () => {
|
||||
assert.equal(
|
||||
parseArguments(['--image=registry.example.com/qinglong/admin@sha256:abc']),
|
||||
'registry.example.com/qinglong/admin@sha256:abc',
|
||||
);
|
||||
});
|
||||
|
||||
test('rejects missing, duplicate, unknown, empty or unsafe image arguments', () => {
|
||||
for (const argv of [
|
||||
[],
|
||||
['--image=one', '--image=two'],
|
||||
['--profile=admin'],
|
||||
['--image='],
|
||||
['--image=admin image'],
|
||||
[`--image=${'a'.repeat(257)}`],
|
||||
]) {
|
||||
assert.throws(() => parseArguments(argv), /live contract failed/);
|
||||
}
|
||||
});
|
||||
|
||||
test('fails closed before Docker without explicit opt-in', () => {
|
||||
const result = spawnSync(
|
||||
process.execPath,
|
||||
[script, '--image=missing:latest'],
|
||||
{
|
||||
encoding: 'utf8',
|
||||
env: { ...process.env, QL3_CLUSTER_ADMIN_PRODUCT_LIVE: '0' },
|
||||
},
|
||||
);
|
||||
assert.equal(result.status, 1);
|
||||
assert.equal(result.stdout, '');
|
||||
assert.match(result.stderr, /QL3_CLUSTER_ADMIN_PRODUCT_LIVE=1 is required/);
|
||||
assert.equal(result.stderr.includes('spawn'), false);
|
||||
});
|
||||
@@ -29,6 +29,7 @@ test('accepts the exact locked non-root multi-replica cluster deployment', () =>
|
||||
'optional-read-only-projected-keyring',
|
||||
);
|
||||
assert.equal(report.promptOutputKeyRotation, 'caller-driven-staged-material');
|
||||
assert.equal(report.clusterAdminImageReferences, 24);
|
||||
assert.deepEqual(report.workspacePackages, [
|
||||
'@qinglong/runtime-core',
|
||||
'@qinglong/cluster-postgres',
|
||||
@@ -41,6 +42,65 @@ test('accepts the exact locked non-root multi-replica cluster deployment', () =>
|
||||
]);
|
||||
});
|
||||
|
||||
test('requires every Cluster Admin Kubernetes workload to override the image command', () => {
|
||||
const report = auditClusterDeployment({
|
||||
root: ROOT,
|
||||
readFile: intercept(
|
||||
'deploy/kubernetes/ql3-cluster/operations/approval-management/base/deployment.yaml',
|
||||
(source) =>
|
||||
source.replace(
|
||||
' command:\n - node\n - /opt/qinglong/node_modules/@qinglong/cluster-admin/dist/approval-management/approvalManagementCli.js\n',
|
||||
'',
|
||||
),
|
||||
),
|
||||
});
|
||||
assert.equal(report.compatible, false);
|
||||
assert.equal(report.clusterAdminImageReferences, 24);
|
||||
assert.equal(
|
||||
report.findings.some(
|
||||
({ code }) => code === 'QL3_CLUSTER_ADMIN_IMAGE_COMMAND_IMPLICIT',
|
||||
),
|
||||
true,
|
||||
);
|
||||
});
|
||||
|
||||
test('requires the bounded Cluster product facade and image entrypoint', () => {
|
||||
const missingBinary = auditClusterDeployment({
|
||||
root: ROOT,
|
||||
readFile: intercept('packages/ql3-cluster-admin/package.json', (source) => {
|
||||
const manifest = JSON.parse(source);
|
||||
delete manifest.bin['ql3-cluster-admin'];
|
||||
return JSON.stringify(manifest);
|
||||
}),
|
||||
});
|
||||
assert.equal(missingBinary.compatible, false);
|
||||
assert.equal(
|
||||
missingBinary.findings.some(
|
||||
({ code }) => code === 'QL3_CLUSTER_PLUGIN_RECOVERY_ENTRYPOINT_MISSING',
|
||||
),
|
||||
true,
|
||||
);
|
||||
|
||||
const legacyEntrypoint = auditClusterDeployment({
|
||||
root: ROOT,
|
||||
readFile: intercept(
|
||||
'deploy/containers/ql3-cluster-admin/Dockerfile',
|
||||
(source) =>
|
||||
source.replace(
|
||||
'dist/product-cli/cli.js',
|
||||
'dist/plugin-package/recovery/pluginPackageRecoveryCli.js',
|
||||
),
|
||||
),
|
||||
});
|
||||
assert.equal(legacyEntrypoint.compatible, false);
|
||||
assert.equal(
|
||||
legacyEntrypoint.findings.some(
|
||||
({ code }) => code === 'QL3_CLUSTER_ADMIN_DOCKERFILE_CONTRACT_MISSING',
|
||||
),
|
||||
true,
|
||||
);
|
||||
});
|
||||
|
||||
test('keeps Cluster AI optional with projected authority and an independent digest', () => {
|
||||
const defaultEnabled = auditClusterDeployment({
|
||||
root: ROOT,
|
||||
|
||||
@@ -26,6 +26,7 @@ test('accepts the reviewed native CI and digest release contracts', () => {
|
||||
images: ['control', 'control-ai', 'admin', 'local'],
|
||||
nativeArchitectures: ['amd64', 'arm64'],
|
||||
runtimeInventory: true,
|
||||
clusterAdminProductFacade: true,
|
||||
ociAttestations: true,
|
||||
osVulnerabilityScan: {
|
||||
scanner: 'trivy@0.70.0',
|
||||
@@ -98,6 +99,17 @@ test('rejects removal of the native arm64 image gate', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('rejects removal of the native Cluster Admin product facade gate', () => {
|
||||
const mutated = ciSource.replace(
|
||||
"QL3_CLUSTER_ADMIN_PRODUCT_LIVE: '1'",
|
||||
"QL3_CLUSTER_ADMIN_PRODUCT_LIVE: '0'",
|
||||
);
|
||||
assert.throws(
|
||||
() => auditClusterImageCiWorkflow(mutated),
|
||||
/bounded product facade contract/,
|
||||
);
|
||||
});
|
||||
|
||||
test('rejects removal of the native cluster-admin image gate', () => {
|
||||
const mutated = ciSource.replace(
|
||||
'image_arch: arm64\n image: admin',
|
||||
|
||||
@@ -340,10 +340,10 @@ test('current QL3 workspace has exactly eighteen reviewed package boundaries', (
|
||||
rootSourceFileRoles: clusterAdmin.rootSourceFileRoles,
|
||||
},
|
||||
{
|
||||
sourceFiles: 94,
|
||||
sourceFiles: 96,
|
||||
rootSourceFiles: 1,
|
||||
rootSourceLines: 61,
|
||||
nestedSourceFiles: 93,
|
||||
nestedSourceFiles: 95,
|
||||
rootSourceFileRoles: {
|
||||
'modelInvocationMigrationCli.ts': 'binary_entry',
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user