shipthis 0.1.3 → 0.1.4

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 (47) hide show
  1. package/dist/AppleBundleIdDetails-Dxo99Sgu.js +72 -0
  2. package/dist/Command-1YAl_0zS.js +204 -0
  3. package/dist/CommandGame-CZUx_VQu.js +8 -0
  4. package/dist/CreateKeystore-BqJdpvsI.js +56 -0
  5. package/dist/commands/apple/apiKey/create.js +1 -1
  6. package/dist/commands/apple/apiKey/export.js +1 -1
  7. package/dist/commands/apple/apiKey/import.js +1 -1
  8. package/dist/commands/apple/apiKey/status.js +1 -1
  9. package/dist/commands/apple/certificate/create.js +1 -1
  10. package/dist/commands/apple/certificate/export.js +1 -1
  11. package/dist/commands/apple/certificate/import.js +1 -1
  12. package/dist/commands/apple/certificate/status.js +1 -1
  13. package/dist/commands/apple/status.js +1 -1
  14. package/dist/commands/game/android/apiKey/connect.js +3 -3
  15. package/dist/commands/game/android/apiKey/create.js +3 -3
  16. package/dist/commands/game/android/apiKey/export.js +1 -1
  17. package/dist/commands/game/android/apiKey/import.js +1 -1
  18. package/dist/commands/game/android/apiKey/status.js +1 -1
  19. package/dist/commands/game/android/keyStore/create.js +3 -3
  20. package/dist/commands/game/android/keyStore/export.js +1 -1
  21. package/dist/commands/game/android/keyStore/import.js +1 -1
  22. package/dist/commands/game/android/keyStore/status.js +1 -1
  23. package/dist/commands/game/android/status.js +1 -1
  24. package/dist/commands/game/android/wizard.js +5 -5
  25. package/dist/commands/game/build/download.js +1 -1
  26. package/dist/commands/game/build/list.js +2 -2
  27. package/dist/commands/game/details.js +1 -1
  28. package/dist/commands/game/ios/app/addTester.js +1 -1
  29. package/dist/commands/game/ios/app/create.js +1 -1
  30. package/dist/commands/game/ios/app/status.js +2 -2
  31. package/dist/commands/game/ios/app/sync.js +1 -1
  32. package/dist/commands/game/ios/profile/create.js +1 -1
  33. package/dist/commands/game/ios/profile/export.js +1 -1
  34. package/dist/commands/game/ios/profile/import.js +1 -1
  35. package/dist/commands/game/ios/profile/status.js +1 -1
  36. package/dist/commands/game/ios/status.js +2 -2
  37. package/dist/commands/game/job/list.js +1 -1
  38. package/dist/commands/game/job/status.js +2 -2
  39. package/dist/commands/game/list.js +1 -1
  40. package/dist/commands/game/status.js +1 -1
  41. package/dist/commands/status.js +1 -1
  42. package/dist/index-DE2Hvx2o.js +122 -0
  43. package/dist/index-X__XH_Fd.js +144 -0
  44. package/dist/useJobWatching-BcBJ5dy1.js +43 -0
  45. package/npm-shrinkwrap.json +2 -2
  46. package/oclif.manifest.json +219 -219
  47. package/package.json +1 -1
