@mexty/cli 1.8.2 → 1.9.1

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 (43) hide show
  1. package/dist/block-68f6a9dd608928af6fbea9ba/.eslintrc +14 -0
  2. package/dist/block-68f6a9dd608928af6fbea9ba/.prettierrc +10 -0
  3. package/dist/block-68f6a9dd608928af6fbea9ba/README.md +63 -0
  4. package/dist/block-68f6a9dd608928af6fbea9ba/index.html +13 -0
  5. package/dist/block-68f6a9dd608928af6fbea9ba/package-lock.json +6657 -0
  6. package/dist/block-68f6a9dd608928af6fbea9ba/package.json +34 -0
  7. package/dist/block-68f6a9dd608928af6fbea9ba/src/App.tsx +45 -0
  8. package/dist/block-68f6a9dd608928af6fbea9ba/src/block.tsx +111 -0
  9. package/dist/block-68f6a9dd608928af6fbea9ba/src/index.tsx +6 -0
  10. package/dist/block-68f6a9dd608928af6fbea9ba/src/styles.css +8 -0
  11. package/dist/block-68f6a9dd608928af6fbea9ba/tsconfig.json +27 -0
  12. package/dist/block-68f6a9dd608928af6fbea9ba/vite.config.ts +20 -0
  13. package/dist/block-68f6a9dd608928af6fbea9ba/webpack.config.js +59 -0
  14. package/dist/block-68f6aa43608928af6fbea9c9/.eslintrc +14 -0
  15. package/dist/block-68f6aa43608928af6fbea9c9/.prettierrc +10 -0
  16. package/dist/block-68f6aa43608928af6fbea9c9/README.md +63 -0
  17. package/dist/block-68f6aa43608928af6fbea9c9/coco +0 -0
  18. package/dist/block-68f6aa43608928af6fbea9c9/index.html +13 -0
  19. package/dist/block-68f6aa43608928af6fbea9c9/package-lock.json +6657 -0
  20. package/dist/block-68f6aa43608928af6fbea9c9/package.json +34 -0
  21. package/dist/block-68f6aa43608928af6fbea9c9/src/App.tsx +45 -0
  22. package/dist/block-68f6aa43608928af6fbea9c9/src/block.tsx +111 -0
  23. package/dist/block-68f6aa43608928af6fbea9c9/src/index.tsx +6 -0
  24. package/dist/block-68f6aa43608928af6fbea9c9/src/styles.css +8 -0
  25. package/dist/block-68f6aa43608928af6fbea9c9/tsconfig.json +27 -0
  26. package/dist/block-68f6aa43608928af6fbea9c9/vite.config.ts +20 -0
  27. package/dist/block-68f6aa43608928af6fbea9c9/webpack.config.js +59 -0
  28. package/dist/coco +0 -0
  29. package/dist/commands/create.d.ts.map +1 -1
  30. package/dist/commands/create.js +61 -1
  31. package/dist/commands/create.js.map +1 -1
  32. package/dist/utils/api.d.ts +7 -0
  33. package/dist/utils/api.d.ts.map +1 -1
  34. package/dist/utils/api.js +4 -0
  35. package/dist/utils/api.js.map +1 -1
  36. package/dist/utils/git.d.ts.map +1 -1
  37. package/dist/utils/git.js +55 -9
  38. package/dist/utils/git.js.map +1 -1
  39. package/package.json +1 -1
  40. package/src/commands/create.ts +69 -1
  41. package/src/commands/github-login.ts +107 -107
  42. package/src/utils/api.ts +5 -0
  43. package/src/utils/git.ts +269 -254
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mexty/cli",
3
- "version": "1.8.2",
3
+ "version": "1.9.1",
4
4
  "description": "MEXT CLI for managing blocks and repositories",
5
5
  "main": "dist/index.js",
