shipthis 0.1.11 → 0.1.13

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 (190) hide show
  1. package/assets/markdown/ship-failure.md +13 -0
  2. package/assets/markdown/ship-success.md +12 -0
  3. package/dist/{AppleBundleIdDetails-DymjrhOZ.js → AppleBundleIdDetails-DxWVnxa5.js} +4 -4
  4. package/dist/{Command-1YAl_0zS.js → Command-zfJ7qIJI.js} +8 -8
  5. package/dist/{CommandGame--SAa3wEL.js → CommandGame-DVsNreSF.js} +1 -1
  6. package/dist/{Create-DIaSKUpl.js → Create-DdF29mIS.js} +3 -3
  7. package/dist/{Import-BIOsf8AA.js → Import-D8ik724M.js} +4 -4
  8. package/dist/{JobProgress-biiLhigg.js → JobProgress-D1Pe4YJc.js} +10 -7
  9. package/dist/JobStatusTable-D-daiV-I.js +203 -0
  10. package/dist/{ProjectCredentialsTable-Ch8022rs.js → ProjectCredentialsTable-Ch2s5qF1.js} +2 -2
  11. package/dist/{UserCredentialsTable-CeJS3_hd.js → UserCredentialsTable-DzyAHhLB.js} +3 -3
  12. package/dist/{baseAppleCommand-1isaFxCQ.js → baseAppleCommand-BGXyWK-R.js} +1 -1
  13. package/dist/{baseGameAndroidCommand-6vsMpE7a.js → baseGameAndroidCommand-mdFhxanf.js} +2 -2
  14. package/dist/commands/apple/apiKey/create.js +7 -7
  15. package/dist/commands/apple/apiKey/export.js +6 -6
  16. package/dist/commands/apple/apiKey/import.js +6 -6
  17. package/dist/commands/apple/apiKey/status.js +5 -5
  18. package/dist/commands/apple/certificate/create.js +7 -7
  19. package/dist/commands/apple/certificate/export.js +6 -6
  20. package/dist/commands/apple/certificate/import.js +6 -6
  21. package/dist/commands/apple/certificate/status.js +5 -5
  22. package/dist/commands/apple/login.js +2 -2
  23. package/dist/commands/apple/status.js +4 -4
  24. package/dist/commands/dashboard.js +1 -1
  25. package/dist/commands/game/android/apiKey/connect.js +9 -9
  26. package/dist/commands/game/android/apiKey/create.js +10 -10
  27. package/dist/commands/game/android/apiKey/export.js +7 -7
  28. package/dist/commands/game/android/apiKey/import.js +9 -9
  29. package/dist/commands/game/android/apiKey/invite.js +4 -4
  30. package/dist/commands/game/android/apiKey/status.js +7 -7
  31. package/dist/commands/game/android/keyStore/create.js +8 -8
  32. package/dist/commands/game/android/keyStore/export.js +6 -6
  33. package/dist/commands/game/android/keyStore/import.js +9 -9
  34. package/dist/commands/game/android/keyStore/status.js +6 -6
  35. package/dist/commands/game/android/status.js +4 -4
  36. package/dist/commands/game/build/download.js +4 -4
  37. package/dist/commands/game/build/list.js +5 -5
  38. package/dist/commands/game/create.js +2 -2
  39. package/dist/commands/game/details.js +4 -4
  40. package/dist/commands/game/export.js +1 -1
  41. package/dist/commands/game/ios/app/addTester.js +5 -5
  42. package/dist/commands/game/ios/app/create.js +4 -4
  43. package/dist/commands/game/ios/app/status.js +7 -7
  44. package/dist/commands/game/ios/app/sync.js +5 -5
  45. package/dist/commands/game/ios/profile/create.js +7 -7
  46. package/dist/commands/game/ios/profile/export.js +6 -6
  47. package/dist/commands/game/ios/profile/import.js +6 -6
  48. package/dist/commands/game/ios/profile/status.js +6 -6
  49. package/dist/commands/game/ios/status.js +7 -7
  50. package/dist/commands/game/ios/wizard.js +2 -2
  51. package/dist/commands/game/job/list.js +4 -4
  52. package/dist/commands/game/job/status.js +17 -131
  53. package/dist/commands/game/list.js +4 -4
  54. package/dist/commands/game/ship.js +74 -19
  55. package/dist/commands/game/status.js +4 -4
  56. package/dist/commands/game/wizard.js +14 -14
  57. package/dist/commands/internal/fastlane.js +1 -1
  58. package/dist/commands/internal/readme.js +1 -1
  59. package/dist/commands/login.js +2 -2
  60. package/dist/commands/status.js +4 -4
  61. package/dist/{export-BDxGDZdh.js → export-Cin4rLWR.js} +1 -1
  62. package/dist/{import-v54PM_Qg.js → import-CXTv9E84.js} +1 -1
  63. package/dist/{index-BDFKyTPb.js → index-B4v66AKo.js} +1 -1
  64. package/dist/{index-ByOvCs4O.js → index-BVvcTBnj.js} +4 -4
  65. package/dist/{index-m4HTrJ5J.js → index-Cx_2qTdS.js} +7 -7
  66. package/dist/{index-BB7X1Pqp.js → index-Dhx6FAHt.js} +1 -1
  67. package/dist/{index-wyPoxiTc.js → index-Dj-chiHz.js} +2 -2
  68. package/dist/{upload-2naN75Zu.js → upload-DZCIfnwf.js} +1 -1
  69. package/dist/{useAndroidServiceAccountTestResult-BDc7XpKE.js → useAndroidServiceAccountTestResult-L4oozjag.js} +1 -1
  70. package/dist/{useAppleApp-DgE0wEaq.js → useAppleApp-DcSr-q-w.js} +1 -1
  71. package/dist/{useAppleBundleId-BNI8swhC.js → useAppleBundleId-BnJVPVIz.js} +1 -1
  72. package/dist/{useJobWatching-BIG6fnTN.js → useJobWatching-DS0qHqPA.js} +3 -3
  73. package/dist/{useProjectCredentials-B5ZmpIxL.js → useProjectCredentials-CI_AoXmH.js} +3 -3
  74. package/dist/{useWebSocket-Bep1zAVG.js → useWebSocket-ZEZvtpT_.js} +1 -1
  75. package/npm-shrinkwrap.json +2 -2
  76. package/oclif.manifest.json +141 -223
  77. package/package.json +1 -1
  78. package/dist/AppleBundleIdDetails-C0XqjxKJ.js +0 -72
  79. package/dist/AppleBundleIdDetails-CjP5y0cj.js +0 -74
  80. package/dist/AppleBundleIdDetails-CztWY_mT.js +0 -73
  81. package/dist/AppleBundleIdDetails-DKeSAte9.js +0 -73
  82. package/dist/AppleBundleIdDetails-Df30MPFC.js +0 -73
  83. package/dist/AppleBundleIdDetails-Dxo99Sgu.js +0 -72
  84. package/dist/Command-BiB9MqbJ.js +0 -204
  85. package/dist/Command-Cl-JfhTy.js +0 -203
  86. package/dist/Command-D6rWEZRM.js +0 -204
  87. package/dist/Command-Dn0P_KOV.js +0 -205
  88. package/dist/Command-DxmQn3XT.js +0 -204
  89. package/dist/Command-YJJp90ru.js +0 -204
  90. package/dist/CommandGame-C1oTlfdb.js +0 -8
  91. package/dist/CommandGame-CZUx_VQu.js +0 -8
  92. package/dist/CommandGame-DspVLTPZ.js +0 -8
  93. package/dist/CommandGame-cPaTk1wh.js +0 -8
  94. package/dist/CommandGame-k04mHiDl.js +0 -8
  95. package/dist/CommandGame-pI9VXKxi.js +0 -8
  96. package/dist/CreateKeystore-BnNdeDUa.js +0 -57
  97. package/dist/CreateKeystore-BqJdpvsI.js +0 -56
  98. package/dist/CreateKeystore-Cf-nsK_M.js +0 -56
  99. package/dist/CreateKeystore-D8uTRamD.js +0 -56
  100. package/dist/CreateKeystore-Dm0KVh85.js +0 -56
  101. package/dist/CreateKeystore-g1z6DsU5.js +0 -56
  102. package/dist/JobProgress-CPkWVSlH.js +0 -108
  103. package/dist/JobProgress-Dk0UoNah.js +0 -108
  104. package/dist/JobProgress-W0QQR49T.js +0 -108
  105. package/dist/JobProgress-jmGAzvxS.js +0 -108
  106. package/dist/JobStatusTable-BA_q-kgE.js +0 -75
  107. package/dist/JobStatusTable-ByW0bN6c.js +0 -75
  108. package/dist/JobStatusTable-CgaTS7jS.js +0 -75
  109. package/dist/JobStatusTable-DqoppRro.js +0 -75
  110. package/dist/JobStatusTable-q4atKzhu.js +0 -75
  111. package/dist/ProjectCredentialsTable-8kXt7sTS.js +0 -37
  112. package/dist/ProjectCredentialsTable-BIWBAXCh.js +0 -37
  113. package/dist/ProjectCredentialsTable-DRMK_SNw.js +0 -37
  114. package/dist/ProjectCredentialsTable-DfkpvTf8.js +0 -37
  115. package/dist/UserCredentialsTable-DMh8Wpy7.js +0 -82
  116. package/dist/UserCredentialsTable-DgHZJSHG.js +0 -82
  117. package/dist/UserCredentialsTable-TflQvTEP.js +0 -82
  118. package/dist/UserCredentialsTable-ysmM5dlV.js +0 -82
  119. package/dist/baseAppleCommand-B3WQtlx-.js +0 -10
  120. package/dist/baseAppleCommand-B9wyIqdL.js +0 -10
  121. package/dist/baseAppleCommand-D-G4h8zQ.js +0 -10
  122. package/dist/baseAppleCommand-DpasCbje.js +0 -10
  123. package/dist/baseGameAndroidCommand-B-CFhPnE.js +0 -43
  124. package/dist/baseGameAndroidCommand-B3LRG701.js +0 -43
  125. package/dist/baseGameAndroidCommand-C9BuS2Sr.js +0 -43
  126. package/dist/baseGameAndroidCommand-DD0H8iy-.js +0 -43
  127. package/dist/commands/game/android/wizard.js +0 -509
  128. package/dist/export-B_F6vXIK.js +0 -36
  129. package/dist/export-BiLHgSJ9.js +0 -36
  130. package/dist/export-C_lu1FD9.js +0 -36
  131. package/dist/export-rS9o87LD.js +0 -36
  132. package/dist/import-7T3J63j2.js +0 -38
  133. package/dist/import-Brg3zYmT.js +0 -38
  134. package/dist/import-BrlJuE2Z.js +0 -38
  135. package/dist/import-CxNikF1c.js +0 -38
  136. package/dist/import-DPbg8WvS.js +0 -38
  137. package/dist/index-B5XHQfs2.js +0 -122
  138. package/dist/index-B6V7vGOj.js +0 -136
  139. package/dist/index-BL-1G60K.js +0 -135
  140. package/dist/index-BQRxiyqn.js +0 -693
  141. package/dist/index-BQnkBr1Q.js +0 -136
  142. package/dist/index-BX9h2vPV.js +0 -123
  143. package/dist/index-BjGSEqP5.js +0 -135
  144. package/dist/index-BuZmCvZh.js +0 -24
  145. package/dist/index-Bv3x8c78.js +0 -693
  146. package/dist/index-BzffuqPa.js +0 -24
  147. package/dist/index-C9734Cj2.js +0 -693
  148. package/dist/index-CKYExssR.js +0 -136
  149. package/dist/index-CgBgZUkL.js +0 -144
  150. package/dist/index-Cz_KLwWf.js +0 -136
  151. package/dist/index-D6BH5UAM.js +0 -135
  152. package/dist/index-DBrQda8r.js +0 -122
  153. package/dist/index-DE2Hvx2o.js +0 -122
  154. package/dist/index-DOgF4dFK.js +0 -24
  155. package/dist/index-DdABTtYO.js +0 -693
  156. package/dist/index-DgbQBx6x.js +0 -122
  157. package/dist/index-DxHPjZav.js +0 -136
  158. package/dist/index-X__XH_Fd.js +0 -144
  159. package/dist/index-o9Y-84Rj.js +0 -122
  160. package/dist/upload-CMo3hUhl.js +0 -60
  161. package/dist/upload-Cx71802W.js +0 -60
  162. package/dist/upload-DvAE1vDq.js +0 -60
  163. package/dist/upload-LXRr4pMa.js +0 -60
  164. package/dist/useAndroidServiceAccountTestResult-B_ekRewZ.js +0 -52
  165. package/dist/useAndroidServiceAccountTestResult-Ce1x0Eh8.js +0 -52
  166. package/dist/useAndroidServiceAccountTestResult-D_30xIJA.js +0 -52
  167. package/dist/useAndroidServiceAccountTestResult-InDf5WSl.js +0 -52
  168. package/dist/useAppleApp-BEtLQa7n.js +0 -32
  169. package/dist/useAppleApp-CApC0-4Q.js +0 -32
  170. package/dist/useAppleApp-CETIcsJS.js +0 -32
  171. package/dist/useAppleApp-DnSjUfSs.js +0 -32
  172. package/dist/useAppleBundleId-DXbMDRLd.js +0 -64
  173. package/dist/useAppleBundleId-DtLODy3p.js +0 -64
  174. package/dist/useAppleBundleId-SmzY6rkm.js +0 -64
  175. package/dist/useAppleBundleId-gPBzJwQg.js +0 -64
  176. package/dist/useJobWatching-BcBJ5dy1.js +0 -43
  177. package/dist/useJobWatching-Bz1e6xOv.js +0 -43
  178. package/dist/useJobWatching-Cp-CYd90.js +0 -45
  179. package/dist/useJobWatching-D-YzSlK8.js +0 -45
  180. package/dist/useJobWatching-I_A3b36f.js +0 -45
  181. package/dist/useJobWatching-P5oC7mNB.js +0 -45
  182. package/dist/useProjectCredentials-BRffcsO3.js +0 -54
  183. package/dist/useProjectCredentials-CKngz2rd.js +0 -54
  184. package/dist/useProjectCredentials-EapDge1I.js +0 -54
  185. package/dist/useProjectCredentials-vjedBbKl.js +0 -54
  186. package/dist/useWebSocket-CBqsjHbt.js +0 -36
  187. package/dist/useWebSocket-D8PojLtx.js +0 -36
  188. package/dist/useWebSocket-DoImIdTy.js +0 -36
  189. package/dist/useWebSocket-rBLiZsKb.js +0 -36
  190. package/dist/wizard-ChPegnMW.js +0 -133
