@doist/todoist-ai 2.2.2 → 4.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (202) hide show
  1. package/README.md +6 -14
  2. package/dist/index.d.ts +619 -250
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +45 -29
  5. package/dist/main.js +2 -1
  6. package/dist/mcp-helpers.d.ts +25 -3
  7. package/dist/mcp-helpers.d.ts.map +1 -1
  8. package/dist/mcp-helpers.js +37 -19
  9. package/dist/mcp-server.d.ts.map +1 -1
  10. package/dist/mcp-server.js +44 -28
  11. package/dist/tools/__tests__/add-comments.test.d.ts +2 -0
  12. package/dist/tools/__tests__/add-comments.test.d.ts.map +1 -0
  13. package/dist/tools/__tests__/add-comments.test.js +241 -0
  14. package/dist/tools/__tests__/add-projects.test.d.ts +2 -0
  15. package/dist/tools/__tests__/add-projects.test.d.ts.map +1 -0
  16. package/dist/tools/__tests__/add-projects.test.js +152 -0
  17. package/dist/tools/__tests__/add-sections.test.d.ts +2 -0
  18. package/dist/tools/__tests__/add-sections.test.d.ts.map +1 -0
  19. package/dist/tools/__tests__/add-sections.test.js +181 -0
  20. package/dist/tools/__tests__/add-tasks.test.d.ts +2 -0
  21. package/dist/tools/__tests__/add-tasks.test.d.ts.map +1 -0
  22. package/dist/tools/__tests__/{tasks-add-multiple.test.js → add-tasks.test.js} +89 -79
  23. package/dist/tools/__tests__/complete-tasks.test.d.ts +2 -0
  24. package/dist/tools/__tests__/complete-tasks.test.d.ts.map +1 -0
  25. package/dist/tools/__tests__/complete-tasks.test.js +206 -0
  26. package/dist/tools/__tests__/delete-object.test.d.ts +2 -0
  27. package/dist/tools/__tests__/delete-object.test.d.ts.map +1 -0
  28. package/dist/tools/__tests__/{delete-one.test.js → delete-object.test.js} +42 -22
  29. package/dist/tools/__tests__/find-comments.test.d.ts +2 -0
  30. package/dist/tools/__tests__/find-comments.test.d.ts.map +1 -0
  31. package/dist/tools/__tests__/find-comments.test.js +242 -0
  32. package/dist/tools/__tests__/find-completed-tasks.test.d.ts +2 -0
  33. package/dist/tools/__tests__/find-completed-tasks.test.d.ts.map +1 -0
  34. package/dist/tools/__tests__/{tasks-list-completed.test.js → find-completed-tasks.test.js} +13 -36
  35. package/dist/tools/__tests__/find-projects.test.d.ts +2 -0
  36. package/dist/tools/__tests__/find-projects.test.d.ts.map +1 -0
  37. package/dist/tools/__tests__/{projects-list.test.js → find-projects.test.js} +55 -39
  38. package/dist/tools/__tests__/find-sections.test.d.ts +2 -0
  39. package/dist/tools/__tests__/find-sections.test.d.ts.map +1 -0
  40. package/dist/tools/__tests__/{sections-search.test.js → find-sections.test.js} +64 -50
  41. package/dist/tools/__tests__/find-tasks-by-date.test.d.ts +2 -0
  42. package/dist/tools/__tests__/find-tasks-by-date.test.d.ts.map +1 -0
  43. package/dist/tools/__tests__/{tasks-list-by-date.test.js → find-tasks-by-date.test.js} +96 -14
  44. package/dist/tools/__tests__/find-tasks.test.d.ts +2 -0
  45. package/dist/tools/__tests__/find-tasks.test.d.ts.map +1 -0
  46. package/dist/tools/__tests__/find-tasks.test.js +334 -0
  47. package/dist/tools/__tests__/get-overview.test.d.ts +2 -0
  48. package/dist/tools/__tests__/get-overview.test.d.ts.map +1 -0
  49. package/dist/tools/__tests__/{overview.test.js → get-overview.test.js} +77 -13
  50. package/dist/tools/__tests__/update-comments.test.d.ts +2 -0
  51. package/dist/tools/__tests__/update-comments.test.d.ts.map +1 -0
  52. package/dist/tools/__tests__/update-comments.test.js +296 -0
  53. package/dist/tools/__tests__/update-projects.test.d.ts +2 -0
  54. package/dist/tools/__tests__/update-projects.test.d.ts.map +1 -0
  55. package/dist/tools/__tests__/update-projects.test.js +205 -0
  56. package/dist/tools/__tests__/update-sections.test.d.ts +2 -0
  57. package/dist/tools/__tests__/update-sections.test.d.ts.map +1 -0
  58. package/dist/tools/__tests__/update-sections.test.js +156 -0
  59. package/dist/tools/__tests__/update-tasks.test.d.ts +2 -0
  60. package/dist/tools/__tests__/update-tasks.test.d.ts.map +1 -0
  61. package/dist/tools/__tests__/update-tasks.test.js +645 -0
  62. package/dist/tools/add-comments.d.ts +51 -0
  63. package/dist/tools/add-comments.d.ts.map +1 -0
  64. package/dist/tools/add-comments.js +79 -0
  65. package/dist/tools/add-projects.d.ts +50 -0
  66. package/dist/tools/add-projects.d.ts.map +1 -0
  67. package/dist/tools/add-projects.js +59 -0
  68. package/dist/tools/add-sections.d.ts +46 -0
  69. package/dist/tools/add-sections.d.ts.map +1 -0
  70. package/dist/tools/add-sections.js +61 -0
  71. package/dist/tools/add-tasks.d.ts +82 -0
  72. package/dist/tools/add-tasks.d.ts.map +1 -0
  73. package/dist/tools/add-tasks.js +96 -0
  74. package/dist/tools/complete-tasks.d.ts +40 -0
  75. package/dist/tools/complete-tasks.d.ts.map +1 -0
  76. package/dist/tools/complete-tasks.js +68 -0
  77. package/dist/tools/delete-object.d.ts +38 -0
  78. package/dist/tools/delete-object.d.ts.map +1 -0
  79. package/dist/tools/delete-object.js +79 -0
  80. package/dist/tools/find-comments.d.ts +46 -0
  81. package/dist/tools/find-comments.d.ts.map +1 -0
  82. package/dist/tools/find-comments.js +143 -0
  83. package/dist/tools/find-completed-tasks.d.ts +74 -0
  84. package/dist/tools/find-completed-tasks.d.ts.map +1 -0
  85. package/dist/tools/find-completed-tasks.js +112 -0
  86. package/dist/tools/find-projects.d.ts +53 -0
  87. package/dist/tools/find-projects.d.ts.map +1 -0
  88. package/dist/tools/find-projects.js +101 -0
  89. package/dist/tools/find-sections.d.ts +42 -0
  90. package/dist/tools/find-sections.d.ts.map +1 -0
  91. package/dist/tools/find-sections.js +96 -0
  92. package/dist/tools/find-tasks-by-date.d.ts +59 -0
  93. package/dist/tools/find-tasks-by-date.d.ts.map +1 -0
  94. package/dist/tools/find-tasks-by-date.js +121 -0
  95. package/dist/tools/find-tasks.d.ts +65 -0
  96. package/dist/tools/find-tasks.d.ts.map +1 -0
  97. package/dist/tools/find-tasks.js +182 -0
  98. package/dist/tools/get-overview.d.ts +67 -0
  99. package/dist/tools/get-overview.d.ts.map +1 -0
  100. package/dist/tools/{overview.js → get-overview.js} +66 -19
  101. package/dist/tools/update-comments.d.ts +50 -0
  102. package/dist/tools/update-comments.d.ts.map +1 -0
  103. package/dist/tools/update-comments.js +82 -0
  104. package/dist/tools/update-projects.d.ts +59 -0
  105. package/dist/tools/update-projects.d.ts.map +1 -0
  106. package/dist/tools/update-projects.js +84 -0
  107. package/dist/tools/update-sections.d.ts +47 -0
  108. package/dist/tools/update-sections.d.ts.map +1 -0
  109. package/dist/tools/update-sections.js +70 -0
  110. package/dist/tools/update-tasks.d.ts +94 -0
  111. package/dist/tools/update-tasks.d.ts.map +1 -0
  112. package/dist/tools/update-tasks.js +120 -0
  113. package/dist/utils/constants.d.ts +39 -0
  114. package/dist/utils/constants.d.ts.map +1 -0
  115. package/dist/utils/constants.js +41 -0
  116. package/dist/utils/response-builders.d.ts +88 -0
  117. package/dist/utils/response-builders.d.ts.map +1 -0
  118. package/dist/utils/response-builders.js +202 -0
  119. package/dist/{tools → utils}/test-helpers.d.ts +16 -0
  120. package/dist/utils/test-helpers.d.ts.map +1 -0
  121. package/dist/{tools → utils}/test-helpers.js +51 -0
  122. package/dist/utils/tool-names.d.ts +28 -0
  123. package/dist/utils/tool-names.d.ts.map +1 -0
  124. package/dist/utils/tool-names.js +31 -0
  125. package/package.json +1 -1
  126. package/dist/tools/__tests__/delete-one.test.d.ts +0 -2
  127. package/dist/tools/__tests__/delete-one.test.d.ts.map +0 -1
  128. package/dist/tools/__tests__/overview.test.d.ts +0 -2
  129. package/dist/tools/__tests__/overview.test.d.ts.map +0 -1
  130. package/dist/tools/__tests__/projects-list.test.d.ts +0 -2
  131. package/dist/tools/__tests__/projects-list.test.d.ts.map +0 -1
  132. package/dist/tools/__tests__/projects-manage.test.d.ts +0 -2
  133. package/dist/tools/__tests__/projects-manage.test.d.ts.map +0 -1
  134. package/dist/tools/__tests__/projects-manage.test.js +0 -106
  135. package/dist/tools/__tests__/sections-manage.test.d.ts +0 -2
  136. package/dist/tools/__tests__/sections-manage.test.d.ts.map +0 -1
  137. package/dist/tools/__tests__/sections-manage.test.js +0 -138
  138. package/dist/tools/__tests__/sections-search.test.d.ts +0 -2
  139. package/dist/tools/__tests__/sections-search.test.d.ts.map +0 -1
  140. package/dist/tools/__tests__/tasks-add-multiple.test.d.ts +0 -2
  141. package/dist/tools/__tests__/tasks-add-multiple.test.d.ts.map +0 -1
  142. package/dist/tools/__tests__/tasks-complete-multiple.test.d.ts +0 -2
  143. package/dist/tools/__tests__/tasks-complete-multiple.test.d.ts.map +0 -1
  144. package/dist/tools/__tests__/tasks-complete-multiple.test.js +0 -146
  145. package/dist/tools/__tests__/tasks-list-by-date.test.d.ts +0 -2
  146. package/dist/tools/__tests__/tasks-list-by-date.test.d.ts.map +0 -1
  147. package/dist/tools/__tests__/tasks-list-completed.test.d.ts +0 -2
  148. package/dist/tools/__tests__/tasks-list-completed.test.d.ts.map +0 -1
  149. package/dist/tools/__tests__/tasks-list-for-container.test.d.ts +0 -2
  150. package/dist/tools/__tests__/tasks-list-for-container.test.d.ts.map +0 -1
  151. package/dist/tools/__tests__/tasks-list-for-container.test.js +0 -232
  152. package/dist/tools/__tests__/tasks-organize-multiple.test.d.ts +0 -2
  153. package/dist/tools/__tests__/tasks-organize-multiple.test.d.ts.map +0 -1
  154. package/dist/tools/__tests__/tasks-organize-multiple.test.js +0 -245
  155. package/dist/tools/__tests__/tasks-search.test.d.ts +0 -2
  156. package/dist/tools/__tests__/tasks-search.test.d.ts.map +0 -1
  157. package/dist/tools/__tests__/tasks-search.test.js +0 -106
  158. package/dist/tools/__tests__/tasks-update-one.test.d.ts +0 -2
  159. package/dist/tools/__tests__/tasks-update-one.test.d.ts.map +0 -1
  160. package/dist/tools/__tests__/tasks-update-one.test.js +0 -251
  161. package/dist/tools/delete-one.d.ts +0 -17
  162. package/dist/tools/delete-one.d.ts.map +0 -1
  163. package/dist/tools/delete-one.js +0 -25
  164. package/dist/tools/overview.d.ts +0 -14
  165. package/dist/tools/overview.d.ts.map +0 -1
  166. package/dist/tools/projects-list.d.ts +0 -29
  167. package/dist/tools/projects-list.d.ts.map +0 -1
  168. package/dist/tools/projects-list.js +0 -39
  169. package/dist/tools/projects-manage.d.ts +0 -24
  170. package/dist/tools/projects-manage.d.ts.map +0 -1
  171. package/dist/tools/projects-manage.js +0 -26
  172. package/dist/tools/sections-manage.d.ts +0 -23
  173. package/dist/tools/sections-manage.d.ts.map +0 -1
  174. package/dist/tools/sections-manage.js +0 -37
  175. package/dist/tools/sections-search.d.ts +0 -18
  176. package/dist/tools/sections-search.d.ts.map +0 -1
  177. package/dist/tools/sections-search.js +0 -27
  178. package/dist/tools/tasks-add-multiple.d.ts +0 -55
  179. package/dist/tools/tasks-add-multiple.d.ts.map +0 -1
  180. package/dist/tools/tasks-add-multiple.js +0 -52
  181. package/dist/tools/tasks-complete-multiple.d.ts +0 -16
  182. package/dist/tools/tasks-complete-multiple.d.ts.map +0 -1
  183. package/dist/tools/tasks-complete-multiple.js +0 -23
  184. package/dist/tools/tasks-list-by-date.d.ts +0 -34
  185. package/dist/tools/tasks-list-by-date.d.ts.map +0 -1
  186. package/dist/tools/tasks-list-by-date.js +0 -53
  187. package/dist/tools/tasks-list-completed.d.ts +0 -44
  188. package/dist/tools/tasks-list-completed.d.ts.map +0 -1
  189. package/dist/tools/tasks-list-completed.js +0 -49
  190. package/dist/tools/tasks-list-for-container.d.ts +0 -34
  191. package/dist/tools/tasks-list-for-container.d.ts.map +0 -1
  192. package/dist/tools/tasks-list-for-container.js +0 -48
  193. package/dist/tools/tasks-organize-multiple.d.ts +0 -37
  194. package/dist/tools/tasks-organize-multiple.d.ts.map +0 -1
  195. package/dist/tools/tasks-organize-multiple.js +0 -34
  196. package/dist/tools/tasks-search.d.ts +0 -32
  197. package/dist/tools/tasks-search.d.ts.map +0 -1
  198. package/dist/tools/tasks-search.js +0 -30
  199. package/dist/tools/tasks-update-one.d.ts +0 -29
  200. package/dist/tools/tasks-update-one.d.ts.map +0 -1
  201. package/dist/tools/tasks-update-one.js +0 -63
  202. package/dist/tools/test-helpers.d.ts.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAE9C,OAAO,EAAE,SAAS,EAAE,MAAM,uBAAuB,CAAA;AACjD,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAA;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAE3D,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAC3D,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAE3D,OAAO,EAAE,QAAQ,EAAE,MAAM,qBAAqB,CAAA;AAC9C,OAAO,EAAE,gBAAgB,EAAE,MAAM,+BAA+B,CAAA;AAChE,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAA;AAC1E,OAAO,EAAE,eAAe,EAAE,MAAM,+BAA+B,CAAA;AAC/D,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAA;AACpE,OAAO,EAAE,qBAAqB,EAAE,MAAM,qCAAqC,CAAA;AAC3E,OAAO,EAAE,qBAAqB,EAAE,MAAM,oCAAoC,CAAA;AAC1E,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAA;AACrD,OAAO,EAAE,cAAc,EAAE,MAAM,6BAA6B,CAAA;AAE5D,QAAA,MAAM,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAeV,CAAA;AAED,OAAO,EAAE,KAAK,EAAE,YAAY,EAAE,CAAA;AAE9B,OAAO,EACH,YAAY,EACZ,cAAc,EACd,SAAS,EACT,cAAc,EACd,cAAc,EACd,eAAe,EACf,qBAAqB,EACrB,kBAAkB,EAClB,qBAAqB,EACrB,WAAW,EACX,gBAAgB,EAChB,cAAc,EACd,qBAAqB,EACrB,QAAQ,GACX,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAG9C,OAAO,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAA;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAA;AACzD,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAA;AACpE,OAAO,EAAE,eAAe,EAAE,MAAM,+BAA+B,CAAA;AAC/D,OAAO,EAAE,SAAS,EAAE,MAAM,uBAAuB,CAAA;AACjD,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAA;AAGrD,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAA;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAA;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAG3D,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAA;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAA;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAA;AAG3D,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAA;AACvD,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAA;AAErD,QAAA,MAAM,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAmBV,CAAA;AAED,OAAO,EAAE,KAAK,EAAE,YAAY,EAAE,CAAA;AAE9B,OAAO,EAEH,QAAQ,EACR,aAAa,EACb,WAAW,EACX,SAAS,EACT,eAAe,EACf,kBAAkB,EAElB,WAAW,EACX,cAAc,EACd,YAAY,EAEZ,WAAW,EACX,cAAc,EACd,YAAY,EAEZ,WAAW,EACX,YAAY,GACf,CAAA"}