6
6
  "bin": {
@@ -132,6 +132,72 @@ export async function createCommand(
132
132
  if (gitUrl) {
133
133
  console.log(chalk.gray(` GitHub URL: ${gitUrl}`));
134
134
 
135
+ const blockId = block.id || block._id;
136
+
137
+ // Check if user has GitHub connected and needs to accept invitation
138
+ try {
139
+ const githubStatus = await apiClient.getGitHubStatus();
140
+
141
+ if (githubStatus.connected) {
142
+ // User has GitHub connected, check if they need to accept invitation
143
+ const invitationStatus = await apiClient.checkGitHubInvitationStatus(blockId);
144
+
145
+ if (!invitationStatus.accepted) {
146
+ // User needs to accept invitation
147
+ console.log(chalk.blue(`\nšŸ” GitHub Repository Access Required`));
148
+ console.log(chalk.gray(` You've been invited as a collaborator to this private repository.`));
149
+ console.log(chalk.gray(` You must accept the invitation before cloning.\n`));
150
+
151
+ console.log(chalk.yellow(`šŸ“§ Accept your invitation:`));
152
+ console.log(chalk.cyan(` ${invitationStatus.invitationUrl}\n`));
153
+
154
+ console.log(chalk.gray(`ā³ Waiting for you to accept the invitation...`));
155
+ console.log(chalk.gray(` You have 10 minutes. Checking every 5 seconds.\n`));
156
+
157
+ // Poll for acceptance (10 minutes = 120 attempts at 5 second intervals)
158
+ const maxAttempts = 120;
159
+ const pollInterval = 5000; // 5 seconds
160
+ let attempts = 0;
161
+ let accepted = false;
162
+
163
+ while (attempts < maxAttempts && !accepted) {
164
+ await new Promise(resolve => setTimeout(resolve, pollInterval));
165
+ attempts++;
166
+
167
+ try {
168
+ const status = await apiClient.checkGitHubInvitationStatus(blockId);
169
+ if (status.accepted) {
170
+ accepted = true;
171
+ console.log(chalk.green(`\nāœ… Invitation accepted! Proceeding with clone...\n`));
172
+ break;
173
+ }
174
+
175
+ // Show progress every 30 seconds
176
+ if (attempts % 6 === 0) {
177
+ const elapsed = Math.floor((attempts * pollInterval) / 1000);
178
+ const remaining = Math.floor(((maxAttempts - attempts) * pollInterval) / 1000);
179
+ console.log(chalk.gray(` Still waiting... (${elapsed}s elapsed, ${remaining}s remaining)`));
180
+ }
181
+ } catch (pollError) {
182
+ // Continue polling even if there's an error
183
+ }
184
+ }
185
+
186
+ if (!accepted) {
187
+ console.error(chalk.red(`\nāŒ Timeout: Invitation not accepted within 10 minutes`));
188
+ console.log(chalk.yellow(`\nšŸ’” You can still accept the invitation later and clone manually:`));
189
+ console.log(chalk.gray(` 1. Accept invitation: ${invitationStatus.invitationUrl}`));
190
+ console.log(chalk.gray(` 2. Clone repository: git clone ${gitUrl}`));
191
+ return;
192
+ }
193
+ } else {
194
+ console.log(chalk.green(`āœ… GitHub access confirmed`));
195
+ }
196
+ }
197
+ } catch (githubError: any) {
198
+ // Silently skip GitHub invitation check if not connected
199
+ }
200
+
135
201
  // Clone the repository
136
202
  const repoName = GitManager.extractRepoName(gitUrl);
137
203
  const targetDir = path.join(process.cwd(), repoName);
@@ -166,7 +232,9 @@ export async function createCommand(
166
232
  console.error(
167
233
  chalk.red(`āŒ Failed to clone repository: ${cloneError.message}`)
168
234
  );
169
- console.log(chalk.yellow(`You can manually clone it later:`));
235
+ console.log(chalk.yellow(`\nšŸ’” This might be a private repository.`));
236
+ console.log(chalk.gray(` Connect your GitHub account: mexty github-login`));
237
+ console.log(chalk.yellow(`\nYou can manually clone it later:`));
170
238
  console.log(chalk.gray(` git clone ${gitUrl}`));
171
239
  }
172
240
  } else {
@@ -1,107 +1,107 @@
1
- import chalk from 'chalk';
2
- import open from 'open';
3
- import { apiClient } from '../utils/api';
4
- import { requireAuthentication } from '../utils/auth';
5
-
6
- async function wait(seconds: number): Promise<void> {
7
- return new Promise(resolve => setTimeout(resolve, seconds * 1000));
8
- }
9
-
10
- export async function githubLoginCommand(): Promise<void> {
11
- try {
12
- // Check authentication first
13
- requireAuthentication();
14
-
15
- console.log(chalk.blue('šŸ” GitHub Authentication'));
16
- console.log(chalk.gray(' Connecting your GitHub account for private repository access\n'));
17
-
18
- // Check if already connected
19
- try {
20
- const status = await apiClient.getGitHubStatus();
21
- if (status.connected) {
22
- console.log(chalk.green('āœ… GitHub already connected!'));
23
- console.log(chalk.gray(` Username: ${status.githubUsername}`));
24
- console.log(chalk.gray(` Status: ${status.message}\n`));
25
-
26
- console.log(chalk.yellow('To disconnect and reconnect, run: mexty github-disconnect'));
27
- return;
28
- }
29
- } catch (error: any) {
30
- // If status check fails, continue with login
31
- console.log(chalk.yellow('āš ļø Could not check GitHub status, proceeding with login...'));
32
- }
33
-
34
- // Get GitHub OAuth URL
35
- console.log(chalk.yellow('šŸ“” Requesting GitHub OAuth URL...'));
36
- const authData = await apiClient.getGitHubAuthUrl();
37
-
38
- if (!authData.success || !authData.url) {
39
- console.error(chalk.red(`āŒ ${authData.message}`));
40
- process.exit(1);
41
- }
42
-
43
- console.log(chalk.green('āœ… OAuth URL generated'));
44
- console.log(chalk.blue('\n🌐 Opening browser for GitHub authentication...'));
45
- console.log(chalk.gray(` URL: ${authData.url}\n`));
46
-
47
- // Open browser
48
- try {
49
- await open(authData.url);
50
- console.log(chalk.yellow('šŸ‘† Please authorize MEXTY in your browser'));
51
- } catch (error) {
52
- console.warn(chalk.yellow('āš ļø Could not open browser automatically'));
53
- console.log(chalk.blue('\nPlease open this URL in your browser:'));
54
- console.log(chalk.cyan(authData.url));
55
- }
56
-
57
- console.log(chalk.gray('\nā³ Waiting for you to authorize...'));
58
- console.log(chalk.gray(' This may take a moment\n'));
59
-
60
- // Poll for connection status
61
- let connected = false;
62
- let attempts = 0;
63
- const maxAttempts = 60; // 2 minutes (2 second intervals)
64
-
65
- while (!connected && attempts < maxAttempts) {
66
- await wait(2);
67
- attempts++;
68
-
69
- try {
70
- const status = await apiClient.getGitHubStatus();
71
- if (status.connected) {
72
- connected = true;
73
- console.log(chalk.green('\nšŸŽ‰ GitHub connected successfully!'));
74
- console.log(chalk.gray(` Username: ${status.githubUsername}`));
75
- console.log(chalk.gray(` Status: ${status.message}\n`));
76
- console.log(chalk.blue('You can now clone private block repositories!'));
77
- break;
78
- }
79
- } catch (error) {
80
- // Continue polling
81
- }
82
-
83
- // Show progress indicator every 10 attempts
84
- if (attempts % 10 === 0) {
85
- console.log(chalk.gray(` Still waiting... (${attempts * 2}s)`));
86
- }
87
- }
88
-
89
- if (!connected) {
90
- console.error(chalk.red('\nāŒ Authentication timeout'));
91
- console.log(chalk.yellow(' Please try again: mexty github-login'));
92
- process.exit(1);
93
- }
94
-
95
- } catch (error: any) {
96
- console.error(chalk.red(`āŒ GitHub login failed: ${error.message}`));
97
-
98
- if (error.response?.status === 401) {
99
- console.log(chalk.yellow(' Please login first: mexty login'));
100
- } else if (error.response?.status === 500) {
101
- console.log(chalk.yellow(' GitHub OAuth may not be configured on the server'));
102
- }
103
-
104
- process.exit(1);
105
- }
106
- }
107
-
1
+ import chalk from 'chalk';
2
+ import open from 'open';
3
+ import { apiClient } from '../utils/api';
4
+ import { requireAuthentication } from '../utils/auth';
5
+
6
+ async function wait(seconds: number): Promise<void> {
7
+ return new Promise(resolve => setTimeout(resolve, seconds * 1000));
8
+ }
9
+
10
+ export async function githubLoginCommand(): Promise<void> {
11
+ try {
12
+ // Check authentication first
13
+ requireAuthentication();
14
+
15
+ console.log(chalk.blue('šŸ” GitHub Authentication'));
16
+ console.log(chalk.gray(' Connecting your GitHub account for private repository access\n'));
17
+
18
+ // Check if already connected
19
+ try {
20
+ const status = await apiClient.getGitHubStatus();
21
+ if (status.connected) {
22
+ console.log(chalk.green('āœ… GitHub already connected!'));
23
+ console.log(chalk.gray(` Username: ${status.githubUsername}`));
24
+ console.log(chalk.gray(` Status: ${status.message}\n`));
25
+
26
+ console.log(chalk.yellow('To disconnect and reconnect, run: mexty github-disconnect'));
27
+ return;
28
+ }
29
+ } catch (error: any) {
30
+ // If status check fails, continue with login
31
+ console.log(chalk.yellow('āš ļø Could not check GitHub status, proceeding with login...'));
32
+ }
33
+
34
+ // Get GitHub OAuth URL
35
+ console.log(chalk.yellow('šŸ“” Requesting GitHub OAuth URL...'));
36
+ const authData = await apiClient.getGitHubAuthUrl();
37
+
38
+ if (!authData.success || !authData.url) {
39
+ console.error(chalk.red(`āŒ ${authData.message}`));
40
+ process.exit(1);
41
+ }
42
+
43
+ console.log(chalk.green('āœ… OAuth URL generated'));
44
+ console.log(chalk.blue('\n🌐 Opening browser for GitHub authentication...'));
45
+ console.log(chalk.gray(` URL: ${authData.url}\n`));
46
+
47
+ // Open browser
48
+ try {
49
+ await open(authData.url);
50
+ console.log(chalk.yellow('šŸ‘† Please authorize MEXTY in your browser'));
51
+ } catch (error) {
52
+ console.warn(chalk.yellow('āš ļø Could not open browser automatically'));
53
+ console.log(chalk.blue('\nPlease open this URL in your browser:'));
54
+ console.log(chalk.cyan(authData.url));
55
+ }
56
+
57
+ console.log(chalk.gray('\nā³ Waiting for you to authorize...'));
58
+ console.log(chalk.gray(' This may take a moment\n'));
59
+
60
+ // Poll for connection status
61
+ let connected = false;
62
+ let attempts = 0;
63
+ const maxAttempts = 60; // 2 minutes (2 second intervals)
64
+
65
+ while (!connected && attempts < maxAttempts) {
66
+ await wait(2);
67
+ attempts++;
68
+
69
+ try {
70
+ const status = await apiClient.getGitHubStatus();
71
+ if (status.connected) {
72
+ connected = true;
73
+ console.log(chalk.green('\nšŸŽ‰ GitHub connected successfully!'));
74
+ console.log(chalk.gray(` Username: ${status.githubUsername}`));
75
+ console.log(chalk.gray(` Status: ${status.message}\n`));
76
+ console.log(chalk.blue('You can now clone private block repositories!'));
77
+ break;
78
+ }
79
+ } catch (error) {
80
+ // Continue polling
81
+ }
82
+
83
+ // Show progress indicator every 10 attempts
84
+ if (attempts % 10 === 0) {
85
+ console.log(chalk.gray(` Still waiting... (${attempts * 2}s)`));
86
+ }
87
+ }
88
+
89
+ if (!connected) {
90
+ console.error(chalk.red('\nāŒ Authentication timeout'));
91
+ console.log(chalk.yellow(' Please try again: mexty github-login'));
92
+ process.exit(1);
93
+ }
94
+
95
+ } catch (error: any) {
96
+ console.error(chalk.red(`āŒ GitHub login failed: ${error.message}`));
97
+
98
+ if (error.response?.status === 401) {
99
+ console.log(chalk.yellow(' Please login first: mexty login'));
100
+ } else if (error.response?.status === 500) {
101
+ console.log(chalk.yellow(' GitHub OAuth may not be configured on the server'));
102
+ }
103
+
104
+ process.exit(1);
105
+ }
106
+ }
107
+
package/src/utils/api.ts CHANGED
@@ -333,6 +333,11 @@ class ApiClient {
333
333
  return response.data;
334
334
  }
335
335
 
336
+ async checkGitHubInvitationStatus(blockId: string): Promise<{ success: boolean; accepted: boolean; invitationUrl?: string; githubUsername?: string; message?: string }> {
337
+ const response = await this.client.get(`/api/auth/github/invitation-status/${blockId}`);
338
+ return response.data;
339
+ }
340
+
336
341
  setBaseUrl(url: string): void {
337
342
  this.baseUrl = url;
338
343
  this.client.defaults.baseURL = url;