magicpath-ai 1.1.2 → 1.3.0-beta.0

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 (45) hide show
  1. package/dist/cli.js +9 -201
  2. package/dist/cli.js.map +1 -1
  3. package/dist/commands/add.d.ts +2 -0
  4. package/dist/commands/add.js +237 -0
  5. package/dist/commands/add.js.map +1 -0
  6. package/dist/commands/auth.d.ts +7 -0
  7. package/dist/commands/auth.js +76 -0
  8. package/dist/commands/auth.js.map +1 -0
  9. package/dist/commands/clone.d.ts +2 -0
  10. package/dist/commands/clone.js +215 -0
  11. package/dist/commands/clone.js.map +1 -0
  12. package/dist/commands/integrate.d.ts +2 -0
  13. package/dist/commands/integrate.js +269 -0
  14. package/dist/commands/integrate.js.map +1 -0
  15. package/dist/util/api.d.ts +5 -1
  16. package/dist/util/api.js +16 -3
  17. package/dist/util/api.js.map +1 -1
  18. package/dist/util/auth.d.ts +11 -0
  19. package/dist/util/auth.js +38 -0
  20. package/dist/util/auth.js.map +1 -0
  21. package/dist/util/authError.d.ts +4 -0
  22. package/dist/util/authError.js +7 -0
  23. package/dist/util/authError.js.map +1 -0
  24. package/dist/util/component.d.ts +186 -0
  25. package/dist/util/component.js +343 -0
  26. package/dist/util/component.js.map +1 -0
  27. package/dist/util/dependencies.d.ts +11 -0
  28. package/dist/util/dependencies.js +71 -6
  29. package/dist/util/dependencies.js.map +1 -1
  30. package/dist/util/diff.d.ts +9 -0
  31. package/dist/util/diff.js +55 -0
  32. package/dist/util/diff.js.map +1 -0
  33. package/dist/util/error.d.ts +0 -1
  34. package/dist/util/error.js +0 -1
  35. package/dist/util/error.js.map +1 -1
  36. package/dist/util/ide.d.ts +1 -1
  37. package/dist/util/ide.js +36 -17
  38. package/dist/util/ide.js.map +1 -1
  39. package/dist/util/integrate.d.ts +73 -0
  40. package/dist/util/integrate.js +660 -0
  41. package/dist/util/integrate.js.map +1 -0
  42. package/dist/util/ui.d.ts +11 -0
  43. package/dist/util/ui.js +30 -0
  44. package/dist/util/ui.js.map +1 -0
  45. package/package.json +3 -1