package/dist/index.js CHANGED
@@ -1,33 +1,49 @@
1
1
  import { getMcpServer } from './mcp-server.js';
2
- import { deleteOne } from './tools/delete-one.js';
3
- import { projectsList } from './tools/projects-list.js';
4
- import { projectsManage } from './tools/projects-manage.js';
5
- import { sectionsManage } from './tools/sections-manage.js';
6
- import { sectionsSearch } from './tools/sections-search.js';
7
- import { overview } from './tools/overview.js';
8
- import { tasksAddMultiple } from './tools/tasks-add-multiple.js';
9
- import { tasksCompleteMultiple } from './tools/tasks-complete-multiple.js';
10
- import { tasksListByDate } from './tools/tasks-list-by-date.js';
11
- import { tasksListCompleted } from './tools/tasks-list-completed.js';
12
- import { tasksListForContainer } from './tools/tasks-list-for-container.js';
13
- import { tasksOrganizeMultiple } from './tools/tasks-organize-multiple.js';
14
- import { tasksSearch } from './tools/tasks-search.js';
15
- import { tasksUpdateOne } from './tools/tasks-update-one.js';
2
+ // Task management tools
3
+ import { addTasks } from './tools/add-tasks.js';
4
+ import { completeTasks } from './tools/complete-tasks.js';
5
+ import { findCompletedTasks } from './tools/find-completed-tasks.js';
6
+ import { findTasksByDate } from './tools/find-tasks-by-date.js';
7
+ import { findTasks } from './tools/find-tasks.js';
8
+ import { updateTasks } from './tools/update-tasks.js';
9
+ // Project management tools
10
+ import { addProjects } from './tools/add-projects.js';
11
+ import { findProjects } from './tools/find-projects.js';
12
+ import { updateProjects } from './tools/update-projects.js';
13
+ // Section management tools
14
+ import { addSections } from './tools/add-sections.js';
15
+ import { findSections } from './tools/find-sections.js';
16
+ import { updateSections } from './tools/update-sections.js';
17
+ // General tools
18
+ import { deleteObject } from './tools/delete-object.js';
19
+ import { getOverview } from './tools/get-overview.js';
16
20
  const tools = {
17
- projectsList,
18
- projectsManage,
19
- deleteOne,
20
- sectionsSearch,
21
- sectionsManage,
22
- tasksListByDate,
23
- tasksListCompleted,
24
- tasksListForContainer,
25
- tasksCompleteMultiple,
26
- tasksSearch,
27
- tasksAddMultiple,
28
- tasksUpdateOne,
29
- tasksOrganizeMultiple,
30
- overview,
21
+ // Task management tools
22
+ addTasks,
23
+ completeTasks,
24
+ updateTasks,
25
+ findTasks,
26
+ findTasksByDate,
27
+ findCompletedTasks,
28
+ // Project management tools
29
+ addProjects,
30
+ updateProjects,
31
+ findProjects,
32
+ // Section management tools
33
+ addSections,
34
+ updateSections,
35
+ findSections,
36
+ // General tools
37
+ getOverview,
38
+ deleteObject,
31
39
  };
