@sanity/cli 6.0.0-alpha.3 → 6.0.0-alpha.5

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 (376) hide show
  1. package/dist/actions/auth/login/{index.js → login.js} +1 -1
  2. package/dist/actions/auth/login/{index.js.map → login.js.map} +1 -1
  3. package/dist/actions/dev/startStudioDevServer.js +3 -8
  4. package/dist/actions/dev/startStudioDevServer.js.map +1 -1
  5. package/dist/actions/dev/types.d.ts +1 -3
  6. package/dist/actions/dev/types.js.map +1 -1
  7. package/dist/actions/documents/validate.d.ts +0 -2
  8. package/dist/actions/documents/validate.js +21 -1
  9. package/dist/actions/documents/validate.js.map +1 -1
  10. package/dist/actions/exec/execScript.js +1 -1
  11. package/dist/actions/exec/execScript.js.map +1 -1
  12. package/dist/actions/graphql/__tests__/getGraphQLAPIs.test.js +1 -1
  13. package/dist/actions/graphql/__tests__/getGraphQLAPIs.test.js.map +1 -1
  14. package/dist/actions/graphql/getGraphQLAPIs.js +1 -1
  15. package/dist/actions/graphql/getGraphQLAPIs.js.map +1 -1
  16. package/dist/actions/manifest/extractManifest.js +1 -4
  17. package/dist/actions/manifest/extractManifest.js.map +1 -1
  18. package/dist/actions/organizations/getOrganizationChoices.d.ts +6 -0
  19. package/dist/actions/organizations/getOrganizationChoices.js +23 -0
  20. package/dist/actions/organizations/getOrganizationChoices.js.map +1 -0
  21. package/dist/actions/organizations/getOrganizationsWithAttachGrantInfo.d.ts +2 -0
  22. package/dist/actions/organizations/getOrganizationsWithAttachGrantInfo.js +9 -0
  23. package/dist/actions/organizations/getOrganizationsWithAttachGrantInfo.js.map +1 -0
  24. package/dist/actions/organizations/hasProjectAttachGrant.d.ts +1 -0
  25. package/dist/actions/organizations/hasProjectAttachGrant.js +24 -0
  26. package/dist/actions/organizations/hasProjectAttachGrant.js.map +1 -0
  27. package/dist/actions/schema/deleteSchemaAction.d.ts +13 -5
  28. package/dist/actions/schema/deleteSchemaAction.js +12 -17
  29. package/dist/actions/schema/deleteSchemaAction.js.map +1 -1
  30. package/dist/actions/schema/deploySchemas.d.ts +15 -0
  31. package/dist/actions/schema/deploySchemas.js +98 -0
  32. package/dist/actions/schema/deploySchemas.js.map +1 -0
  33. package/dist/actions/schema/listSchemas.d.ts +12 -0
  34. package/dist/actions/schema/listSchemas.js +119 -0
  35. package/dist/actions/schema/listSchemas.js.map +1 -0
  36. package/dist/actions/schema/schemaStoreTypes.d.ts +0 -11
  37. package/dist/actions/schema/schemaStoreTypes.js.map +1 -1
  38. package/dist/actions/schema/utils/debug.d.ts +2 -0
  39. package/dist/actions/schema/utils/debug.js +5 -0
  40. package/dist/actions/schema/utils/debug.js.map +1 -0
  41. package/dist/actions/schema/utils/manifestExtractor.d.ts +3 -8
  42. package/dist/actions/schema/utils/manifestExtractor.js +12 -17
  43. package/dist/actions/schema/utils/manifestExtractor.js.map +1 -1
  44. package/dist/actions/schema/utils/manifestReader.d.ts +2 -9
  45. package/dist/actions/schema/utils/manifestReader.js +6 -12
  46. package/dist/actions/schema/utils/manifestReader.js.map +1 -1
  47. package/dist/actions/schema/utils/schemaStoreOutStrings.d.ts +0 -1
  48. package/dist/actions/schema/utils/schemaStoreOutStrings.js +1 -1
  49. package/dist/actions/schema/utils/schemaStoreOutStrings.js.map +1 -1
  50. package/dist/actions/schema/utils/schemaStoreValidation.d.ts +10 -62
  51. package/dist/actions/schema/utils/schemaStoreValidation.js +40 -127
  52. package/dist/actions/schema/utils/schemaStoreValidation.js.map +1 -1
  53. package/dist/actions/schema/utils/uniqByProjectIdDataset.d.ts +14 -0
  54. package/dist/actions/schema/utils/uniqByProjectIdDataset.js +9 -0
  55. package/dist/actions/schema/utils/uniqByProjectIdDataset.js.map +1 -0
  56. package/dist/actions/users/getMembersForProject.d.ts +1 -3
  57. package/dist/actions/users/getMembersForProject.js +6 -17
  58. package/dist/actions/users/getMembersForProject.js.map +1 -1
  59. package/dist/actions/users/types.d.ts +0 -11
  60. package/dist/actions/users/types.js.map +1 -1
  61. package/dist/commands/__tests__/debug.test.js +113 -220
  62. package/dist/commands/__tests__/debug.test.js.map +1 -1
  63. package/dist/commands/__tests__/deploy.test.js +325 -293
  64. package/dist/commands/__tests__/deploy.test.js.map +1 -1
  65. package/dist/commands/__tests__/dev.test.js +62 -19
  66. package/dist/commands/__tests__/dev.test.js.map +1 -1
  67. package/dist/commands/__tests__/init/init.authentication.test.js +73 -0
  68. package/dist/commands/__tests__/init/init.authentication.test.js.map +1 -0
  69. package/dist/commands/__tests__/init/init.create-new-project.test.js +195 -0
  70. package/dist/commands/__tests__/init/init.create-new-project.test.js.map +1 -0
  71. package/dist/commands/__tests__/init/init.plan.test.js +279 -0
  72. package/dist/commands/__tests__/init/init.plan.test.js.map +1 -0
  73. package/dist/commands/__tests__/init/init.setup.test.js +335 -0
  74. package/dist/commands/__tests__/init/init.setup.test.js.map +1 -0
  75. package/dist/commands/__tests__/install.test.js +46 -22
  76. package/dist/commands/__tests__/install.test.js.map +1 -1
  77. package/dist/commands/__tests__/logout.test.js +8 -5
  78. package/dist/commands/__tests__/logout.test.js.map +1 -1
  79. package/dist/commands/__tests__/manage.test.js +29 -24
  80. package/dist/commands/__tests__/manage.test.js.map +1 -1
  81. package/dist/commands/__tests__/migration.test.js +119 -0
  82. package/dist/commands/__tests__/migration.test.js.map +1 -0
  83. package/dist/commands/__tests__/versions.test.js +22 -14
  84. package/dist/commands/__tests__/versions.test.js.map +1 -1
  85. package/dist/commands/backup/__tests__/disable.test.js +72 -75
  86. package/dist/commands/backup/__tests__/disable.test.js.map +1 -1
  87. package/dist/commands/backup/__tests__/download.test.js +169 -80
  88. package/dist/commands/backup/__tests__/download.test.js.map +1 -1
  89. package/dist/commands/backup/__tests__/enable.test.js +109 -140
  90. package/dist/commands/backup/__tests__/enable.test.js.map +1 -1
  91. package/dist/commands/backup/__tests__/list.test.js +84 -75
  92. package/dist/commands/backup/__tests__/list.test.js.map +1 -1
  93. package/dist/commands/backup/disable.js +5 -11
  94. package/dist/commands/backup/disable.js.map +1 -1
  95. package/dist/commands/backup/enable.js +5 -11
  96. package/dist/commands/backup/enable.js.map +1 -1
  97. package/dist/commands/backup/list.js +7 -8
  98. package/dist/commands/backup/list.js.map +1 -1
  99. package/dist/commands/cors/__tests__/add.test.js +68 -38
  100. package/dist/commands/cors/__tests__/add.test.js.map +1 -1
  101. package/dist/commands/cors/__tests__/delete.test.js +52 -37
  102. package/dist/commands/cors/__tests__/delete.test.js.map +1 -1
  103. package/dist/commands/cors/__tests__/list.test.js +80 -57
  104. package/dist/commands/cors/__tests__/list.test.js.map +1 -1
  105. package/dist/commands/cors/add.js +5 -13
  106. package/dist/commands/cors/add.js.map +1 -1
  107. package/dist/commands/cors/delete.js +7 -15
  108. package/dist/commands/cors/delete.js.map +1 -1
  109. package/dist/commands/cors/list.js +2 -10
  110. package/dist/commands/cors/list.js.map +1 -1
  111. package/dist/commands/dataset/__tests__/copy.test.js +197 -89
  112. package/dist/commands/dataset/__tests__/copy.test.js.map +1 -1
  113. package/dist/commands/dataset/__tests__/create.test.js +147 -117
  114. package/dist/commands/dataset/__tests__/create.test.js.map +1 -1
  115. package/dist/commands/dataset/__tests__/delete.test.js +75 -68
  116. package/dist/commands/dataset/__tests__/delete.test.js.map +1 -1
  117. package/dist/commands/dataset/__tests__/export.test.js +123 -83
  118. package/dist/commands/dataset/__tests__/export.test.js.map +1 -1
  119. package/dist/commands/dataset/__tests__/import.test.js +2 -2
  120. package/dist/commands/dataset/__tests__/import.test.js.map +1 -1
  121. package/dist/commands/dataset/__tests__/list.test.js +107 -65
  122. package/dist/commands/dataset/__tests__/list.test.js.map +1 -1
  123. package/dist/commands/dataset/alias/__tests__/create.test.js +114 -74
  124. package/dist/commands/dataset/alias/__tests__/create.test.js.map +1 -1
  125. package/dist/commands/dataset/alias/__tests__/delete.test.js +40 -29
  126. package/dist/commands/dataset/alias/__tests__/delete.test.js.map +1 -1
  127. package/dist/commands/dataset/alias/__tests__/link.test.js +114 -74
  128. package/dist/commands/dataset/alias/__tests__/link.test.js.map +1 -1
  129. package/dist/commands/dataset/alias/__tests__/unlink.test.js +44 -29
  130. package/dist/commands/dataset/alias/__tests__/unlink.test.js.map +1 -1
  131. package/dist/commands/dataset/export.js +4 -4
  132. package/dist/commands/dataset/export.js.map +1 -1
  133. package/dist/commands/dataset/visibility/__tests__/get.test.js +48 -67
  134. package/dist/commands/dataset/visibility/__tests__/get.test.js.map +1 -1
  135. package/dist/commands/dataset/visibility/__tests__/set.test.js +76 -123
  136. package/dist/commands/dataset/visibility/__tests__/set.test.js.map +1 -1
  137. package/dist/commands/dev.js +0 -1
  138. package/dist/commands/dev.js.map +1 -1
  139. package/dist/commands/docs/__tests__/search.test.js +8 -7
  140. package/dist/commands/docs/__tests__/search.test.js.map +1 -1
  141. package/dist/commands/documents/__tests__/create.test.js +328 -265
  142. package/dist/commands/documents/__tests__/create.test.js.map +1 -1
  143. package/dist/commands/documents/__tests__/delete.test.js +119 -87
  144. package/dist/commands/documents/__tests__/delete.test.js.map +1 -1
  145. package/dist/commands/documents/__tests__/get.test.js +68 -95
  146. package/dist/commands/documents/__tests__/get.test.js.map +1 -1
  147. package/dist/commands/documents/__tests__/query.test.js +87 -192
  148. package/dist/commands/documents/__tests__/query.test.js.map +1 -1
  149. package/dist/commands/documents/__tests__/validate.test.js +52 -29
  150. package/dist/commands/documents/__tests__/validate.test.js.map +1 -1
  151. package/dist/commands/documents/create.d.ts +1 -0
  152. package/dist/commands/documents/create.js +10 -9
  153. package/dist/commands/documents/create.js.map +1 -1
  154. package/dist/commands/documents/delete.js +2 -3
  155. package/dist/commands/documents/delete.js.map +1 -1
  156. package/dist/commands/documents/get.js +2 -3
  157. package/dist/commands/documents/get.js.map +1 -1
  158. package/dist/commands/documents/query.js +2 -3
  159. package/dist/commands/documents/query.js.map +1 -1
  160. package/dist/commands/documents/validate.js +0 -20
  161. package/dist/commands/documents/validate.js.map +1 -1
  162. package/dist/commands/graphql/__tests__/list.test.js +57 -45
  163. package/dist/commands/graphql/__tests__/list.test.js.map +1 -1
  164. package/dist/commands/graphql/__tests__/undeploy.test.js +85 -59
  165. package/dist/commands/graphql/__tests__/undeploy.test.js.map +1 -1
  166. package/dist/commands/graphql/list.js +2 -2
  167. package/dist/commands/graphql/list.js.map +1 -1
  168. package/dist/commands/graphql/undeploy.js +4 -9
  169. package/dist/commands/graphql/undeploy.js.map +1 -1
  170. package/dist/commands/hook/__tests__/attempt.test.js +48 -33
  171. package/dist/commands/hook/__tests__/attempt.test.js.map +1 -1
  172. package/dist/commands/hook/__tests__/create.test.js +49 -51
  173. package/dist/commands/hook/__tests__/create.test.js.map +1 -1
  174. package/dist/commands/hook/__tests__/delete.test.js +43 -30
  175. package/dist/commands/hook/__tests__/delete.test.js.map +1 -1
  176. package/dist/commands/hook/__tests__/list.test.js +38 -31
  177. package/dist/commands/hook/__tests__/list.test.js.map +1 -1
  178. package/dist/commands/hook/__tests__/logs.test.js +68 -40
  179. package/dist/commands/hook/__tests__/logs.test.js.map +1 -1
  180. package/dist/commands/hook/create.js +2 -6
  181. package/dist/commands/hook/create.js.map +1 -1
  182. package/dist/commands/hook/delete.js +5 -17
  183. package/dist/commands/hook/delete.js.map +1 -1
  184. package/dist/commands/hook/list.js +2 -8
  185. package/dist/commands/hook/list.js.map +1 -1
  186. package/dist/commands/init.d.ts +4 -0
  187. package/dist/commands/init.js +151 -18
  188. package/dist/commands/init.js.map +1 -1
  189. package/dist/commands/login.js +1 -1
  190. package/dist/commands/login.js.map +1 -1
  191. package/dist/commands/manifest/__tests__/extract.test.js +22 -13
  192. package/dist/commands/manifest/__tests__/extract.test.js.map +1 -1
  193. package/dist/commands/media/__tests__/create-aspect.test.js +41 -28
  194. package/dist/commands/media/__tests__/create-aspect.test.js.map +1 -1
  195. package/dist/commands/media/__tests__/delete-aspect.test.js +44 -35
  196. package/dist/commands/media/__tests__/delete-aspect.test.js.map +1 -1
  197. package/dist/commands/media/__tests__/deploy-aspect.test.js +67 -80
  198. package/dist/commands/media/__tests__/deploy-aspect.test.js.map +1 -1
  199. package/dist/commands/media/__tests__/export.test.js +365 -66
  200. package/dist/commands/media/__tests__/export.test.js.map +1 -1
  201. package/dist/commands/media/__tests__/import.test.js +171 -105
  202. package/dist/commands/media/__tests__/import.test.js.map +1 -1
  203. package/dist/commands/media/export.js +2 -2
  204. package/dist/commands/media/export.js.map +1 -1
  205. package/dist/commands/media/import.js +2 -2
  206. package/dist/commands/media/import.js.map +1 -1
  207. package/dist/commands/projects/__tests__/list.test.js +5 -4
  208. package/dist/commands/projects/__tests__/list.test.js.map +1 -1
  209. package/dist/commands/projects/list.js +2 -6
  210. package/dist/commands/projects/list.js.map +1 -1
  211. package/dist/commands/schema/__tests__/delete.test.js +396 -151
  212. package/dist/commands/schema/__tests__/delete.test.js.map +1 -1
  213. package/dist/commands/schema/__tests__/deploy.test.js +348 -0
  214. package/dist/commands/schema/__tests__/deploy.test.js.map +1 -0
  215. package/dist/commands/schema/__tests__/extract.test.js +19 -11
  216. package/dist/commands/schema/__tests__/extract.test.js.map +1 -1
  217. package/dist/commands/schema/__tests__/list.test.js +399 -0
  218. package/dist/commands/schema/__tests__/list.test.js.map +1 -0
  219. package/dist/commands/schema/__tests__/validate.test.js +27 -10
  220. package/dist/commands/schema/__tests__/validate.test.js.map +1 -1
  221. package/dist/commands/schema/delete.d.ts +1 -1
  222. package/dist/commands/schema/delete.js +20 -23
  223. package/dist/commands/schema/delete.js.map +1 -1
  224. package/dist/commands/schema/deploy.d.ts +16 -0
  225. package/dist/commands/schema/deploy.js +98 -0
  226. package/dist/commands/schema/deploy.js.map +1 -0
  227. package/dist/commands/schema/list.d.ts +15 -0
  228. package/dist/commands/schema/list.js +104 -0
  229. package/dist/commands/schema/list.js.map +1 -0
  230. package/dist/commands/telemetry/__tests__/disable.test.js +7 -5
  231. package/dist/commands/telemetry/__tests__/disable.test.js.map +1 -1
  232. package/dist/commands/telemetry/__tests__/enable.test.js +7 -5
  233. package/dist/commands/telemetry/__tests__/enable.test.js.map +1 -1
  234. package/dist/commands/telemetry/__tests__/status.test.js +7 -5
  235. package/dist/commands/telemetry/__tests__/status.test.js.map +1 -1
  236. package/dist/commands/tokens/__tests__/add.test.js +55 -40
  237. package/dist/commands/tokens/__tests__/add.test.js.map +1 -1
  238. package/dist/commands/tokens/__tests__/delete.test.js +72 -42
  239. package/dist/commands/tokens/__tests__/delete.test.js.map +1 -1
  240. package/dist/commands/tokens/__tests__/list.test.js +87 -60
  241. package/dist/commands/tokens/__tests__/list.test.js.map +1 -1
  242. package/dist/commands/tokens/add.js +3 -5
  243. package/dist/commands/tokens/add.js.map +1 -1
  244. package/dist/commands/users/__tests__/invite.test.js +100 -79
  245. package/dist/commands/users/__tests__/invite.test.js.map +1 -1
  246. package/dist/commands/users/__tests__/list.test.js +186 -180
  247. package/dist/commands/users/__tests__/list.test.js.map +1 -1
  248. package/dist/commands/users/invite.js +6 -17
  249. package/dist/commands/users/invite.js.map +1 -1
  250. package/dist/commands/users/list.js +4 -7
  251. package/dist/commands/users/list.js.map +1 -1
  252. package/dist/config/createCliConfig.d.ts +4 -4
  253. package/dist/services/backup.d.ts +8 -0
  254. package/dist/services/backup.js +19 -0
  255. package/dist/services/backup.js.map +1 -1
  256. package/dist/services/cors.d.ts +23 -0
  257. package/dist/services/cors.js +38 -0
  258. package/dist/services/cors.js.map +1 -0
  259. package/dist/services/graphql.d.ts +7 -0
  260. package/dist/services/graphql.js +11 -0
  261. package/dist/services/graphql.js.map +1 -1
  262. package/dist/services/hooks.d.ts +2 -0
  263. package/dist/services/hooks.js +19 -0
  264. package/dist/services/hooks.js.map +1 -1
  265. package/dist/services/organizations.d.ts +40 -0
  266. package/dist/services/organizations.js +41 -0
  267. package/dist/services/organizations.js.map +1 -0
  268. package/dist/services/projects.d.ts +31 -0
  269. package/dist/services/projects.js +71 -1
  270. package/dist/services/projects.js.map +1 -1
  271. package/dist/services/schemas.d.ts +4 -0
  272. package/dist/services/schemas.js +40 -0
  273. package/dist/services/schemas.js.map +1 -0
  274. package/dist/services/user.d.ts +10 -0
  275. package/dist/services/user.js +24 -0
  276. package/dist/services/user.js.map +1 -0
  277. package/dist/util/__tests__/getCliVersion.test.js +2 -2
  278. package/dist/util/__tests__/getCliVersion.test.js.map +1 -1
  279. package/dist/util/errorMessages.d.ts +1 -0
  280. package/dist/util/errorMessages.js +1 -0
  281. package/dist/util/errorMessages.js.map +1 -1
  282. package/dist/util/getCliVersion.js +1 -1
  283. package/dist/util/getCliVersion.js.map +1 -1
  284. package/dist/util/readPackageJson.d.ts +1 -15
  285. package/dist/util/readPackageJson.js +1 -1
  286. package/dist/util/readPackageJson.js.map +1 -1
  287. package/dist/util/uniqBy.d.ts +1 -0
  288. package/dist/util/uniqBy.js +14 -0
  289. package/dist/util/uniqBy.js.map +1 -0
  290. package/oclif.config.js +6 -1
  291. package/oclif.manifest.json +152 -158
  292. package/package.json +30 -31
  293. package/dist/actions/cors/constants.d.ts +0 -1
  294. package/dist/actions/cors/constants.js +0 -3
  295. package/dist/actions/cors/constants.js.map +0 -1
  296. package/dist/actions/cors/types.d.ts +0 -9
  297. package/dist/actions/cors/types.js +0 -3
  298. package/dist/actions/cors/types.js.map +0 -1
  299. package/dist/actions/migration/getMigrationRootDirectory.d.ts +0 -2
  300. package/dist/actions/migration/getMigrationRootDirectory.js +0 -14
  301. package/dist/actions/migration/getMigrationRootDirectory.js.map +0 -1
  302. package/dist/actions/migration/resolveMigrations.d.ts +0 -19
  303. package/dist/actions/migration/resolveMigrations.js +0 -43
  304. package/dist/actions/migration/resolveMigrations.js.map +0 -1
  305. package/dist/actions/migration/templates/__tests__/minimalAdvanced.test.js +0 -65
  306. package/dist/actions/migration/templates/__tests__/minimalAdvanced.test.js.map +0 -1
  307. package/dist/actions/migration/templates/__tests__/minimalSimple.test.js +0 -145
  308. package/dist/actions/migration/templates/__tests__/minimalSimple.test.js.map +0 -1
  309. package/dist/actions/migration/templates/__tests__/renameField.test.js +0 -63
  310. package/dist/actions/migration/templates/__tests__/renameField.test.js.map +0 -1
  311. package/dist/actions/migration/templates/__tests__/renameType.test.js +0 -61
  312. package/dist/actions/migration/templates/__tests__/renameType.test.js.map +0 -1
  313. package/dist/actions/migration/templates/__tests__/stringToPTE.test.js +0 -87
  314. package/dist/actions/migration/templates/__tests__/stringToPTE.test.js.map +0 -1
  315. package/dist/actions/migration/templates/index.d.ts +0 -5
  316. package/dist/actions/migration/templates/index.js +0 -7
  317. package/dist/actions/migration/templates/index.js.map +0 -1
  318. package/dist/actions/migration/templates/minimalAdvanced.d.ts +0 -4
  319. package/dist/actions/migration/templates/minimalAdvanced.js +0 -21
  320. package/dist/actions/migration/templates/minimalAdvanced.js.map +0 -1
  321. package/dist/actions/migration/templates/minimalSimple.d.ts +0 -4
  322. package/dist/actions/migration/templates/minimalSimple.js +0 -61
  323. package/dist/actions/migration/templates/minimalSimple.js.map +0 -1
  324. package/dist/actions/migration/templates/renameField.d.ts +0 -4
  325. package/dist/actions/migration/templates/renameField.js +0 -20
  326. package/dist/actions/migration/templates/renameField.js.map +0 -1
  327. package/dist/actions/migration/templates/renameType.d.ts +0 -4
  328. package/dist/actions/migration/templates/renameType.js +0 -19
  329. package/dist/actions/migration/templates/renameType.js.map +0 -1
  330. package/dist/actions/migration/templates/stringToPTE.d.ts +0 -4
  331. package/dist/actions/migration/templates/stringToPTE.js +0 -32
  332. package/dist/actions/migration/templates/stringToPTE.js.map +0 -1
  333. package/dist/actions/schema/__tests__/deleteSchemaAction.test.js +0 -294
  334. package/dist/actions/schema/__tests__/deleteSchemaAction.test.js.map +0 -1
  335. package/dist/actions/schema/schemaStoreConstants.d.ts +0 -1
  336. package/dist/actions/schema/schemaStoreConstants.js +0 -4
  337. package/dist/actions/schema/schemaStoreConstants.js.map +0 -1
  338. package/dist/actions/schema/utils/schemaActionHelpers.d.ts +0 -1
  339. package/dist/actions/schema/utils/schemaActionHelpers.js +0 -5
  340. package/dist/actions/schema/utils/schemaActionHelpers.js.map +0 -1
  341. package/dist/actions/schema/utils/schemaApiClient.d.ts +0 -6
  342. package/dist/actions/schema/utils/schemaApiClient.js +0 -17
  343. package/dist/actions/schema/utils/schemaApiClient.js.map +0 -1
  344. package/dist/actions/users/apiVersion.d.ts +0 -6
  345. package/dist/actions/users/apiVersion.js +0 -7
  346. package/dist/actions/users/apiVersion.js.map +0 -1
  347. package/dist/commands/__tests__/init.test.js +0 -411
  348. package/dist/commands/__tests__/init.test.js.map +0 -1
  349. package/dist/commands/migration/__tests__/create.test.js +0 -296
  350. package/dist/commands/migration/__tests__/create.test.js.map +0 -1
  351. package/dist/commands/migration/__tests__/list.test.js +0 -166
  352. package/dist/commands/migration/__tests__/list.test.js.map +0 -1
  353. package/dist/commands/migration/__tests__/run.test.js +0 -481
  354. package/dist/commands/migration/__tests__/run.test.js.map +0 -1
  355. package/dist/commands/migration/create.d.ts +0 -17
  356. package/dist/commands/migration/create.js +0 -143
  357. package/dist/commands/migration/create.js.map +0 -1
  358. package/dist/commands/migration/list.d.ts +0 -9
  359. package/dist/commands/migration/list.js +0 -61
  360. package/dist/commands/migration/list.js.map +0 -1
  361. package/dist/commands/migration/run.d.ts +0 -26
  362. package/dist/commands/migration/run.js +0 -271
  363. package/dist/commands/migration/run.js.map +0 -1
  364. package/dist/util/migration/constants.d.ts +0 -3
  365. package/dist/util/migration/constants.js +0 -10
  366. package/dist/util/migration/constants.js.map +0 -1
  367. package/dist/util/migration/ensureApiVersionFormat.d.ts +0 -9
  368. package/dist/util/migration/ensureApiVersionFormat.js +0 -16
  369. package/dist/util/migration/ensureApiVersionFormat.js.map +0 -1
  370. package/dist/util/migration/prettyMutationFormatter.d.ts +0 -8
  371. package/dist/util/migration/prettyMutationFormatter.js +0 -141
  372. package/dist/util/migration/prettyMutationFormatter.js.map +0 -1
  373. package/dist/utils/migration/resolveMigrationScript.d.ts +0 -44
  374. package/dist/utils/migration/resolveMigrationScript.js +0 -74
  375. package/dist/utils/migration/resolveMigrationScript.js.map +0 -1
  376. /package/dist/actions/auth/login/{index.d.ts → login.d.ts} +0 -0
