joelniklaus's picture
joelniklaus HF Staff
deploy: 38a879272d474ca1517a3617e512db53d1460598 (part 2)
31c6cca verified
Raw
History Blame Contribute Delete
8.95 kB
import { HuggingFaceBucketWriteProbe } from "./bucket-write-probe.js";
import { SystemInstallerClock } from "./clock.js";
import { HuggingFaceControlTokenScope } from "./control-token-scope.js";
import { HfCli } from "./hf.js";
import { BoundedHttpAdapter } from "./http.js";
import { StableIdentityAdapter } from "./identity.js";
import { HuggingFaceInferenceTokenScope } from "./inference-token-scope.js";
import type { InstallPlan } from "./model.js";
import { BoundedJsonProcess } from "./process.js";
import { TtyInstallerSecretInput } from "./secret-input.js";
import { GitSourceAdapter } from "./source.js";
import type {
ActivationResult,
ApplyInstallResult,
ConfigureProgressEvent,
InstallerDependencies,
} from "./workflow.js";
export function defaultDependencies(): InstallerDependencies {
const hf = new HfCli(new BoundedJsonProcess());
const http = new BoundedHttpAdapter();
return {
hf,
clock: new SystemInstallerClock(),
bucketWriteProbe: new HuggingFaceBucketWriteProbe(),
controlTokenScope: new HuggingFaceControlTokenScope(http),
inferenceTokenScope: new HuggingFaceInferenceTokenScope(http),
reportControlCredentialWarnings(warnings) {
process.stderr.write(formatControlCredentialWarnings(warnings));
},
reportConfigureProgress(event) {
process.stderr.write(`${formatConfigureProgress(event)}\n`);
},
http,
identity: new StableIdentityAdapter(hf, http),
secretInput: new TtyInstallerSecretInput(),
source: new GitSourceAdapter(),
};
}
function formatElapsed(milliseconds: number): string {
const seconds = Math.max(0, Math.floor(milliseconds / 1000));
const minutes = Math.floor(seconds / 60);
const remainingSeconds = seconds % 60;
return minutes === 0 ? `${seconds}s` : `${minutes}m ${remainingSeconds}s`;
}
export function formatConfigureProgress(event: ConfigureProgressEvent): string {
switch (event.kind) {
case "runtime_wait_started":
return "Waiting for the Space runtime to start...";
case "runtime_waiting":
return `Space runtime is still starting (${formatElapsed(event.elapsedMilliseconds)} elapsed).`;
case "runtime_wait_complete":
return `Space runtime wait completed (${formatElapsed(event.elapsedMilliseconds)} elapsed).`;
case "readiness_wait_started":
return "Waiting for the control service to become ready...";
case "readiness_initializing":
return `Control service is still initializing (${formatElapsed(event.elapsedMilliseconds)} elapsed).`;
case "readiness_ready":
return `Control service is ready (${formatElapsed(event.elapsedMilliseconds)} elapsed).`;
case "readiness_timed_out":
return `Control service readiness timed out (${formatElapsed(event.elapsedMilliseconds)} elapsed).`;
}
}
export function parseOptions(
args: readonly string[],
specification: Record<string, { required: boolean }>,
): Record<string, string> | "help" {
if (args.includes("--help")) return "help";
const output: Record<string, string> = {};
for (let index = 0; index < args.length; index += 2) {
const key = args[index];
const value = args[index + 1];
if (!key?.startsWith("--") || !value || value.startsWith("--")) {
throw new Error("invalid command arguments");
}
const name = key.slice(2);
if (!(name in specification) || name in output) {
throw new Error("invalid command arguments");
}
output[name] = value;
}
for (const [name, option] of Object.entries(specification)) {
if (option.required && !output[name]) {
throw new Error(`missing --${name}`);
}
}
return output;
}
export function parseSavedPlanOptions(
args: readonly string[],
): { space: string; stateDirectory?: string } | "help" {
const options = parseOptions(args, {
space: { required: true },
"state-dir": { required: false },
});
if (options === "help") return options;
return {
space: options.space as string,
...(options["state-dir"] ? { stateDirectory: options["state-dir"] as string } : {}),
};
}
export function parseConfigureOptions(
args: readonly string[],
): { space: string; stateDirectory?: string; replaceCredentials: boolean } | "help" {
if (args.includes("--help")) return "help";
const replacementFlags = args.filter((arg) => arg === "--replace-credentials");
if (replacementFlags.length > 1) throw new Error("invalid command arguments");
const saved = parseSavedPlanOptions(
args.filter((arg) => arg !== "--replace-credentials"),
);
if (saved === "help") return saved;
return {
...saved,
replaceCredentials: replacementFlags.length === 1,
};
}
export function formatPlanOutput(
plan: InstallPlan,
customStateDirectory = false,
): string {
const observed = plan.observed_preconditions;
const phase = observed.space?.variables.HARBOR_HF_INSTALL_PHASE;
const action =
phase === "credentials_required" || phase === "source_staged"
? "continue paused credential bootstrap"
: !observed.space
? "create paused bootstrap Space and Bucket"
: observed.bucket
? "update installer-managed Space"
: "update Space and create Bucket";
const nextCommand =
!observed.space || !observed.bucket ? "install:provision" : "install:configure";
return [
`Space: ${plan.targets.space_id}`,
`Bucket: ${plan.targets.bucket_id}`,
"Access: protected",
"Hardware: cpu-basic",
"Write mode: disabled",
`Action: ${action}`,
"",
"Plan saved privately.",
...(!observed.space ? ["No service credentials are required for bootstrap."] : []),
customStateDirectory
? `Next: rerun ${nextCommand} with this Space and the same --state-dir.`
: `Next: npm run ${nextCommand} -- --space ${plan.targets.space_id}`,
"",
].join("\n");
}
export function formatProvisionOutput(
result: Extract<ApplyInstallResult, { status: "credentials_required" }>,
customStateDirectory = false,
): string {
return [
"Provisioning verified.",
"",
`Space: ${result.space_id}`,
`Bucket: ${result.bucket_id}`,
"Runtime: paused",
"Write mode: disabled",
"Secrets stored: no",
"Source uploaded: no",
"",
customStateDirectory
? "Next: rerun install:configure with this Space and the same --state-dir."
: `Next: npm run install:configure -- --space ${result.space_id}`,
"",
].join("\n");
}
export function formatConfigureOutput(
spaceId: string,
result: Extract<ApplyInstallResult, { status: "installed" }>,
): string {
const verification = result.verification;
const warnings =
result.control_credential_warnings.length === 0 ||
result.control_credential_warnings_reported
? []
: formatControlCredentialWarnings(result.control_credential_warnings)
.trimEnd()
.split("\n");
return [
...warnings,
"Installation verified.",
`Space: ${spaceId}`,
`URL: ${verification.space_url}`,
`Anonymous health: ${verification.anonymous_live}`,
`Authenticated system: ${verification.authenticated_system}`,
`Source upload: ${verification.source_upload_revision}`,
"Write mode: disabled",
"Production ready: no",
"",
"Review access and credential scopes before activation.",
"",
].join("\n");
}
export function formatControlCredentialWarnings(warnings: readonly string[]): string {
if (warnings.length === 0) return "";
return [
"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!",
"WARNING: THE CONTROL CREDENTIAL IS OVER-SCOPED",
"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!",
...warnings.map((warning) => `WARNING: ${warning}`),
"WARNING: Installation is continuing because required permissions and",
"WARNING: the fresh artifact Bucket write/read-back proof passed.",
"WARNING: Replace this credential with a narrower token when possible.",
"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!",
"",
].join("\n");
}
export function formatActivationOutput(
spaceId: string,
result: ActivationResult,
): string {
return [
result.write_mode === "enabled"
? "Installation activated."
: "Writes disabled and Space paused.",
`Space: ${spaceId}`,
`URL: ${result.space_url}`,
"Hardware: cpu-basic",
`Runtime: ${result.runtime}`,
`Write mode: ${result.write_mode}`,
`Authenticated system: ${result.authenticated_system}`,
"Production ready: no",
...(result.write_mode === "enabled"
? ["", "Campaign submissions and reconciliation are enabled."]
: []),
"",
].join("\n");
}
export async function cliMain(action: () => Promise<void>): Promise<void> {
try {
await action();
} catch (error) {
const message = error instanceof Error ? error.message : "installer failed";
process.stderr.write(`error: ${message}\n`);
process.exitCode = 1;
}
}