scientify 1.9.0 → 1.10.1

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.
Files changed (63) hide show
  1. package/README.md +29 -0
  2. package/README.zh.md +29 -0
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +29 -0
  5. package/dist/index.js.map +1 -1
  6. package/dist/src/hooks/research-mode.d.ts.map +1 -1
  7. package/dist/src/hooks/research-mode.js +6 -0
  8. package/dist/src/hooks/research-mode.js.map +1 -1
  9. package/dist/src/hooks/scientify-cron-autofill.d.ts +15 -0
  10. package/dist/src/hooks/scientify-cron-autofill.d.ts.map +1 -0
  11. package/dist/src/hooks/scientify-cron-autofill.js +156 -0
  12. package/dist/src/hooks/scientify-cron-autofill.js.map +1 -0
  13. package/dist/src/hooks/scientify-signature.d.ts.map +1 -1
  14. package/dist/src/hooks/scientify-signature.js +4 -1
  15. package/dist/src/hooks/scientify-signature.js.map +1 -1
  16. package/dist/src/literature/subscription-state.d.ts +90 -0
  17. package/dist/src/literature/subscription-state.d.ts.map +1 -0
  18. package/dist/src/literature/subscription-state.js +521 -0
  19. package/dist/src/literature/subscription-state.js.map +1 -0
  20. package/dist/src/research-subscriptions/constants.d.ts +16 -0
  21. package/dist/src/research-subscriptions/constants.d.ts.map +1 -0
  22. package/dist/src/research-subscriptions/constants.js +59 -0
  23. package/dist/src/research-subscriptions/constants.js.map +1 -0
  24. package/dist/src/research-subscriptions/cron-client.d.ts +8 -0
  25. package/dist/src/research-subscriptions/cron-client.d.ts.map +1 -0
  26. package/dist/src/research-subscriptions/cron-client.js +81 -0
  27. package/dist/src/research-subscriptions/cron-client.js.map +1 -0
  28. package/dist/src/research-subscriptions/delivery.d.ts +10 -0
  29. package/dist/src/research-subscriptions/delivery.d.ts.map +1 -0
  30. package/dist/src/research-subscriptions/delivery.js +82 -0
  31. package/dist/src/research-subscriptions/delivery.js.map +1 -0
  32. package/dist/src/research-subscriptions/handlers.d.ts +6 -0
  33. package/dist/src/research-subscriptions/handlers.d.ts.map +1 -0
  34. package/dist/src/research-subscriptions/handlers.js +200 -0
  35. package/dist/src/research-subscriptions/handlers.js.map +1 -0
  36. package/dist/src/research-subscriptions/parse.d.ts +11 -0
  37. package/dist/src/research-subscriptions/parse.d.ts.map +1 -0
  38. package/dist/src/research-subscriptions/parse.js +478 -0
  39. package/dist/src/research-subscriptions/parse.js.map +1 -0
  40. package/dist/src/research-subscriptions/prompt.d.ts +5 -0
  41. package/dist/src/research-subscriptions/prompt.d.ts.map +1 -0
  42. package/dist/src/research-subscriptions/prompt.js +161 -0
  43. package/dist/src/research-subscriptions/prompt.js.map +1 -0
  44. package/dist/src/research-subscriptions/types.d.ts +65 -0
  45. package/dist/src/research-subscriptions/types.d.ts.map +1 -0
  46. package/dist/src/research-subscriptions/types.js +2 -0
  47. package/dist/src/research-subscriptions/types.js.map +1 -0
  48. package/dist/src/research-subscriptions.d.ts +2 -0
  49. package/dist/src/research-subscriptions.d.ts.map +1 -0
  50. package/dist/src/research-subscriptions.js +2 -0
  51. package/dist/src/research-subscriptions.js.map +1 -0
  52. package/dist/src/tools/scientify-cron.d.ts +62 -0
  53. package/dist/src/tools/scientify-cron.d.ts.map +1 -0
  54. package/dist/src/tools/scientify-cron.js +224 -0
  55. package/dist/src/tools/scientify-cron.js.map +1 -0
  56. package/dist/src/tools/scientify-literature-state.d.ts +70 -0
  57. package/dist/src/tools/scientify-literature-state.d.ts.map +1 -0
  58. package/dist/src/tools/scientify-literature-state.js +312 -0
  59. package/dist/src/tools/scientify-literature-state.js.map +1 -0
  60. package/openclaw.plugin.json +2 -1
  61. package/package.json +1 -1
  62. package/skills/_shared/workspace-spec.md +13 -0
  63. package/skills/research-subscription/SKILL.md +102 -0