@@ -1,509 +0,0 @@
1
- import { jsxs, Fragment, jsx } from 'react/jsx-runtime';
2
- import { Text, Box, render } from 'ink';
3
- import { p as getAuthedHeaders, q as API_URL, H as castArrayObjectDates, $ as queryClient, u as getGodotVersion, t as GameEngine, v as createProject, w as DEFAULT_IGNORED_FILES_GLOBS, x as DEFAULT_SHIPPED_FILES_GLOBS, P as Platform, J as JobStatus, X as WEB_URL, E as getProject, C as CredentialsType, Q as getGoogleStatus, B as BaseAuthenticatedCommand, D as DetailsFlags } from '../../../index-DdABTtYO.js';
4
- import React, { useState, useContext, useEffect, useRef } from 'react';
5
- import { c as CommandContext, b as GameContext, d as useBuilds, M as Markdown, q as queryBuilds, G as GameProvider, e as CreateGooglePlayGame, C as Command } from '../../../Command-DxmQn3XT.js';
6
- import Spinner from 'ink-spinner';
7
- import { Alert, TextInput } from '@inkjs/ui';
8
- import axios from 'axios';
9
- import 'crypto-js';
10
- import 'uuid';
11
- import 'luxon';
12
- import 'fs';
13
- import { useQuery, useMutation } from '@tanstack/react-query';
14
- import 'open';
15
- import 'crypto';
16
- import 'readline-sync';
17
- import 'node:readline';
18
- import 'node:path';
19
- import 'node:url';
20
- import 'fast-glob';
21
- import 'yazl';
22
- import 'socket.io-client';
23
- import 'isomorphic-git';
24
- import '@oclif/core';
25
- import 'qrcode';
26
- import 'string-length';
27
- import 'strip-ansi';
28
- import { C as CreateKeystore } from '../../../CreateKeystore-D8uTRamD.js';
29
- import { C as ConnectGoogle } from '../../../index-DBrQda8r.js';
30
- import { C as CreateServiceAccountKey } from '../../../index-BL-1G60K.js';
31
- import { c as cacheKeys, f as fetchKeyTestResult, K as KeyTestStatus, a as KeyTestError } from '../../../useAndroidServiceAccountTestResult-InDf5WSl.js';
32
- import { u as useShip, J as JobProgress } from '../../../JobProgress-Dk0UoNah.js';
33
- import { a as getProjectCredentials } from '../../../index-BDFKyTPb.js';
34
- import { T as Title } from '../../../Title-BCQtayg6.js';
35
- import 'path';
36
- import '@expo/apple-utils/build/index.js';
37
- import 'ini';
38
- import 'deepmerge';
39
- import '../../../index-wyPoxiTc.js';
40
- import 'marked';
41
- import 'marked-terminal';
42
- import '../../../RunWithSpinner-BVXNWGD3.js';
43
- import '../../../useWebSocket-D8PojLtx.js';
44
- import '../../../useProjectCredentials-BRffcsO3.js';
45
- import '../../../ProgressSpinner-6pw1T8Iw.js';
46
- import '../../../git-DREGq-jc.js';
47
- import '../../../useJobWatching-P5oC7mNB.js';
48
-
49
- async function queryJobs({ projectId, ...pageAndSortParams }) {
50
- try {
51
- const headers = getAuthedHeaders();
52
- const url = `${API_URL}/projects/${projectId}/jobs`;
53
- const response = await axios.get(url, { headers, params: pageAndSortParams });
54
- return {
55
- ...response.data,
56
- data: castArrayObjectDates(response.data.data)
57
- };
58
- } catch (error) {
59
- console.warn("queryJobs Error", error);
60
- throw error;
61
- }
62
- }
63
- const useJobs = (props) => {
64
- const queryResult = useQuery({
65
- queryKey: cacheKeys.jobs(props),
66
- queryFn: async () => queryJobs(props)
67
- });
68
- return queryResult;
69
- };
70
-
71
- const useInviteServiceAccount = () => {
72
- return useMutation({
73
- mutationFn: async ({ projectId, developerId }) => {
74
- try {
75
- const headers = getAuthedHeaders();
76
- const { data } = await axios.post(
77
- `${API_URL}/projects/${projectId}/credentials/android/key/invite/`,
78
- { developerId },
79
- {
80
- headers
81
- }
82
- );
83
- return data;
84
- } catch (error) {
85
- console.error("useInviteMutation Error", error);
86
- throw error;
87
- }
88
- },
89
- onSuccess: async (data) => {
90
- const sleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
91
- await sleep(1e3);
92
- queryClient.invalidateQueries({
93
- queryKey: cacheKeys.androidKeyTestResult({ projectId: data.projectId })
94
- });
95
- }
96
- });
97
- };
98
-
99
- const GameInfoForm = ({ gameInfo, onSubmit }) => {
100
- const [activeInput, setActiveInput] = useState("name");
101
- const [error, setError] = useState(null);
102
- const [name, setName] = useState(gameInfo.name);
103
- const [androidPackageName, setAndroidPackageName] = useState(gameInfo?.details?.androidPackageName);
104
- const handleSubmitName = () => {
105
- setError(null);
106
- if (name.length === 0) {
107
- setError("Please enter a name for your game");
108
- return;
109
- }
110
- setActiveInput("androidPackageName");
111
- };
112
- const handleSubmitPackageName = () => {
113
- setError(null);
114
- const packageRegex = /^[a-zA-Z][a-zA-Z0-9_]*(\.[a-zA-Z][a-zA-Z0-9_]*)+$/;
115
- if (!packageRegex.test(`${androidPackageName}`)) {
116
- setError("Please enter a valid package name e.g. com.flappy.souls");
117
- return;
118
- }
119
- onSubmit({
120
- ...gameInfo,
121
- name,
122
- details: {
123
- ...gameInfo.details,
124
- androidPackageName
125
- }
126
- });
127
- };
128
- return /* @__PURE__ */ jsxs(Fragment, { children: [
129
- /* @__PURE__ */ jsx(Text, { bold: true, children: "Please confirm the following information about your game" }),
130
- error && /* @__PURE__ */ jsx(Alert, { variant: "error", children: error }),
131
- /* @__PURE__ */ jsxs(Box, { flexDirection: "column", marginLeft: 1, children: [
132
- /* @__PURE__ */ jsx(
133
- FormTextInput,
134
- {
135
- label: "Game name:",
136
- isDisabled: activeInput !== "name",
137
- defaultValue: name,
138
- placeholder: "Enter the name of your game...",
139
- onChange: setName,
140
- onSubmit: handleSubmitName
141
- }
142
- ),
143
- /* @__PURE__ */ jsx(
144
- FormTextInput,
145
- {
146
- label: "Android package name :",
147
- isDisabled: activeInput !== "androidPackageName",
148
- defaultValue: androidPackageName,
149
- placeholder: "e.g. com.flappy.souls",
150
- onChange: setAndroidPackageName,
151
- onSubmit: handleSubmitPackageName
152
- }
153
- )
154
- ] })
155
- ] });
156
- };
157
-
158
- const getGameInfo = (flagValues, project) => {
159
- const androidPackageName = flagValues.androidPackageName || project?.details?.androidPackageName || "";
160
- const gameInfo = {
161
- name: project?.name || flagValues.name || "",
162
- details: {
163
- ...project?.details,
164
- androidPackageName
165
- }
166
- };
167
- return gameInfo;
168
- };
169
- const CreateGame = (props) => {
170
- const [isLoading, setIsLoading] = useState(true);
171
- const [gameInfo, setGameInfo] = useState(null);
172
- const [showForm, setShowForm] = useState(false);
173
- const { command } = useContext(CommandContext);
174
- const { setGameId, game } = useContext(GameContext);
175
- const handleLoad = async () => {
176
- if (!command) return;
177
- const flagValues = command.getDetailsFlagsValues();
178
- const projectConfig = await command.getProjectConfigSafe();
179
- if (!projectConfig.project) {
180
- setShowForm(true);
181
- setIsLoading(false);
182
- const gameInfo3 = getGameInfo(flagValues);
183
- setGameInfo(gameInfo3);
184
- return;
185
- }
186
- const gameInfo2 = getGameInfo(flagValues, game || undefined);
187
- setGameInfo(gameInfo2);
188
- setShowForm(true);
189
- setIsLoading(false);
190
- };
191
- useEffect(() => {
192
- handleLoad();
193
- }, []);
194
- const handleGameInfoSubmit = async (gameInfo2) => {
195
- if (!command) return;
196
- setShowForm(false);
197
- setIsLoading(true);
198
- const isNew = !(await command.getProjectConfigSafe()).project;
199
- if (!isNew) {
200
- const cmd = command;
201
- await cmd.updateGame(gameInfo2);
202
- return props.onComplete();
203
- }
204
- const { name, details } = gameInfo2;
205
- const projectDetails = {
206
- ...details,
207
- gameEngine: GameEngine.GODOT,
208
- gameEngineVersion: getGodotVersion()
209
- };
210
- const project = await createProject({ name, details: projectDetails });
211
- await command.setProjectConfig({
212
- project,
213
- shippedFilesGlobs: DEFAULT_SHIPPED_FILES_GLOBS,
214
- ignoredFilesGlobs: DEFAULT_IGNORED_FILES_GLOBS
215
- });
216
- setGameId(project.id);
217
- props.onComplete();
218
- };
219
- return /* @__PURE__ */ jsxs(Box, { flexDirection: "column", gap: 1, borderStyle: "single", margin: 1, children: [
220
- isLoading && /* @__PURE__ */ jsx(Spinner, {}),
221
- showForm && gameInfo && /* @__PURE__ */ jsx(GameInfoForm, { gameInfo, onSubmit: handleGameInfoSubmit })
222
- ] });
223
- };
224
-
225
- const FormTextInput = ({ label, labelProps, ...rest }) => /* @__PURE__ */ jsxs(Box, { flexDirection: "row", gap: 1, children: [
226
- /* @__PURE__ */ jsx(Text, { ...labelProps, children: label }),
227
- /* @__PURE__ */ jsx(TextInput, { ...rest })
228
- ] });
229
-
230
- const CreateInitialBuild = (props) => {
231
- const { gameId } = useContext(GameContext);
232
- return /* @__PURE__ */ jsx(Fragment, { children: gameId && /* @__PURE__ */ jsx(CreateForGame, { gameId, ...props }) });
233
- };
234
- const CreateForGame = ({ onComplete, onError, gameId, ...boxProps }) => {
235
- const { command } = useContext(CommandContext);
236
- const { data: buildData, isLoading: isLoadingBuilds } = useBuilds({ projectId: gameId, pageNumber: 0 });
237
- const { data: jobData, isLoading: isLoadingJobs } = useJobs({
238
- projectId: gameId,
239
- pageNumber: 0
240
- });
241
- const prevHasBuild = useRef(false);
242
- const shipMutation = useShip();
243
- const [shipLog, setShipLog] = useState("");
244
- useEffect(() => {
245
- if (isLoadingBuilds || isLoadingJobs) return;
246
- if (!buildData) return;
247
- if (!jobData) return;
248
- if (!command) return;
249
- const hasAndroidBuild = buildData.data.some((build) => build.platform === Platform.ANDROID);
250
- if (!prevHasBuild.current && hasAndroidBuild) return onComplete();
251
- prevHasBuild.current = hasAndroidBuild;
252
- const hasAndroidJob = jobData.data.some((job) => job.type === Platform.ANDROID);
253
- const shouldRun = !hasAndroidBuild && !hasAndroidJob;
254
- if (shouldRun)
255
- shipMutation.mutateAsync({
256
- command,
257
- log: setShipLog
258
- }).catch(onError);
259
- }, [buildData, jobData, command]);
260
- const androidJob = jobData?.data.find(
261
- (job) => job.type === Platform.ANDROID && [JobStatus.PENDING, JobStatus.PROCESSING].includes(job.status)
262
- );
263
- return /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsxs(Box, { flexDirection: "column", gap: 1, ...boxProps, children: [
264
- /* @__PURE__ */ jsxs(Box, { flexDirection: "row", gap: 1, children: [
265
- /* @__PURE__ */ jsx(Text, { children: "Create an initial build..." }),
266
- (isLoadingBuilds || isLoadingJobs || shipMutation.isPending) && /* @__PURE__ */ jsx(Spinner, { type: "dots" })
267
- ] }),
268
- androidJob == null && /* @__PURE__ */ jsx(Text, { children: shipLog }),
269
- androidJob && /* @__PURE__ */ jsx(JobProgress, { job: androidJob, onComplete })
270
- ] }) });
271
- };
272
-
273
- const InviteForm = ({ onSubmit }) => {
274
- const [error, setError] = useState(null);
275
- const [accountId, setAccountId] = useState("");
276
- const handleSubmitAccountId = () => {
277
- setError(null);
278
- const idRegEx = /^\d{10,20}$/;
279
- if (!idRegEx.test(`${accountId}`)) {
280
- setError("Please enter a valid Google Play Account ID (10-20 digits)");
281
- return;
282
- }
283
- return onSubmit(accountId);
284
- };
285
- return /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsxs(Box, { flexDirection: "column", marginLeft: 1, children: [
286
- /* @__PURE__ */ jsx(
287
- FormTextInput,
288
- {
289
- label: "Please enter your Google Play Account ID:",
290
- labelProps: { bold: true },
291
- defaultValue: accountId,
292
- placeholder: "e.g. 8110853839480950872",
293
- onChange: setAccountId,
294
- onSubmit: handleSubmitAccountId
295
- }
296
- ),
297
- error && /* @__PURE__ */ jsx(Alert, { variant: "error", children: error })
298
- ] }) });
299
- };
300
-
301
- const InviteServiceAccount = ({ onComplete, onError, ...boxProps }) => {
302
- const { gameId } = useContext(GameContext);
303
- const inviteMutation = useInviteServiceAccount();
304
- const handleSubmit = async (developerId) => {
305
- try {
306
- if (!gameId) return;
307
- await inviteMutation.mutateAsync({ projectId: gameId, developerId });
308
- onComplete();
309
- } catch (error) {
310
- onError(error);
311
- }
312
- };
313
- const templateVars = {
314
- guideURL: new URL("/docs/guides/google-play-account-id", WEB_URL).toString()
315
- };
316
- return /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsxs(Box, { flexDirection: "column", gap: 1, ...boxProps, children: [
317
- /* @__PURE__ */ jsx(Markdown, { filename: "invite-service-account.md", templateVars }),
318
- /* @__PURE__ */ jsxs(Box, { children: [
319
- inviteMutation.isPending && /* @__PURE__ */ jsx(Spinner, { type: "dots" }),
320
- !inviteMutation.isPending && /* @__PURE__ */ jsx(InviteForm, { onSubmit: handleSubmit })
321
- ] })
322
- ] }) });
323
- };
324
-
325
- var StepStatus = /* @__PURE__ */ ((StepStatus2) => {
326
- StepStatus2["PENDING"] = "PENDING";
327
- StepStatus2["RUNNING"] = "RUNNING";
328
- StepStatus2["SUCCESS"] = "SUCCESS";
329
- StepStatus2["FAILURE"] = "FAILURE";
330
- StepStatus2["WARN"] = "WARN";
331
- return StepStatus2;
332
- })(StepStatus || {});
333
- const Steps = [
334
- "createGame",
335
- "createKeystore",
336
- "connectGoogle",
337
- "createServiceAccount",
338
- "createInitialBuild",
339
- "createGooglePlayGame",
340
- "inviteServiceAccount"
341
- ];
342
- const getStepInitialStatus = (step, statusFlags) => {
343
- const base = {
344
- gameInfo: statusFlags.hasGameName && statusFlags.hasAndroidPackageName,
345
- createGame: statusFlags.hasShipThisProject,
346
- createKeystore: statusFlags.hasAndroidKeystore,
347
- createServiceAccount: statusFlags.hasServiceAccountKey,
348
- createGooglePlayGame: statusFlags.hasGooglePlayGame,
349
- inviteServiceAccount: statusFlags.hasInvitedServiceAccount
350
- };
351
- if (step in base) return base[step] ? "SUCCESS" /* SUCCESS */ : "PENDING" /* PENDING */;
352
- if (step === "connectGoogle") {
353
- if (!statusFlags.hasGoogleConnection && statusFlags.hasServiceAccountKey && statusFlags.hasInvitedServiceAccount)
354
- return "WARN" /* WARN */;
355
- return statusFlags.hasGoogleConnection ? "SUCCESS" /* SUCCESS */ : "PENDING" /* PENDING */;
356
- }
357
- if (step === "createInitialBuild") {
358
- if (!statusFlags.hasInitialBuild && statusFlags.hasGooglePlayGame) return "WARN" /* WARN */;
359
- return statusFlags.hasInitialBuild ? "SUCCESS" /* SUCCESS */ : "PENDING" /* PENDING */;
360
- }
361
- throw new Error(`Unknown step: ${step}`);
362
- };
363
- const getStatusFlags = async (cmd) => {
364
- const projectConfig = await cmd.getProjectConfigSafe();
365
- const projectId = projectConfig.project?.id;
366
- const project = !!projectId && await getProject(projectId);
367
- const hasShipThisProject = !!project;
368
- const hasGameName = project && !!project?.name;
369
- const hasAndroidPackageName = project && !!project?.details?.androidPackageName;
370
- const projectCredentials = hasShipThisProject ? await getProjectCredentials(project.id) : [];
371
- const hasAndroidKeystore = projectCredentials.some(
372
- (cred) => cred.isActive && cred.platform === Platform.ANDROID && cred.type == CredentialsType.CERTIFICATE
373
- );
374
- const googleStatus = await getGoogleStatus();
375
- const hasGoogleConnection = googleStatus.isAuthenticated;
376
- const hasServiceAccountKey = projectCredentials.some(
377
- (cred) => cred.isActive && cred.platform == Platform.ANDROID && cred.type == CredentialsType.KEY
378
- );
379
- const buildsResponse = !!projectId && hasShipThisProject && await queryBuilds({ projectId, pageNumber: 0 });
380
- const hasInitialBuild = !!buildsResponse && buildsResponse.data.length > 0;
381
- const testResult = projectId ? await fetchKeyTestResult({ projectId }) : null;
382
- const hasGooglePlayGame = testResult && testResult?.status === KeyTestStatus.SUCCESS || testResult?.status === KeyTestStatus.ERROR && testResult?.error === KeyTestError.NOT_INVITED;
383
- const hasInvitedServiceAccount = testResult ? testResult?.status === KeyTestStatus.SUCCESS : false;
384
- return {
385
- hasShipThisProject,
386
- hasGameName,
387
- hasAndroidPackageName,
388
- hasAndroidKeystore,
389
- hasGoogleConnection,
390
- hasServiceAccountKey,
391
- hasInitialBuild,
392
- hasGooglePlayGame,
393
- hasInvitedServiceAccount
394
- };
395
- };
396
-
397
- const StepLabels = {
398
- createGame: "Create game in ShipThis",
399
- createKeystore: "Create an Android Keystore",
400
- connectGoogle: "Connect ShipThis with Google",
401
- createServiceAccount: "Create a Service Account & API Key",
402
- createInitialBuild: "Create an initial build",
403
- createGooglePlayGame: "Create the game in Google Play",
404
- inviteServiceAccount: "Invite the Service Account"
405
- };
406
- const StepWithStatus = ({ position, title, status }) => {
407
- const indicator = {
408
- [StepStatus.PENDING]: " ",
409
- // double space
410
- [StepStatus.RUNNING]: /* @__PURE__ */ jsxs(Fragment, { children: [
411
- /* @__PURE__ */ jsx(Spinner, { type: "dots" }),
412
- " "
413
- ] }),
414
- [StepStatus.SUCCESS]: "\u2705",
415
- // this is 2 wide?
416
- [StepStatus.FAILURE]: "\u274C",
417
- // this is 2 wide?
418
- [StepStatus.WARN]: "\u26A0\uFE0F "
419
- // double
420
- }[status];
421
- const isBold = status !== StepStatus.PENDING;
422
- return /* @__PURE__ */ jsxs(Text, { bold: isBold, children: [
423
- /* @__PURE__ */ jsx(Fragment, { children: indicator }),
424
- " ",
425
- position,
426
- ". ",
427
- title
428
- ] });
429
- };
430
- const StepStatusTable = ({ stepStatuses }) => {
431
- return /* @__PURE__ */ jsx(Box, { flexDirection: "column", marginLeft: 1, children: Steps.map((step, index) => {
432
- return /* @__PURE__ */ jsx(StepWithStatus, { position: index + 1, title: StepLabels[step], status: stepStatuses[index] }, step);
433
- }) });
434
- };
435
-
436
- const stepComponentMap = {
437
- createGame: CreateGame,
438
- createKeystore: CreateKeystore,
439
- connectGoogle: ConnectGoogle,
440
- createServiceAccount: CreateServiceAccountKey,
441
- createInitialBuild: CreateInitialBuild,
442
- createGooglePlayGame: CreateGooglePlayGame,
443
- inviteServiceAccount: InviteServiceAccount
444
- };
445
- const ON_COMPLETE_DELAY_MS = 500;
446
- const AndroidWizard = (props) => {
447
- const { command } = React.useContext(CommandContext);
448
- const [currentStep, setCurrentStep] = useState(null);
449
- const [stepStatuses, setStepStatuses] = useState(null);
450
- const [showSuccess, setShowSuccess] = useState(false);
451
- const determineStep = async () => {
452
- if (!command) return;
453
- const statusFlags = await getStatusFlags(command);
454
- const initStatuses = Steps.map((step) => getStepInitialStatus(step, statusFlags));
455
- const firstPending = initStatuses.findIndex((status) => status === StepStatus.PENDING);
456
- const pendingStep = firstPending === -1 ? null : Steps[firstPending];
457
- const withPending = initStatuses.map((status, index) => {
458
- if (index === firstPending) return StepStatus.RUNNING;
459
- return status;
460
- });
461
- setCurrentStep(pendingStep);
462
- setStepStatuses(withPending);
463
- const isAllDone = firstPending === -1;
464
- setShowSuccess(isAllDone);
465
- if (isAllDone) setTimeout(props.onComplete, ON_COMPLETE_DELAY_MS);
466
- };
467
- useEffect(() => {
468
- determineStep().catch(props.onError);
469
- }, [command]);
470
- const handleStepComplete = () => determineStep().catch(props.onError);
471
- const StepInterface = currentStep ? stepComponentMap[currentStep] : null;
472
- const templateVars = {
473
- iosSetupURL: new URL("/docs/ios", WEB_URL).toString(),
474
- docsURL: new URL("/docs", WEB_URL).toString()
475
- };
476
- return /* @__PURE__ */ jsxs(GameProvider, { children: [
477
- /* @__PURE__ */ jsxs(Box, { flexDirection: "column", children: [
478
- /* @__PURE__ */ jsx(Box, { marginBottom: 1, children: /* @__PURE__ */ jsx(Title, { children: "ShipThis Android Wizard" }) }),
479
- stepStatuses && /* @__PURE__ */ jsx(StepStatusTable, { stepStatuses })
480
- ] }),
481
- StepInterface && /* @__PURE__ */ jsx(
482
- StepInterface,
483
- {
484
- onComplete: handleStepComplete,
485
- onError: props.onError,
486
- margin: 1,
487
- borderStyle: "single",
488
- padding: 1
489
- }
490
- ),
491
- showSuccess && /* @__PURE__ */ jsx(Box, { marginTop: 1, children: /* @__PURE__ */ jsx(Markdown, { filename: "android-success.md", templateVars }) })
492
- ] });
493
- };
494
-
495
- class GameAndroidWizard extends BaseAuthenticatedCommand {
496
- static args = {};
497
- static description = "Prototype Android Wizard";
498
- static examples = ["<%= config.bin %> <%= command.id %>"];
499
- static flags = {
500
- ...DetailsFlags
501
- };
502
- async run() {
503
- render(
504
- /* @__PURE__ */ jsx(Command, { command: this, children: /* @__PURE__ */ jsx(AndroidWizard, { onComplete: () => process.exit(0), onError: (e) => this.error(e) }) })
505
- );
506
- }
507
- }
508
-
509
- export { GameAndroidWizard as default };
@@ -1,36 +0,0 @@
1
- import axios from 'axios';
2
- import * as fs from 'fs';
3
- import { o as getAuthedHeaders, p as API_URL } from './index-C9734Cj2.js';
4
-
5
- async function exportCredential({ zipPath, credentialId, projectId }) {
6
- const headers = getAuthedHeaders();
7
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/${credentialId}/export` : `${API_URL}/credentials/${credentialId}/export`;
8
- const { data } = await axios.post(
9
- url,
10
- {},
11
- // no-body
12
- { headers }
13
- );
14
- const downloadUrl = data.url;
15
- return await downloadFile(downloadUrl, zipPath);
16
- }
17
- async function downloadFile(url, destination) {
18
- const response = await axios({
19
- url,
20
- method: "GET",
21
- responseType: "stream"
22
- });
23
- return new Promise((resolve, reject) => {
24
- const file = fs.createWriteStream(destination);
25
- response.data.pipe(file);
26
- file.on("finish", () => {
27
- file.close();
28
- resolve();
29
- });
30
- file.on("error", (err) => {
31
- fs.unlink(destination, () => reject(err));
32
- });
33
- });
34
- }
35
-
36
- export { exportCredential as e };
@@ -1,36 +0,0 @@
1
- import axios from 'axios';
2
- import * as fs from 'fs';
3
- import { p as getAuthedHeaders, q as API_URL } from './index-BQRxiyqn.js';
4
-
5
- async function exportCredential({ zipPath, credentialId, projectId }) {
6
- const headers = getAuthedHeaders();
7
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/${credentialId}/export` : `${API_URL}/credentials/${credentialId}/export`;
8
- const { data } = await axios.post(
9
- url,
10
- {},
11
- // no-body
12
- { headers }
13
- );
14
- const downloadUrl = data.url;
15
- return await downloadFile(downloadUrl, zipPath);
16
- }
17
- async function downloadFile(url, destination) {
18
- const response = await axios({
19
- url,
20
- method: "GET",
21
- responseType: "stream"
22
- });
23
- return new Promise((resolve, reject) => {
24
- const file = fs.createWriteStream(destination);
25
- response.data.pipe(file);
26
- file.on("finish", () => {
27
- file.close();
28
- resolve();
29
- });
30
- file.on("error", (err) => {
31
- fs.unlink(destination, () => reject(err));
32
- });
33
- });
34
- }
35
-
36
- export { exportCredential as e };
@@ -1,36 +0,0 @@
1
- import axios from 'axios';
2
- import * as fs from 'fs';
3
- import { p as getAuthedHeaders, q as API_URL } from './index-Bv3x8c78.js';
4
-
5
- async function exportCredential({ zipPath, credentialId, projectId }) {
6
- const headers = getAuthedHeaders();
7
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/${credentialId}/export` : `${API_URL}/credentials/${credentialId}/export`;
8
- const { data } = await axios.post(
9
- url,
10
- {},
11
- // no-body
12
- { headers }
13
- );
14
- const downloadUrl = data.url;
15
- return await downloadFile(downloadUrl, zipPath);
16
- }
17
- async function downloadFile(url, destination) {
18
- const response = await axios({
19
- url,
20
- method: "GET",
21
- responseType: "stream"
22
- });
23
- return new Promise((resolve, reject) => {
24
- const file = fs.createWriteStream(destination);
25
- response.data.pipe(file);
26
- file.on("finish", () => {
27
- file.close();
28
- resolve();
29
- });
30
- file.on("error", (err) => {
31
- fs.unlink(destination, () => reject(err));
32
- });
33
- });
34
- }
35
-
36
- export { exportCredential as e };
@@ -1,36 +0,0 @@
1
- import axios from 'axios';
2
- import * as fs from 'fs';
3
- import { p as getAuthedHeaders, q as API_URL } from './index-BB7X1Pqp.js';
4
-
5
- async function exportCredential({ zipPath, credentialId, projectId }) {
6
- const headers = getAuthedHeaders();
7
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/${credentialId}/export` : `${API_URL}/credentials/${credentialId}/export`;
8
- const { data } = await axios.post(
9
- url,
10
- {},
11
- // no-body
12
- { headers }
13
- );
14
- const downloadUrl = data.url;
15
- return await downloadFile(downloadUrl, zipPath);
16
- }
17
- async function downloadFile(url, destination) {
18
- const response = await axios({
19
- url,
20
- method: "GET",
21
- responseType: "stream"
22
- });
23
- return new Promise((resolve, reject) => {
24
- const file = fs.createWriteStream(destination);
25
- response.data.pipe(file);
26
- file.on("finish", () => {
27
- file.close();
28
- resolve();
29
- });
30
- file.on("error", (err) => {
31
- fs.unlink(destination, () => reject(err));
32
- });
33
- });
34
- }
35
-
36
- export { exportCredential as e };
@@ -1,38 +0,0 @@
1
- import axios from 'axios';
2
- import { promises } from 'fs';
3
- import { p as getAuthedHeaders, q as API_URL } from './index-BB7X1Pqp.js';
4
-
5
- async function getNewImportTicket(projectId) {
6
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/import/url` : `${API_URL}/credentials/import/url`;
7
- const headers = getAuthedHeaders();
8
- const { data: importInfo } = await axios({
9
- method: "post",
10
- url,
11
- headers
12
- });
13
- return importInfo;
14
- }
15
- async function importCredential({ projectId, zipPath, type, platform }) {
16
- const importTicket = await getNewImportTicket(projectId);
17
- const zipBuffer = await promises.readFile(zipPath);
18
- await axios.put(importTicket.url, zipBuffer, {
19
- headers: {
20
- "Content-length": zipBuffer.length,
21
- "Content-Type": "application/zip"
22
- }
23
- });
24
- const headers = getAuthedHeaders();
25
- const url = projectId ? `${API_URL}/projects/${projectId}/credentials/import` : `${API_URL}/credentials/import`;
26
- return await axios({
27
- method: "post",
28
- url,
29
- headers,
30
- data: {
31
- uuid: importTicket.uuid,
32
- type,
33
- platform
34
- }
35
- });
36
- }
37
-
38
- export { importCredential as i };