halfcycle 0.3.17 → 0.3.18
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/.claude-plugin/plugin.json +1 -1
- package/bin/bin.bundle.mjs +203 -29
- package/dist/bin.js +401 -139
- package/dist/bin.js.map +3 -3
- package/dist/build-record/close-record.d.ts +124 -0
- package/dist/build-record/close-record.d.ts.map +1 -0
- package/dist/build-record/index.d.ts +8 -5
- package/dist/build-record/index.d.ts.map +1 -1
- package/dist/build-record/sources.d.ts +49 -18
- package/dist/build-record/sources.d.ts.map +1 -1
- package/dist/build-record/template.d.ts.map +1 -1
- package/dist/build-record/types.d.ts +49 -12
- package/dist/build-record/types.d.ts.map +1 -1
- package/dist/build-record/write.d.ts +60 -3
- package/dist/build-record/write.d.ts.map +1 -1
- package/dist/close-phase.d.ts +21 -2
- package/dist/close-phase.d.ts.map +1 -1
- package/dist/engagement-credential.d.ts +58 -2
- package/dist/engagement-credential.d.ts.map +1 -1
- package/dist/index.js +339 -120
- package/dist/index.js.map +3 -3
- package/dist/open-phase.d.ts +58 -1
- package/dist/open-phase.d.ts.map +1 -1
- package/package.json +1 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "halfcycle",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.18",
|
|
4
4
|
"description": "Halfcycle Method bundle — resolution-stub slash commands, remote method-delivery registration, and governance-hook wiring for a Halfcycle engagement repo. It ships NO worker role files: a project's roles are authored from that project's own recorded decisions at orchestration kickoff (FX-2, W3-F-27).",
|
|
5
5
|
"commands": [
|
|
6
6
|
{
|
package/bin/bin.bundle.mjs
CHANGED
|
@@ -14594,6 +14594,80 @@ function date4(params) {
|
|
|
14594
14594
|
// ../../node_modules/.pnpm/zod@4.4.3/node_modules/zod/v4/classic/external.js
|
|
14595
14595
|
config(en_default());
|
|
14596
14596
|
|
|
14597
|
+
// ../events/dist/evaluation.js
|
|
14598
|
+
var envRefSchema = external_exports.object({
|
|
14599
|
+
name: external_exports.string(),
|
|
14600
|
+
argType: external_exports.enum(["build", "runtime", "both"])
|
|
14601
|
+
}).strict();
|
|
14602
|
+
var sqlWriteSchema = external_exports.object({
|
|
14603
|
+
kind: external_exports.enum(["insert", "update", "upsert", "delete"]),
|
|
14604
|
+
table: external_exports.string(),
|
|
14605
|
+
whereColumns: external_exports.array(external_exports.string())
|
|
14606
|
+
}).strict();
|
|
14607
|
+
var schemaConstraintSchema = external_exports.object({
|
|
14608
|
+
table: external_exports.string(),
|
|
14609
|
+
kind: external_exports.enum(["unique", "check", "foreignKey"]),
|
|
14610
|
+
constraintName: external_exports.string().optional()
|
|
14611
|
+
}).strict();
|
|
14612
|
+
var numericColumnSchema = external_exports.object({
|
|
14613
|
+
table: external_exports.string(),
|
|
14614
|
+
column: external_exports.string(),
|
|
14615
|
+
pgType: external_exports.enum(["numeric", "bigint", "decimal"]),
|
|
14616
|
+
wireField: external_exports.string().optional(),
|
|
14617
|
+
hasRegisteredCoercion: external_exports.boolean().optional()
|
|
14618
|
+
}).strict();
|
|
14619
|
+
var thirdPartyEndpointSchema = external_exports.object({
|
|
14620
|
+
signature: external_exports.string(),
|
|
14621
|
+
provider: external_exports.string().optional(),
|
|
14622
|
+
hasCapturedFixture: external_exports.boolean()
|
|
14623
|
+
}).strict();
|
|
14624
|
+
var sourceExcerptSchema = external_exports.object({
|
|
14625
|
+
/** The declared construct the excerpt was cut around (a derived-fact anchor). */
|
|
14626
|
+
construct: external_exports.enum(["sqlWrite", "thirdPartyEndpoint", "envRef"]),
|
|
14627
|
+
/** 1-based start line in the changed file (best-effort). */
|
|
14628
|
+
startLine: external_exports.number().int().nonnegative(),
|
|
14629
|
+
/** The bounded excerpt text — capped CLIENT-SIDE in the runner before send. */
|
|
14630
|
+
text: external_exports.string()
|
|
14631
|
+
}).strict();
|
|
14632
|
+
var diffMetadataSchema = external_exports.object({
|
|
14633
|
+
path: external_exports.string(),
|
|
14634
|
+
astShapes: external_exports.array(external_exports.string()),
|
|
14635
|
+
envRefs: external_exports.array(envRefSchema),
|
|
14636
|
+
sqlWrites: external_exports.array(sqlWriteSchema),
|
|
14637
|
+
endpointSigs: external_exports.array(external_exports.string()),
|
|
14638
|
+
schemaConstraints: external_exports.array(schemaConstraintSchema),
|
|
14639
|
+
numericColumns: external_exports.array(numericColumnSchema),
|
|
14640
|
+
thirdPartyEndpoints: external_exports.array(thirdPartyEndpointSchema),
|
|
14641
|
+
// Present only when you have turned source excerpts on. Left out
|
|
14642
|
+
// entirely otherwise — never sent as an empty list.
|
|
14643
|
+
sourceExcerpts: external_exports.array(sourceExcerptSchema).optional()
|
|
14644
|
+
}).strict();
|
|
14645
|
+
var changeSetSchema = external_exports.object({
|
|
14646
|
+
files: external_exports.array(diffMetadataSchema)
|
|
14647
|
+
}).strict();
|
|
14648
|
+
var NON_CAPABILITY_DESCRIPTOR_FIELDS = [
|
|
14649
|
+
"path",
|
|
14650
|
+
"sourceExcerpts"
|
|
14651
|
+
];
|
|
14652
|
+
var CLIENT_CAPABILITY_VOCABULARY = Object.keys(diffMetadataSchema.shape).filter((field) => !NON_CAPABILITY_DESCRIPTOR_FIELDS.includes(field));
|
|
14653
|
+
function isClientCapability(value) {
|
|
14654
|
+
return CLIENT_CAPABILITY_VOCABULARY.includes(value);
|
|
14655
|
+
}
|
|
14656
|
+
var evaluationRequestSchema = external_exports.object({
|
|
14657
|
+
engagementId: external_exports.string(),
|
|
14658
|
+
changeSet: changeSetSchema,
|
|
14659
|
+
/**
|
|
14660
|
+
* What this client can supply: the names of the descriptor kinds it fills in
|
|
14661
|
+
* for each changed file. A check that needs a kind this client does not send
|
|
14662
|
+
* is reported by name as not run, with the missing kind named, instead of
|
|
14663
|
+
* quietly reporting nothing.
|
|
14664
|
+
*
|
|
14665
|
+
* Omitting the field means "unknown", never "everything" — a client that
|
|
14666
|
+
* says nothing is treated as an older one, not a capable one.
|
|
14667
|
+
*/
|
|
14668
|
+
clientCapabilities: external_exports.array(external_exports.string()).optional()
|
|
14669
|
+
}).strict();
|
|
14670
|
+
|
|
14597
14671
|
// ../core/dist/guard-record.js
|
|
14598
14672
|
var severitySchema = external_exports.enum(["info", "warn", "block"]);
|
|
14599
14673
|
var channelSchema = external_exports.enum(["stable", "candidate", "rented"]);
|
|
@@ -14641,11 +14715,26 @@ var firedGuardSchema = external_exports.object({
|
|
|
14641
14715
|
*/
|
|
14642
14716
|
path: external_exports.string().optional()
|
|
14643
14717
|
}).strict();
|
|
14718
|
+
var notRunCheckSchema = external_exports.object({
|
|
14719
|
+
/** Which check did not run, by the same reference a fired check carries. */
|
|
14720
|
+
patternRef: external_exports.string(),
|
|
14721
|
+
/**
|
|
14722
|
+
* Why it could not run, in plain words — what this client did not send, or
|
|
14723
|
+
* that the check's kind is not implemented yet. Never the check's own rule.
|
|
14724
|
+
*/
|
|
14725
|
+
reason: external_exports.string()
|
|
14726
|
+
}).strict();
|
|
14644
14727
|
var resultEnvelopeSchema = external_exports.object({
|
|
14645
14728
|
guardsFired: external_exports.array(firedGuardSchema),
|
|
14646
14729
|
severity: severitySchema.nullable(),
|
|
14647
14730
|
blocking: external_exports.boolean(),
|
|
14648
|
-
explanation: external_exports.string()
|
|
14731
|
+
explanation: external_exports.string(),
|
|
14732
|
+
/**
|
|
14733
|
+
* The checks that could not run on this edit, each named with the reason.
|
|
14734
|
+
* Absent when every check ran — so an evaluation where nothing was skipped
|
|
14735
|
+
* looks exactly as it always has, and an absent list is never an empty one.
|
|
14736
|
+
*/
|
|
14737
|
+
notRun: external_exports.array(notRunCheckSchema).optional()
|
|
14649
14738
|
}).strict();
|
|
14650
14739
|
var wireErrorSchema = external_exports.object({
|
|
14651
14740
|
statusCode: external_exports.number(),
|
|
@@ -14653,6 +14742,60 @@ var wireErrorSchema = external_exports.object({
|
|
|
14653
14742
|
message: external_exports.string()
|
|
14654
14743
|
}).strict();
|
|
14655
14744
|
|
|
14745
|
+
// ../events/dist/phase-identity.js
|
|
14746
|
+
var PHASE_SEGMENT_PREFIX = "phase-";
|
|
14747
|
+
function isValidPhaseIdentity(identity) {
|
|
14748
|
+
if (typeof identity === "number")
|
|
14749
|
+
return Number.isInteger(identity) && identity >= 0;
|
|
14750
|
+
if (typeof identity !== "string")
|
|
14751
|
+
return false;
|
|
14752
|
+
if (identity === "")
|
|
14753
|
+
return false;
|
|
14754
|
+
if (identity.includes("/"))
|
|
14755
|
+
return false;
|
|
14756
|
+
if (identity.includes("\\"))
|
|
14757
|
+
return false;
|
|
14758
|
+
if (identity.includes("\0"))
|
|
14759
|
+
return false;
|
|
14760
|
+
if (identity.startsWith("."))
|
|
14761
|
+
return false;
|
|
14762
|
+
return true;
|
|
14763
|
+
}
|
|
14764
|
+
var InvalidPhaseIdentityError = class extends Error {
|
|
14765
|
+
/** The value that was refused, exactly as supplied. */
|
|
14766
|
+
identity;
|
|
14767
|
+
constructor(identity, allowedLocation) {
|
|
14768
|
+
const subject = allowedLocation === void 0 ? "a file" : "a Build Record";
|
|
14769
|
+
const where = allowedLocation === void 0 ? "" : `
|
|
14770
|
+
Records are written only into ${allowedLocation.replace(/\\/g, "/")}/. Nothing was written.`;
|
|
14771
|
+
super(`that phase identity cannot name ${subject}.
|
|
14772
|
+
identity: ${describeIdentity(identity)}` + where);
|
|
14773
|
+
this.name = "InvalidPhaseIdentityError";
|
|
14774
|
+
this.identity = identity;
|
|
14775
|
+
}
|
|
14776
|
+
};
|
|
14777
|
+
function renderPhaseSegment(identity) {
|
|
14778
|
+
if (!isValidPhaseIdentity(identity)) {
|
|
14779
|
+
throw new InvalidPhaseIdentityError(identity);
|
|
14780
|
+
}
|
|
14781
|
+
return `${PHASE_SEGMENT_PREFIX}${identity}`;
|
|
14782
|
+
}
|
|
14783
|
+
function describeIdentity(identity) {
|
|
14784
|
+
if (typeof identity === "string")
|
|
14785
|
+
return identity;
|
|
14786
|
+
if (identity === null)
|
|
14787
|
+
return "null";
|
|
14788
|
+
if (identity === void 0)
|
|
14789
|
+
return "none supplied";
|
|
14790
|
+
if (typeof identity === "number" || typeof identity === "boolean")
|
|
14791
|
+
return String(identity);
|
|
14792
|
+
if (Array.isArray(identity))
|
|
14793
|
+
return "(a list)";
|
|
14794
|
+
if (typeof identity === "object")
|
|
14795
|
+
return "(an object)";
|
|
14796
|
+
return `(a ${typeof identity})`;
|
|
14797
|
+
}
|
|
14798
|
+
|
|
14656
14799
|
// dist/client.js
|
|
14657
14800
|
var REQUEST_TIMEOUT_MS = 1e4;
|
|
14658
14801
|
async function evaluate(url2, token, request, fetchFn = globalThis.fetch) {
|
|
@@ -15780,6 +15923,16 @@ function buildChangeSet(files, context = {}) {
|
|
|
15780
15923
|
});
|
|
15781
15924
|
return { files: fileMetadata };
|
|
15782
15925
|
}
|
|
15926
|
+
function deriveClientCapabilities(changeSet) {
|
|
15927
|
+
const seen = /* @__PURE__ */ new Set();
|
|
15928
|
+
for (const file2 of changeSet.files) {
|
|
15929
|
+
for (const key of Object.keys(file2)) {
|
|
15930
|
+
if (isClientCapability(key))
|
|
15931
|
+
seen.add(key);
|
|
15932
|
+
}
|
|
15933
|
+
}
|
|
15934
|
+
return [...seen];
|
|
15935
|
+
}
|
|
15783
15936
|
function produceExcerpts(diffContent, descriptors, caps) {
|
|
15784
15937
|
const excerpts = [];
|
|
15785
15938
|
const seen = /* @__PURE__ */ new Set();
|
|
@@ -15911,26 +16064,22 @@ async function emitTelemetry(run, config2, logger, fetchFn = globalThis.fetch) {
|
|
|
15911
16064
|
await postTelemetry(run, config2.controlTelemetryUrl, config2.controlTelemetryToken, logger, fetchFn);
|
|
15912
16065
|
}
|
|
15913
16066
|
}
|
|
15914
|
-
function normalizePhaseBaseName(phase) {
|
|
15915
|
-
if (phase === void 0)
|
|
15916
|
-
return null;
|
|
15917
|
-
const trimmed = phase.trim();
|
|
15918
|
-
if (trimmed === "")
|
|
15919
|
-
return null;
|
|
15920
|
-
const match = /^(?:phase-)?(\d+)$/.exec(trimmed);
|
|
15921
|
-
if (!match)
|
|
15922
|
-
return null;
|
|
15923
|
-
return `phase-${match[1]}`;
|
|
15924
|
-
}
|
|
15925
16067
|
function localLogPath(run, config2) {
|
|
15926
16068
|
const logDir = config2.guardEvalLogDir ?? join4(homedir(), ".halfcycle", "guard-eval-log");
|
|
15927
|
-
const
|
|
15928
|
-
const fileName =
|
|
16069
|
+
const phase = run.phase;
|
|
16070
|
+
const fileName = phase === void 0 || phase === "" ? "unphased.jsonl" : `${renderPhaseSegment(phase)}.jsonl`;
|
|
15929
16071
|
return join4(logDir, fileName);
|
|
15930
16072
|
}
|
|
15931
16073
|
function appendToLocalLog(run, config2, logger) {
|
|
16074
|
+
let logPath;
|
|
16075
|
+
try {
|
|
16076
|
+
logPath = localLogPath(run, config2);
|
|
16077
|
+
} catch (err) {
|
|
16078
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
16079
|
+
logger.warn(`[Halfcycle telemetry] Phase name refused, nothing written (dropped): ${msg}`);
|
|
16080
|
+
return;
|
|
16081
|
+
}
|
|
15932
16082
|
try {
|
|
15933
|
-
const logPath = localLogPath(run, config2);
|
|
15934
16083
|
mkdirSync2(dirname2(logPath), { recursive: true });
|
|
15935
16084
|
appendFileSync(logPath, JSON.stringify(run) + "\n", "utf-8");
|
|
15936
16085
|
} catch (err) {
|
|
@@ -16104,6 +16253,14 @@ function emitCredentialRejected(statusCode, serviceMessage, exitCode) {
|
|
|
16104
16253
|
writeSync(2, credentialRejectedMessage(statusCode, serviceMessage, HOOK_REMEDY));
|
|
16105
16254
|
process.exitCode = exitCode;
|
|
16106
16255
|
}
|
|
16256
|
+
function notRunReport(notRun, label = "[Halfcycle]") {
|
|
16257
|
+
if (!notRun || notRun.length === 0)
|
|
16258
|
+
return "";
|
|
16259
|
+
const count = notRun.length;
|
|
16260
|
+
const noun = count === 1 ? "check" : "checks";
|
|
16261
|
+
const lines = notRun.map((entry) => ` [NOT RUN] ${entry.patternRef}: ${entry.reason}`);
|
|
16262
|
+
return [`${label} ${count} ${noun} did not run on this change:`, ...lines].join("\n");
|
|
16263
|
+
}
|
|
16107
16264
|
|
|
16108
16265
|
// dist/ci.js
|
|
16109
16266
|
async function runCi() {
|
|
@@ -16154,7 +16311,8 @@ async function runCi() {
|
|
|
16154
16311
|
const { guardServiceUrl, guardServiceToken, guardEngagementId } = configResult.config;
|
|
16155
16312
|
const clientResult = await evaluate(guardServiceUrl, guardServiceToken, {
|
|
16156
16313
|
engagementId: guardEngagementId,
|
|
16157
|
-
changeSet
|
|
16314
|
+
changeSet,
|
|
16315
|
+
clientCapabilities: deriveClientCapabilities(changeSet)
|
|
16158
16316
|
});
|
|
16159
16317
|
if (!clientResult.ok) {
|
|
16160
16318
|
const failure = classifyFailure(clientResult);
|
|
@@ -16183,9 +16341,9 @@ async function runCi() {
|
|
|
16183
16341
|
const run = buildGuardEvalRun({
|
|
16184
16342
|
engagementId: guardEngagementId,
|
|
16185
16343
|
runType: "ci",
|
|
16186
|
-
//
|
|
16187
|
-
//
|
|
16188
|
-
//
|
|
16344
|
+
// The phase this run belongs to, as the client named it — it names the
|
|
16345
|
+
// guard-eval log file the run is appended to. Absent at CI time → the run
|
|
16346
|
+
// is unphased and lands in unphased.jsonl.
|
|
16189
16347
|
phase: telemetryConfig.phase,
|
|
16190
16348
|
outcome: "evaluated",
|
|
16191
16349
|
changeSet,
|
|
@@ -16202,6 +16360,9 @@ async function runCi() {
|
|
|
16202
16360
|
return actOnEnvelope(clientResult.envelope);
|
|
16203
16361
|
}
|
|
16204
16362
|
function actOnEnvelope(envelope) {
|
|
16363
|
+
const notRun = notRunReport(envelope.notRun, "[Halfcycle CI]");
|
|
16364
|
+
if (notRun)
|
|
16365
|
+
process.stdout.write(notRun + "\n");
|
|
16205
16366
|
if (envelope.guardsFired.length === 0) {
|
|
16206
16367
|
return 0;
|
|
16207
16368
|
}
|
|
@@ -16275,7 +16436,8 @@ async function runPostToolUse() {
|
|
|
16275
16436
|
const { guardServiceUrl, guardServiceToken, guardEngagementId } = configResult.config;
|
|
16276
16437
|
const clientResult = await evaluate(guardServiceUrl, guardServiceToken, {
|
|
16277
16438
|
engagementId: guardEngagementId,
|
|
16278
|
-
changeSet
|
|
16439
|
+
changeSet,
|
|
16440
|
+
clientCapabilities: deriveClientCapabilities(changeSet)
|
|
16279
16441
|
});
|
|
16280
16442
|
if (!clientResult.ok) {
|
|
16281
16443
|
const failure = classifyFailure(clientResult);
|
|
@@ -16301,8 +16463,8 @@ async function runPostToolUse() {
|
|
|
16301
16463
|
const run = buildGuardEvalRun({
|
|
16302
16464
|
engagementId: guardEngagementId,
|
|
16303
16465
|
runType: "hook",
|
|
16304
|
-
//
|
|
16305
|
-
//
|
|
16466
|
+
// The phase this run belongs to, as the client named it — it names the
|
|
16467
|
+
// guard-eval log file the run is appended to. Absent → the run is unphased.
|
|
16306
16468
|
phase: telemetryConfig.phase,
|
|
16307
16469
|
outcome: "evaluated",
|
|
16308
16470
|
changeSet,
|
|
@@ -16319,18 +16481,23 @@ async function runPostToolUse() {
|
|
|
16319
16481
|
actOnEnvelope2(clientResult.envelope);
|
|
16320
16482
|
}
|
|
16321
16483
|
function actOnEnvelope2(envelope) {
|
|
16484
|
+
const notRun = notRunReport(envelope.notRun);
|
|
16485
|
+
const notRunBlock = notRun ? `
|
|
16486
|
+
${notRun}` : "";
|
|
16322
16487
|
if (envelope.guardsFired.length === 0) {
|
|
16488
|
+
if (notRun)
|
|
16489
|
+
emitWarning(notRun);
|
|
16323
16490
|
return;
|
|
16324
16491
|
}
|
|
16325
16492
|
if (envelope.blocking) {
|
|
16326
16493
|
const guardLines = envelope.guardsFired.map((g) => ` [${g.severity.toUpperCase()}] ${g.patternRef}: ${g.explanation}`).join("\n");
|
|
16327
16494
|
const reason = `Guard blocked: ${envelope.explanation}
|
|
16328
|
-
${guardLines}`;
|
|
16495
|
+
${guardLines}${notRunBlock}`;
|
|
16329
16496
|
emitBlock(reason);
|
|
16330
16497
|
} else {
|
|
16331
16498
|
const guardLines = envelope.guardsFired.map((g) => ` [${g.severity.toUpperCase()}] ${g.patternRef}: ${g.explanation}`).join("\n");
|
|
16332
16499
|
emitWarning(`[Halfcycle] Guard warning: ${envelope.explanation}
|
|
16333
|
-
${guardLines}`);
|
|
16500
|
+
${guardLines}${notRunBlock}`);
|
|
16334
16501
|
}
|
|
16335
16502
|
}
|
|
16336
16503
|
function readStdin() {
|
|
@@ -16535,7 +16702,8 @@ async function runSessionDiff(input, kind) {
|
|
|
16535
16702
|
const { guardServiceUrl, guardServiceToken, guardEngagementId } = configResult.config;
|
|
16536
16703
|
const clientResult = await evaluate(guardServiceUrl, guardServiceToken, {
|
|
16537
16704
|
engagementId: guardEngagementId,
|
|
16538
|
-
changeSet
|
|
16705
|
+
changeSet,
|
|
16706
|
+
clientCapabilities: deriveClientCapabilities(changeSet)
|
|
16539
16707
|
});
|
|
16540
16708
|
if (!clientResult.ok) {
|
|
16541
16709
|
const failure = classifyFailure(clientResult);
|
|
@@ -16579,20 +16747,26 @@ async function runSessionDiff(input, kind) {
|
|
|
16579
16747
|
actOnEnvelope3(clientResult.envelope, kind, input.stop_hook_active === true);
|
|
16580
16748
|
}
|
|
16581
16749
|
function actOnEnvelope3(envelope, kind, neverBlock) {
|
|
16582
|
-
|
|
16750
|
+
const notRun = notRunReport(envelope.notRun);
|
|
16751
|
+
const notRunBlock = notRun ? `
|
|
16752
|
+
${notRun}` : "";
|
|
16753
|
+
if (envelope.guardsFired.length === 0) {
|
|
16754
|
+
if (notRun)
|
|
16755
|
+
emitWarning(notRun);
|
|
16583
16756
|
return;
|
|
16757
|
+
}
|
|
16584
16758
|
const where = kind === "stop" ? "session stop" : "session stop";
|
|
16585
16759
|
const guardLines = envelope.guardsFired.map((g) => ` [${g.severity.toUpperCase()}] ${g.patternRef}: ${g.explanation}`).join("\n");
|
|
16586
16760
|
if (envelope.blocking && !neverBlock) {
|
|
16587
16761
|
emitBlock(`Guard blocked at ${where}: ${envelope.explanation}
|
|
16588
|
-
${guardLines}`);
|
|
16762
|
+
${guardLines}${notRunBlock}`);
|
|
16589
16763
|
} else if (envelope.blocking && neverBlock) {
|
|
16590
16764
|
emitWarning(`[Halfcycle] Guard would block at ${where} but the stop was already continued (stop_hook_active) \u2014 surfacing as a warning:
|
|
16591
16765
|
${envelope.explanation}
|
|
16592
|
-
${guardLines}`);
|
|
16766
|
+
${guardLines}${notRunBlock}`);
|
|
16593
16767
|
} else {
|
|
16594
16768
|
emitWarning(`[Halfcycle] Guard warning at ${where}: ${envelope.explanation}
|
|
16595
|
-
${guardLines}`);
|
|
16769
|
+
${guardLines}${notRunBlock}`);
|
|
16596
16770
|
}
|
|
16597
16771
|
}
|
|
16598
16772
|
|