@@ -0,0 +1,215 @@
1
+ import prompts from 'prompts';
2
+ import ora from 'ora';
3
+ import { z } from 'zod';
4
+ import path from 'path';
5
+ import os from 'os';
6
+ import fs from 'fs-extra';
7
+ import { enableDebugLogger, logger } from '../util/logger.js';
8
+ import { MagicPathError } from '../util/error.js';
9
+ import { downloadProject, releaseProject, unpackProject, } from '../util/project.js';
10
+ import { installDependencies } from '../util/dependencies.js';
11
+ import { openInIDE, openInFileManager } from '../util/ide.js';
12
+ const cloneOptionsSchema = z.object({
13
+ key: z.string(),
14
+ debug: z.boolean().default(false),
15
+ ide: z.enum(['cursor', 'antigravity', 'vscode', 'webstorm']).optional(),
16
+ });
17
+ export function registerCloneCommand(program) {
18
+ program
19
+ .command('clone')
20
+ .description('✨ Instantly bring your MagicPath project to your local playground. Edit, remix, and create in your own vibe.')
21
+ .requiredOption('-k, --key <accessKey>', '🔑 One-time magic access key to unlock and download your project')
22
+ .option('-d, --debug', 'Get verbose debug logs in the CLI')
23
+ .option('-i, --ide <ide>', 'Pre-select IDE to open project in (cursor, antigravity, vscode, webstorm)')
24
+ .action(async (options) => {
25
+ let cloneOptions;
26
+ try {
27
+ cloneOptions = cloneOptionsSchema.parse(options);
28
+ }
29
+ catch {
30
+ throw new Error('Invalid CLI options for clone command.');
31
+ }
32
+ if (cloneOptions.debug)
33
+ enableDebugLogger();
34
+ logger.debug({ options });
35
+ logger.debug({ options: cloneOptions });
36
+ // Step 1: Ask the user where to drop their fresh code
37
+ const homeDir = os.homedir();
38
+ const commonDirs = [
39
+ { name: 'Documents', path: path.join(homeDir, 'Documents') },
40
+ { name: 'Desktop', path: path.join(homeDir, 'Desktop') },
41
+ { name: 'Downloads', path: path.join(homeDir, 'Downloads') },
42
+ ];
43
+ // Filter to only include directories that actually exist
44
+ const existingDirs = await Promise.all(commonDirs.map(async (dir) => {
45
+ try {
46
+ const exists = await fs.pathExists(dir.path);
47
+ return exists ? dir : null;
48
+ }
49
+ catch {
50
+ return null;
51
+ }
52
+ }));
53
+ const validDirs = existingDirs.filter((dir) => dir !== null);
54
+ // Build choices array starting with current directory and home directory
55
+ const choices = [
56
+ {
57
+ title: `Right here (current folder: ${process.cwd()})`,
58
+ value: process.cwd(),
59
+ },
60
+ { title: `Home directory (${homeDir})`, value: homeDir },
61
+ ];
62
+ // Add existing standard directories
63
+ validDirs.forEach((dir) => {
64
+ choices.push({ title: dir.name, value: dir.path });
65
+ });
66
+ // Add option for custom directory
67
+ choices.push({ title: 'Other (specify custom path)', value: 'custom' });
68
+ const { targetDir } = await prompts({
69
+ type: 'select',
70
+ name: 'targetDir',
71
+ message: 'Where should we put your code?',
72
+ choices,
73
+ initial: 0,
74
+ });
75
+ let finalTargetDir = targetDir;
76
+ // Handle custom directory selection
77
+ if (targetDir === 'custom') {
78
+ const { customPath } = await prompts({
79
+ type: 'text',
80
+ name: 'customPath',
81
+ message: 'Enter the full path where you want to create your project:',
82
+ initial: homeDir,
83
+ validate: (value) => {
84
+ if (!value)
85
+ return 'Please enter a path';
86
+ try {
87
+ // Try to resolve the path to check if it's valid
88
+ const resolvedPath = path.resolve(value);
89
+ return true;
90
+ }
91
+ catch {
92
+ return 'Please enter a valid path';
93
+ }
94
+ },
95
+ });
96
+ if (!customPath) {
97
+ throw new MagicPathError('Project creation cancelled');
98
+ }
99
+ finalTargetDir = path.resolve(customPath);
100
+ // Ensure the custom directory exists, create if it doesn't
101
+ try {
102
+ await fs.ensureDir(finalTargetDir);
103
+ }
104
+ catch (err) {
105
+ throw new MagicPathError(`Failed to create or access directory: ${finalTargetDir}`);
106
+ }
107
+ }
108
+ if (!finalTargetDir) {
109
+ throw new MagicPathError('Download cancelled');
110
+ }
111
+ // Step 2: Ask for project name
112
+ const { projectName } = await prompts({
113
+ type: 'text',
114
+ name: 'projectName',
115
+ message: 'What would you like to name your project?',
116
+ initial: 'magicpath-project',
117
+ });
118
+ if (!projectName) {
119
+ throw new MagicPathError('Project creation cancelled');
120
+ }
121
+ let filename;
122
+ // Step 3: Download project
123
+ const downloadSpinner = ora('📥 Downloading project...').start();
124
+ try {
125
+ filename = await downloadProject(cloneOptions.key);
126
+ logger.debug({ filename });
127
+ downloadSpinner.succeed('Project downloaded');
128
+ }
129
+ catch (err) {
130
+ downloadSpinner.fail('Download failed');
131
+ if (err instanceof MagicPathError) {
132
+ throw err;
133
+ }
134
+ else {
135
+ throw new MagicPathError('Something went wrong!');
136
+ }
137
+ }
138
+ // Step 3: Unpack project
139
+ const unpackSpinner = ora('📦 Unpacking project...').start();
140
+ let projectDir;
141
+ try {
142
+ projectDir = unpackProject(filename, projectName, finalTargetDir);
143
+ unpackSpinner.succeed(`Project unpacked to ${projectName}`);
144
+ }
145
+ catch (err) {
146
+ unpackSpinner.fail('Failed to unpack project');
147
+ releaseProject(filename);
148
+ if (err instanceof MagicPathError) {
149
+ throw err;
150
+ }
151
+ else {
152
+ throw new MagicPathError('Something went wrong!');
153
+ }
154
+ }
155
+ // Step 5: Install dependencies
156
+ try {
157
+ installDependencies(projectDir);
158
+ }
159
+ catch (err) {
160
+ if (err instanceof MagicPathError) {
161
+ throw err;
162
+ }
163
+ else {
164
+ throw new MagicPathError('Something went wrong!');
165
+ }
166
+ }
167
+ // Step 6: Ask which IDE to open the project in (or use pre-selected one)
168
+ const ideChoices = [
169
+ { title: 'Cursor', value: 'cursor' },
170
+ { title: 'Antigravity', value: 'antigravity' },
171
+ { title: 'VS Code', value: 'vscode' },
172
+ { title: 'WebStorm', value: 'webstorm' },
173
+ { title: 'Open in file manager', value: 'filemanager' },
174
+ { title: 'None (just finish)', value: 'none' },
175
+ ];
176
+ // Determine initial selection based on --ide flag
177
+ let initialSelection = 0;
178
+ if (cloneOptions.ide) {
179
+ const preselectedIndex = ideChoices.findIndex((choice) => choice.value === cloneOptions.ide);
180
+ if (preselectedIndex !== -1) {
181
+ initialSelection = preselectedIndex;
182
+ }
183
+ }
184
+ const ideResponse = await prompts({
185
+ type: 'select',
186
+ name: 'ide',
187
+ message: 'Which IDE would you like to open the project in?',
188
+ choices: ideChoices,
189
+ initial: initialSelection,
190
+ });
191
+ // Step 7: Open in IDE or file manager if selected
192
+ if (ideResponse.ide && ideResponse.ide !== 'none') {
193
+ try {
194
+ if (ideResponse.ide === 'filemanager') {
195
+ openInFileManager(projectDir);
196
+ }
197
+ else {
198
+ openInIDE(projectDir, ideResponse.ide);
199
+ }
200
+ }
201
+ catch (err) {
202
+ logger.debug({ err });
203
+ // Don't throw error if opening fails, just continue
204
+ if (err instanceof MagicPathError) {
205
+ console.log(err.message);
206
+ }
207
+ else {
208
+ console.log('⚠️ Opening failed, but your project is ready!');
209
+ }
210
+ }
211
+ }
212
+ console.log(`\n🎉 Done! Your project is ready to go at: ${projectDir}`);
213
+ });
214
+ }
215
+ //# sourceMappingURL=clone.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"clone.js","sourceRoot":"","sources":["../../src/commands/clone.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ import type { Command } from 'commander';
2
+ export declare function registerIntegrateCommand(program: Command): void;
@@ -0,0 +1,269 @@
1
+ import prompts from 'prompts';
2
+ import path from 'path';
3
+ import fs from 'fs-extra';
4
+ import { enableDebugLogger } from '../util/logger.js';
5
+ import { MagicPathError } from '../util/error.js';
6
+ import { brandSpinner, BRAND_GREEN, ANSI_RESET, patchPromptsColor, } from '../util/ui.js';
7
+ import { reviewAndApplyChanges } from '../util/diff.js';
8
+ import { detectFramework, findCandidates, readTargetWithContext, requestIntegration, requestRetheme, gatherProjectFiles, detectProjectLanguage, detectLanguageFromExtension, getLanguageDisplayName, } from '../util/integrate.js';
9
+ import { fetchComponent, sanitizeComponentFolderName, resolveComponentsPath, } from '../util/component.js';
10
+ import { runLoginFlow } from './auth.js';
11
+ export function registerIntegrateCommand(program) {
12
+ program
13
+ .command('integrate')
14
+ .description('Integrate a MagicPath component into your project using AI')
15
+ .argument('<generatedName>', 'The generated name of the component (e.g., wispy-river-5234)')
16
+ .option('-d, --debug', 'Enable debug logging', false)
17
+ .action(async (generatedName, options) => {
18
+ try {
19
+ if (options.debug)
20
+ enableDebugLogger();
21
+ const cwd = process.cwd();
22
+ // Step 1: Detect project language and framework
23
+ const hasPackageJson = fs.existsSync(path.join(cwd, 'package.json'));
24
+ const framework = hasPackageJson
25
+ ? detectFramework(cwd)
26
+ : 'unknown';
27
+ const language = hasPackageJson
28
+ ? 'js'
29
+ : detectProjectLanguage(cwd);
30
+ // Step 2: Verify auth
31
+ const { getAuthHeaders } = await import('../util/auth.js');
32
+ try {
33
+ getAuthHeaders();
34
+ }
35
+ catch {
36
+ console.log('You need to be logged in to use AI integration.');
37
+ const { shouldLogin } = await prompts({
38
+ type: 'confirm',
39
+ name: 'shouldLogin',
40
+ message: 'Log in now?',
41
+ initial: true,
42
+ });
43
+ if (!shouldLogin) {
44
+ console.log('Integration cancelled.');
45
+ return;
46
+ }
47
+ const loggedIn = await runLoginFlow();
48
+ if (!loggedIn) {
49
+ console.log('Integration cancelled.');
50
+ return;
51
+ }
52
+ }
53
+ // Step 3: Choose mode
54
+ const restoreColor = patchPromptsColor();
55
+ const { mode } = await prompts({
56
+ type: 'select',
57
+ name: 'mode',
58
+ message: 'What would you like to do?',
59
+ choices: [
60
+ { title: 'Integrate into a specific file', value: 'integrate' },
61
+ {
62
+ title: `Retheme entire project to match this component's style \x1b[31m(EXTREMELY EXPERIMENTAL)\x1b[0m`,
63
+ value: 'retheme',
64
+ },
65
+ ],
66
+ initial: 0,
67
+ });
68
+ restoreColor();
69
+ if (!mode) {
70
+ console.log('Integration cancelled.');
71
+ return;
72
+ }
73
+ if (mode === 'retheme') {
74
+ await runRethemeFlow(generatedName, cwd, language, framework);
75
+ return;
76
+ }
77
+ // ── Integrate flow ──
78
+ await runIntegrateFlow(generatedName, cwd, language, framework);
79
+ }
80
+ catch (err) {
81
+ if (err instanceof MagicPathError) {
82
+ console.error(`\n${err.message}`);
83
+ process.exit(1);
84
+ }
85
+ throw err;
86
+ }
87
+ });
88
+ }
89
+ async function runRethemeFlow(generatedName, cwd, language, framework) {
90
+ // Optional user instruction
91
+ const { userInstruction: rethemeInstruction } = await prompts({
92
+ type: 'text',
93
+ name: 'userInstruction',
94
+ message: 'Any specific instructions for the retheme? (optional — press Enter to skip)',
95
+ });
96
+ // Gather all project UI files
97
+ const gatherSpinner = brandSpinner('Scanning project files...').start();
98
+ const { files: projectFiles, truncated, skippedFiles, } = gatherProjectFiles(cwd, language, framework);
99
+ gatherSpinner.succeed(`Found ${projectFiles.length} UI files`);
100
+ if (truncated && skippedFiles.length > 0) {
101
+ console.log(` Note: ${skippedFiles.length} file(s) skipped to stay within the 1MB total size budget. Pages and layouts are prioritized.`);
102
+ for (const f of skippedFiles) {
103
+ console.log(` - ${f}`);
104
+ }
105
+ }
106
+ if (projectFiles.length === 0) {
107
+ throw new MagicPathError('No UI files found in the project.');
108
+ }
109
+ // Process files one by one
110
+ const totalFiles = projectFiles.length;
111
+ const allModifiedFiles = [];
112
+ const rethemeSpinner = brandSpinner('').start();
113
+ rethemeSpinner.spinner = {
114
+ frames: ['⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏'].map((f) => `${BRAND_GREEN}${f}${ANSI_RESET}`),
115
+ };
116
+ const totalStart = Date.now();
117
+ const BAR_WIDTH = 20;
118
+ const makeBar = (done, total) => {
119
+ const filled = Math.round((done / total) * BAR_WIDTH);
120
+ const filledStr = '█'.repeat(filled);
121
+ const emptyStr = '░'.repeat(BAR_WIDTH - filled);
122
+ return `\x1b[38;2;8;92;52m${filledStr}${emptyStr}\x1b[0m`;
123
+ };
124
+ try {
125
+ for (let i = 0; i < totalFiles; i++) {
126
+ const file = projectFiles[i];
127
+ const fileStart = Date.now();
128
+ const fmtTime = (ms) => {
129
+ const s = Math.floor(ms / 1000);
130
+ const m = Math.floor(s / 60);
131
+ return m > 0 ? `${m}m ${s % 60}s` : `${s}s`;
132
+ };
133
+ const fileElapsed = () => fmtTime(Date.now() - fileStart);
134
+ const totalElapsed = () => fmtTime(Date.now() - totalStart);
135
+ const status = () => `${makeBar(i, totalFiles)} ${i + 1}/${totalFiles} ${file.path} — ${fileElapsed()} (${totalElapsed()} total)`;
136
+ rethemeSpinner.text = status();
137
+ const elapsedTimer = setInterval(() => {
138
+ rethemeSpinner.text = status();
139
+ }, 1000);
140
+ let fileResult;
141
+ try {
142
+ fileResult = await requestRetheme({
143
+ mode: 'retheme',
144
+ projectFiles: [file],
145
+ componentGeneratedName: generatedName,
146
+ framework,
147
+ userInstruction: rethemeInstruction || undefined,
148
+ targetLanguage: language !== 'js' ? language : undefined,
149
+ });
150
+ }
151
+ finally {
152
+ clearInterval(elapsedTimer);
153
+ }
154
+ for (const modified of fileResult.modifiedFiles) {
155
+ allModifiedFiles.push(modified);
156
+ }
157
+ }
158
+ const totalSeconds = Math.floor((Date.now() - totalStart) / 1000);
159
+ const minutes = Math.floor(totalSeconds / 60);
160
+ const seconds = totalSeconds % 60;
161
+ const timeStr = minutes > 0 ? `${minutes}m ${seconds}s` : `${totalSeconds}s`;
162
+ rethemeSpinner.succeed(`Retheme generated (${totalFiles} files in ${timeStr})`);
163
+ await reviewAndApplyChanges(allModifiedFiles, cwd, 'Retheme');
164
+ }
165
+ catch (rethemeErr) {
166
+ rethemeSpinner.fail('Retheme failed');
167
+ throw rethemeErr;
168
+ }
169
+ }
170
+ async function runIntegrateFlow(generatedName, cwd, language, framework) {
171
+ // Find candidate files
172
+ const candidates = findCandidates(cwd, language, framework);
173
+ if (candidates.length === 0) {
174
+ throw new MagicPathError('No suitable files found for integration.');
175
+ }
176
+ // User picks target file
177
+ const allChoices = candidates.map((c) => ({
178
+ title: `${c.relativePath}${c.label ? ` ${c.label}` : ''}`,
179
+ value: c.relativePath,
180
+ }));
181
+ const { targetPath } = await prompts({
182
+ type: 'autocomplete',
183
+ name: 'targetPath',
184
+ message: 'Where do you want to use this component?',
185
+ choices: allChoices,
186
+ limit: 10,
187
+ suggest: async (input, _choices) => {
188
+ const query = input.toLowerCase();
189
+ if (!query)
190
+ return allChoices;
191
+ const filtered = allChoices.filter((c) => c.title.toLowerCase().includes(query));
192
+ if (filtered.length === 0) {
193
+ return [{ title: input, value: input }];
194
+ }
195
+ return filtered;
196
+ },
197
+ });
198
+ if (!targetPath) {
199
+ console.log('Integration cancelled.');
200
+ return;
201
+ }
202
+ const absTarget = path.resolve(cwd, targetPath);
203
+ if (!fs.existsSync(absTarget)) {
204
+ throw new MagicPathError(`File not found: ${targetPath}`);
205
+ }
206
+ // Refine language from the actual file extension
207
+ const fileLanguage = detectLanguageFromExtension(targetPath);
208
+ if (fileLanguage !== 'unknown') {
209
+ language = fileLanguage;
210
+ }
211
+ if (language !== 'js') {
212
+ console.log(` Target language: ${getLanguageDisplayName(language)}`);
213
+ }
214
+ // Optional user instruction
215
+ const { userInstruction } = await prompts({
216
+ type: 'text',
217
+ name: 'userInstruction',
218
+ message: 'How should this component be used? (optional — press Enter to skip)',
219
+ });
220
+ // Read target with context
221
+ // For JS targets, also fetch component from registry to follow its imports into user project
222
+ let componentFiles;
223
+ if (language === 'js') {
224
+ const fetchSpinner = brandSpinner(`Fetching component "${generatedName}"...`).start();
225
+ let componentData;
226
+ try {
227
+ componentData = await fetchComponent(generatedName);
228
+ fetchSpinner.succeed(`Found component: ${componentData.name}`);
229
+ }
230
+ catch (err) {
231
+ fetchSpinner.fail('Failed to fetch component');
232
+ if (err instanceof MagicPathError) {
233
+ throw err;
234
+ }
235
+ throw new MagicPathError('Something went wrong!');
236
+ }
237
+ const componentFolderName = sanitizeComponentFolderName(componentData.name);
238
+ const basePath = resolveComponentsPath(undefined, cwd);
239
+ const componentsPath = path.join(basePath, componentFolderName);
240
+ componentFiles = componentData.files.map((f) => {
241
+ const installedRelPath = path.relative(cwd, path.join(componentsPath, f.path));
242
+ return {
243
+ path: installedRelPath,
244
+ content: f.content,
245
+ };
246
+ });
247
+ }
248
+ const { targetFile, importedFiles, referencingFiles } = readTargetWithContext(targetPath, cwd, componentFiles, language);
249
+ // Call integrate API
250
+ const integrationSpinner = brandSpinner('Generating integration...').start();
251
+ try {
252
+ const result = await requestIntegration({
253
+ targetFile,
254
+ importedFiles,
255
+ referencingFiles,
256
+ componentGeneratedName: generatedName,
257
+ framework,
258
+ userInstruction: userInstruction || undefined,
259
+ targetLanguage: language !== 'js' ? language : undefined,
260
+ });
261
+ integrationSpinner.succeed('Integration generated');
262
+ await reviewAndApplyChanges(result.modifiedFiles, cwd, 'Integration');
263
+ }
264
+ catch (intErr) {
265
+ integrationSpinner.fail('Integration failed');
266
+ throw intErr;
267
+ }
268
+ }
269
+ //# sourceMappingURL=integrate.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"integrate.js","sourceRoot":"","sources":["../../src/commands/integrate.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,8 @@
1
1
  export declare enum APIVersion {
2
2
  V1 = "v1"
3
3
  }
