@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
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../../../src/commands/__tests__/init/init.setup.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {testCommand} from '@sanity/cli-test'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {InitCommand} from '../../init'\n\nconst mocks = vi.hoisted(() => ({\n checkIsRemoteTemplate: vi.fn().mockReturnValue(false),\n detectFrameworkRecord: vi.fn(),\n getById: vi.fn(),\n getGitHubRepoInfo: vi.fn(),\n}))\n\nvi.mock('@vercel/fs-detectors', () => ({\n detectFrameworkRecord: mocks.detectFrameworkRecord,\n LocalFileSystemDetector: vi.fn(),\n}))\n\nvi.mock('../../../actions/init/remoteTemplate.js', () => ({\n checkIsRemoteTemplate: mocks.checkIsRemoteTemplate,\n getGitHubRepoInfo: mocks.getGitHubRepoInfo,\n}))\n\nvi.mock('@sanity/cli-core', async (importOriginal) => {\n const actual = await importOriginal<typeof import('@sanity/cli-core')>()\n return {\n ...actual,\n getGlobalCliClient: vi.fn().mockResolvedValue({\n users: {\n getById: mocks.getById,\n } as never,\n }),\n }\n})\n\n// Set default mock behavior for getById\nmocks.getById.mockResolvedValue({\n email: 'test@example.com',\n id: 'user-123',\n name: 'Test User',\n provider: 'saml-123',\n})\n\ndescribe('#init: oclif command setup', () => {\n afterEach(() => {\n vi.clearAllMocks()\n })\n\n test('--help works', async () => {\n const {stdout} = await runCommand('init --help')\n\n expect(stdout).toMatchInlineSnapshot(String.raw`\n \"Initialize a new Sanity Studio, project and/or app\n\n USAGE\n $ sanity init [--json] [--auto-updates | --bare] [--coupon\n <code> | --project-plan <name>] [--dataset <name> | --dataset-default]\n [--env <filename> | ] [--git <message> | ] [--mcp]\n [--nextjs-add-config-files] [--nextjs-append-env] [--nextjs-embed-studio]\n [--organization <id>] [--output-path <path> | ] [--overwrite-files]\n [--package-manager <manager> | ] [--project <id> | --create-project <name>]\n [--provider <provider>] [--template <template> | ] [--typescript | ]\n [--visibility <mode>] [-y]\n\n FLAGS\n -y, --yes Unattended mode, answers \"yes\" to any\n \"yes/no\" prompt and otherwise uses defaults\n --[no-]auto-updates Enable auto updates of studio versions\n --bare Skip the Studio initialization and only print\n the selected project ID and dataset name to\n stdout\n --coupon=<code> Optionally select a coupon for a new project\n (cannot be used with --project-plan)\n --create-project=<name> Create a new project with the given name\n --dataset=<name> Dataset name for the studio\n --dataset-default Set up a project with a public dataset named\n \"production\"\n --env=<filename> Write environment variables to file\n --[no-]git=<message> Specify a commit message for initial commit,\n or disable git init\n --[no-]mcp Enable AI editor integration (MCP) setup\n --organization=<id> Organization ID to use for the project\n --output-path=<path> Path to write studio project to\n --overwrite-files Overwrite existing files\n --package-manager=<manager> Specify which package manager to use\n [allowed: npm, yarn, pnpm]\n --project=<id> Project ID to use for the studio\n --project-plan=<name> Optionally select a plan for a new project\n --provider=<provider> Login provider to use\n --template=<template> [default: clean] Project template to use\n [default: \"clean\"]\n --[no-]typescript Enable TypeScript support\n --visibility=<mode> Visibility mode for dataset\n\n GLOBAL FLAGS\n --json Format output as json.\n\n NEXT.JS FLAGS\n --[no-]nextjs-add-config-files Add config files to Next.js project\n --[no-]nextjs-append-env Append project ID and dataset to .env file\n --[no-]nextjs-embed-studio Embed the Studio in Next.js application\n\n DESCRIPTION\n Initialize a new Sanity Studio, project and/or app\n\n EXAMPLES\n $ sanity init\n\n Initialize a new project with a public dataset named \"production\"\n\n $ sanity init --dataset-default\n\n Initialize a project with the given project ID and dataset to the given path\n\n $ sanity init -y --project abc123 --dataset production --output-path \\\n ~/myproj\n\n Initialize a project with the given project ID and dataset using the moviedb\n template to the given path\n\n $ sanity init -y --project abc123 --dataset staging --template moviedb \\\n --output-path .\n\n Create a brand new project with name \"Movies Unlimited\"\n\n $ sanity init -y --create-project \"Movies Unlimited\" --dataset moviedb \\\n --visibility private --template moviedb --output-path \\\n /Users/espenh/movies-unlimited\n\n \"\n `)\n })\n\n test.each([\n {flag1: 'auto-updates', flag2: 'bare'},\n {flag1: 'coupon=123', flag2: 'project-plan=123'},\n {flag1: 'dataset=\"123', flag2: 'dataset-default'},\n {flag1: 'env=.env', flag2: 'bare'},\n {flag1: 'git=test', flag2: 'bare'},\n {flag1: 'no-git', flag2: 'git=test'},\n {flag1: 'output-path=/test-path', flag2: 'bare'},\n {flag1: 'package-manager=pnpm', flag2: 'bare'},\n {flag1: 'template=test', flag2: 'bare'},\n {flag1: 'typescript', flag2: 'bare'},\n {flag1: 'project=test', flag2: 'create-project=test'},\n ])('throws error when `$flag1` and `$flag2` flags are both passed', async ({flag1, flag2}) => {\n const {error} = await testCommand(InitCommand, [`--${flag1}`, `--${flag2}`], {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n })\n\n const [name1] = flag1.split('=')\n const [name2, value2 = 'true'] = flag2.split('=')\n\n expect(error?.message).toContain(\n `--${name2}=${value2} cannot also be provided when using --${name1}`,\n )\n })\n\n test.each([\n {flag: 'env', message: 'Env filename (`--env`) must start with `.env`', value: 'invalid.txt'},\n {\n flag: 'visibility',\n message: 'Expected --visibility=opaque to be one of: public, private',\n value: 'opaque',\n },\n {\n flag: 'package-manager',\n message: 'Expected --package-manager=pnm to be one of: npm, yarn, pnpm',\n value: 'pnm',\n },\n ])('throws error when `$flag` value is invalid', async ({flag, message, value}) => {\n const {error} = await testCommand(InitCommand, [`--${flag}=${value}`], {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n })\n\n expect(error?.message).toContain(message)\n })\n\n test('throws error when type argument is passed', async () => {\n const {error} = await testCommand(InitCommand, ['bad-argument'], {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n })\n\n expect(error?.message).toContain('Unknown init type \"bad-argument\"')\n })\n\n test('throws deprecation error when type argument is passed with `plugin`', async () => {\n const {error} = await testCommand(InitCommand, ['plugin'], {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n })\n\n expect(error?.message).toContain('Initializing plugins through the CLI is no longer supported')\n })\n\n test('throws error when `reconfigure` flag is passed', async () => {\n const {error} = await testCommand(InitCommand, ['--reconfigure'], {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n })\n\n expect(error?.message).toContain(\n '--reconfigure is deprecated - manual configuration is now required',\n )\n })\n\n test('throws error when framework and remote template are used together', async () => {\n mocks.detectFrameworkRecord.mockResolvedValueOnce({\n name: 'Next.js',\n slug: 'nextjs',\n })\n mocks.checkIsRemoteTemplate.mockReturnValueOnce(true)\n mocks.getGitHubRepoInfo.mockResolvedValueOnce({\n branch: 'main',\n owner: 'sanity-io',\n repo: 'sanity',\n })\n\n const {error} = await testCommand(\n InitCommand,\n ['--template=https://github.com/sanity-io/sanity'],\n {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n },\n )\n\n expect(error?.message).toContain(\n 'A remote template cannot be used with a detected framework. Detected: Next.js',\n )\n })\n\n test('throws error when in unattended mode and `dataset` is not set', async () => {\n const {error} = await testCommand(InitCommand, ['--yes'], {\n mocks: {\n token: 'test-token',\n },\n })\n\n expect(error?.message).toContain('`--dataset` must be specified in unattended mode')\n })\n\n test('throws error when `output-path` is not used in unattended mode with non-nextjs project', async () => {\n // Mock no framework or a non-Next.js framework\n mocks.detectFrameworkRecord.mockResolvedValueOnce(null)\n\n const {error} = await testCommand(\n InitCommand,\n ['--yes', '--dataset=production', '--project=test-project'],\n {\n mocks: {\n token: 'test-token',\n },\n },\n )\n\n // Should throw output-path error for non-Next.js projects\n expect(error?.message).toContain('`--output-path` must be specified in unattended mode')\n })\n\n test('throws error when in unattended mode and `project` and `create-project` not set', async () => {\n mocks.detectFrameworkRecord.mockResolvedValueOnce({\n name: 'Next.js',\n slug: 'nextjs',\n })\n\n const {error} = await testCommand(\n InitCommand,\n [\n '--yes',\n '--dataset=production',\n // Deliberately omitting --project and --create-project\n ],\n {\n mocks: {\n token: 'test-token',\n },\n },\n )\n\n expect(error?.message).toContain(\n '`--project <id>` or `--create-project <name>` must be specified in unattended mode',\n )\n })\n\n test('throws error when in unattended mode and `create-project` not set with `organization`', async () => {\n mocks.detectFrameworkRecord.mockResolvedValueOnce({\n name: 'Next.js',\n slug: 'nextjs',\n })\n\n const {error} = await testCommand(\n InitCommand,\n ['--yes', '--dataset=production', '--create-project=test'],\n {\n mocks: {\n token: 'test-token',\n },\n },\n )\n\n expect(error?.message).toContain(\n '--create-project is not supported in unattended mode without an organization, please specify an organization with `--organization <id>`',\n )\n })\n\n test('logs properly if app template flag is not valid', async () => {\n mocks.detectFrameworkRecord.mockResolvedValueOnce(null)\n\n const {stdout} = await testCommand(\n InitCommand,\n [\n '--template=invalid-template-name', // Not a valid app template\n ],\n {\n mocks: {\n isInteractive: true,\n token: 'test-token',\n },\n },\n )\n\n // When template is not an app template, it should log \"Fetching existing projects\"\n expect(stdout).toContain('Fetching existing projects')\n })\n})\n"],"names":["runCommand","testCommand","afterEach","describe","expect","test","vi","InitCommand","mocks","hoisted","checkIsRemoteTemplate","fn","mockReturnValue","detectFrameworkRecord","getById","getGitHubRepoInfo","mock","LocalFileSystemDetector","importOriginal","actual","getGlobalCliClient","mockResolvedValue","users","email","id","name","provider","clearAllMocks","stdout","toMatchInlineSnapshot","String","raw","each","flag1","flag2","error","isInteractive","token","name1","split","name2","value2","message","toContain","flag","value","mockResolvedValueOnce","slug","mockReturnValueOnce","branch","owner","repo"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,WAAW,QAAO,mBAAkB;AAC5C,SAAQC,SAAS,EAAEC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,EAAEC,EAAE,QAAO,SAAQ;AAE5D,SAAQC,WAAW,QAAO,aAAY;AAEtC,MAAMC,QAAQF,GAAGG,OAAO,CAAC,IAAO,CAAA;QAC9BC,uBAAuBJ,GAAGK,EAAE,GAAGC,eAAe,CAAC;QAC/CC,uBAAuBP,GAAGK,EAAE;QAC5BG,SAASR,GAAGK,EAAE;QACdI,mBAAmBT,GAAGK,EAAE;IAC1B,CAAA;AAEAL,GAAGU,IAAI,CAAC,wBAAwB,IAAO,CAAA;QACrCH,uBAAuBL,MAAMK,qBAAqB;QAClDI,yBAAyBX,GAAGK,EAAE;IAChC,CAAA;AAEAL,GAAGU,IAAI,CAAC,2CAA2C,IAAO,CAAA;QACxDN,uBAAuBF,MAAME,qBAAqB;QAClDK,mBAAmBP,MAAMO,iBAAiB;IAC5C,CAAA;AAEAT,GAAGU,IAAI,CAAC,oBAAoB,OAAOE;IACjC,MAAMC,SAAS,MAAMD;IACrB,OAAO;QACL,GAAGC,MAAM;QACTC,oBAAoBd,GAAGK,EAAE,GAAGU,iBAAiB,CAAC;YAC5CC,OAAO;gBACLR,SAASN,MAAMM,OAAO;YACxB;QACF;IACF;AACF;AAEA,wCAAwC;AACxCN,MAAMM,OAAO,CAACO,iBAAiB,CAAC;IAC9BE,OAAO;IACPC,IAAI;IACJC,MAAM;IACNC,UAAU;AACZ;AAEAvB,SAAS,8BAA8B;IACrCD,UAAU;QACRI,GAAGqB,aAAa;IAClB;IAEAtB,KAAK,gBAAgB;QACnB,MAAM,EAACuB,MAAM,EAAC,GAAG,MAAM5B,WAAW;QAElCI,OAAOwB,QAAQC,qBAAqB,CAACC,OAAOC,GAAG,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;MA+E9C,CAAC;IACL;IAEA1B,KAAK2B,IAAI,CAAC;QACR;YAACC,OAAO;YAAgBC,OAAO;QAAM;QACrC;YAACD,OAAO;YAAcC,OAAO;QAAkB;QAC/C;YAACD,OAAO;YAAgBC,OAAO;QAAiB;QAChD;YAACD,OAAO;YAAYC,OAAO;QAAM;QACjC;YAACD,OAAO;YAAYC,OAAO;QAAM;QACjC;YAACD,OAAO;YAAUC,OAAO;QAAU;QACnC;YAACD,OAAO;YAA0BC,OAAO;QAAM;QAC/C;YAACD,OAAO;YAAwBC,OAAO;QAAM;QAC7C;YAACD,OAAO;YAAiBC,OAAO;QAAM;QACtC;YAACD,OAAO;YAAcC,OAAO;QAAM;QACnC;YAACD,OAAO;YAAgBC,OAAO;QAAqB;KACrD,EAAE,iEAAiE,OAAO,EAACD,KAAK,EAAEC,KAAK,EAAC;QACvF,MAAM,EAACC,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC,CAAC,EAAE,EAAE0B,OAAO;YAAE,CAAC,EAAE,EAAEC,OAAO;SAAC,EAAE;YAC3E1B,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAEA,MAAM,CAACC,MAAM,GAAGL,MAAMM,KAAK,CAAC;QAC5B,MAAM,CAACC,OAAOC,SAAS,MAAM,CAAC,GAAGP,MAAMK,KAAK,CAAC;QAE7CnC,OAAO+B,OAAOO,SAASC,SAAS,CAC9B,CAAC,EAAE,EAAEH,MAAM,CAAC,EAAEC,OAAO,sCAAsC,EAAEH,OAAO;IAExE;IAEAjC,KAAK2B,IAAI,CAAC;QACR;YAACY,MAAM;YAAOF,SAAS;YAAiDG,OAAO;QAAa;QAC5F;YACED,MAAM;YACNF,SAAS;YACTG,OAAO;QACT;QACA;YACED,MAAM;YACNF,SAAS;YACTG,OAAO;QACT;KACD,EAAE,8CAA8C,OAAO,EAACD,IAAI,EAAEF,OAAO,EAAEG,KAAK,EAAC;QAC5E,MAAM,EAACV,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC,CAAC,EAAE,EAAEqC,KAAK,CAAC,EAAEC,OAAO;SAAC,EAAE;YACrErC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAEAjC,OAAO+B,OAAOO,SAASC,SAAS,CAACD;IACnC;IAEArC,KAAK,6CAA6C;QAChD,MAAM,EAAC8B,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC;SAAe,EAAE;YAC/DC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAEAjC,OAAO+B,OAAOO,SAASC,SAAS,CAAC;IACnC;IAEAtC,KAAK,uEAAuE;QAC1E,MAAM,EAAC8B,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC;SAAS,EAAE;YACzDC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAEAjC,OAAO+B,OAAOO,SAASC,SAAS,CAAC;IACnC;IAEAtC,KAAK,kDAAkD;QACrD,MAAM,EAAC8B,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC;SAAgB,EAAE;YAChEC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAEAjC,OAAO+B,OAAOO,SAASC,SAAS,CAC9B;IAEJ;IAEAtC,KAAK,qEAAqE;QACxEG,MAAMK,qBAAqB,CAACiC,qBAAqB,CAAC;YAChDrB,MAAM;YACNsB,MAAM;QACR;QACAvC,MAAME,qBAAqB,CAACsC,mBAAmB,CAAC;QAChDxC,MAAMO,iBAAiB,CAAC+B,qBAAqB,CAAC;YAC5CG,QAAQ;YACRC,OAAO;YACPC,MAAM;QACR;QAEA,MAAM,EAAChB,KAAK,EAAC,GAAG,MAAMlC,YACpBM,aACA;YAAC;SAAiD,EAClD;YACEC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAGFjC,OAAO+B,OAAOO,SAASC,SAAS,CAC9B;IAEJ;IAEAtC,KAAK,iEAAiE;QACpE,MAAM,EAAC8B,KAAK,EAAC,GAAG,MAAMlC,YAAYM,aAAa;YAAC;SAAQ,EAAE;YACxDC,OAAO;gBACL6B,OAAO;YACT;QACF;QAEAjC,OAAO+B,OAAOO,SAASC,SAAS,CAAC;IACnC;IAEAtC,KAAK,0FAA0F;QAC7F,+CAA+C;QAC/CG,MAAMK,qBAAqB,CAACiC,qBAAqB,CAAC;QAElD,MAAM,EAACX,KAAK,EAAC,GAAG,MAAMlC,YACpBM,aACA;YAAC;YAAS;YAAwB;SAAyB,EAC3D;YACEC,OAAO;gBACL6B,OAAO;YACT;QACF;QAGF,0DAA0D;QAC1DjC,OAAO+B,OAAOO,SAASC,SAAS,CAAC;IACnC;IAEAtC,KAAK,mFAAmF;QACtFG,MAAMK,qBAAqB,CAACiC,qBAAqB,CAAC;YAChDrB,MAAM;YACNsB,MAAM;QACR;QAEA,MAAM,EAACZ,KAAK,EAAC,GAAG,MAAMlC,YACpBM,aACA;YACE;YACA;SAED,EACD;YACEC,OAAO;gBACL6B,OAAO;YACT;QACF;QAGFjC,OAAO+B,OAAOO,SAASC,SAAS,CAC9B;IAEJ;IAEAtC,KAAK,yFAAyF;QAC5FG,MAAMK,qBAAqB,CAACiC,qBAAqB,CAAC;YAChDrB,MAAM;YACNsB,MAAM;QACR;QAEA,MAAM,EAACZ,KAAK,EAAC,GAAG,MAAMlC,YACpBM,aACA;YAAC;YAAS;YAAwB;SAAwB,EAC1D;YACEC,OAAO;gBACL6B,OAAO;YACT;QACF;QAGFjC,OAAO+B,OAAOO,SAASC,SAAS,CAC9B;IAEJ;IAEAtC,KAAK,mDAAmD;QACtDG,MAAMK,qBAAqB,CAACiC,qBAAqB,CAAC;QAElD,MAAM,EAAClB,MAAM,EAAC,GAAG,MAAM3B,YACrBM,aACA;YACE;SACD,EACD;YACEC,OAAO;gBACL4B,eAAe;gBACfC,OAAO;YACT;QACF;QAGF,mFAAmF;QACnFjC,OAAOwB,QAAQe,SAAS,CAAC;IAC3B;AACF"}
@@ -4,15 +4,6 @@ import { afterEach, describe, expect, test, vi } from 'vitest';
4
4
  import { installDeclaredPackages, installNewPackages } from '../../util/packageManager/installPackages.js';