32
40
  export { tools, getMcpServer };
33
- export { projectsList, projectsManage, deleteOne, sectionsSearch, sectionsManage, tasksListByDate, tasksListForContainer, tasksListCompleted, tasksCompleteMultiple, tasksSearch, tasksAddMultiple, tasksUpdateOne, tasksOrganizeMultiple, overview, };
41
+ export {
42
+ // Task management tools
43
+ addTasks, completeTasks, updateTasks, findTasks, findTasksByDate, findCompletedTasks,
44
+ // Project management tools
45
+ addProjects, updateProjects, findProjects,
46
+ // Section management tools
47
+ addSections, updateSections, findSections,
48
+ // General tools
49
+ getOverview, deleteObject, };
package/dist/main.js CHANGED
@@ -3,11 +3,12 @@ import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js'
3
3
  import dotenv from 'dotenv';
4
4
  import { getMcpServer } from './mcp-server.js';
5
5
  function main() {
6
+ const baseUrl = process.env.TODOIST_BASE_URL;
6
7
  const todoistApiKey = process.env.TODOIST_API_KEY;
7
8
  if (!todoistApiKey) {
8
9
  throw new Error('TODOIST_API_KEY is not set');
9
10
  }
10
- const server = getMcpServer({ todoistApiKey });
11
+ const server = getMcpServer({ todoistApiKey, baseUrl });
11
12
  const transport = new StdioServerTransport();
12
13
  server
13
14
  .connect(transport)
@@ -2,12 +2,34 @@ import type { TodoistApi } from '@doist/todoist-api-typescript';
2
2
  import type { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
3
3
  import type { z } from 'zod';
4
4
  import type { TodoistTool } from './todoist-tool.js';
5
- declare function errorContent(error: string): {
6
- isError: boolean;
5
+ /**
6
+ * Get the output payload for a tool, in the correct format expected by MCP client apps.
7
+ *
8
+ * @param textContent - The text content to return.
9
+ * @param structuredContent - The structured content to return.
10
+ * @returns The output payload.
11
+ * @see USE_STRUCTURED_CONTENT - Wether to use the structured content feature of the MCP protocol.
12
+ */
13
+ declare function getToolOutput<StructuredContent extends Record<string, unknown>>({ textContent, structuredContent, }: {
14
+ textContent: string;
15
+ structuredContent: StructuredContent;
16
+ }): {
7
17
  content: {
8
18
  type: "text";
9
19
  text: string;
10
20
  }[];
21
+ structuredContent: StructuredContent;
22
+ } | {
23
+ content: ({
24
+ type: "text";
25
+ text: string;
26
+ mimeType?: undefined;
27
+ } | {
28
+ type: "text";
29
+ mimeType: string;
30
+ text: string;
31
+ })[];
32
+ structuredContent?: undefined;
11
33
  };
12
34
  /**
13
35
  * Register a Todoist tool in an MCP server.
@@ -16,5 +38,5 @@ declare function errorContent(error: string): {
16
38
  * @param client - The Todoist API client to use to execute the tool.
17
39
  */
18
40
  declare function registerTool<Params extends z.ZodRawShape>(tool: TodoistTool<Params>, server: McpServer, client: TodoistApi): void;
19
- export { registerTool, errorContent };
41
+ export { registerTool, getToolOutput };
20
42
  //# sourceMappingURL=mcp-helpers.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"mcp-helpers.d.ts","sourceRoot":"","sources":["../src/mcp-helpers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,+BAA+B,CAAA;AAC/D,OAAO,KAAK,EAAE,SAAS,EAAgB,MAAM,yCAAyC,CAAA;AACtF,OAAO,KAAK,EAAc,CAAC,EAAE,MAAM,KAAK,CAAA;AACxC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AAwBpD,iBAAS,YAAY,CAAC,KAAK,EAAE,MAAM;;;;;;EAKlC;AAED;;;;;GAKG;AACH,iBAAS,YAAY,CAAC,MAAM,SAAS,CAAC,CAAC,WAAW,EAC9C,IAAI,EAAE,WAAW,CAAC,MAAM,CAAC,EACzB,MAAM,EAAE,SAAS,EACjB,MAAM,EAAE,UAAU,QAqBrB;AAED,OAAO,EAAE,YAAY,EAAE,YAAY,EAAE,CAAA"}
1
+ {"version":3,"file":"mcp-helpers.d.ts","sourceRoot":"","sources":["../src/mcp-helpers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,+BAA+B,CAAA;AAC/D,OAAO,KAAK,EAAE,SAAS,EAAgB,MAAM,yCAAyC,CAAA;AACtF,OAAO,KAAK,EAAc,CAAC,EAAE,MAAM,KAAK,CAAA;AACxC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AAkBpD;;;;;;;GAOG;AACH,iBAAS,aAAa,CAAC,iBAAiB,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,EACtE,WAAW,EACX,iBAAiB,GACpB,EAAE;IAAE,WAAW,EAAE,MAAM,CAAC;IAAC,iBAAiB,EAAE,iBAAiB,CAAA;CAAE;;;;;;;;;;;;;;;;;EAe/D;AASD;;;;;GAKG;AACH,iBAAS,YAAY,CAAC,MAAM,SAAS,CAAC,CAAC,WAAW,EAC9C,IAAI,EAAE,WAAW,CAAC,MAAM,CAAC,EACzB,MAAM,EAAE,SAAS,EACjB,MAAM,EAAE,UAAU,QAqBrB;AAED,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,CAAA"}
@@ -1,25 +1,43 @@
1
- function textContent(text) {
2
- return {
3
- content: [{ type: 'text', text }],
4
- };
5
- }
6
- function jsonContent(data) {
1
+ /**
2
+ * Wether to return the structured content directly, vs. in the `content` part of the output.
3
+ *
4
+ * The `structuredContent` part of the output is relatively new in the spec, and it's not yet
5
+ * supported by all clients. This flag controls wether we return the structured content using this
6
+ * new feature of the MCP protocol or not.
7
+ *
8
+ * If `false`, the `structuredContent` will be returned as stringified JSON in one of the `content`
9
+ * parts.
10
+ *
11
+ * Eventually we should be able to remove this, and change the code to always work with the
12
+ * structured content returned directly, once most or all MCP clients support it.
13
+ */
14
+ const USE_STRUCTURED_CONTENT = process.env.USE_STRUCTURED_CONTENT === 'true' || process.env.NODE_ENV === 'test';
15
+ /**
16
+ * Get the output payload for a tool, in the correct format expected by MCP client apps.
17
+ *
18
+ * @param textContent - The text content to return.
19
+ * @param structuredContent - The structured content to return.
20
+ * @returns The output payload.
21
+ * @see USE_STRUCTURED_CONTENT - Wether to use the structured content feature of the MCP protocol.
22
+ */
23
+ function getToolOutput({ textContent, structuredContent, }) {
24
+ if (USE_STRUCTURED_CONTENT) {
25
+ return {
26
+ content: [{ type: 'text', text: textContent }],
27
+ structuredContent,
28
+ };
29
+ }
30
+ const json = JSON.stringify(structuredContent);
7
31
  return {
8
32
  content: [
9
- {
10
- type: 'text',
11
- mimeType: 'application/json',
12
- text: JSON.stringify(data, null, 2),
13
- },
33
+ { type: 'text', text: textContent },
34
+ { type: 'text', mimeType: 'application/json', text: json },
14
35
  ],
15
36
  };
16
37
  }
17
- function textOrJsonContent(data) {
18
- return typeof data === 'string' ? textContent(data) : jsonContent(data);
19
- }
20
- function errorContent(error) {
38
+ function getErrorOutput(error) {
21
39
  return {
22
- ...textContent(error),
40
+ content: [{ type: 'text', text: error }],
23
41
  isError: true,
24
42
  };
25
43
  }
@@ -34,7 +52,7 @@ function registerTool(tool, server, client) {
34
52
  const cb = async (args, _context) => {
35
53
  try {
36
54
  const result = await tool.execute(args, client);
37
- return textOrJsonContent(result);
55
+ return result;
38
56
  }
39
57
  catch (error) {
40
58
  console.error(`Error executing tool ${tool.name}:`, {
@@ -42,9 +60,9 @@ function registerTool(tool, server, client) {
42
60
  error,
43
61
  });
44
62
  const message = error instanceof Error ? error.message : 'An unknown error occurred';
45
- return errorContent(message);
63
+ return getErrorOutput(message);
46
64
  }
47
65
  };
48
66
  server.tool(tool.name, tool.description, tool.parameters, cb);
49
67
  }
50
- export { registerTool, errorContent };
68
+ export { registerTool, getToolOutput };
@@ -1 +1 @@
1
- {"version":3,"file":"mcp-server.d.ts","sourceRoot":"","sources":["../src/mcp-server.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AAwBnE;;;;;GAKG;AACH,iBAAS,YAAY,CAAC,EAAE,aAAa,EAAE,OAAO,EAAE,EAAE;IAAE,aAAa,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAE,aA6B5F;AAED,OAAO,EAAE,YAAY,EAAE,CAAA"}
1
+ {"version":3,"file":"mcp-server.d.ts","sourceRoot":"","sources":["../src/mcp-server.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AAkCnE;;;;;GAKG;AACH,iBAAS,YAAY,CAAC,EAAE,aAAa,EAAE,OAAO,EAAE,EAAE;IAAE,aAAa,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAA;CAAE,aAyC5F;AAED,OAAO,EAAE,YAAY,EAAE,CAAA"}
@@ -1,20 +1,28 @@
1
1
  import { TodoistApi } from '@doist/todoist-api-typescript';
2
2
  import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
3
3
  import { registerTool } from './mcp-helpers.js';
4
- import { deleteOne } from './tools/delete-one.js';
5
- import { projectsList } from './tools/projects-list.js';
6
- import { projectsManage } from './tools/projects-manage.js';
7
- import { sectionsManage } from './tools/sections-manage.js';
8
- import { sectionsSearch } from './tools/sections-search.js';
9
- import { overview } from './tools/overview.js';
10
- import { tasksAddMultiple } from './tools/tasks-add-multiple.js';
11
- import { tasksCompleteMultiple } from './tools/tasks-complete-multiple.js';
12
- import { tasksListByDate } from './tools/tasks-list-by-date.js';
13
- import { tasksListCompleted } from './tools/tasks-list-completed.js';
14
- import { tasksListForContainer } from './tools/tasks-list-for-container.js';
15
- import { tasksOrganizeMultiple } from './tools/tasks-organize-multiple.js';
16
- import { tasksSearch } from './tools/tasks-search.js';
17
- import { tasksUpdateOne } from './tools/tasks-update-one.js';
4
+ // Task management tools
5
+ import { addTasks } from './tools/add-tasks.js';
6
+ import { completeTasks } from './tools/complete-tasks.js';
7
+ import { findCompletedTasks } from './tools/find-completed-tasks.js';
8
+ import { findTasksByDate } from './tools/find-tasks-by-date.js';
9
+ import { findTasks } from './tools/find-tasks.js';
10
+ import { updateTasks } from './tools/update-tasks.js';
11
+ // Project management tools
12
+ import { addProjects } from './tools/add-projects.js';
13
+ import { findProjects } from './tools/find-projects.js';
14
+ import { updateProjects } from './tools/update-projects.js';
15
+ // Section management tools
16
+ import { addSections } from './tools/add-sections.js';
17
+ import { findSections } from './tools/find-sections.js';
18
+ import { updateSections } from './tools/update-sections.js';
19
+ // Comment management tools
20
+ import { addComments } from './tools/add-comments.js';
21
+ import { findComments } from './tools/find-comments.js';
22
+ import { updateComments } from './tools/update-comments.js';
23
+ // General tools
24
+ import { deleteObject } from './tools/delete-object.js';
25
+ import { getOverview } from './tools/get-overview.js';
18
26
  const instructions = `
19
27
  Tools to help you manage your todoist tasks.
20
28
  `;
@@ -32,20 +40,28 @@ function getMcpServer({ todoistApiKey, baseUrl }) {
32
40
  instructions,
33
41
  });
34
42
  const todoist = new TodoistApi(todoistApiKey, baseUrl);
35
- registerTool(tasksListCompleted, server, todoist);
36
- registerTool(tasksListByDate, server, todoist);
37
- registerTool(tasksSearch, server, todoist);
38
- registerTool(projectsList, server, todoist);
39
- registerTool(tasksAddMultiple, server, todoist);
40
- registerTool(tasksUpdateOne, server, todoist);
41
- registerTool(deleteOne, server, todoist);
42
- registerTool(tasksCompleteMultiple, server, todoist);
43
- registerTool(projectsManage, server, todoist);
44
- registerTool(sectionsManage, server, todoist);
45
- registerTool(tasksOrganizeMultiple, server, todoist);
46
- registerTool(sectionsSearch, server, todoist);
47
- registerTool(overview, server, todoist);
48
- registerTool(tasksListForContainer, server, todoist);
43
+ // Task management tools
44
+ registerTool(addTasks, server, todoist);
45
+ registerTool(completeTasks, server, todoist);
46
+ registerTool(updateTasks, server, todoist);
47
+ registerTool(findTasks, server, todoist);
48
+ registerTool(findTasksByDate, server, todoist);
49
+ registerTool(findCompletedTasks, server, todoist);
50
+ // Project management tools
51
+ registerTool(addProjects, server, todoist);
52
+ registerTool(updateProjects, server, todoist);
53
+ registerTool(findProjects, server, todoist);
54
+ // Section management tools
55
+ registerTool(addSections, server, todoist);
56
+ registerTool(updateSections, server, todoist);
57
+ registerTool(findSections, server, todoist);
58
+ // Comment management tools
59
+ registerTool(addComments, server, todoist);
60
+ registerTool(findComments, server, todoist);
61
+ registerTool(updateComments, server, todoist);
62
+ // General tools
63
+ registerTool(getOverview, server, todoist);
64
+ registerTool(deleteObject, server, todoist);
49
65
  return server;
50
66
  }
51
67
  export { getMcpServer };
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=add-comments.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"add-comments.test.d.ts","sourceRoot":"","sources":["../../../src/tools/__tests__/add-comments.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,241 @@
1
+ import { jest } from '@jest/globals';
2
+ import { extractStructuredContent, extractTextContent } from '../../utils/test-helpers.js';
3
+ import { ToolNames } from '../../utils/tool-names.js';
4
+ import { addComments } from '../add-comments.js';
5
+ // Mock the Todoist API
6
+ const mockTodoistApi = {
7
+ addComment: jest.fn(),
8
+ };
9
+ const { ADD_COMMENTS } = ToolNames;
10
+ const createMockComment = (overrides = {}) => ({
11
+ id: '12345',
12
+ content: 'Test comment content',
13
+ postedAt: '2024-01-01T12:00:00Z',
14
+ postedUid: 'user123',
15
+ taskId: 'task123',
16
+ projectId: undefined,
17
+ fileAttachment: null,
18
+ uidsToNotify: null,
19
+ reactions: null,
20
+ isDeleted: false,
21
+ ...overrides,
22
+ });
23
+ describe(`${ADD_COMMENTS} tool`, () => {
24
+ beforeEach(() => {
25
+ jest.clearAllMocks();
26
+ });
27
+ describe('adding comments to tasks', () => {
28
+ it('should add comment to task', async () => {
29
+ const mockComment = createMockComment({
30
+ id: '98765',
31
+ content: 'This is a task comment',
32
+ taskId: 'task456',
33
+ });
34
+ mockTodoistApi.addComment.mockResolvedValue(mockComment);
35
+ const result = await addComments.execute({ comments: [{ taskId: 'task456', content: 'This is a task comment' }] }, mockTodoistApi);
36
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
37
+ content: 'This is a task comment',
38
+ taskId: 'task456',
39
+ });
40
+ // Verify result is a concise summary
41
+ expect(extractTextContent(result)).toMatchSnapshot();
42
+ // Verify structured content
43
+ const structuredContent = extractStructuredContent(result);
44
+ expect(structuredContent).toEqual(expect.objectContaining({
45
+ comments: [
46
+ expect.objectContaining({
47
+ id: '98765',
48
+ content: 'This is a task comment',
49
+ taskId: 'task456',
50
+ }),
51
+ ],
52
+ totalCount: 1,
53
+ addedCommentIds: ['98765'],
54
+ }));
55
+ });
56
+ });
57
+ describe('adding comments to projects', () => {
58
+ it('should add comment to project', async () => {
59
+ const mockComment = createMockComment({
60
+ id: '98767',
61
+ content: 'This is a project comment',
62
+ taskId: undefined,
63
+ projectId: 'project789',
64
+ });
65
+ mockTodoistApi.addComment.mockResolvedValue(mockComment);
66
+ const result = await addComments.execute({ comments: [{ projectId: 'project789', content: 'This is a project comment' }] }, mockTodoistApi);
67
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
68
+ content: 'This is a project comment',
69
+ projectId: 'project789',
70
+ });
71
+ // Verify result is a concise summary
72
+ expect(extractTextContent(result)).toMatchSnapshot();
73
+ // Verify structured content
74
+ const structuredContent = extractStructuredContent(result);
75
+ expect(structuredContent).toEqual(expect.objectContaining({
76
+ comments: [
77
+ expect.objectContaining({
78
+ id: '98767',
79
+ content: 'This is a project comment',
80
+ taskId: undefined,
81
+ projectId: 'project789',
82
+ }),
83
+ ],
84
+ totalCount: 1,
85
+ addedCommentIds: ['98767'],
86
+ }));
87
+ });
88
+ });
89
+ describe('bulk operations', () => {
90
+ it('should add multiple comments to different entities (task + project)', async () => {
91
+ const mockTaskComment = createMockComment({
92
+ id: '11111',
93
+ content: 'Task comment',
94
+ taskId: 'task123',
95
+ projectId: undefined,
96
+ });
97
+ const mockProjectComment = createMockComment({
98
+ id: '22222',
99
+ content: 'Project comment',
100
+ taskId: undefined,
101
+ projectId: 'project456',
102
+ });
103
+ mockTodoistApi.addComment
104
+ .mockResolvedValueOnce(mockTaskComment)
105
+ .mockResolvedValueOnce(mockProjectComment);
106
+ const result = await addComments.execute({
107
+ comments: [
108
+ { taskId: 'task123', content: 'Task comment' },
109
+ { projectId: 'project456', content: 'Project comment' },
110
+ ],
111
+ }, mockTodoistApi);
112
+ expect(mockTodoistApi.addComment).toHaveBeenCalledTimes(2);
113
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
114
+ content: 'Task comment',
115
+ taskId: 'task123',
116
+ });
117
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
118
+ content: 'Project comment',
119
+ projectId: 'project456',
120
+ });
121
+ // Verify result is a concise summary
122
+ expect(extractTextContent(result)).toMatchSnapshot();
123
+ const structuredContent = extractStructuredContent(result);
124
+ expect(structuredContent).toEqual(expect.objectContaining({
125
+ comments: [
126
+ expect.objectContaining({
127
+ id: '11111',
128
+ content: 'Task comment',
129
+ taskId: 'task123',
130
+ }),
131
+ expect.objectContaining({
132
+ id: '22222',
133
+ content: 'Project comment',
134
+ projectId: 'project456',
135
+ }),
136
+ ],
137
+ totalCount: 2,
138
+ addedCommentIds: ['11111', '22222'],
139
+ }));
140
+ });
141
+ it('should add multiple comments to different tasks', async () => {
142
+ const mockComment1 = createMockComment({
143
+ id: '33333',
144
+ content: 'First task comment',
145
+ taskId: 'task111',
146
+ });
147
+ const mockComment2 = createMockComment({
148
+ id: '44444',
149
+ content: 'Second task comment',
150
+ taskId: 'task222',
151
+ });
152
+ mockTodoistApi.addComment
153
+ .mockResolvedValueOnce(mockComment1)
154
+ .mockResolvedValueOnce(mockComment2);
155
+ const result = await addComments.execute({
156
+ comments: [
157
+ { taskId: 'task111', content: 'First task comment' },
158
+ { taskId: 'task222', content: 'Second task comment' },
159
+ ],
160
+ }, mockTodoistApi);
161
+ expect(mockTodoistApi.addComment).toHaveBeenCalledTimes(2);
162
+ // Verify result is a concise summary
163
+ expect(extractTextContent(result)).toMatchSnapshot();
164
+ const structuredContent = extractStructuredContent(result);
165
+ expect(structuredContent).toEqual(expect.objectContaining({
166
+ comments: expect.arrayContaining([
167
+ expect.objectContaining({
168
+ id: '33333',
169
+ content: 'First task comment',
170
+ taskId: 'task111',
171
+ }),
172
+ expect.objectContaining({
173
+ id: '44444',
174
+ content: 'Second task comment',
175
+ taskId: 'task222',
176
+ }),
177
+ ]),
178
+ totalCount: 2,
179
+ addedCommentIds: ['33333', '44444'],
180
+ }));
181
+ });
182
+ it('should add multiple comments to the same task', async () => {
183
+ const mockComment1 = createMockComment({
184
+ id: '55555',
185
+ content: 'First comment on same task',
186
+ taskId: 'task999',
187
+ });
188
+ const mockComment2 = createMockComment({
189
+ id: '66666',
190
+ content: 'Second comment on same task',
191
+ taskId: 'task999',
192
+ });
193
+ mockTodoistApi.addComment
194
+ .mockResolvedValueOnce(mockComment1)
195
+ .mockResolvedValueOnce(mockComment2);
196
+ const result = await addComments.execute({
197
+ comments: [
198
+ { taskId: 'task999', content: 'First comment on same task' },
199
+ { taskId: 'task999', content: 'Second comment on same task' },
200
+ ],
201
+ }, mockTodoistApi);
202
+ expect(mockTodoistApi.addComment).toHaveBeenCalledTimes(2);
203
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
204
+ content: 'First comment on same task',
205
+ taskId: 'task999',
206
+ });
207
+ expect(mockTodoistApi.addComment).toHaveBeenCalledWith({
208
+ content: 'Second comment on same task',
209
+ taskId: 'task999',
210
+ });
211
+ // Verify result is a concise summary
212
+ expect(extractTextContent(result)).toMatchSnapshot();
213
+ const structuredContent = extractStructuredContent(result);
214
+ expect(structuredContent).toEqual(expect.objectContaining({
215
+ comments: expect.arrayContaining([
216
+ expect.objectContaining({
217
+ id: '55555',
218
+ content: 'First comment on same task',
219
+ taskId: 'task999',
220
+ }),
221
+ expect.objectContaining({
222
+ id: '66666',
223
+ content: 'Second comment on same task',
224
+ taskId: 'task999',
225
+ }),
226
+ ]),
227
+ totalCount: 2,
228
+ addedCommentIds: ['55555', '66666'],
229
+ }));
230
+ });
231
+ });
232
+ describe('validation', () => {
233
+ it('should throw error when neither taskId nor projectId provided', async () => {
234
+ await expect(addComments.execute({ comments: [{ content: 'Test comment' }] }, mockTodoistApi)).rejects.toThrow('Comment 1: Either taskId or projectId must be provided.');
235
+ });
236
+ it('should throw error when both taskId and projectId provided', async () => {
237
+ const comment = { taskId: 'task123', projectId: 'project456', content: 'Test comment' };
238
+ await expect(addComments.execute({ comments: [comment] }, mockTodoistApi)).rejects.toThrow('Comment 1: Cannot provide both taskId and projectId. Choose one.');
239
+ });
240
+ });
241
+ });
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=add-projects.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"add-projects.test.d.ts","sourceRoot":"","sources":["../../../src/tools/__tests__/add-projects.test.ts"],"names":[],"mappings":""}