4
- export declare function makeUrl(verison: APIVersion, endpoint: string): string;
4
+ export declare function makeUrl(version: APIVersion, endpoint: string): string;
5
+ export declare function makeRegistryUrl(generatedName: string): string;
6
+ export declare function makeWebUrl(path: string): string;
7
+ export declare function makeAuthUrl(endpoint: string): string;
8
+ export declare function makeIntegrateUrl(): string;
package/dist/util/api.js CHANGED
@@ -1,9 +1,22 @@
1
- const MAGICPATH_BASE_URL = 'https://api.magicpath.ai';
1
+ const MAGICPATH_BASE_URL = process.env.MAGICPATH_API_URL ?? 'https://api.magicpath.ai';
2
2
  export var APIVersion;
3
3
  (function (APIVersion) {
4
4
  APIVersion["V1"] = "v1";
5
5
  })(APIVersion || (APIVersion = {}));
6
- export function makeUrl(verison, endpoint) {
7
- return `${MAGICPATH_BASE_URL}/${verison}/${endpoint}`;
6
+ export function makeUrl(version, endpoint) {
7
+ return `${MAGICPATH_BASE_URL}/${version}/${endpoint}`;
8
+ }
9
+ export function makeRegistryUrl(generatedName) {
10
+ return `${MAGICPATH_BASE_URL}/${APIVersion.V1}/registry/${generatedName}`;
11
+ }
12
+ const MAGICPATH_WEB_URL = process.env.MAGICPATH_WEB_URL ?? 'https://magicpath.ai';
13
+ export function makeWebUrl(path) {
14
+ return `${MAGICPATH_WEB_URL}${path}`;
15
+ }
16
+ export function makeAuthUrl(endpoint) {
17
+ return `${MAGICPATH_BASE_URL}/auth/${endpoint}`;
18
+ }
19
+ export function makeIntegrateUrl() {
20
+ return `${MAGICPATH_BASE_URL}/${APIVersion.V1}/integrate`;
8
21
  }
9
22
  //# sourceMappingURL=api.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"api.js","sourceRoot":"","sources":["../../src/util/api.ts"],"names":[],"mappings":"AAAA,MAAM,kBAAkB,GAAG,0BAA0B,CAAC;AAEtD,MAAM,CAAN,IAAY,UAEX;AAFD,WAAY,UAAU;IACpB,uBAAS,CAAA;AACX,CAAC,EAFW,UAAU,KAAV,UAAU,QAErB;AAED,MAAM,UAAU,OAAO,CAAC,OAAmB,EAAE,QAAgB;IAC3D,OAAO,GAAG,kBAAkB,IAAI,OAAO,IAAI,QAAQ,EAAE,CAAC;AACxD,CAAC"}
1
+ {"version":3,"file":"api.js","sourceRoot":"","sources":["../../src/util/api.ts"],"names":[],"mappings":"AAAA,MAAM,kBAAkB,GACtB,OAAO,CAAC,GAAG,CAAC,iBAAiB,IAAI,0BAA0B,CAAC;AAE9D,MAAM,CAAN,IAAY,UAEX;AAFD,WAAY,UAAU;IACpB,uBAAS,CAAA;AACX,CAAC,EAFW,UAAU,KAAV,UAAU,QAErB;AAED,MAAM,UAAU,OAAO,CAAC,OAAmB,EAAE,QAAgB;IAC3D,OAAO,GAAG,kBAAkB,IAAI,OAAO,IAAI,QAAQ,EAAE,CAAC;AACxD,CAAC;AAED,MAAM,UAAU,eAAe,CAAC,aAAqB;IACnD,OAAO,GAAG,kBAAkB,IAAI,UAAU,CAAC,EAAE,aAAa,aAAa,EAAE,CAAC;AAC5E,CAAC;AAED,MAAM,iBAAiB,GACrB,OAAO,CAAC,GAAG,CAAC,iBAAiB,IAAI,sBAAsB,CAAC;AAE1D,MAAM,UAAU,UAAU,CAAC,IAAY;IACrC,OAAO,GAAG,iBAAiB,GAAG,IAAI,EAAE,CAAC;AACvC,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,QAAgB;IAC1C,OAAO,GAAG,kBAAkB,SAAS,QAAQ,EAAE,CAAC;AAClD,CAAC;AAED,MAAM,UAAU,gBAAgB;IAC9B,OAAO,GAAG,kBAAkB,IAAI,UAAU,CAAC,EAAE,YAAY,CAAC;AAC5D,CAAC"}
@@ -0,0 +1,11 @@
1
+ interface StoredTokens {
2
+ accessToken: string;
3
+ refreshToken: string;
4
+ }
5
+ export declare function saveTokens(accessToken: string, refreshToken: string): void;
6
+ export declare function loadTokens(): StoredTokens | null;
7
+ export declare function clearTokens(): void;
8
+ export declare function getAuthHeaders(): {
9
+ Authorization: string;
10
+ };
11
+ export {};
@@ -0,0 +1,38 @@
1
+ import fs from 'fs-extra';
2
+ import path from 'path';
3
+ import os from 'os';
4
+ const CONFIG_DIR = path.join(os.homedir(), '.magicpath');
5
+ const AUTH_FILE = path.join(CONFIG_DIR, 'auth.json');
6
+ export function saveTokens(accessToken, refreshToken) {
7
+ fs.ensureDirSync(CONFIG_DIR);
8
+ fs.writeJsonSync(AUTH_FILE, { accessToken, refreshToken });
9
+ }
10
+ export function loadTokens() {
11
+ try {
12
+ if (!fs.existsSync(AUTH_FILE))
13
+ return null;
14
+ const data = fs.readJsonSync(AUTH_FILE);
15
+ if (data.accessToken && data.refreshToken)
16
+ return data;
17
+ return null;
18
+ }
19
+ catch {
20
+ return null;
21
+ }
22
+ }
23
+ export function clearTokens() {
24
+ try {
25
+ fs.removeSync(AUTH_FILE);
26
+ }
27
+ catch {
28
+ // Ignore if file doesn't exist
29
+ }
30
+ }
31
+ export function getAuthHeaders() {
32
+ const tokens = loadTokens();
33
+ if (!tokens) {
34
+ throw new Error('Not logged in. Run `magicpath-ai login` first.');
35
+ }
36
+ return { Authorization: `Bearer ${tokens.accessToken}` };
37
+ }
38
+ //# sourceMappingURL=auth.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth.js","sourceRoot":"","sources":["../../src/util/auth.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,UAAU,CAAC;AAC1B,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,EAAE,MAAM,IAAI,CAAC;AAEpB,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,YAAY,CAAC,CAAC;AACzD,MAAM,SAAS,GAAG,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC;AAOrD,MAAM,UAAU,UAAU,CAAC,WAAmB,EAAE,YAAoB;IAClE,EAAE,CAAC,aAAa,CAAC,UAAU,CAAC,CAAC;IAC7B,EAAE,CAAC,aAAa,CAAC,SAAS,EAAE,EAAE,WAAW,EAAE,YAAY,EAAE,CAAC,CAAC;AAC7D,CAAC;AAED,MAAM,UAAU,UAAU;IACxB,IAAI,CAAC;QACH,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,SAAS,CAAC;YAAE,OAAO,IAAI,CAAC;QAC3C,MAAM,IAAI,GAAG,EAAE,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;QACxC,IAAI,IAAI,CAAC,WAAW,IAAI,IAAI,CAAC,YAAY;YAAE,OAAO,IAAI,CAAC;QACvD,OAAO,IAAI,CAAC;IACd,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC;AAED,MAAM,UAAU,WAAW;IACzB,IAAI,CAAC;QACH,EAAE,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACP,+BAA+B;IACjC,CAAC;AACH,CAAC;AAED,MAAM,UAAU,cAAc;IAC5B,MAAM,MAAM,GAAG,UAAU,EAAE,CAAC;IAC5B,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CAAC,gDAAgD,CAAC,CAAC;IACpE,CAAC;IACD,OAAO,EAAE,aAAa,EAAE,UAAU,MAAM,CAAC,WAAW,EAAE,EAAE,CAAC;AAC3D,CAAC"}
@@ -0,0 +1,4 @@
1
+ import { MagicPathError } from './error.js';
2
+ export declare class AuthRequiredError extends MagicPathError {
3
+ constructor();
4
+ }
@@ -0,0 +1,7 @@
1
+ import { MagicPathError } from './error.js';
2
+ export class AuthRequiredError extends MagicPathError {
3
+ constructor() {
4
+ super('You must be logged in to install components.');
5
+ }
6
+ }
7
+ //# sourceMappingURL=authError.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"authError.js","sourceRoot":"","sources":["../../src/util/authError.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAE5C,MAAM,OAAO,iBAAkB,SAAQ,cAAc;IACnD;QACE,KAAK,CAAC,8CAA8C,CAAC,CAAC;IACxD,CAAC;CACF"}