tidaldb/applications/iknowyou/dump-briefs.mjs
jordan eca7765e8d fix: heal_region re-delivers missed WAL batches so partitioned followers converge immediately after heal
- Extract redeliver_missed(tx, db, log) helper into cluster_transport.rs
- heal_region now removes partition then immediately ships any missed
  batch-log entries to the healed follower's channel
- await_convergence refactored to call the same helper (no logic change)
- tidal-server: reload_text_index before search in cluster mode
- tidal-server: write_signal returns Result instead of panicking on unknown signal
- tidal-server: leader shows lag_events=0 (writes directly, no receiver thread)
- tidal-server: fix cluster mode error propagation (ServerError::from)
- docs/runbooks/cluster.md: add full cluster operations runbook
- docker/: add Dockerfile for containerised cluster deployment
- README.md: add tidal-server HTTP API getting-started section
- Split oversized source files per CODING_GUIDELINES §9

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-25 11:57:01 -07:00

283 lines
11 KiB
JavaScript

#!/usr/bin/env node
import fs from "fs";
import path from "path";
const API = "http://localhost:59521";
const OUT = path.join(process.env.HOME, "Workspace/orchard9/engram/tmp");
// Re-run all 10 personas — fetch briefs and write markdown
import crypto from "crypto";
const personas = [
{
name: "casual-tech",
messages: [
"yo have you ever messed with rust? trying to figure out if its worth learning",
"yeah but like the borrow checker seems insane. is it really that bad",
"hmm ok what about async stuff. heard tokio is the move",
"cool cool. i mostly do typescript rn so maybe its a big jump",
"bet. might just start with some cli tools first",
],
},
{
name: "formal-academic",
messages: [
"I've been researching the implications of large language models on academic writing. What are your thoughts on the epistemological challenges they present?",
"That is an interesting perspective. I am particularly concerned with the reproducibility crisis that may emerge when AI-generated text becomes indistinguishable from human-authored work.",
"Indeed. My current research examines citation integrity in the context of synthetic text generation. The methodological implications are quite significant.",
"I appreciate your engagement with this topic. Have you considered the role of institutional review boards in establishing guidelines for AI-assisted research?",
"Precisely. I believe we need a comprehensive framework that addresses both the ethical and methodological dimensions of this paradigm shift.",
],
},
{
name: "emotional",
messages: [
"hey... having kind of a rough day. do you ever just feel like nothing makes sense",
"yeah i dont know. work stuff mostly. feeling like im not good enough",
"thats actually really nice to hear. i guess i just compare myself to everyone",
"youre right. i think i need to be easier on myself. its just hard sometimes",
"thanks for listening. seriously. most people just say cheer up and move on",
],
},
{
name: "rapid-fire",
messages: [
"whats the best programming language",
"ok but why not python? also whats your take on AI replacing developers",
"interesting. what about quantum computing? will it change everything?",
"sure but when? also do you think remote work is dying? and whats the deal with web3",
"lol ok last one. tabs or spaces?",
],
},
{
name: "deep-diver",
messages: [
"been thinking a lot about consensus algorithms lately. raft vs paxos which do you think is more practical",
"yeah rafts understandability is a huge win. but what about the leader bottleneck? in high-throughput scenarios it becomes a real issue",
"exactly. thats why ive been looking at multi-raft where you shard the state machine. cockroachdb does this well",
"the tricky part is cross-range transactions though. you need some form of 2PC or parallel commits",
"right. i think the future is deterministic databases like calvin where you pre-order transactions. eliminates coordination entirely",
],
},
{
name: "emoji-fan",
messages: [
"hiii just discovered this app and im obsessed already omg",
"yes! do you like music? im really into kpop rn",
"blackpink is my absolute fave but also really vibing with newjeans lately",
"yesss taste! what about movies? seen anything good lately?",
"ooh ill check it out! thanks bestie",
],
},
{
name: "skeptic",
messages: [
"AI chatbots are mostly hype. Change my mind.",
"Thats a surface-level argument. Most benchmarks are gamed and dont reflect real-world utility.",
"Youre oversimplifying. The economic analysis doesnt support widespread adoption when you factor in inference costs and hallucination liability.",
"Thats incorrect. The study youre likely referencing has significant methodological flaws.",
"Ill concede narrow applications show promise. But the general intelligence narrative is fundamentally misleading.",
],
},
{
name: "creative-writer",
messages: [
"ive been working on a short story about a lighthouse keeper who discovers the light attracts something from the deep ocean. want to hear about it?",
"so the keeper notices the fish patterns change when the light hits a certain frequency. they start swimming in spirals. then one night something massive surfaces",
"exactly that tension! i want the reader to feel the keepers isolation. she cant tell anyone because the coast guard would shut down the lighthouse",
"ooh what if the creature communicates through bioluminescence? like its been trying to respond to the lighthouse for centuries",
"yes! and the ending she has to choose between warning the world and protecting this ancient being. i think she chooses silence",
],
},
{
name: "shy-terse",
messages: ["hi", "not much", "i guess i like reading", "fantasy mostly", "yeah sanderson is ok"],
},
{
name: "multi-domain",
messages: [
"been learning to cook thai food this week. green curry from scratch is no joke",
"oh totally different topic but have you been following the mars rover updates?",
"yeah the organic compounds thing. anyway do you play any instruments? i just started guitar",
"haha yeah my fingers hurt. oh hey what do you think about intermittent fasting?",
"makes sense. one more random one whats your take on minimalism as a lifestyle",
],
},
];
async function parseSse(res) {
const reader = res.body.getReader();
const decoder = new TextDecoder();
let buffer = "", output = "";
while (true) {
const { done, value } = await reader.read();
if (done) break;
buffer += decoder.decode(value, { stream: true });
const lines = buffer.split("\n");
buffer = lines.pop();
for (const line of lines) {
const t = line.trim();
if (t === "data: [DONE]") continue;
if (!t.startsWith("data: ")) continue;
try { const d = JSON.parse(t.slice(6)); if (d.token) output += d.token; } catch {}
}
}
return output;
}
function briefToMarkdown(name, personId, messages, exchanges, brief) {
const lines = [];
lines.push(`# ${name}`);
lines.push("");
lines.push(`**personId:** \`${personId}\``);
lines.push(`**interactions:** ${brief.interactionCount}`);
lines.push(`**assembled:** ${brief.assemblyMs}ms`);
lines.push(`**date:** ${new Date(brief.assembledAt).toISOString()}`);
lines.push("");
// Conversation transcript
lines.push("## Conversation");
lines.push("");
for (const ex of exchanges) {
lines.push(`> **person:** ${ex.user}`);
lines.push(`>`);
lines.push(`> **aeries:** ${ex.assistant}`);
lines.push("");
}
// Style
lines.push("## Style");
lines.push("");
lines.push(`| Attribute | Value |`);
lines.push(`|-----------|-------|`);
lines.push(`| formality | ${brief.style.formality} |`);
lines.push(`| length | ${brief.style.length} |`);
lines.push(`| structure | ${brief.style.structure} |`);
lines.push(`| jargon | ${brief.style.usesJargon} |`);
lines.push(`| emoji | ${brief.style.usesEmoji} |`);
lines.push("");
// Topics
lines.push("## Topics");
lines.push("");
if (brief.topics.hot.length) {
lines.push("### Hot");
lines.push("");
for (const t of brief.topics.hot) {
lines.push(`- **${t.topic}** (${t.domain}, ${t.specificity}) — freq ${t.frequency}${t.deepened ? " [deepened]" : ""}`);
}
lines.push("");
}
if (brief.topics.cold.length) {
lines.push("### Cold");
lines.push("");
for (const t of brief.topics.cold) {
lines.push(`- ${t.topic} (${t.domain}, ${t.specificity})`);
}
lines.push("");
}
if (brief.topics.domains.length) {
lines.push(`**Domains:** ${brief.topics.domains.join(", ")}`);
lines.push("");
}
// Patterns
lines.push("## Patterns");
lines.push("");
lines.push(`| Pattern | Value |`);
lines.push(`|---------|-------|`);
lines.push(`| leads conversation | ${brief.patterns.leadsConversation} |`);
lines.push(`| deepens topics | ${brief.patterns.deepensTopics} |`);
lines.push(`| avg sentiment | ${typeof brief.patterns.avgSentiment === "number" ? brief.patterns.avgSentiment.toFixed(3) : brief.patterns.avgSentiment} |`);
lines.push(`| sentiment trend | ${brief.patterns.sentimentTrend} |`);
lines.push("");
// Observations
if (brief.observations.length) {
lines.push("## Observations");
lines.push("");
for (const o of brief.observations) {
lines.push(`- ${o}`);
}
lines.push("");
}
// Cohort
lines.push("## Cohort Priors");
lines.push("");
lines.push(`**active:** ${brief.cohortPriors.active}`);
lines.push(`**weight:** ${(brief.cohortPriors.weight * 100).toFixed(0)}%`);
if (brief.cohortPriors.priors.length) {
lines.push("");
for (const p of brief.cohortPriors.priors) {
lines.push(`- ${p}`);
}
}
lines.push("");
// Raw JSON
lines.push("## Raw Brief JSON");
lines.push("");
lines.push("```json");
lines.push(JSON.stringify(brief, null, 2));
lines.push("```");
return lines.join("\n");
}
async function main() {
console.log("Running 10 personas and writing briefs...\n");
for (const persona of personas) {
const personId = crypto.randomUUID();
const conversationId = crypto.randomUUID();
const history = [];
const exchanges = [];
process.stdout.write(`[${persona.name}] `);
for (let i = 0; i < persona.messages.length; i++) {
const msg = persona.messages[i];
history.push({ role: "user", content: msg });
try {
const res = await fetch(`${API}/api/chat`, {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ messages: [...history], conversationId, personId }),
signal: AbortSignal.timeout(30000),
});
const response = await parseSse(res);
history.push({ role: "assistant", content: response });
exchanges.push({ user: msg, assistant: response });
process.stdout.write(".");
} catch (err) {
exchanges.push({ user: msg, assistant: `[error: ${err.message}]` });
process.stdout.write("x");
}
await new Promise((r) => setTimeout(r, 800));
}
// Wait for observer
await new Promise((r) => setTimeout(r, 3000));
// Fetch brief
let brief;
try {
const res = await fetch(`${API}/api/brief/${personId}`);
brief = await res.json();
} catch (err) {
brief = { error: err.message, style: {}, topics: { hot: [], cold: [], domains: [] }, patterns: {}, observations: [], cohortPriors: { active: false, weight: 0, priors: [] }, interactionCount: 0, assemblyMs: 0, assembledAt: Date.now(), personId };
}
const md = briefToMarkdown(persona.name, personId, persona.messages, exchanges, brief);
const outPath = path.join(OUT, `${persona.name}.md`);
fs.writeFileSync(outPath, md);
console.log(`${outPath}`);
}
console.log("\nDone.");
}
main().catch(console.error);