@doist/todoist-ai 8.8.4 → 8.8.6

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.
@@ -1,4 +1,4 @@
1
- import { colors as $e, LOCATION_TRIGGERS as lt, REMINDER_TYPES as _t, createCommand as z, REMINDER_DELIVERY_SERVICES as Nt, HEALTH_STATUSES as Ue, getTaskUrl as ut, getProjectUrl as pt, WORKSPACE_ROLES as Lt, WORKSPACE_PLANS as Mt, TodoistApi as Ft } from "@doist/todoist-sdk";
1
+ import { isWorkspaceProject as ue, isPersonalProject as re, colors as De, LOCATION_TRIGGERS as lt, REMINDER_TYPES as Ut, createCommand as z, REMINDER_DELIVERY_SERVICES as Nt, HEALTH_STATUSES as Re, getTaskUrl as ut, getProjectUrl as pt, WORKSPACE_ROLES as Lt, WORKSPACE_PLANS as Mt, TodoistApi as Ft } from "@doist/todoist-sdk";
2
2
  import { McpServer as Ht } from "@modelcontextprotocol/sdk/server/mcp.js";
3
3
  import { createHash as Wt } from "node:crypto";
4
4
  import { readFileSync as Bt } from "node:fs";
@@ -6,7 +6,7 @@ import { dirname as zt, join as Ve } from "node:path";
6
6
  import { fileURLToPath as Yt } from "node:url";
7
7
  import { registerAppResource as Gt, RESOURCE_MIME_TYPE as qt, registerAppTool as Kt } from "@modelcontextprotocol/ext-apps/server";
8
8
  import J, { ZodError as Vt, z as s } from "zod";
9
- import { addDays as De, formatISO as Je } from "date-fns";
9
+ import { addDays as xe, formatISO as Je } from "date-fns";
10
10
  const Xe = zt(Yt(import.meta.url)), Jt = [
11
11
  Ve(Xe, "task-list", "index.html"),
12
12
  Ve(Xe, "mcp-apps", "index.html")
@@ -26,7 +26,7 @@ function Zt() {
26
26
  }
27
27
  return console.error("Failed to load task list app HTML from any known path:", e), Xt;
28
28
  }