5
5
  import { getPackageManagerChoice } from '../../util/packageManager/packageManagerChoice.js';
6
6
  import { Install } from '../install.js';
7
- vi.mock('../../../../cli-core/src/config/findProjectRoot.js', async ()=>{
8
- return {
9
- findProjectRoot: vi.fn().mockResolvedValue({
10
- directory: '/test/project',
11
- root: '/test/project',
12
- type: 'studio'
13
- })
14
- };
15
- });
16
7
  vi.mock('../../util/packageManager/packageManagerChoice.js', ()=>({
17
8
  getPackageManagerChoice: vi.fn()
18
9
  }));
@@ -23,6 +14,13 @@ vi.mock('../../util/packageManager/installPackages.js', ()=>({
23
14
  const mockGetPackageManagerChoice = vi.mocked(getPackageManagerChoice);
24
15
  const mockInstallDeclaredPackages = vi.mocked(installDeclaredPackages);
25
16
  const mockInstallNewPackages = vi.mocked(installNewPackages);
17
+ const defaultMocks = {
18
+ projectRoot: {
19
+ directory: '/test/project',
20
+ path: '/test/project/sanity.config.ts',
21
+ type: 'studio'
22
+ }
23
+ };
26
24
  afterEach(()=>{
27
25
  vi.clearAllMocks();
28
26
  });
@@ -58,7 +56,9 @@ describe('#install', ()=>{
58
56
  mostOptimal: 'npm'
59
57
  });
60
58
  mockInstallDeclaredPackages.mockResolvedValueOnce();
61
- const { error } = await testCommand(Install, []);
59
+ const { error } = await testCommand(Install, [], {
60
+ mocks: defaultMocks
61
+ });
62
62
  expect(error).toBeUndefined();
63
63
  expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {
64
64
  interactive: true
@@ -74,7 +74,9 @@ describe('#install', ()=>{
74
74
  mostOptimal: 'yarn'
75
75
  });
76
76
  mockInstallDeclaredPackages.mockResolvedValueOnce();
77
- const { error } = await testCommand(Install, []);
77
+ const { error } = await testCommand(Install, [], {
78
+ mocks: defaultMocks
79
+ });
78
80
  expect(error).toBeUndefined();
79
81
  expect(mockInstallDeclaredPackages).toHaveBeenCalledWith('/test/project', 'yarn', expect.objectContaining({
80
82
  workDir: '/test/project'
@@ -86,7 +88,9 @@ describe('#install', ()=>{
86
88
  mostOptimal: 'pnpm'
87
89
  });
88
90
  mockInstallDeclaredPackages.mockResolvedValueOnce();
89
- const { error } = await testCommand(Install, []);
91
+ const { error } = await testCommand(Install, [], {
92
+ mocks: defaultMocks
93
+ });
90
94
  expect(error).toBeUndefined();
91
95
  expect(mockInstallDeclaredPackages).toHaveBeenCalledWith('/test/project', 'pnpm', expect.objectContaining({
92
96
  workDir: '/test/project'
@@ -98,7 +102,9 @@ describe('#install', ()=>{
98
102
  mostOptimal: 'bun'
99
103
  });
100
104
  mockInstallDeclaredPackages.mockResolvedValueOnce();
101
- const { error } = await testCommand(Install, []);
105
+ const { error } = await testCommand(Install, [], {
106
+ mocks: defaultMocks
107
+ });
102
108
  expect(error).toBeUndefined();
103
109
  expect(mockInstallDeclaredPackages).toHaveBeenCalledWith('/test/project', 'bun', expect.objectContaining({
104
110
  workDir: '/test/project'
@@ -110,7 +116,9 @@ describe('#install', ()=>{
110
116
  mostOptimal: 'npm'
111
117
  });
112
118
  mockInstallDeclaredPackages.mockResolvedValueOnce();
113
- const { error } = await testCommand(Install, []);
119
+ const { error } = await testCommand(Install, [], {
120
+ mocks: defaultMocks
121
+ });
114
122
  expect(error).toBeUndefined();
115
123
  expect(mockInstallDeclaredPackages).toHaveBeenCalledWith('/test/project', 'manual', expect.objectContaining({
116
124
  workDir: '/test/project'
@@ -126,7 +134,9 @@ describe('#install', ()=>{
126
134
  mockInstallNewPackages.mockResolvedValueOnce();
127
135
  const { error } = await testCommand(Install, [
128
136
  '@sanity/vision'
129
- ]);
137
+ ], {
138
+ mocks: defaultMocks
139
+ });
130
140
  expect(error).toBeUndefined();
131
141
  expect(mockInstallNewPackages).toHaveBeenCalledWith({
132
142
  packageManager: 'npm',
@@ -148,7 +158,9 @@ describe('#install', ()=>{
148
158
  '@sanity/vision',
149
159
  'react-icons',
150
160
  'lodash'
151
- ]);
161
+ ], {
162
+ mocks: defaultMocks
163
+ });
152
164
  expect(error).toBeUndefined();
153
165
  expect(mockInstallNewPackages).toHaveBeenCalledWith({
154
166
  packageManager: 'yarn',
@@ -170,7 +182,9 @@ describe('#install', ()=>{
170
182
  mockInstallNewPackages.mockResolvedValueOnce();
171
183
  const { error } = await testCommand(Install, [
172
184
  'some-package'
173
- ]);
185
+ ], {
186
+ mocks: defaultMocks
187
+ });
174
188
  expect(error).toBeUndefined();
175
189
  expect(mockInstallNewPackages).toHaveBeenCalledWith({
176
190
  packageManager: 'pnpm',
@@ -185,7 +199,9 @@ describe('#install', ()=>{
185
199
  describe('error handling', ()=>{
186
200
  test('handles package manager choice failure', async ()=>{
187
201
  mockGetPackageManagerChoice.mockRejectedValueOnce(new Error('Failed to detect package manager'));
188
- const { error } = await testCommand(Install, []);
202
+ const { error } = await testCommand(Install, [], {
203
+ mocks: defaultMocks
204
+ });
189
205
  expect(error).toBeDefined();
190
206
  expect(error?.message).toContain('Failed to detect package manager');
191
207
  expect(mockInstallDeclaredPackages).not.toHaveBeenCalled();
@@ -197,7 +213,9 @@ describe('#install', ()=>{
197
213
  mostOptimal: 'npm'
198
214
  });
199
215
  mockInstallDeclaredPackages.mockRejectedValueOnce(new Error('Installation failed'));
200
- const { error } = await testCommand(Install, []);
216
+ const { error } = await testCommand(Install, [], {
217
+ mocks: defaultMocks
218
+ });
201
219
  expect(error).toBeDefined();
202
220
  expect(error?.message).toContain('Installation failed');
203
221
  });
@@ -209,7 +227,9 @@ describe('#install', ()=>{
209
227
  mockInstallNewPackages.mockRejectedValueOnce(new Error('Package not found'));
210
228
  const { error } = await testCommand(Install, [
211
229
  'nonexistent-package'
212
- ]);
230
+ ], {
231
+ mocks: defaultMocks
232
+ });
213
233
  expect(error).toBeDefined();
214
234
  expect(error?.message).toContain('Package not found');
215
235
  });
@@ -221,7 +241,9 @@ describe('#install', ()=>{
221
241
  mostOptimal: 'npm'
222
242
  });
223
243
  mockInstallDeclaredPackages.mockResolvedValueOnce();
224
- await testCommand(Install, []);
244
+ await testCommand(Install, [], {
245
+ mocks: defaultMocks
246
+ });
225
247
  expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {
226
248
  interactive: true
227
249
  });
@@ -237,7 +259,9 @@ describe('#install', ()=>{
237
259
  mockInstallNewPackages.mockResolvedValueOnce();
238
260
  await testCommand(Install, [
239
261
  'test-package'
240
- ]);
262
+ ], {
263
+ mocks: defaultMocks
264
+ });
241
265
  expect(mockInstallNewPackages).toHaveBeenCalledWith({
242
266
  packageManager: 'npm',
243
267
  packages: [
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/commands/__tests__/install.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {testCommand} from '@sanity/cli-test'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {\n installDeclaredPackages,\n installNewPackages,\n} from '../../util/packageManager/installPackages.js'\nimport {getPackageManagerChoice} from '../../util/packageManager/packageManagerChoice.js'\nimport {Install} from '../install.js'\n\nvi.mock('../../../../cli-core/src/config/findProjectRoot.js', async () => {\n return {\n findProjectRoot: vi.fn().mockResolvedValue({\n directory: '/test/project',\n root: '/test/project',\n type: 'studio',\n }),\n }\n})\n\nvi.mock('../../util/packageManager/packageManagerChoice.js', () => ({\n getPackageManagerChoice: vi.fn(),\n}))\n\nvi.mock('../../util/packageManager/installPackages.js', () => ({\n installDeclaredPackages: vi.fn(),\n installNewPackages: vi.fn(),\n}))\n\nconst mockGetPackageManagerChoice = vi.mocked(getPackageManagerChoice)\nconst mockInstallDeclaredPackages = vi.mocked(installDeclaredPackages)\nconst mockInstallNewPackages = vi.mocked(installNewPackages)\n\nafterEach(() => {\n vi.clearAllMocks()\n})\n\ndescribe('#install', () => {\n test('help text is correct', async () => {\n const {stdout} = await runCommand('install --help')\n expect(stdout).toMatchInlineSnapshot(`\n \"Installs dependencies for Sanity Studio project\n\n USAGE\n $ sanity install [PACKAGES...]\n\n ARGUMENTS\n [PACKAGES...] Packages to install\n\n DESCRIPTION\n Installs dependencies for Sanity Studio project\n\n EXAMPLES\n $ sanity install\n\n $ sanity install @sanity/vision\n\n $ sanity install some-package another-package\n\n \"\n `)\n })\n\n describe('install declared packages (no arguments)', () => {\n test('installs declared packages with npm', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeUndefined()\n expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {\n interactive: true,\n })\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'npm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallNewPackages).not.toHaveBeenCalled()\n })\n\n test('installs declared packages with yarn', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'yarn',\n mostOptimal: 'yarn',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'yarn',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('installs declared packages with pnpm', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'pnpm',\n mostOptimal: 'pnpm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'pnpm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('installs declared packages with bun', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'bun',\n mostOptimal: 'bun',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'bun',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('handles manual package manager selection', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'manual',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'manual',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n })\n\n describe('install specific packages (with arguments)', () => {\n test('installs single package', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['@sanity/vision'])\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'npm',\n packages: ['@sanity/vision'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n })\n\n test('installs multiple packages', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'yarn',\n mostOptimal: 'yarn',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['@sanity/vision', 'react-icons', 'lodash'])\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'yarn',\n packages: ['@sanity/vision', 'react-icons', 'lodash'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n })\n\n test('installs packages with different package managers', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'pnpm',\n mostOptimal: 'pnpm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['some-package'])\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'pnpm',\n packages: ['some-package'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n })\n\n describe('error handling', () => {\n test('handles package manager choice failure', async () => {\n mockGetPackageManagerChoice.mockRejectedValueOnce(\n new Error('Failed to detect package manager'),\n )\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Failed to detect package manager')\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n expect(mockInstallNewPackages).not.toHaveBeenCalled()\n })\n\n test('handles declared packages installation failure', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockRejectedValueOnce(new Error('Installation failed'))\n\n const {error} = await testCommand(Install, [])\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Installation failed')\n })\n\n test('handles new packages installation failure', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockRejectedValueOnce(new Error('Package not found'))\n\n const {error} = await testCommand(Install, ['nonexistent-package'])\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Package not found')\n })\n })\n\n describe('integration with project root', () => {\n test('passes correct working directory to functions', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n await testCommand(Install, [])\n\n expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {\n interactive: true,\n })\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'npm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('provides output object to install functions', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n await testCommand(Install, ['test-package'])\n\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'npm',\n packages: ['test-package'],\n },\n expect.objectContaining({\n output: expect.objectContaining({\n error: expect.any(Function),\n log: expect.any(Function),\n warn: expect.any(Function),\n }),\n workDir: '/test/project',\n }),\n )\n })\n })\n})\n"],"names":["runCommand","testCommand","afterEach","describe","expect","test","vi","installDeclaredPackages","installNewPackages","getPackageManagerChoice","Install","mock","findProjectRoot","fn","mockResolvedValue","directory","root","type","mockGetPackageManagerChoice","mocked","mockInstallDeclaredPackages","mockInstallNewPackages","clearAllMocks","stdout","toMatchInlineSnapshot","mockResolvedValueOnce","chosen","mostOptimal","error","toBeUndefined","toHaveBeenCalledWith","interactive","objectContaining","workDir","not","toHaveBeenCalled","packageManager","packages","mockRejectedValueOnce","Error","toBeDefined","message","toContain","output","any","Function","log","warn"],"mappings":"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"}
1
+ {"version":3,"sources":["../../../src/commands/__tests__/install.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {testCommand} from '@sanity/cli-test'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {\n installDeclaredPackages,\n installNewPackages,\n} from '../../util/packageManager/installPackages.js'\nimport {getPackageManagerChoice} from '../../util/packageManager/packageManagerChoice.js'\nimport {Install} from '../install.js'\n\nvi.mock('../../util/packageManager/packageManagerChoice.js', () => ({\n getPackageManagerChoice: vi.fn(),\n}))\n\nvi.mock('../../util/packageManager/installPackages.js', () => ({\n installDeclaredPackages: vi.fn(),\n installNewPackages: vi.fn(),\n}))\n\nconst mockGetPackageManagerChoice = vi.mocked(getPackageManagerChoice)\nconst mockInstallDeclaredPackages = vi.mocked(installDeclaredPackages)\nconst mockInstallNewPackages = vi.mocked(installNewPackages)\n\nconst defaultMocks = {\n projectRoot: {\n directory: '/test/project',\n path: '/test/project/sanity.config.ts',\n type: 'studio' as const,\n },\n}\n\nafterEach(() => {\n vi.clearAllMocks()\n})\n\ndescribe('#install', () => {\n test('help text is correct', async () => {\n const {stdout} = await runCommand('install --help')\n expect(stdout).toMatchInlineSnapshot(`\n \"Installs dependencies for Sanity Studio project\n\n USAGE\n $ sanity install [PACKAGES...]\n\n ARGUMENTS\n [PACKAGES...] Packages to install\n\n DESCRIPTION\n Installs dependencies for Sanity Studio project\n\n EXAMPLES\n $ sanity install\n\n $ sanity install @sanity/vision\n\n $ sanity install some-package another-package\n\n \"\n `)\n })\n\n describe('install declared packages (no arguments)', () => {\n test('installs declared packages with npm', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {\n interactive: true,\n })\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'npm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallNewPackages).not.toHaveBeenCalled()\n })\n\n test('installs declared packages with yarn', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'yarn',\n mostOptimal: 'yarn',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'yarn',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('installs declared packages with pnpm', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'pnpm',\n mostOptimal: 'pnpm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'pnpm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('installs declared packages with bun', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'bun',\n mostOptimal: 'bun',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'bun',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('handles manual package manager selection', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'manual',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'manual',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n })\n\n describe('install specific packages (with arguments)', () => {\n test('installs single package', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['@sanity/vision'], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'npm',\n packages: ['@sanity/vision'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n })\n\n test('installs multiple packages', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'yarn',\n mostOptimal: 'yarn',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['@sanity/vision', 'react-icons', 'lodash'], {\n mocks: defaultMocks,\n })\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'yarn',\n packages: ['@sanity/vision', 'react-icons', 'lodash'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n })\n\n test('installs packages with different package managers', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'pnpm',\n mostOptimal: 'pnpm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n const {error} = await testCommand(Install, ['some-package'], {mocks: defaultMocks})\n\n expect(error).toBeUndefined()\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'pnpm',\n packages: ['some-package'],\n },\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n })\n\n describe('error handling', () => {\n test('handles package manager choice failure', async () => {\n mockGetPackageManagerChoice.mockRejectedValueOnce(\n new Error('Failed to detect package manager'),\n )\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Failed to detect package manager')\n expect(mockInstallDeclaredPackages).not.toHaveBeenCalled()\n expect(mockInstallNewPackages).not.toHaveBeenCalled()\n })\n\n test('handles declared packages installation failure', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockRejectedValueOnce(new Error('Installation failed'))\n\n const {error} = await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Installation failed')\n })\n\n test('handles new packages installation failure', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockRejectedValueOnce(new Error('Package not found'))\n\n const {error} = await testCommand(Install, ['nonexistent-package'], {mocks: defaultMocks})\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Package not found')\n })\n })\n\n describe('integration with project root', () => {\n test('passes correct working directory to functions', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallDeclaredPackages.mockResolvedValueOnce()\n\n await testCommand(Install, [], {mocks: defaultMocks})\n\n expect(mockGetPackageManagerChoice).toHaveBeenCalledWith('/test/project', {\n interactive: true,\n })\n expect(mockInstallDeclaredPackages).toHaveBeenCalledWith(\n '/test/project',\n 'npm',\n expect.objectContaining({\n workDir: '/test/project',\n }),\n )\n })\n\n test('provides output object to install functions', async () => {\n mockGetPackageManagerChoice.mockResolvedValueOnce({\n chosen: 'npm',\n mostOptimal: 'npm',\n })\n mockInstallNewPackages.mockResolvedValueOnce()\n\n await testCommand(Install, ['test-package'], {mocks: defaultMocks})\n\n expect(mockInstallNewPackages).toHaveBeenCalledWith(\n {\n packageManager: 'npm',\n packages: ['test-package'],\n },\n expect.objectContaining({\n output: expect.objectContaining({\n error: expect.any(Function),\n log: expect.any(Function),\n warn: expect.any(Function),\n }),\n workDir: '/test/project',\n }),\n )\n })\n })\n})\n"],"names":["runCommand","testCommand","afterEach","describe","expect","test","vi","installDeclaredPackages","installNewPackages","getPackageManagerChoice","Install","mock","fn","mockGetPackageManagerChoice","mocked","mockInstallDeclaredPackages","mockInstallNewPackages","defaultMocks","projectRoot","directory","path","type","clearAllMocks","stdout","toMatchInlineSnapshot","mockResolvedValueOnce","chosen","mostOptimal","error","mocks","toBeUndefined","toHaveBeenCalledWith","interactive","objectContaining","workDir","not","toHaveBeenCalled","packageManager","packages","mockRejectedValueOnce","Error","toBeDefined","message","toContain","output","any","Function","log","warn"],"mappings":"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"}
@@ -1,15 +1,18 @@
1
1
  import { runCommand } from '@oclif/test';
2
+ import { getCliToken, setConfig } from '@sanity/cli-core';
2
3
  import { mockApi, testCommand } from '@sanity/cli-test';
3
4
  import nock from 'nock';
4
5
  import { afterEach, describe, expect, test, vi } from 'vitest';
5
- import { setConfig } from '../../../../cli-core/src/services/cliUserConfig.js';
6
- import { getCliToken } from '../../../../cli-core/src/services/getCliToken.js';
7
6
  import { AUTH_API_VERSION } from '../../services/auth.js';
8
7
  import { LogoutCommand } from '../logout.js';
9
- vi.mock('../../../../cli-core/src/services/getCliToken.js');
10
- vi.mock('../../../../cli-core/src/services/cliUserConfig.js', ()=>({
8
+ vi.mock('@sanity/cli-core', async ()=>{
9
+ const actual = await vi.importActual('@sanity/cli-core');
10
+ return {
11
+ ...actual,
12
+ getCliToken: vi.fn(),
11
13
  setConfig: vi.fn()
12
- }));
14
+ };
15
+ });
13
16
  const mockedGetCliToken = vi.mocked(getCliToken);
14
17
  const mockedSetConfig = vi.mocked(setConfig);
15
18
  afterEach(()=>{
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/commands/__tests__/logout.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {mockApi, testCommand} from '@sanity/cli-test'\nimport nock from 'nock'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {setConfig} from '../../../../cli-core/src/services/cliUserConfig.js'\nimport {getCliToken} from '../../../../cli-core/src/services/getCliToken.js'\nimport {AUTH_API_VERSION} from '../../services/auth.js'\nimport {LogoutCommand} from '../logout.js'\n\nvi.mock('../../../../cli-core/src/services/getCliToken.js')\nvi.mock('../../../../cli-core/src/services/cliUserConfig.js', () => ({\n setConfig: vi.fn(),\n}))\n\nconst mockedGetCliToken = vi.mocked(getCliToken)\nconst mockedSetConfig = vi.mocked(setConfig)\n\nafterEach(() => {\n vi.clearAllMocks()\n const pending = nock.pendingMocks()\n nock.cleanAll()\n expect(pending, 'pending mocks').toEqual([])\n})\n\ndescribe('#logout', () => {\n test('--help works', async () => {\n const {stdout} = await runCommand(['logout', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Logs out the CLI from the current user session\n\n USAGE\n $ sanity logout\n\n DESCRIPTION\n Logs out the CLI from the current user session\n\n \"\n `)\n })\n\n test('logs out successfully if a token exists', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(200)\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('Logged out successfully')\n expect(mockedSetConfig).toHaveBeenCalledWith('authToken', undefined)\n expect(mockedSetConfig).toHaveBeenCalledWith('telemetryConsent', undefined)\n })\n\n test('logs out successfully when session is expired (401)', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(401, {\n message: 'Unauthorized',\n statusCode: 401,\n })\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('Logged out successfully')\n expect(mockedSetConfig).toHaveBeenCalledWith('authToken', undefined)\n expect(mockedSetConfig).toHaveBeenCalledWith('telemetryConsent', undefined)\n })\n\n test('shows an error if no token exists', async () => {\n mockedGetCliToken.mockResolvedValueOnce('')\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('No login credentials found')\n expect(mockedSetConfig).not.toHaveBeenCalled()\n })\n\n test('throws error on API failure (non-401)', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(500, {message: 'Internal Server Error'})\n\n const {error} = await testCommand(LogoutCommand)\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Failed to logout')\n expect(mockedSetConfig).not.toHaveBeenCalled()\n })\n})\n"],"names":["runCommand","mockApi","testCommand","nock","afterEach","describe","expect","test","vi","setConfig","getCliToken","AUTH_API_VERSION","LogoutCommand","mock","fn","mockedGetCliToken","mocked","mockedSetConfig","clearAllMocks","pending","pendingMocks","cleanAll","toEqual","stdout","toMatchInlineSnapshot","mockResolvedValueOnce","apiVersion","method","uri","reply","toContain","toHaveBeenCalledWith","undefined","message","statusCode","not","toHaveBeenCalled","error","toBeDefined"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,OAAO,EAAEC,WAAW,QAAO,mBAAkB;AACrD,OAAOC,UAAU,OAAM;AACvB,SAAQC,SAAS,EAAEC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,EAAEC,EAAE,QAAO,SAAQ;AAE5D,SAAQC,SAAS,QAAO,qDAAoD;AAC5E,SAAQC,WAAW,QAAO,mDAAkD;AAC5E,SAAQC,gBAAgB,QAAO,yBAAwB;AACvD,SAAQC,aAAa,QAAO,eAAc;AAE1CJ,GAAGK,IAAI,CAAC;AACRL,GAAGK,IAAI,CAAC,sDAAsD,IAAO,CAAA;QACnEJ,WAAWD,GAAGM,EAAE;IAClB,CAAA;AAEA,MAAMC,oBAAoBP,GAAGQ,MAAM,CAACN;AACpC,MAAMO,kBAAkBT,GAAGQ,MAAM,CAACP;AAElCL,UAAU;IACRI,GAAGU,aAAa;IAChB,MAAMC,UAAUhB,KAAKiB,YAAY;IACjCjB,KAAKkB,QAAQ;IACbf,OAAOa,SAAS,iBAAiBG,OAAO,CAAC,EAAE;AAC7C;AAEAjB,SAAS,WAAW;IAClBE,KAAK,gBAAgB;QACnB,MAAM,EAACgB,MAAM,EAAC,GAAG,MAAMvB,WAAW;YAAC;YAAU;SAAS;QAEtDM,OAAOiB,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;IAUtC,CAAC;IACH;IAEAjB,KAAK,2CAA2C;QAC9CQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYf;YACZgB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC;QAET,MAAM,EAACN,MAAM,EAAC,GAAG,MAAMrB,YAAYU;QAEnCN,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBc,oBAAoB,CAAC,aAAaC;QAC1D1B,OAAOW,iBAAiBc,oBAAoB,CAAC,oBAAoBC;IACnE;IAEAzB,KAAK,uDAAuD;QAC1DQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYf;YACZgB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC,KAAK;YACZI,SAAS;YACTC,YAAY;QACd;QAEA,MAAM,EAACX,MAAM,EAAC,GAAG,MAAMrB,YAAYU;QAEnCN,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBc,oBAAoB,CAAC,aAAaC;QAC1D1B,OAAOW,iBAAiBc,oBAAoB,CAAC,oBAAoBC;IACnE;IAEAzB,KAAK,qCAAqC;QACxCQ,kBAAkBU,qBAAqB,CAAC;QAExC,MAAM,EAACF,MAAM,EAAC,GAAG,MAAMrB,YAAYU;QAEnCN,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBkB,GAAG,CAACC,gBAAgB;IAC9C;IAEA7B,KAAK,yCAAyC;QAC5CQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYf;YACZgB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC,KAAK;YAACI,SAAS;QAAuB;QAE/C,MAAM,EAACI,KAAK,EAAC,GAAG,MAAMnC,YAAYU;QAElCN,OAAO+B,OAAOC,WAAW;QACzBhC,OAAO+B,OAAOJ,SAASH,SAAS,CAAC;QACjCxB,OAAOW,iBAAiBkB,GAAG,CAACC,gBAAgB;IAC9C;AACF"}
1
+ {"version":3,"sources":["../../../src/commands/__tests__/logout.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {getCliToken, setConfig} from '@sanity/cli-core'\nimport {mockApi, testCommand} from '@sanity/cli-test'\nimport nock from 'nock'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {AUTH_API_VERSION} from '../../services/auth.js'\nimport {LogoutCommand} from '../logout.js'\n\nvi.mock('@sanity/cli-core', async () => {\n const actual = await vi.importActual<typeof import('@sanity/cli-core')>('@sanity/cli-core')\n return {\n ...actual,\n getCliToken: vi.fn(),\n setConfig: vi.fn(),\n }\n})\n\nconst mockedGetCliToken = vi.mocked(getCliToken)\nconst mockedSetConfig = vi.mocked(setConfig)\n\nafterEach(() => {\n vi.clearAllMocks()\n const pending = nock.pendingMocks()\n nock.cleanAll()\n expect(pending, 'pending mocks').toEqual([])\n})\n\ndescribe('#logout', () => {\n test('--help works', async () => {\n const {stdout} = await runCommand(['logout', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Logs out the CLI from the current user session\n\n USAGE\n $ sanity logout\n\n DESCRIPTION\n Logs out the CLI from the current user session\n\n \"\n `)\n })\n\n test('logs out successfully if a token exists', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(200)\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('Logged out successfully')\n expect(mockedSetConfig).toHaveBeenCalledWith('authToken', undefined)\n expect(mockedSetConfig).toHaveBeenCalledWith('telemetryConsent', undefined)\n })\n\n test('logs out successfully when session is expired (401)', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(401, {\n message: 'Unauthorized',\n statusCode: 401,\n })\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('Logged out successfully')\n expect(mockedSetConfig).toHaveBeenCalledWith('authToken', undefined)\n expect(mockedSetConfig).toHaveBeenCalledWith('telemetryConsent', undefined)\n })\n\n test('shows an error if no token exists', async () => {\n mockedGetCliToken.mockResolvedValueOnce('')\n\n const {stdout} = await testCommand(LogoutCommand)\n\n expect(stdout).toContain('No login credentials found')\n expect(mockedSetConfig).not.toHaveBeenCalled()\n })\n\n test('throws error on API failure (non-401)', async () => {\n mockedGetCliToken.mockResolvedValueOnce('test-token')\n\n mockApi({\n apiVersion: AUTH_API_VERSION,\n method: 'post',\n uri: '/auth/logout',\n }).reply(500, {message: 'Internal Server Error'})\n\n const {error} = await testCommand(LogoutCommand)\n\n expect(error).toBeDefined()\n expect(error?.message).toContain('Failed to logout')\n expect(mockedSetConfig).not.toHaveBeenCalled()\n })\n})\n"],"names":["runCommand","getCliToken","setConfig","mockApi","testCommand","nock","afterEach","describe","expect","test","vi","AUTH_API_VERSION","LogoutCommand","mock","actual","importActual","fn","mockedGetCliToken","mocked","mockedSetConfig","clearAllMocks","pending","pendingMocks","cleanAll","toEqual","stdout","toMatchInlineSnapshot","mockResolvedValueOnce","apiVersion","method","uri","reply","toContain","toHaveBeenCalledWith","undefined","message","statusCode","not","toHaveBeenCalled","error","toBeDefined"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,WAAW,EAAEC,SAAS,QAAO,mBAAkB;AACvD,SAAQC,OAAO,EAAEC,WAAW,QAAO,mBAAkB;AACrD,OAAOC,UAAU,OAAM;AACvB,SAAQC,SAAS,EAAEC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,EAAEC,EAAE,QAAO,SAAQ;AAE5D,SAAQC,gBAAgB,QAAO,yBAAwB;AACvD,SAAQC,aAAa,QAAO,eAAc;AAE1CF,GAAGG,IAAI,CAAC,oBAAoB;IAC1B,MAAMC,SAAS,MAAMJ,GAAGK,YAAY,CAAoC;IACxE,OAAO;QACL,GAAGD,MAAM;QACTb,aAAaS,GAAGM,EAAE;QAClBd,WAAWQ,GAAGM,EAAE;IAClB;AACF;AAEA,MAAMC,oBAAoBP,GAAGQ,MAAM,CAACjB;AACpC,MAAMkB,kBAAkBT,GAAGQ,MAAM,CAAChB;AAElCI,UAAU;IACRI,GAAGU,aAAa;IAChB,MAAMC,UAAUhB,KAAKiB,YAAY;IACjCjB,KAAKkB,QAAQ;IACbf,OAAOa,SAAS,iBAAiBG,OAAO,CAAC,EAAE;AAC7C;AAEAjB,SAAS,WAAW;IAClBE,KAAK,gBAAgB;QACnB,MAAM,EAACgB,MAAM,EAAC,GAAG,MAAMzB,WAAW;YAAC;YAAU;SAAS;QAEtDQ,OAAOiB,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;IAUtC,CAAC;IACH;IAEAjB,KAAK,2CAA2C;QAC9CQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYjB;YACZkB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC;QAET,MAAM,EAACN,MAAM,EAAC,GAAG,MAAMrB,YAAYQ;QAEnCJ,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBc,oBAAoB,CAAC,aAAaC;QAC1D1B,OAAOW,iBAAiBc,oBAAoB,CAAC,oBAAoBC;IACnE;IAEAzB,KAAK,uDAAuD;QAC1DQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYjB;YACZkB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC,KAAK;YACZI,SAAS;YACTC,YAAY;QACd;QAEA,MAAM,EAACX,MAAM,EAAC,GAAG,MAAMrB,YAAYQ;QAEnCJ,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBc,oBAAoB,CAAC,aAAaC;QAC1D1B,OAAOW,iBAAiBc,oBAAoB,CAAC,oBAAoBC;IACnE;IAEAzB,KAAK,qCAAqC;QACxCQ,kBAAkBU,qBAAqB,CAAC;QAExC,MAAM,EAACF,MAAM,EAAC,GAAG,MAAMrB,YAAYQ;QAEnCJ,OAAOiB,QAAQO,SAAS,CAAC;QACzBxB,OAAOW,iBAAiBkB,GAAG,CAACC,gBAAgB;IAC9C;IAEA7B,KAAK,yCAAyC;QAC5CQ,kBAAkBU,qBAAqB,CAAC;QAExCxB,QAAQ;YACNyB,YAAYjB;YACZkB,QAAQ;YACRC,KAAK;QACP,GAAGC,KAAK,CAAC,KAAK;YAACI,SAAS;QAAuB;QAE/C,MAAM,EAACI,KAAK,EAAC,GAAG,MAAMnC,YAAYQ;QAElCJ,OAAO+B,OAAOC,WAAW;QACzBhC,OAAO+B,OAAOJ,SAASH,SAAS,CAAC;QACjCxB,OAAOW,iBAAiBkB,GAAG,CAACC,gBAAgB;IAC9C;AACF"}
@@ -1,28 +1,24 @@
1
1
  import { runCommand } from '@oclif/test';
2
- import { getCliConfig, getStudioConfig } from '@sanity/cli-core';
2
+ import { getStudioConfig } from '@sanity/cli-core';
3
3
  import { testCommand } from '@sanity/cli-test';
4
4
  import open from 'open';
5
5
  import { afterEach, describe, expect, test, vi } from 'vitest';
6
6
  import { ManageCommand } from '../manage.js';
7
- vi.mock('../../../../cli-core/src/config/studio/getStudioConfig.js', async ()=>{
7
+ vi.mock('@sanity/cli-core', async ()=>{
8
+ const actual = await vi.importActual('@sanity/cli-core');
8
9
  return {
10
+ ...actual,
9
11
  getStudioConfig: vi.fn()
10
12
  };
11
13
  });
12
- vi.mock('../../../../cli-core/src/config/findProjectRoot.js', async ()=>{
13
- return {
14
- findProjectRoot: vi.fn().mockResolvedValue({
15
- directory: '/test/path',
16
- root: '/test/path',
17
- type: 'studio'
18
- })
19
- };
20
- });
21
- vi.mock('../../../../cli-core/src/config/cli/getCliConfig.js', async ()=>{
22
- return {
23
- getCliConfig: vi.fn().mockResolvedValue({})
24
- };
25
- });
14
+ const defaultMocks = {
15
+ cliConfig: {},
16
+ projectRoot: {
17
+ directory: '/test/path',
18
+ path: '/test/path/sanity.config.ts',
19
+ type: 'studio'
20
+ }
21
+ };
26
22
  afterEach(()=>{
27
23
  vi.clearAllMocks();
28
24
  });
@@ -45,12 +41,16 @@ describe('#manage', ()=>{
45
41
  `);
46
42
  });
47
43
  test('open link to project management interface if cli config has projectId', async ()=>{
48
- vi.mocked(getCliConfig).mockResolvedValueOnce({
49
- api: {
50
- projectId: 'test-project-id'
44
+ const { stdout } = await testCommand(ManageCommand, [], {
45
+ mocks: {
46
+ ...defaultMocks,
47
+ cliConfig: {
48
+ api: {
49
+ projectId: 'test-project-id'
50
+ }
51
+ }
51
52
  }
52
53
  });
53
- const { stdout } = await testCommand(ManageCommand);
54
54
  expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id');
55
55
  // Mocked in test setup
56
56
  expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id');
@@ -66,7 +66,9 @@ describe('#manage', ()=>{
66
66
  },
67
67
  unstable_sources: []
68
68
  });
69
- const { stdout } = await testCommand(ManageCommand);
69
+ const { stdout } = await testCommand(ManageCommand, [], {
70
+ mocks: defaultMocks
71
+ });
70
72
  expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id');
71
73
  // Mocked in test setup
72
74
  expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id');
@@ -87,15 +89,18 @@ describe('#manage', ()=>{
87
89
  unstable_sources: []
88
90
  }
89
91
  ]);
90
- const { stdout } = await testCommand(ManageCommand);
92
+ const { stdout } = await testCommand(ManageCommand, [], {
93
+ mocks: defaultMocks
94
+ });
91
95
  expect(stdout).toContain('Opening https://www.sanity.io/manage/');
92
96
  // Mocked in test setup
93
97
  expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/');
94
98
  });
95
99
  test('opens root manage page if no projectId is found', async ()=>{
96
- vi.mocked(getCliConfig).mockResolvedValueOnce({});
97
100
  vi.mocked(getStudioConfig).mockResolvedValueOnce({});
98
- const { stdout } = await testCommand(ManageCommand);
101
+ const { stdout } = await testCommand(ManageCommand, [], {
102
+ mocks: defaultMocks
103
+ });
99
104
  expect(stdout).toContain('Opening https://www.sanity.io/manage/');
100
105
  // Mocked in test setup
101
106
  expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/');
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/commands/__tests__/manage.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {getCliConfig, getStudioConfig} from '@sanity/cli-core'\nimport {testCommand} from '@sanity/cli-test'\nimport open from 'open'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {ManageCommand} from '../manage.js'\n\nvi.mock('../../../../cli-core/src/config/studio/getStudioConfig.js', async () => {\n return {\n getStudioConfig: vi.fn(),\n }\n})\n\nvi.mock('../../../../cli-core/src/config/findProjectRoot.js', async () => {\n return {\n findProjectRoot: vi.fn().mockResolvedValue({\n directory: '/test/path',\n root: '/test/path',\n type: 'studio',\n }),\n }\n})\n\nvi.mock('../../../../cli-core/src/config/cli/getCliConfig.js', async () => {\n return {\n getCliConfig: vi.fn().mockResolvedValue({}),\n }\n})\n\nafterEach(() => {\n vi.clearAllMocks()\n})\n\ndescribe('#manage', () => {\n test('--help works', async () => {\n const {stdout} = await runCommand(['manage', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Opens project management interface in your web browser\n\n USAGE\n $ sanity manage\n\n DESCRIPTION\n Opens project management interface in your web browser\n\n \"\n `)\n })\n\n test('open link to project management interface if cli config has projectId', async () => {\n vi.mocked(getCliConfig).mockResolvedValueOnce({\n api: {\n projectId: 'test-project-id',\n },\n })\n\n const {stdout} = await testCommand(ManageCommand)\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id')\n })\n\n test('open link to project management interface if studio config has projectId', async () => {\n vi.mocked(getStudioConfig).mockResolvedValueOnce({\n basePath: 'test-base-path',\n dataset: 'test-dataset',\n name: 'test-name',\n projectId: 'test-project-id',\n schema: {\n types: [],\n },\n unstable_sources: [],\n })\n\n const {stdout} = await testCommand(ManageCommand)\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id')\n })\n\n test('open root link to manage page if studio config is array', async () => {\n vi.mocked(getStudioConfig).mockResolvedValueOnce([\n {\n basePath: 'test-base-path',\n dataset: 'test-dataset',\n name: 'test-name',\n projectId: 'test-project-id',\n schema: {\n _original: {\n types: [],\n },\n },\n title: 'test-title',\n unstable_sources: [],\n },\n ])\n\n const {stdout} = await testCommand(ManageCommand)\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/')\n })\n\n test('opens root manage page if no projectId is found', async () => {\n vi.mocked(getCliConfig).mockResolvedValueOnce({})\n vi.mocked(getStudioConfig).mockResolvedValueOnce({} as never)\n\n const {stdout} = await testCommand(ManageCommand)\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/')\n })\n})\n"],"names":["runCommand","getCliConfig","getStudioConfig","testCommand","open","afterEach","describe","expect","test","vi","ManageCommand","mock","fn","findProjectRoot","mockResolvedValue","directory","root","type","clearAllMocks","stdout","toMatchInlineSnapshot","mocked","mockResolvedValueOnce","api","projectId","toContain","toHaveBeenCalledWith","basePath","dataset","name","schema","types","unstable_sources","_original","title"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,YAAY,EAAEC,eAAe,QAAO,mBAAkB;AAC9D,SAAQC,WAAW,QAAO,mBAAkB;AAC5C,OAAOC,UAAU,OAAM;AACvB,SAAQC,SAAS,EAAEC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,EAAEC,EAAE,QAAO,SAAQ;AAE5D,SAAQC,aAAa,QAAO,eAAc;AAE1CD,GAAGE,IAAI,CAAC,6DAA6D;IACnE,OAAO;QACLT,iBAAiBO,GAAGG,EAAE;IACxB;AACF;AAEAH,GAAGE,IAAI,CAAC,sDAAsD;IAC5D,OAAO;QACLE,iBAAiBJ,GAAGG,EAAE,GAAGE,iBAAiB,CAAC;YACzCC,WAAW;YACXC,MAAM;YACNC,MAAM;QACR;IACF;AACF;AAEAR,GAAGE,IAAI,CAAC,uDAAuD;IAC7D,OAAO;QACLV,cAAcQ,GAAGG,EAAE,GAAGE,iBAAiB,CAAC,CAAC;IAC3C;AACF;AAEAT,UAAU;IACRI,GAAGS,aAAa;AAClB;AAEAZ,SAAS,WAAW;IAClBE,KAAK,gBAAgB;QACnB,MAAM,EAACW,MAAM,EAAC,GAAG,MAAMnB,WAAW;YAAC;YAAU;SAAS;QAEtDO,OAAOY,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;IAUtC,CAAC;IACH;IAEAZ,KAAK,yEAAyE;QAC5EC,GAAGY,MAAM,CAACpB,cAAcqB,qBAAqB,CAAC;YAC5CC,KAAK;gBACHC,WAAW;YACb;QACF;QAEA,MAAM,EAACL,MAAM,EAAC,GAAG,MAAMhB,YAAYO;QAEnCH,OAAOY,QAAQM,SAAS,CAAC;QACzB,uBAAuB;QACvBlB,OAAOH,MAAMsB,oBAAoB,CAAC;IACpC;IAEAlB,KAAK,4EAA4E;QAC/EC,GAAGY,MAAM,CAACnB,iBAAiBoB,qBAAqB,CAAC;YAC/CK,UAAU;YACVC,SAAS;YACTC,MAAM;YACNL,WAAW;YACXM,QAAQ;gBACNC,OAAO,EAAE;YACX;YACAC,kBAAkB,EAAE;QACtB;QAEA,MAAM,EAACb,MAAM,EAAC,GAAG,MAAMhB,YAAYO;QAEnCH,OAAOY,QAAQM,SAAS,CAAC;QACzB,uBAAuB;QACvBlB,OAAOH,MAAMsB,oBAAoB,CAAC;IACpC;IAEAlB,KAAK,2DAA2D;QAC9DC,GAAGY,MAAM,CAACnB,iBAAiBoB,qBAAqB,CAAC;YAC/C;gBACEK,UAAU;gBACVC,SAAS;gBACTC,MAAM;gBACNL,WAAW;gBACXM,QAAQ;oBACNG,WAAW;wBACTF,OAAO,EAAE;oBACX;gBACF;gBACAG,OAAO;gBACPF,kBAAkB,EAAE;YACtB;SACD;QAED,MAAM,EAACb,MAAM,EAAC,GAAG,MAAMhB,YAAYO;QAEnCH,OAAOY,QAAQM,SAAS,CAAC;QACzB,uBAAuB;QACvBlB,OAAOH,MAAMsB,oBAAoB,CAAC;IACpC;IAEAlB,KAAK,mDAAmD;QACtDC,GAAGY,MAAM,CAACpB,cAAcqB,qBAAqB,CAAC,CAAC;QAC/Cb,GAAGY,MAAM,CAACnB,iBAAiBoB,qBAAqB,CAAC,CAAC;QAElD,MAAM,EAACH,MAAM,EAAC,GAAG,MAAMhB,YAAYO;QAEnCH,OAAOY,QAAQM,SAAS,CAAC;QACzB,uBAAuB;QACvBlB,OAAOH,MAAMsB,oBAAoB,CAAC;IACpC;AACF"}
1
+ {"version":3,"sources":["../../../src/commands/__tests__/manage.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {getStudioConfig} from '@sanity/cli-core'\nimport {testCommand} from '@sanity/cli-test'\nimport open from 'open'\nimport {afterEach, describe, expect, test, vi} from 'vitest'\n\nimport {ManageCommand} from '../manage.js'\n\nvi.mock('@sanity/cli-core', async () => {\n const actual = await vi.importActual<typeof import('@sanity/cli-core')>('@sanity/cli-core')\n return {\n ...actual,\n getStudioConfig: vi.fn(),\n }\n})\n\nconst defaultMocks = {\n cliConfig: {},\n projectRoot: {\n directory: '/test/path',\n path: '/test/path/sanity.config.ts',\n type: 'studio' as const,\n },\n}\n\nafterEach(() => {\n vi.clearAllMocks()\n})\n\ndescribe('#manage', () => {\n test('--help works', async () => {\n const {stdout} = await runCommand(['manage', '--help'])\n\n expect(stdout).toMatchInlineSnapshot(`\n \"Opens project management interface in your web browser\n\n USAGE\n $ sanity manage\n\n DESCRIPTION\n Opens project management interface in your web browser\n\n \"\n `)\n })\n\n test('open link to project management interface if cli config has projectId', async () => {\n const {stdout} = await testCommand(ManageCommand, [], {\n mocks: {\n ...defaultMocks,\n cliConfig: {\n api: {\n projectId: 'test-project-id',\n },\n },\n },\n })\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id')\n })\n\n test('open link to project management interface if studio config has projectId', async () => {\n vi.mocked(getStudioConfig).mockResolvedValueOnce({\n basePath: 'test-base-path',\n dataset: 'test-dataset',\n name: 'test-name',\n projectId: 'test-project-id',\n schema: {\n types: [],\n },\n unstable_sources: [],\n })\n\n const {stdout} = await testCommand(ManageCommand, [], {mocks: defaultMocks})\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/project/test-project-id')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/project/test-project-id')\n })\n\n test('open root link to manage page if studio config is array', async () => {\n vi.mocked(getStudioConfig).mockResolvedValueOnce([\n {\n basePath: 'test-base-path',\n dataset: 'test-dataset',\n name: 'test-name',\n projectId: 'test-project-id',\n schema: {\n _original: {\n types: [],\n },\n },\n title: 'test-title',\n unstable_sources: [],\n },\n ])\n\n const {stdout} = await testCommand(ManageCommand, [], {mocks: defaultMocks})\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/')\n })\n\n test('opens root manage page if no projectId is found', async () => {\n vi.mocked(getStudioConfig).mockResolvedValueOnce({} as never)\n\n const {stdout} = await testCommand(ManageCommand, [], {mocks: defaultMocks})\n\n expect(stdout).toContain('Opening https://www.sanity.io/manage/')\n // Mocked in test setup\n expect(open).toHaveBeenCalledWith('https://www.sanity.io/manage/')\n })\n})\n"],"names":["runCommand","getStudioConfig","testCommand","open","afterEach","describe","expect","test","vi","ManageCommand","mock","actual","importActual","fn","defaultMocks","cliConfig","projectRoot","directory","path","type","clearAllMocks","stdout","toMatchInlineSnapshot","mocks","api","projectId","toContain","toHaveBeenCalledWith","mocked","mockResolvedValueOnce","basePath","dataset","name","schema","types","unstable_sources","_original","title"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,eAAe,QAAO,mBAAkB;AAChD,SAAQC,WAAW,QAAO,mBAAkB;AAC5C,OAAOC,UAAU,OAAM;AACvB,SAAQC,SAAS,EAAEC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,EAAEC,EAAE,QAAO,SAAQ;AAE5D,SAAQC,aAAa,QAAO,eAAc;AAE1CD,GAAGE,IAAI,CAAC,oBAAoB;IAC1B,MAAMC,SAAS,MAAMH,GAAGI,YAAY,CAAoC;IACxE,OAAO;QACL,GAAGD,MAAM;QACTV,iBAAiBO,GAAGK,EAAE;IACxB;AACF;AAEA,MAAMC,eAAe;IACnBC,WAAW,CAAC;IACZC,aAAa;QACXC,WAAW;QACXC,MAAM;QACNC,MAAM;IACR;AACF;AAEAf,UAAU;IACRI,GAAGY,aAAa;AAClB;AAEAf,SAAS,WAAW;IAClBE,KAAK,gBAAgB;QACnB,MAAM,EAACc,MAAM,EAAC,GAAG,MAAMrB,WAAW;YAAC;YAAU;SAAS;QAEtDM,OAAOe,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;IAUtC,CAAC;IACH;IAEAf,KAAK,yEAAyE;QAC5E,MAAM,EAACc,MAAM,EAAC,GAAG,MAAMnB,YAAYO,eAAe,EAAE,EAAE;YACpDc,OAAO;gBACL,GAAGT,YAAY;gBACfC,WAAW;oBACTS,KAAK;wBACHC,WAAW;oBACb;gBACF;YACF;QACF;QAEAnB,OAAOe,QAAQK,SAAS,CAAC;QACzB,uBAAuB;QACvBpB,OAAOH,MAAMwB,oBAAoB,CAAC;IACpC;IAEApB,KAAK,4EAA4E;QAC/EC,GAAGoB,MAAM,CAAC3B,iBAAiB4B,qBAAqB,CAAC;YAC/CC,UAAU;YACVC,SAAS;YACTC,MAAM;YACNP,WAAW;YACXQ,QAAQ;gBACNC,OAAO,EAAE;YACX;YACAC,kBAAkB,EAAE;QACtB;QAEA,MAAM,EAACd,MAAM,EAAC,GAAG,MAAMnB,YAAYO,eAAe,EAAE,EAAE;YAACc,OAAOT;QAAY;QAE1ER,OAAOe,QAAQK,SAAS,CAAC;QACzB,uBAAuB;QACvBpB,OAAOH,MAAMwB,oBAAoB,CAAC;IACpC;IAEApB,KAAK,2DAA2D;QAC9DC,GAAGoB,MAAM,CAAC3B,iBAAiB4B,qBAAqB,CAAC;YAC/C;gBACEC,UAAU;gBACVC,SAAS;gBACTC,MAAM;gBACNP,WAAW;gBACXQ,QAAQ;oBACNG,WAAW;wBACTF,OAAO,EAAE;oBACX;gBACF;gBACAG,OAAO;gBACPF,kBAAkB,EAAE;YACtB;SACD;QAED,MAAM,EAACd,MAAM,EAAC,GAAG,MAAMnB,YAAYO,eAAe,EAAE,EAAE;YAACc,OAAOT;QAAY;QAE1ER,OAAOe,QAAQK,SAAS,CAAC;QACzB,uBAAuB;QACvBpB,OAAOH,MAAMwB,oBAAoB,CAAC;IACpC;IAEApB,KAAK,mDAAmD;QACtDC,GAAGoB,MAAM,CAAC3B,iBAAiB4B,qBAAqB,CAAC,CAAC;QAElD,MAAM,EAACR,MAAM,EAAC,GAAG,MAAMnB,YAAYO,eAAe,EAAE,EAAE;YAACc,OAAOT;QAAY;QAE1ER,OAAOe,QAAQK,SAAS,CAAC;QACzB,uBAAuB;QACvBpB,OAAOH,MAAMwB,oBAAoB,CAAC;IACpC;AACF"}
@@ -0,0 +1,119 @@
1
+ import { runCommand } from '@oclif/test';
2
+ import { describe, expect, test } from 'vitest';
3
+ describe('#migration', ()=>{
4
+ test('should print migrations help', async ()=>{
5
+ const { stdout } = await runCommand('migration --help');
6
+ expect(stdout).toMatchInlineSnapshot(`
7
+ "Create a new migration within your project
8
+
9
+ USAGE
10
+ $ sanity migration COMMAND
11
+
12
+ COMMANDS
13
+ migration create Create a new migration within your project
14
+ migration list List available migrations
15
+ migration run Run a migration against a dataset
16
+
17
+ "
18
+ `);
19
+ });
20
+ test('should print migration create help', async ()=>{
21
+ const { stdout } = await runCommand('migration create --help');
22
+ expect(stdout).toMatchInlineSnapshot(`
23
+ "Create a new migration within your project
24
+
25
+ USAGE
26
+ $ sanity migration create [TITLE]
27
+
28
+ ARGUMENTS
29
+ [TITLE] Title of migration
30
+
31
+ DESCRIPTION
32
+ Create a new migration within your project
33
+
34
+ EXAMPLES
35
+ Create a new migration, prompting for title and options
36
+
37
+ $ sanity migration create
38
+
39
+ Create a new migration with the provided title, prompting for options
40
+
41
+ $ sanity migration create "Rename field from location to address"
42
+
43
+ "
44
+ `);
45
+ });
46
+ test('should print migration list help', async ()=>{
47
+ const { stdout } = await runCommand('migration list --help');
48
+ expect(stdout).toMatchInlineSnapshot(`
49
+ "List available migrations
50
+
51
+ USAGE
52
+ $ sanity migration list
53
+
54
+ DESCRIPTION
55
+ List available migrations
56
+
57
+ EXAMPLES
58
+ List all available migrations in the project
59
+
60
+ $ sanity migration list
61
+
62
+ "
63
+ `);
64
+ });
65
+ test('should print migration run help', async ()=>{
66
+ const { stdout } = await runCommand('migration run --help');
67
+ expect(stdout).toMatchInlineSnapshot(String.raw`
68
+ "Run a migration against a dataset
69
+
70
+ USAGE
71
+ $ sanity migration run [ID] [--api-version <value>] [--concurrency
72
+ <value>] [--confirm] [--dataset <value>] [--dry-run] [--from-export <value>]
73
+ [--progress] [--project <value>]
74
+
75
+ ARGUMENTS
76
+ [ID] ID
77
+
78
+ FLAGS
79
+ --api-version=<value> API version to use when migrating. Defaults to
80
+ v2024-01-29.
81
+ --concurrency=<value> [default: 6] How many mutation requests to run in
82
+ parallel. Must be between 1 and 10. Default: 6.
83
+ --[no-]confirm Prompt for confirmation before running the migration
84
+ (default: true). Use --no-confirm to skip.
85
+ --dataset=<value> Dataset to migrate. Defaults to the dataset configured
86
+ in your Sanity CLI config.
87
+ --[no-]dry-run By default the migration runs in dry mode. Use
88
+ --no-dry-run to migrate dataset.
89
+ --from-export=<value> Use a local dataset export as source for migration
90
+ instead of calling the Sanity API. Note: this is only
91
+ supported for dry runs.
92
+ --[no-]progress Display progress during migration (default: true). Use
93
+ --no-progress to hide output.
94
+ --project=<value> Project ID of the dataset to migrate. Defaults to the
95
+ projectId configured in your Sanity CLI config.
96
+
97
+ DESCRIPTION
98
+ Run a migration against a dataset
99
+
100
+ EXAMPLES
101
+ dry run the migration
102
+
103
+ $ sanity migration run <id>
104
+
105
+ execute the migration against a dataset
106
+
107
+ $ sanity migration run <id> --no-dry-run --project xyz --dataset staging
108
+
109
+ execute the migration using a dataset export as the source
110
+
111
+ $ sanity migration run <id> --from-export=production.tar.gz --no-dry-run \
112
+ --project xyz --dataset staging
113
+
114
+ "
115
+ `);
116
+ });
117
+ });
118
+
119
+ //# sourceMappingURL=migration.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../../src/commands/__tests__/migration.test.ts"],"sourcesContent":["import {runCommand} from '@oclif/test'\nimport {describe, expect, test} from 'vitest'\n\ndescribe('#migration', () => {\n test('should print migrations help', async () => {\n const {stdout} = await runCommand('migration --help')\n expect(stdout).toMatchInlineSnapshot(`\n \"Create a new migration within your project\n\n USAGE\n $ sanity migration COMMAND\n\n COMMANDS\n migration create Create a new migration within your project\n migration list List available migrations\n migration run Run a migration against a dataset\n\n \"\n `)\n })\n\n test('should print migration create help', async () => {\n const {stdout} = await runCommand('migration create --help')\n expect(stdout).toMatchInlineSnapshot(`\n \"Create a new migration within your project\n\n USAGE\n $ sanity migration create [TITLE]\n\n ARGUMENTS\n [TITLE] Title of migration\n\n DESCRIPTION\n Create a new migration within your project\n\n EXAMPLES\n Create a new migration, prompting for title and options\n\n $ sanity migration create\n\n Create a new migration with the provided title, prompting for options\n\n $ sanity migration create \"Rename field from location to address\"\n\n \"\n `)\n })\n\n test('should print migration list help', async () => {\n const {stdout} = await runCommand('migration list --help')\n expect(stdout).toMatchInlineSnapshot(`\n \"List available migrations\n\n USAGE\n $ sanity migration list\n\n DESCRIPTION\n List available migrations\n\n EXAMPLES\n List all available migrations in the project\n\n $ sanity migration list\n\n \"\n `)\n })\n\n test('should print migration run help', async () => {\n const {stdout} = await runCommand('migration run --help')\n expect(stdout).toMatchInlineSnapshot(String.raw`\n \"Run a migration against a dataset\n\n USAGE\n $ sanity migration run [ID] [--api-version <value>] [--concurrency\n <value>] [--confirm] [--dataset <value>] [--dry-run] [--from-export <value>]\n [--progress] [--project <value>]\n\n ARGUMENTS\n [ID] ID\n\n FLAGS\n --api-version=<value> API version to use when migrating. Defaults to\n v2024-01-29.\n --concurrency=<value> [default: 6] How many mutation requests to run in\n parallel. Must be between 1 and 10. Default: 6.\n --[no-]confirm Prompt for confirmation before running the migration\n (default: true). Use --no-confirm to skip.\n --dataset=<value> Dataset to migrate. Defaults to the dataset configured\n in your Sanity CLI config.\n --[no-]dry-run By default the migration runs in dry mode. Use\n --no-dry-run to migrate dataset.\n --from-export=<value> Use a local dataset export as source for migration\n instead of calling the Sanity API. Note: this is only\n supported for dry runs.\n --[no-]progress Display progress during migration (default: true). Use\n --no-progress to hide output.\n --project=<value> Project ID of the dataset to migrate. Defaults to the\n projectId configured in your Sanity CLI config.\n\n DESCRIPTION\n Run a migration against a dataset\n\n EXAMPLES\n dry run the migration\n\n $ sanity migration run <id>\n\n execute the migration against a dataset\n\n $ sanity migration run <id> --no-dry-run --project xyz --dataset staging\n\n execute the migration using a dataset export as the source\n\n $ sanity migration run <id> --from-export=production.tar.gz --no-dry-run \\\n --project xyz --dataset staging\n\n \"\n `)\n })\n})\n"],"names":["runCommand","describe","expect","test","stdout","toMatchInlineSnapshot","String","raw"],"mappings":"AAAA,SAAQA,UAAU,QAAO,cAAa;AACtC,SAAQC,QAAQ,EAAEC,MAAM,EAAEC,IAAI,QAAO,SAAQ;AAE7CF,SAAS,cAAc;IACrBE,KAAK,gCAAgC;QACnC,MAAM,EAACC,MAAM,EAAC,GAAG,MAAMJ,WAAW;QAClCE,OAAOE,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;;;IAYtC,CAAC;IACH;IAEAF,KAAK,sCAAsC;QACzC,MAAM,EAACC,MAAM,EAAC,GAAG,MAAMJ,WAAW;QAClCE,OAAOE,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;;;;;;;;;;;;;IAsBtC,CAAC;IACH;IAEAF,KAAK,oCAAoC;QACvC,MAAM,EAACC,MAAM,EAAC,GAAG,MAAMJ,WAAW;QAClCE,OAAOE,QAAQC,qBAAqB,CAAC,CAAC;;;;;;;;;;;;;;;IAetC,CAAC;IACH;IAEAF,KAAK,mCAAmC;QACtC,MAAM,EAACC,MAAM,EAAC,GAAG,MAAMJ,WAAW;QAClCE,OAAOE,QAAQC,qBAAqB,CAACC,OAAOC,GAAG,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;IAgDhD,CAAC;IACH;AACF"}