@@ -1,28 +1,31 @@
1
1
  import { runCommand } from '@oclif/test';
2
2
  import { select } from '@sanity/cli-core/ux';
3
- import { testCommand } from '@sanity/cli-test';
3
+ import { createTestClient, mockApi, testCommand } from '@sanity/cli-test';
4
+ import nock from 'nock';
4
5
  import { of, throwError } from 'rxjs';
5
6
  import { afterEach, describe, expect, test, vi } from 'vitest';
6
- import { getCliConfig } from '../../../../../cli-core/src/config/cli/getCliConfig.js';
7
- import * as datasetsService from '../../../services/datasets.js';
7
+ import { DATASET_API_VERSION, followCopyJobProgress } from '../../../services/datasets.js';
8
8
  import { CopyDatasetCommand } from '../copy.js';
9
- vi.mock('../../../../../cli-core/src/config/findProjectRoot.js', ()=>({
10
- findProjectRoot: vi.fn().mockResolvedValue({
11
- directory: '/test/path',
12
- root: '/test/path',
13
- type: 'studio'
14
- })
15
- }));
16
- vi.mock('../../../../../cli-core/src/config/cli/getCliConfig.js', ()=>({
17
- getCliConfig: vi.fn().mockResolvedValue({
18
- api: {
19
- projectId: 'test-project'
20
- }
9
+ const mockListDatasets = vi.hoisted(()=>vi.fn());
10
+ const testProjectId = vi.hoisted(()=>'test-project');
11
+ const testToken = vi.hoisted(()=>'test-token');
12
+ vi.mock('@sanity/cli-core', async (importOriginal)=>{
13
+ const actual = await importOriginal();
14
+ const testClient = createTestClient({
15
+ apiVersion: 'v2025-09-16',
16
+ projectId: testProjectId,
17
+ token: testToken
18
+ });
19
+ return {
20
+ ...actual,
21
+ getProjectCliClient: vi.fn().mockResolvedValue({
22
+ datasets: {
23
+ list: mockListDatasets
24
+ },
25
+ request: testClient.request
21
26
  })
22
- }));
23
- vi.mock('../../../../../cli-core/src/services/getCliToken.js', ()=>({
24
- getCliToken: vi.fn().mockResolvedValue('test-token')
25
- }));
27
+ };
28
+ });
26
29
  vi.mock('@sanity/cli-core/ux', async ()=>{
27
30
  const actual = await vi.importActual('@sanity/cli-core/ux');
28
31
  return {
@@ -31,19 +34,29 @@ vi.mock('@sanity/cli-core/ux', async ()=>{
31
34
  select: vi.fn()
32
35
  };
33
36
  });
34
- vi.mock('../../../services/datasets.js', ()=>({
35
- copyDataset: vi.fn(),
36
- followCopyJobProgress: vi.fn(),
37
- listDatasetCopyJobs: vi.fn(),
38
- listDatasets: vi.fn()
39
- }));
40
- const mockGetCliConfig = vi.mocked(getCliConfig);
37
+ vi.mock('../../../services/datasets.js', async (importOriginal)=>{
38
+ const actual = await importOriginal();
39
+ return {
40
+ ...actual,
41
+ // Keep only followCopyJobProgress mocked since it uses EventSource streaming
42
+ followCopyJobProgress: vi.fn()
43
+ };
44
+ });
45
+ const defaultMocks = {
46
+ cliConfig: {
47
+ api: {
48
+ projectId: testProjectId
49
+ }
50
+ },
51
+ projectRoot: {
52
+ directory: '/test/path',
53
+ path: '/test/path/sanity.config.ts',
54
+ type: 'studio'
55
+ },
56
+ token: testToken
57
+ };
41
58
  const mockSelect = vi.mocked(select);
42
- const mockCopyDataset = vi.mocked(datasetsService.copyDataset);
43
- const mockFollowCopyJobProgress = vi.mocked(datasetsService.followCopyJobProgress);
44
- const mockListDatasetCopyJobs = vi.mocked(datasetsService.listDatasetCopyJobs);
45
- const mockListDatasets = vi.mocked(datasetsService.listDatasets);
46
- // Helper to create mock datasets
59
+ const mockFollowCopyJobProgress = vi.mocked(followCopyJobProgress);
47
60
  function createMockDataset(name) {
48
61
  return {
49
62
  aclMode: 'public',
@@ -59,6 +72,9 @@ function createMockDataset(name) {
59
72
  describe('#dataset:copy', ()=>{
60
73
  afterEach(()=>{
61
74
  vi.clearAllMocks();
75
+ const pending = nock.pendingMocks();
76
+ nock.cleanAll();
77
+ expect(pending, 'pending mocks').toEqual([]);
62
78
  });
63
79
  test('help works', async ()=>{
64
80
  const { stdout } = await runCommand([
@@ -126,7 +142,12 @@ describe('#dataset:copy', ()=>{
126
142
  });
127
143
  describe('list mode', ()=>{
128
144
  test('lists copy jobs successfully', async ()=>{
129
- mockListDatasetCopyJobs.mockResolvedValue([
145
+ mockApi({
146
+ apiHost: `https://${testProjectId}.api.sanity.io`,
147
+ apiVersion: DATASET_API_VERSION,
148
+ method: 'get',
149
+ uri: `/projects/${testProjectId}/datasets/copy`
150
+ }).reply(200, [
130
151
  {
131
152
  createdAt: '2023-01-01T00:00:00Z',
132
153
  id: 'job-1',
@@ -148,11 +169,8 @@ describe('#dataset:copy', ()=>{
148
169
  ]);
149
170
  const { stdout } = await testCommand(CopyDatasetCommand, [
150
171
  '--list'
151
- ]);
152
- expect(mockListDatasetCopyJobs).toHaveBeenCalledWith({
153
- limit: undefined,
154
- offset: undefined,
155
- projectId: 'test-project'
172
+ ], {
173
+ mocks: defaultMocks
156
174
  });
157
175
  expect(stdout).toContain('Dataset copy jobs');
158
176
  expect(stdout).toContain('job-1');
@@ -161,33 +179,79 @@ describe('#dataset:copy', ()=>{
161
179
  expect(stdout).toContain('staging');
162
180
  });
163
181
  test('lists copy jobs with offset and limit', async ()=>{
164
- mockListDatasetCopyJobs.mockResolvedValue([]);
165
- await testCommand(CopyDatasetCommand, [
182
+ mockApi({
183
+ apiHost: `https://${testProjectId}.api.sanity.io`,
184
+ apiVersion: DATASET_API_VERSION,
185
+ method: 'get',
186
+ query: {
187
+ limit: '10',
188
+ offset: '2'
189
+ },
190
+ uri: `/projects/${testProjectId}/datasets/copy`
191
+ }).reply(200, [
192
+ {
193
+ createdAt: '2023-01-01T00:00:00Z',
194
+ id: 'job-2',
195
+ sourceDataset: 'production',
196
+ state: 'completed',
197
+ targetDataset: 'backup',
198
+ updatedAt: '2023-01-01T00:05:00Z',
199
+ withHistory: true
200
+ },
201
+ {
202
+ createdAt: '2023-01-02T00:00:00Z',
203
+ id: 'job-3',
204
+ sourceDataset: 'staging',
205
+ state: 'failed',
206
+ targetDataset: 'test',
207
+ updatedAt: '2023-01-02T00:02:00Z',
208
+ withHistory: false
209
+ }
210
+ ]);
211
+ const { stdout } = await testCommand(CopyDatasetCommand, [
166
212
  '--list',
167
213
  '--offset',
168
214
  '2',
169
215
  '--limit',
170
216
  '10'
171
- ]);
172
- expect(mockListDatasetCopyJobs).toHaveBeenCalledWith({
173
- limit: 10,
174
- offset: 2,
175
- projectId: 'test-project'
217
+ ], {
218
+ mocks: defaultMocks
176
219
  });
220
+ expect(stdout).toContain('job-2');
221
+ expect(stdout).toContain('job-3');
222
+ expect(stdout).toContain('production');
223
+ expect(stdout).toContain('staging');
177
224
  });
178
225
  test('shows message when no copy jobs exist', async ()=>{
179
- mockListDatasetCopyJobs.mockResolvedValue([]);
226
+ mockApi({
227
+ apiHost: `https://${testProjectId}.api.sanity.io`,
228
+ apiVersion: DATASET_API_VERSION,
229
+ method: 'get',
230
+ uri: `/projects/${testProjectId}/datasets/copy`
231
+ }).reply(200, []);
180
232
  const { stdout } = await testCommand(CopyDatasetCommand, [
181
233
  '--list'
182
- ]);
234
+ ], {
235
+ mocks: defaultMocks
236
+ });
183
237
  expect(stdout).toContain("This project doesn't have any dataset copy jobs");
184
238
  });
185
239
  test('handles errors when listing copy jobs', async ()=>{
186
- mockListDatasetCopyJobs.mockRejectedValue(new Error('API Error'));
240
+ mockApi({
241
+ apiHost: `https://${testProjectId}.api.sanity.io`,
242
+ apiVersion: DATASET_API_VERSION,
243
+ method: 'get',
244
+ uri: `/projects/${testProjectId}/datasets/copy`
245
+ }).reply(500, {
246
+ error: 'API Error',
247
+ message: 'API Error'
248
+ });
187
249
  const { error } = await testCommand(CopyDatasetCommand, [
188
250
  '--list'
189
- ]);
190
- expect(error?.message).toContain('Failed to list dataset copy jobs: API Error');
251
+ ], {
252
+ mocks: defaultMocks
253
+ });
254
+ expect(error?.message).toContain('Failed to list dataset copy jobs');
191
255
  expect(error?.oclif?.exit).toBe(1);
192
256
  });
193
257
  });
@@ -209,7 +273,9 @@ describe('#dataset:copy', ()=>{
209
273
  const { stdout } = await testCommand(CopyDatasetCommand, [
210
274
  '--attach',
211
275
  'job-123'
212
- ]);
276
+ ], {
277
+ mocks: defaultMocks
278
+ });
213
279
  expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({
214
280
  jobId: 'job-123',
215
281
  projectId: 'test-project'
@@ -221,7 +287,9 @@ describe('#dataset:copy', ()=>{
221
287
  const { error } = await testCommand(CopyDatasetCommand, [
222
288
  '--attach',
223
289
  'job-123'
224
- ]);
290
+ ], {
291
+ mocks: defaultMocks
292
+ });
225
293
  expect(error?.message).toContain('Failed to attach to copy job: Connection lost');
226
294
  expect(error?.oclif?.exit).toBe(1);
227
295
  });
@@ -229,7 +297,9 @@ describe('#dataset:copy', ()=>{
229
297
  const { error } = await testCommand(CopyDatasetCommand, [
230
298
  '--attach',
231
299
  ' '
232
- ]);
300
+ ], {
301
+ mocks: defaultMocks
302
+ });
233
303
  expect(error?.message).toContain('Please supply a valid jobId');
234
304
  expect(error?.oclif?.exit).toBe(1);
235
305
  });
@@ -238,7 +308,9 @@ describe('#dataset:copy', ()=>{
238
308
  const { error } = await testCommand(CopyDatasetCommand, [
239
309
  '--attach',
240
310
  'job-123'
241
- ]);
311
+ ], {
312
+ mocks: defaultMocks
313
+ });
242
314
  expect(error?.message).toContain('Invalid JSON received from server');
243
315
  expect(error?.oclif?.exit).toBe(1);
244
316
  });
@@ -255,7 +327,9 @@ describe('#dataset:copy', ()=>{
255
327
  const { stdout } = await testCommand(CopyDatasetCommand, [
256
328
  '--attach',
257
329
  'job-123'
258
- ]);
330
+ ], {
331
+ mocks: defaultMocks
332
+ });
259
333
  expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({
260
334
  jobId: 'job-123',
261
335
  projectId: 'test-project'
@@ -267,7 +341,9 @@ describe('#dataset:copy', ()=>{
267
341
  const { error } = await testCommand(CopyDatasetCommand, [
268
342
  '--attach',
269
343
  'job-123'
270
- ]);
344
+ ], {
345
+ mocks: defaultMocks
346
+ });
271
347
  expect(error?.message).toContain('Copy job failed');
272
348
  expect(error?.oclif?.exit).toBe(1);
273
349
  });
@@ -278,7 +354,12 @@ describe('#dataset:copy', ()=>{
278
354
  createMockDataset('production'),
279
355
  createMockDataset('staging')
280
356
  ]);
281
- mockCopyDataset.mockResolvedValue({
357
+ mockApi({
358
+ apiHost: `https://${testProjectId}.api.sanity.io`,
359
+ apiVersion: DATASET_API_VERSION,
360
+ method: 'put',
361
+ uri: `/datasets/production/copy`
362
+ }).reply(200, {
282
363
  jobId: 'job-456'
283
364
  });
284
365
  mockFollowCopyJobProgress.mockReturnValue(of({
@@ -288,12 +369,8 @@ describe('#dataset:copy', ()=>{
288
369
  const { stdout } = await testCommand(CopyDatasetCommand, [
289
370
  'production',
290
371
  'backup'
291
- ]);
292
- expect(mockCopyDataset).toHaveBeenCalledWith({
293
- projectId: 'test-project',
294
- skipHistory: false,
295
- sourceDataset: 'production',
296
- targetDataset: 'backup'
372
+ ], {
373
+ mocks: defaultMocks
297
374
  });
298
375
  expect(stdout).toContain('Copying dataset production to backup');
299
376
  expect(stdout).toContain('Job job-456 started');
@@ -306,14 +383,21 @@ describe('#dataset:copy', ()=>{
306
383
  ]);
307
384
  mockSelect.mockResolvedValueOnce('production');
308
385
  mockSelect.mockResolvedValueOnce('backup');
309
- mockCopyDataset.mockResolvedValue({
386
+ mockApi({
387
+ apiHost: `https://${testProjectId}.api.sanity.io`,
388
+ apiVersion: DATASET_API_VERSION,
389
+ method: 'put',
390
+ uri: `/datasets/production/copy`
391
+ }).reply(200, {
310
392
  jobId: 'job-789'
311
393
  });
312
394
  mockFollowCopyJobProgress.mockReturnValue(of({
313
395
  progress: 100,
314
396
  type: 'progress'
315
397
  }));
316
- await testCommand(CopyDatasetCommand, []);
398
+ await testCommand(CopyDatasetCommand, [], {
399
+ mocks: defaultMocks
400
+ });
317
401
  expect(mockSelect).toHaveBeenCalledWith({
318
402
  choices: expect.arrayContaining([
319
403
  expect.objectContaining({
@@ -382,7 +466,9 @@ describe('#dataset:copy', ()=>{
382
466
  }
383
467
  ])('errors when $description', async ({ args, expectedError, setupMocks })=>{
384
468
  setupMocks();
385
- const { error } = await testCommand(CopyDatasetCommand, args);
469
+ const { error } = await testCommand(CopyDatasetCommand, args, {
470
+ mocks: defaultMocks
471
+ });
386
472
  expect(error?.message).toContain(expectedError);
387
473
  expect(error?.oclif?.exit).toBe(1);
388
474
  });
@@ -391,7 +477,12 @@ describe('#dataset:copy', ()=>{
391
477
  createMockDataset('production'),
392
478
  createMockDataset('staging')
393
479
  ]);
394
- mockCopyDataset.mockResolvedValue({
480
+ mockApi({
481
+ apiHost: `https://${testProjectId}.api.sanity.io`,
482
+ apiVersion: DATASET_API_VERSION,
483
+ method: 'put',
484
+ uri: `/datasets/production/copy`
485
+ }).reply(200, {
395
486
  jobId: 'job-skip'
396
487
  });
397
488
  mockFollowCopyJobProgress.mockReturnValue(of({
@@ -402,12 +493,8 @@ describe('#dataset:copy', ()=>{
402
493
  'production',
403
494
  'backup',
404
495
  '--skip-history'
405
- ]);
406
- expect(mockCopyDataset).toHaveBeenCalledWith({
407
- projectId: 'test-project',
408
- skipHistory: true,
409
- sourceDataset: 'production',
410
- targetDataset: 'backup'
496
+ ], {
497
+ mocks: defaultMocks
411
498
  });
412
499
  });
413
500
  test('copies dataset with detach flag (does not wait for completion)', async ()=>{
@@ -415,19 +502,20 @@ describe('#dataset:copy', ()=>{
415
502
  createMockDataset('production'),
416
503
  createMockDataset('staging')
417
504
  ]);
418
- mockCopyDataset.mockResolvedValue({
505
+ mockApi({
506
+ apiHost: `https://${testProjectId}.api.sanity.io`,
507
+ apiVersion: DATASET_API_VERSION,
508
+ method: 'put',
509
+ uri: `/datasets/production/copy`
510
+ }).reply(200, {
419
511
  jobId: 'job-detach'
420
512
  });
421
513
  const { stdout } = await testCommand(CopyDatasetCommand, [
422
514
  'production',
423
515
  'backup',
424
516
  '--detach'
425
- ]);
426
- expect(mockCopyDataset).toHaveBeenCalledWith({
427
- projectId: 'test-project',
428
- skipHistory: false,
429
- sourceDataset: 'production',
430
- targetDataset: 'backup'
517
+ ], {
518
+ mocks: defaultMocks
431
519
  });
432
520
  expect(stdout).toContain('Job job-detach started');
433
521
  expect(stdout).not.toContain('Job job-detach completed');
@@ -438,12 +526,22 @@ describe('#dataset:copy', ()=>{
438
526
  createMockDataset('production'),
439
527
  createMockDataset('staging')
440
528
  ]);
441
- mockCopyDataset.mockRejectedValue(new Error('Insufficient permissions'));
529
+ mockApi({
530
+ apiHost: `https://${testProjectId}.api.sanity.io`,
531
+ apiVersion: DATASET_API_VERSION,
532
+ method: 'put',
533
+ uri: `/datasets/production/copy`
534
+ }).reply(500, {
535
+ error: 'Insufficient permissions',
536
+ message: 'Insufficient permissions'
537
+ });
442
538
  const { error } = await testCommand(CopyDatasetCommand, [
443
539
  'production',
444
540
  'backup'
445
- ]);
446
- expect(error?.message).toContain('Dataset copying failed: Insufficient permissions');
541
+ ], {
542
+ mocks: defaultMocks
543
+ });
544
+ expect(error?.message).toContain('Dataset copying failed');
447
545
  expect(error?.oclif?.exit).toBe(1);
448
546
  });
449
547
  test('handles fetch datasets error', async ()=>{
@@ -451,7 +549,9 @@ describe('#dataset:copy', ()=>{
451
549
  const { error } = await testCommand(CopyDatasetCommand, [
452
550
  'production',
453
551
  'backup'
454
- ]);
552
+ ], {
553
+ mocks: defaultMocks
554
+ });
455
555
  expect(error?.message).toContain('Failed to fetch datasets: Network error');
456
556
  expect(error?.oclif?.exit).toBe(1);
457
557
  });
@@ -482,7 +582,9 @@ describe('#dataset:copy', ()=>{
482
582
  ]
483
583
  }
484
584
  ])('errors when using mutually exclusive flags: $desc', async ({ flags })=>{
485
- const { error } = await testCommand(CopyDatasetCommand, flags);
585
+ const { error } = await testCommand(CopyDatasetCommand, flags, {
586
+ mocks: defaultMocks
587
+ });
486
588
  expect(error?.message).toContain('cannot also be provided when using');
487
589
  expect(error?.oclif?.exit).toBe(2);
488
590
  });
@@ -499,19 +601,25 @@ describe('#dataset:copy', ()=>{
499
601
  const { error } = await testCommand(CopyDatasetCommand, [
500
602
  flag,
501
603
  value
502
- ]);
604
+ ], {
605
+ mocks: defaultMocks
606
+ });
503
607
  expect(error?.message).toContain('--list');
504
608
  expect(error?.oclif?.exit).toBe(2);
505
609
  });
506
610
  });
507
611
  test('errors when no project ID is found', async ()=>{
508
- mockGetCliConfig.mockResolvedValueOnce({
509
- api: undefined
510
- });
511
612
  const { error } = await testCommand(CopyDatasetCommand, [
512
613
  'production',
513
614
  'backup'
514
- ]);
615
+ ], {
616
+ mocks: {
617
+ ...defaultMocks,
618
+ cliConfig: {
619
+ api: undefined
620
+ }
621
+ }
622
+ });
515
623
  expect(error?.message).toContain('sanity.cli.ts does not contain a project identifier');
516
624
  expect(error?.oclif?.exit).toBe(1);
517
625
  });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../src/commands/dataset/__tests__/copy.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {select} from '@sanity/cli-core/ux'\nimport {testCommand} from '@sanity/cli-test'\nimport {of, throwError} from 'rxjs'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {getCliConfig} from '../../../../../cli-core/src/config/cli/getCliConfig.js'\nimport * as datasetsService from '../../../services/datasets.js'\nimport {CopyDatasetCommand} from '../copy.js'\n\nvi.mock('../../../../../cli-core/src/config/findProjectRoot.js', () => ({\n findProjectRoot: vi.fn().mockResolvedValue({\n directory: '/test/path',\n root: '/test/path',\n type: 'studio',\n }),\n}))\n\nvi.mock('../../../../../cli-core/src/config/cli/getCliConfig.js', () => ({\n getCliConfig: vi.fn().mockResolvedValue({\n api: {\n projectId: 'test-project',\n },\n }),\n}))\n\nvi.mock('../../../../../cli-core/src/services/getCliToken.js', () => ({\n getCliToken: vi.fn().mockResolvedValue('test-token'),\n}))\n\nvi.mock('@sanity/cli-core/ux', async () => {\n const actual = await vi.importActual<typeof import('@sanity/cli-core/ux')>('@sanity/cli-core/ux')\n return {\n ...actual,\n input: vi.fn(),\n select: vi.fn(),\n }\n})\n\nvi.mock('../../../services/datasets.js', () => ({\n copyDataset: vi.fn(),\n followCopyJobProgress: vi.fn(),\n listDatasetCopyJobs: vi.fn(),\n listDatasets: vi.fn(),\n}))\n\nconst mockGetCliConfig = vi.mocked(getCliConfig)\nconst mockSelect = vi.mocked(select)\nconst mockCopyDataset = vi.mocked(datasetsService.copyDataset)\nconst mockFollowCopyJobProgress = vi.mocked(datasetsService.followCopyJobProgress)\nconst mockListDatasetCopyJobs = vi.mocked(datasetsService.listDatasetCopyJobs)\nconst mockListDatasets = vi.mocked(datasetsService.listDatasets)\n\n// Helper to create mock datasets\nfunction createMockDataset(name: string) {\n return {\n aclMode: 'public' as const,\n addonFor: null,\n createdAt: '2023-01-01T00:00:00Z',\n createdByUserId: 'test-user',\n datasetProfile: 'default',\n features: [],\n name,\n tags: [],\n }\n}\n\ndescribe('#dataset:copy', () => {\n afterEach(() => {\n vi.clearAllMocks()\n })\n\n test('help works', async () => {\n const {stdout} = await runCommand(['dataset copy', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Manages dataset copying, including starting a new copy job, listing copy jobs and following the progress of a running copy job\n\n USAGE\n $ sanity dataset copy [SOURCE] [TARGET] [--attach <value> | --list |\n --detach | --skip-history] [--limit <value> ] [--offset <value> ]\n\n ARGUMENTS\n [SOURCE] Name of the dataset to copy from\n [TARGET] Name of the dataset to copy to\n\n FLAGS\n --attach=<value> Attach to the running copy process to show progress\n --detach Start the copy without waiting for it to finish\n --limit=<value> Maximum number of jobs returned (default 10, max 1000)\n --list Lists all dataset copy jobs\n --offset=<value> Start position in the list of jobs (default 0)\n --skip-history Don't preserve document history on copy\n\n DESCRIPTION\n Manages dataset copying, including starting a new copy job, listing copy jobs\n and following the progress of a running copy job\n\n EXAMPLES\n Interactively copy a dataset\n\n $ sanity dataset copy\n\n Copy from source-dataset (prompts for target)\n\n $ sanity dataset copy source-dataset\n\n Copy from source-dataset to target-dataset\n\n $ sanity dataset copy source-dataset target-dataset\n\n Copy without preserving document history (faster for large datasets)\n\n $ sanity dataset copy --skip-history source target\n\n Start copy job without waiting for completion\n\n $ sanity dataset copy --detach source target\n\n Attach to a running copy job to follow progress\n\n $ sanity dataset copy --attach <job-id>\n\n List all dataset copy jobs\n\n $ sanity dataset copy --list\n\n List copy jobs with pagination\n\n $ sanity dataset copy --list --offset 2 --limit 10\n\n \"\n `)\n })\n\n describe('list mode', () => {\n test('lists copy jobs successfully', async () => {\n mockListDatasetCopyJobs.mockResolvedValue([\n {\n createdAt: '2023-01-01T00:00:00Z',\n id: 'job-1',\n sourceDataset: 'production',\n state: 'completed',\n targetDataset: 'backup',\n updatedAt: '2023-01-01T00:05:00Z',\n withHistory: true,\n },\n {\n createdAt: '2023-01-02T00:00:00Z',\n id: 'job-2',\n sourceDataset: 'staging',\n state: 'failed',\n targetDataset: 'test',\n updatedAt: '2023-01-02T00:02:00Z',\n withHistory: false,\n },\n ])\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--list'])\n\n expect(mockListDatasetCopyJobs).toHaveBeenCalledWith({\n limit: undefined,\n offset: undefined,\n projectId: 'test-project',\n })\n expect(stdout).toContain('Dataset copy jobs')\n expect(stdout).toContain('job-1')\n expect(stdout).toContain('job-2')\n expect(stdout).toContain('production')\n expect(stdout).toContain('staging')\n })\n\n test('lists copy jobs with offset and limit', async () => {\n mockListDatasetCopyJobs.mockResolvedValue([])\n\n await testCommand(CopyDatasetCommand, ['--list', '--offset', '2', '--limit', '10'])\n\n expect(mockListDatasetCopyJobs).toHaveBeenCalledWith({\n limit: 10,\n offset: 2,\n projectId: 'test-project',\n })\n })\n\n test('shows message when no copy jobs exist', async () => {\n mockListDatasetCopyJobs.mockResolvedValue([])\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--list'])\n\n expect(stdout).toContain(\"This project doesn't have any dataset copy jobs\")\n })\n\n test('handles errors when listing copy jobs', async () => {\n mockListDatasetCopyJobs.mockRejectedValue(new Error('API Error'))\n\n const {error} = await testCommand(CopyDatasetCommand, ['--list'])\n\n expect(error?.message).toContain('Failed to list dataset copy jobs: API Error')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('attach mode', () => {\n test('attaches to running job and shows progress', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n of(\n {progress: 25, type: 'progress'},\n {progress: 50, type: 'progress'},\n {progress: 75, type: 'progress'},\n {progress: 100, type: 'progress'},\n ),\n )\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'])\n\n expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({\n jobId: 'job-123',\n projectId: 'test-project',\n })\n expect(stdout).toContain('Job job-123 completed')\n })\n\n test('handles progress tracking errors', async () => {\n mockFollowCopyJobProgress.mockReturnValue(throwError(() => new Error('Connection lost')))\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'])\n\n expect(error?.message).toContain('Failed to attach to copy job: Connection lost')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('rejects whitespace-only jobId', async () => {\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', ' '])\n\n expect(error?.message).toContain('Please supply a valid jobId')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles JSON parse errors from EventSource', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n throwError(() => new Error('Invalid JSON received from server: Unexpected token')),\n )\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'])\n\n expect(error?.message).toContain('Invalid JSON received from server')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles EventSource reconnection', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n of({progress: 25, type: 'progress'}, {type: 'reconnect'}, {progress: 50, type: 'progress'}),\n )\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'])\n\n expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({\n jobId: 'job-123',\n projectId: 'test-project',\n })\n expect(stdout).toContain('Job job-123 completed')\n })\n\n test('handles channel_error from EventSource', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n throwError(() => new Error('Copy job failed: Channel closed unexpectedly')),\n )\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'])\n\n expect(error?.message).toContain('Copy job failed')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('copy mode', () => {\n test('copies dataset with provided arguments', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockCopyDataset.mockResolvedValue({jobId: 'job-456'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['production', 'backup'])\n\n expect(mockCopyDataset).toHaveBeenCalledWith({\n projectId: 'test-project',\n skipHistory: false,\n sourceDataset: 'production',\n targetDataset: 'backup',\n })\n expect(stdout).toContain('Copying dataset production to backup')\n expect(stdout).toContain('Job job-456 started')\n expect(stdout).toContain('Job job-456 completed')\n })\n\n test('prompts for source dataset when not provided', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockSelect.mockResolvedValueOnce('production')\n mockSelect.mockResolvedValueOnce('backup')\n mockCopyDataset.mockResolvedValue({jobId: 'job-789'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n await testCommand(CopyDatasetCommand, [])\n\n expect(mockSelect).toHaveBeenCalledWith({\n choices: expect.arrayContaining([\n expect.objectContaining({value: 'production'}),\n expect.objectContaining({value: 'staging'}),\n ]),\n message: 'Select the dataset name:',\n })\n })\n\n test.each([\n {\n args: ['Invalid-Dataset', 'backup'],\n description: 'source dataset name is invalid',\n expectedError: 'must be all lowercase',\n setupMocks: () => {\n // No additional mocks needed - validation happens before dataset fetch\n },\n },\n {\n args: ['nonexistent', 'backup'],\n description: 'source dataset does not exist',\n expectedError: 'Source dataset \"nonexistent\" doesn\\'t exist',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n {\n args: ['production', 'Invalid-Dataset'],\n description: 'target dataset name is invalid',\n expectedError: 'must be all lowercase',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n {\n args: ['production', 'staging'],\n description: 'target dataset already exists',\n expectedError: 'Target dataset \"staging\" already exists',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n ])('errors when $description', async ({args, expectedError, setupMocks}) => {\n setupMocks()\n\n const {error} = await testCommand(CopyDatasetCommand, args)\n\n expect(error?.message).toContain(expectedError)\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('copies dataset with skip-history flag', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockCopyDataset.mockResolvedValue({jobId: 'job-skip'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n await testCommand(CopyDatasetCommand, ['production', 'backup', '--skip-history'])\n\n expect(mockCopyDataset).toHaveBeenCalledWith({\n projectId: 'test-project',\n skipHistory: true,\n sourceDataset: 'production',\n targetDataset: 'backup',\n })\n })\n\n test('copies dataset with detach flag (does not wait for completion)', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockCopyDataset.mockResolvedValue({jobId: 'job-detach'})\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['production', 'backup', '--detach'])\n\n expect(mockCopyDataset).toHaveBeenCalledWith({\n projectId: 'test-project',\n skipHistory: false,\n sourceDataset: 'production',\n targetDataset: 'backup',\n })\n expect(stdout).toContain('Job job-detach started')\n expect(stdout).not.toContain('Job job-detach completed')\n expect(mockFollowCopyJobProgress).not.toHaveBeenCalled()\n })\n\n test('handles copy dataset errors', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockCopyDataset.mockRejectedValue(new Error('Insufficient permissions'))\n\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'])\n\n expect(error?.message).toContain('Dataset copying failed: Insufficient permissions')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles fetch datasets error', async () => {\n mockListDatasets.mockRejectedValue(new Error('Network error'))\n\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'])\n\n expect(error?.message).toContain('Failed to fetch datasets: Network error')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('flag validation', () => {\n test.each([\n {desc: '--list with --attach', flags: ['--list', '--attach', 'job-123']},\n {desc: '--list with --detach', flags: ['--list', '--detach']},\n {desc: '--attach with --detach', flags: ['--attach', 'job-123', '--detach']},\n ])('errors when using mutually exclusive flags: $desc', async ({flags}) => {\n const {error} = await testCommand(CopyDatasetCommand, flags)\n\n expect(error?.message).toContain('cannot also be provided when using')\n expect(error?.oclif?.exit).toBe(2)\n })\n\n test.each([\n {flag: '--offset', value: '2'},\n {flag: '--limit', value: '10'},\n ])('errors when $flag is used without --list', async ({flag, value}) => {\n const {error} = await testCommand(CopyDatasetCommand, [flag, value])\n\n expect(error?.message).toContain('--list')\n expect(error?.oclif?.exit).toBe(2)\n })\n })\n\n test('errors when no project ID is found', async () => {\n mockGetCliConfig.mockResolvedValueOnce({\n api: undefined,\n } as ReturnType<typeof getCliConfig> extends Promise<infer T> ? T : never)\n\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'])\n\n expect(error?.message).toContain('sanity.cli.ts does not contain a project identifier')\n expect(error?.oclif?.exit).toBe(1)\n })\n})\n"],"names":["runCommand","select","testCommand","of","throwError","afterEach","describe","expect","test","vi","getCliConfig","datasetsService","CopyDatasetCommand","mock","findProjectRoot","fn","mockResolvedValue","directory","root","type","api","projectId","getCliToken","actual","importActual","input","copyDataset","followCopyJobProgress","listDatasetCopyJobs","listDatasets","mockGetCliConfig","mocked","mockSelect","mockCopyDataset","mockFollowCopyJobProgress","mockListDatasetCopyJobs","mockListDatasets","createMockDataset","name","aclMode","addonFor","createdAt","createdByUserId","datasetProfile","features","tags","clearAllMocks","stdout","toMatchInlineSnapshot","id","sourceDataset","state","targetDataset","updatedAt","withHistory","toHaveBeenCalledWith","limit","undefined","offset","toContain","mockRejectedValue","Error","error","message","oclif","exit","toBe","mockReturnValue","progress","jobId","skipHistory","mockResolvedValueOnce","choices","arrayContaining","objectContaining","value","each","args","description","expectedError","setupMocks","not","toHaveBeenCalled","desc","flags","flag"],"mappings":"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"}
1
+ {"version":3,"sources":["../../../../src/commands/dataset/__tests__/copy.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {select} from '@sanity/cli-core/ux'\nimport {createTestClient, mockApi, testCommand} from '@sanity/cli-test'\nimport nock from 'nock'\nimport {of, throwError} from 'rxjs'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {DATASET_API_VERSION, followCopyJobProgress} from '../../../services/datasets.js'\nimport {CopyDatasetCommand} from '../copy.js'\n\nconst mockListDatasets = vi.hoisted(() => vi.fn())\nconst testProjectId = vi.hoisted(() => 'test-project')\nconst testToken = vi.hoisted(() => 'test-token')\n\nvi.mock('@sanity/cli-core', async (importOriginal) => {\n const actual = await importOriginal<typeof import('@sanity/cli-core')>()\n const testClient = createTestClient({\n apiVersion: 'v2025-09-16',\n projectId: testProjectId,\n token: testToken,\n })\n\n return {\n ...actual,\n getProjectCliClient: vi.fn().mockResolvedValue({\n datasets: {\n list: mockListDatasets,\n } as never,\n request: testClient.request,\n }),\n }\n})\n\nvi.mock('@sanity/cli-core/ux', async () => {\n const actual = await vi.importActual<typeof import('@sanity/cli-core/ux')>('@sanity/cli-core/ux')\n return {\n ...actual,\n input: vi.fn(),\n select: vi.fn(),\n }\n})\n\nvi.mock('../../../services/datasets.js', async (importOriginal) => {\n const actual = await importOriginal<typeof import('../../../services/datasets.js')>()\n return {\n ...actual,\n // Keep only followCopyJobProgress mocked since it uses EventSource streaming\n followCopyJobProgress: vi.fn(),\n }\n})\n\nconst defaultMocks = {\n cliConfig: {api: {projectId: testProjectId}},\n projectRoot: {\n directory: '/test/path',\n path: '/test/path/sanity.config.ts',\n type: 'studio' as const,\n },\n token: testToken,\n}\n\nconst mockSelect = vi.mocked(select)\nconst mockFollowCopyJobProgress = vi.mocked(followCopyJobProgress)\n\nfunction createMockDataset(name: string) {\n return {\n aclMode: 'public' as const,\n addonFor: null,\n createdAt: '2023-01-01T00:00:00Z',\n createdByUserId: 'test-user',\n datasetProfile: 'default',\n features: [],\n name,\n tags: [],\n }\n}\n\ndescribe('#dataset:copy', () => {\n afterEach(() => {\n vi.clearAllMocks()\n const pending = nock.pendingMocks()\n nock.cleanAll()\n expect(pending, 'pending mocks').toEqual([])\n })\n\n test('help works', async () => {\n const {stdout} = await runCommand(['dataset copy', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Manages dataset copying, including starting a new copy job, listing copy jobs and following the progress of a running copy job\n\n USAGE\n $ sanity dataset copy [SOURCE] [TARGET] [--attach <value> | --list |\n --detach | --skip-history] [--limit <value> ] [--offset <value> ]\n\n ARGUMENTS\n [SOURCE] Name of the dataset to copy from\n [TARGET] Name of the dataset to copy to\n\n FLAGS\n --attach=<value> Attach to the running copy process to show progress\n --detach Start the copy without waiting for it to finish\n --limit=<value> Maximum number of jobs returned (default 10, max 1000)\n --list Lists all dataset copy jobs\n --offset=<value> Start position in the list of jobs (default 0)\n --skip-history Don't preserve document history on copy\n\n DESCRIPTION\n Manages dataset copying, including starting a new copy job, listing copy jobs\n and following the progress of a running copy job\n\n EXAMPLES\n Interactively copy a dataset\n\n $ sanity dataset copy\n\n Copy from source-dataset (prompts for target)\n\n $ sanity dataset copy source-dataset\n\n Copy from source-dataset to target-dataset\n\n $ sanity dataset copy source-dataset target-dataset\n\n Copy without preserving document history (faster for large datasets)\n\n $ sanity dataset copy --skip-history source target\n\n Start copy job without waiting for completion\n\n $ sanity dataset copy --detach source target\n\n Attach to a running copy job to follow progress\n\n $ sanity dataset copy --attach <job-id>\n\n List all dataset copy jobs\n\n $ sanity dataset copy --list\n\n List copy jobs with pagination\n\n $ sanity dataset copy --list --offset 2 --limit 10\n\n \"\n `)\n })\n\n describe('list mode', () => {\n test('lists copy jobs successfully', async () => {\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'get',\n uri: `/projects/${testProjectId}/datasets/copy`,\n }).reply(200, [\n {\n createdAt: '2023-01-01T00:00:00Z',\n id: 'job-1',\n sourceDataset: 'production',\n state: 'completed',\n targetDataset: 'backup',\n updatedAt: '2023-01-01T00:05:00Z',\n withHistory: true,\n },\n {\n createdAt: '2023-01-02T00:00:00Z',\n id: 'job-2',\n sourceDataset: 'staging',\n state: 'failed',\n targetDataset: 'test',\n updatedAt: '2023-01-02T00:02:00Z',\n withHistory: false,\n },\n ])\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--list'], {mocks: defaultMocks})\n\n expect(stdout).toContain('Dataset copy jobs')\n expect(stdout).toContain('job-1')\n expect(stdout).toContain('job-2')\n expect(stdout).toContain('production')\n expect(stdout).toContain('staging')\n })\n\n test('lists copy jobs with offset and limit', async () => {\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'get',\n query: {\n limit: '10',\n offset: '2',\n },\n uri: `/projects/${testProjectId}/datasets/copy`,\n }).reply(200, [\n {\n createdAt: '2023-01-01T00:00:00Z',\n id: 'job-2',\n sourceDataset: 'production',\n state: 'completed',\n targetDataset: 'backup',\n updatedAt: '2023-01-01T00:05:00Z',\n withHistory: true,\n },\n {\n createdAt: '2023-01-02T00:00:00Z',\n id: 'job-3',\n sourceDataset: 'staging',\n state: 'failed',\n targetDataset: 'test',\n updatedAt: '2023-01-02T00:02:00Z',\n withHistory: false,\n },\n ])\n\n const {stdout} = await testCommand(\n CopyDatasetCommand,\n ['--list', '--offset', '2', '--limit', '10'],\n {\n mocks: defaultMocks,\n },\n )\n\n expect(stdout).toContain('job-2')\n expect(stdout).toContain('job-3')\n expect(stdout).toContain('production')\n expect(stdout).toContain('staging')\n })\n\n test('shows message when no copy jobs exist', async () => {\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'get',\n uri: `/projects/${testProjectId}/datasets/copy`,\n }).reply(200, [])\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--list'], {mocks: defaultMocks})\n\n expect(stdout).toContain(\"This project doesn't have any dataset copy jobs\")\n })\n\n test('handles errors when listing copy jobs', async () => {\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'get',\n uri: `/projects/${testProjectId}/datasets/copy`,\n }).reply(500, {\n error: 'API Error',\n message: 'API Error',\n })\n\n const {error} = await testCommand(CopyDatasetCommand, ['--list'], {mocks: defaultMocks})\n\n expect(error?.message).toContain('Failed to list dataset copy jobs')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('attach mode', () => {\n test('attaches to running job and shows progress', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n of(\n {progress: 25, type: 'progress'},\n {progress: 50, type: 'progress'},\n {progress: 75, type: 'progress'},\n {progress: 100, type: 'progress'},\n ),\n )\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'], {\n mocks: defaultMocks,\n })\n\n expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({\n jobId: 'job-123',\n projectId: 'test-project',\n })\n expect(stdout).toContain('Job job-123 completed')\n })\n\n test('handles progress tracking errors', async () => {\n mockFollowCopyJobProgress.mockReturnValue(throwError(() => new Error('Connection lost')))\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Failed to attach to copy job: Connection lost')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('rejects whitespace-only jobId', async () => {\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', ' '], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Please supply a valid jobId')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles JSON parse errors from EventSource', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n throwError(() => new Error('Invalid JSON received from server: Unexpected token')),\n )\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Invalid JSON received from server')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles EventSource reconnection', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n of({progress: 25, type: 'progress'}, {type: 'reconnect'}, {progress: 50, type: 'progress'}),\n )\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'], {\n mocks: defaultMocks,\n })\n\n expect(mockFollowCopyJobProgress).toHaveBeenCalledWith({\n jobId: 'job-123',\n projectId: 'test-project',\n })\n expect(stdout).toContain('Job job-123 completed')\n })\n\n test('handles channel_error from EventSource', async () => {\n mockFollowCopyJobProgress.mockReturnValue(\n throwError(() => new Error('Copy job failed: Channel closed unexpectedly')),\n )\n\n const {error} = await testCommand(CopyDatasetCommand, ['--attach', 'job-123'], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Copy job failed')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('copy mode', () => {\n test('copies dataset with provided arguments', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'put',\n uri: `/datasets/production/copy`,\n }).reply(200, {jobId: 'job-456'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['production', 'backup'], {\n mocks: defaultMocks,\n })\n\n expect(stdout).toContain('Copying dataset production to backup')\n expect(stdout).toContain('Job job-456 started')\n expect(stdout).toContain('Job job-456 completed')\n })\n\n test('prompts for source dataset when not provided', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockSelect.mockResolvedValueOnce('production')\n mockSelect.mockResolvedValueOnce('backup')\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'put',\n uri: `/datasets/production/copy`,\n }).reply(200, {jobId: 'job-789'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n await testCommand(CopyDatasetCommand, [], {mocks: defaultMocks})\n\n expect(mockSelect).toHaveBeenCalledWith({\n choices: expect.arrayContaining([\n expect.objectContaining({value: 'production'}),\n expect.objectContaining({value: 'staging'}),\n ]),\n message: 'Select the dataset name:',\n })\n })\n\n test.each([\n {\n args: ['Invalid-Dataset', 'backup'],\n description: 'source dataset name is invalid',\n expectedError: 'must be all lowercase',\n setupMocks: () => {\n // No additional mocks needed - validation happens before dataset fetch\n },\n },\n {\n args: ['nonexistent', 'backup'],\n description: 'source dataset does not exist',\n expectedError: 'Source dataset \"nonexistent\" doesn\\'t exist',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n {\n args: ['production', 'Invalid-Dataset'],\n description: 'target dataset name is invalid',\n expectedError: 'must be all lowercase',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n {\n args: ['production', 'staging'],\n description: 'target dataset already exists',\n expectedError: 'Target dataset \"staging\" already exists',\n setupMocks: () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n },\n },\n ])('errors when $description', async ({args, expectedError, setupMocks}) => {\n setupMocks()\n\n const {error} = await testCommand(CopyDatasetCommand, args, {mocks: defaultMocks})\n\n expect(error?.message).toContain(expectedError)\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('copies dataset with skip-history flag', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'put',\n uri: `/datasets/production/copy`,\n }).reply(200, {jobId: 'job-skip'})\n mockFollowCopyJobProgress.mockReturnValue(of({progress: 100, type: 'progress'}))\n\n await testCommand(CopyDatasetCommand, ['production', 'backup', '--skip-history'], {\n mocks: defaultMocks,\n })\n })\n\n test('copies dataset with detach flag (does not wait for completion)', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'put',\n uri: `/datasets/production/copy`,\n }).reply(200, {jobId: 'job-detach'})\n\n const {stdout} = await testCommand(CopyDatasetCommand, ['production', 'backup', '--detach'], {\n mocks: defaultMocks,\n })\n\n expect(stdout).toContain('Job job-detach started')\n expect(stdout).not.toContain('Job job-detach completed')\n expect(mockFollowCopyJobProgress).not.toHaveBeenCalled()\n })\n\n test('handles copy dataset errors', async () => {\n mockListDatasets.mockResolvedValue([\n createMockDataset('production'),\n createMockDataset('staging'),\n ])\n mockApi({\n apiHost: `https://${testProjectId}.api.sanity.io`,\n apiVersion: DATASET_API_VERSION,\n method: 'put',\n uri: `/datasets/production/copy`,\n }).reply(500, {\n error: 'Insufficient permissions',\n message: 'Insufficient permissions',\n })\n\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Dataset copying failed')\n expect(error?.oclif?.exit).toBe(1)\n })\n\n test('handles fetch datasets error', async () => {\n mockListDatasets.mockRejectedValue(new Error('Network error'))\n\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'], {\n mocks: defaultMocks,\n })\n\n expect(error?.message).toContain('Failed to fetch datasets: Network error')\n expect(error?.oclif?.exit).toBe(1)\n })\n })\n\n describe('flag validation', () => {\n test.each([\n {desc: '--list with --attach', flags: ['--list', '--attach', 'job-123']},\n {desc: '--list with --detach', flags: ['--list', '--detach']},\n {desc: '--attach with --detach', flags: ['--attach', 'job-123', '--detach']},\n ])('errors when using mutually exclusive flags: $desc', async ({flags}) => {\n const {error} = await testCommand(CopyDatasetCommand, flags, {mocks: defaultMocks})\n\n expect(error?.message).toContain('cannot also be provided when using')\n expect(error?.oclif?.exit).toBe(2)\n })\n\n test.each([\n {flag: '--offset', value: '2'},\n {flag: '--limit', value: '10'},\n ])('errors when $flag is used without --list', async ({flag, value}) => {\n const {error} = await testCommand(CopyDatasetCommand, [flag, value], {mocks: defaultMocks})\n\n expect(error?.message).toContain('--list')\n expect(error?.oclif?.exit).toBe(2)\n })\n })\n\n test('errors when no project ID is found', async () => {\n const {error} = await testCommand(CopyDatasetCommand, ['production', 'backup'], {\n mocks: {\n ...defaultMocks,\n cliConfig: {api: undefined},\n },\n })\n\n expect(error?.message).toContain('sanity.cli.ts does not contain a project identifier')\n expect(error?.oclif?.exit).toBe(1)\n })\n})\n"],"names":["runCommand","select","createTestClient","mockApi","testCommand","nock","of","throwError","afterEach","describe","expect","test","vi","DATASET_API_VERSION","followCopyJobProgress","CopyDatasetCommand","mockListDatasets","hoisted","fn","testProjectId","testToken","mock","importOriginal","actual","testClient","apiVersion","projectId","token","getProjectCliClient","mockResolvedValue","datasets","list","request","importActual","input","defaultMocks","cliConfig","api","projectRoot","directory","path","type","mockSelect","mocked","mockFollowCopyJobProgress","createMockDataset","name","aclMode","addonFor","createdAt","createdByUserId","datasetProfile","features","tags","clearAllMocks","pending","pendingMocks","cleanAll","toEqual","stdout","toMatchInlineSnapshot","apiHost","method","uri","reply","id","sourceDataset","state","targetDataset","updatedAt","withHistory","mocks","toContain","query","limit","offset","error","message","oclif","exit","toBe","mockReturnValue","progress","toHaveBeenCalledWith","jobId","Error","mockResolvedValueOnce","choices","arrayContaining","objectContaining","value","each","args","description","expectedError","setupMocks","not","toHaveBeenCalled","mockRejectedValue","desc","flags","flag","undefined"],"mappings":"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"}