@@ -0,0 +1,81 @@
1
+ export async function runCommand(deps, argv, timeoutMs = 30_000) {
2
+ deps.logger.debug?.(`[scientify-cron] run: ${argv.join(" ")}`);
3
+ return deps.runtime.system.runCommandWithTimeout(argv, { timeoutMs });
4
+ }
5
+ export function parseJsonFromOutput(stdout) {
6
+ const trimmed = stdout.trim();
7
+ if (!trimmed)
8
+ return null;
9
+ try {
10
+ return JSON.parse(trimmed);
11
+ }
12
+ catch {
13
+ // Continue to best-effort extraction.
14
+ }
15
+ const start = trimmed.indexOf("{");
16
+ const end = trimmed.lastIndexOf("}");
17
+ if (start >= 0 && end > start) {
18
+ const maybeJson = trimmed.slice(start, end + 1);
19
+ try {
20
+ return JSON.parse(maybeJson);
21
+ }
22
+ catch {
23
+ return null;
24
+ }
25
+ }
26
+ return null;
27
+ }
28
+ export async function listAllJobs(deps) {
29
+ const res = await runCommand(deps, ["openclaw", "cron", "list", "--all", "--json"]);
30
+ if (res.code !== 0) {
31
+ throw new Error(res.stderr || "cron list failed");
32
+ }
33
+ const payload = parseJsonFromOutput(res.stdout);
34
+ return payload?.jobs ?? [];
35
+ }
36
+ async function getJobById(deps, jobId) {
37
+ const jobs = await listAllJobs(deps);
38
+ return jobs.find((job) => job.id === jobId);
39
+ }
40
+ export async function ensureJobEnabled(deps, jobId) {
41
+ const current = await getJobById(deps, jobId);
42
+ if (!current || current.enabled !== false) {
43
+ return current;
44
+ }
45
+ const enable = await runCommand(deps, ["openclaw", "cron", "enable", jobId]);
46
+ if (enable.code !== 0) {
47
+ throw new Error(enable.stderr || `failed to enable cron job ${jobId}`);
48
+ }
49
+ const after = await getJobById(deps, jobId);
50
+ if (after?.enabled === false) {
51
+ throw new Error(`cron job ${jobId} is disabled after enable attempt`);
52
+ }
53
+ return after;
54
+ }
55
+ export function scheduleText(job) {
56
+ const schedule = job.schedule;
57
+ if (!schedule)
58
+ return "(unknown)";
59
+ if (schedule.kind === "cron") {
60
+ const expr = schedule.expr ?? "(missing expr)";
61
+ const tz = schedule.tz ? ` (${schedule.tz})` : "";
62
+ return `${expr}${tz}`;
63
+ }
64
+ if (schedule.kind === "every") {
65
+ if (typeof schedule.everyMs === "number" && schedule.everyMs > 0) {
66
+ const totalSeconds = Math.floor(schedule.everyMs / 1000);
67
+ if (totalSeconds % 3600 === 0)
68
+ return `every ${totalSeconds / 3600}h`;
69
+ if (totalSeconds % 60 === 0)
70
+ return `every ${totalSeconds / 60}m`;
71
+ return `every ${totalSeconds}s`;
72
+ }
73
+ }
74
+ if (schedule.kind === "at") {
75
+ if (typeof schedule.at === "string" && schedule.at.trim().length > 0) {
76
+ return `at ${schedule.at}`;
77
+ }
78
+ }
79
+ return JSON.stringify(schedule);
80
+ }
81
+ //# sourceMappingURL=cron-client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cron-client.js","sourceRoot":"","sources":["../../../src/research-subscriptions/cron-client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ import type { PluginCommandContext } from "openclaw";
2
+ import type { DeliveryTarget, SubscriptionOptions } from "./types.js";
3
+ export declare function sanitizeIdPart(value: string | undefined): string;
4
+ export declare function buildScopedJobName(ctx: PluginCommandContext): string;
5
+ export declare function normalizeDeliveryChannelOverride(value: string): string;
6
+ export declare function resolveDeliveryTarget(ctx: PluginCommandContext, opts: SubscriptionOptions): DeliveryTarget | {
7
+ error: string;
8
+ };
9
+ export declare function buildStateScopeKey(ctx: PluginCommandContext, delivery: DeliveryTarget): string;
10
+ //# sourceMappingURL=delivery.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delivery.d.ts","sourceRoot":"","sources":["../../../src/research-subscriptions/delivery.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,UAAU,CAAC;AAErD,OAAO,KAAK,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAEtE,wBAAgB,cAAc,CAAC,KAAK,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,CAOhE;AAED,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,oBAAoB,GAAG,MAAM,CAIpE;AAED,wBAAgB,gCAAgC,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAGtE;AAED,wBAAgB,qBAAqB,CACnC,GAAG,EAAE,oBAAoB,EACzB,IAAI,EAAE,mBAAmB,GACxB,cAAc,GAAG;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CAiEpC;AAED,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,oBAAoB,EAAE,QAAQ,EAAE,cAAc,GAAG,MAAM,CAO9F"}
@@ -0,0 +1,82 @@
1
+ import { ALLOWED_DELIVERY_CHANNELS, DELIVERY_LAST_ALIASES } from "./constants.js";
2
+ export function sanitizeIdPart(value) {
3
+ const cleaned = (value ?? "unknown")
4
+ .toLowerCase()
5
+ .replace(/[^a-z0-9_-]+/g, "-")
6
+ .replace(/-+/g, "-")
7
+ .replace(/^-|-$/g, "");
8
+ return cleaned.slice(0, 48) || "unknown";
9
+ }
10
+ export function buildScopedJobName(ctx) {
11
+ const channel = sanitizeIdPart(ctx.channel);
12
+ const sender = sanitizeIdPart(ctx.senderId);
13
+ return `scientify-report-${channel}-${sender}`;
14
+ }
15
+ export function normalizeDeliveryChannelOverride(value) {
16
+ const channel = value.trim().toLowerCase();
17
+ return DELIVERY_LAST_ALIASES.has(channel) ? "last" : channel;
18
+ }
19
+ export function resolveDeliveryTarget(ctx, opts) {
20
+ if (opts.noDeliver) {
21
+ return {
22
+ mode: "none",
23
+ channel: "last",
24
+ display: "none",
25
+ };
26
+ }
27
+ if (opts.channelOverride) {
28
+ const channel = normalizeDeliveryChannelOverride(opts.channelOverride);
29
+ const displayChannel = channel === "last" && opts.channelOverride !== "last"
30
+ ? `last(${opts.channelOverride.toLowerCase()})`
31
+ : channel;
32
+ if (channel !== "last" && !ALLOWED_DELIVERY_CHANNELS.has(channel)) {
33
+ return {
34
+ error: "Error: unsupported channel override. Try one of: feishu, telegram, slack, discord, last (or aliases: webui, tui).",
35
+ };
36
+ }
37
+ if (channel !== "last" && !opts.toOverride) {
38
+ return {
39
+ error: "Error: `--to` is required when `--channel` is set to a concrete channel (for example: `--channel feishu --to ou_xxx`).",
40
+ };
41
+ }
42
+ return {
43
+ mode: "announce",
44
+ channel,
45
+ to: opts.toOverride,
46
+ display: `${displayChannel}${opts.toOverride ? `:${opts.toOverride}` : ""}`,
47
+ };
48
+ }
49
+ const channel = (ctx.channel ?? "").trim().toLowerCase();
50
+ const senderId = ctx.senderId?.trim();
51
+ if (senderId && ALLOWED_DELIVERY_CHANNELS.has(channel)) {
52
+ return {
53
+ mode: "announce",
54
+ channel,
55
+ to: opts.toOverride ?? senderId,
56
+ display: `${channel}:${opts.toOverride ?? senderId}`,
57
+ };
58
+ }
59
+ if (opts.toOverride) {
60
+ return {
61
+ error: "Error: cannot infer channel from current source. Please set \`--channel\` together with \`--to\`.",
62
+ };
63
+ }
64
+ if ((ctx.channel ?? "").trim().toLowerCase() === "tool") {
65
+ return {
66
+ error: "Error: cannot infer delivery target in tool context. Provide both \`--channel\` and \`--to\` (or set \`--no-deliver\`).",
67
+ };
68
+ }
69
+ return {
70
+ mode: "announce",
71
+ channel: "last",
72
+ display: "last",
73
+ };
74
+ }
75
+ export function buildStateScopeKey(ctx, delivery) {
76
+ const channel = delivery.channel && delivery.channel !== "last"
77
+ ? delivery.channel
78
+ : (ctx.channel ?? "").trim().toLowerCase() || "unknown";
79
+ const target = (delivery.to ?? ctx.senderId ?? "unknown").trim();
80
+ return `${sanitizeIdPart(channel)}:${sanitizeIdPart(target)}`;
81
+ }
82
+ //# sourceMappingURL=delivery.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delivery.js","sourceRoot":"","sources":["../../../src/research-subscriptions/delivery.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,6 @@
1
+ import type { PluginCommandContext, PluginCommandResult } from "openclaw";
2
+ import type { CronCommandDeps } from "./types.js";
3
+ export declare function createResearchSubscribeHandler(deps: CronCommandDeps): (ctx: PluginCommandContext) => Promise<PluginCommandResult>;
4
+ export declare function createResearchUnsubscribeHandler(deps: CronCommandDeps): (ctx: PluginCommandContext) => Promise<PluginCommandResult>;
5
+ export declare function createResearchSubscriptionsHandler(deps: CronCommandDeps): (ctx: PluginCommandContext) => Promise<PluginCommandResult>;
6
+ //# sourceMappingURL=handlers.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"handlers.d.ts","sourceRoot":"","sources":["../../../src/research-subscriptions/handlers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,mBAAmB,EAAE,MAAM,UAAU,CAAC;AAK1E,OAAO,KAAK,EAAE,eAAe,EAAW,MAAM,YAAY,CAAC;AAE3D,wBAAgB,8BAA8B,CAAC,IAAI,EAAE,eAAe,IACpD,KAAK,oBAAoB,KAAG,OAAO,CAAC,mBAAmB,CAAC,CA0IvE;AAED,wBAAgB,gCAAgC,CAAC,IAAI,EAAE,eAAe,IACtD,KAAK,oBAAoB,KAAG,OAAO,CAAC,mBAAmB,CAAC,CA0CvE;AAED,wBAAgB,kCAAkC,CAAC,IAAI,EAAE,eAAe,IACxD,KAAK,oBAAoB,KAAG,OAAO,CAAC,mBAAmB,CAAC,CAiCvE"}
@@ -0,0 +1,200 @@
1
+ import { buildScopedJobName, buildStateScopeKey, resolveDeliveryTarget } from "./delivery.js";
2
+ import { ensureJobEnabled, listAllJobs, parseJsonFromOutput, runCommand, scheduleText } from "./cron-client.js";
3
+ import { isDurationLike, parseScheduleArgs, parseSubscribeOptions } from "./parse.js";
4
+ import { buildScheduledTaskMessage, formatUsage, withSignature } from "./prompt.js";
5
+ export function createResearchSubscribeHandler(deps) {
6
+ return async (ctx) => {
7
+ const options = parseSubscribeOptions(ctx.args);
8
+ if ("error" in options) {
9
+ return {
10
+ error: options.error,
11
+ text: `${options.error}\n\n${formatUsage()}`,
12
+ };
13
+ }
14
+ const parsed = parseScheduleArgs(options.scheduleTokens);
15
+ if ("error" in parsed) {
16
+ return {
17
+ error: parsed.error,
18
+ text: `${parsed.error}\n\n${formatUsage()}`,
19
+ };
20
+ }
21
+ if (parsed.kind === "at" && !isDurationLike(parsed.when)) {
22
+ const atMs = Date.parse(parsed.when);
23
+ if (!Number.isNaN(atMs) && atMs <= Date.now()) {
24
+ const error = "Error: `at` time is in the past. Use a future ISO datetime (for example `2026-03-04T08:00:00+08:00`) or a relative duration like `at 5m`.";
25
+ return {
26
+ error,
27
+ text: `${error}\n\n${formatUsage()}`,
28
+ };
29
+ }
30
+ }
31
+ const jobName = buildScopedJobName(ctx);
32
+ const delivery = resolveDeliveryTarget(ctx, options);
33
+ if ("error" in delivery) {
34
+ return {
35
+ error: delivery.error,
36
+ text: `${delivery.error}\n\n${formatUsage()}`,
37
+ };
38
+ }
39
+ const stateScopeKey = buildStateScopeKey(ctx, delivery);
40
+ try {
41
+ const jobs = await listAllJobs(deps);
42
+ const existing = jobs.filter((job) => job.name === jobName);
43
+ const addArgs = [
44
+ "openclaw",
45
+ "cron",
46
+ "add",
47
+ "--name",
48
+ jobName,
49
+ "--description",
50
+ "Scientify scheduled job",
51
+ "--session",
52
+ "isolated",
53
+ "--message",
54
+ buildScheduledTaskMessage(options, parsed.kind, stateScopeKey),
55
+ "--timeout-seconds",
56
+ "1800",
57
+ ];
58
+ if (delivery.mode === "none") {
59
+ addArgs.push("--no-deliver");
60
+ }
61
+ else {
62
+ addArgs.push("--announce", "--best-effort-deliver", "--channel", delivery.channel);
63
+ if (delivery.to) {
64
+ addArgs.push("--to", delivery.to);
65
+ }
66
+ }
67
+ if (parsed.kind === "cron") {
68
+ addArgs.push("--cron", parsed.expr, "--tz", parsed.tz);
69
+ }
70
+ else if (parsed.kind === "every") {
71
+ addArgs.push("--every", parsed.duration);
72
+ }
73
+ else {
74
+ addArgs.push("--at", parsed.when, "--delete-after-run");
75
+ }
76
+ addArgs.push("--json");
77
+ const addRes = await runCommand(deps, addArgs, 60_000);
78
+ if (addRes.code !== 0) {
79
+ throw new Error(addRes.stderr || "cron add failed");
80
+ }
81
+ const created = parseJsonFromOutput(addRes.stdout);
82
+ if (!created?.id) {
83
+ throw new Error("cron add did not return job id");
84
+ }
85
+ const createdId = created.id;
86
+ const persisted = await ensureJobEnabled(deps, createdId);
87
+ if (delivery.mode === "announce" && delivery.channel !== "last" && !created.delivery?.to) {
88
+ await runCommand(deps, ["openclaw", "cron", "rm", createdId, "--json"]).catch(() => undefined);
89
+ throw new Error(`cron add created a job without delivery.to for channel "${delivery.channel}". Refusing to keep this job.`);
90
+ }
91
+ const cleanupErrors = [];
92
+ for (const job of existing) {
93
+ const rm = await runCommand(deps, ["openclaw", "cron", "rm", job.id, "--json"]);
94
+ if (rm.code !== 0) {
95
+ cleanupErrors.push(rm.stderr || `failed to remove previous job ${job.id}`);
96
+ }
97
+ }
98
+ const lines = [
99
+ "Created scheduled job successfully.",
100
+ "",
101
+ `- Job ID: \`${createdId}\``,
102
+ `- Name: \`${jobName}\``,
103
+ `- Enabled: \`${persisted?.enabled === false ? "no" : "yes"}\``,
104
+ `- Schedule: \`${parsed.display}\``,
105
+ `- Delivery: \`${delivery.display}\``,
106
+ `- Incremental Scope: \`${stateScopeKey}\``,
107
+ "",
108
+ "Useful commands:",
109
+ `- Run now: \`openclaw cron run ${createdId}\``,
110
+ `- Show runs: \`openclaw cron runs --id ${createdId} --limit 20\``,
111
+ "- Cancel: `/research-unsubscribe`",
112
+ ];
113
+ if (cleanupErrors.length > 0) {
114
+ lines.push(`- Warning: previous job cleanup had ${cleanupErrors.length} error(s).`);
115
+ }
116
+ const message = lines.join("\n");
117
+ return { text: ctx.channel === "tool" ? message : withSignature(message) };
118
+ }
119
+ catch (error) {
120
+ const message = `Error: failed to create scheduled job: ${error instanceof Error ? error.message : String(error)}`;
121
+ deps.logger.warn(`[scientify-cron] subscribe failed: ${error instanceof Error ? error.message : String(error)}`);
122
+ return {
123
+ error: message,
124
+ text: message,
125
+ };
126
+ }
127
+ };
128
+ }
129
+ export function createResearchUnsubscribeHandler(deps) {
130
+ return async (ctx) => {
131
+ const maybeId = (ctx.args ?? "").trim();
132
+ const jobName = buildScopedJobName(ctx);
133
+ try {
134
+ if (maybeId) {
135
+ const rm = await runCommand(deps, ["openclaw", "cron", "rm", maybeId, "--json"]);
136
+ if (rm.code !== 0) {
137
+ throw new Error(rm.stderr || `failed to remove ${maybeId}`);
138
+ }
139
+ return { text: `Removed scheduled job: \`${maybeId}\`` };
140
+ }
141
+ const jobs = await listAllJobs(deps);
142
+ const mine = jobs.filter((job) => job.name === jobName);
143
+ if (mine.length === 0) {
144
+ return {
145
+ text: "No Scientify scheduled jobs found for this scope.",
146
+ };
147
+ }
148
+ for (const job of mine) {
149
+ const rm = await runCommand(deps, ["openclaw", "cron", "rm", job.id, "--json"]);
150
+ if (rm.code !== 0) {
151
+ throw new Error(rm.stderr || `failed to remove ${job.id}`);
152
+ }
153
+ }
154
+ return {
155
+ text: `Canceled Scientify subscription. Removed ${mine.length} job(s).`,
156
+ };
157
+ }
158
+ catch (error) {
159
+ deps.logger.warn(`[scientify-cron] unsubscribe failed: ${error instanceof Error ? error.message : String(error)}`);
160
+ const message = `Error: failed to cancel subscription: ${error instanceof Error ? error.message : String(error)}`;
161
+ return {
162
+ error: message,
163
+ text: message,
164
+ };
165
+ }
166
+ };
167
+ }
168
+ export function createResearchSubscriptionsHandler(deps) {
169
+ return async (ctx) => {
170
+ const jobName = buildScopedJobName(ctx);
171
+ try {
172
+ const jobs = await listAllJobs(deps);
173
+ const mine = jobs.filter((job) => job.name === jobName);
174
+ if (mine.length === 0) {
175
+ return {
176
+ text: "No Scientify scheduled jobs found. Use `/research-subscribe daily 09:00 Asia/Shanghai` to create one.",
177
+ };
178
+ }
179
+ const lines = ["Your Scientify scheduled jobs:", ""];
180
+ for (const job of mine) {
181
+ lines.push(`- ID: \`${job.id}\``);
182
+ lines.push(` enabled: ${job.enabled ? "yes" : "no"}`);
183
+ lines.push(` schedule: \`${scheduleText(job)}\``);
184
+ lines.push(` delivery: \`${job.delivery?.channel ?? "unknown"}${job.delivery?.to ? `:${job.delivery.to}` : ""}\``);
185
+ }
186
+ lines.push("");
187
+ lines.push("Cancel all: `/research-unsubscribe`");
188
+ return { text: lines.join("\n") };
189
+ }
190
+ catch (error) {
191
+ deps.logger.warn(`[scientify-cron] list subscriptions failed: ${error instanceof Error ? error.message : String(error)}`);
192
+ const message = `Error: failed to list scheduled jobs: ${error instanceof Error ? error.message : String(error)}`;
193
+ return {
194
+ error: message,
195
+ text: message,
196
+ };
197
+ }
198
+ };
199
+ }
200
+ //# sourceMappingURL=handlers.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"handlers.js","sourceRoot":"","sources":["../../../src/research-subscriptions/handlers.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,kBAAkB,EAAE,kBAAkB,EAAE,qBAAqB,EAAE,MAAM,eAAe,CAAC;AAC9F,OAAO,EAAE,gBAAgB,EAAE,WAAW,EAAE,mBAAmB,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAChH,OAAO,EAAE,cAAc,EAAE,iBAAiB,EAAE,qBAAqB,EAAE,MAAM,YAAY,CAAC;AACtF,OAAO,EAAE,yBAAyB,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAGpF,MAAM,UAAU,8BAA8B,CAAC,IAAqB;IAClE,OAAO,KAAK,EAAE,GAAyB,EAAgC,EAAE;QACvE,MAAM,OAAO,GAAG,qBAAqB,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;QAChD,IAAI,OAAO,IAAI,OAAO,EAAE,CAAC;YACvB,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,KAAK;gBACpB,IAAI,EAAE,GAAG,OAAO,CAAC,KAAK,OAAO,WAAW,EAAE,EAAE;aAC7C,CAAC;QACJ,CAAC;QAED,MAAM,MAAM,GAAG,iBAAiB,CAAC,OAAO,CAAC,cAAc,CAAC,CAAC;QACzD,IAAI,OAAO,IAAI,MAAM,EAAE,CAAC;YACtB,OAAO;gBACL,KAAK,EAAE,MAAM,CAAC,KAAK;gBACnB,IAAI,EAAE,GAAG,MAAM,CAAC,KAAK,OAAO,WAAW,EAAE,EAAE;aAC5C,CAAC;QACJ,CAAC;QAED,IAAI,MAAM,CAAC,IAAI,KAAK,IAAI,IAAI,CAAC,cAAc,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC;YACzD,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YACrC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,IAAI,IAAI,IAAI,CAAC,GAAG,EAAE,EAAE,CAAC;gBAC9C,MAAM,KAAK,GACT,2IAA2I,CAAC;gBAC9I,OAAO;oBACL,KAAK;oBACL,IAAI,EAAE,GAAG,KAAK,OAAO,WAAW,EAAE,EAAE;iBACrC,CAAC;YACJ,CAAC;QACH,CAAC;QAED,MAAM,OAAO,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAC;QACxC,MAAM,QAAQ,GAAG,qBAAqB,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;QACrD,IAAI,OAAO,IAAI,QAAQ,EAAE,CAAC;YACxB,OAAO;gBACL,KAAK,EAAE,QAAQ,CAAC,KAAK;gBACrB,IAAI,EAAE,GAAG,QAAQ,CAAC,KAAK,OAAO,WAAW,EAAE,EAAE;aAC9C,CAAC;QACJ,CAAC;QACD,MAAM,aAAa,GAAG,kBAAkB,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC;QAExD,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,IAAI,CAAC,CAAC;YACrC,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,OAAO,CAAC,CAAC;YAE5D,MAAM,OAAO,GAAG;gBACd,UAAU;gBACV,MAAM;gBACN,KAAK;gBACL,QAAQ;gBACR,OAAO;gBACP,eAAe;gBACf,yBAAyB;gBACzB,WAAW;gBACX,UAAU;gBACV,WAAW;gBACX,yBAAyB,CAAC,OAAO,EAAE,MAAM,CAAC,IAAI,EAAE,aAAa,CAAC;gBAC9D,mBAAmB;gBACnB,MAAM;aACP,CAAC;YAEF,IAAI,QAAQ,CAAC,IAAI,KAAK,MAAM,EAAE,CAAC;gBAC7B,OAAO,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;YAC/B,CAAC;iBAAM,CAAC;gBACN,OAAO,CAAC,IAAI,CAAC,YAAY,EAAE,uBAAuB,EAAE,WAAW,EAAE,QAAQ,CAAC,OAAO,CAAC,CAAC;gBACnF,IAAI,QAAQ,CAAC,EAAE,EAAE,CAAC;oBAChB,OAAO,CAAC,IAAI,CAAC,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,CAAC;gBACpC,CAAC;YACH,CAAC;YAED,IAAI,MAAM,CAAC,IAAI,KAAK,MAAM,EAAE,CAAC;gBAC3B,OAAO,CAAC,IAAI,CAAC,QAAQ,EAAE,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,CAAC,CAAC;YACzD,CAAC;iBAAM,IAAI,MAAM,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;gBACnC,OAAO,CAAC,IAAI,CAAC,SAAS,EAAE,MAAM,CAAC,QAAQ,CAAC,CAAC;YAC3C,CAAC;iBAAM,CAAC;gBACN,OAAO,CAAC,IAAI,CAAC,MAAM,EAAE,MAAM,CAAC,IAAI,EAAE,oBAAoB,CAAC,CAAC;YAC1D,CAAC;YAED,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;YAEvB,MAAM,MAAM,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,OAAO,EAAE,MAAM,CAAC,CAAC;YACvD,IAAI,MAAM,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;gBACtB,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,MAAM,IAAI,iBAAiB,CAAC,CAAC;YACtD,CAAC;YAED,MAAM,OAAO,GAAG,mBAAmB,CAAU,MAAM,CAAC,MAAM,CAAC,CAAC;YAC5D,IAAI,CAAC,OAAO,EAAE,EAAE,EAAE,CAAC;gBACjB,MAAM,IAAI,KAAK,CAAC,gCAAgC,CAAC,CAAC;YACpD,CAAC;YACD,MAAM,SAAS,GAAG,OAAO,CAAC,EAAE,CAAC;YAE7B,MAAM,SAAS,GAAG,MAAM,gBAAgB,CAAC,IAAI,EAAE,SAAS,CAAC,CAAC;YAE1D,IAAI,QAAQ,CAAC,IAAI,KAAK,UAAU,IAAI,QAAQ,CAAC,OAAO,KAAK,MAAM,IAAI,CAAC,OAAO,CAAC,QAAQ,EAAE,EAAE,EAAE,CAAC;gBACzF,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;gBAC/F,MAAM,IAAI,KAAK,CACb,2DAA2D,QAAQ,CAAC,OAAO,+BAA+B,CAC3G,CAAC;YACJ,CAAC;YAED,MAAM,aAAa,GAAa,EAAE,CAAC;YACnC,KAAK,MAAM,GAAG,IAAI,QAAQ,EAAE,CAAC;gBAC3B,MAAM,EAAE,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC,CAAC;gBAChF,IAAI,EAAE,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;oBAClB,aAAa,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,IAAI,iCAAiC,GAAG,CAAC,EAAE,EAAE,CAAC,CAAC;gBAC7E,CAAC;YACH,CAAC;YAED,MAAM,KAAK,GAAG;gBACZ,qCAAqC;gBACrC,EAAE;gBACF,eAAe,SAAS,IAAI;gBAC5B,aAAa,OAAO,IAAI;gBACxB,gBAAgB,SAAS,EAAE,OAAO,KAAK,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,IAAI;gBAC/D,iBAAiB,MAAM,CAAC,OAAO,IAAI;gBACnC,iBAAiB,QAAQ,CAAC,OAAO,IAAI;gBACrC,0BAA0B,aAAa,IAAI;gBAC3C,EAAE;gBACF,kBAAkB;gBAClB,kCAAkC,SAAS,IAAI;gBAC/C,0CAA0C,SAAS,eAAe;gBAClE,mCAAmC;aACpC,CAAC;YACF,IAAI,aAAa,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBAC7B,KAAK,CAAC,IAAI,CAAC,uCAAuC,aAAa,CAAC,MAAM,YAAY,CAAC,CAAC;YACtF,CAAC;YAED,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACjC,OAAO,EAAE,IAAI,EAAE,GAAG,CAAC,OAAO,KAAK,MAAM,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,aAAa,CAAC,OAAO,CAAC,EAAE,CAAC;QAC7E,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,OAAO,GAAG,0CAA0C,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;YACnH,IAAI,CAAC,MAAM,CAAC,IAAI,CACd,sCAAsC,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAC/F,CAAC;YACF,OAAO;gBACL,KAAK,EAAE,OAAO;gBACd,IAAI,EAAE,OAAO;aACd,CAAC;QACJ,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,gCAAgC,CAAC,IAAqB;IACpE,OAAO,KAAK,EAAE,GAAyB,EAAgC,EAAE;QACvE,MAAM,OAAO,GAAG,CAAC,GAAG,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;QACxC,MAAM,OAAO,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAC;QAExC,IAAI,CAAC;YACH,IAAI,OAAO,EAAE,CAAC;gBACZ,MAAM,EAAE,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC,CAAC;gBACjF,IAAI,EAAE,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;oBAClB,MAAM,IAAI,KAAK,CAAC,EAAE,CAAC,MAAM,IAAI,oBAAoB,OAAO,EAAE,CAAC,CAAC;gBAC9D,CAAC;gBACD,OAAO,EAAE,IAAI,EAAE,4BAA4B,OAAO,IAAI,EAAE,CAAC;YAC3D,CAAC;YAED,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,IAAI,CAAC,CAAC;YACrC,MAAM,IAAI,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,OAAO,CAAC,CAAC;YACxD,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBACtB,OAAO;oBACL,IAAI,EAAE,mDAAmD;iBAC1D,CAAC;YACJ,CAAC;YAED,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;gBACvB,MAAM,EAAE,GAAG,MAAM,UAAU,CAAC,IAAI,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC,CAAC;gBAChF,IAAI,EAAE,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;oBAClB,MAAM,IAAI,KAAK,CAAC,EAAE,CAAC,MAAM,IAAI,oBAAoB,GAAG,CAAC,EAAE,EAAE,CAAC,CAAC;gBAC7D,CAAC;YACH,CAAC;YAED,OAAO;gBACL,IAAI,EAAE,4CAA4C,IAAI,CAAC,MAAM,UAAU;aACxE,CAAC;QACJ,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,MAAM,CAAC,IAAI,CACd,wCAAwC,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CACjG,CAAC;YACF,MAAM,OAAO,GAAG,yCAAyC,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;YAClH,OAAO;gBACL,KAAK,EAAE,OAAO;gBACd,IAAI,EAAE,OAAO;aACd,CAAC;QACJ,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,kCAAkC,CAAC,IAAqB;IACtE,OAAO,KAAK,EAAE,GAAyB,EAAgC,EAAE;QACvE,MAAM,OAAO,GAAG,kBAAkB,CAAC,GAAG,CAAC,CAAC;QACxC,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,WAAW,CAAC,IAAI,CAAC,CAAC;YACrC,MAAM,IAAI,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,OAAO,CAAC,CAAC;YACxD,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBACtB,OAAO;oBACL,IAAI,EAAE,uGAAuG;iBAC9G,CAAC;YACJ,CAAC;YAED,MAAM,KAAK,GAAG,CAAC,gCAAgC,EAAE,EAAE,CAAC,CAAC;YACrD,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;gBACvB,KAAK,CAAC,IAAI,CAAC,WAAW,GAAG,CAAC,EAAE,IAAI,CAAC,CAAC;gBAClC,KAAK,CAAC,IAAI,CAAC,cAAc,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC;gBACvD,KAAK,CAAC,IAAI,CAAC,iBAAiB,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;gBACnD,KAAK,CAAC,IAAI,CAAC,iBAAiB,GAAG,CAAC,QAAQ,EAAE,OAAO,IAAI,SAAS,GAAG,GAAG,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC;YACtH,CAAC;YACD,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YACf,KAAK,CAAC,IAAI,CAAC,qCAAqC,CAAC,CAAC;YAElD,OAAO,EAAE,IAAI,EAAE,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QACpC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,MAAM,CAAC,IAAI,CACd,+CAA+C,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CACxG,CAAC;YACF,MAAM,OAAO,GAAG,yCAAyC,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;YAClH,OAAO;gBACL,KAAK,EAAE,OAAO;gBACd,IAAI,EAAE,OAAO;aACd,CAAC;QACJ,CAAC;IACH,CAAC,CAAC;AACJ,CAAC"}
@@ -0,0 +1,11 @@
1
+ import type { ScheduleSpec, ScoreWeights, SubscriptionOptions } from "./types.js";
2
+ export declare function isDurationLike(raw: string): boolean;
3
+ export declare function resolveCandidatePool(candidatePool: number | undefined, maxPapers: number): number;
4
+ export declare function formatScoreWeights(weights: ScoreWeights): string;
5
+ export declare function parseScheduleArgs(tokens: string[]): ScheduleSpec | {
6
+ error: string;
7
+ };
8
+ export declare function parseSubscribeOptions(rawArgs: string | undefined): SubscriptionOptions | {
9
+ error: string;
10
+ };
11
+ //# sourceMappingURL=parse.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"parse.d.ts","sourceRoot":"","sources":["../../../src/research-subscriptions/parse.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,YAAY,EAAE,YAAY,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AA0ElF,wBAAgB,cAAc,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAEnD;AA8FD,wBAAgB,oBAAoB,CAAC,aAAa,EAAE,MAAM,GAAG,SAAS,EAAE,SAAS,EAAE,MAAM,GAAG,MAAM,CAIjG;AAED,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,YAAY,GAAG,MAAM,CAQhE;AAuCD,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,YAAY,GAAG;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CAmJpF;AAED,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,MAAM,GAAG,SAAS,GAAG,mBAAmB,GAAG;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CAsK1G"}