hunter-harness 0.2.7 → 0.2.8
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/dist/bin.js +63 -9
- package/package.json +1 -1
package/dist/bin.js
CHANGED
|
@@ -4,6 +4,7 @@
|
|
|
4
4
|
import { realpathSync } from "node:fs";
|
|
5
5
|
import { pathToFileURL } from "node:url";
|
|
6
6
|
import { createInterface } from "node:readline/promises";
|
|
7
|
+
import { Writable } from "node:stream";
|
|
7
8
|
import { Command, CommanderError } from "commander";
|
|
8
9
|
|
|
9
10
|
// ../contracts/dist/ai-config.js
|
|
@@ -3379,6 +3380,17 @@ async function ensureCredentialsGitignore(projectRoot) {
|
|
|
3379
3380
|
}
|
|
3380
3381
|
}
|
|
3381
3382
|
const existing = new Set(content.split("\n").map((line) => line.trim()));
|
|
3383
|
+
const harnessDirectoryIgnored = [
|
|
3384
|
+
".harness",
|
|
3385
|
+
".harness/",
|
|
3386
|
+
"/.harness",
|
|
3387
|
+
"/.harness/",
|
|
3388
|
+
".harness/**",
|
|
3389
|
+
"/.harness/**"
|
|
3390
|
+
].some((line) => existing.has(line));
|
|
3391
|
+
if (harnessDirectoryIgnored) {
|
|
3392
|
+
return;
|
|
3393
|
+
}
|
|
3382
3394
|
const missing = CREDENTIALS_GITIGNORE_LINES.filter((line) => !existing.has(line));
|
|
3383
3395
|
if (missing.length === 0) {
|
|
3384
3396
|
return;
|
|
@@ -3392,11 +3404,21 @@ function resolvePushAuth(input) {
|
|
|
3392
3404
|
const localToken = input.local?.token?.trim();
|
|
3393
3405
|
const token = envToken && envToken.length > 0 ? envToken : localToken && localToken.length > 0 ? localToken : void 0;
|
|
3394
3406
|
const serverUrl = input.serverUrlFlag ?? input.local?.server_url ?? input.projectUrl ?? void 0;
|
|
3407
|
+
const missing = [];
|
|
3395
3408
|
if (serverUrl === void 0 || serverUrl === null || serverUrl.trim() === "") {
|
|
3396
|
-
|
|
3409
|
+
missing.push("url");
|
|
3397
3410
|
}
|
|
3398
3411
|
if (token === void 0) {
|
|
3399
|
-
|
|
3412
|
+
missing.push("token");
|
|
3413
|
+
}
|
|
3414
|
+
if (missing.length > 0) {
|
|
3415
|
+
return {
|
|
3416
|
+
code: missing.includes("url") ? "SERVER_URL_REQUIRED" : "TOKEN_INVALID",
|
|
3417
|
+
missing
|
|
3418
|
+
};
|
|
3419
|
+
}
|
|
3420
|
+
if (serverUrl === void 0 || token === void 0) {
|
|
3421
|
+
throw new Error("push auth resolution invariant failed");
|
|
3400
3422
|
}
|
|
3401
3423
|
return { serverUrl, token };
|
|
3402
3424
|
}
|
|
@@ -3734,9 +3756,6 @@ async function pushProject(options) {
|
|
|
3734
3756
|
if (options.dryRun) {
|
|
3735
3757
|
return { preview, proposalId: null, projectId: project.project.project_id };
|
|
3736
3758
|
}
|
|
3737
|
-
if (options.confirmProposal !== void 0 && !await options.confirmProposal(preview)) {
|
|
3738
|
-
return { preview, proposalId: null, projectId: project.project.project_id, cancelled: true };
|
|
3739
|
-
}
|
|
3740
3759
|
const localCredentials = await readLocalCredentials(root);
|
|
3741
3760
|
const auth = resolvePushAuth({
|
|
3742
3761
|
...options.serverUrl === void 0 ? {} : { serverUrlFlag: options.serverUrl },
|
|
@@ -3748,10 +3767,10 @@ async function pushProject(options) {
|
|
|
3748
3767
|
});
|
|
3749
3768
|
if ("code" in auth) {
|
|
3750
3769
|
if (auth.code === "SERVER_URL_REQUIRED") {
|
|
3751
|
-
throw new PushWorkflowError("server_url is required; use --server-url, project.yaml server.url, or " + CREDENTIALS_HINT, 3, "SERVER_URL_REQUIRED");
|
|
3770
|
+
throw new PushWorkflowError("server_url is required; use --server-url, project.yaml server.url, or " + CREDENTIALS_HINT, 3, "SERVER_URL_REQUIRED", { missing_credentials: auth.missing });
|
|
3752
3771
|
}
|
|
3753
3772
|
const tokenEnv2 = options.tokenEnv ?? project.server.token_env;
|
|
3754
|
-
throw new PushWorkflowError("API token is unset; set " + tokenEnv2 + " or " + CREDENTIALS_HINT, 8, "TOKEN_INVALID");
|
|
3773
|
+
throw new PushWorkflowError("API token is unset; set " + tokenEnv2 + " or " + CREDENTIALS_HINT, 8, "TOKEN_INVALID", { missing_credentials: auth.missing });
|
|
3755
3774
|
}
|
|
3756
3775
|
const serverUrl = auth.serverUrl;
|
|
3757
3776
|
const token = auth.token;
|
|
@@ -3768,6 +3787,9 @@ async function pushProject(options) {
|
|
|
3768
3787
|
if (parsedServerUrl.protocol !== "https:") {
|
|
3769
3788
|
throw new PushWorkflowError("server_url must use HTTPS", 3, "SERVER_URL_INVALID");
|
|
3770
3789
|
}
|
|
3790
|
+
if (options.confirmProposal !== void 0 && !await options.confirmProposal(preview)) {
|
|
3791
|
+
return { preview, proposalId: null, projectId: project.project.project_id, cancelled: true };
|
|
3792
|
+
}
|
|
3771
3793
|
const workflowPath = join10(root, ".harness", "state", "local", "push-workflow.json");
|
|
3772
3794
|
const priorWorkflow = await readOptionalJson(workflowPath);
|
|
3773
3795
|
const provisionalRequestId = priorWorkflow?.local_project_key === project.project.local_project_key ? priorWorkflow.request_id : uuidV7();
|
|
@@ -5089,7 +5111,9 @@ function errorPayload(error) {
|
|
|
5089
5111
|
}
|
|
5090
5112
|
async function promptForCredentials(dependencies, missing) {
|
|
5091
5113
|
const serverUrl = missing === "token" ? void 0 : (await dependencies.prompt("\u670D\u52A1\u7AEF URL (https://...): ")).trim();
|
|
5092
|
-
const token = missing === "url" ? void 0 : (await dependencies.
|
|
5114
|
+
const token = missing === "url" ? void 0 : (await (dependencies.promptSecret ?? dependencies.prompt)(
|
|
5115
|
+
"API Token\uFF08\u8F93\u5165\u5C06\u9690\u85CF\uFF09: "
|
|
5116
|
+
)).trim();
|
|
5093
5117
|
if ((missing === "url" || missing === "both") && (serverUrl === void 0 || serverUrl === "")) {
|
|
5094
5118
|
return null;
|
|
5095
5119
|
}
|
|
@@ -5198,7 +5222,8 @@ async function runPush(options, dependencies) {
|
|
|
5198
5222
|
return 0;
|
|
5199
5223
|
} catch (error) {
|
|
5200
5224
|
if (attempt === 0 && options.nonInteractive !== true && options.dryRun !== true && error instanceof PushWorkflowError && (error.code === "SERVER_URL_REQUIRED" || error.code === "TOKEN_INVALID")) {
|
|
5201
|
-
const
|
|
5225
|
+
const missingCredentials = error.details?.missing_credentials;
|
|
5226
|
+
const missing = missingCredentials?.includes("url") === true && missingCredentials.includes("token") ? "both" : missingCredentials?.includes("url") === true || error.code === "SERVER_URL_REQUIRED" ? "url" : "token";
|
|
5202
5227
|
dependencies.stderr(
|
|
5203
5228
|
error.message + "\n\u53EF\u5728\u4E0B\u65B9\u5F55\u5165\u5E76\u5199\u5165 .harness/credentials.local.yaml\u3002\n"
|
|
5204
5229
|
);
|
|
@@ -5668,6 +5693,33 @@ async function readWorkflowFamilyManifest(resourcesRoot) {
|
|
|
5668
5693
|
}
|
|
5669
5694
|
|
|
5670
5695
|
// src/bin.ts
|
|
5696
|
+
async function promptSecret(question, input = process.stdin, output = process.stdout) {
|
|
5697
|
+
if (input.isTTY !== true || output.isTTY !== true) {
|
|
5698
|
+
const terminal2 = createInterface({ input, output });
|
|
5699
|
+
try {
|
|
5700
|
+
return await terminal2.question(question);
|
|
5701
|
+
} finally {
|
|
5702
|
+
terminal2.close();
|
|
5703
|
+
}
|
|
5704
|
+
}
|
|
5705
|
+
output.write(question);
|
|
5706
|
+
const mutedOutput = new Writable({
|
|
5707
|
+
write(_chunk, _encoding, callback) {
|
|
5708
|
+
callback();
|
|
5709
|
+
}
|
|
5710
|
+
});
|
|
5711
|
+
const terminal = createInterface({
|
|
5712
|
+
input,
|
|
5713
|
+
output: mutedOutput,
|
|
5714
|
+
terminal: true
|
|
5715
|
+
});
|
|
5716
|
+
try {
|
|
5717
|
+
return await terminal.question("");
|
|
5718
|
+
} finally {
|
|
5719
|
+
terminal.close();
|
|
5720
|
+
output.write("\n");
|
|
5721
|
+
}
|
|
5722
|
+
}
|
|
5671
5723
|
function defaultDependencies(overrides) {
|
|
5672
5724
|
return {
|
|
5673
5725
|
cwd: overrides.cwd ?? process.cwd(),
|
|
@@ -5682,6 +5734,7 @@ function defaultDependencies(overrides) {
|
|
|
5682
5734
|
terminal.close();
|
|
5683
5735
|
}
|
|
5684
5736
|
}),
|
|
5737
|
+
promptSecret: overrides.promptSecret ?? overrides.prompt ?? promptSecret,
|
|
5685
5738
|
fetch: overrides.fetch ?? globalThis.fetch,
|
|
5686
5739
|
env: overrides.env ?? process.env
|
|
5687
5740
|
};
|
|
@@ -5765,5 +5818,6 @@ if (isDirectCliEntrypoint()) {
|
|
|
5765
5818
|
}
|
|
5766
5819
|
export {
|
|
5767
5820
|
isDirectCliEntrypoint,
|
|
5821
|
+
promptSecret,
|
|
5768
5822
|
runCli
|
|
5769
5823
|
};
|