@poncho-ai/cli 0.36.9 → 0.37.0
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/.turbo/turbo-build.log +5 -5
- package/CHANGELOG.md +19 -0
- package/dist/{chunk-IZLDZWPA.js → chunk-GUGBKAIM.js} +26 -10
- package/dist/cli.js +1 -1
- package/dist/index.js +1 -1
- package/dist/{run-interactive-ink-KDWRD7FT.js → run-interactive-ink-75GKYSEC.js} +1 -1
- package/package.json +2 -2
- package/src/index.ts +34 -8
package/.turbo/turbo-build.log
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
|
|
2
|
-
> @poncho-ai/cli@0.
|
|
2
|
+
> @poncho-ai/cli@0.37.0 build /home/runner/work/poncho-ai/poncho-ai/packages/cli
|
|
3
3
|
> tsup src/index.ts src/cli.ts --format esm --dts
|
|
4
4
|
|
|
5
5
|
[34mCLI[39m Building entry: src/cli.ts, src/index.ts
|
|
@@ -9,10 +9,10 @@
|
|
|
9
9
|
[34mESM[39m Build start
|
|
10
10
|
[32mESM[39m [1mdist/cli.js [22m[32m94.00 B[39m
|
|
11
11
|
[32mESM[39m [1mdist/index.js [22m[32m917.00 B[39m
|
|
12
|
-
[32mESM[39m [1mdist/run-interactive-ink-
|
|
13
|
-
[32mESM[39m [1mdist/chunk-
|
|
14
|
-
[32mESM[39m ⚡️ Build success in
|
|
12
|
+
[32mESM[39m [1mdist/run-interactive-ink-75GKYSEC.js [22m[32m56.86 KB[39m
|
|
13
|
+
[32mESM[39m [1mdist/chunk-GUGBKAIM.js [22m[32m572.60 KB[39m
|
|
14
|
+
[32mESM[39m ⚡️ Build success in 68ms
|
|
15
15
|
[34mDTS[39m Build start
|
|
16
|
-
[32mDTS[39m ⚡️ Build success in
|
|
16
|
+
[32mDTS[39m ⚡️ Build success in 4119ms
|
|
17
17
|
[32mDTS[39m [1mdist/cli.d.ts [22m[32m20.00 B[39m
|
|
18
18
|
[32mDTS[39m [1mdist/index.d.ts [22m[32m7.07 KB[39m
|
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,24 @@
|
|
|
1
1
|
# @poncho-ai/cli
|
|
2
2
|
|
|
3
|
+
## 0.37.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [`620a0c8`](https://github.com/cesr/poncho-ai/commit/620a0c89efaafce28968fca5cbde2e2b19bd1595) Thanks [@cesr](https://github.com/cesr)! - feat: add recurrent reminders (daily, weekly, monthly, cron)
|
|
8
|
+
|
|
9
|
+
The `set_reminder` tool now accepts an optional `recurrence` parameter that makes reminders repeat on a schedule instead of firing once. Supports daily, weekly (with specific days-of-week), monthly, and cron expressions. Recurring reminders are rescheduled after each firing and can be bounded by `maxOccurrences` or `endsAt`. Cancel a recurring reminder to stop all future occurrences.
|
|
10
|
+
|
|
11
|
+
### Patch Changes
|
|
12
|
+
|
|
13
|
+
- [`6486de2`](https://github.com/cesr/poncho-ai/commit/6486de2242a2976068e4bd09f7c0f2d978c35c96) Thanks [@cesr](https://github.com/cesr)! - fix: persist subagent `parentConversationId` atomically so children never appear top-level in the sidebar.
|
|
14
|
+
|
|
15
|
+
`SubagentManager.spawn` previously did a two-step write: `conversationStore.create(...)` followed by `conversationStore.update(...)` to attach `parentConversationId`, `subagentMeta`, and the initial user message. If the follow-up update was interrupted (serverless timeout, transient DB error), the child row was left in the database with `parent_conversation_id = NULL`, so it slipped past the `!c.parentConversationId` filter on `/api/conversations` and showed up as a top-level conversation. This was especially visible with cron-driven research subagents.
|
|
16
|
+
|
|
17
|
+
`ConversationStore.create` now accepts an optional `init` bag (`parentConversationId`, `subagentMeta`, `messages`, `channelMeta`) that is written in the single INSERT — both into the `data` blob and into the dedicated `parent_conversation_id` column. `spawn` passes those fields through and drops the redundant update, eliminating the orphan window. All existing `create(ownerId, title, tenantId)` callers keep working since `init` is optional.
|
|
18
|
+
|
|
19
|
+
- Updated dependencies [[`6486de2`](https://github.com/cesr/poncho-ai/commit/6486de2242a2976068e4bd09f7c0f2d978c35c96), [`0d0578f`](https://github.com/cesr/poncho-ai/commit/0d0578fbc97a3d2644c4e22cab14ff02a79f805f), [`620a0c8`](https://github.com/cesr/poncho-ai/commit/620a0c89efaafce28968fca5cbde2e2b19bd1595)]:
|
|
20
|
+
- @poncho-ai/harness@0.38.0
|
|
21
|
+
|
|
3
22
|
## 0.36.9
|
|
4
23
|
|
|
5
24
|
### Patch Changes
|
|
@@ -22,7 +22,8 @@ import {
|
|
|
22
22
|
parseAgentMarkdown,
|
|
23
23
|
resolveStateConfig,
|
|
24
24
|
verifyTenantToken,
|
|
25
|
-
createSecretsStore
|
|
25
|
+
createSecretsStore,
|
|
26
|
+
computeNextOccurrence
|
|
26
27
|
} from "@poncho-ai/harness";
|
|
27
28
|
import { getTextContent } from "@poncho-ai/sdk";
|
|
28
29
|
import {
|
|
@@ -10612,12 +10613,16 @@ ${resultBody}`,
|
|
|
10612
10613
|
if (getRunningSubagentCountForParent(opts.parentConversationId) >= MAX_CONCURRENT_SUBAGENTS) {
|
|
10613
10614
|
throw new Error(`Maximum concurrent subagents (${MAX_CONCURRENT_SUBAGENTS}) per parent reached. Wait for running subagents to complete or stop some first.`);
|
|
10614
10615
|
}
|
|
10615
|
-
const conversation = await conversationStore.create(
|
|
10616
|
-
|
|
10617
|
-
|
|
10618
|
-
|
|
10619
|
-
|
|
10620
|
-
|
|
10616
|
+
const conversation = await conversationStore.create(
|
|
10617
|
+
opts.ownerId,
|
|
10618
|
+
opts.task.slice(0, 80),
|
|
10619
|
+
opts.tenantId ?? null,
|
|
10620
|
+
{
|
|
10621
|
+
parentConversationId: opts.parentConversationId,
|
|
10622
|
+
subagentMeta: { task: opts.task, status: "running" },
|
|
10623
|
+
messages: [{ role: "user", content: opts.task }]
|
|
10624
|
+
}
|
|
10625
|
+
);
|
|
10621
10626
|
recentlySpawnedParents.set(
|
|
10622
10627
|
opts.parentConversationId,
|
|
10623
10628
|
(recentlySpawnedParents.get(opts.parentConversationId) ?? 0) + 1
|
|
@@ -13594,13 +13599,24 @@ ${cronJob.task}`;
|
|
|
13594
13599
|
const due = reminders.filter((r) => r.status === "pending" && r.scheduledAt <= cutoff);
|
|
13595
13600
|
for (const reminder of due) {
|
|
13596
13601
|
try {
|
|
13597
|
-
|
|
13602
|
+
const nextScheduledAt = computeNextOccurrence(reminder);
|
|
13603
|
+
if (nextScheduledAt) {
|
|
13604
|
+
await reminderStore.update(reminder.id, {
|
|
13605
|
+
scheduledAt: nextScheduledAt,
|
|
13606
|
+
occurrenceCount: (reminder.occurrenceCount ?? 0) + 1
|
|
13607
|
+
});
|
|
13608
|
+
} else {
|
|
13609
|
+
await reminderStore.delete(reminder.id);
|
|
13610
|
+
}
|
|
13598
13611
|
const originConv = reminder.conversationId ? await conversationStore.get(reminder.conversationId) : void 0;
|
|
13599
13612
|
const channelMeta = originConv?.channelMeta;
|
|
13613
|
+
const isRecurring = !!reminder.recurrence;
|
|
13614
|
+
const recurrenceNote = isRecurring && nextScheduledAt ? `
|
|
13615
|
+
Next occurrence: ${new Date(nextScheduledAt).toISOString()}` : isRecurring ? "\nThis was the final occurrence." : "";
|
|
13600
13616
|
const framedMessage = `[Reminder] A reminder you previously set has fired.
|
|
13601
13617
|
Task: "${reminder.task}"
|
|
13602
13618
|
Originally set at: ${new Date(reminder.createdAt).toISOString()}
|
|
13603
|
-
Scheduled for: ${new Date(reminder.scheduledAt).toISOString()}
|
|
13619
|
+
Scheduled for: ${new Date(reminder.scheduledAt).toISOString()}` + recurrenceNote;
|
|
13604
13620
|
if (channelMeta) {
|
|
13605
13621
|
const adapter = messagingAdapters.get(channelMeta.platform);
|
|
13606
13622
|
if (adapter && originConv) {
|
|
@@ -14048,7 +14064,7 @@ var runInteractive = async (workingDir, params) => {
|
|
|
14048
14064
|
await harness.initialize();
|
|
14049
14065
|
const identity = await ensureAgentIdentity2(workingDir);
|
|
14050
14066
|
try {
|
|
14051
|
-
const { runInteractiveInk } = await import("./run-interactive-ink-
|
|
14067
|
+
const { runInteractiveInk } = await import("./run-interactive-ink-75GKYSEC.js");
|
|
14052
14068
|
await runInteractiveInk({
|
|
14053
14069
|
harness,
|
|
14054
14070
|
params,
|
package/dist/cli.js
CHANGED
package/dist/index.js
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@poncho-ai/cli",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.37.0",
|
|
4
4
|
"description": "CLI for building and deploying AI agents",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -28,8 +28,8 @@
|
|
|
28
28
|
"react": "^19.2.4",
|
|
29
29
|
"react-devtools-core": "^6.1.5",
|
|
30
30
|
"yaml": "^2.8.1",
|
|
31
|
+
"@poncho-ai/harness": "0.38.0",
|
|
31
32
|
"@poncho-ai/messaging": "0.8.3",
|
|
32
|
-
"@poncho-ai/harness": "0.37.2",
|
|
33
33
|
"@poncho-ai/sdk": "1.8.1"
|
|
34
34
|
},
|
|
35
35
|
"devDependencies": {
|
package/src/index.ts
CHANGED
|
@@ -35,6 +35,7 @@ import {
|
|
|
35
35
|
type UploadStore,
|
|
36
36
|
verifyTenantToken,
|
|
37
37
|
createSecretsStore,
|
|
38
|
+
computeNextOccurrence,
|
|
38
39
|
} from "@poncho-ai/harness";
|
|
39
40
|
import type { AgentEvent, FileInput, Message, RunInput } from "@poncho-ai/sdk";
|
|
40
41
|
import { getTextContent } from "@poncho-ai/sdk";
|
|
@@ -3110,12 +3111,19 @@ export const createRequestHandler = async (options?: {
|
|
|
3110
3111
|
throw new Error(`Maximum concurrent subagents (${MAX_CONCURRENT_SUBAGENTS}) per parent reached. Wait for running subagents to complete or stop some first.`);
|
|
3111
3112
|
}
|
|
3112
3113
|
|
|
3113
|
-
|
|
3114
|
-
|
|
3115
|
-
|
|
3116
|
-
conversation
|
|
3117
|
-
|
|
3118
|
-
|
|
3114
|
+
// Atomic create: parent_conversation_id and initial state are persisted
|
|
3115
|
+
// in the single INSERT. This prevents orphaned top-level-looking
|
|
3116
|
+
// subagents if a follow-up update is interrupted.
|
|
3117
|
+
const conversation = await conversationStore.create(
|
|
3118
|
+
opts.ownerId,
|
|
3119
|
+
opts.task.slice(0, 80),
|
|
3120
|
+
opts.tenantId ?? null,
|
|
3121
|
+
{
|
|
3122
|
+
parentConversationId: opts.parentConversationId,
|
|
3123
|
+
subagentMeta: { task: opts.task, status: "running" },
|
|
3124
|
+
messages: [{ role: "user", content: opts.task }],
|
|
3125
|
+
},
|
|
3126
|
+
);
|
|
3119
3127
|
|
|
3120
3128
|
// Register this parent as having a pending spawn BEFORE the async
|
|
3121
3129
|
// runSubagent starts, so hasPendingSubagentWorkForParent sees it
|
|
@@ -6486,18 +6494,36 @@ export const createRequestHandler = async (options?: {
|
|
|
6486
6494
|
|
|
6487
6495
|
for (const reminder of due) {
|
|
6488
6496
|
try {
|
|
6489
|
-
|
|
6497
|
+
// For recurring reminders, compute the next occurrence before any
|
|
6498
|
+
// state changes so we can reschedule. For one-off reminders, delete.
|
|
6499
|
+
const nextScheduledAt = computeNextOccurrence(reminder);
|
|
6500
|
+
if (nextScheduledAt) {
|
|
6501
|
+
await reminderStore.update(reminder.id, {
|
|
6502
|
+
scheduledAt: nextScheduledAt,
|
|
6503
|
+
occurrenceCount: (reminder.occurrenceCount ?? 0) + 1,
|
|
6504
|
+
});
|
|
6505
|
+
} else {
|
|
6506
|
+
await reminderStore.delete(reminder.id);
|
|
6507
|
+
}
|
|
6490
6508
|
|
|
6491
6509
|
const originConv = reminder.conversationId
|
|
6492
6510
|
? await conversationStore.get(reminder.conversationId)
|
|
6493
6511
|
: undefined;
|
|
6494
6512
|
const channelMeta = originConv?.channelMeta;
|
|
6495
6513
|
|
|
6514
|
+
const isRecurring = !!reminder.recurrence;
|
|
6515
|
+
const recurrenceNote = isRecurring && nextScheduledAt
|
|
6516
|
+
? `\nNext occurrence: ${new Date(nextScheduledAt).toISOString()}`
|
|
6517
|
+
: isRecurring
|
|
6518
|
+
? "\nThis was the final occurrence."
|
|
6519
|
+
: "";
|
|
6520
|
+
|
|
6496
6521
|
const framedMessage =
|
|
6497
6522
|
`[Reminder] A reminder you previously set has fired.\n` +
|
|
6498
6523
|
`Task: "${reminder.task}"\n` +
|
|
6499
6524
|
`Originally set at: ${new Date(reminder.createdAt).toISOString()}\n` +
|
|
6500
|
-
`Scheduled for: ${new Date(reminder.scheduledAt).toISOString()}
|
|
6525
|
+
`Scheduled for: ${new Date(reminder.scheduledAt).toISOString()}` +
|
|
6526
|
+
recurrenceNote;
|
|
6501
6527
|
|
|
6502
6528
|
if (channelMeta) {
|
|
6503
6529
|
const adapter = messagingAdapters.get(channelMeta.platform);
|