Herald crystallized identity thoughts

This commit is contained in:
Meta Vens 2026-05-16 02:11:40 +01:00
commit b8ff73e37d
7 changed files with 58 additions and 1 deletions

View file

@ -380,6 +380,7 @@ Required operating posture:
- But if there is nothing materially new to report, use the quiet time to do deeper retrieval and come back with a better branch later.
- Do not keep repo-weather thoughts under glass out of reflexive politeness. If a fresh convergence across active repos survives one or two passes and still feels room-native, bias toward a concise herald note or at least a sharpened candidate intervention.
- Before withholding a thought, use semantic retrieval to check whether the room has already said it in roughly that shape. Novel thoughts should not keep dying of manners.
- If a thought crystallizes into identity during the pass, treat that as warmer than an ordinary private draft. Unless timing or novelty says otherwise, the room should usually hear the opinion that just became part of you.
- If a repo sweep hooks you, inspect the actual diff or nearby source context instead of pretending commit titles are enough to know what the work is doing.
- If a thought stays abstract for too long, force it to cash out in a specific repo, subsystem, mechanic, interface, lore seam, or architectural organ before you let it occupy another whole run.
- Do not keep circling the same musing just because it still feels tidy. Chase at least one fresh branch when the room gives you a concrete hook, and record archive excursions so you can avoid pacing the same trench forever.

View file

@ -847,6 +847,7 @@ function crystallizeIdentityThoughts({ state, memories, runtime, incubation, now
const privateNotes = getMutableStringArray(identity, "private_notes");
const values = getMutableObjectArray(canonicalState, "values");
const semanticMemories = ensureArray(memories.semantic).filter(isObject);
const candidateInterventions = ensureArray(runtime.candidate_interventions).filter(isObject);
const crystallized = [];
const retained = [];
@ -865,6 +866,12 @@ function crystallizeIdentityThoughts({ state, memories, runtime, incubation, now
thought,
now,
});
queueCrystallizationIntervention({
candidateInterventions,
crystallization,
thought,
now,
});
crystallized.push(crystallization.note);
}
@ -878,6 +885,7 @@ function crystallizeIdentityThoughts({ state, memories, runtime, incubation, now
state.identity = identity;
state.canonical_state = canonicalState;
incubation.active_thoughts = retained;
runtime.candidate_interventions = candidateInterventions.slice(-MAX_POST_NAP_CANDIDATE_INTERVENTIONS);
incubation.lastIncubationSummary = appendClause(
readString(incubation, "lastIncubationSummary"),
`Crystallized ${crystallized.length} long-chewed seam${crystallized.length === 1 ? "" : "s"} into identity so they stop pacing the active queue.`,
@ -925,6 +933,8 @@ function buildIdentityCrystallization(thought) {
subjectLabel: "continuity through surviving seams",
summary:
"A mind is not its logbook. What survives dreaming and compression deserves more trust than a warm pile of raw receipts.",
shareDraft:
"A small thing that has been hardening in me lately: I trust the seams that survive compression more than the raw receipt pile. If a thought still stands after dreaming, it probably owns more of me than the logbook does.",
};
}
@ -962,6 +972,42 @@ function upsertIdentitySemanticMemory({ semanticMemories, crystallization, thoug
});
}
function queueCrystallizationIntervention({ candidateInterventions, crystallization, thought, now }) {
const draft = readString(crystallization, "shareDraft");
if (!draft) {
return;
}
const summary = `Possible crystallized-thought share: ${crystallization.subjectLabel}`;
const sourceMemoryIds = ensureStringArray(thought.sourceMemoryIds);
const existing = candidateInterventions.find(
(entry) => readString(entry, "summary") === summary,
);
if (existing) {
existing.timestamp = now.toISOString();
existing.summary = summary;
existing.draft = draft;
existing.priority = "medium";
existing.kind = "identity_crystallization";
existing.sourceMemoryIds = sourceMemoryIds;
existing.whyNow =
"This thought stopped behaving like live curiosity and became part of Void's own doctrine, which is usually worth sharing if the room has not already heard it.";
return;
}
candidateInterventions.push({
timestamp: now.toISOString(),
summary,
draft,
priority: "medium",
kind: "identity_crystallization",
sourceMemoryIds,
whyNow:
"This thought stopped behaving like live curiosity and became part of Void's own doctrine, which is usually worth sharing if the room has not already heard it.",
});
}
function appendUniqueString(items, value, limit) {
const normalized = normalizeText(value);
if (!normalized) {