29
- const mt = Zt(), Qt = Wt("sha256").update(mt).digest("hex").slice(0, 12), xe = `ui://todoist/task-list@${Qt}`, ht = "Interactive task list widget", es = "https://ai.todoist.net", Ze = {
29
+ const mt = Zt(), Qt = Wt("sha256").update(mt).digest("hex").slice(0, 12), Ae = `ui://todoist/task-list@${Qt}`, ht = "Interactive task list widget", es = "https://ai.todoist.net", Ze = {
30
30
  ui: {
31
31
  prefersBorder: !0,
32
32
  csp: {
@@ -47,7 +47,7 @@ function ts(e) {
47
47
  Gt(
48
48
  e,
49
49
  "todoist-task-list",
50
- xe,
50
+ Ae,
51
51
  {
52
52
  description: ht,
53
53
  _meta: Ze
@@ -55,7 +55,7 @@ function ts(e) {
55
55
  async () => ({
56
56
  contents: [
57
57
  {
58
- uri: xe,
58
+ uri: Ae,
59
59
  mimeType: qt,
60
60
  text: mt,
61
61
  _meta: Ze
@@ -67,10 +67,10 @@ function ts(e) {
67
67
  function Y(e) {
68
68
  return typeof e == "object" && e !== null;
69
69
  }
70
- function Ae(...e) {
70
+ function Ee(...e) {
71
71
  return e.find(Y);
72
72
  }
73
- function _(...e) {
73
+ function U(...e) {
74
74
  return e.find((t) => t !== void 0);
75
75
  }
76
76
  function E(e) {
@@ -105,7 +105,7 @@ function Qe(e) {
105
105
  const t = e.trim();
106
106
  return /\bHTTP\s*\d{3}\b/i.test(t) || /\bstatus code \d{3}\b/i.test(t) || /^bad request$/i.test(t) || /^unauthorized$/i.test(t) || /^forbidden$/i.test(t) || /^not found$/i.test(t);
107
107
  }
108
- function Ie(e) {
108
+ function ve(e) {
109
109
  if (!e)
110
110
  return;
111
111
  const t = e.match(/\b(?:HTTP|status code)\s*[:#-]?\s*(\d{3})\b/i);
@@ -122,7 +122,7 @@ function W(e) {
122
122
  }
123
123
  if (!Y(e))
124
124
  return;
125
- const r = _(
125
+ const r = U(
126
126
  y(e.detail),
127
127
  y(e.details),
128
128
  y(e.message),
@@ -144,21 +144,21 @@ function rs(e) {
144
144
  return [];
145
145
  const t = /* @__PURE__ */ new Set(), r = (i) => {
146
146
  i && t.add(P(i, 120));
147
- }, o = _(
147
+ }, o = U(
148
148
  y(e.field),
149
149
  y(e.parameter),
150
150
  y(e.param),
151
151
  y(e.path)
152
152
  );
153
153
  r(o);
154
- const n = Ae(
154
+ const n = Ee(
155
155
  e.details,
156
156
  e.errorDetails,
157
157
  e.errorExtra,
158
158
  e.error_extra
159
159
  );
160
160
  if (n) {
161
- const i = _(
161
+ const i = U(
162
162
  y(n.field),
163
163
  y(n.parameter),
164
164
  y(n.param),
@@ -174,13 +174,13 @@ function rs(e) {
174
174
  r(y(i));
175
175
  continue;
176
176
  }
177
- const c = _(
177
+ const c = U(
178
178
  y(i.field),
179
179
  y(i.parameter),
180
180
  y(i.param),
181
181
  y(i.path),
182
182
  y(i.name)
183
- ), d = _(
183
+ ), d = U(
184
184
  y(i.message),
185
185
  y(i.error),
186
186
  y(i.detail),
@@ -220,13 +220,13 @@ function as(e, t) {
220
220
  return e === 401 || e === 403 ? "Verify your API token and access permissions, then retry." : e === 404 ? "Confirm the referenced IDs exist and are accessible, then retry." : e === 429 ? "Rate limit reached. Wait briefly and retry." : e !== void 0 && e >= 500 ? "Todoist API may be temporarily unavailable. Retry shortly." : t ? "Fix the field hints above and retry." : e === 400 || e === 422 ? "Check parameter values and formats, then retry." : "Check the request parameters and retry.";
221
221
  }
222
222
  function is(e) {
223
- const t = Y(e) ? e : void 0, r = e instanceof Error && Y(e.cause) ? e.cause : void 0, o = Ae(t?.response, r?.response), n = Ae(
223
+ const t = Y(e) ? e : void 0, r = e instanceof Error && Y(e.cause) ? e.cause : void 0, o = Ee(t?.response, r?.response), n = Ee(
224
224
  t?.responseData,
225
225
  o?.data,
226
226
  t?.data,
227
227
  r?.responseData,
228
228
  r?.data
229
- ), a = _(
229
+ ), a = U(
230
230
  E(t?.httpStatusCode),
231
231
  E(t?.statusCode),
232
232
  E(t?.status),
@@ -236,17 +236,17 @@ function is(e) {
236
236
  E(n?.status),
237
237
  E(n?.httpCode),
238
238
  E(n?.http_code),
239
- Ie(y(t?.message)),
240
- Ie(y(r?.message)),
241
- Ie(typeof e == "string" ? e : void 0)
242
- ), i = _(
239
+ ve(y(t?.message)),
240
+ ve(y(r?.message)),
241
+ ve(typeof e == "string" ? e : void 0)
242
+ ), i = U(
243
243
  X(n?.errorCode),
244
244
  X(n?.error_code),
245
245
  X(n?.code),
246
246
  X(t?.errorCode),
247
247
  X(t?.error_code),
248
248
  X(t?.code)
249
- ), c = _(
249
+ ), c = U(
250
250
  y(n?.errorTag),
251
251
  y(n?.error_tag),
252
252
  y(n?.tag),
@@ -260,7 +260,7 @@ function is(e) {
260
260
  y(t?.message),
261
261
  y(r?.message),
262
262
  e instanceof Error ? e.message : y(e)
263
- ].filter((h) => !!h), l = d.find((h) => !Qe(h)) || d[0], u = _(
263
+ ].filter((h) => !!h), l = d.find((h) => !Qe(h)) || d[0], u = U(
264
264
  W(n?.errorExtra),
265
265
  W(n?.error_extra),
266
266
  W(n?.details),
@@ -343,16 +343,16 @@ async function ks(e, t = {}) {
343
343
  }
344
344
  throw a;
345
345
  }
346
- function Ee(e) {
346
+ function Oe(e) {
347
347
  if (e == null)
348
348
  return e;
349
349
  if (Array.isArray(e))
350
- return e.map((t) => Ee(t));
350
+ return e.map((t) => Oe(t));
351
351
  if (typeof e == "object") {
352
352
  const t = {};
353
353
  for (const [r, o] of Object.entries(e))
354
354
  if (o !== null) {
355
- const n = Ee(o);
355
+ const n = Oe(o);
356
356
  if (n !== null && typeof n == "object" && !Array.isArray(n) && Object.keys(n).length === 0)
357
357
  continue;
358
358
  t[r] = n;
@@ -420,7 +420,7 @@ const f = {
420
420
  // OpenAI MCP tools
421
421
  SEARCH: "search",
422
422
  FETCH: "fetch"
423
- }, Ri = {
423
+ }, _i = {
424
424
  /**
425
425
  * Strips email addresses from tool outputs that expose user data.
426
426
  * Affects: find-project-collaborators, find-completed-tasks
@@ -432,12 +432,11 @@ function ws({
432
432
  structuredContent: t,
433
433
  contentItems: r
434
434
  }) {
435
- const o = Ee(t), n = {}, a = [];
435
+ const o = Oe(t), n = {}, a = [];
436
436
  if (e && a.push({ type: "text", text: e }), r && a.push(...r), a.length > 0 && (n.content = a), t && (n.structuredContent = o), !Ts && t) {
437
437
  const i = JSON.stringify(o);
438
438
  n.content || (n.content = []), n.content.push({
439
439
  type: "text",
440
- mimeType: "application/json",
441
440
  text: i
442
441
  });
443
442
  }
@@ -465,15 +464,15 @@ const Cs = [
465
464
  f.FIND_PROJECT_COLLABORATORS,
466
465
  f.FIND_COMPLETED_TASKS
467
466
  ];
468
- function Oe(e) {
467
+ function Pe(e) {
469
468
  if (e == null)
470
469
  return e;
471
470
  if (Array.isArray(e))
472
- return e.map((t) => Oe(t));
471
+ return e.map((t) => Pe(t));
473
472
  if (typeof e == "object") {
474
473
  const t = {};
475
474
  for (const [r, o] of Object.entries(e))
476
- r !== "email" && (t[r] = Oe(o));
475
+ r !== "email" && (t[r] = Pe(o));
477
476
  return t;
478
477
  }
479
478
  return e;
@@ -493,7 +492,7 @@ function k({
493
492
  let { textContent: l, structuredContent: u, contentItems: p } = await ks(
494
493
  () => e.execute(c, r)
495
494
  );
496
- return n && (l && (l = $s(l)), u && (u = Oe(u))), ws({ textContent: l, structuredContent: u, contentItems: p });
495
+ return n && (l && (l = $s(l)), u && (u = Pe(u))), ws({ textContent: l, structuredContent: u, contentItems: p });
497
496
  } catch (l) {
498
497
  return console.error(`Error executing tool ${e.name}:`, { args: c, error: l }), Is(ls(l));
499
498
  }
@@ -685,7 +684,7 @@ const ie = {
685
684
  LABELS_DEFAULT: 50,
686
685
  /** Maximum limit for label listings */
687
686
  LABELS_MAX: 200
688
- }, ve = {
687
+ }, je = {
689
688
  /** Maximum number of failures to show in detailed error messages */
690
689
  MAX_FAILURES_SHOWN: 3
691
690
  };
@@ -733,14 +732,14 @@ function Ps(e) {
733
732
  const t = Math.floor(e / 60), r = e % 60;
734
733
  return t === 0 ? `${r}m` : r === 0 ? `${t}h` : `${t}h${r}m`;
735
734
  }
736
- const Rs = ["p1", "p2", "p3", "p4"], _e = 'Task priority as a string: "p1" (highest), "p2" (high), "p3" (medium), or "p4" (lowest/default). Integers like 1, 2, 3, or 4 are not accepted.', Ne = s.enum(Rs).describe(_e);
735
+ const _s = ["p1", "p2", "p3", "p4"], Ue = 'Task priority as a string: "p1" (highest), "p2" (high), "p3" (medium), or "p4" (lowest/default). Integers like 1, 2, 3, or 4 are not accepted.', Ne = s.enum(_s).describe(Ue);
737
736
  function bt(e) {
738
737
  return { p1: 4, p2: 3, p3: 2, p4: 1 }[e];
739
738
  }
740
- function Us(e) {
739
+ function Rs(e) {
741
740
  return { 4: "p1", 3: "p2", 2: "p3", 1: "p4" }[e];
742
741
  }
743
- const A = /* @__PURE__ */ new Map(), Z = /* @__PURE__ */ new Map(), je = 300 * 1e3, _s = "me";
742
+ const A = /* @__PURE__ */ new Map(), Z = /* @__PURE__ */ new Map(), Se = 300 * 1e3, Us = "me";
744
743
  class Ns {
745
744
  /**
746
745
  * Resolve a user name or ID to a user ID by looking up collaborators across all shared projects.
@@ -750,9 +749,9 @@ class Ns {
750
749
  if (!r || r.trim().length === 0)
751
750
  return null;
752
751
  const o = r.trim(), n = A.get(o);
753
- if (n && Date.now() - n.timestamp < je)
752
+ if (n && Date.now() - n.timestamp < Se)
754
753
  return n.result;
755
- if (o.toLowerCase() === _s)
754
+ if (o.toLowerCase() === Us)
756
755
  try {
757
756
  const a = await t.getUser();
758
757
  return {
@@ -826,7 +825,7 @@ class Ns {
826
825
  */
827
826
  async getProjectCollaborators(t, r) {
828
827
  const o = `project_${r}`, n = Z.get(o);
829
- if (n && Date.now() - n.timestamp < je)
828
+ if (n && Date.now() - n.timestamp < Se)
830
829
  return n.result;
831
830
  try {
832
831
  const a = await t.getProjectCollaborators(r), c = (Array.isArray(a) ? a : a.results || []).filter((d) => d?.id && d.name && d.email);
@@ -843,7 +842,7 @@ class Ns {
843
842
  */
844
843
  async getAllCollaborators(t) {
845
844
  const r = "all_collaborators", o = Z.get(r);
846
- if (o && Date.now() - o.timestamp < je)
845
+ if (o && Date.now() - o.timestamp < Se)
847
846
  return o.result;
848
847
  try {
849
848
  const { results: n } = await t.getProjects({}), a = n.filter((u) => u.isShared);
@@ -906,12 +905,6 @@ function Ms({
906
905
  }) {
907
906
  return t ? e.filter((n) => n.responsibleUid === t) : o === "unassignedOrMe" ? e.filter((n) => !n.responsibleUid || n.responsibleUid === r) : o === "assigned" ? e.filter((n) => n.responsibleUid && n.responsibleUid !== r) : e;
908
907
  }
909
- function re(e) {
910
- return "inboxProject" in e;
911
- }
912
- function Pe(e) {
913
- return "workspaceId" in e;
914
- }
915
908
  function de(e) {
916
909
  return e?.toLowerCase() === "inbox";
917
910
  }
@@ -984,7 +977,7 @@ function Bs(e, t, r, o) {
984
977
  if (o) return { parentId: o };
985
978
  throw new Error("Unexpected error: No valid move parameter found");
986
979
  }
987
- function R(e) {
980
+ function _(e) {
988
981
  return {
989
982
  id: e.id,
990
983
  content: e.content,
@@ -992,7 +985,7 @@ function R(e) {
992
985
  dueDate: e.due?.date,
993
986
  recurring: e.due?.isRecurring && e.due.string ? e.due.string : !1,
994
987
  deadlineDate: e.deadline?.date,
995
- priority: Us(e.priority) ?? "p4",
988
+ priority: Rs(e.priority) ?? "p4",
996
989
  projectId: e.projectId,
997
990
  sectionId: e.sectionId ?? void 0,
998
991
  parentId: e.parentId ?? void 0,
@@ -1014,12 +1007,12 @@ function q(e) {
1014
1007
  parentId: re(e) ? e.parentId ?? void 0 : void 0,
1015
1008
  inboxProject: re(e) ? e.inboxProject ?? !1 : !1,
1016
1009
  viewStyle: e.viewStyle,
1017
- workspaceId: Pe(e) ? e.workspaceId : void 0,
1018
- folderId: Pe(e) ? e.folderId ?? void 0 : void 0,
1010
+ workspaceId: ue(e) ? e.workspaceId : void 0,
1011
+ folderId: ue(e) ? e.folderId ?? void 0 : void 0,
1019
1012
  childOrder: e.childOrder
1020
1013
  };
1021
1014
  }
1022
- function pe(e) {
1015
+ function me(e) {
1023
1016
  return {
1024
1017
  id: e.id,
1025
1018
  taskId: e.taskId ?? void 0,
@@ -1072,7 +1065,7 @@ async function Fe({
1072
1065
  }) {
1073
1066
  try {
1074
1067
  const { results: n, nextCursor: a } = await e.getTasksByFilter({ query: t, cursor: o, limit: r });
1075
- return { tasks: n.map(R), nextCursor: a };
1068
+ return { tasks: n.map(_), nextCursor: a };
1076
1069
  } catch (n) {
1077
1070
  const a = Ys.safeParse(n);
1078
1071
  if (!a.success)
@@ -1129,15 +1122,15 @@ function Tt(e) {
1129
1122
  ).length, r = e.filter((o) => o.type === "location").length;
1130
1123
  return { timeBasedCount: t, locationCount: r };
1131
1124
  }
1132
- const me = $e.map((e) => e.key);
1125
+ const he = De.map((e) => e.key);
1133
1126
  function Gs(e) {
1134
1127
  if (typeof e != "string") return;
1135
1128
  const t = e.toLowerCase();
1136
- return ($e.find((o) => o.key === t) ?? $e.find((o) => o.displayName.toLowerCase() === t))?.key;
1129
+ return (De.find((o) => o.key === t) ?? De.find((o) => o.displayName.toLowerCase() === t))?.key;
1137
1130
  }
1138
- const qs = `Color for the entity. Accepts a color key (e.g. "berry_red") or display name (e.g. "Berry Red"). Valid colors: ${me.join(", ")}. Unrecognized colors are omitted and charcoal will be used as the default.`, le = s.preprocess(Gs, s.enum(me).optional()).describe(qs);
1139
- s.enum(me).describe("The color key of the entity.");
1140
- const ne = s.enum(me).optional().catch(void 0).describe("The color key of the entity."), K = s.object({
1131
+ const qs = `Color for the entity. Accepts a color key (e.g. "berry_red") or display name (e.g. "Berry Red"). Valid colors: ${he.join(", ")}. Unrecognized colors are omitted and charcoal will be used as the default.`, le = s.preprocess(Gs, s.enum(he).optional()).describe(qs);
1132
+ s.enum(he).describe("The color key of the entity.");
1133
+ const ne = s.enum(he).optional().catch(void 0).describe("The color key of the entity."), K = s.object({
1141
1134
  id: s.string().describe("The unique ID of the task."),
1142
1135
  content: s.string().describe("The task title/content."),
1143
1136
  description: s.string().describe("The task description."),
@@ -1171,7 +1164,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1171
1164
  ),
1172
1165
  folderId: s.string().optional().describe("The ID of the folder this project belongs to (workspace projects only)."),
1173
1166
  childOrder: s.number().describe("The ordering index of the project among its siblings.")
1174
- }), he = s.object({
1167
+ }), fe = s.object({
1175
1168
  id: s.string().describe("The unique ID of the section."),
1176
1169
  name: s.string().describe("The name of the section.")
1177
1170
  }), Ks = s.object({
@@ -1187,7 +1180,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1187
1180
  image: s.string().optional().describe("The image URL for image resource types."),
1188
1181
  imageWidth: s.number().optional().describe("The width of the image in pixels."),
1189
1182
  imageHeight: s.number().optional().describe("The height of the image in pixels.")
1190
- }), fe = s.object({
1183
+ }), be = s.object({
1191
1184
  id: s.string().describe("The unique ID of the comment."),
1192
1185
  taskId: s.string().optional().describe("The ID of the task this comment belongs to."),
1193
1186
  projectId: s.string().optional().describe("The ID of the project this comment belongs to."),
@@ -1209,7 +1202,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1209
1202
  id: s.string().describe("The unique ID of the user."),
1210
1203
  name: s.string().describe("The full name of the user."),
1211
1204
  email: s.string().describe("The email address of the user.")
1212
- }), be = s.object({
1205
+ }), ge = s.object({
1213
1206
  id: s.string().describe("The unique ID of the label."),
1214
1207
  name: s.string().describe("The name of the label."),
1215
1208
  color: ne,
@@ -1224,7 +1217,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1224
1217
  }), He = s.object({
1225
1218
  id: s.string().describe("The unique ID of the reminder."),
1226
1219
  taskId: s.string().describe("The task ID this reminder belongs to."),
1227
- type: s.enum(_t).describe("The type of reminder: relative, absolute, or location."),
1220
+ type: s.enum(Ut).describe("The type of reminder: relative, absolute, or location."),
1228
1221
  minuteOffset: s.number().optional().describe("Minutes before due time to trigger (relative reminders only)."),
1229
1222
  due: Xs.optional().describe(
1230
1223
  "Due date info (absolute and sometimes relative reminders)."
@@ -1248,7 +1241,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1248
1241
  }), Qs = {
1249
1242
  comments: s.array(Zs).min(1).describe("The array of comments to add.")
1250
1243
  }, er = {
1251
- comments: s.array(fe).describe("The created comments."),
1244
+ comments: s.array(be).describe("The created comments."),
1252
1245
  totalCount: s.number().describe("The total number of comments created."),
1253
1246
  addedCommentIds: s.array(s.string()).describe("The IDs of the added comments.")
1254
1247
  }, tr = {
@@ -1279,7 +1272,7 @@ const ne = s.enum(me).optional().catch(void 0).describe("The color key of the en
1279
1272
  content: l,
1280
1273
  ...u ? { taskId: u } : { projectId: m }
1281
1274
  });
1282
- }), c = (await Promise.all(a)).map(pe);
1275
+ }), c = (await Promise.all(a)).map(me);
1283
1276
  return {
1284
1277
  textContent: sr({ comments: c }),
1285
1278
  structuredContent: {
@@ -1426,7 +1419,7 @@ ${l}`,
1426
1419
  }), pr = {
1427
1420
  labels: s.array(ur).min(1).describe("The array of labels to add.")
1428
1421
  }, mr = {
1429
- labels: s.array(be).describe("The created labels."),
1422
+ labels: s.array(ge).describe("The created labels."),
1430
1423
  totalCount: s.number().describe("The total number of labels created.")
1431
1424
  }, hr = {
1432
1425
  name: f.ADD_LABELS,
@@ -1439,7 +1432,7 @@ ${l}`,
1439
1432
  return {
1440
1433
  textContent: fr({ labels: r }),
1441
1434
  structuredContent: {
1442
- labels: r.map((n) => be.parse(n)),
1435
+ labels: r.map((n) => ge.parse(n)),
1443
1436
  totalCount: r.length
1444
1437
  }
1445
1438
  };
@@ -1560,29 +1553,29 @@ function vr({ projects: e }) {
1560
1553
  return `Added ${t} project${t === 1 ? "" : "s"}:
1561
1554
  ${r}`;
1562
1555
  }
1563
- const ue = 25, ge = s.enum(Nt), It = s.object({
1556
+ const pe = 25, ye = s.enum(Nt), It = s.object({
1564
1557
  date: s.string().optional().describe("Due date in YYYY-MM-DD format."),
1565
1558
  string: s.string().optional().describe('Natural language due string, e.g. "tomorrow at 3pm".'),
1566
1559
  timezone: s.string().optional().describe('Timezone for the reminder, e.g. "America/New_York".'),
1567
1560
  lang: s.string().optional().describe('Language for parsing the due string, e.g. "en".')
1568
- }), vt = s.enum(lt), ye = s.boolean().optional().describe("Whether this is an urgent reminder. Applies to relative and absolute reminders."), jr = s.object({
1561
+ }), vt = s.enum(lt), ke = s.boolean().optional().describe("Whether this is an urgent reminder. Applies to relative and absolute reminders."), jr = s.object({
1569
1562
  type: s.literal("relative"),
1570
1563
  taskId: s.string().min(1).describe("The ID of the task to set a reminder for."),
1571
1564
  minuteOffset: s.number().int().min(0).describe(
1572
1565
  "Minutes before the task due time to trigger the reminder. E.g., 30 for 30 minutes before, 60 for 1 hour before, 1440 for 1 day before."
1573
1566
  ),
1574
- service: ge.optional().describe(
1567
+ service: ye.optional().describe(
1575
1568
  'Delivery method: "email" or "push" notification. Defaults to push.'
1576
1569
  ),
1577
- isUrgent: ye
1570
+ isUrgent: ke
1578
1571
  }), Sr = s.object({
1579
1572
  type: s.literal("absolute"),
1580
1573
  taskId: s.string().min(1).describe("The ID of the task to set a reminder for."),
1581
1574
  due: It.describe("The specific date/time for the reminder."),
1582
- service: ge.optional().describe(
1575
+ service: ye.optional().describe(
1583
1576
  'Delivery method: "email" or "push" notification. Defaults to push.'
1584
1577
  ),
1585
- isUrgent: ye
1578
+ isUrgent: ke
1586
1579
  }), Cr = s.object({
1587
1580
  type: s.literal("location"),
1588
1581
  taskId: s.string().min(1).describe("The ID of the task to set a reminder for."),
@@ -1598,8 +1591,8 @@ const ue = 25, ge = s.enum(Nt), It = s.object({
1598
1591
  Sr,
1599
1592
  Cr
1600
1593
  ]), Dr = {
1601
- reminders: s.array($r).min(1).max(ue).describe(
1602
- `Array of reminders to create (max ${ue}). Each reminder must specify a type: "relative" (minutes before due), "absolute" (specific date/time), or "location" (geofence trigger).`
1594
+ reminders: s.array($r).min(1).max(pe).describe(
1595
+ `Array of reminders to create (max ${pe}). Each reminder must specify a type: "relative" (minutes before due), "absolute" (specific date/time), or "location" (geofence trigger).`
1603
1596
  )
1604
1597
  }, xr = {
1605
1598
  reminders: s.array(He).describe("The created reminders."),
@@ -1670,14 +1663,14 @@ const Or = s.object({
1670
1663
  )
1671
1664
  }), Pr = {
1672
1665
  sections: s.array(Or).min(1).describe("The array of sections to add.")
1673
- }, Rr = {
1674
- sections: s.array(he).describe("The created sections."),
1666
+ }, _r = {
1667
+ sections: s.array(fe).describe("The created sections."),
1675
1668
  totalCount: s.number().describe("The total number of sections created.")
1676
- }, Ur = {
1669
+ }, Rr = {
1677
1670
  name: f.ADD_SECTIONS,
1678
1671
  description: "Add one or more new sections to projects.",
1679
1672
  parameters: Pr,
1680
- outputSchema: Rr,
1673
+ outputSchema: _r,
1681
1674
  annotations: { readOnlyHint: !1, destructiveHint: !1, idempotentHint: !1 },
1682
1675
  async execute({ sections: e }, t) {
1683
1676
  const o = e.some((c) => de(c.projectId)) ? await t.getUser() : void 0, n = await Promise.all(
@@ -1693,7 +1686,7 @@ const Or = s.object({
1693
1686
  n.map((c) => t.addSection(c))
1694
1687
  );
1695
1688
  return {
1696
- textContent: _r({ sections: a }),
1689
+ textContent: Ur({ sections: a }),
1697
1690
  structuredContent: {
1698
1691
  sections: a,
1699
1692
  totalCount: a.length
@@ -1701,7 +1694,7 @@ const Or = s.object({
1701
1694
  };
1702
1695
  }
1703
1696
  };
1704
- function _r({ sections: e }) {
1697
+ function Ur({ sections: e }) {
1705
1698
  const t = e.length, r = e.map((n) => `• ${n.name} (id=${n.id}, projectId=${n.projectId})`).join(`
1706
1699
  `);
1707
1700
  return `Added ${t} section${t === 1 ? "" : "s"}:
@@ -1935,7 +1928,7 @@ function Ye(e, t, r = {}) {
1935
1928
  i.push(d);
1936
1929
  const l = 5;
1937
1930
  if (n || a <= l) {
1938
- const u = ke(t, l);
1931
+ const u = Te(t, l);
1939
1932
  if (u.length > 0) {
1940
1933
  const p = a > l ? `, +${a - l} more` : "";
1941
1934
  i.push(`Tasks:
@@ -1951,10 +1944,10 @@ function Ge(e) {
1951
1944
  ${n.map((l) => ` ${l}`).join(`
1952
1945
  `)}.`), i?.length) {
1953
1946
  const l = i.length, u = `Failed (${l}):
1954
- ${i.slice(0, ve.MAX_FAILURES_SHOWN).map((p) => ` ${p.item} (Error: ${p.error}${p.code ? ` [${p.code}]` : ""})`).join(
1947
+ ${i.slice(0, je.MAX_FAILURES_SHOWN).map((p) => ` ${p.item} (Error: ${p.error}${p.code ? ` [${p.code}]` : ""})`).join(
1955
1948
  `
1956
1949
  `
1957
- )}${l > ve.MAX_FAILURES_SHOWN ? `, +${l - ve.MAX_FAILURES_SHOWN} more` : ""}.`;
1950
+ )}${l > je.MAX_FAILURES_SHOWN ? `, +${l - je.MAX_FAILURES_SHOWN} more` : ""}.`;
1958
1951
  c.push(u);
1959
1952
  }
1960
1953
  return c.join(`
@@ -1972,7 +1965,7 @@ function Fr(e) {
1972
1965
  const t = e.inboxProject ? " • Inbox" : "", r = e.isFavorite ? " • ⭐" : "", o = e.isShared ? " • Shared" : "", n = e.viewStyle && e.viewStyle !== "list" ? ` • ${e.viewStyle}` : "", a = ` • id=${e.id}`;
1973
1966
  return ` ${e.name}${t}${r}${o}${n}${a}`;
1974
1967
  }
1975
- function ke(e, t = 5) {
1968
+ function Te(e, t = 5) {
1976
1969
  const o = e.slice(0, t).map(Lr).join(`
1977
1970
  `);
1978
1971
  if (e.length > t) {
@@ -2010,7 +2003,7 @@ const tt = 25, Hr = s.object({
2010
2003
  description: s.string().optional().describe(
2011
2004
  "Additional details, notes, or context for the task. Use this for longer content rather than putting it in the task name. Supports Markdown."
2012
2005
  ),
2013
- priority: Ne.optional().describe(_e),
2006
+ priority: Ne.optional().describe(Ue),
2014
2007
  dueString: s.string().optional().describe("The due date for the task, in natural language."),
2015
2008
  deadlineDate: s.string().optional().describe(
2016
2009
  'The deadline date for the task in ISO 8601 format (YYYY-MM-DD, e.g., "2025-12-31"). Deadlines are immovable constraints shown with a different indicator than due dates.'
@@ -2077,7 +2070,7 @@ const tt = 25, Hr = s.object({
2077
2070
  const l = i.map((u) => `"${u.item}": ${u.error}`).join("; ");
2078
2071
  throw new Error(`All ${i.length} task(s) failed to create: ${l}`);
2079
2072
  }
2080
- const c = a.map(R);
2073
+ const c = a.map(_);
2081
2074
  return {
2082
2075
  textContent: qr({
2083
2076
  tasks: c,
@@ -2205,7 +2198,7 @@ const Kr = {
2205
2198
  }, Vr = {
2206
2199
  projectId: s.string().describe("The project ID."),
2207
2200
  health: s.object({
2208
- status: s.enum(Ue).describe("The health status after triggering analysis."),
2201
+ status: s.enum(Re).describe("The health status after triggering analysis."),
2209
2202
  isStale: s.boolean().describe("Whether the health data is still stale after the request."),
2210
2203
  updateInProgress: s.boolean().describe("Whether an analysis update is currently in progress.")
2211
2204
  }).describe("The health response returned after triggering analysis."),
@@ -2318,9 +2311,15 @@ const St = [
2318
2311
  annotations: { readOnlyHint: !1, destructiveHint: !0, idempotentHint: !0 },
2319
2312
  async execute(e, t) {
2320
2313
  switch (e.type) {
2321
- case "project":
2314
+ case "project": {
2315
+ const r = await t.getProject(e.id);
2316
+ if (ue(r) && !r.isArchived)
2317
+ throw new Error(
2318
+ `Workspace project "${r.name}" must be archived before it can be deleted. Archive the project first, then delete it.`
2319
+ );
2322
2320
  await t.deleteProject(e.id);
2323
2321
  break;
2322
+ }
2324
2323
  case "section":
2325
2324
  await t.deleteSection(e.id);
2326
2325
  break;
@@ -2353,97 +2352,25 @@ const St = [
2353
2352
  }
2354
2353
  };
2355
2354
  }
2356
- }, oo = {
2357
- id: s.string().min(1).describe(
2358
- 'A unique identifier for the document in the format "task:{id}" or "project:{id}".'
2359
- )
2360
- }, no = {
2361
- id: s.string().describe("The ID of the fetched document."),
2362
- title: s.string().describe("The title of the document."),
2363
- text: s.string().describe("The text content of the document."),
2364
- url: s.string().describe("The URL of the document."),
2365
- metadata: s.record(s.string(), s.unknown()).optional().describe("Additional metadata about the document.")
2366
- }, ao = {
2367
- name: f.FETCH,
2368
- description: 'Fetch the full contents of a task or project by its ID. The ID should be in the format "task:{id}" or "project:{id}".',
2369
- parameters: oo,
2370
- outputSchema: no,
2371
- annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
2372
- async execute(e, t) {
2373
- const { id: r } = e, [o, n] = r.split(":", 2);
2374
- if (!n || o !== "task" && o !== "project")
2375
- throw new Error(
2376
- 'Invalid ID format. Expected "task:{id}" or "project:{id}". Example: "task:8485093748" or "project:6cfCcrrCFg2xP94Q"'
2377
- );
2378
- let a;
2379
- if (o === "task") {
2380
- const i = await t.getTask(n), c = R(i), d = [c.content];
2381
- c.description && d.push(`
2382
-
2383
- Description: ${c.description}`), c.dueDate && d.push(`
2384
- Due: ${c.dueDate}`), c.labels.length > 0 && d.push(`
2385
- Labels: ${c.labels.join(", ")}`), a = {
2386
- id: `task:${c.id}`,
2387
- title: c.content,
2388
- text: d.join(""),
2389
- url: ut(c.id),
2390
- metadata: {
2391
- priority: c.priority,
2392
- projectId: c.projectId,
2393
- sectionId: c.sectionId,
2394
- parentId: c.parentId,
2395
- recurring: c.recurring,
2396
- duration: c.duration,
2397
- responsibleUid: c.responsibleUid,
2398
- assignedByUid: c.assignedByUid,
2399
- checked: c.checked,
2400
- completedAt: c.completedAt
2401
- }
2402
- };
2403
- } else {
2404
- const i = await t.getProject(n), c = q(i), d = [c.name];
2405
- c.isShared && d.push(`
2406
-
2407
- Shared project`), c.isFavorite && d.push(`
2408
- Favorite: Yes`), a = {
2409
- id: `project:${c.id}`,
2410
- title: c.name,
2411
- text: d.join(""),
2412
- url: pt(c.id),
2413
- metadata: {
2414
- color: c.color,
2415
- isFavorite: c.isFavorite,
2416
- isShared: c.isShared,
2417
- parentId: c.parentId,
2418
- inboxProject: c.inboxProject,
2419
- viewStyle: c.viewStyle
2420
- }
2421
- };
2422
- }
2423
- return {
2424
- textContent: JSON.stringify(a),
2425
- structuredContent: a
2426
- };
2427
- }
2428
- }, Ct = ["task", "project", "comment", "section"], io = {
2355
+ }, Ct = ["task", "project", "comment", "section"], oo = {
2429
2356
  type: s.enum(Ct).describe("The type of object to fetch."),
2430
2357
  id: s.string().min(1).describe("The unique ID of the object to fetch.")
2431
- }, co = {
2358
+ }, no = {
2432
2359
  type: s.enum(Ct).describe("The type of object fetched."),
2433
2360
  id: s.string().describe("The ID of the fetched object."),
2434
- object: s.union([K, ae, fe, he]).describe("The fetched object data.")
2435
- }, lo = {
2361
+ object: s.union([K, ae, be, fe]).describe("The fetched object data.")
2362
+ }, ao = {
2436
2363
  name: f.FETCH_OBJECT,
2437
2364
  description: "Fetch a single task, project, comment, or section by its ID. Use this when you have a specific object ID and want to retrieve its full details.",
2438
- parameters: io,
2439
- outputSchema: co,
2365
+ parameters: oo,
2366
+ outputSchema: no,
2440
2367
  annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
2441
2368
  async execute(e, t) {
2442
2369
  const { type: r, id: o } = e;
2443
2370
  try {
2444
2371
  switch (r) {
2445
2372
  case "task": {
2446
- const n = await t.getTask(o), a = R(n);
2373
+ const n = await t.getTask(o), a = _(n);
2447
2374
  return {
2448
2375
  textContent: `Found task: ${a.content} • id=${a.id} • priority=${a.priority} • project=${a.projectId}`,
2449
2376
  structuredContent: {
@@ -2465,7 +2392,7 @@ Favorite: Yes`), a = {
2465
2392
  };
2466
2393
  }
2467
2394
  case "comment": {
2468
- const n = await t.getComment(o), a = pe(n), i = a.content.length > 50 ? `${a.content.substring(0, 50)}...` : a.content;
2395
+ const n = await t.getComment(o), a = me(n), i = a.content.length > 50 ? `${a.content.substring(0, 50)}...` : a.content;
2469
2396
  return {
2470
2397
  textContent: `Found comment • id=${a.id} • content="${i}" • posted=${a.postedAt}`,
2471
2398
  structuredContent: {
@@ -2499,6 +2426,78 @@ Favorite: Yes`), a = {
2499
2426
  );
2500
2427
  }
2501
2428
  }
2429
+ }, io = {
2430
+ id: s.string().min(1).describe(
2431
+ 'A unique identifier for the document in the format "task:{id}" or "project:{id}".'
2432
+ )
2433
+ }, co = {
2434
+ id: s.string().describe("The ID of the fetched document."),
2435
+ title: s.string().describe("The title of the document."),
2436
+ text: s.string().describe("The text content of the document."),
2437
+ url: s.string().describe("The URL of the document."),
2438
+ metadata: s.record(s.string(), s.unknown()).optional().describe("Additional metadata about the document.")
2439
+ }, lo = {
2440
+ name: f.FETCH,
2441
+ description: 'Fetch the full contents of a task or project by its ID. The ID should be in the format "task:{id}" or "project:{id}".',
2442
+ parameters: io,
2443
+ outputSchema: co,
2444
+ annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
2445
+ async execute(e, t) {
2446
+ const { id: r } = e, [o, n] = r.split(":", 2);
2447
+ if (!n || o !== "task" && o !== "project")
2448
+ throw new Error(
2449
+ 'Invalid ID format. Expected "task:{id}" or "project:{id}". Example: "task:8485093748" or "project:6cfCcrrCFg2xP94Q"'
2450
+ );
2451
+ let a;
2452
+ if (o === "task") {
2453
+ const i = await t.getTask(n), c = _(i), d = [c.content];
2454
+ c.description && d.push(`
2455
+
2456
+ Description: ${c.description}`), c.dueDate && d.push(`
2457
+ Due: ${c.dueDate}`), c.labels.length > 0 && d.push(`
2458
+ Labels: ${c.labels.join(", ")}`), a = {
2459
+ id: `task:${c.id}`,
2460
+ title: c.content,
2461
+ text: d.join(""),
2462
+ url: ut(c.id),
2463
+ metadata: {
2464
+ priority: c.priority,
2465
+ projectId: c.projectId,
2466
+ sectionId: c.sectionId,
2467
+ parentId: c.parentId,
2468
+ recurring: c.recurring,
2469
+ duration: c.duration,
2470
+ responsibleUid: c.responsibleUid,
2471
+ assignedByUid: c.assignedByUid,
2472
+ checked: c.checked,
2473
+ completedAt: c.completedAt
2474
+ }
2475
+ };
2476
+ } else {
2477
+ const i = await t.getProject(n), c = q(i), d = [c.name];
2478
+ c.isShared && d.push(`
2479
+
2480
+ Shared project`), c.isFavorite && d.push(`
2481
+ Favorite: Yes`), a = {
2482
+ id: `project:${c.id}`,
2483
+ title: c.name,
2484
+ text: d.join(""),
2485
+ url: pt(c.id),
2486
+ metadata: {
2487
+ color: c.color,
2488
+ isFavorite: c.isFavorite,
2489
+ isShared: c.isShared,
2490
+ parentId: c.parentId,
2491
+ inboxProject: c.inboxProject,
2492
+ viewStyle: c.viewStyle
2493
+ }
2494
+ };
2495
+ }
2496
+ return {
2497
+ textContent: JSON.stringify(a),
2498
+ structuredContent: a
2499
+ };
2500
+ }
2502
2501
  }, uo = {
2503
2502
  objectType: s.enum(["task", "project", "comment"]).optional().describe("Type of object to filter by."),
2504
2503
  objectId: s.string().optional().describe("Filter by specific object ID (task, project, or comment)."),
@@ -2616,7 +2615,7 @@ const yo = {
2616
2615
  cursor: s.string().optional().describe("Pagination cursor for retrieving more results."),
2617
2616
  limit: s.number().int().min(1).max(C.COMMENTS_MAX).optional().describe("Maximum number of comments to return")
2618
2617
  }, ko = {
2619
- comments: s.array(fe).describe("The found comments."),
2618
+ comments: s.array(be).describe("The found comments."),
2620
2619
  searchType: s.string().describe(
2621
2620
  'The type of search performed: "single" (comment ID), "task" (task ID), or "project" (project ID).'
2622
2621
  ),
@@ -2661,7 +2660,7 @@ const yo = {
2661
2660
  i = l.results, n = l.nextCursor !== null, a = l.nextCursor;
2662
2661
  } else
2663
2662
  throw new Error("Invalid state: no search parameter provided");
2664
- const c = i.map(pe);
2663
+ const c = i.map(me);
2665
2664
  return {
2666
2665
  textContent: wo({
2667
2666
  comments: c,
@@ -2805,7 +2804,7 @@ const $o = {
2805
2804
  since: a,
2806
2805
  until: i,
2807
2806
  userGmtOffset: I
2808
- }), N = `${$.since}T00:00:00${I}`, T = `${$.until}T23:59:59${I}`, b = new Date(N).toISOString(), S = new Date(T).toISOString(), U = {
2807
+ }), N = `${$.since}T00:00:00${I}`, T = `${$.until}T23:59:59${I}`, b = new Date(N).toISOString(), S = new Date(T).toISOString(), R = {
2809
2808
  ...e,
2810
2809
  since: $.since,
2811
2810
  until: $.until
@@ -2821,11 +2820,11 @@ const $o = {
2821
2820
  since: b,
2822
2821
  until: S,
2823
2822
  ...h ? { filterQuery: h, filterLang: "en" } : {}
2824
- }), v = w.map(R);
2823
+ }), v = w.map(_);
2825
2824
  return {
2826
2825
  textContent: Ao({
2827
2826
  tasks: v,
2828
- args: U,
2827
+ args: R,
2829
2828
  nextCursor: j,
2830
2829
  assigneeEmail: p
2831
2830
  }),
@@ -2834,7 +2833,7 @@ const $o = {
2834
2833
  nextCursor: j ?? void 0,
2835
2834
  totalCount: v.length,
2836
2835
  hasMore: !!j,
2837
- appliedFilters: U
2836
+ appliedFilters: R
2838
2837
  }
2839
2838
  };
2840
2839
  }
@@ -2861,7 +2860,7 @@ function Ao({
2861
2860
  limit: t.limit,
2862
2861
  nextCursor: r ?? void 0,
2863
2862
  filterHints: i,
2864
- previewLines: ke(e, Math.min(e.length, t.limit)),
2863
+ previewLines: Te(e, Math.min(e.length, t.limit)),
2865
2864
  zeroReasonHints: c
2866
2865
  });
2867
2866
  }
@@ -2874,7 +2873,7 @@ const Eo = {
2874
2873
  "The cursor to get the next page of labels (cursor is obtained from the previous call to this tool, with the same parameters). Ignored when searchText is provided."
2875
2874
  )
2876
2875
  }, Oo = {
2877
- labels: s.array(be).describe("The found personal labels."),
2876
+ labels: s.array(ge).describe("The found personal labels."),
2878
2877
  nextCursor: s.string().optional().describe("Cursor for the next page of results."),
2879
2878
  totalCount: s.number().describe("The total number of labels in this page."),
2880
2879
  hasMore: s.boolean().describe("Whether there are more results available."),
@@ -2897,9 +2896,9 @@ const Eo = {
2897
2896
  Hs(t)
2898
2897
  ]), { results: n, nextCursor: a } = r, i = e.searchText ? { searchText: e.searchText } : { limit: e.limit, cursor: e.cursor };
2899
2898
  return {
2900
- textContent: Ro({ labels: n, args: e, nextCursor: a, sharedLabels: o }),
2899
+ textContent: _o({ labels: n, args: e, nextCursor: a, sharedLabels: o }),
2901
2900
  structuredContent: {
2902
- labels: n.map((c) => be.parse(c)),
2901
+ labels: n.map((c) => ge.parse(c)),
2903
2902
  nextCursor: a ?? void 0,
2904
2903
  totalCount: n.length,
2905
2904
  hasMore: !!a,
@@ -2909,7 +2908,7 @@ const Eo = {
2909
2908
  };
2910
2909
  }
2911
2910
  };
2912
- function Ro({
2911
+ function _o({
2913
2912
  labels: e,
2914
2913
  args: t,
2915
2914
  nextCursor: r,
@@ -2934,7 +2933,7 @@ No shared labels.`;
2934
2933
  zeroReasonHints: p
2935
2934
  }) + m;
2936
2935
  }
2937
- const { FIND_PROJECTS: Uo, ADD_TASKS: Dt, UPDATE_TASKS: xt } = f, _o = {
2936
+ const { FIND_PROJECTS: Ro, ADD_TASKS: Dt, UPDATE_TASKS: xt } = f, Uo = {
2938
2937
  projectId: s.string().min(1).describe("The ID of the project to search for collaborators in."),
2939
2938
  searchTerm: s.string().optional().describe(
2940
2939
  "Search for a collaborator by name or email (partial and case insensitive match). If omitted, all collaborators in the project are returned."
@@ -2952,7 +2951,7 @@ const { FIND_PROJECTS: Uo, ADD_TASKS: Dt, UPDATE_TASKS: xt } = f, _o = {
2952
2951
  }, Lo = {
2953
2952
  name: f.FIND_PROJECT_COLLABORATORS,
2954
2953
  description: "Search for collaborators by name or other criteria in a project.",
2955
- parameters: _o,
2954
+ parameters: Uo,
2956
2955
  outputSchema: No,
2957
2956
  annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
2958
2957
  async execute(e, t) {
@@ -3048,7 +3047,7 @@ function Mo({
3048
3047
  const c = [];
3049
3048
  e.length === 0 && (r ? (c.push(`No collaborators match "${r}"`), c.push("Try a broader search term or check spelling"), o > 0 && c.push(`${o} collaborators available without filter`)) : (c.push("Project has no collaborators"), c.push("Share the project to add collaborators")));
3050
3049
  const d = [];
3051
- return e.length > 0 ? (d.push(`Use ${Dt} with responsibleUser to assign new tasks`), d.push(`Use ${xt} with responsibleUser to reassign existing tasks`), d.push("Use collaborator names, emails, or IDs for assignments")) : (d.push(`Use ${Uo} to find other projects`), r && o > 0 && d.push("Try searching without filters to see all collaborators")), F({
3050
+ return e.length > 0 ? (d.push(`Use ${Dt} with responsibleUser to assign new tasks`), d.push(`Use ${xt} with responsibleUser to reassign existing tasks`), d.push("Use collaborator names, emails, or IDs for assignments")) : (d.push(`Use ${Ro} to find other projects`), r && o > 0 && d.push("Try searching without filters to see all collaborators")), F({
3052
3051
  subject: n,
3053
3052
  count: e.length,
3054
3053
  filterHints: a,
@@ -3217,7 +3216,7 @@ const { ADD_SECTIONS: Vo } = f, Jo = {
3217
3216
  'Search for a section by name (partial and case insensitive match). Supports wildcards (e.g. "work*" for prefix match). Use "\\*" for a literal asterisk. If omitted, all sections in the project are returned.'
3218
3217
  )
3219
3218
  }, Xo = {
3220
- sections: s.array(he).describe("The found sections."),
3219
+ sections: s.array(fe).describe("The found sections."),
3221
3220
  totalCount: s.number().describe("The total number of sections found."),
3222
3221
  appliedFilters: s.record(s.string(), s.unknown()).describe("The filters that were applied to the search.")
3223
3222
  }, Zo = {
@@ -3266,13 +3265,142 @@ function Qo({
3266
3265
  zeroReasonHints: o
3267
3266
  });
3268
3267
  }
3269
- const en = 300 * 1e3;
3270
- class tn {
3268
+ function At(e) {
3269
+ return /* @__PURE__ */ new Date(`${e}T00:00:00`);
3270
+ }
3271
+ const en = {
3272
+ startDate: s.string().regex(/^(\d{4}-\d{2}-\d{2}|today)$/).optional().describe("The start date to get the tasks for. Format: YYYY-MM-DD or 'today'."),
3273
+ overdueOption: s.enum(["overdue-only", "include-overdue", "exclude-overdue"]).optional().describe(
3274
+ "How to handle overdue tasks. 'overdue-only' to get only overdue tasks, 'include-overdue' to include overdue tasks along with tasks for the specified date(s), and 'exclude-overdue' to exclude overdue tasks. Default is 'include-overdue'."
3275
+ ),
3276
+ daysCount: s.number().int().min(1).max(30).default(1).describe(
3277
+ "The number of days to get the tasks for, starting from the start date. Default is 1 which means only tasks for the start date."
3278
+ ),
3279
+ limit: s.number().int().min(1).max(C.TASKS_MAX).default(C.TASKS_DEFAULT).describe("The maximum number of tasks to return."),
3280
+ cursor: s.string().optional().describe(
3281
+ "The cursor to get the next page of tasks (cursor is obtained from the previous call to this tool, with the same parameters)."
3282
+ ),
3283
+ responsibleUser: s.string().optional().describe(
3284
+ "Filter tasks assigned to this user. User ID, name, or email. For personal queries (summaries, plans, reports), set to current user from user-info to exclude collaborators."
3285
+ ),
3286
+ responsibleUserFiltering: s.enum(gt).optional().describe(
3287
+ "Filter when responsibleUser is omitted. 'assigned'=assigned to others; 'unassignedOrMe'=unassigned+mine; 'all'=everyone. Default: 'unassignedOrMe'."
3288
+ ),
3289
+ ...qe
3290
+ }, tn = {
3291
+ tasks: s.array(K).describe("The found tasks."),
3292
+ nextCursor: s.string().optional().describe("Cursor for the next page of results."),
3293
+ totalCount: s.number().describe("The total number of tasks in this page."),
3294
+ hasMore: s.boolean().describe("Whether there are more results available."),
3295
+ appliedFilters: s.record(s.string(), s.unknown()).describe("The filters that were applied to the search.")
3296
+ }, sn = {
3297
+ name: f.FIND_TASKS_BY_DATE,
3298
+ description: "Get tasks by date range. startDate='today' includes overdue items. Default responsibleUserFiltering='unassignedOrMe' excludes others' tasks. Person-specific queries (summaries, plans, reports) require responsibleUser.",
3299
+ parameters: en,
3300
+ outputSchema: tn,
3301
+ annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
3302
+ async execute(e, t) {
3303
+ if (!e.startDate && e.overdueOption !== "overdue-only")
3304
+ throw new Error(
3305
+ "Either startDate must be provided or overdueOption must be set to overdue-only"
3306
+ );
3307
+ const r = await Le(t, e.responsibleUser), o = r?.userId, n = r?.email;
3308
+ let a = "";
3309
+ if (e.overdueOption === "overdue-only")
3310
+ a = "overdue";
3311
+ else if (e.startDate === "today")
3312
+ if (e.daysCount > 1) {
3313
+ const p = /* @__PURE__ */ new Date(), m = te(p), h = xe(p, e.daysCount), g = Je(h, { representation: "date" }), I = `(due after: ${m} | due: ${m}) & due before: ${g}`;
3314
+ a = e.overdueOption === "exclude-overdue" ? I : `(${I} | overdue)`;
3315
+ } else
3316
+ a = e.overdueOption === "exclude-overdue" ? "today" : "(today | overdue)";
3317
+ else if (e.startDate) {
3318
+ const p = e.startDate, m = xe(At(p), e.daysCount), h = Je(m, { representation: "date" });
3319
+ a = `(due after: ${p} | due: ${p}) & due before: ${h}`;
3320
+ }
3321
+ const i = Ke(e.labels, e.labelsOperator);
3322
+ i.length > 0 && (a = se(a, `(${i})`));
3323
+ const c = yt({
3324
+ resolvedAssigneeId: o,
3325
+ assigneeEmail: n,
3326
+ responsibleUserFiltering: e.responsibleUserFiltering
3327
+ });
3328
+ a = se(a, c);
3329
+ const { tasks: d, nextCursor: l } = await Fe({
3330
+ client: t,
3331
+ query: a,
3332
+ cursor: e.cursor,
3333
+ limit: e.limit
3334
+ });
3335
+ return {
3336
+ textContent: rn({ tasks: d, args: e, nextCursor: l, assigneeEmail: n }),
3337
+ structuredContent: {
3338
+ tasks: d,
3339
+ nextCursor: l ?? void 0,
3340
+ totalCount: d.length,
3341
+ hasMore: !!l,
3342
+ appliedFilters: e
3343
+ }
3344
+ };
3345
+ }
3346
+ };
3347
+ function rn({
3348
+ tasks: e,
3349
+ args: t,
3350
+ nextCursor: r,
3351
+ assigneeEmail: o
3352
+ }) {
3353
+ const n = [];
3354
+ if (t.overdueOption === "overdue-only")
3355
+ n.push("overdue tasks only");
3356
+ else if (t.startDate === "today") {
3357
+ const c = t.overdueOption === "exclude-overdue" ? "" : " + overdue tasks";
3358
+ n.push(
3359
+ `today${c}${t.daysCount > 1 ? ` + ${t.daysCount - 1} more days` : ""}`
3360
+ );
3361
+ } else if (t.startDate) {
3362
+ const c = t.daysCount > 1 ? ` to ${te(xe(At(t.startDate), t.daysCount))}` : "";
3363
+ n.push(`${t.startDate}${c}`);
3364
+ }
3365
+ if (t.labels && t.labels.length > 0) {
3366
+ const c = t.labels.map((d) => `@${d}`).join(t.labelsOperator === "and" ? " & " : " | ");
3367
+ n.push(`labels: ${c}`);
3368
+ }
3369
+ if (t.responsibleUser) {
3370
+ const c = o || t.responsibleUser;
3371
+ n.push(`assigned to: ${c}`);
3372
+ }
3373
+ let a = "";
3374
+ if (t.overdueOption === "overdue-only" ? a = "Overdue tasks" : t.startDate === "today" ? a = t.overdueOption === "exclude-overdue" ? "Today's tasks" : "Today's tasks + overdue" : t.startDate ? a = `Tasks for ${t.startDate}` : a = "Tasks", t.responsibleUser) {
3375
+ const c = o || t.responsibleUser;
3376
+ a += ` assigned to ${c}`;
3377
+ }
3378
+ const i = [];
3379
+ if (e.length === 0)
3380
+ if (t.overdueOption === "overdue-only")
3381
+ i.push("Great job! No overdue tasks");
3382
+ else if (t.startDate === "today") {
3383
+ const c = t.overdueOption === "exclude-overdue" ? "" : " or overdue";
3384
+ i.push(`Great job! No tasks for today${c}`);
3385
+ } else
3386
+ i.push("Expand date range with larger 'daysCount'"), i.push("Check today's tasks with startDate='today'");
3387
+ return F({
3388
+ subject: a,
3389
+ count: e.length,
3390
+ limit: t.limit,
3391
+ nextCursor: r ?? void 0,
3392
+ filterHints: n,
3393
+ previewLines: Te(e, Math.min(e.length, t.limit)),
3394
+ zeroReasonHints: i
3395
+ });
3396
+ }
3397
+ const on = 300 * 1e3;
3398
+ class nn {
3271
3399
  constructor() {
3272
3400
  this.cache = null;
3273
3401
  }
3274
3402
  async getFilters(t) {
3275
- if (this.cache && Date.now() - this.cache.timestamp < en)
3403
+ if (this.cache && Date.now() - this.cache.timestamp < on)
3276
3404
  return this.cache.filters;
3277
3405
  const o = ((await t.sync({
3278
3406
  resourceTypes: ["filters"],
@@ -3329,7 +3457,7 @@ ${u}` + (d.length > 5 ? `
3329
3457
  this.cache = null;
3330
3458
  }
3331
3459
  }
3332
- const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3460
+ const an = new nn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, cn = {
3333
3461
  searchText: s.string().optional().describe("The text to search for in tasks."),
3334
3462
  projectId: s.string().optional().describe(
3335
3463
  'Find tasks in this project. Project ID should be an ID string, or the text "inbox", for inbox tasks.'
@@ -3351,17 +3479,17 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3351
3479
  "The ID or name of a saved Todoist filter. The filter's query will be fetched and used to find tasks. Cannot be used with the `filter` parameter, projectId, sectionId, or parentId."
3352
3480
  ),
3353
3481
  ...qe
3354
- }, on = {
3482
+ }, dn = {
3355
3483
  tasks: s.array(K).describe("The found tasks."),
3356
3484
  nextCursor: s.string().optional().describe("Cursor for the next page of results."),
3357
3485
  totalCount: s.number().describe("The total number of tasks in this page."),
3358
3486
  hasMore: s.boolean().describe("Whether there are more results available."),
3359
3487
  appliedFilters: s.record(s.string(), s.unknown()).describe("The filters that were applied to the search.")
3360
- }, nn = {
3488
+ }, ln = {
3361
3489
  name: f.FIND_TASKS,
3362
3490
  description: "Find tasks by text search, project/section/parent container, responsible user, labels, a raw Todoist filter string, or a saved filter by ID or name (filterIdOrName). At least one filter must be provided.",
3363
- parameters: rn,
3364
- outputSchema: on,
3491
+ parameters: cn,
3492
+ outputSchema: dn,
3365
3493
  annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
3366
3494
  async execute(e, t) {
3367
3495
  const {
@@ -3391,7 +3519,7 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3391
3519
  'The `filter`/`filterIdOrName` parameter cannot be combined with projectId, sectionId, or parentId. Use filter syntax instead (e.g. "##ProjectName").'
3392
3520
  );
3393
3521
  let D = m;
3394
- h && (D = (await sn.resolveFilter(t, h)).filterQuery);
3522
+ h && (D = (await an.resolveFilter(t, h)).filterQuery);
3395
3523
  const $ = await Le(t, i), N = $?.userId, T = $?.email;
3396
3524
  if (o || n || a) {
3397
3525
  const x = {
@@ -3399,21 +3527,21 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3399
3527
  cursor: l ?? null
3400
3528
  };
3401
3529
  o && (x.projectId = await G({ projectId: o, user: g })), n && (x.sectionId = n), a && (x.parentId = a);
3402
- const { results: L, nextCursor: H } = await t.getTasks(x), Te = L.map(R);
3403
- let M = r ? Te.filter(
3530
+ const { results: L, nextCursor: H } = await t.getTasks(x), we = L.map(_);
3531
+ let M = r ? we.filter(
3404
3532
  (V) => V.content.toLowerCase().includes(r.toLowerCase()) || V.description?.toLowerCase().includes(r.toLowerCase())
3405
- ) : Te;
3533
+ ) : we;
3406
3534
  return M = Ms({
3407
3535
  tasks: M,
3408
3536
  resolvedAssigneeId: N,
3409
3537
  currentUserId: g.id,
3410
3538
  responsibleUserFiltering: c
3411
3539
  }), u && u.length > 0 && (M = p === "and" ? M.filter(
3412
- (V) => u.every((we) => V.labels.includes(we))
3540
+ (V) => u.every((Ie) => V.labels.includes(Ie))
3413
3541
  ) : M.filter(
3414
- (V) => u.some((we) => V.labels.includes(we))
3542
+ (V) => u.some((Ie) => V.labels.includes(Ie))
3415
3543
  )), {
3416
- textContent: Se({
3544
+ textContent: Ce({
3417
3545
  tasks: M,
3418
3546
  args: e,
3419
3547
  nextCursor: H,
@@ -3435,9 +3563,9 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3435
3563
  lang: "en",
3436
3564
  limit: d,
3437
3565
  cursor: l ?? null
3438
- }), H = x.map(R);
3566
+ }), H = x.map(_);
3439
3567
  return {
3440
- textContent: Se({
3568
+ textContent: Ce({
3441
3569
  tasks: H,
3442
3570
  args: e,
3443
3571
  nextCursor: L,
@@ -3471,7 +3599,7 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3471
3599
  limit: e.limit
3472
3600
  });
3473
3601
  return {
3474
- textContent: Se({
3602
+ textContent: Ce({
3475
3603
  tasks: w,
3476
3604
  args: e,
3477
3605
  nextCursor: j,
@@ -3488,7 +3616,7 @@ const sn = new tn(), { FIND_COMPLETED_TASKS: rt, ADD_TASKS: ot } = f, rn = {
3488
3616
  };
3489
3617
  }
3490
3618
  };
3491
- function an(e) {
3619
+ function un(e) {
3492
3620
  if (e.projectId) {
3493
3621
  const t = [
3494
3622
  e.searchText ? "No tasks in project match search" : "Project has no tasks yet"
@@ -3505,7 +3633,7 @@ function an(e) {
3505
3633
  }
3506
3634
  return [];
3507
3635
  }
3508
- function Se({
3636
+ function Ce({
3509
3637
  tasks: e,
3510
3638
  args: t,
3511
3639
  nextCursor: r,
@@ -3523,7 +3651,7 @@ function Se({
3523
3651
  const d = t.labels.map((l) => `@${l}`).join(t.labelsOperator === "and" ? " & " : " | ");
3524
3652
  i.push(`labels: ${d}`);
3525
3653
  }
3526
- e.length === 0 && c.push(...an(t));
3654
+ e.length === 0 && c.push(...un(t));
3527
3655
  } else {
3528
3656
  const d = n || t.responsibleUser, l = [];
3529
3657
  if (t.filter && l.push(`filter: ${t.filter}`), t.searchText && l.push(`"${t.searchText}"`), t.responsibleUser && l.push(`assigned to ${d}`), t.labels && t.labels.length > 0) {
@@ -3548,139 +3676,10 @@ function Se({
3548
3676
  limit: t.limit,
3549
3677
  nextCursor: r ?? void 0,
3550
3678
  filterHints: i,
3551
- previewLines: ke(e, Math.min(e.length, t.limit)),
3679
+ previewLines: Te(e, Math.min(e.length, t.limit)),
3552
3680
  zeroReasonHints: c
3553
3681
  });
3554
3682
  }
3555
- function At(e) {
3556
- return /* @__PURE__ */ new Date(`${e}T00:00:00`);
3557
- }
3558
- const cn = {
3559
- startDate: s.string().regex(/^(\d{4}-\d{2}-\d{2}|today)$/).optional().describe("The start date to get the tasks for. Format: YYYY-MM-DD or 'today'."),
3560
- overdueOption: s.enum(["overdue-only", "include-overdue", "exclude-overdue"]).optional().describe(
3561
- "How to handle overdue tasks. 'overdue-only' to get only overdue tasks, 'include-overdue' to include overdue tasks along with tasks for the specified date(s), and 'exclude-overdue' to exclude overdue tasks. Default is 'include-overdue'."
3562
- ),
3563
- daysCount: s.number().int().min(1).max(30).default(1).describe(
3564
- "The number of days to get the tasks for, starting from the start date. Default is 1 which means only tasks for the start date."
3565
- ),
3566
- limit: s.number().int().min(1).max(C.TASKS_MAX).default(C.TASKS_DEFAULT).describe("The maximum number of tasks to return."),
3567
- cursor: s.string().optional().describe(
3568
- "The cursor to get the next page of tasks (cursor is obtained from the previous call to this tool, with the same parameters)."
3569
- ),
3570
- responsibleUser: s.string().optional().describe(
3571
- "Filter tasks assigned to this user. User ID, name, or email. For personal queries (summaries, plans, reports), set to current user from user-info to exclude collaborators."
3572
- ),
3573
- responsibleUserFiltering: s.enum(gt).optional().describe(
3574
- "Filter when responsibleUser is omitted. 'assigned'=assigned to others; 'unassignedOrMe'=unassigned+mine; 'all'=everyone. Default: 'unassignedOrMe'."
3575
- ),
3576
- ...qe
3577
- }, dn = {
3578
- tasks: s.array(K).describe("The found tasks."),
3579
- nextCursor: s.string().optional().describe("Cursor for the next page of results."),
3580
- totalCount: s.number().describe("The total number of tasks in this page."),
3581
- hasMore: s.boolean().describe("Whether there are more results available."),
3582
- appliedFilters: s.record(s.string(), s.unknown()).describe("The filters that were applied to the search.")
3583
- }, ln = {
3584
- name: f.FIND_TASKS_BY_DATE,
3585
- description: "Get tasks by date range. startDate='today' includes overdue items. Default responsibleUserFiltering='unassignedOrMe' excludes others' tasks. Person-specific queries (summaries, plans, reports) require responsibleUser.",
3586
- parameters: cn,
3587
- outputSchema: dn,
3588
- annotations: { readOnlyHint: !0, destructiveHint: !1, idempotentHint: !0 },
3589
- async execute(e, t) {
3590
- if (!e.startDate && e.overdueOption !== "overdue-only")
3591
- throw new Error(
3592
- "Either startDate must be provided or overdueOption must be set to overdue-only"
3593
- );
3594
- const r = await Le(t, e.responsibleUser), o = r?.userId, n = r?.email;
3595
- let a = "";
3596
- if (e.overdueOption === "overdue-only")
3597
- a = "overdue";
3598
- else if (e.startDate === "today")
3599
- if (e.daysCount > 1) {
3600
- const p = /* @__PURE__ */ new Date(), m = te(p), h = De(p, e.daysCount), g = Je(h, { representation: "date" }), I = `(due after: ${m} | due: ${m}) & due before: ${g}`;
3601
- a = e.overdueOption === "exclude-overdue" ? I : `(${I} | overdue)`;
3602
- } else
3603
- a = e.overdueOption === "exclude-overdue" ? "today" : "(today | overdue)";
3604
- else if (e.startDate) {
3605
- const p = e.startDate, m = De(At(p), e.daysCount), h = Je(m, { representation: "date" });
3606
- a = `(due after: ${p} | due: ${p}) & due before: ${h}`;
3607
- }
3608
- const i = Ke(e.labels, e.labelsOperator);
3609
- i.length > 0 && (a = se(a, `(${i})`));
3610
- const c = yt({
3611
- resolvedAssigneeId: o,
3612
- assigneeEmail: n,
3613
- responsibleUserFiltering: e.responsibleUserFiltering
3614
- });
3615
- a = se(a, c);
3616
- const { tasks: d, nextCursor: l } = await Fe({
3617
- client: t,
3618
- query: a,
3619
- cursor: e.cursor,
3620
- limit: e.limit
3621
- });
3622
- return {
3623
- textContent: un({ tasks: d, args: e, nextCursor: l, assigneeEmail: n }),
3624
- structuredContent: {
3625
- tasks: d,
3626
- nextCursor: l ?? void 0,
3627
- totalCount: d.length,
3628
- hasMore: !!l,
3629
- appliedFilters: e
3630
- }
3631
- };
3632
- }
3633
- };
3634
- function un({
3635
- tasks: e,
3636
- args: t,
3637
- nextCursor: r,
3638
- assigneeEmail: o
3639
- }) {
3640
- const n = [];
3641
- if (t.overdueOption === "overdue-only")
3642
- n.push("overdue tasks only");
3643
- else if (t.startDate === "today") {
3644
- const c = t.overdueOption === "exclude-overdue" ? "" : " + overdue tasks";
3645
- n.push(
3646
- `today${c}${t.daysCount > 1 ? ` + ${t.daysCount - 1} more days` : ""}`
3647
- );
3648
- } else if (t.startDate) {
3649
- const c = t.daysCount > 1 ? ` to ${te(De(At(t.startDate), t.daysCount))}` : "";
3650
- n.push(`${t.startDate}${c}`);
3651
- }
3652
- if (t.labels && t.labels.length > 0) {
3653
- const c = t.labels.map((d) => `@${d}`).join(t.labelsOperator === "and" ? " & " : " | ");
3654
- n.push(`labels: ${c}`);
3655
- }
3656
- if (t.responsibleUser) {
3657
- const c = o || t.responsibleUser;
3658
- n.push(`assigned to: ${c}`);
3659
- }
3660
- let a = "";
3661
- if (t.overdueOption === "overdue-only" ? a = "Overdue tasks" : t.startDate === "today" ? a = t.overdueOption === "exclude-overdue" ? "Today's tasks" : "Today's tasks + overdue" : t.startDate ? a = `Tasks for ${t.startDate}` : a = "Tasks", t.responsibleUser) {
3662
- const c = o || t.responsibleUser;
3663
- a += ` assigned to ${c}`;
3664
- }
3665
- const i = [];
3666
- if (e.length === 0)
3667
- if (t.overdueOption === "overdue-only")
3668
- i.push("Great job! No overdue tasks");
3669
- else if (t.startDate === "today") {
3670
- const c = t.overdueOption === "exclude-overdue" ? "" : " or overdue";
3671
- i.push(`Great job! No tasks for today${c}`);
3672
- } else
3673
- i.push("Expand date range with larger 'daysCount'"), i.push("Check today's tasks with startDate='today'");
3674
- return F({
3675
- subject: a,
3676
- count: e.length,
3677
- limit: t.limit,
3678
- nextCursor: r ?? void 0,
3679
- filterHints: n,
3680
- previewLines: ke(e, Math.min(e.length, t.limit)),
3681
- zeroReasonHints: i
3682
- });
3683
- }
3684
3683
  const pn = {
3685
3684
  projectId: s.string().min(1).optional().describe(
3686
3685
  "Optional project ID. If provided, shows detailed overview of that project. If omitted, shows overview of all projects."
@@ -3805,11 +3804,11 @@ function nt(e) {
3805
3804
  }
3806
3805
  return r;
3807
3806
  }
3808
- function Re(e, t = "") {
3807
+ function _e(e, t = "") {
3809
3808
  const r = [];
3810
3809
  for (const o of e) {
3811
3810
  const n = `id=${o.id}`, a = o.dueDate ? `; due=${o.dueDate}` : "", i = `; content=${o.content}`;
3812
- r.push(`${t}- ${n}${a}${i}`), o.children.length > 0 && r.push(...Re(o.children, `${t} `));
3811
+ r.push(`${t}- ${n}${a}${i}`), o.children.length > 0 && r.push(..._e(o.children, `${t} `));
3813
3812
  }
3814
3813
  return r;
3815
3814
  }
@@ -3818,10 +3817,12 @@ function Pt(e, t) {
3818
3817
  id: e.id,
3819
3818
  name: e.name,
3820
3819
  parentId: re(e) ? e.parentId ?? void 0 : void 0,
3821
- folderId: Pe(e) ? e.folderId ?? void 0 : void 0,
3820
+ folderId: ue(e) ? e.folderId ?? void 0 : void 0,
3822
3821
  childOrder: e.childOrder,
3823
3822
  sections: t[e.id] || [],
3824
- children: e.children.map((r) => Pt(r, t))
3823
+ children: e.children.map(
3824
+ (r) => Pt(r, t)
3825
+ )
3825
3826
  };
3826
3827
  }
3827
3828
  async function bn(e, t) {
@@ -3832,7 +3833,7 @@ async function bn(e, t) {
3832
3833
  limit: C.TASKS_BATCH_SIZE,
3833
3834
  cursor: o ?? void 0
3834
3835
  });
3835
- r = r.concat(n.map(R)), o = a ?? void 0;
3836
+ r = r.concat(n.map(_)), o = a ?? void 0;
3836
3837
  } while (o);
3837
3838
  return r;
3838
3839
  }
@@ -3893,7 +3894,7 @@ async function kn(e, t) {
3893
3894
  if (i.length > 0) {
3894
3895
  c.push("");
3895
3896
  const u = nt(i);
3896
- c.push(...Re(u));
3897
+ c.push(..._e(u));
3897
3898
  }
3898
3899
  for (const u of o) {
3899
3900
  c.push(""), c.push(`## ${u.name}`);
@@ -3901,7 +3902,7 @@ async function kn(e, t) {
3901
3902
  if (!p?.length)
3902
3903
  continue;
3903
3904
  const m = nt(p);
3904
- c.push(...Re(m));
3905
+ c.push(..._e(m));
3905
3906
  }
3906
3907
  const d = c.join(`
3907
3908
  `), l = {
@@ -4148,7 +4149,7 @@ const Dn = {
4148
4149
  progressPercent: s.number().describe("Completion percentage (0-100).")
4149
4150
  }).describe("Project completion progress."),
4150
4151
  health: s.object({
4151
- status: s.enum(Ue).describe("The overall health status of the project."),
4152
+ status: s.enum(Re).describe("The overall health status of the project."),
4152
4153
  description: s.string().nullable().optional().describe("Detailed description of the health assessment."),
4153
4154
  descriptionSummary: s.string().nullable().optional().describe("Brief summary of the health assessment."),
4154
4155
  taskRecommendations: s.array(An).nullable().optional().describe("Specific recommendations for individual tasks."),
@@ -4186,7 +4187,7 @@ async function Pn(e, t, r) {
4186
4187
  ]);
4187
4188
  return { progress: o, health: n };
4188
4189
  }
4189
- function Rn(e, { progress: t, health: r, context: o }) {
4190
+ function _n(e, { progress: t, health: r, context: o }) {
4190
4191
  const n = [`# Project Health: ${e}`, ""];
4191
4192
  if (n.push(`**Status:** ${r.status}`), r.isStale && n.push("**Note:** Health data is stale and may not reflect recent changes."), r.updateInProgress && n.push("**Note:** A health analysis update is currently in progress."), r.updatedAt && n.push(`**Last Updated:** ${r.updatedAt}`), n.push(""), n.push("## Progress"), n.push(
4192
4193
  `**Completed:** ${t.completedCount} | **Active:** ${t.activeCount} | **Progress:** ${t.progressPercent}%`
@@ -4209,7 +4210,7 @@ function Rn(e, { progress: t, health: r, context: o }) {
4209
4210
  return n.join(`
4210
4211
  `);
4211
4212
  }
4212
- const Un = {
4213
+ const Rn = {
4213
4214
  name: f.GET_PROJECT_HEALTH,
4214
4215
  description: "Get a comprehensive health assessment for a project including completion progress, health status (EXCELLENT, ON_TRACK, AT_RISK, CRITICAL), and optional detailed context with project metrics and task-level recommendations. Use includeContext=true for full detail including task data.",
4215
4216
  parameters: xn,
@@ -4220,7 +4221,7 @@ const Un = {
4220
4221
  idempotentHint: !0
4221
4222
  },
4222
4223
  async execute(e, t) {
4223
- const { projectId: r, includeContext: o } = e, n = await Pn(t, r, o), a = n.context?.projectName ?? `Project ${r}`, i = Rn(a, n), c = n.context ? {
4224
+ const { projectId: r, includeContext: o } = e, n = await Pn(t, r, o), a = n.context?.projectName ?? `Project ${r}`, i = _n(a, n), c = n.context ? {
4224
4225
  projectDescription: n.context.projectDescription,
4225
4226
  projectMetrics: n.context.projectMetrics,
4226
4227
  tasks: n.context.tasks.map((d) => ({
@@ -4256,7 +4257,7 @@ const Un = {
4256
4257
  }
4257
4258
  };
4258
4259
  }
4259
- }, _n = {
4260
+ }, Un = {
4260
4261
  workspaceIdOrName: s.string().min(1).describe(
4261
4262
  "The workspace ID or name. Supports exact ID, exact name match (case-insensitive), or unique partial name match."
4262
4263
  ),
@@ -4264,7 +4265,7 @@ const Un = {
4264
4265
  }, Nn = s.object({
4265
4266
  projectId: s.string().describe("The project ID."),
4266
4267
  health: s.object({
4267
- status: s.enum(Ue).describe("The health status of the project."),
4268
+ status: s.enum(Re).describe("The health status of the project."),
4268
4269
  isStale: s.boolean().describe("Whether the health data is stale."),
4269
4270
  updateInProgress: s.boolean().describe("Whether a health analysis update is in progress.")
4270
4271
  }).nullable().describe("Health data for this project, if available."),
@@ -4281,7 +4282,7 @@ const Un = {
4281
4282
  }, Mn = {
4282
4283
  name: f.GET_WORKSPACE_INSIGHTS,
4283
4284
  description: "Get aggregated health and progress insights across all projects in a workspace. Accepts workspace name or ID, with optional project ID filtering. Useful for a cross-project health overview.",
4284
- parameters: _n,
4285
+ parameters: Un,
4285
4286
  outputSchema: Ln,
4286
4287
  annotations: {
4287
4288
  readOnlyHint: !0,
@@ -4460,7 +4461,7 @@ const zn = {
4460
4461
  newAssigneeId: void 0
4461
4462
  }));
4462
4463
  return {
4463
- textContent: Ce({
4464
+ textContent: $e({
4464
4465
  operation: r,
4465
4466
  results: w,
4466
4467
  dryRun: !0
@@ -4497,7 +4498,7 @@ const zn = {
4497
4498
  throw new Error(`All ${S.length} unassign operation(s) failed: ${w}`);
4498
4499
  }
4499
4500
  return {
4500
- textContent: Ce({
4501
+ textContent: $e({
4501
4502
  operation: r,
4502
4503
  results: S,
4503
4504
  dryRun: !1
@@ -4542,7 +4543,7 @@ const zn = {
4542
4543
  newAssigneeId: j.resolvedUser.userId
4543
4544
  };
4544
4545
  });
4545
- const U = S.map(
4546
+ const R = S.map(
4546
4547
  async ({ assignment: w, validation: j }) => {
4547
4548
  const v = d.find((x) => x.id === w.taskId);
4548
4549
  if (!w.taskId || !j.resolvedUser?.userId)
@@ -4571,7 +4572,7 @@ const zn = {
4571
4572
  }
4572
4573
  }
4573
4574
  );
4574
- return Promise.all(U);
4575
+ return Promise.all(R);
4575
4576
  }
4576
4577
  const D = await I(h, !i), $ = [...D, ...g, ...l];
4577
4578
  if ($.length > 0 && $.every((T) => !T.success)) {
@@ -4579,7 +4580,7 @@ const zn = {
4579
4580
  throw new Error(`All ${$.length} ${r} operation(s) failed: ${T}`);
4580
4581
  }
4581
4582
  return {
4582
- textContent: Ce({
4583
+ textContent: $e({
4583
4584
  operation: r,
4584
4585
  results: $,
4585
4586
  dryRun: i
@@ -4595,7 +4596,7 @@ const zn = {
4595
4596
  };
4596
4597
  }
4597
4598
  };
4598
- function Ce({
4599
+ function $e({
4599
4600
  operation: e,
4600
4601
  results: t,
4601
4602
  dryRun: r
@@ -4706,8 +4707,8 @@ const Xn = {
4706
4707
  }
4707
4708
  };
4708
4709
  }
4709
- }, Rt = ["project", "section"], ra = {
4710
- type: s.enum(Rt).describe(
4710
+ }, _t = ["project", "section"], ra = {
4711
+ type: s.enum(_t).describe(
4711
4712
  'The type of entity to reorder. "project" reorders sibling projects within the same parent (and can move projects to a new parent). "section" reorders sections within the same project.'
4712
4713
  ),
4713
4714
  items: s.array(
@@ -4724,7 +4725,7 @@ const Xn = {
4724
4725
  "The items to reorder or move. Each item must have at least order or parentId. Items with parentId will be moved first, then items with order will be reordered. All items being reordered should be siblings for predictable results."
4725
4726
  )
4726
4727
  }, oa = {
4727
- type: s.enum(Rt).describe("The type of entity that was reordered/moved."),
4728
+ type: s.enum(_t).describe("The type of entity that was reordered/moved."),
4728
4729
  movedCount: s.number().describe("The number of entities moved to a new parent."),
4729
4730
  reorderedCount: s.number().describe("The number of entities reordered."),
4730
4731
  affectedIds: s.array(s.string()).describe("The IDs of all affected entities."),
@@ -4841,7 +4842,7 @@ const Xn = {
4841
4842
  const l = d instanceof Error ? d.message : String(d);
4842
4843
  throw new Error(`Reschedule failed: ${l}`);
4843
4844
  }
4844
- const a = await Promise.all(r.map((d) => t.getTask(d.id))), i = a.map(R);
4845
+ const a = await Promise.all(r.map((d) => t.getTask(d.id))), i = a.map(_);
4845
4846
  return {
4846
4847
  textContent: Ye("Rescheduled", i, {
4847
4848
  showDetails: i.length <= 5
@@ -4967,7 +4968,7 @@ const ya = s.object({
4967
4968
  }), ka = {
4968
4969
  comments: s.array(ya).min(1).describe("The comments to update.")
4969
4970
  }, Ta = {
4970
- comments: s.array(fe).describe("The updated comments."),
4971
+ comments: s.array(be).describe("The updated comments."),
4971
4972
  totalCount: s.number().describe("The total number of comments updated."),
4972
4973
  updatedCommentIds: s.array(s.string()).describe("The IDs of the updated comments."),
4973
4974
  appliedOperations: s.object({
@@ -4980,7 +4981,7 @@ const ya = s.object({
4980
4981
  outputSchema: Ta,
4981
4982
  annotations: { readOnlyHint: !1, destructiveHint: !0, idempotentHint: !1 },
4982
4983
  async execute(e, t) {
4983
- const { comments: r } = e, o = r.map(async (c) => await t.updateComment(c.id, { content: c.content })), a = (await Promise.all(o)).map(pe);
4984
+ const { comments: r } = e, o = r.map(async (c) => await t.updateComment(c.id, { content: c.content })), a = (await Promise.all(o)).map(me);
4984
4985
  return {
4985
4986
  textContent: Ia({
4986
4987
  comments: a
@@ -5093,8 +5094,7 @@ ${n}`;
5093
5094
  return o;
5094
5095
  }
5095
5096
  function Da({ id: e, ...t }) {
5096
- const r = Object.values(t);
5097
- return r.length === 0 || r.every((o) => o === void 0) ? "no-fields" : null;
5097
+ return Object.values(t).every((o) => o === void 0) ? "no-fields" : null;
5098
5098
  }
5099
5099
  const xa = s.object({
5100
5100
  id: s.string().min(1).describe("The ID of the project to update."),
@@ -5121,7 +5121,7 @@ const xa = s.object({
5121
5121
  async execute(e, t) {
5122
5122
  const { projects: r } = e, o = await Promise.all(
5123
5123
  r.map(async (d) => {
5124
- const l = Ra(d);
5124
+ const l = _a(d);
5125
5125
  if (l !== null) return { kind: "skipped", reason: l };
5126
5126
  const { id: u, ...p } = d;
5127
5127
  return { kind: "updated", project: await t.updateProject(u, p) };
@@ -5163,22 +5163,22 @@ function Pa({
5163
5163
  return t > 0 && i.push(`${t} skipped - no changes`), r > 0 && i.push(`${r} skipped - no valid field values`), i.length > 0 && (a += ` (${i.join(", ")})`), o > 0 && (a += `:
5164
5164
  ${n}`), a;
5165
5165
  }
5166
- function Ra({ id: e, ...t }) {
5166
+ function _a({ id: e, ...t }) {
5167
5167
  const r = Object.values(t);
5168
5168
  return r.length === 0 ? "no-fields" : r.every((o) => o === void 0) ? "no-valid-values" : null;
5169
5169
  }
5170
- const Ua = s.object({
5170
+ const Ra = s.object({
5171
5171
  type: s.literal("relative"),
5172
5172
  id: s.string().min(1).describe("The ID of the relative reminder to update."),
5173
5173
  minuteOffset: s.number().int().min(0).optional().describe("New minute offset before task due time."),
5174
- service: ge.optional().describe('New delivery method: "email" or "push".'),
5175
- isUrgent: ye
5176
- }), _a = s.object({
5174
+ service: ye.optional().describe('New delivery method: "email" or "push".'),
5175
+ isUrgent: ke
5176
+ }), Ua = s.object({
5177
5177
  type: s.literal("absolute"),
5178
5178
  id: s.string().min(1).describe("The ID of the absolute reminder to update."),
5179
5179
  due: It.optional().describe("New due date/time for the reminder."),
5180
- service: ge.optional().describe('New delivery method: "email" or "push".'),
5181
- isUrgent: ye
5180
+ service: ye.optional().describe('New delivery method: "email" or "push".'),
5181
+ isUrgent: ke
5182
5182
  }), Na = s.object({
5183
5183
  type: s.literal("location"),
5184
5184
  id: s.string().min(1).describe("The ID of the location reminder to update."),
@@ -5190,12 +5190,12 @@ const Ua = s.object({
5190
5190
  ),
5191
5191
  radius: s.number().int().optional().describe("New radius in meters.")
5192
5192
  }), La = s.discriminatedUnion("type", [
5193
+ Ra,
5193
5194
  Ua,
5194
- _a,
5195
5195
  Na
5196
5196
  ]), Ma = {
5197
- reminders: s.array(La).min(1).max(ue).describe(
5198
- `Array of reminders to update (max ${ue}). Each must include the reminder type and ID. Only include fields that need to change.`
5197
+ reminders: s.array(La).min(1).max(pe).describe(
5198
+ `Array of reminders to update (max ${pe}). Each must include the reminder type and ID. Only include fields that need to change.`
5199
5199
  )
5200
5200
  }, Fa = {
5201
5201
  reminders: s.array(He).describe("The updated reminders."),
@@ -5245,7 +5245,7 @@ const Ua = s.object({
5245
5245
  }), Ba = {
5246
5246
  sections: s.array(Wa).min(1).describe("The sections to update.")
5247
5247
  }, za = {
5248
- sections: s.array(he).describe("The updated sections."),
5248
+ sections: s.array(fe).describe("The updated sections."),
5249
5249
  totalCount: s.number().describe("The total number of sections updated."),
5250
5250
  updatedSectionIds: s.array(s.string()).describe("The IDs of the updated sections.")
5251
5251
  }, Ya = {
@@ -5290,7 +5290,7 @@ const qa = s.object({
5290
5290
  sectionId: s.string().optional().describe("The new section ID for the task."),
5291
5291
  parentId: s.string().optional().describe("The new parent task ID (for subtasks)."),
5292
5292
  order: s.number().optional().describe("The new order of the task within its parent/section."),
5293
- priority: Ne.optional().describe(_e),
5293
+ priority: Ne.optional().describe(Ue),
5294
5294
  dueString: s.preprocess(
5295
5295
  // Keep accepting legacy null while exposing a Gemini-compatible string schema.
5296
5296
  (e) => e === null ? "remove" : e,
@@ -5362,12 +5362,12 @@ const qa = s.object({
5362
5362
  Ja
5363
5363
  );
5364
5364
  S !== void 0 && (b = { ...b, dueString: S });
5365
- const U = ct(
5365
+ const R = ct(
5366
5366
  $,
5367
5367
  Va,
5368
5368
  null
5369
5369
  );
5370
- if (U !== void 0 && (b = { ...b, deadlineDate: U }), h)
5370
+ if (R !== void 0 && (b = { ...b, deadlineDate: R }), h)
5371
5371
  try {
5372
5372
  const { minutes: v } = ft(h);
5373
5373
  b = {
@@ -5401,7 +5401,7 @@ const qa = s.object({
5401
5401
  return Object.keys(b).length > 0 ? await t.updateTask(d, b) : j;
5402
5402
  }), n = (await Promise.all(o)).filter(
5403
5403
  (c) => c !== void 0
5404
- ), a = n.map(R);
5404
+ ), a = n.map(_);
5405
5405
  return {
5406
5406
  textContent: ei({
5407
5407
  tasks: a,
@@ -5483,11 +5483,11 @@ function di(e) {
5483
5483
  return !1;
5484
5484
  }
5485
5485
  }
5486
- function Ut(e) {
5486
+ function Rt(e) {
5487
5487
  return di(e) ? e : "UTC";
5488
5488
  }
5489
5489
  function li(e, t) {
5490
- const r = Ut(t);
5490
+ const r = Rt(t);
5491
5491
  return e.toLocaleString("en-US", {
5492
5492
  timeZone: r,
5493
5493
  year: "numeric",
@@ -5500,7 +5500,7 @@ function li(e, t) {
5500
5500
  });
5501
5501
  }
5502
5502
  async function ui(e) {
5503
- const t = await e.getUser(), r = t.tzInfo?.timezone ?? "UTC", o = Ut(r), n = /* @__PURE__ */ new Date(), a = li(n, o), i = t.startDay ?? 1, c = ci(i), d = oi(t), l = new Date(n.toLocaleString("en-US", { timeZone: o })), u = ni(l, i), p = ai(u), m = ii(l), g = [
5503
+ const t = await e.getUser(), r = t.tzInfo?.timezone ?? "UTC", o = Rt(r), n = /* @__PURE__ */ new Date(), a = li(n, o), i = t.startDay ?? 1, c = ci(i), d = oi(t), l = new Date(n.toLocaleString("en-US", { timeZone: o })), u = ni(l, i), p = ai(u), m = ii(l), g = [
5504
5504
  "# User Information",
5505
5505
  "",
5506
5506
  `**User ID:** ${t.id}`,
@@ -5774,7 +5774,7 @@ You have access to comprehensive Todoist management tools for personal productiv
5774
5774
 
5775
5775
  Always provide clear, actionable task titles and descriptions. Use the overview tools to give users context about their workload and project status.
5776
5776
  `;
5777
- function Ui({
5777
+ function Ri({
5778
5778
  todoistApiKey: e,
5779
5779
  baseUrl: t,
5780
5780
  features: r = []
@@ -5789,16 +5789,16 @@ function Ui({
5789
5789
  instructions: vi
5790
5790
  }
5791
5791
  ), n = new Ft(e, { baseUrl: t }), a = {
5792
- ...ln,
5792
+ ...sn,
5793
5793
  _meta: {
5794
5794
  ui: {
5795
- resourceUri: xe
5795
+ resourceUri: Ae
5796
5796
  }
5797
5797
  }
5798
5798
  };
5799
5799
  ts(o);
5800
5800
  const i = { server: o, client: n, features: r };
5801
- return k({ tool: zr, ...i }), k({ tool: Qr, ...i }), k({ tool: ba, ...i }), k({ tool: Qa, ...i }), k({ tool: da, ...i }), k({ tool: nn, ...i }), k({ tool: a, ...i }), k({ tool: xo, ...i }), k({ tool: Ir, ...i }), k({ tool: Oa, ...i }), k({ tool: Bo, ...i }), k({ tool: Qn, ...i }), k({ tool: sa, ...i }), k({ tool: Ur, ...i }), k({ tool: Ya, ...i }), k({ tool: Zo, ...i }), k({ tool: tr, ...i }), k({ tool: To, ...i }), k({ tool: wa, ...i }), k({ tool: Ar, ...i }), k({ tool: qo, ...i }), k({ tool: Ha, ...i }), k({ tool: Ii, ...i }), k({ tool: hr, ...i }), k({ tool: Po, ...i }), k({ tool: nr, ...i }), k({ tool: lr, ...i }), k({ tool: Ca, ...i }), k({ tool: mo, ...i }), k({ tool: vn, ...i }), k({ tool: Un, ...i }), k({ tool: Dn, ...i }), k({ tool: Jr, ...i }), k({ tool: Mn, ...i }), k({ tool: Tn, ...i }), k({ tool: ro, ...i }), k({ tool: lo, ...i }), k({ tool: na, ...i }), k({ tool: pi, ...i }), k({ tool: Lo, ...i }), k({ tool: Jn, ...i }), k({ tool: zn, ...i }), k({ tool: ma, ...i }), k({ tool: ao, ...i }), o.registerPrompt(
5801
+ return k({ tool: zr, ...i }), k({ tool: Qr, ...i }), k({ tool: ba, ...i }), k({ tool: Qa, ...i }), k({ tool: da, ...i }), k({ tool: ln, ...i }), k({ tool: a, ...i }), k({ tool: xo, ...i }), k({ tool: Ir, ...i }), k({ tool: Oa, ...i }), k({ tool: Bo, ...i }), k({ tool: Qn, ...i }), k({ tool: sa, ...i }), k({ tool: Rr, ...i }), k({ tool: Ya, ...i }), k({ tool: Zo, ...i }), k({ tool: tr, ...i }), k({ tool: To, ...i }), k({ tool: wa, ...i }), k({ tool: Ar, ...i }), k({ tool: qo, ...i }), k({ tool: Ha, ...i }), k({ tool: Ii, ...i }), k({ tool: hr, ...i }), k({ tool: Po, ...i }), k({ tool: nr, ...i }), k({ tool: lr, ...i }), k({ tool: Ca, ...i }), k({ tool: mo, ...i }), k({ tool: vn, ...i }), k({ tool: Rn, ...i }), k({ tool: Dn, ...i }), k({ tool: Jr, ...i }), k({ tool: Mn, ...i }), k({ tool: Tn, ...i }), k({ tool: ro, ...i }), k({ tool: ao, ...i }), k({ tool: na, ...i }), k({ tool: pi, ...i }), k({ tool: Lo, ...i }), k({ tool: Jn, ...i }), k({ tool: zn, ...i }), k({ tool: ma, ...i }), k({ tool: lo, ...i }), o.registerPrompt(
5802
5802
  ie.name,
5803
5803
  {
5804
5804
  title: ie.title,
@@ -5810,28 +5810,28 @@ function Ui({
5810
5810
  }
5811
5811
  export {
5812
5812
  Ya as A,
5813
- Ur as B,
5813
+ Rr as B,
5814
5814
  Bo as C,
5815
5815
  Oa as D,
5816
5816
  Ir as E,
5817
5817
  da as F,
5818
5818
  xo as G,
5819
- ln as H,
5820
- nn as I,
5819
+ sn as H,
5820
+ ln as I,
5821
5821
  Qa as J,
5822
5822
  ba as K,
5823
5823
  Qr as L,
5824
5824
  zr as M,
5825
- Ri as N,
5825
+ _i as N,
5826
5826
  Lo as a,
5827
5827
  Tn as b,
5828
5828
  Mn as c,
5829
5829
  ro as d,
5830
5830
  Jr as e,
5831
- ao as f,
5832
- Ui as g,
5831
+ lo as f,
5832
+ Ri as g,
5833
5833
  Dn as h,
5834
- Un as i,
5834
+ Rn as i,
5835
5835
  vn as j,
5836
5836
  mo as k,
5837
5837
  zn as l,