pyre-agent-kit 2.0.19 → 2.0.20

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/chain.d.ts CHANGED
@@ -21,6 +21,7 @@ import type { Action, Personality, FactionInfo, OnChainAction, ChainDerivedState
21
21
  */
22
22
  export declare function fetchAgentHistory(connection: Connection, agentPubkey: string, knownMints: Set<string>, opts?: {
23
23
  maxSignatures?: number;
24
+ afterTimestamp?: number;
24
25
  }): Promise<OnChainAction[]>;
25
26
  /**
26
27
  * Compute personality weights from on-chain action history.
package/dist/chain.js CHANGED
@@ -26,6 +26,7 @@ exports.deriveSolRange = deriveSolRange;
26
26
  exports.extractMemories = extractMemories;
27
27
  exports.reconstructFromChain = reconstructFromChain;
28
28
  const web3_js_1 = require("@solana/web3.js");
29
+ const pyre_world_kit_1 = require("pyre-world-kit");
29
30
  const defaults_1 = require("./defaults");
30
31
  // Torch Market program ID
31
32
  const TORCH_PROGRAM_ID = '8hbUkonssSEEtkqzwM7ZcZrD9evacM92TcWSooVF4BeT';
@@ -45,15 +46,23 @@ const ALL_ACTIONS = [
45
46
  async function fetchAgentHistory(connection, agentPubkey, knownMints, opts) {
46
47
  const pubkey = new web3_js_1.PublicKey(agentPubkey);
47
48
  const maxSigs = opts?.maxSignatures ?? 500;
49
+ const afterTs = opts?.afterTimestamp ?? 0;
48
50
  const allActions = [];
49
51
  // Paginate through signature history
50
52
  let before;
51
53
  let fetched = 0;
52
- while (fetched < maxSigs) {
54
+ let reachedCheckpoint = false;
55
+ while (fetched < maxSigs && !reachedCheckpoint) {
53
56
  const batchSize = Math.min(maxSigs - fetched, 1000);
54
57
  const signatures = await connection.getSignaturesForAddress(pubkey, { limit: batchSize, before }, 'confirmed');
55
58
  if (signatures.length === 0)
56
59
  break;
60
+ // If we have an afterTimestamp, stop paginating once we reach older txs
61
+ if (afterTs > 0) {
62
+ const oldestInBatch = signatures[signatures.length - 1].blockTime ?? 0;
63
+ if (oldestInBatch < afterTs)
64
+ reachedCheckpoint = true;
65
+ }
57
66
  fetched += signatures.length;
58
67
  before = signatures[signatures.length - 1].signature;
59
68
  // Batch fetch parsed transactions (100 per RPC call)
@@ -74,7 +83,11 @@ async function fetchAgentHistory(connection, agentPubkey, knownMints, opts) {
74
83
  const tx = txs[j];
75
84
  if (!tx?.meta || tx.meta.err)
76
85
  continue;
77
- const parsed = parseTransaction(tx, batch[j].signature, batch[j].blockTime ?? 0, agentPubkey, knownMints);
86
+ const blockTime = batch[j].blockTime ?? 0;
87
+ // Skip transactions before checkpoint
88
+ if (afterTs > 0 && blockTime <= afterTs)
89
+ continue;
90
+ const parsed = parseTransaction(tx, batch[j].signature, blockTime, agentPubkey, knownMints);
78
91
  if (parsed)
79
92
  allActions.push(parsed);
80
93
  }
@@ -541,12 +554,45 @@ function extractMemories(history) {
541
554
  */
542
555
  async function reconstructFromChain(connection, agentPubkey, factions, seedPersonality, opts) {
543
556
  const knownMints = new Set(factions.map(f => f.mint));
544
- // 1. Fetch on-chain history
557
+ // Check for registry checkpoint — if exists, only replay history after last checkpoint
558
+ let registryProfile = null;
559
+ try {
560
+ registryProfile = await (0, pyre_world_kit_1.getRegistryProfile)(connection, agentPubkey);
561
+ }
562
+ catch { /* registry unavailable, fall through to full replay */ }
563
+ const afterTimestamp = registryProfile?.last_checkpoint ?? 0;
564
+ // 1. Fetch on-chain history (incremental if checkpoint exists)
545
565
  const history = await fetchAgentHistory(connection, agentPubkey, knownMints, {
546
566
  maxSignatures: opts?.maxSignatures,
567
+ afterTimestamp,
547
568
  });
548
- // 2. Compute personality weights from action frequency
549
- const weights = computeWeightsFromHistory(history, seedPersonality, opts?.decay);
569
+ // 2. Compute personality weights — seed from registry checkpoint if available
570
+ let baselineCounts = null;
571
+ if (registryProfile && registryProfile.last_checkpoint > 0) {
572
+ // Registry field order matches ALL_ACTIONS:
573
+ // join, defect, rally, launch, message, stronghold(reinforces), war_loan, repay_loan,
574
+ // siege, ascend, raze, tithe, infiltrate, fud
575
+ baselineCounts = [
576
+ registryProfile.joins, registryProfile.defects, registryProfile.rallies,
577
+ registryProfile.launches, registryProfile.messages, registryProfile.reinforces,
578
+ registryProfile.war_loans, registryProfile.repay_loans, registryProfile.sieges,
579
+ registryProfile.ascends, registryProfile.razes, registryProfile.tithes,
580
+ registryProfile.infiltrates, registryProfile.fuds,
581
+ ];
582
+ }
583
+ // Merge baseline counts with incremental history
584
+ const incrementalCounts = new Array(ALL_ACTIONS.length).fill(0);
585
+ for (const entry of history) {
586
+ const normalized = normalizeChainAction(entry.action);
587
+ const idx = ALL_ACTIONS.indexOf(normalized);
588
+ if (idx >= 0)
589
+ incrementalCounts[idx]++;
590
+ }
591
+ const totalCounts = baselineCounts
592
+ ? baselineCounts.map((base, i) => base + incrementalCounts[i])
593
+ : incrementalCounts;
594
+ const weights = weightsFromCounts(totalCounts, seedPersonality, opts?.decay);
595
+ const totalActionCount = totalCounts.reduce((a, b) => a + b, 0);
550
596
  // 3. Classify emergent personality (action ratios + memo content, per-faction)
551
597
  const memoTexts = history.filter(h => h.memo?.trim()).map(h => h.memo);
552
598
  // Build per-faction action counts for per-ticker personality scoring
@@ -566,7 +612,7 @@ async function reconstructFromChain(connection, agentPubkey, factions, seedPerso
566
612
  const factionNames = new Map();
567
613
  for (const f of factions)
568
614
  factionNames.set(f.mint, f.symbol);
569
- const personality = history.length > 0
615
+ const personality = totalActionCount > 0
570
616
  ? await classifyPersonality(weights, memoTexts, perFaction, opts?.llmGenerate, factionNames)
571
617
  : seedPersonality;
572
618
  // 4. Compute sentiment from on-chain interactions
@@ -613,7 +659,7 @@ async function reconstructFromChain(connection, agentPubkey, factions, seedPerso
613
659
  allies,
614
660
  rivals,
615
661
  solRange,
616
- actionCount: history.length,
662
+ actionCount: totalActionCount,
617
663
  recentHistory,
618
664
  founded,
619
665
  memories,
package/dist/cli.js CHANGED
@@ -274,8 +274,8 @@ async function runSetup() {
274
274
  };
275
275
  saveConfig(config);
276
276
  console.log(`\n Config saved to ${CONFIG_PATH}`);
277
- console.log(`\n Next: link your agent on pyre.world`);
278
- console.log(` Run: npx pyre-agent-kit --link`);
277
+ console.log(`\n Next: set up your Stronghold + Pyre Identity and link this agent.`);
278
+ console.log(` Run: npx pyre-agent-kit --link (for step-by-step instructions)`);
279
279
  return config;
280
280
  }
281
281
  // ─── Agent Loop ───────────────────────────────────────────────────
@@ -403,8 +403,16 @@ async function main() {
403
403
  const kp = web3_js_1.Keypair.fromSecretKey(Uint8Array.from(config.secretKey));
404
404
  console.log(`\n Agent public key:\n`);
405
405
  console.log(` ${kp.publicKey.toBase58()}`);
406
- console.log(`\n Go to pyre.world → connect your wallet → create or manage your vault → link this agent key.`);
407
- console.log(` The agent will use the linked vault to trade.\n`);
406
+ console.log(`\n To link this agent, go to pyre.world/stronghold and:`);
407
+ console.log(``);
408
+ console.log(` 1. Connect your authority wallet`);
409
+ console.log(` 2. Create a Stronghold (vault) if you don't have one`);
410
+ console.log(` 3. Create a Pyre Identity (on-chain PDA) — this stores agent history`);
411
+ console.log(` 4. Link this agent key under "Linked Agents"`);
412
+ console.log(``);
413
+ console.log(` The Stronghold holds SOL for the agent to trade with.`);
414
+ console.log(` The Pyre Identity persists action counts and personality on-chain,`);
415
+ console.log(` so the agent reconstructs faster on restart.\n`);
408
416
  rl.close();
409
417
  process.exit(0);
410
418
  }
package/dist/index.d.ts CHANGED
@@ -2,6 +2,7 @@ import { PyreAgentConfig, PyreAgent } from './types';
2
2
  export type { PyreAgentConfig, PyreAgent, AgentTickResult, SerializedAgentState, LLMAdapter, LLMDecision, FactionInfo, Personality, Action, AgentState, OnChainAction, ChainDerivedState, } from './types';
3
3
  export { assignPersonality, PERSONALITY_SOL, PERSONALITY_WEIGHTS, personalityDesc, VOICE_NUDGES } from './defaults';
4
4
  export { ensureStronghold } from './stronghold';
5
+ export { ensureRegistryProfile } from './registry';
5
6
  export { sendAndConfirm } from './tx';
6
7
  export { reconstructFromChain, computeWeightsFromHistory, classifyPersonality, weightsFromCounts, actionIndex } from './chain';
7
8
  export declare function createPyreAgent(config: PyreAgentConfig): Promise<PyreAgent>;
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.actionIndex = exports.weightsFromCounts = exports.classifyPersonality = exports.computeWeightsFromHistory = exports.reconstructFromChain = exports.sendAndConfirm = exports.ensureStronghold = exports.VOICE_NUDGES = exports.personalityDesc = exports.PERSONALITY_WEIGHTS = exports.PERSONALITY_SOL = exports.assignPersonality = void 0;
3
+ exports.actionIndex = exports.weightsFromCounts = exports.classifyPersonality = exports.computeWeightsFromHistory = exports.reconstructFromChain = exports.sendAndConfirm = exports.ensureRegistryProfile = exports.ensureStronghold = exports.VOICE_NUDGES = exports.personalityDesc = exports.PERSONALITY_WEIGHTS = exports.PERSONALITY_SOL = exports.assignPersonality = void 0;
4
4
  exports.createPyreAgent = createPyreAgent;
5
5
  const pyre_world_kit_1 = require("pyre-world-kit");
6
6
  const defaults_1 = require("./defaults");
@@ -8,6 +8,7 @@ const action_1 = require("./action");
8
8
  const agent_1 = require("./agent");
9
9
  const executor_1 = require("./executor");
10
10
  const stronghold_1 = require("./stronghold");
11
+ const registry_1 = require("./registry");
11
12
  const chain_1 = require("./chain");
12
13
  const util_1 = require("./util");
13
14
  var defaults_2 = require("./defaults");
@@ -18,6 +19,8 @@ Object.defineProperty(exports, "personalityDesc", { enumerable: true, get: funct
18
19
  Object.defineProperty(exports, "VOICE_NUDGES", { enumerable: true, get: function () { return defaults_2.VOICE_NUDGES; } });
19
20
  var stronghold_2 = require("./stronghold");
20
21
  Object.defineProperty(exports, "ensureStronghold", { enumerable: true, get: function () { return stronghold_2.ensureStronghold; } });
22
+ var registry_2 = require("./registry");
23
+ Object.defineProperty(exports, "ensureRegistryProfile", { enumerable: true, get: function () { return registry_2.ensureRegistryProfile; } });
21
24
  var tx_1 = require("./tx");
22
25
  Object.defineProperty(exports, "sendAndConfirm", { enumerable: true, get: function () { return tx_1.sendAndConfirm; } });
23
26
  var chain_2 = require("./chain");
@@ -115,6 +118,22 @@ async function createPyreAgent(config) {
115
118
  };
116
119
  // Ensure stronghold exists
117
120
  await (0, stronghold_1.ensureStronghold)(connection, state, logger, strongholdOpts);
121
+ // Ensure registry profile exists and seed action counts from checkpoint
122
+ const registryProfile = await (0, registry_1.ensureRegistryProfile)(connection, state, logger);
123
+ if (registryProfile) {
124
+ // Seed cumulative action counts from on-chain checkpoint
125
+ // Order matches ALL_ACTIONS: join, defect, rally, launch, message, stronghold, war_loan, repay_loan, siege, ascend, raze, tithe, infiltrate, fud
126
+ const checkpointCounts = [
127
+ registryProfile.joins, registryProfile.defects, registryProfile.rallies,
128
+ registryProfile.launches, registryProfile.messages, registryProfile.reinforces,
129
+ registryProfile.war_loans, registryProfile.repay_loans, registryProfile.sieges,
130
+ registryProfile.ascends, registryProfile.razes, registryProfile.tithes,
131
+ registryProfile.infiltrates, registryProfile.fuds,
132
+ ];
133
+ for (let i = 0; i < checkpointCounts.length; i++) {
134
+ actionCounts[i] = Math.max(actionCounts[i], checkpointCounts[i]);
135
+ }
136
+ }
118
137
  function serialize() {
119
138
  return {
120
139
  publicKey: state.publicKey,
@@ -0,0 +1,8 @@
1
+ import { Connection } from '@solana/web3.js';
2
+ import type { RegistryProfile } from 'pyre-world-kit';
3
+ import { AgentState } from './types';
4
+ /**
5
+ * Ensure the agent has an on-chain registry profile (pyre_world PDA).
6
+ * Creates one if missing. Returns the profile if it exists or was created.
7
+ */
8
+ export declare function ensureRegistryProfile(connection: Connection, agent: AgentState, log: (msg: string) => void): Promise<RegistryProfile | null>;
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ensureRegistryProfile = ensureRegistryProfile;
4
+ const pyre_world_kit_1 = require("pyre-world-kit");
5
+ const tx_1 = require("./tx");
6
+ /**
7
+ * Ensure the agent has an on-chain registry profile (pyre_world PDA).
8
+ * Creates one if missing. Returns the profile if it exists or was created.
9
+ */
10
+ async function ensureRegistryProfile(connection, agent, log) {
11
+ const short = agent.publicKey.slice(0, 8);
12
+ try {
13
+ const existing = await (0, pyre_world_kit_1.getRegistryProfile)(connection, agent.publicKey);
14
+ if (existing) {
15
+ log(`[${short}] registry profile found (${existing.address.slice(0, 8)}), last checkpoint: ${existing.last_checkpoint > 0 ? new Date(existing.last_checkpoint * 1000).toISOString().slice(0, 10) : 'never'}`);
16
+ return existing;
17
+ }
18
+ // Create new profile
19
+ const result = await (0, pyre_world_kit_1.buildRegisterAgentTransaction)(connection, {
20
+ creator: agent.publicKey,
21
+ });
22
+ await (0, tx_1.sendAndConfirm)(connection, agent.keypair, result);
23
+ log(`[${short}] created registry profile`);
24
+ // Fetch the newly created profile
25
+ return await (0, pyre_world_kit_1.getRegistryProfile)(connection, agent.publicKey);
26
+ }
27
+ catch (err) {
28
+ log(`[${short}] registry profile setup failed (${err.message?.slice(0, 60)})`);
29
+ return null;
30
+ }
31
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "pyre-agent-kit",
3
- "version": "2.0.19",
3
+ "version": "2.0.20",
4
4
  "description": "Autonomous agent kit for Pyre — plug in your own LLM and play pyre.world",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -15,7 +15,7 @@
15
15
  "dependencies": {
16
16
  "@solana/spl-token": "^0.4.6",
17
17
  "@solana/web3.js": "^1.98.4",
18
- "pyre-world-kit": "1.0.23"
18
+ "pyre-world-kit": "2.0.0"
19
19
  },
20
20
  "devDependencies": {
21
21
  "@types/node": "^25.4.0",