@voltenworks/shipui 0.1.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.
- package/LICENSE +21 -0
- package/README.md +125 -0
- package/dist/commands/add.d.ts +2 -0
- package/dist/commands/add.js +153 -0
- package/dist/commands/add.js.map +1 -0
- package/dist/commands/info.d.ts +2 -0
- package/dist/commands/info.js +44 -0
- package/dist/commands/info.js.map +1 -0
- package/dist/commands/init.d.ts +2 -0
- package/dist/commands/init.js +70 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/list.d.ts +2 -0
- package/dist/commands/list.js +54 -0
- package/dist/commands/list.js.map +1 -0
- package/dist/commands/login.d.ts +2 -0
- package/dist/commands/login.js +40 -0
- package/dist/commands/login.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +19 -0
- package/dist/index.js.map +1 -0
- package/dist/lib/api.d.ts +52 -0
- package/dist/lib/api.js +32 -0
- package/dist/lib/api.js.map +1 -0
- package/dist/lib/auth.d.ts +5 -0
- package/dist/lib/auth.js +24 -0
- package/dist/lib/auth.js.map +1 -0
- package/dist/lib/config.d.ts +16 -0
- package/dist/lib/config.js +56 -0
- package/dist/lib/config.js.map +1 -0
- package/dist/lib/css-merger.d.ts +12 -0
- package/dist/lib/css-merger.js +59 -0
- package/dist/lib/css-merger.js.map +1 -0
- package/dist/lib/deps.d.ts +5 -0
- package/dist/lib/deps.js +38 -0
- package/dist/lib/deps.js.map +1 -0
- package/dist/lib/parse.d.ts +9 -0
- package/dist/lib/parse.js +29 -0
- package/dist/lib/parse.js.map +1 -0
- package/dist/lib/paths.d.ts +1 -0
- package/dist/lib/paths.js +13 -0
- package/dist/lib/paths.js.map +1 -0
- package/dist/lib/prompts.d.ts +3 -0
- package/dist/lib/prompts.js +28 -0
- package/dist/lib/prompts.js.map +1 -0
- package/dist/lib/writer.d.ts +21 -0
- package/dist/lib/writer.js +63 -0
- package/dist/lib/writer.js.map +1 -0
- package/package.json +32 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Voltenworks
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
# shipui
|
|
2
|
+
|
|
3
|
+
Install [ShipUI](https://voltenworks.com/shipui) components into your project. Base components are free. Premium theme styling requires a theme purchase.
|
|
4
|
+
|
|
5
|
+
## Quick Start
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
npx shipui add button
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## Commands
|
|
12
|
+
|
|
13
|
+
### `npx shipui add <name>`
|
|
14
|
+
|
|
15
|
+
Install a base component (free, no auth required).
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
npx shipui add button
|
|
19
|
+
npx shipui add badge
|
|
20
|
+
npx shipui add card
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
### `npx shipui add <name> --theme <slug>`
|
|
24
|
+
|
|
25
|
+
Install a component with premium theme styling.
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
npx shipui add button --theme aloha
|
|
29
|
+
npx shipui add card --theme retro
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
Free themes (like Candy) don't require auth. Paid themes require a purchase token via `shipui login`.
|
|
33
|
+
|
|
34
|
+
### `npx shipui list`
|
|
35
|
+
|
|
36
|
+
List available components and themes.
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
npx shipui list
|
|
40
|
+
npx shipui list --theme aloha
|
|
41
|
+
npx shipui list --category ui
|
|
42
|
+
npx shipui list --free
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
### `npx shipui login`
|
|
46
|
+
|
|
47
|
+
Authenticate with your purchase token (from your purchase confirmation email).
|
|
48
|
+
|
|
49
|
+
```bash
|
|
50
|
+
npx shipui login
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
Tokens are stored in `~/.config/shipui/config.json` and persist across all projects.
|
|
54
|
+
|
|
55
|
+
### `npx shipui init`
|
|
56
|
+
|
|
57
|
+
Create a `shipui.json` config file for your project. Optional, sensible defaults are used without it.
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
npx shipui init
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
### `npx shipui info <name>`
|
|
64
|
+
|
|
65
|
+
Show component details, available themes, and install commands.
|
|
66
|
+
|
|
67
|
+
```bash
|
|
68
|
+
npx shipui info button
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
## Configuration
|
|
72
|
+
|
|
73
|
+
### `shipui.json` (optional)
|
|
74
|
+
|
|
75
|
+
```json
|
|
76
|
+
{
|
|
77
|
+
"$schemaVersion": 1,
|
|
78
|
+
"registry": "https://voltenworks.com/api/registry",
|
|
79
|
+
"paths": {
|
|
80
|
+
"components": "src/components",
|
|
81
|
+
"lib": "src/lib",
|
|
82
|
+
"css": "src/app/globals.css"
|
|
83
|
+
},
|
|
84
|
+
"importAlias": "@/"
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
Without a config file, the CLI auto-detects paths from your project structure.
|
|
89
|
+
|
|
90
|
+
## Flags
|
|
91
|
+
|
|
92
|
+
| Flag | Description |
|
|
93
|
+
|------|-------------|
|
|
94
|
+
| `--theme <slug>` | Apply theme styling |
|
|
95
|
+
| `--yes` | Skip all confirmation prompts |
|
|
96
|
+
| `--overwrite` | Overwrite existing files |
|
|
97
|
+
| `--dry-run` | Preview changes without writing |
|
|
98
|
+
| `--force` | Override theme conflict guard |
|
|
99
|
+
| `--token <token>` | Auth token (alternative to `shipui login`) |
|
|
100
|
+
|
|
101
|
+
## CSS Merging
|
|
102
|
+
|
|
103
|
+
When installing with a theme, the CLI appends theme tokens and component CSS to your `globals.css` using markers:
|
|
104
|
+
|
|
105
|
+
```css
|
|
106
|
+
/* shipui:theme:aloha:start */
|
|
107
|
+
@theme { ... }
|
|
108
|
+
/* shipui:theme:aloha:end */
|
|
109
|
+
|
|
110
|
+
/* shipui:component:aloha-button:start */
|
|
111
|
+
.btn-base { ... }
|
|
112
|
+
/* shipui:component:aloha-button:end */
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
One theme per project by default. Use `--force` to mix themes.
|
|
116
|
+
|
|
117
|
+
## Environment Variables
|
|
118
|
+
|
|
119
|
+
| Variable | Description |
|
|
120
|
+
|----------|-------------|
|
|
121
|
+
| `SHIPUI_TOKEN` | Auth token (overrides stored config) |
|
|
122
|
+
|
|
123
|
+
## License
|
|
124
|
+
|
|
125
|
+
MIT
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import path from 'path';
|
|
4
|
+
import { parseInput } from '../lib/parse.js';
|
|
5
|
+
import { getProjectConfig } from '../lib/config.js';
|
|
6
|
+
import { resolveToken } from '../lib/auth.js';
|
|
7
|
+
import { fetchComponent, fetchRegistryIndex } from '../lib/api.js';
|
|
8
|
+
import { writeComponentFiles, writeUtility } from '../lib/writer.js';
|
|
9
|
+
import { mergeCss } from '../lib/css-merger.js';
|
|
10
|
+
import { detectPackageManager, getMissingDeps, installDeps } from '../lib/deps.js';
|
|
11
|
+
import { confirmOverwrite, confirmInstallDeps } from '../lib/prompts.js';
|
|
12
|
+
export const addCommand = new Command('add')
|
|
13
|
+
.description('Add a ShipUI component to your project')
|
|
14
|
+
.argument('<name>', 'Component name (e.g., button, badge, card)')
|
|
15
|
+
.option('--theme <slug>', 'Apply theme styling (e.g., aloha, retro)')
|
|
16
|
+
.option('--yes', 'Skip all confirmation prompts')
|
|
17
|
+
.option('--overwrite', 'Overwrite existing files')
|
|
18
|
+
.option('--dry-run', 'Preview changes without writing files')
|
|
19
|
+
.option('--force', 'Override theme conflict guard')
|
|
20
|
+
.option('--token <token>', 'Authentication token')
|
|
21
|
+
.action(async (name, options) => {
|
|
22
|
+
try {
|
|
23
|
+
const config = getProjectConfig();
|
|
24
|
+
// Get known themes for dash-syntax parsing
|
|
25
|
+
let knownThemes;
|
|
26
|
+
try {
|
|
27
|
+
const index = await fetchRegistryIndex(config.registry);
|
|
28
|
+
const themeSlugs = new Set();
|
|
29
|
+
for (const c of index.components) {
|
|
30
|
+
for (const t of c.themes) {
|
|
31
|
+
themeSlugs.add(t.themeSlug);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
knownThemes = [...themeSlugs];
|
|
35
|
+
}
|
|
36
|
+
catch {
|
|
37
|
+
// Proceed without known themes, dash syntax won't work
|
|
38
|
+
}
|
|
39
|
+
const parsed = parseInput(name, options.theme, knownThemes);
|
|
40
|
+
console.log();
|
|
41
|
+
if (options.dryRun) {
|
|
42
|
+
console.log(chalk.yellow('DRY RUN, no files will be written\n'));
|
|
43
|
+
}
|
|
44
|
+
// Resolve token if theme is specified
|
|
45
|
+
const token = parsed.themeSlug ? resolveToken(parsed.themeSlug, options.token) : null;
|
|
46
|
+
// Fetch component
|
|
47
|
+
console.log(`Fetching ${parsed.componentName}${parsed.themeSlug ? ` with ${parsed.themeSlug} theme` : ''}...`);
|
|
48
|
+
const manifest = await fetchComponent(config.registry, parsed.componentName, parsed.themeSlug, token);
|
|
49
|
+
// Handle registry dependencies (e.g., utils)
|
|
50
|
+
if (manifest.registryDependencies.includes('utils')) {
|
|
51
|
+
const utilPath = await writeUtility(config, {
|
|
52
|
+
overwrite: options.overwrite ?? false,
|
|
53
|
+
dryRun: options.dryRun ?? false,
|
|
54
|
+
});
|
|
55
|
+
if (utilPath) {
|
|
56
|
+
console.log(` ${chalk.green('+')} ${path.relative(process.cwd(), utilPath)}`);
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
// Check for existing files
|
|
60
|
+
if (!options.overwrite && !options.yes) {
|
|
61
|
+
for (const file of manifest.files) {
|
|
62
|
+
let targetPath;
|
|
63
|
+
if (file.path.startsWith('components/')) {
|
|
64
|
+
targetPath = path.join(process.cwd(), config.paths.components, file.path.slice('components/'.length));
|
|
65
|
+
}
|
|
66
|
+
else {
|
|
67
|
+
targetPath = path.join(process.cwd(), config.paths.components, file.path);
|
|
68
|
+
}
|
|
69
|
+
const fsExtra = await import('fs-extra');
|
|
70
|
+
if (fsExtra.default.existsSync(targetPath)) {
|
|
71
|
+
const confirmed = await confirmOverwrite(path.relative(process.cwd(), targetPath));
|
|
72
|
+
if (!confirmed) {
|
|
73
|
+
console.log(chalk.yellow(`Skipped ${manifest.displayName}.`));
|
|
74
|
+
return;
|
|
75
|
+
}
|
|
76
|
+
options.overwrite = true;
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
// Write component files
|
|
81
|
+
const writeResult = await writeComponentFiles(manifest.files, config, {
|
|
82
|
+
overwrite: options.overwrite ?? false,
|
|
83
|
+
dryRun: options.dryRun ?? false,
|
|
84
|
+
});
|
|
85
|
+
for (const f of writeResult.written) {
|
|
86
|
+
console.log(` ${chalk.green('+')} ${path.relative(process.cwd(), f)}`);
|
|
87
|
+
}
|
|
88
|
+
for (const f of writeResult.skipped) {
|
|
89
|
+
console.log(` ${chalk.yellow('~')} ${path.relative(process.cwd(), f)} (exists, skipped)`);
|
|
90
|
+
}
|
|
91
|
+
// Merge CSS if theme is included
|
|
92
|
+
if (manifest.theme) {
|
|
93
|
+
const cssPath = path.join(process.cwd(), config.paths.css);
|
|
94
|
+
const cssResults = await mergeCss(cssPath, parsed.componentName, manifest.theme, {
|
|
95
|
+
overwrite: options.overwrite ?? false,
|
|
96
|
+
force: options.force ?? false,
|
|
97
|
+
});
|
|
98
|
+
for (const r of cssResults) {
|
|
99
|
+
if (r.action === 'appended') {
|
|
100
|
+
console.log(` ${chalk.green('+')} ${r.message}`);
|
|
101
|
+
}
|
|
102
|
+
else if (r.action === 'skipped') {
|
|
103
|
+
console.log(` ${chalk.yellow('~')} ${r.message}`);
|
|
104
|
+
}
|
|
105
|
+
else if (r.action === 'conflict') {
|
|
106
|
+
console.log(` ${chalk.red('!')} ${r.message}`);
|
|
107
|
+
return;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
// Auto-install npm deps
|
|
112
|
+
if (manifest.npmDependencies.length > 0 && !options.dryRun) {
|
|
113
|
+
const missing = getMissingDeps(manifest.npmDependencies);
|
|
114
|
+
if (missing.length > 0) {
|
|
115
|
+
const pm = detectPackageManager();
|
|
116
|
+
const shouldInstall = options.yes || await confirmInstallDeps(missing, pm);
|
|
117
|
+
if (shouldInstall) {
|
|
118
|
+
console.log(`\nInstalling dependencies with ${pm}...`);
|
|
119
|
+
installDeps(missing, pm);
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
console.log(chalk.yellow(`\nSkipped installing: ${missing.join(', ')}`));
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
// Summary
|
|
127
|
+
console.log();
|
|
128
|
+
if (manifest.theme) {
|
|
129
|
+
console.log(chalk.green(`Installed ${manifest.displayName} with ${manifest.theme.themeName} styling.`));
|
|
130
|
+
}
|
|
131
|
+
else if (manifest.themeAccess === 'unauthorized') {
|
|
132
|
+
console.log(chalk.green(`Installed ${manifest.displayName} (base).`));
|
|
133
|
+
console.log(chalk.yellow(`Premium ${manifest.themeSlug?.toUpperCase()} styling requires a purchase:`));
|
|
134
|
+
console.log(chalk.cyan(manifest.purchaseUrl ?? ''));
|
|
135
|
+
console.log(`\nOr run: ${chalk.bold('npx shipui login')} after purchasing.`);
|
|
136
|
+
}
|
|
137
|
+
else {
|
|
138
|
+
console.log(chalk.green(`Installed ${manifest.displayName} (base).`));
|
|
139
|
+
console.log(`Add theme styling: ${chalk.bold(`npx shipui add ${parsed.componentName} --theme <slug>`)}`);
|
|
140
|
+
}
|
|
141
|
+
// Usage example
|
|
142
|
+
if (manifest.usage) {
|
|
143
|
+
console.log(`\nUsage:`);
|
|
144
|
+
console.log(chalk.dim(manifest.usage));
|
|
145
|
+
}
|
|
146
|
+
console.log();
|
|
147
|
+
}
|
|
148
|
+
catch (error) {
|
|
149
|
+
console.error(chalk.red(error.message));
|
|
150
|
+
process.exit(1);
|
|
151
|
+
}
|
|
152
|
+
});
|
|
153
|
+
//# sourceMappingURL=add.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"add.js","sourceRoot":"","sources":["../../src/commands/add.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import { getProjectConfig } from '../lib/config.js';
|
|
4
|
+
import { fetchRegistryIndex } from '../lib/api.js';
|
|
5
|
+
export const infoCommand = new Command('info')
|
|
6
|
+
.description('Show details about a component')
|
|
7
|
+
.argument('<name>', 'Component name (e.g., button, badge, card)')
|
|
8
|
+
.action(async (name) => {
|
|
9
|
+
try {
|
|
10
|
+
const config = getProjectConfig();
|
|
11
|
+
const index = await fetchRegistryIndex(config.registry);
|
|
12
|
+
const component = index.components.find((c) => c.name === name.toLowerCase());
|
|
13
|
+
if (!component) {
|
|
14
|
+
console.log(chalk.red(`Component "${name}" not found.`));
|
|
15
|
+
console.log(`Run ${chalk.bold('npx shipui list')} to see available components.`);
|
|
16
|
+
process.exit(1);
|
|
17
|
+
}
|
|
18
|
+
console.log();
|
|
19
|
+
console.log(chalk.bold(component.displayName));
|
|
20
|
+
console.log(chalk.dim(component.category));
|
|
21
|
+
console.log();
|
|
22
|
+
console.log(component.description);
|
|
23
|
+
console.log();
|
|
24
|
+
console.log(chalk.bold('Available themes:'));
|
|
25
|
+
for (const theme of component.themes) {
|
|
26
|
+
const price = theme.free
|
|
27
|
+
? chalk.green('free')
|
|
28
|
+
: chalk.dim(`$${theme.themePrice}`);
|
|
29
|
+
console.log(` ${theme.themeSlug.padEnd(14)} ${theme.themeName.padEnd(20)} ${price}`);
|
|
30
|
+
}
|
|
31
|
+
console.log();
|
|
32
|
+
console.log(chalk.bold('Install:'));
|
|
33
|
+
console.log(` ${chalk.cyan(`npx shipui add ${name}`)}`);
|
|
34
|
+
if (component.themes.length > 0) {
|
|
35
|
+
console.log(` ${chalk.cyan(`npx shipui add ${name} --theme ${component.themes[0].themeSlug}`)}`);
|
|
36
|
+
}
|
|
37
|
+
console.log();
|
|
38
|
+
}
|
|
39
|
+
catch (error) {
|
|
40
|
+
console.error(chalk.red(error.message));
|
|
41
|
+
process.exit(1);
|
|
42
|
+
}
|
|
43
|
+
});
|
|
44
|
+
//# sourceMappingURL=info.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"info.js","sourceRoot":"","sources":["../../src/commands/info.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import fs from 'fs-extra';
|
|
4
|
+
import path from 'path';
|
|
5
|
+
import promptsLib from 'prompts';
|
|
6
|
+
export const initCommand = new Command('init')
|
|
7
|
+
.description('Initialize ShipUI configuration for your project')
|
|
8
|
+
.option('--yes', 'Use defaults without prompting')
|
|
9
|
+
.action(async (options) => {
|
|
10
|
+
try {
|
|
11
|
+
const configPath = path.join(process.cwd(), 'shipui.json');
|
|
12
|
+
if (fs.existsSync(configPath)) {
|
|
13
|
+
console.log(chalk.yellow('shipui.json already exists.'));
|
|
14
|
+
return;
|
|
15
|
+
}
|
|
16
|
+
const config = {
|
|
17
|
+
$schemaVersion: 1,
|
|
18
|
+
registry: 'https://voltenworks.com/api/registry',
|
|
19
|
+
paths: {
|
|
20
|
+
components: 'src/components',
|
|
21
|
+
lib: 'src/lib',
|
|
22
|
+
css: 'src/app/globals.css',
|
|
23
|
+
},
|
|
24
|
+
importAlias: '@/',
|
|
25
|
+
};
|
|
26
|
+
if (!options.yes) {
|
|
27
|
+
const responses = await promptsLib([
|
|
28
|
+
{
|
|
29
|
+
type: 'text',
|
|
30
|
+
name: 'components',
|
|
31
|
+
message: 'Components path:',
|
|
32
|
+
initial: fs.existsSync(path.join(process.cwd(), 'components')) ? 'components' : 'src/components',
|
|
33
|
+
},
|
|
34
|
+
{
|
|
35
|
+
type: 'text',
|
|
36
|
+
name: 'lib',
|
|
37
|
+
message: 'Lib path:',
|
|
38
|
+
initial: fs.existsSync(path.join(process.cwd(), 'lib')) ? 'lib' : 'src/lib',
|
|
39
|
+
},
|
|
40
|
+
{
|
|
41
|
+
type: 'text',
|
|
42
|
+
name: 'css',
|
|
43
|
+
message: 'CSS path:',
|
|
44
|
+
initial: fs.existsSync(path.join(process.cwd(), 'app/globals.css')) ? 'app/globals.css' : 'src/app/globals.css',
|
|
45
|
+
},
|
|
46
|
+
{
|
|
47
|
+
type: 'text',
|
|
48
|
+
name: 'importAlias',
|
|
49
|
+
message: 'Import alias:',
|
|
50
|
+
initial: '@/',
|
|
51
|
+
},
|
|
52
|
+
]);
|
|
53
|
+
config.paths = {
|
|
54
|
+
components: responses.components ?? config.paths.components,
|
|
55
|
+
lib: responses.lib ?? config.paths.lib,
|
|
56
|
+
css: responses.css ?? config.paths.css,
|
|
57
|
+
};
|
|
58
|
+
config.importAlias = responses.importAlias ?? config.importAlias;
|
|
59
|
+
}
|
|
60
|
+
await fs.writeJson(configPath, config, { spaces: 2 });
|
|
61
|
+
console.log(chalk.green('Created shipui.json'));
|
|
62
|
+
console.log(`\nRun ${chalk.bold('npx shipui add button')} to install your first component.`);
|
|
63
|
+
console.log();
|
|
64
|
+
}
|
|
65
|
+
catch (error) {
|
|
66
|
+
console.error(chalk.red(error.message));
|
|
67
|
+
process.exit(1);
|
|
68
|
+
}
|
|
69
|
+
});
|
|
70
|
+
//# sourceMappingURL=init.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"init.js","sourceRoot":"","sources":["../../src/commands/init.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import { getProjectConfig } from '../lib/config.js';
|
|
4
|
+
import { fetchRegistryIndex } from '../lib/api.js';
|
|
5
|
+
export const listCommand = new Command('list')
|
|
6
|
+
.description('List available ShipUI components')
|
|
7
|
+
.option('--theme <slug>', 'Filter by theme')
|
|
8
|
+
.option('--category <category>', 'Filter by category (ui, section)')
|
|
9
|
+
.option('--free', 'Show only free theme components')
|
|
10
|
+
.action(async (options) => {
|
|
11
|
+
try {
|
|
12
|
+
const config = getProjectConfig();
|
|
13
|
+
const index = await fetchRegistryIndex(config.registry);
|
|
14
|
+
let components = index.components;
|
|
15
|
+
if (options.category) {
|
|
16
|
+
components = components.filter((c) => c.category === options.category);
|
|
17
|
+
}
|
|
18
|
+
if (options.theme) {
|
|
19
|
+
components = components.filter((c) => c.themes.some((t) => t.themeSlug === options.theme));
|
|
20
|
+
}
|
|
21
|
+
if (options.free) {
|
|
22
|
+
components = components.filter((c) => c.themes.some((t) => t.free));
|
|
23
|
+
}
|
|
24
|
+
if (components.length === 0) {
|
|
25
|
+
console.log(chalk.yellow('No components found matching your filters.'));
|
|
26
|
+
return;
|
|
27
|
+
}
|
|
28
|
+
console.log();
|
|
29
|
+
console.log(chalk.bold('Available Components'));
|
|
30
|
+
console.log();
|
|
31
|
+
// Table header
|
|
32
|
+
const nameWidth = 20;
|
|
33
|
+
const catWidth = 10;
|
|
34
|
+
console.log(chalk.dim('Name'.padEnd(nameWidth) + 'Type'.padEnd(catWidth) + 'Themes'));
|
|
35
|
+
console.log(chalk.dim('-'.repeat(70)));
|
|
36
|
+
for (const comp of components) {
|
|
37
|
+
const themes = comp.themes
|
|
38
|
+
.map((t) => t.free ? chalk.green(t.themeSlug) : t.themeSlug)
|
|
39
|
+
.join(', ');
|
|
40
|
+
console.log(chalk.white(comp.displayName.padEnd(nameWidth)) +
|
|
41
|
+
chalk.dim(comp.category.padEnd(catWidth)) +
|
|
42
|
+
themes);
|
|
43
|
+
}
|
|
44
|
+
console.log();
|
|
45
|
+
console.log(`Install: ${chalk.bold('npx shipui add <name>')}`);
|
|
46
|
+
console.log(`With theme: ${chalk.bold('npx shipui add <name> --theme <slug>')}`);
|
|
47
|
+
console.log();
|
|
48
|
+
}
|
|
49
|
+
catch (error) {
|
|
50
|
+
console.error(chalk.red(error.message));
|
|
51
|
+
process.exit(1);
|
|
52
|
+
}
|
|
53
|
+
});
|
|
54
|
+
//# sourceMappingURL=list.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"list.js","sourceRoot":"","sources":["../../src/commands/list.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAA;AACnD,OAAO,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAA;AAElD,MAAM,CAAC,MAAM,WAAW,GAAG,IAAI,OAAO,CAAC,MAAM,CAAC;KAC3C,WAAW,CAAC,kCAAkC,CAAC;KAC/C,MAAM,CAAC,gBAAgB,EAAE,iBAAiB,CAAC;KAC3C,MAAM,CAAC,uBAAuB,EAAE,kCAAkC,CAAC;KACnE,MAAM,CAAC,QAAQ,EAAE,iCAAiC,CAAC;KACnD,MAAM,CAAC,KAAK,EAAE,OAA8D,EAAE,EAAE;IAC/E,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,gBAAgB,EAAE,CAAA;QACjC,MAAM,KAAK,GAAG,MAAM,kBAAkB,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAA;QAEvD,IAAI,UAAU,GAAG,KAAK,CAAC,UAAU,CAAA;QAEjC,IAAI,OAAO,CAAC,QAAQ,EAAE,CAAC;YACrB,UAAU,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAA;QACxE,CAAC;QAED,IAAI,OAAO,CAAC,KAAK,EAAE,CAAC;YAClB,UAAU,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CACnC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,SAAS,KAAK,OAAO,CAAC,KAAK,CAAC,CACpD,CAAA;QACH,CAAC;QAED,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC;YACjB,UAAU,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CACnC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAC7B,CAAA;QACH,CAAC;QAED,IAAI,UAAU,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC5B,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,4CAA4C,CAAC,CAAC,CAAA;YACvE,OAAM;QACR,CAAC;QAED,OAAO,CAAC,GAAG,EAAE,CAAA;QACb,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,sBAAsB,CAAC,CAAC,CAAA;QAC/C,OAAO,CAAC,GAAG,EAAE,CAAA;QAEb,eAAe;QACf,MAAM,SAAS,GAAG,EAAE,CAAA;QACpB,MAAM,QAAQ,GAAG,EAAE,CAAA;QAEnB,OAAO,CAAC,GAAG,CACT,KAAK,CAAC,GAAG,CACP,MAAM,CAAC,MAAM,CAAC,SAAS,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,QAAQ,CAAC,GAAG,QAAQ,CAC9D,CACF,CAAA;QACD,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,CAAA;QAEtC,KAAK,MAAM,IAAI,IAAI,UAAU,EAAE,CAAC;YAC9B,MAAM,MAAM,GAAG,IAAI,CAAC,MAAM;iBACvB,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;iBAC3D,IAAI,CAAC,IAAI,CAAC,CAAA;YAEb,OAAO,CAAC,GAAG,CACT,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;gBAC/C,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;gBACzC,MAAM,CACP,CAAA;QACH,CAAC;QAED,OAAO,CAAC,GAAG,EAAE,CAAA;QACb,OAAO,CAAC,GAAG,CAAC,YAAY,KAAK,CAAC,IAAI,CAAC,uBAAuB,CAAC,EAAE,CAAC,CAAA;QAC9D,OAAO,CAAC,GAAG,CAAC,eAAe,KAAK,CAAC,IAAI,CAAC,sCAAsC,CAAC,EAAE,CAAC,CAAA;QAChF,OAAO,CAAC,GAAG,EAAE,CAAA;IAEf,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAE,KAAe,CAAC,OAAO,CAAC,CAAC,CAAA;QAClD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;AACH,CAAC,CAAC,CAAA"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import { getProjectConfig, getGlobalConfig, saveGlobalConfig } from '../lib/config.js';
|
|
4
|
+
import { validateToken } from '../lib/api.js';
|
|
5
|
+
import { promptToken } from '../lib/prompts.js';
|
|
6
|
+
export const loginCommand = new Command('login')
|
|
7
|
+
.description('Authenticate with your ShipUI download token')
|
|
8
|
+
.option('--token <token>', 'Token to save (skips prompt)')
|
|
9
|
+
.action(async (options) => {
|
|
10
|
+
try {
|
|
11
|
+
const token = options.token ?? await promptToken();
|
|
12
|
+
if (!token) {
|
|
13
|
+
console.log(chalk.yellow('No token provided.'));
|
|
14
|
+
return;
|
|
15
|
+
}
|
|
16
|
+
const config = getProjectConfig();
|
|
17
|
+
console.log('Validating token...');
|
|
18
|
+
const result = await validateToken(config.registry, token);
|
|
19
|
+
if (!result.valid || !result.product) {
|
|
20
|
+
console.log(chalk.red('Invalid token. Please check your purchase email for the correct token.'));
|
|
21
|
+
process.exit(1);
|
|
22
|
+
}
|
|
23
|
+
// Save to global config
|
|
24
|
+
const globalConfig = getGlobalConfig();
|
|
25
|
+
globalConfig.tokens[result.product] = token;
|
|
26
|
+
saveGlobalConfig(globalConfig);
|
|
27
|
+
console.log();
|
|
28
|
+
console.log(chalk.green(`Authenticated for ${result.product.replace(/_/g, ' ').toUpperCase()}.`));
|
|
29
|
+
if (result.email) {
|
|
30
|
+
console.log(chalk.dim(`Account: ${result.email}`));
|
|
31
|
+
}
|
|
32
|
+
console.log(`\nYou can now install themed components with: ${chalk.bold('npx shipui add <name> --theme <slug>')}`);
|
|
33
|
+
console.log();
|
|
34
|
+
}
|
|
35
|
+
catch (error) {
|
|
36
|
+
console.error(chalk.red(error.message));
|
|
37
|
+
process.exit(1);
|
|
38
|
+
}
|
|
39
|
+
});
|
|
40
|
+
//# sourceMappingURL=login.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"login.js","sourceRoot":"","sources":["../../src/commands/login.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAAE,gBAAgB,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAA;AACtF,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAA;AAC7C,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AAE/C,MAAM,CAAC,MAAM,YAAY,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC;KAC7C,WAAW,CAAC,8CAA8C,CAAC;KAC3D,MAAM,CAAC,iBAAiB,EAAE,8BAA8B,CAAC;KACzD,MAAM,CAAC,KAAK,EAAE,OAA2B,EAAE,EAAE;IAC5C,IAAI,CAAC;QACH,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,IAAI,MAAM,WAAW,EAAE,CAAA;QAElD,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,oBAAoB,CAAC,CAAC,CAAA;YAC/C,OAAM;QACR,CAAC;QAED,MAAM,MAAM,GAAG,gBAAgB,EAAE,CAAA;QACjC,OAAO,CAAC,GAAG,CAAC,qBAAqB,CAAC,CAAA;QAElC,MAAM,MAAM,GAAG,MAAM,aAAa,CAAC,MAAM,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAA;QAE1D,IAAI,CAAC,MAAM,CAAC,KAAK,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC;YACrC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,wEAAwE,CAAC,CAAC,CAAA;YAChG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;QACjB,CAAC;QAED,wBAAwB;QACxB,MAAM,YAAY,GAAG,eAAe,EAAE,CAAA;QACtC,YAAY,CAAC,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,KAAK,CAAA;QAC3C,gBAAgB,CAAC,YAAY,CAAC,CAAA;QAE9B,OAAO,CAAC,GAAG,EAAE,CAAA;QACb,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,CAAC,qBAAqB,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC,WAAW,EAAE,GAAG,CAAC,CAAC,CAAA;QACjG,IAAI,MAAM,CAAC,KAAK,EAAE,CAAC;YACjB,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,YAAY,MAAM,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;QACpD,CAAC;QACD,OAAO,CAAC,GAAG,CAAC,iDAAiD,KAAK,CAAC,IAAI,CAAC,sCAAsC,CAAC,EAAE,CAAC,CAAA;QAClH,OAAO,CAAC,GAAG,EAAE,CAAA;IAEf,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAE,KAAe,CAAC,OAAO,CAAC,CAAC,CAAA;QAClD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;IACjB,CAAC;AACH,CAAC,CAAC,CAAA"}
|
package/dist/index.d.ts
ADDED
package/dist/index.js
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { Command } from 'commander';
|
|
3
|
+
import { addCommand } from './commands/add.js';
|
|
4
|
+
import { listCommand } from './commands/list.js';
|
|
5
|
+
import { loginCommand } from './commands/login.js';
|
|
6
|
+
import { initCommand } from './commands/init.js';
|
|
7
|
+
import { infoCommand } from './commands/info.js';
|
|
8
|
+
const program = new Command();
|
|
9
|
+
program
|
|
10
|
+
.name('shipui')
|
|
11
|
+
.description('Install ShipUI components into your project')
|
|
12
|
+
.version('0.1.0');
|
|
13
|
+
program.addCommand(addCommand);
|
|
14
|
+
program.addCommand(listCommand);
|
|
15
|
+
program.addCommand(loginCommand);
|
|
16
|
+
program.addCommand(initCommand);
|
|
17
|
+
program.addCommand(infoCommand);
|
|
18
|
+
program.parse();
|
|
19
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAA;AAC9C,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAA;AAChD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAA;AAClD,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAA;AAChD,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAA;AAEhD,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAA;AAE7B,OAAO;KACJ,IAAI,CAAC,QAAQ,CAAC;KACd,WAAW,CAAC,6CAA6C,CAAC;KAC1D,OAAO,CAAC,OAAO,CAAC,CAAA;AAEnB,OAAO,CAAC,UAAU,CAAC,UAAU,CAAC,CAAA;AAC9B,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC,CAAA;AAC/B,OAAO,CAAC,UAAU,CAAC,YAAY,CAAC,CAAA;AAChC,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC,CAAA;AAC/B,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC,CAAA;AAE/B,OAAO,CAAC,KAAK,EAAE,CAAA"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
export interface RegistryFile {
|
|
2
|
+
path: string;
|
|
3
|
+
content: string;
|
|
4
|
+
hash: string;
|
|
5
|
+
}
|
|
6
|
+
export interface ThemeOverlay {
|
|
7
|
+
themeSlug: string;
|
|
8
|
+
themeName: string;
|
|
9
|
+
themeTokens: string;
|
|
10
|
+
componentCss: string;
|
|
11
|
+
mode: 'light' | 'dark';
|
|
12
|
+
}
|
|
13
|
+
export interface ComponentManifest {
|
|
14
|
+
version: number;
|
|
15
|
+
kind: 'component';
|
|
16
|
+
name: string;
|
|
17
|
+
displayName: string;
|
|
18
|
+
files: RegistryFile[];
|
|
19
|
+
registryDependencies: string[];
|
|
20
|
+
npmDependencies: string[];
|
|
21
|
+
theme: ThemeOverlay | null;
|
|
22
|
+
themeAccess?: 'unauthorized';
|
|
23
|
+
themeSlug?: string;
|
|
24
|
+
purchaseUrl?: string;
|
|
25
|
+
usage: string;
|
|
26
|
+
variantSnippets: string[];
|
|
27
|
+
updatedAt: string;
|
|
28
|
+
}
|
|
29
|
+
export interface RegistryIndex {
|
|
30
|
+
version: number;
|
|
31
|
+
components: {
|
|
32
|
+
name: string;
|
|
33
|
+
displayName: string;
|
|
34
|
+
category: string;
|
|
35
|
+
description: string;
|
|
36
|
+
tags: string[];
|
|
37
|
+
themes: {
|
|
38
|
+
themeSlug: string;
|
|
39
|
+
themeName: string;
|
|
40
|
+
free: boolean;
|
|
41
|
+
themePrice: number;
|
|
42
|
+
}[];
|
|
43
|
+
}[];
|
|
44
|
+
}
|
|
45
|
+
export interface ValidateResponse {
|
|
46
|
+
valid: boolean;
|
|
47
|
+
product?: string;
|
|
48
|
+
email?: string;
|
|
49
|
+
}
|
|
50
|
+
export declare function fetchRegistryIndex(registryUrl: string): Promise<RegistryIndex>;
|
|
51
|
+
export declare function fetchComponent(registryUrl: string, name: string, themeSlug?: string, token?: string | null): Promise<ComponentManifest>;
|
|
52
|
+
export declare function validateToken(registryUrl: string, token: string): Promise<ValidateResponse>;
|
package/dist/lib/api.js
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
export async function fetchRegistryIndex(registryUrl) {
|
|
2
|
+
const response = await fetch(registryUrl);
|
|
3
|
+
if (!response.ok) {
|
|
4
|
+
throw new Error(`Failed to fetch registry index: ${response.status}`);
|
|
5
|
+
}
|
|
6
|
+
return response.json();
|
|
7
|
+
}
|
|
8
|
+
export async function fetchComponent(registryUrl, name, themeSlug, token) {
|
|
9
|
+
const url = new URL(`${registryUrl}/components/${name}`);
|
|
10
|
+
if (themeSlug)
|
|
11
|
+
url.searchParams.set('theme', themeSlug);
|
|
12
|
+
const headers = {};
|
|
13
|
+
if (token)
|
|
14
|
+
headers['Authorization'] = `Bearer ${token}`;
|
|
15
|
+
const response = await fetch(url.toString(), { headers });
|
|
16
|
+
if (response.status === 404) {
|
|
17
|
+
throw new Error(`Component "${name}" not found. Run \`npx shipui list\` to see available components.`);
|
|
18
|
+
}
|
|
19
|
+
if (!response.ok) {
|
|
20
|
+
throw new Error(`Registry error: ${response.status}`);
|
|
21
|
+
}
|
|
22
|
+
return response.json();
|
|
23
|
+
}
|
|
24
|
+
export async function validateToken(registryUrl, token) {
|
|
25
|
+
const url = `${registryUrl}/validate?token=${encodeURIComponent(token)}`;
|
|
26
|
+
const response = await fetch(url);
|
|
27
|
+
if (!response.ok) {
|
|
28
|
+
throw new Error(`Validation failed: ${response.status}`);
|
|
29
|
+
}
|
|
30
|
+
return response.json();
|
|
31
|
+
}
|
|
32
|
+
//# sourceMappingURL=api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"api.js","sourceRoot":"","sources":["../../src/lib/api.ts"],"names":[],"mappings":"AAsDA,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,WAAmB;IAC1D,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,WAAW,CAAC,CAAA;IACzC,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,mCAAmC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAA;IACvE,CAAC;IACD,OAAO,QAAQ,CAAC,IAAI,EAA4B,CAAA;AAClD,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,cAAc,CAClC,WAAmB,EACnB,IAAY,EACZ,SAAkB,EAClB,KAAqB;IAErB,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,GAAG,WAAW,eAAe,IAAI,EAAE,CAAC,CAAA;IACxD,IAAI,SAAS;QAAE,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,OAAO,EAAE,SAAS,CAAC,CAAA;IAEvD,MAAM,OAAO,GAA2B,EAAE,CAAA;IAC1C,IAAI,KAAK;QAAE,OAAO,CAAC,eAAe,CAAC,GAAG,UAAU,KAAK,EAAE,CAAA;IAEvD,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,GAAG,CAAC,QAAQ,EAAE,EAAE,EAAE,OAAO,EAAE,CAAC,CAAA;IACzD,IAAI,QAAQ,CAAC,MAAM,KAAK,GAAG,EAAE,CAAC;QAC5B,MAAM,IAAI,KAAK,CAAC,cAAc,IAAI,mEAAmE,CAAC,CAAA;IACxG,CAAC;IACD,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,mBAAmB,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAA;IACvD,CAAC;IACD,OAAO,QAAQ,CAAC,IAAI,EAAgC,CAAA;AACtD,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,aAAa,CAAC,WAAmB,EAAE,KAAa;IACpE,MAAM,GAAG,GAAG,GAAG,WAAW,mBAAmB,kBAAkB,CAAC,KAAK,CAAC,EAAE,CAAA;IACxE,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,GAAG,CAAC,CAAA;IACjC,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,sBAAsB,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAA;IAC1D,CAAC;IACD,OAAO,QAAQ,CAAC,IAAI,EAA+B,CAAA;AACrD,CAAC"}
|
package/dist/lib/auth.js
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { getGlobalConfig } from './config.js';
|
|
2
|
+
/**
|
|
3
|
+
* Find the best token for a given theme slug.
|
|
4
|
+
* Priority: env var > Pro > bundle > theme-specific.
|
|
5
|
+
*/
|
|
6
|
+
export function resolveToken(themeSlug, explicitToken) {
|
|
7
|
+
// Explicit token from --token flag
|
|
8
|
+
if (explicitToken)
|
|
9
|
+
return explicitToken;
|
|
10
|
+
// Env var override
|
|
11
|
+
if (process.env.SHIPUI_TOKEN)
|
|
12
|
+
return process.env.SHIPUI_TOKEN;
|
|
13
|
+
const config = getGlobalConfig();
|
|
14
|
+
const { tokens } = config;
|
|
15
|
+
// Priority: Pro > bundle > theme-specific
|
|
16
|
+
if (tokens.theme_pro)
|
|
17
|
+
return tokens.theme_pro;
|
|
18
|
+
if (tokens[`theme_${themeSlug}_bundle`])
|
|
19
|
+
return tokens[`theme_${themeSlug}_bundle`];
|
|
20
|
+
if (tokens[`theme_${themeSlug}`])
|
|
21
|
+
return tokens[`theme_${themeSlug}`];
|
|
22
|
+
return null;
|
|
23
|
+
}
|
|
24
|
+
//# sourceMappingURL=auth.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"auth.js","sourceRoot":"","sources":["../../src/lib/auth.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAA;AAE7C;;;GAGG;AACH,MAAM,UAAU,YAAY,CAAC,SAAiB,EAAE,aAAsB;IACpE,mCAAmC;IACnC,IAAI,aAAa;QAAE,OAAO,aAAa,CAAA;IAEvC,mBAAmB;IACnB,IAAI,OAAO,CAAC,GAAG,CAAC,YAAY;QAAE,OAAO,OAAO,CAAC,GAAG,CAAC,YAAY,CAAA;IAE7D,MAAM,MAAM,GAAG,eAAe,EAAE,CAAA;IAChC,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,CAAA;IAEzB,0CAA0C;IAC1C,IAAI,MAAM,CAAC,SAAS;QAAE,OAAO,MAAM,CAAC,SAAS,CAAA;IAC7C,IAAI,MAAM,CAAC,SAAS,SAAS,SAAS,CAAC;QAAE,OAAO,MAAM,CAAC,SAAS,SAAS,SAAS,CAAC,CAAA;IACnF,IAAI,MAAM,CAAC,SAAS,SAAS,EAAE,CAAC;QAAE,OAAO,MAAM,CAAC,SAAS,SAAS,EAAE,CAAC,CAAA;IAErE,OAAO,IAAI,CAAA;AACb,CAAC"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export interface ProjectConfig {
|
|
2
|
+
$schemaVersion: number;
|
|
3
|
+
registry: string;
|
|
4
|
+
paths: {
|
|
5
|
+
components: string;
|
|
6
|
+
lib: string;
|
|
7
|
+
css: string;
|
|
8
|
+
};
|
|
9
|
+
importAlias: string;
|
|
10
|
+
}
|
|
11
|
+
export interface GlobalConfig {
|
|
12
|
+
tokens: Record<string, string>;
|
|
13
|
+
}
|
|
14
|
+
export declare function getProjectConfig(): ProjectConfig;
|
|
15
|
+
export declare function getGlobalConfig(): GlobalConfig;
|
|
16
|
+
export declare function saveGlobalConfig(config: GlobalConfig): void;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import fs from 'fs-extra';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import { getGlobalConfigPath } from './paths.js';
|
|
4
|
+
const DEFAULT_REGISTRY = 'https://voltenworks.com/api/registry';
|
|
5
|
+
const DEFAULT_PATHS = {
|
|
6
|
+
components: 'src/components',
|
|
7
|
+
lib: 'src/lib',
|
|
8
|
+
css: 'src/app/globals.css',
|
|
9
|
+
};
|
|
10
|
+
const DEFAULT_IMPORT_ALIAS = '@/';
|
|
11
|
+
export function getProjectConfig() {
|
|
12
|
+
const configPath = path.join(process.cwd(), 'shipui.json');
|
|
13
|
+
if (fs.existsSync(configPath)) {
|
|
14
|
+
const raw = fs.readJsonSync(configPath);
|
|
15
|
+
return {
|
|
16
|
+
$schemaVersion: raw.$schemaVersion ?? 1,
|
|
17
|
+
registry: raw.registry ?? DEFAULT_REGISTRY,
|
|
18
|
+
paths: {
|
|
19
|
+
components: raw.paths?.components ?? DEFAULT_PATHS.components,
|
|
20
|
+
lib: raw.paths?.lib ?? DEFAULT_PATHS.lib,
|
|
21
|
+
css: raw.paths?.css ?? DEFAULT_PATHS.css,
|
|
22
|
+
},
|
|
23
|
+
importAlias: raw.importAlias ?? DEFAULT_IMPORT_ALIAS,
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
// Auto-detect paths
|
|
27
|
+
const paths = { ...DEFAULT_PATHS };
|
|
28
|
+
if (fs.existsSync(path.join(process.cwd(), 'components'))) {
|
|
29
|
+
paths.components = 'components';
|
|
30
|
+
}
|
|
31
|
+
if (fs.existsSync(path.join(process.cwd(), 'lib'))) {
|
|
32
|
+
paths.lib = 'lib';
|
|
33
|
+
}
|
|
34
|
+
if (fs.existsSync(path.join(process.cwd(), 'app/globals.css'))) {
|
|
35
|
+
paths.css = 'app/globals.css';
|
|
36
|
+
}
|
|
37
|
+
return {
|
|
38
|
+
$schemaVersion: 1,
|
|
39
|
+
registry: DEFAULT_REGISTRY,
|
|
40
|
+
paths,
|
|
41
|
+
importAlias: DEFAULT_IMPORT_ALIAS,
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
export function getGlobalConfig() {
|
|
45
|
+
const configPath = getGlobalConfigPath();
|
|
46
|
+
if (fs.existsSync(configPath)) {
|
|
47
|
+
return fs.readJsonSync(configPath);
|
|
48
|
+
}
|
|
49
|
+
return { tokens: {} };
|
|
50
|
+
}
|
|
51
|
+
export function saveGlobalConfig(config) {
|
|
52
|
+
const configPath = getGlobalConfigPath();
|
|
53
|
+
fs.ensureDirSync(path.dirname(configPath));
|
|
54
|
+
fs.writeJsonSync(configPath, config, { spaces: 2 });
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=config.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,UAAU,CAAA;AACzB,OAAO,IAAI,MAAM,MAAM,CAAA;AACvB,OAAO,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAA;AAiBhD,MAAM,gBAAgB,GAAG,sCAAsC,CAAA;AAE/D,MAAM,aAAa,GAAG;IACpB,UAAU,EAAE,gBAAgB;IAC5B,GAAG,EAAE,SAAS;IACd,GAAG,EAAE,qBAAqB;CAC3B,CAAA;AAED,MAAM,oBAAoB,GAAG,IAAI,CAAA;AAEjC,MAAM,UAAU,gBAAgB;IAC9B,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,CAAC,CAAA;IAE1D,IAAI,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC9B,MAAM,GAAG,GAAG,EAAE,CAAC,YAAY,CAAC,UAAU,CAA2B,CAAA;QACjE,OAAO;YACL,cAAc,EAAE,GAAG,CAAC,cAAc,IAAI,CAAC;YACvC,QAAQ,EAAE,GAAG,CAAC,QAAQ,IAAI,gBAAgB;YAC1C,KAAK,EAAE;gBACL,UAAU,EAAE,GAAG,CAAC,KAAK,EAAE,UAAU,IAAI,aAAa,CAAC,UAAU;gBAC7D,GAAG,EAAE,GAAG,CAAC,KAAK,EAAE,GAAG,IAAI,aAAa,CAAC,GAAG;gBACxC,GAAG,EAAE,GAAG,CAAC,KAAK,EAAE,GAAG,IAAI,aAAa,CAAC,GAAG;aACzC;YACD,WAAW,EAAE,GAAG,CAAC,WAAW,IAAI,oBAAoB;SACrD,CAAA;IACH,CAAC;IAED,oBAAoB;IACpB,MAAM,KAAK,GAAG,EAAE,GAAG,aAAa,EAAE,CAAA;IAClC,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,YAAY,CAAC,CAAC,EAAE,CAAC;QAC1D,KAAK,CAAC,UAAU,GAAG,YAAY,CAAA;IACjC,CAAC;IACD,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,KAAK,CAAC,CAAC,EAAE,CAAC;QACnD,KAAK,CAAC,GAAG,GAAG,KAAK,CAAA;IACnB,CAAC;IACD,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,iBAAiB,CAAC,CAAC,EAAE,CAAC;QAC/D,KAAK,CAAC,GAAG,GAAG,iBAAiB,CAAA;IAC/B,CAAC;IAED,OAAO;QACL,cAAc,EAAE,CAAC;QACjB,QAAQ,EAAE,gBAAgB;QAC1B,KAAK;QACL,WAAW,EAAE,oBAAoB;KAClC,CAAA;AACH,CAAC;AAED,MAAM,UAAU,eAAe;IAC7B,MAAM,UAAU,GAAG,mBAAmB,EAAE,CAAA;IAExC,IAAI,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC9B,OAAO,EAAE,CAAC,YAAY,CAAC,UAAU,CAAiB,CAAA;IACpD,CAAC;IAED,OAAO,EAAE,MAAM,EAAE,EAAE,EAAE,CAAA;AACvB,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,MAAoB;IACnD,MAAM,UAAU,GAAG,mBAAmB,EAAE,CAAA;IACxC,EAAE,CAAC,aAAa,CAAC,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC,CAAA;IAC1C,EAAE,CAAC,aAAa,CAAC,UAAU,EAAE,MAAM,EAAE,EAAE,MAAM,EAAE,CAAC,EAAE,CAAC,CAAA;AACrD,CAAC"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { ThemeOverlay } from './api.js';
|
|
2
|
+
export interface MergeResult {
|
|
3
|
+
action: 'appended' | 'skipped' | 'conflict';
|
|
4
|
+
message: string;
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* Merge theme tokens and component CSS into globals.css using markers.
|
|
8
|
+
*/
|
|
9
|
+
export declare function mergeCss(cssPath: string, componentName: string, theme: ThemeOverlay, options: {
|
|
10
|
+
overwrite: boolean;
|
|
11
|
+
force: boolean;
|
|
12
|
+
}): Promise<MergeResult[]>;
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import fs from 'fs-extra';
|
|
2
|
+
const THEME_START = (slug) => `/* shipui:theme:${slug}:start */`;
|
|
3
|
+
const THEME_END = (slug) => `/* shipui:theme:${slug}:end */`;
|
|
4
|
+
const COMPONENT_START = (id) => `/* shipui:component:${id}:start */`;
|
|
5
|
+
const COMPONENT_END = (id) => `/* shipui:component:${id}:end */`;
|
|
6
|
+
/**
|
|
7
|
+
* Merge theme tokens and component CSS into globals.css using markers.
|
|
8
|
+
*/
|
|
9
|
+
export async function mergeCss(cssPath, componentName, theme, options) {
|
|
10
|
+
const results = [];
|
|
11
|
+
let css = '';
|
|
12
|
+
if (await fs.pathExists(cssPath)) {
|
|
13
|
+
css = await fs.readFile(cssPath, 'utf-8');
|
|
14
|
+
}
|
|
15
|
+
const componentId = `${theme.themeSlug}-${componentName}`;
|
|
16
|
+
// Check for theme block
|
|
17
|
+
const themeStart = THEME_START(theme.themeSlug);
|
|
18
|
+
const hasThemeBlock = css.includes(themeStart);
|
|
19
|
+
// Check for a DIFFERENT theme block (conflict)
|
|
20
|
+
const otherThemeMatch = css.match(/\/\* shipui:theme:(\w+):start \*\//);
|
|
21
|
+
if (otherThemeMatch && otherThemeMatch[1] !== theme.themeSlug && !options.force) {
|
|
22
|
+
results.push({
|
|
23
|
+
action: 'conflict',
|
|
24
|
+
message: `Theme "${otherThemeMatch[1]}" is already installed. Use --force to override with "${theme.themeSlug}" theme tokens.`,
|
|
25
|
+
});
|
|
26
|
+
return results;
|
|
27
|
+
}
|
|
28
|
+
// Add theme tokens
|
|
29
|
+
if (!hasThemeBlock && theme.themeTokens) {
|
|
30
|
+
const themeBlock = `\n${themeStart}\n${theme.themeTokens}\n${THEME_END(theme.themeSlug)}\n`;
|
|
31
|
+
css += themeBlock;
|
|
32
|
+
results.push({ action: 'appended', message: `Added ${theme.themeName} theme tokens` });
|
|
33
|
+
}
|
|
34
|
+
else if (hasThemeBlock) {
|
|
35
|
+
results.push({ action: 'skipped', message: `${theme.themeName} theme tokens already installed` });
|
|
36
|
+
}
|
|
37
|
+
// Add component CSS
|
|
38
|
+
const componentStart = COMPONENT_START(componentId);
|
|
39
|
+
const hasComponentBlock = css.includes(componentStart);
|
|
40
|
+
if (!hasComponentBlock && theme.componentCss) {
|
|
41
|
+
const componentBlock = `\n${componentStart}\n${theme.componentCss}\n${COMPONENT_END(componentId)}\n`;
|
|
42
|
+
css += componentBlock;
|
|
43
|
+
results.push({ action: 'appended', message: `Added ${componentName} CSS rules` });
|
|
44
|
+
}
|
|
45
|
+
else if (hasComponentBlock && !options.overwrite) {
|
|
46
|
+
results.push({ action: 'skipped', message: `${componentName} CSS already installed` });
|
|
47
|
+
}
|
|
48
|
+
else if (hasComponentBlock && options.overwrite) {
|
|
49
|
+
// Replace existing block
|
|
50
|
+
const startIdx = css.indexOf(componentStart);
|
|
51
|
+
const endMarker = COMPONENT_END(componentId);
|
|
52
|
+
const endIdx = css.indexOf(endMarker) + endMarker.length;
|
|
53
|
+
css = css.slice(0, startIdx) + `${componentStart}\n${theme.componentCss}\n${endMarker}` + css.slice(endIdx);
|
|
54
|
+
results.push({ action: 'appended', message: `Replaced ${componentName} CSS rules` });
|
|
55
|
+
}
|
|
56
|
+
await fs.writeFile(cssPath, css, 'utf-8');
|
|
57
|
+
return results;
|
|
58
|
+
}
|
|
59
|
+
//# sourceMappingURL=css-merger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"css-merger.js","sourceRoot":"","sources":["../../src/lib/css-merger.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,UAAU,CAAA;AAQzB,MAAM,WAAW,GAAG,CAAC,IAAY,EAAE,EAAE,CAAC,mBAAmB,IAAI,WAAW,CAAA;AACxE,MAAM,SAAS,GAAG,CAAC,IAAY,EAAE,EAAE,CAAC,mBAAmB,IAAI,SAAS,CAAA;AACpE,MAAM,eAAe,GAAG,CAAC,EAAU,EAAE,EAAE,CAAC,uBAAuB,EAAE,WAAW,CAAA;AAC5E,MAAM,aAAa,GAAG,CAAC,EAAU,EAAE,EAAE,CAAC,uBAAuB,EAAE,SAAS,CAAA;AAExE;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,QAAQ,CAC5B,OAAe,EACf,aAAqB,EACrB,KAAmB,EACnB,OAA+C;IAE/C,MAAM,OAAO,GAAkB,EAAE,CAAA;IAEjC,IAAI,GAAG,GAAG,EAAE,CAAA;IACZ,IAAI,MAAM,EAAE,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;QACjC,GAAG,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC,CAAA;IAC3C,CAAC;IAED,MAAM,WAAW,GAAG,GAAG,KAAK,CAAC,SAAS,IAAI,aAAa,EAAE,CAAA;IAEzD,wBAAwB;IACxB,MAAM,UAAU,GAAG,WAAW,CAAC,KAAK,CAAC,SAAS,CAAC,CAAA;IAC/C,MAAM,aAAa,GAAG,GAAG,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAA;IAE9C,+CAA+C;IAC/C,MAAM,eAAe,GAAG,GAAG,CAAC,KAAK,CAAC,oCAAoC,CAAC,CAAA;IACvE,IAAI,eAAe,IAAI,eAAe,CAAC,CAAC,CAAC,KAAK,KAAK,CAAC,SAAS,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC;QAChF,OAAO,CAAC,IAAI,CAAC;YACX,MAAM,EAAE,UAAU;YAClB,OAAO,EAAE,UAAU,eAAe,CAAC,CAAC,CAAC,yDAAyD,KAAK,CAAC,SAAS,iBAAiB;SAC/H,CAAC,CAAA;QACF,OAAO,OAAO,CAAA;IAChB,CAAC;IAED,mBAAmB;IACnB,IAAI,CAAC,aAAa,IAAI,KAAK,CAAC,WAAW,EAAE,CAAC;QACxC,MAAM,UAAU,GAAG,KAAK,UAAU,KAAK,KAAK,CAAC,WAAW,KAAK,SAAS,CAAC,KAAK,CAAC,SAAS,CAAC,IAAI,CAAA;QAC3F,GAAG,IAAI,UAAU,CAAA;QACjB,OAAO,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,UAAU,EAAE,OAAO,EAAE,SAAS,KAAK,CAAC,SAAS,eAAe,EAAE,CAAC,CAAA;IACxF,CAAC;SAAM,IAAI,aAAa,EAAE,CAAC;QACzB,OAAO,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,GAAG,KAAK,CAAC,SAAS,iCAAiC,EAAE,CAAC,CAAA;IACnG,CAAC;IAED,oBAAoB;IACpB,MAAM,cAAc,GAAG,eAAe,CAAC,WAAW,CAAC,CAAA;IACnD,MAAM,iBAAiB,GAAG,GAAG,CAAC,QAAQ,CAAC,cAAc,CAAC,CAAA;IAEtD,IAAI,CAAC,iBAAiB,IAAI,KAAK,CAAC,YAAY,EAAE,CAAC;QAC7C,MAAM,cAAc,GAAG,KAAK,cAAc,KAAK,KAAK,CAAC,YAAY,KAAK,aAAa,CAAC,WAAW,CAAC,IAAI,CAAA;QACpG,GAAG,IAAI,cAAc,CAAA;QACrB,OAAO,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,UAAU,EAAE,OAAO,EAAE,SAAS,aAAa,YAAY,EAAE,CAAC,CAAA;IACnF,CAAC;SAAM,IAAI,iBAAiB,IAAI,CAAC,OAAO,CAAC,SAAS,EAAE,CAAC;QACnD,OAAO,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,SAAS,EAAE,OAAO,EAAE,GAAG,aAAa,wBAAwB,EAAE,CAAC,CAAA;IACxF,CAAC;SAAM,IAAI,iBAAiB,IAAI,OAAO,CAAC,SAAS,EAAE,CAAC;QAClD,yBAAyB;QACzB,MAAM,QAAQ,GAAG,GAAG,CAAC,OAAO,CAAC,cAAc,CAAC,CAAA;QAC5C,MAAM,SAAS,GAAG,aAAa,CAAC,WAAW,CAAC,CAAA;QAC5C,MAAM,MAAM,GAAG,GAAG,CAAC,OAAO,CAAC,SAAS,CAAC,GAAG,SAAS,CAAC,MAAM,CAAA;QACxD,GAAG,GAAG,GAAG,CAAC,KAAK,CAAC,CAAC,EAAE,QAAQ,CAAC,GAAG,GAAG,cAAc,KAAK,KAAK,CAAC,YAAY,KAAK,SAAS,EAAE,GAAG,GAAG,CAAC,KAAK,CAAC,MAAM,CAAC,CAAA;QAC3G,OAAO,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,UAAU,EAAE,OAAO,EAAE,YAAY,aAAa,YAAY,EAAE,CAAC,CAAA;IACtF,CAAC;IAED,MAAM,EAAE,CAAC,SAAS,CAAC,OAAO,EAAE,GAAG,EAAE,OAAO,CAAC,CAAA;IACzC,OAAO,OAAO,CAAA;AAChB,CAAC"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
type PackageManager = 'npm' | 'yarn' | 'pnpm' | 'bun';
|
|
2
|
+
export declare function detectPackageManager(): PackageManager;
|
|
3
|
+
export declare function getMissingDeps(deps: string[]): string[];
|
|
4
|
+
export declare function installDeps(deps: string[], pm: PackageManager): void;
|
|
5
|
+
export {};
|
package/dist/lib/deps.js
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import fs from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import { execSync } from 'child_process';
|
|
4
|
+
export function detectPackageManager() {
|
|
5
|
+
const cwd = process.cwd();
|
|
6
|
+
if (fs.existsSync(path.join(cwd, 'bun.lockb')) || fs.existsSync(path.join(cwd, 'bun.lock')))
|
|
7
|
+
return 'bun';
|
|
8
|
+
if (fs.existsSync(path.join(cwd, 'pnpm-lock.yaml')))
|
|
9
|
+
return 'pnpm';
|
|
10
|
+
if (fs.existsSync(path.join(cwd, 'yarn.lock')))
|
|
11
|
+
return 'yarn';
|
|
12
|
+
return 'npm';
|
|
13
|
+
}
|
|
14
|
+
export function getMissingDeps(deps) {
|
|
15
|
+
const missing = [];
|
|
16
|
+
for (const dep of deps) {
|
|
17
|
+
try {
|
|
18
|
+
const pkgPath = path.join(process.cwd(), 'node_modules', dep, 'package.json');
|
|
19
|
+
if (!fs.existsSync(pkgPath)) {
|
|
20
|
+
missing.push(dep);
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
catch {
|
|
24
|
+
missing.push(dep);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
return missing;
|
|
28
|
+
}
|
|
29
|
+
export function installDeps(deps, pm) {
|
|
30
|
+
const installCmd = {
|
|
31
|
+
npm: `npm install ${deps.join(' ')}`,
|
|
32
|
+
yarn: `yarn add ${deps.join(' ')}`,
|
|
33
|
+
pnpm: `pnpm add ${deps.join(' ')}`,
|
|
34
|
+
bun: `bun add ${deps.join(' ')}`,
|
|
35
|
+
};
|
|
36
|
+
execSync(installCmd[pm], { stdio: 'inherit', cwd: process.cwd() });
|
|
37
|
+
}
|
|
38
|
+
//# sourceMappingURL=deps.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"deps.js","sourceRoot":"","sources":["../../src/lib/deps.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAA;AACnB,OAAO,IAAI,MAAM,MAAM,CAAA;AACvB,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAA;AAIxC,MAAM,UAAU,oBAAoB;IAClC,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,EAAE,CAAA;IAEzB,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,CAAC,CAAC,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,UAAU,CAAC,CAAC;QAAE,OAAO,KAAK,CAAA;IACzG,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,gBAAgB,CAAC,CAAC;QAAE,OAAO,MAAM,CAAA;IAClE,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,CAAC,CAAC;QAAE,OAAO,MAAM,CAAA;IAC7D,OAAO,KAAK,CAAA;AACd,CAAC;AAED,MAAM,UAAU,cAAc,CAAC,IAAc;IAC3C,MAAM,OAAO,GAAa,EAAE,CAAA;IAC5B,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE,CAAC;QACvB,IAAI,CAAC;YACH,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,cAAc,EAAE,GAAG,EAAE,cAAc,CAAC,CAAA;YAC7E,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;gBAC5B,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;YACnB,CAAC;QACH,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAA;QACnB,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAA;AAChB,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,IAAc,EAAE,EAAkB;IAC5D,MAAM,UAAU,GAAG;QACjB,GAAG,EAAE,eAAe,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;QACpC,IAAI,EAAE,YAAY,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;QAClC,IAAI,EAAE,YAAY,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;QAClC,GAAG,EAAE,WAAW,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;KACjC,CAAA;IAED,QAAQ,CAAC,UAAU,CAAC,EAAE,CAAC,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE,EAAE,CAAC,CAAA;AACpE,CAAC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export interface ParsedInput {
|
|
2
|
+
componentName: string;
|
|
3
|
+
themeSlug?: string;
|
|
4
|
+
}
|
|
5
|
+
/**
|
|
6
|
+
* Parse input into { componentName, themeSlug? }.
|
|
7
|
+
* Supports: "button", "aloha/button", "aloha-button" (with known theme list)
|
|
8
|
+
*/
|
|
9
|
+
export declare function parseInput(input: string, themeFlag?: string, knownThemes?: string[]): ParsedInput;
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Parse input into { componentName, themeSlug? }.
|
|
3
|
+
* Supports: "button", "aloha/button", "aloha-button" (with known theme list)
|
|
4
|
+
*/
|
|
5
|
+
export function parseInput(input, themeFlag, knownThemes) {
|
|
6
|
+
// --theme flag takes priority
|
|
7
|
+
if (themeFlag) {
|
|
8
|
+
return { componentName: input.toLowerCase(), themeSlug: themeFlag.toLowerCase() };
|
|
9
|
+
}
|
|
10
|
+
// Check for slash syntax: "aloha/button"
|
|
11
|
+
if (input.includes('/')) {
|
|
12
|
+
const [theme, ...rest] = input.split('/');
|
|
13
|
+
return { componentName: rest.join('/').toLowerCase(), themeSlug: theme.toLowerCase() };
|
|
14
|
+
}
|
|
15
|
+
// Check for dash syntax: "aloha-button" (only if we know the theme list)
|
|
16
|
+
if (knownThemes) {
|
|
17
|
+
for (const theme of knownThemes) {
|
|
18
|
+
if (input.toLowerCase().startsWith(`${theme}-`)) {
|
|
19
|
+
const componentName = input.slice(theme.length + 1).toLowerCase();
|
|
20
|
+
if (componentName) {
|
|
21
|
+
return { componentName, themeSlug: theme };
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
// Plain component name
|
|
27
|
+
return { componentName: input.toLowerCase() };
|
|
28
|
+
}
|
|
29
|
+
//# sourceMappingURL=parse.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parse.js","sourceRoot":"","sources":["../../src/lib/parse.ts"],"names":[],"mappings":"AAKA;;;GAGG;AACH,MAAM,UAAU,UAAU,CAAC,KAAa,EAAE,SAAkB,EAAE,WAAsB;IAClF,8BAA8B;IAC9B,IAAI,SAAS,EAAE,CAAC;QACd,OAAO,EAAE,aAAa,EAAE,KAAK,CAAC,WAAW,EAAE,EAAE,SAAS,EAAE,SAAS,CAAC,WAAW,EAAE,EAAE,CAAA;IACnF,CAAC;IAED,yCAAyC;IACzC,IAAI,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;QACxB,MAAM,CAAC,KAAK,EAAE,GAAG,IAAI,CAAC,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;QACzC,OAAO,EAAE,aAAa,EAAE,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,WAAW,EAAE,EAAE,SAAS,EAAE,KAAK,CAAC,WAAW,EAAE,EAAE,CAAA;IACxF,CAAC;IAED,yEAAyE;IACzE,IAAI,WAAW,EAAE,CAAC;QAChB,KAAK,MAAM,KAAK,IAAI,WAAW,EAAE,CAAC;YAChC,IAAI,KAAK,CAAC,WAAW,EAAE,CAAC,UAAU,CAAC,GAAG,KAAK,GAAG,CAAC,EAAE,CAAC;gBAChD,MAAM,aAAa,GAAG,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,WAAW,EAAE,CAAA;gBACjE,IAAI,aAAa,EAAE,CAAC;oBAClB,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,KAAK,EAAE,CAAA;gBAC5C,CAAC;YACH,CAAC;QACH,CAAC;IACH,CAAC;IAED,uBAAuB;IACvB,OAAO,EAAE,aAAa,EAAE,KAAK,CAAC,WAAW,EAAE,EAAE,CAAA;AAC/C,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function getGlobalConfigPath(): string;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import path from 'path';
|
|
2
|
+
import os from 'os';
|
|
3
|
+
export function getGlobalConfigPath() {
|
|
4
|
+
const platform = os.platform();
|
|
5
|
+
if (platform === 'win32') {
|
|
6
|
+
const appData = process.env.APPDATA ?? path.join(os.homedir(), 'AppData', 'Roaming');
|
|
7
|
+
return path.join(appData, 'shipui', 'config.json');
|
|
8
|
+
}
|
|
9
|
+
// macOS and Linux
|
|
10
|
+
const configHome = process.env.XDG_CONFIG_HOME ?? path.join(os.homedir(), '.config');
|
|
11
|
+
return path.join(configHome, 'shipui', 'config.json');
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=paths.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paths.js","sourceRoot":"","sources":["../../src/lib/paths.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,MAAM,MAAM,CAAA;AACvB,OAAO,EAAE,MAAM,IAAI,CAAA;AAEnB,MAAM,UAAU,mBAAmB;IACjC,MAAM,QAAQ,GAAG,EAAE,CAAC,QAAQ,EAAE,CAAA;IAE9B,IAAI,QAAQ,KAAK,OAAO,EAAE,CAAC;QACzB,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,OAAO,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,SAAS,CAAC,CAAA;QACpF,OAAO,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,QAAQ,EAAE,aAAa,CAAC,CAAA;IACpD,CAAC;IAED,kBAAkB;IAClB,MAAM,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,eAAe,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,SAAS,CAAC,CAAA;IACpF,OAAO,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE,QAAQ,EAAE,aAAa,CAAC,CAAA;AACvD,CAAC"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import promptsLib from 'prompts';
|
|
2
|
+
export async function confirmOverwrite(filePath) {
|
|
3
|
+
const response = await promptsLib({
|
|
4
|
+
type: 'confirm',
|
|
5
|
+
name: 'overwrite',
|
|
6
|
+
message: `${filePath} already exists. Overwrite?`,
|
|
7
|
+
initial: false,
|
|
8
|
+
});
|
|
9
|
+
return response.overwrite === true;
|
|
10
|
+
}
|
|
11
|
+
export async function confirmInstallDeps(deps, pm) {
|
|
12
|
+
const response = await promptsLib({
|
|
13
|
+
type: 'confirm',
|
|
14
|
+
name: 'install',
|
|
15
|
+
message: `Missing dependencies: ${deps.join(', ')}. Install with ${pm}?`,
|
|
16
|
+
initial: true,
|
|
17
|
+
});
|
|
18
|
+
return response.install === true;
|
|
19
|
+
}
|
|
20
|
+
export async function promptToken() {
|
|
21
|
+
const response = await promptsLib({
|
|
22
|
+
type: 'text',
|
|
23
|
+
name: 'token',
|
|
24
|
+
message: 'Paste your ShipUI download token (from purchase email):',
|
|
25
|
+
});
|
|
26
|
+
return response.token ?? '';
|
|
27
|
+
}
|
|
28
|
+
//# sourceMappingURL=prompts.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"prompts.js","sourceRoot":"","sources":["../../src/lib/prompts.ts"],"names":[],"mappings":"AAAA,OAAO,UAAU,MAAM,SAAS,CAAA;AAEhC,MAAM,CAAC,KAAK,UAAU,gBAAgB,CAAC,QAAgB;IACrD,MAAM,QAAQ,GAAG,MAAM,UAAU,CAAC;QAChC,IAAI,EAAE,SAAS;QACf,IAAI,EAAE,WAAW;QACjB,OAAO,EAAE,GAAG,QAAQ,6BAA6B;QACjD,OAAO,EAAE,KAAK;KACf,CAAC,CAAA;IACF,OAAO,QAAQ,CAAC,SAAS,KAAK,IAAI,CAAA;AACpC,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,IAAc,EAAE,EAAU;IACjE,MAAM,QAAQ,GAAG,MAAM,UAAU,CAAC;QAChC,IAAI,EAAE,SAAS;QACf,IAAI,EAAE,SAAS;QACf,OAAO,EAAE,yBAAyB,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,kBAAkB,EAAE,GAAG;QACxE,OAAO,EAAE,IAAI;KACd,CAAC,CAAA;IACF,OAAO,QAAQ,CAAC,OAAO,KAAK,IAAI,CAAA;AAClC,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,WAAW;IAC/B,MAAM,QAAQ,GAAG,MAAM,UAAU,CAAC;QAChC,IAAI,EAAE,MAAM;QACZ,IAAI,EAAE,OAAO;QACb,OAAO,EAAE,yDAAyD;KACnE,CAAC,CAAA;IACF,OAAO,QAAQ,CAAC,KAAK,IAAI,EAAE,CAAA;AAC7B,CAAC"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import type { RegistryFile } from './api.js';
|
|
2
|
+
import type { ProjectConfig } from './config.js';
|
|
3
|
+
export interface WriteResult {
|
|
4
|
+
written: string[];
|
|
5
|
+
skipped: string[];
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Write component files to the user's project.
|
|
9
|
+
* Rewrites import aliases from @/ to the project's configured alias.
|
|
10
|
+
*/
|
|
11
|
+
export declare function writeComponentFiles(files: RegistryFile[], config: ProjectConfig, options: {
|
|
12
|
+
overwrite: boolean;
|
|
13
|
+
dryRun: boolean;
|
|
14
|
+
}): Promise<WriteResult>;
|
|
15
|
+
/**
|
|
16
|
+
* Write the cn() utility to the project's lib directory.
|
|
17
|
+
*/
|
|
18
|
+
export declare function writeUtility(config: ProjectConfig, options: {
|
|
19
|
+
overwrite: boolean;
|
|
20
|
+
dryRun: boolean;
|
|
21
|
+
}): Promise<string | null>;
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import fs from 'fs-extra';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
/**
|
|
4
|
+
* Write component files to the user's project.
|
|
5
|
+
* Rewrites import aliases from @/ to the project's configured alias.
|
|
6
|
+
*/
|
|
7
|
+
export async function writeComponentFiles(files, config, options) {
|
|
8
|
+
const result = { written: [], skipped: [] };
|
|
9
|
+
for (const file of files) {
|
|
10
|
+
// Map file path: "components/ui/Button.tsx" -> "<config.paths.components>/ui/Button.tsx"
|
|
11
|
+
let targetPath;
|
|
12
|
+
if (file.path.startsWith('components/')) {
|
|
13
|
+
targetPath = path.join(process.cwd(), config.paths.components, file.path.slice('components/'.length));
|
|
14
|
+
}
|
|
15
|
+
else if (file.path.startsWith('lib/')) {
|
|
16
|
+
targetPath = path.join(process.cwd(), config.paths.lib, file.path.slice('lib/'.length));
|
|
17
|
+
}
|
|
18
|
+
else {
|
|
19
|
+
targetPath = path.join(process.cwd(), config.paths.components, file.path);
|
|
20
|
+
}
|
|
21
|
+
// Check if file exists
|
|
22
|
+
if (fs.existsSync(targetPath) && !options.overwrite) {
|
|
23
|
+
result.skipped.push(targetPath);
|
|
24
|
+
continue;
|
|
25
|
+
}
|
|
26
|
+
if (options.dryRun) {
|
|
27
|
+
result.written.push(targetPath);
|
|
28
|
+
continue;
|
|
29
|
+
}
|
|
30
|
+
// Rewrite import aliases
|
|
31
|
+
let content = file.content;
|
|
32
|
+
if (config.importAlias !== '@/') {
|
|
33
|
+
content = content.replace(/@\//g, config.importAlias);
|
|
34
|
+
}
|
|
35
|
+
// Ensure directory exists and write
|
|
36
|
+
await fs.ensureDir(path.dirname(targetPath));
|
|
37
|
+
await fs.writeFile(targetPath, content, 'utf-8');
|
|
38
|
+
result.written.push(targetPath);
|
|
39
|
+
}
|
|
40
|
+
return result;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Write the cn() utility to the project's lib directory.
|
|
44
|
+
*/
|
|
45
|
+
export async function writeUtility(config, options) {
|
|
46
|
+
const utilPath = path.join(process.cwd(), config.paths.lib, 'utils.ts');
|
|
47
|
+
if (fs.existsSync(utilPath) && !options.overwrite) {
|
|
48
|
+
return null;
|
|
49
|
+
}
|
|
50
|
+
const utilContent = `import { type ClassValue, clsx } from 'clsx'
|
|
51
|
+
import { twMerge } from 'tailwind-merge'
|
|
52
|
+
|
|
53
|
+
export function cn(...inputs: ClassValue[]): string {
|
|
54
|
+
return twMerge(clsx(inputs))
|
|
55
|
+
}
|
|
56
|
+
`;
|
|
57
|
+
if (options.dryRun)
|
|
58
|
+
return utilPath;
|
|
59
|
+
await fs.ensureDir(path.dirname(utilPath));
|
|
60
|
+
await fs.writeFile(utilPath, utilContent, 'utf-8');
|
|
61
|
+
return utilPath;
|
|
62
|
+
}
|
|
63
|
+
//# sourceMappingURL=writer.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"writer.js","sourceRoot":"","sources":["../../src/lib/writer.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@voltenworks/shipui",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Install ShipUI components into your project",
|
|
5
|
+
"bin": {
|
|
6
|
+
"shipui": "./dist/index.js"
|
|
7
|
+
},
|
|
8
|
+
"type": "module",
|
|
9
|
+
"scripts": {
|
|
10
|
+
"build": "tsc",
|
|
11
|
+
"dev": "tsc --watch",
|
|
12
|
+
"prepublishOnly": "tsc"
|
|
13
|
+
},
|
|
14
|
+
"files": ["dist"],
|
|
15
|
+
"dependencies": {
|
|
16
|
+
"commander": "^12.0.0",
|
|
17
|
+
"prompts": "^2.4.2",
|
|
18
|
+
"chalk": "^5.3.0",
|
|
19
|
+
"fs-extra": "^11.2.0"
|
|
20
|
+
},
|
|
21
|
+
"devDependencies": {
|
|
22
|
+
"@types/prompts": "^2.4.9",
|
|
23
|
+
"@types/fs-extra": "^11.0.4",
|
|
24
|
+
"typescript": "^5.4.0"
|
|
25
|
+
},
|
|
26
|
+
"keywords": ["shipui", "components", "nextjs", "tailwind", "cli"],
|
|
27
|
+
"license": "MIT",
|
|
28
|
+
"repository": {
|
|
29
|
+
"type": "git",
|
|
30
|
+
"url": "https://github.com/voltenworks/shipui-cli"
|
|
31
|
+
}
|
|
32
|
+
}
|