@@ -2,7 +2,7 @@ import { jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
6
6
  import { c as BaseGameCommand, i as BetaGroup } from '../../../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import 'axios';
@@ -2,7 +2,7 @@ import { jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
6
6
  import { c as BaseGameCommand, d as getGodotAppleBundleIdentifier, e as BundleId, f as App } from '../../../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import 'axios';
@@ -2,7 +2,7 @@ import { jsxs, jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
6
6
  import { c as BaseGameCommand } from '../../../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import 'axios';
@@ -26,7 +26,7 @@ import { N as NextSteps } from '../../../../NextSteps-CK9zHOCt.js';
26
26
  import 'qrcode';
27
27
  import 'string-length';
28
28
  import 'strip-ansi';
29
- import { A as AppleAppDetails, a as AppleBundleIdDetails } from '../../../../AppleBundleIdDetails-C0XqjxKJ.js';
29
+ import { A as AppleAppDetails, a as AppleBundleIdDetails } from '../../../../AppleBundleIdDetails-Dxo99Sgu.js';
30
30
  import '../../../../index-B6V7vGOj.js';
31
31
  import '../../../../useAndroidServiceAccountTestResult-D_30xIJA.js';
32
32
  import 'marked';
@@ -2,7 +2,7 @@ import { jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
6
6
  import { c as BaseGameCommand, h as CapabilityTypeOption } from '../../../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import 'axios';
@@ -3,7 +3,7 @@ import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import axios from 'axios';
5
5
  import 'react';
6
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
6
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
7
7
  import { c as BaseGameCommand, P as Platform, C as CredentialsType, l as Certificate, m as CertificateType, n as Profile, o as ProfileType } from '../../../../index-BQRxiyqn.js';
8
8
  import 'ink-spinner';
9
9
  import 'crypto-js';
@@ -5,7 +5,7 @@ import * as fs from 'fs';
5
5
  import { c as BaseGameCommand, P as Platform, C as CredentialsType } from '../../../../index-BQRxiyqn.js';
6
6
  import { a as getProjectCredentials } from '../../../../index-BuZmCvZh.js';
7
7
  import 'react';
8
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
8
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
9
9
  import 'ink-spinner';
10
10
  import 'axios';
11
11
  import 'crypto-js';
@@ -5,7 +5,7 @@ import * as fs from 'fs';
5
5
  import { c as BaseGameCommand, P as Platform, C as CredentialsType } from '../../../../index-BQRxiyqn.js';
6
6
  import { a as getProjectCredentials } from '../../../../index-BuZmCvZh.js';
7
7
  import 'react';
8
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
8
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
9
9
  import 'ink-spinner';
10
10
  import 'axios';
11
11
  import 'crypto-js';
@@ -2,7 +2,7 @@ import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
2
2
  import { Box, Text, render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../../Command-1YAl_0zS.js';
6
6
  import { b as getShortDate, n as Profile, o as ProfileType, C as CredentialsType, P as Platform, c as BaseGameCommand } from '../../../../index-BQRxiyqn.js';
7
7
  import Spinner from 'ink-spinner';
8
8
  import 'axios';
@@ -2,7 +2,7 @@ import { jsxs, jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../../Command-1YAl_0zS.js';
6
6
  import { c as BaseGameCommand, k as getProjectPlatformProgress, P as Platform, b as getShortDate } from '../../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import '@inkjs/ui';
@@ -15,7 +15,7 @@ import 'qrcode';
15
15
  import { S as StatusTable } from '../../../StatusTable-Dm5St4g-.js';
16
16
  import 'string-length';
17
17
  import 'strip-ansi';
18
- import { A as AppleAppDetails, a as AppleBundleIdDetails } from '../../../AppleBundleIdDetails-C0XqjxKJ.js';
18
+ import { A as AppleAppDetails, a as AppleBundleIdDetails } from '../../../AppleBundleIdDetails-Dxo99Sgu.js';
19
19
  import 'luxon';
20
20
  import 'uuid';
21
21
  import 'fast-glob';
@@ -3,7 +3,7 @@ import { render, Box, Text } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import { c as BaseGameCommand, F as getProjectJobs } from '../../../index-BQRxiyqn.js';
5
5
  import 'react';
6
- import { g as getJobSummary, C as Command } from '../../../Command-Cl-JfhTy.js';
6
+ import { g as getJobSummary, C as Command } from '../../../Command-1YAl_0zS.js';
7
7
  import 'ink-spinner';
8
8
  import '@inkjs/ui';
9
9
  import 'axios';
@@ -3,7 +3,7 @@ import { Args, Flags } from '@oclif/core';
3
3
  import { measureElement, Box, Text, render } from 'ink';
4
4
  import { p as getAuthedHeaders, q as API_URL, J as castArrayObjectDates, O as castObjectDates, a3 as getShortTime, K as JobStatus, c as BaseGameCommand, a4 as getJob } from '../../../index-BQRxiyqn.js';
5
5
  import { useState, useEffect, useRef } from 'react';
6
- import { g as getJobSummary, c as getBuildSummary, C as Command } from '../../../Command-Cl-JfhTy.js';
6
+ import { g as getJobSummary, c as getBuildSummary, C as Command } from '../../../Command-1YAl_0zS.js';
7
7
  import Spinner from 'ink-spinner';
8
8
  import '@inkjs/ui';
9
9
  import axios from 'axios';
@@ -30,7 +30,7 @@ import 'crypto-js';
30
30
  import { c as cacheKeys } from '../../../useAndroidServiceAccountTestResult-D_30xIJA.js';
31
31
  import { u as useWebSocket } from '../../../useWebSocket-DoImIdTy.js';
32
32
  import { T as Title } from '../../../Title-BCQtayg6.js';
33
- import { u as useJobWatching } from '../../../useJobWatching-Bz1e6xOv.js';
33
+ import { u as useJobWatching } from '../../../useJobWatching-BcBJ5dy1.js';
34
34
  import { a as StatusRow, b as StatusRowLabel } from '../../../StatusTable-Dm5St4g-.js';
35
35
  import 'path';
36
36
  import '@expo/apple-utils/build/index.js';
@@ -3,7 +3,7 @@ import { render, Text, Box } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import { B as BaseAuthenticatedCommand, g as getProjects, b as getShortDate } from '../../index-BQRxiyqn.js';
5
5
  import 'react';
6
- import { C as Command } from '../../Command-Cl-JfhTy.js';
6
+ import { C as Command } from '../../Command-1YAl_0zS.js';
7
7
  import 'ink-spinner';
8
8
  import '@inkjs/ui';
9
9
  import 'axios';
@@ -2,7 +2,7 @@ import { jsxs, jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { Flags } from '@oclif/core';
4
4
  import 'react';
5
- import { C as Command } from '../../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../../Command-1YAl_0zS.js';
6
6
  import { B as BaseAuthenticatedCommand, H as getProject, P as Platform, k as getProjectPlatformProgress, b as getShortDate } from '../../index-BQRxiyqn.js';
7
7
  import 'ink-spinner';
8
8
  import '@inkjs/ui';
@@ -2,7 +2,7 @@ import { jsxs, jsx } from 'react/jsx-runtime';
2
2
  import { render } from 'ink';
3
3
  import { X as BaseCommand, j as isCWDGodotGame } from '../index-BQRxiyqn.js';
4
4
  import 'react';
5
- import { C as Command } from '../Command-Cl-JfhTy.js';
5
+ import { C as Command } from '../Command-1YAl_0zS.js';
6
6
  import 'ink-spinner';
7
7
  import 'axios';
8
8
  import 'crypto-js';
@@ -0,0 +1,122 @@
1
+ import { jsx, Fragment, jsxs } from 'react/jsx-runtime';
2
+ import { Text, useInput, Box } from 'ink';
3
+ import open from 'open';
4
+ import { useState, useEffect, useContext } from 'react';
5
+ import { S as getGoogleStatus, a1 as getShortAuthRequiredUrl, a2 as getGoogleAuthUrl, Z as WEB_URL } from './index-BQRxiyqn.js';
6
+ import 'crypto';
7
+ import 'fs';
8
+ import 'readline-sync';
9
+ import 'node:readline';
10
+ import 'node:path';
11
+ import 'node:url';
12
+ import 'axios';
13
+ import { useQuery } from '@tanstack/react-query';
14
+ import 'crypto-js';
15
+ import 'uuid';
16
+ import 'luxon';
17
+ import 'fast-glob';
18
+ import 'yazl';
19
+ import 'socket.io-client';
20
+ import { u as useWebSocket } from './useWebSocket-DoImIdTy.js';
21
+ import { c as cacheKeys } from './useAndroidServiceAccountTestResult-D_30xIJA.js';
22
+ import 'isomorphic-git';
23
+ import '@oclif/core';
24
+ import { a as GameContext, M as Markdown } from './Command-1YAl_0zS.js';
25
+ import 'ink-spinner';
26
+ import '@inkjs/ui';
27
+ import qrcode from 'qrcode';
28
+ import 'string-length';
29
+ import 'strip-ansi';
30
+
31
+ const useGoogleStatus = () => {
32
+ return useQuery({
33
+ queryKey: cacheKeys.googleStatus(),
34
+ queryFn: getGoogleStatus
35
+ });
36
+ };
37
+
38
+ function useGoogleStatusWatching({
39
+ projectId,
40
+ isWatching,
41
+ onGoogleStatusUpdate
42
+ }) {
43
+ const [wsGoogleStatus, setWsGoogleStatus] = useState(null);
44
+ const listener = {
45
+ getPattern: () => `project.${projectId}:google-status`,
46
+ eventHandler: async (pattern, data2) => {
47
+ setWsGoogleStatus(data2);
48
+ if (onGoogleStatusUpdate) onGoogleStatusUpdate(data2);
49
+ }
50
+ };
51
+ useWebSocket([listener] );
52
+ const { isLoading, data: googleStatus } = useGoogleStatus();
53
+ useEffect(() => {
54
+ setWsGoogleStatus(null);
55
+ }, [projectId, isWatching, googleStatus]);
56
+ const fetchedGoogleStatus = googleStatus ? googleStatus : null;
57
+ const data = wsGoogleStatus ? wsGoogleStatus : fetchedGoogleStatus;
58
+ return {
59
+ isLoading,
60
+ data
61
+ };
62
+ }
63
+
64
+ const QRCodeTerminal = ({ url }) => {
65
+ const [code, setCode] = useState(null);
66
+ const handleLoad = async () => {
67
+ const codeString = await qrcode.toString(url, { type: "terminal", errorCorrectionLevel: "L", small: true });
68
+ setCode(codeString);
69
+ };
70
+ useEffect(() => {
71
+ handleLoad();
72
+ }, []);
73
+ return /* @__PURE__ */ jsx(Fragment, { children: code && /* @__PURE__ */ jsx(Text, { children: code }) });
74
+ };
75
+
76
+ async function getConnectUrl(gameId, helpPage) {
77
+ const helpPagePath = `/docs/android?gameId=${gameId}#2-connect-shipthis-with-google`;
78
+ const url = helpPage ? await getShortAuthRequiredUrl(helpPagePath) : await getGoogleAuthUrl(gameId);
79
+ return url;
80
+ }
81
+ const GoogleAuthQRCode = ({ gameId, helpPage }) => {
82
+ const [url, setUrl] = useState(null);
83
+ const handleLoad = async () => {
84
+ const url2 = await getConnectUrl(gameId, helpPage);
85
+ setUrl(url2);
86
+ };
87
+ useEffect(() => {
88
+ handleLoad();
89
+ }, []);
90
+ return /* @__PURE__ */ jsx(Fragment, { children: url && /* @__PURE__ */ jsx(QRCodeTerminal, { url }) });
91
+ };
92
+
93
+ const ConnectGoogle = (props) => {
94
+ const { gameId } = useContext(GameContext);
95
+ return /* @__PURE__ */ jsx(Fragment, { children: gameId && /* @__PURE__ */ jsx(ConnectForGame, { gameId, ...props }) });
96
+ };
97
+ const ConnectForGame = ({ onComplete, onError, helpPage, gameId, ...boxProps }) => {
98
+ useGoogleStatusWatching({
99
+ projectId: gameId,
100
+ isWatching: true,
101
+ onGoogleStatusUpdate: (status) => {
102
+ if (status.isAuthenticated) return onComplete();
103
+ }
104
+ });
105
+ useInput(async (input) => {
106
+ if (!gameId) return;
107
+ if (input !== "d") return;
108
+ const url = await getConnectUrl(gameId, true);
109
+ await open(url);
110
+ });
111
+ const templateVars = {
112
+ privacyURL: new URL("/privacy", WEB_URL).toString()
113
+ };
114
+ return /* @__PURE__ */ jsxs(Box, { flexDirection: "column", gap: 1, ...boxProps, children: [
115
+ /* @__PURE__ */ jsx(Markdown, { filename: "privacy-notification.md", templateVars }),
116
+ /* @__PURE__ */ jsx(Text, { children: "Scan the QR code below to connect your Google account to ShipThis:" }),
117
+ gameId && /* @__PURE__ */ jsx(GoogleAuthQRCode, { gameId, helpPage: !!helpPage }),
118
+ /* @__PURE__ */ jsx(Text, { children: "Or press D to sign-in using your browser" })
119
+ ] });
120
+ };
121
+
122
+ export { ConnectGoogle as C };
@@ -0,0 +1,144 @@
1
+ import { jsx, Fragment, jsxs } from 'react/jsx-runtime';
2
+ import { Box, Text } from 'ink';
3
+ import { useState, useRef, useEffect, useContext } from 'react';
4
+ import Spinner from 'ink-spinner';
5
+ import { a as GameContext } from './Command-1YAl_0zS.js';
6
+ import { p as getAuthedHeaders, q as API_URL, O as castObjectDates, P as Platform, C as CredentialsType, S as getGoogleStatus } from './index-BQRxiyqn.js';
7
+ import axios from 'axios';
8
+ import 'crypto-js';
9
+ import 'uuid';
10
+ import 'luxon';
11
+ import 'fs';
12
+ import { ProgressBar } from '@inkjs/ui';
13
+ import { useQuery, useQueryClient } 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 { c as cacheKeys } from './useAndroidServiceAccountTestResult-D_30xIJA.js';
21
+ import 'fast-glob';
22
+ import 'yazl';
23
+ import 'socket.io-client';
24
+ import 'isomorphic-git';
25
+ import '@oclif/core';
26
+ import { u as useWebSocket } from './useWebSocket-DoImIdTy.js';
27
+ import { u as useProjectCredentials } from './useProjectCredentials-B5ZmpIxL.js';
28
+ import 'qrcode';
29
+ import 'string-length';
30
+ import 'strip-ansi';
31
+
32
+ async function fetchStatus({ projectId }) {
33
+ try {
34
+ if (!projectId) throw new Error("projectId is required");
35
+ const headers = getAuthedHeaders();
36
+ const url = `${API_URL}/projects/${projectId}/credentials/android/key/status/`;
37
+ const response = await axios.get(url, { headers });
38
+ return castObjectDates(response.data);
39
+ } catch (error) {
40
+ console.warn("fetchStatus Error", error);
41
+ throw error;
42
+ }
43
+ }
44
+ const useAndroidServiceAccountSetupStatus = (props) => {
45
+ return useQuery({
46
+ queryKey: cacheKeys.androidSetupStatus(props),
47
+ queryFn: () => fetchStatus(props),
48
+ // Status changes frequently, so we want to keep it fresh
49
+ refetchInterval: 1e3 * 5,
50
+ staleTime: 1e3 * 5
51
+ });
52
+ };
53
+
54
+ const ERR_NOT_AUTHENTICATED = "You must be connected to Google to create a Service Account Key";
55
+ const useHasServiceAccountKey = (projectId) => {
56
+ const { data, isSuccess } = useProjectCredentials({ projectId, platform: Platform.ANDROID });
57
+ return isSuccess && data.data.some((cred) => cred.isActive && cred.platform === Platform.ANDROID && cred.type == CredentialsType.KEY);
58
+ };
59
+ const useAndroidServiceAccount = ({ projectId, onError, onComplete }) => {
60
+ const queryClient = useQueryClient();
61
+ const [isStarting, setIsStarting] = useState(false);
62
+ const hasServiceAccountKey = useHasServiceAccountKey(projectId);
63
+ const listener = {
64
+ getPattern: () => `project.${projectId}:android-setup-status`,
65
+ eventHandler: async (pattern, data) => {
66
+ const key = cacheKeys.androidSetupStatus({ projectId });
67
+ queryClient.setQueryData(key, () => data);
68
+ }
69
+ };
70
+ useWebSocket([listener]);
71
+ const { data: setupStatus } = useAndroidServiceAccountSetupStatus({ projectId });
72
+ const prevSetupStatusRef = useRef("unknown");
73
+ useEffect(() => {
74
+ if (["running", "queued"].includes(prevSetupStatusRef.current)) {
75
+ if (setupStatus?.status === "complete") onComplete();
76
+ if (setupStatus?.status === "error") onError(new Error(setupStatus.errorMessage));
77
+ }
78
+ prevSetupStatusRef.current = setupStatus?.status || "unknown";
79
+ }, [setupStatus]);
80
+ const handleStart = async () => {
81
+ try {
82
+ setIsStarting(true);
83
+ const currentStatus = await getGoogleStatus();
84
+ if (!currentStatus.isAuthenticated) throw new Error(ERR_NOT_AUTHENTICATED);
85
+ const headers = getAuthedHeaders();
86
+ const androidKeyApiBase = `${API_URL}/projects/${projectId}/credentials/android/key`;
87
+ const startUrl = `${androidKeyApiBase}/setup/`;
88
+ const { data: updatedStatus } = await axios.post(startUrl, {}, { headers });
89
+ queryClient.invalidateQueries({
90
+ queryKey: cacheKeys.projectCredentials({ projectId, pageNumber: 0 })
91
+ });
92
+ await queryClient.setQueryData(cacheKeys.androidSetupStatus({ projectId }), (_) => updatedStatus);
93
+ setIsStarting(false);
94
+ return true;
95
+ } catch (error) {
96
+ setIsStarting(false);
97
+ console.warn("useAndroidServiceAccount.handleStart Error", error);
98
+ onError(error);
99
+ return false;
100
+ }
101
+ };
102
+ const isCreating = isStarting || setupStatus?.status === "queued" || setupStatus?.status === "running";
103
+ return {
104
+ handleStart,
105
+ setupStatus,
106
+ isCreating,
107
+ hasServiceAccountKey
108
+ };
109
+ };
110
+
111
+ const ProgressSpinner = ({ progress, label, spinnerType, labelProps, boxProps }) => /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsx(Box, { flexDirection: "column", gap: 1, ...boxProps, children: /* @__PURE__ */ jsxs(Box, { flexDirection: "row", gap: 1, children: [
112
+ label && label != "" && /* @__PURE__ */ jsx(Text, { ...labelProps, children: label }),
113
+ /* @__PURE__ */ jsx(ProgressBar, { value: progress || 0 }),
114
+ /* @__PURE__ */ jsxs(Text, { children: [
115
+ Math.floor(progress || 0),
116
+ "%"
117
+ ] }),
118
+ /* @__PURE__ */ jsx(Spinner, { type: spinnerType })
119
+ ] }) }) });
120
+
121
+ const CreateServiceAccountKey = (props) => {
122
+ const { gameId } = useContext(GameContext);
123
+ return /* @__PURE__ */ jsx(Fragment, { children: gameId && /* @__PURE__ */ jsx(CreateForGame, { gameId, ...props }) });
124
+ };
125
+ const CreateForGame = ({ onComplete, onError, gameId, ...boxProps }) => {
126
+ const [didStart, setDidStart] = useState(false);
127
+ const { handleStart, setupStatus, isCreating } = useAndroidServiceAccount({
128
+ projectId: gameId,
129
+ onError,
130
+ onComplete
131
+ });
132
+ useEffect(() => {
133
+ handleStart().then(() => setDidStart(true));
134
+ }, [gameId]);
135
+ return /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsxs(Box, { flexDirection: "column", gap: 1, ...boxProps, children: [
136
+ /* @__PURE__ */ jsxs(Box, { flexDirection: "row", gap: 1, children: [
137
+ /* @__PURE__ */ jsx(Text, { children: "Creating a Service Account and API Key..." }),
138
+ isCreating && /* @__PURE__ */ jsx(Spinner, { type: "dots" })
139
+ ] }),
140
+ didStart && /* @__PURE__ */ jsx(ProgressSpinner, { progress: (setupStatus?.progress || 0) * 100, spinnerType: "dots" })
141
+ ] }) });
142
+ };
143
+
144
+ export { CreateServiceAccountKey as C, ProgressSpinner as P };
@@ -0,0 +1,43 @@
1
+ import { u as useJob } from './Command-1YAl_0zS.js';
2
+ import { useState, useEffect } from 'react';
3
+ import { u as useWebSocket } from './useWebSocket-DoImIdTy.js';
4
+ import { N as castJobDates, O as castObjectDates } from './index-BQRxiyqn.js';
5
+
6
+ function useJobWatching({ projectId, jobId, isWatching, onJobUpdate }) {
7
+ const [websocketJob, setWebsocketJob] = useState(null);
8
+ const [mostRecentLog, setMostRecentLog] = useState(null);
9
+ const jobStatusListener = {
10
+ getPattern: () => [`project.${projectId}:job:created`, `project.${projectId}:job:updated`],
11
+ eventHandler: async (pattern, rawJob) => {
12
+ if (rawJob.id !== jobId) return;
13
+ const job2 = castJobDates(rawJob);
14
+ setWebsocketJob(job2);
15
+ if (onJobUpdate) onJobUpdate(job2);
16
+ }
17
+ };
18
+ const jobProgressListener = {
19
+ getPattern: () => `project.${projectId}:job.${jobId}:log`,
20
+ eventHandler: async (pattern, rawLogEntry) => {
21
+ const logEntry = castObjectDates(rawLogEntry, ["sentAt", "createdAt"]);
22
+ setMostRecentLog(logEntry);
23
+ }
24
+ };
25
+ useWebSocket(isWatching ? [jobStatusListener, jobProgressListener] : []);
26
+ const { isLoading, data: job } = useJob({
27
+ projectId,
28
+ jobId
29
+ });
30
+ useEffect(() => {
31
+ setWebsocketJob(null);
32
+ }, [jobId, projectId, isWatching, job]);
33
+ const fetchedJob = job ? job : null;
34
+ const data = websocketJob ? websocketJob : fetchedJob;
35
+ const progress = mostRecentLog?.progress || null;
36
+ return {
37
+ isLoading,
38
+ data,
39
+ progress
40
+ };
41
+ }
42
+
43
+ export { useJobWatching as u };
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "shipthis",
3
- "version": "0.1.3",
3
+ "version": "0.1.4",
4
4
  "lockfileVersion": 3,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "shipthis",
9
- "version": "0.1.3",
9
+ "version": "0.1.4",
10
10
  "license": "MIT",
11
11
  "dependencies": {
12
12
  "@expo/apple-utils": "2.0.3",