fix: improve reminder context plumbing (#993) (thanks @cpojer)
This commit is contained in:
parent
61b52eb3c7
commit
f2de7aa108
@ -17,6 +17,7 @@
|
|||||||
- Docs: clarify multi-gateway rescue bot guidance. (#969) — thanks @bjesuiter.
|
- Docs: clarify multi-gateway rescue bot guidance. (#969) — thanks @bjesuiter.
|
||||||
- Agents: add Current Date & Time system prompt section with configurable time format (auto/12/24).
|
- Agents: add Current Date & Time system prompt section with configurable time format (auto/12/24).
|
||||||
- Agents: avoid false positives when logging unsupported Google tool schema keywords.
|
- Agents: avoid false positives when logging unsupported Google tool schema keywords.
|
||||||
|
- Agents: include recent context in reminder cron payloads. (#993) — thanks @cpojer.
|
||||||
- Status: restore usage summary line for current provider when no OAuth profiles exist.
|
- Status: restore usage summary line for current provider when no OAuth profiles exist.
|
||||||
- Tools: normalize Slack/Discord message timestamps with `timestampMs`/`timestampUtc` while keeping raw provider fields.
|
- Tools: normalize Slack/Discord message timestamps with `timestampMs`/`timestampUtc` while keeping raw provider fields.
|
||||||
- Docs: add Date & Time guide and update prompt/timezone configuration docs.
|
- Docs: add Date & Time guide and update prompt/timezone configuration docs.
|
||||||
|
|||||||
@ -77,6 +77,7 @@ export function createClawdbotTools(options?: {
|
|||||||
createNodesTool(),
|
createNodesTool(),
|
||||||
createCronTool({
|
createCronTool({
|
||||||
agentSessionKey: options?.agentSessionKey,
|
agentSessionKey: options?.agentSessionKey,
|
||||||
|
config: options?.config,
|
||||||
}),
|
}),
|
||||||
createMessageTool({
|
createMessageTool({
|
||||||
agentAccountId: options?.agentAccountId,
|
agentAccountId: options?.agentAccountId,
|
||||||
|
|||||||
@ -99,7 +99,7 @@ describe("cron tool", () => {
|
|||||||
})
|
})
|
||||||
.mockResolvedValueOnce({ ok: true });
|
.mockResolvedValueOnce({ ok: true });
|
||||||
|
|
||||||
const tool = createCronTool({ agentSessionKey: "main" });
|
const tool = createCronTool({ agentSessionKey: "main", config: {} });
|
||||||
await tool.execute("call3", {
|
await tool.execute("call3", {
|
||||||
action: "add",
|
action: "add",
|
||||||
job: {
|
job: {
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
import { Type } from "@sinclair/typebox";
|
import { Type } from "@sinclair/typebox";
|
||||||
import { normalizeCronJobCreate, normalizeCronJobPatch } from "../../cron/normalize.js";
|
import { normalizeCronJobCreate, normalizeCronJobPatch } from "../../cron/normalize.js";
|
||||||
import { loadConfig } from "../../config/config.js";
|
import { loadConfig, type ClawdbotConfig } from "../../config/config.js";
|
||||||
import { truncateUtf16Safe } from "../../utils.js";
|
import { truncateUtf16Safe } from "../../utils.js";
|
||||||
import { optionalStringEnum, stringEnum } from "../schema/typebox.js";
|
import { optionalStringEnum, stringEnum } from "../schema/typebox.js";
|
||||||
import { type AnyAgentTool, jsonResult, readStringParam } from "./common.js";
|
import { type AnyAgentTool, jsonResult, readStringParam } from "./common.js";
|
||||||
@ -38,6 +38,7 @@ const CronToolSchema = Type.Object({
|
|||||||
|
|
||||||
type CronToolOptions = {
|
type CronToolOptions = {
|
||||||
agentSessionKey?: string;
|
agentSessionKey?: string;
|
||||||
|
config?: ClawdbotConfig;
|
||||||
};
|
};
|
||||||
|
|
||||||
type ChatMessage = {
|
type ChatMessage = {
|
||||||
@ -86,10 +87,11 @@ function extractMessageText(message: ChatMessage): { role: string; text: string
|
|||||||
async function buildReminderContextLines(params: {
|
async function buildReminderContextLines(params: {
|
||||||
agentSessionKey?: string;
|
agentSessionKey?: string;
|
||||||
gatewayOpts: GatewayCallOptions;
|
gatewayOpts: GatewayCallOptions;
|
||||||
|
config?: ClawdbotConfig;
|
||||||
}) {
|
}) {
|
||||||
const sessionKey = params.agentSessionKey?.trim();
|
const sessionKey = params.agentSessionKey?.trim();
|
||||||
if (!sessionKey) return [];
|
if (!sessionKey) return [];
|
||||||
const cfg = loadConfig();
|
const cfg = params.config ?? loadConfig();
|
||||||
const { mainKey, alias } = resolveMainSessionAlias(cfg);
|
const { mainKey, alias } = resolveMainSessionAlias(cfg);
|
||||||
const resolvedKey = resolveInternalSessionKey({ key: sessionKey, alias, mainKey });
|
const resolvedKey = resolveInternalSessionKey({ key: sessionKey, alias, mainKey });
|
||||||
try {
|
try {
|
||||||
@ -160,6 +162,7 @@ export function createCronTool(opts?: CronToolOptions): AnyAgentTool {
|
|||||||
const contextLines = await buildReminderContextLines({
|
const contextLines = await buildReminderContextLines({
|
||||||
agentSessionKey: opts?.agentSessionKey,
|
agentSessionKey: opts?.agentSessionKey,
|
||||||
gatewayOpts,
|
gatewayOpts,
|
||||||
|
config: opts?.config,
|
||||||
});
|
});
|
||||||
if (contextLines.length > 0) {
|
if (contextLines.length > 0) {
|
||||||
const baseText = stripExistingContext(payload.text);
|
const baseText = stripExistingContext(payload.text);
|
||||||
|
|||||||
@ -374,7 +374,7 @@ describe("doctor command", () => {
|
|||||||
|
|
||||||
expect(runLegacyStateMigrations).toHaveBeenCalledTimes(1);
|
expect(runLegacyStateMigrations).toHaveBeenCalledTimes(1);
|
||||||
expect(confirm).not.toHaveBeenCalled();
|
expect(confirm).not.toHaveBeenCalled();
|
||||||
}, 20_000);
|
});
|
||||||
|
|
||||||
it("skips gateway restarts in non-interactive mode", async () => {
|
it("skips gateway restarts in non-interactive mode", async () => {
|
||||||
readConfigFileSnapshot.mockResolvedValue({
|
readConfigFileSnapshot.mockResolvedValue({
|
||||||
|
|||||||
@ -372,7 +372,7 @@ describe("doctor command", () => {
|
|||||||
);
|
);
|
||||||
}),
|
}),
|
||||||
).toBe(true);
|
).toBe(true);
|
||||||
}, 10_000);
|
});
|
||||||
|
|
||||||
it("warns when extra workspace directories exist", async () => {
|
it("warns when extra workspace directories exist", async () => {
|
||||||
readConfigFileSnapshot.mockResolvedValue({
|
readConfigFileSnapshot.mockResolvedValue({
|
||||||
|
|||||||
@ -343,7 +343,7 @@ describe("doctor command", () => {
|
|||||||
const stateNote = note.mock.calls.find((call) => call[1] === "State integrity");
|
const stateNote = note.mock.calls.find((call) => call[1] === "State integrity");
|
||||||
expect(stateNote).toBeTruthy();
|
expect(stateNote).toBeTruthy();
|
||||||
expect(String(stateNote?.[0])).toContain("CRITICAL");
|
expect(String(stateNote?.[0])).toContain("CRITICAL");
|
||||||
}, 20_000);
|
});
|
||||||
|
|
||||||
it("warns about opencode provider overrides", async () => {
|
it("warns about opencode provider overrides", async () => {
|
||||||
readConfigFileSnapshot.mockResolvedValue({
|
readConfigFileSnapshot.mockResolvedValue({
|
||||||
|
|||||||
@ -42,5 +42,5 @@ describe("sandbox explain command", () => {
|
|||||||
expect(Array.isArray(parsed.fixIt)).toBe(true);
|
expect(Array.isArray(parsed.fixIt)).toBe(true);
|
||||||
expect(parsed.fixIt).toContain("agents.defaults.sandbox.mode=off");
|
expect(parsed.fixIt).toContain("agents.defaults.sandbox.mode=off");
|
||||||
expect(parsed.fixIt).toContain("tools.sandbox.tools.deny");
|
expect(parsed.fixIt).toContain("tools.sandbox.tools.deny");
|
||||||
}, 15_000);
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user