@monkilab/backbone 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/README.md +86 -0
- package/bin/cli.mjs +2 -0
- package/dist/__tests__/create.test.d.ts +2 -0
- package/dist/__tests__/create.test.d.ts.map +1 -0
- package/dist/__tests__/create.test.js +109 -0
- package/dist/__tests__/create.test.js.map +1 -0
- package/dist/__tests__/generators/convex.test.d.ts +2 -0
- package/dist/__tests__/generators/convex.test.d.ts.map +1 -0
- package/dist/__tests__/generators/convex.test.js +101 -0
- package/dist/__tests__/generators/convex.test.js.map +1 -0
- package/dist/__tests__/generators/github-actions.test.d.ts +2 -0
- package/dist/__tests__/generators/github-actions.test.d.ts.map +1 -0
- package/dist/__tests__/generators/github-actions.test.js +92 -0
- package/dist/__tests__/generators/github-actions.test.js.map +1 -0
- package/dist/__tests__/generators/ionic.test.d.ts +2 -0
- package/dist/__tests__/generators/ionic.test.d.ts.map +1 -0
- package/dist/__tests__/generators/ionic.test.js +94 -0
- package/dist/__tests__/generators/ionic.test.js.map +1 -0
- package/dist/__tests__/generators/llm-lib.test.d.ts +2 -0
- package/dist/__tests__/generators/llm-lib.test.d.ts.map +1 -0
- package/dist/__tests__/generators/llm-lib.test.js +67 -0
- package/dist/__tests__/generators/llm-lib.test.js.map +1 -0
- package/dist/__tests__/generators/nextjs.test.d.ts +2 -0
- package/dist/__tests__/generators/nextjs.test.d.ts.map +1 -0
- package/dist/__tests__/generators/nextjs.test.js +88 -0
- package/dist/__tests__/generators/nextjs.test.js.map +1 -0
- package/dist/__tests__/generators/nx.test.d.ts +2 -0
- package/dist/__tests__/generators/nx.test.d.ts.map +1 -0
- package/dist/__tests__/generators/nx.test.js +87 -0
- package/dist/__tests__/generators/nx.test.js.map +1 -0
- package/dist/__tests__/generators/supabase.test.d.ts +2 -0
- package/dist/__tests__/generators/supabase.test.d.ts.map +1 -0
- package/dist/__tests__/generators/supabase.test.js +98 -0
- package/dist/__tests__/generators/supabase.test.js.map +1 -0
- package/dist/__tests__/generators/ui-lib.test.d.ts +2 -0
- package/dist/__tests__/generators/ui-lib.test.d.ts.map +1 -0
- package/dist/__tests__/generators/ui-lib.test.js +67 -0
- package/dist/__tests__/generators/ui-lib.test.js.map +1 -0
- package/dist/__tests__/index.test.d.ts +2 -0
- package/dist/__tests__/index.test.d.ts.map +1 -0
- package/dist/__tests__/index.test.js +117 -0
- package/dist/__tests__/index.test.js.map +1 -0
- package/dist/__tests__/prompts.test.d.ts +2 -0
- package/dist/__tests__/prompts.test.d.ts.map +1 -0
- package/dist/__tests__/prompts.test.js +78 -0
- package/dist/__tests__/prompts.test.js.map +1 -0
- package/dist/cli/create.d.ts +3 -0
- package/dist/cli/create.d.ts.map +1 -0
- package/dist/cli/create.js +58 -0
- package/dist/cli/create.js.map +1 -0
- package/dist/cli/generators/convex.d.ts +8 -0
- package/dist/cli/generators/convex.d.ts.map +1 -0
- package/dist/cli/generators/convex.js +51 -0
- package/dist/cli/generators/convex.js.map +1 -0
- package/dist/cli/generators/github-actions.d.ts +6 -0
- package/dist/cli/generators/github-actions.d.ts.map +1 -0
- package/dist/cli/generators/github-actions.js +16 -0
- package/dist/cli/generators/github-actions.js.map +1 -0
- package/dist/cli/generators/ionic.d.ts +13 -0
- package/dist/cli/generators/ionic.d.ts.map +1 -0
- package/dist/cli/generators/ionic.js +57 -0
- package/dist/cli/generators/ionic.js.map +1 -0
- package/dist/cli/generators/llm-lib.d.ts +10 -0
- package/dist/cli/generators/llm-lib.d.ts.map +1 -0
- package/dist/cli/generators/llm-lib.js +38 -0
- package/dist/cli/generators/llm-lib.js.map +1 -0
- package/dist/cli/generators/nextjs.d.ts +16 -0
- package/dist/cli/generators/nextjs.d.ts.map +1 -0
- package/dist/cli/generators/nextjs.js +59 -0
- package/dist/cli/generators/nextjs.js.map +1 -0
- package/dist/cli/generators/nx.d.ts +7 -0
- package/dist/cli/generators/nx.d.ts.map +1 -0
- package/dist/cli/generators/nx.js +59 -0
- package/dist/cli/generators/nx.js.map +1 -0
- package/dist/cli/generators/supabase.d.ts +8 -0
- package/dist/cli/generators/supabase.d.ts.map +1 -0
- package/dist/cli/generators/supabase.js +54 -0
- package/dist/cli/generators/supabase.js.map +1 -0
- package/dist/cli/generators/ui-lib.d.ts +10 -0
- package/dist/cli/generators/ui-lib.d.ts.map +1 -0
- package/dist/cli/generators/ui-lib.js +38 -0
- package/dist/cli/generators/ui-lib.js.map +1 -0
- package/dist/cli/index.d.ts +2 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +22 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/prompts.d.ts +6 -0
- package/dist/cli/prompts.d.ts.map +1 -0
- package/dist/cli/prompts.js +18 -0
- package/dist/cli/prompts.js.map +1 -0
- package/dist/cli/templates/packages/llm/src/index.d.ts +2 -0
- package/dist/cli/templates/packages/llm/src/index.d.ts.map +1 -0
- package/dist/cli/templates/packages/llm/src/index.js +2 -0
- package/dist/cli/templates/packages/llm/src/index.js.map +1 -0
- package/dist/cli/templates/packages/ui/src/index.d.ts +2 -0
- package/dist/cli/templates/packages/ui/src/index.d.ts.map +1 -0
- package/dist/cli/templates/packages/ui/src/index.js +2 -0
- package/dist/cli/templates/packages/ui/src/index.js.map +1 -0
- package/dist/cli/types.d.ts +11 -0
- package/dist/cli/types.d.ts.map +1 -0
- package/dist/cli/types.js +2 -0
- package/dist/cli/types.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +46 -0
- package/dist/index.js.map +1 -0
- package/package.json +30 -0
- package/src/cli/templates/.github/workflows/deploy.yml +26 -0
- package/src/cli/templates/apps/mobile/capacitor.config.ts.tpl +12 -0
- package/src/cli/templates/apps/mobile/index.html +12 -0
- package/src/cli/templates/apps/mobile/package.json +30 -0
- package/src/cli/templates/apps/mobile/project.json +18 -0
- package/src/cli/templates/apps/mobile/src/App.tsx.tpl +21 -0
- package/src/cli/templates/apps/mobile/src/main.tsx.tpl +11 -0
- package/src/cli/templates/apps/mobile/src/pages/Home.tsx.tpl +22 -0
- package/src/cli/templates/apps/mobile/src/theme/tailwind.css +1 -0
- package/src/cli/templates/apps/mobile/tsconfig.json.tpl +17 -0
- package/src/cli/templates/apps/mobile/vite.config.ts.tpl +9 -0
- package/src/cli/templates/apps/web/app/globals.css +1 -0
- package/src/cli/templates/apps/web/app/layout.tsx.tpl +19 -0
- package/src/cli/templates/apps/web/app/page.tsx.tpl +3 -0
- package/src/cli/templates/apps/web/jest.config.ts.tpl +11 -0
- package/src/cli/templates/apps/web/next.config.ts.tpl +5 -0
- package/src/cli/templates/apps/web/package.json +29 -0
- package/src/cli/templates/apps/web/playwright.config.ts.tpl +13 -0
- package/src/cli/templates/apps/web/postcss.config.js +7 -0
- package/src/cli/templates/apps/web/project.json +39 -0
- package/src/cli/templates/apps/web/tsconfig.json +23 -0
- package/src/cli/templates/nx/README.md +19 -0
- package/src/cli/templates/nx/nx.json +25 -0
- package/src/cli/templates/nx/package.json +22 -0
- package/src/cli/templates/nx/tsconfig.base.json +21 -0
- package/src/cli/templates/packages/llm/package.json +17 -0
- package/src/cli/templates/packages/llm/src/index.ts +2 -0
- package/src/cli/templates/packages/llm/tsconfig.json +8 -0
- package/src/cli/templates/packages/ui/package.json +19 -0
- package/src/cli/templates/packages/ui/src/index.ts +2 -0
- package/src/cli/templates/packages/ui/tsconfig.json +8 -0
- package/templates/.github/workflows/deploy.yml +20 -0
- package/templates/apps/mobile/capacitor.config.ts +7 -0
- package/templates/apps/mobile/ionic.config.json +5 -0
- package/templates/apps/mobile/jest.config.ts +7 -0
- package/templates/apps/mobile/project.json +13 -0
- package/templates/apps/mobile/src/app/globals.css +1 -0
- package/templates/apps/mobile/src/app/layout.tsx +7 -0
- package/templates/apps/mobile/src/app/page.tsx +8 -0
- package/templates/apps/mobile/tailwind.config.js +6 -0
- package/templates/apps/mobile/tsconfig.json +6 -0
- package/templates/apps/web/jest.config.ts +7 -0
- package/templates/apps/web/next.config.ts +3 -0
- package/templates/apps/web/postcss.config.js +1 -0
- package/templates/apps/web/project.json +12 -0
- package/templates/apps/web/src/app/globals.css +1 -0
- package/templates/apps/web/src/app/layout.tsx +10 -0
- package/templates/apps/web/src/app/page.tsx +3 -0
- package/templates/apps/web/tailwind.config.js +6 -0
- package/templates/apps/web/tsconfig.json +6 -0
- package/templates/backend/convex/apps/web/src/lib/backend.ts +7 -0
- package/templates/backend/convex/convex/.gitkeep +0 -0
- package/templates/backend/convex/convex.config.ts +2 -0
- package/templates/backend/supabase/apps/web/src/lib/backend.ts +8 -0
- package/templates/backend/supabase/supabase/config.toml +16 -0
- package/templates/backend/supabase/supabase/migrations/.gitkeep +0 -0
- package/templates/docs/README.md +3 -0
- package/templates/nx/.env.example +9 -0
- package/templates/nx/.prettierrc +1 -0
- package/templates/nx/jest.preset.js +2 -0
- package/templates/nx/nx.json +25 -0
- package/templates/nx/package.json +33 -0
- package/templates/nx/playwright.config.ts +19 -0
- package/templates/nx/tsconfig.base.json +20 -0
- package/templates/packages/llm/jest.config.ts +6 -0
- package/templates/packages/llm/project.json +11 -0
- package/templates/packages/llm/src/email/resend.ts +4 -0
- package/templates/packages/llm/src/index.ts +2 -0
- package/templates/packages/llm/tsconfig.json +6 -0
- package/templates/packages/ui/jest.config.ts +6 -0
- package/templates/packages/ui/project.json +11 -0
- package/templates/packages/ui/src/index.ts +2 -0
- package/templates/packages/ui/tsconfig.json +6 -0
- package/templates/templates/README.md +3 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.test.js","sourceRoot":"","sources":["../../src/__tests__/index.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"prompts.test.d.ts","sourceRoot":"","sources":["../../src/__tests__/prompts.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
|
|
2
|
+
import * as clack from '@clack/prompts';
|
|
3
|
+
vi.mock('@clack/prompts', () => ({
|
|
4
|
+
intro: vi.fn(),
|
|
5
|
+
outro: vi.fn(),
|
|
6
|
+
select: vi.fn(),
|
|
7
|
+
isCancel: vi.fn().mockReturnValue(false),
|
|
8
|
+
cancel: vi.fn(),
|
|
9
|
+
}));
|
|
10
|
+
import { collectOptions } from '../cli/prompts.js';
|
|
11
|
+
describe('collectOptions()', () => {
|
|
12
|
+
beforeEach(() => {
|
|
13
|
+
vi.clearAllMocks();
|
|
14
|
+
// Default: not cancelled
|
|
15
|
+
vi.mocked(clack.isCancel).mockReturnValue(false);
|
|
16
|
+
});
|
|
17
|
+
afterEach(() => {
|
|
18
|
+
vi.restoreAllMocks();
|
|
19
|
+
});
|
|
20
|
+
describe('happy path — backend: convex', () => {
|
|
21
|
+
it('resolves with correct projectName and backend', async () => {
|
|
22
|
+
vi.mocked(clack.select).mockResolvedValue('convex');
|
|
23
|
+
const result = await collectOptions('my-app');
|
|
24
|
+
expect(result).toEqual({ projectName: 'my-app', backend: 'convex' });
|
|
25
|
+
});
|
|
26
|
+
it('calls clack.intro() exactly once', async () => {
|
|
27
|
+
vi.mocked(clack.select).mockResolvedValue('convex');
|
|
28
|
+
await collectOptions('my-app');
|
|
29
|
+
expect(clack.intro).toHaveBeenCalledOnce();
|
|
30
|
+
});
|
|
31
|
+
it('calls clack.outro() exactly once', async () => {
|
|
32
|
+
vi.mocked(clack.select).mockResolvedValue('convex');
|
|
33
|
+
await collectOptions('my-app');
|
|
34
|
+
expect(clack.outro).toHaveBeenCalledOnce();
|
|
35
|
+
});
|
|
36
|
+
});
|
|
37
|
+
describe('happy path — backend: supabase', () => {
|
|
38
|
+
it('resolves with backend: supabase', async () => {
|
|
39
|
+
vi.mocked(clack.select).mockResolvedValue('supabase');
|
|
40
|
+
const result = await collectOptions('my-app');
|
|
41
|
+
expect(result).toEqual({ projectName: 'my-app', backend: 'supabase' });
|
|
42
|
+
});
|
|
43
|
+
it('preserves the passed projectName unchanged', async () => {
|
|
44
|
+
vi.mocked(clack.select).mockResolvedValue('supabase');
|
|
45
|
+
const result = await collectOptions('cool-project');
|
|
46
|
+
expect(result.projectName).toBe('cool-project');
|
|
47
|
+
});
|
|
48
|
+
it('calls intro and outro each exactly once', async () => {
|
|
49
|
+
vi.mocked(clack.select).mockResolvedValue('supabase');
|
|
50
|
+
await collectOptions('my-app');
|
|
51
|
+
expect(clack.intro).toHaveBeenCalledOnce();
|
|
52
|
+
expect(clack.outro).toHaveBeenCalledOnce();
|
|
53
|
+
});
|
|
54
|
+
});
|
|
55
|
+
describe('cancellation', () => {
|
|
56
|
+
it('calls process.exit(0) when user cancels', async () => {
|
|
57
|
+
const cancelSymbol = Symbol('cancel');
|
|
58
|
+
vi.mocked(clack.select).mockResolvedValue(cancelSymbol);
|
|
59
|
+
vi.mocked(clack.isCancel).mockReturnValue(true);
|
|
60
|
+
const exitSpy = vi.spyOn(process, 'exit').mockImplementation((() => {
|
|
61
|
+
throw new Error('PROCESS_EXIT_0');
|
|
62
|
+
}));
|
|
63
|
+
await expect(collectOptions('my-app')).rejects.toThrow('PROCESS_EXIT_0');
|
|
64
|
+
expect(exitSpy).toHaveBeenCalledWith(0);
|
|
65
|
+
});
|
|
66
|
+
it('calls clack.cancel() with a message before exiting', async () => {
|
|
67
|
+
const cancelSymbol = Symbol('cancel');
|
|
68
|
+
vi.mocked(clack.select).mockResolvedValue(cancelSymbol);
|
|
69
|
+
vi.mocked(clack.isCancel).mockReturnValue(true);
|
|
70
|
+
vi.spyOn(process, 'exit').mockImplementation((() => {
|
|
71
|
+
throw new Error('exit');
|
|
72
|
+
}));
|
|
73
|
+
await expect(collectOptions('my-app')).rejects.toThrow();
|
|
74
|
+
expect(clack.cancel).toHaveBeenCalledOnce();
|
|
75
|
+
});
|
|
76
|
+
});
|
|
77
|
+
});
|
|
78
|
+
//# sourceMappingURL=prompts.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"prompts.test.js","sourceRoot":"","sources":["../../src/__tests__/prompts.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,QAAQ,CAAC;AACzE,OAAO,KAAK,KAAK,MAAM,gBAAgB,CAAC;AAExC,EAAE,CAAC,IAAI,CAAC,gBAAgB,EAAE,GAAG,EAAE,CAAC,CAAC;IAC/B,KAAK,EAAE,EAAE,CAAC,EAAE,EAAE;IACd,KAAK,EAAE,EAAE,CAAC,EAAE,EAAE;IACd,MAAM,EAAE,EAAE,CAAC,EAAE,EAAE;IACf,QAAQ,EAAE,EAAE,CAAC,EAAE,EAAE,CAAC,eAAe,CAAC,KAAK,CAAC;IACxC,MAAM,EAAE,EAAE,CAAC,EAAE,EAAE;CAChB,CAAC,CAAC,CAAC;AAEJ,OAAO,EAAE,cAAc,EAAE,MAAM,mBAAmB,CAAC;AAEnD,QAAQ,CAAC,kBAAkB,EAAE,GAAG,EAAE;IAChC,UAAU,CAAC,GAAG,EAAE;QACd,EAAE,CAAC,aAAa,EAAE,CAAC;QACnB,yBAAyB;QACzB,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,eAAe,CAAC,KAAK,CAAC,CAAC;IACnD,CAAC,CAAC,CAAC;IAEH,SAAS,CAAC,GAAG,EAAE;QACb,EAAE,CAAC,eAAe,EAAE,CAAC;IACvB,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,8BAA8B,EAAE,GAAG,EAAE;QAC5C,EAAE,CAAC,+CAA+C,EAAE,KAAK,IAAI,EAAE;YAC7D,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,QAAiB,CAAC,CAAC;YAE7D,MAAM,MAAM,GAAG,MAAM,cAAc,CAAC,QAAQ,CAAC,CAAC;YAC9C,MAAM,CAAC,MAAM,CAAC,CAAC,OAAO,CAAC,EAAE,WAAW,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,CAAC,CAAC;QACvE,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,kCAAkC,EAAE,KAAK,IAAI,EAAE;YAChD,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,QAAiB,CAAC,CAAC;YAC7D,MAAM,cAAc,CAAC,QAAQ,CAAC,CAAC;YAC/B,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,oBAAoB,EAAE,CAAC;QAC7C,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,kCAAkC,EAAE,KAAK,IAAI,EAAE;YAChD,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,QAAiB,CAAC,CAAC;YAC7D,MAAM,cAAc,CAAC,QAAQ,CAAC,CAAC;YAC/B,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,oBAAoB,EAAE,CAAC;QAC7C,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,gCAAgC,EAAE,GAAG,EAAE;QAC9C,EAAE,CAAC,iCAAiC,EAAE,KAAK,IAAI,EAAE;YAC/C,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,UAAmB,CAAC,CAAC;YAE/D,MAAM,MAAM,GAAG,MAAM,cAAc,CAAC,QAAQ,CAAC,CAAC;YAC9C,MAAM,CAAC,MAAM,CAAC,CAAC,OAAO,CAAC,EAAE,WAAW,EAAE,QAAQ,EAAE,OAAO,EAAE,UAAU,EAAE,CAAC,CAAC;QACzE,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,4CAA4C,EAAE,KAAK,IAAI,EAAE;YAC1D,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,UAAmB,CAAC,CAAC;YAE/D,MAAM,MAAM,GAAG,MAAM,cAAc,CAAC,cAAc,CAAC,CAAC;YACpD,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QAClD,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,yCAAyC,EAAE,KAAK,IAAI,EAAE;YACvD,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,UAAmB,CAAC,CAAC;YAC/D,MAAM,cAAc,CAAC,QAAQ,CAAC,CAAC;YAC/B,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,oBAAoB,EAAE,CAAC;YAC3C,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,oBAAoB,EAAE,CAAC;QAC7C,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,cAAc,EAAE,GAAG,EAAE;QAC5B,EAAE,CAAC,yCAAyC,EAAE,KAAK,IAAI,EAAE;YACvD,MAAM,YAAY,GAAG,MAAM,CAAC,QAAQ,CAAC,CAAC;YACtC,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,YAAqB,CAAC,CAAC;YACjE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;YAEhD,MAAM,OAAO,GAAG,EAAE,CAAC,KAAK,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC,kBAAkB,CAAC,CAAC,GAAG,EAAE;gBACjE,MAAM,IAAI,KAAK,CAAC,gBAAgB,CAAC,CAAC;YACpC,CAAC,CAAU,CAAC,CAAC;YAEb,MAAM,MAAM,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC,CAAC,OAAO,CAAC,OAAO,CAAC,gBAAgB,CAAC,CAAC;YACzE,MAAM,CAAC,OAAO,CAAC,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC;QAC1C,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,oDAAoD,EAAE,KAAK,IAAI,EAAE;YAClE,MAAM,YAAY,GAAG,MAAM,CAAC,QAAQ,CAAC,CAAC;YACtC,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,iBAAiB,CAAC,YAAqB,CAAC,CAAC;YACjE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;YAEhD,EAAE,CAAC,KAAK,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC,kBAAkB,CAAC,CAAC,GAAG,EAAE;gBACjD,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,CAAC;YAC1B,CAAC,CAAU,CAAC,CAAC;YAEb,MAAM,MAAM,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC;YACzD,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,oBAAoB,EAAE,CAAC;QAC9C,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"create.d.ts","sourceRoot":"","sources":["../../src/cli/create.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,wBAAsB,MAAM,CAAC,OAAO,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,CAsD/D"}
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import * as clack from '@clack/prompts';
|
|
2
|
+
import { join } from 'node:path';
|
|
3
|
+
import { generateNxWorkspace } from './generators/nx.js';
|
|
4
|
+
import { generateNextjsApp } from './generators/nextjs.js';
|
|
5
|
+
import { generateIonicApp } from './generators/ionic.js';
|
|
6
|
+
import { generateUiLib } from './generators/ui-lib.js';
|
|
7
|
+
import { generateLlmLib } from './generators/llm-lib.js';
|
|
8
|
+
import { generateConvex } from './generators/convex.js';
|
|
9
|
+
import { generateSupabase } from './generators/supabase.js';
|
|
10
|
+
import { generateGithubActions } from './generators/github-actions.js';
|
|
11
|
+
export async function create(options) {
|
|
12
|
+
const outDir = join(process.cwd(), options.projectName);
|
|
13
|
+
const spinner = clack.spinner();
|
|
14
|
+
try {
|
|
15
|
+
spinner.start('Generating Nx workspace…');
|
|
16
|
+
await generateNxWorkspace(options.projectName, outDir);
|
|
17
|
+
spinner.stop('Nx workspace created');
|
|
18
|
+
spinner.start('Generating Next.js app…');
|
|
19
|
+
await generateNextjsApp(options.projectName, outDir);
|
|
20
|
+
spinner.stop('Next.js app created');
|
|
21
|
+
spinner.start('Generating Ionic app…');
|
|
22
|
+
await generateIonicApp(options.projectName, outDir);
|
|
23
|
+
spinner.stop('Ionic app created');
|
|
24
|
+
spinner.start('Generating UI library…');
|
|
25
|
+
await generateUiLib(options.projectName, outDir);
|
|
26
|
+
spinner.stop('UI library created');
|
|
27
|
+
spinner.start('Generating LLM library…');
|
|
28
|
+
await generateLlmLib(options.projectName, outDir);
|
|
29
|
+
spinner.stop('LLM library created');
|
|
30
|
+
if (options.backend === 'convex') {
|
|
31
|
+
spinner.start('Generating Convex backend…');
|
|
32
|
+
await generateConvex(options.projectName, outDir);
|
|
33
|
+
spinner.stop('Convex backend created');
|
|
34
|
+
}
|
|
35
|
+
else {
|
|
36
|
+
spinner.start('Generating Supabase backend…');
|
|
37
|
+
await generateSupabase(options.projectName, outDir);
|
|
38
|
+
spinner.stop('Supabase backend created');
|
|
39
|
+
}
|
|
40
|
+
spinner.start('Generating GitHub Actions workflows…');
|
|
41
|
+
await generateGithubActions(options.projectName, outDir);
|
|
42
|
+
spinner.stop('GitHub Actions workflows created');
|
|
43
|
+
}
|
|
44
|
+
catch (err) {
|
|
45
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
46
|
+
clack.log.error(message);
|
|
47
|
+
throw err;
|
|
48
|
+
}
|
|
49
|
+
clack.log.success([
|
|
50
|
+
`✅ Project "${options.projectName}" scaffolded successfully!`,
|
|
51
|
+
'',
|
|
52
|
+
'Next steps:',
|
|
53
|
+
` cd ${options.projectName}`,
|
|
54
|
+
' npm install',
|
|
55
|
+
' npx nx run-many --target=build --all',
|
|
56
|
+
].join('\n'));
|
|
57
|
+
}
|
|
58
|
+
//# sourceMappingURL=create.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"create.js","sourceRoot":"","sources":["../../src/cli/create.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generates a Convex backend at `outDir/convex/` and injects the Convex
|
|
3
|
+
* client shim into `outDir/apps/web/src/lib/backend.ts`.
|
|
4
|
+
*
|
|
5
|
+
* Also adds `convex` to `outDir/apps/web/package.json` dependencies.
|
|
6
|
+
*/
|
|
7
|
+
export declare function generateConvex(projectName: string, outDir: string): Promise<void>;
|
|
8
|
+
//# sourceMappingURL=convex.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"convex.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/convex.ts"],"names":[],"mappings":"AA6CA;;;;;GAKG;AACH,wBAAsB,cAAc,CAClC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAuBf"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, stat, writeFile } from 'node:fs/promises';
|
|
2
|
+
import { dirname, join } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
const TEMPLATE_DIR = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', 'backend', 'convex');
|
|
5
|
+
const CONVEX_SHIM = `// Auto-generated — do not edit
|
|
6
|
+
export { ConvexProvider, useConvex, useQuery, useMutation } from 'convex/react';
|
|
7
|
+
`;
|
|
8
|
+
function interpolate(content, projectName) {
|
|
9
|
+
return content.replaceAll('{{projectName}}', projectName);
|
|
10
|
+
}
|
|
11
|
+
async function copyInterpolated(src, dest, projectName) {
|
|
12
|
+
await mkdir(dest, { recursive: true });
|
|
13
|
+
const entries = await readdir(src, { withFileTypes: true });
|
|
14
|
+
for (const entry of entries) {
|
|
15
|
+
const srcPath = join(src, entry.name);
|
|
16
|
+
const destPath = join(dest, entry.name);
|
|
17
|
+
if (entry.isDirectory()) {
|
|
18
|
+
await copyInterpolated(srcPath, destPath, projectName);
|
|
19
|
+
}
|
|
20
|
+
else {
|
|
21
|
+
const resolvedDest = destPath.endsWith('.tpl')
|
|
22
|
+
? destPath.slice(0, -4)
|
|
23
|
+
: destPath;
|
|
24
|
+
const raw = await readFile(srcPath, 'utf8');
|
|
25
|
+
await writeFile(resolvedDest, interpolate(raw, projectName), 'utf8');
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Generates a Convex backend at `outDir/convex/` and injects the Convex
|
|
31
|
+
* client shim into `outDir/apps/web/src/lib/backend.ts`.
|
|
32
|
+
*
|
|
33
|
+
* Also adds `convex` to `outDir/apps/web/package.json` dependencies.
|
|
34
|
+
*/
|
|
35
|
+
export async function generateConvex(projectName, outDir) {
|
|
36
|
+
const templateStat = await stat(TEMPLATE_DIR).catch(() => null);
|
|
37
|
+
if (!templateStat?.isDirectory()) {
|
|
38
|
+
throw new Error(`Convex backend template directory not found: ${TEMPLATE_DIR}`);
|
|
39
|
+
}
|
|
40
|
+
const destDir = join(outDir, 'convex');
|
|
41
|
+
await copyInterpolated(TEMPLATE_DIR, destDir, projectName);
|
|
42
|
+
const libDir = join(outDir, 'apps', 'web', 'src', 'lib');
|
|
43
|
+
await mkdir(libDir, { recursive: true });
|
|
44
|
+
await writeFile(join(libDir, 'backend.ts'), CONVEX_SHIM, 'utf8');
|
|
45
|
+
const pkgPath = join(outDir, 'apps', 'web', 'package.json');
|
|
46
|
+
const pkgRaw = await readFile(pkgPath, 'utf8');
|
|
47
|
+
const pkg = JSON.parse(pkgRaw);
|
|
48
|
+
pkg.dependencies = { ...pkg.dependencies, convex: 'latest' };
|
|
49
|
+
await writeFile(pkgPath, JSON.stringify(pkg, null, 2) + '\n', 'utf8');
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=convex.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"convex.js","sourceRoot":"","sources":["../../../src/cli/generators/convex.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generate a GitHub Actions workflow at `outDir/.github/workflows/deploy.yml`.
|
|
3
|
+
* Replaces `{{projectName}}` in the workflow template with the given project name.
|
|
4
|
+
*/
|
|
5
|
+
export declare function generateGithubActions(projectName: string, outDir: string): Promise<void>;
|
|
6
|
+
//# sourceMappingURL=github-actions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"github-actions.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/github-actions.ts"],"names":[],"mappings":"AAaA;;;GAGG;AACH,wBAAsB,qBAAqB,CACzC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAOf"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { mkdir, readFile, writeFile } from 'node:fs/promises';
|
|
2
|
+
import { join, dirname } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
const TEMPLATE_PATH = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', '.github', 'workflows', 'deploy.yml');
|
|
5
|
+
/**
|
|
6
|
+
* Generate a GitHub Actions workflow at `outDir/.github/workflows/deploy.yml`.
|
|
7
|
+
* Replaces `{{projectName}}` in the workflow template with the given project name.
|
|
8
|
+
*/
|
|
9
|
+
export async function generateGithubActions(projectName, outDir) {
|
|
10
|
+
const raw = await readFile(TEMPLATE_PATH, 'utf8');
|
|
11
|
+
const content = raw.replaceAll('{{projectName}}', projectName);
|
|
12
|
+
const destDir = join(outDir, '.github', 'workflows');
|
|
13
|
+
await mkdir(destDir, { recursive: true });
|
|
14
|
+
await writeFile(join(destDir, 'deploy.yml'), content, 'utf8');
|
|
15
|
+
}
|
|
16
|
+
//# sourceMappingURL=github-actions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"github-actions.js","sourceRoot":"","sources":["../../../src/cli/generators/github-actions.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AAC9D,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,aAAa,GAAG,IAAI,CACxB,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EACvC,IAAI,EACJ,WAAW,EACX,SAAS,EACT,WAAW,EACX,YAAY,CACb,CAAC;AAEF;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,qBAAqB,CACzC,WAAmB,EACnB,MAAc;IAEd,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC;IAClD,MAAM,OAAO,GAAG,GAAG,CAAC,UAAU,CAAC,iBAAiB,EAAE,WAAW,CAAC,CAAC;IAE/D,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,EAAE,SAAS,EAAE,WAAW,CAAC,CAAC;IACrD,MAAM,KAAK,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,MAAM,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,YAAY,CAAC,EAAE,OAAO,EAAE,MAAM,CAAC,CAAC;AAChE,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generates an Ionic + Capacitor mobile app at `outDir/apps/mobile/` by
|
|
3
|
+
* copying `src/cli/templates/apps/mobile/` and interpolating tokens.
|
|
4
|
+
*
|
|
5
|
+
* Token substitutions applied to all file contents:
|
|
6
|
+
* - `{{projectName}}` → `projectName`
|
|
7
|
+
* - `{{scope}}` → `@monkilab`
|
|
8
|
+
*
|
|
9
|
+
* The resulting `capacitor.config.ts` will have:
|
|
10
|
+
* `appId: 'com.monkilab.<projectName>'`
|
|
11
|
+
*/
|
|
12
|
+
export declare function generateIonicApp(projectName: string, outDir: string): Promise<void>;
|
|
13
|
+
//# sourceMappingURL=ionic.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ionic.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/ionic.ts"],"names":[],"mappings":"AAsDA;;;;;;;;;;GAUG;AACH,wBAAsB,gBAAgB,CACpC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAUf"}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, writeFile, stat } from 'node:fs/promises';
|
|
2
|
+
import { join, dirname } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
const TEMPLATE_DIR = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', 'apps', 'mobile');
|
|
5
|
+
const SCOPE = '@monkilab';
|
|
6
|
+
/**
|
|
7
|
+
* Replaces `{{projectName}}` and `{{scope}}` placeholders in a string.
|
|
8
|
+
*/
|
|
9
|
+
function interpolate(content, projectName) {
|
|
10
|
+
return content
|
|
11
|
+
.replaceAll('{{projectName}}', projectName)
|
|
12
|
+
.replaceAll('{{scope}}', SCOPE);
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Recursively copies a directory tree into `dest`, interpolating tokens in all
|
|
16
|
+
* text file contents.
|
|
17
|
+
*/
|
|
18
|
+
async function copyInterpolated(src, dest, projectName) {
|
|
19
|
+
await mkdir(dest, { recursive: true });
|
|
20
|
+
const entries = await readdir(src, { withFileTypes: true });
|
|
21
|
+
for (const entry of entries) {
|
|
22
|
+
const srcPath = join(src, entry.name);
|
|
23
|
+
const destPath = join(dest, entry.name);
|
|
24
|
+
if (entry.isDirectory()) {
|
|
25
|
+
await copyInterpolated(srcPath, destPath, projectName);
|
|
26
|
+
}
|
|
27
|
+
else {
|
|
28
|
+
// Strip the `.tpl` suffix used to prevent the root tsconfig from
|
|
29
|
+
// accidentally compiling template source files.
|
|
30
|
+
const resolvedDest = destPath.endsWith('.tpl')
|
|
31
|
+
? destPath.slice(0, -4)
|
|
32
|
+
: destPath;
|
|
33
|
+
const raw = await readFile(srcPath, 'utf8');
|
|
34
|
+
await writeFile(resolvedDest, interpolate(raw, projectName), 'utf8');
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Generates an Ionic + Capacitor mobile app at `outDir/apps/mobile/` by
|
|
40
|
+
* copying `src/cli/templates/apps/mobile/` and interpolating tokens.
|
|
41
|
+
*
|
|
42
|
+
* Token substitutions applied to all file contents:
|
|
43
|
+
* - `{{projectName}}` → `projectName`
|
|
44
|
+
* - `{{scope}}` → `@monkilab`
|
|
45
|
+
*
|
|
46
|
+
* The resulting `capacitor.config.ts` will have:
|
|
47
|
+
* `appId: 'com.monkilab.<projectName>'`
|
|
48
|
+
*/
|
|
49
|
+
export async function generateIonicApp(projectName, outDir) {
|
|
50
|
+
const mobileTemplateStat = await stat(TEMPLATE_DIR).catch(() => null);
|
|
51
|
+
if (!mobileTemplateStat?.isDirectory()) {
|
|
52
|
+
throw new Error(`Ionic mobile template directory not found: ${TEMPLATE_DIR}`);
|
|
53
|
+
}
|
|
54
|
+
const destDir = join(outDir, 'apps', 'mobile');
|
|
55
|
+
await copyInterpolated(TEMPLATE_DIR, destDir, projectName);
|
|
56
|
+
}
|
|
57
|
+
//# sourceMappingURL=ionic.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ionic.js","sourceRoot":"","sources":["../../../src/cli/generators/ionic.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAC7E,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,YAAY,GAAG,IAAI,CACvB,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EACvC,IAAI,EACJ,WAAW,EACX,MAAM,EACN,QAAQ,CACT,CAAC;AAEF,MAAM,KAAK,GAAG,WAAW,CAAC;AAE1B;;GAEG;AACH,SAAS,WAAW,CAAC,OAAe,EAAE,WAAmB;IACvD,OAAO,OAAO;SACX,UAAU,CAAC,iBAAiB,EAAE,WAAW,CAAC;SAC1C,UAAU,CAAC,WAAW,EAAE,KAAK,CAAC,CAAC;AACpC,CAAC;AAED;;;GAGG;AACH,KAAK,UAAU,gBAAgB,CAC7B,GAAW,EACX,IAAY,EACZ,WAAmB;IAEnB,MAAM,KAAK,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEvC,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAE5D,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;QAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QAExC,IAAI,KAAK,CAAC,WAAW,EAAE,EAAE,CAAC;YACxB,MAAM,gBAAgB,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC,CAAC;QACzD,CAAC;aAAM,CAAC;YACN,iEAAiE;YACjE,gDAAgD;YAChD,MAAM,YAAY,GAAG,QAAQ,CAAC,QAAQ,CAAC,MAAM,CAAC;gBAC5C,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;gBACvB,CAAC,CAAC,QAAQ,CAAC;YACb,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;YAC5C,MAAM,SAAS,CAAC,YAAY,EAAE,WAAW,CAAC,GAAG,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,CAAC;QACvE,CAAC;IACH,CAAC;AACH,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CACpC,WAAmB,EACnB,MAAc;IAEd,MAAM,kBAAkB,GAAG,MAAM,IAAI,CAAC,YAAY,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC;IACtE,IAAI,CAAC,kBAAkB,EAAE,WAAW,EAAE,EAAE,CAAC;QACvC,MAAM,IAAI,KAAK,CACb,8CAA8C,YAAY,EAAE,CAC7D,CAAC;IACJ,CAAC;IAED,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC;IAC/C,MAAM,gBAAgB,CAAC,YAAY,EAAE,OAAO,EAAE,WAAW,CAAC,CAAC;AAC7D,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generate the LLM library package under `outDir/packages/llm/`.
|
|
3
|
+
*
|
|
4
|
+
* Copies templates from `src/cli/templates/packages/llm/`, replacing
|
|
5
|
+
* `{{projectName}}` and `{{scope}}` tokens in all file contents.
|
|
6
|
+
* The output `package.json` will use the scoped name
|
|
7
|
+
* `@monkilab/<projectName>-llm`.
|
|
8
|
+
*/
|
|
9
|
+
export declare function generateLlmLib(projectName: string, outDir: string): Promise<void>;
|
|
10
|
+
//# sourceMappingURL=llm-lib.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"llm-lib.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/llm-lib.ts"],"names":[],"mappings":"AA0CA;;;;;;;GAOG;AACH,wBAAsB,cAAc,CAClC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAGf"}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, writeFile } from 'node:fs/promises';
|
|
2
|
+
import { join, dirname } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
const TEMPLATE_DIR = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', 'packages', 'llm');
|
|
5
|
+
const SCOPE = '@monkilab';
|
|
6
|
+
function interpolate(content, projectName) {
|
|
7
|
+
return content
|
|
8
|
+
.replaceAll('{{projectName}}', projectName)
|
|
9
|
+
.replaceAll('{{scope}}', SCOPE);
|
|
10
|
+
}
|
|
11
|
+
async function copyInterpolated(src, dest, projectName) {
|
|
12
|
+
await mkdir(dest, { recursive: true });
|
|
13
|
+
const entries = await readdir(src, { withFileTypes: true });
|
|
14
|
+
for (const entry of entries) {
|
|
15
|
+
const srcPath = join(src, entry.name);
|
|
16
|
+
const destPath = join(dest, entry.name);
|
|
17
|
+
if (entry.isDirectory()) {
|
|
18
|
+
await copyInterpolated(srcPath, destPath, projectName);
|
|
19
|
+
}
|
|
20
|
+
else {
|
|
21
|
+
const raw = await readFile(srcPath, 'utf8');
|
|
22
|
+
await writeFile(destPath, interpolate(raw, projectName), 'utf8');
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Generate the LLM library package under `outDir/packages/llm/`.
|
|
28
|
+
*
|
|
29
|
+
* Copies templates from `src/cli/templates/packages/llm/`, replacing
|
|
30
|
+
* `{{projectName}}` and `{{scope}}` tokens in all file contents.
|
|
31
|
+
* The output `package.json` will use the scoped name
|
|
32
|
+
* `@monkilab/<projectName>-llm`.
|
|
33
|
+
*/
|
|
34
|
+
export async function generateLlmLib(projectName, outDir) {
|
|
35
|
+
const dest = join(outDir, 'packages', 'llm');
|
|
36
|
+
await copyInterpolated(TEMPLATE_DIR, dest, projectName);
|
|
37
|
+
}
|
|
38
|
+
//# sourceMappingURL=llm-lib.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"llm-lib.js","sourceRoot":"","sources":["../../../src/cli/generators/llm-lib.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AACvE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,YAAY,GAAG,IAAI,CACvB,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EACvC,IAAI,EACJ,WAAW,EACX,UAAU,EACV,KAAK,CACN,CAAC;AAEF,MAAM,KAAK,GAAG,WAAW,CAAC;AAE1B,SAAS,WAAW,CAAC,OAAe,EAAE,WAAmB;IACvD,OAAO,OAAO;SACX,UAAU,CAAC,iBAAiB,EAAE,WAAW,CAAC;SAC1C,UAAU,CAAC,WAAW,EAAE,KAAK,CAAC,CAAC;AACpC,CAAC;AAED,KAAK,UAAU,gBAAgB,CAC7B,GAAW,EACX,IAAY,EACZ,WAAmB;IAEnB,MAAM,KAAK,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEvC,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAE5D,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;QAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QAExC,IAAI,KAAK,CAAC,WAAW,EAAE,EAAE,CAAC;YACxB,MAAM,gBAAgB,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC,CAAC;QACzD,CAAC;aAAM,CAAC;YACN,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;YAC5C,MAAM,SAAS,CAAC,QAAQ,EAAE,WAAW,CAAC,GAAG,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,CAAC;QACnE,CAAC;IACH,CAAC;AACH,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CAClC,WAAmB,EACnB,MAAc;IAEd,MAAM,IAAI,GAAG,IAAI,CAAC,MAAM,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;IAC7C,MAAM,gBAAgB,CAAC,YAAY,EAAE,IAAI,EAAE,WAAW,CAAC,CAAC;AAC1D,CAAC"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generates a Next.js 15 web app at `outDir/apps/web/` by copying
|
|
3
|
+
* `src/cli/templates/apps/web/` and interpolating tokens.
|
|
4
|
+
*
|
|
5
|
+
* Token substitutions applied to all file contents:
|
|
6
|
+
* - `{{projectName}}` → `projectName`
|
|
7
|
+
* - `{{scope}}` → `@monkilab`
|
|
8
|
+
*
|
|
9
|
+
* The generated `apps/web/package.json` declares:
|
|
10
|
+
* - `next@^15.0.0`, `tailwindcss@^4.0.0`, `jest` with `ts-jest`, `@playwright/test`
|
|
11
|
+
*
|
|
12
|
+
* Styling uses Tailwind's base reset only — no color values, design tokens,
|
|
13
|
+
* or layout CSS are added.
|
|
14
|
+
*/
|
|
15
|
+
export declare function generateNextjsApp(projectName: string, outDir: string): Promise<void>;
|
|
16
|
+
//# sourceMappingURL=nextjs.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nextjs.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/nextjs.ts"],"names":[],"mappings":"AAqDA;;;;;;;;;;;;;GAaG;AACH,wBAAsB,iBAAiB,CACrC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAUf"}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, writeFile, stat } from 'node:fs/promises';
|
|
2
|
+
import { join, dirname } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
const TEMPLATE_DIR = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', 'apps', 'web');
|
|
5
|
+
const SCOPE = '@monkilab';
|
|
6
|
+
/**
|
|
7
|
+
* Replaces `{{projectName}}` and `{{scope}}` placeholders in a string.
|
|
8
|
+
*/
|
|
9
|
+
function interpolate(content, projectName) {
|
|
10
|
+
return content
|
|
11
|
+
.replaceAll('{{projectName}}', projectName)
|
|
12
|
+
.replaceAll('{{scope}}', SCOPE);
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Recursively copies a directory tree into `dest`, interpolating tokens in all
|
|
16
|
+
* text file contents. `.tpl` suffixes are stripped from destination filenames
|
|
17
|
+
* so that template TypeScript/TSX files are not compiled by the root tsconfig.
|
|
18
|
+
*/
|
|
19
|
+
async function copyInterpolated(src, dest, projectName) {
|
|
20
|
+
await mkdir(dest, { recursive: true });
|
|
21
|
+
const entries = await readdir(src, { withFileTypes: true });
|
|
22
|
+
for (const entry of entries) {
|
|
23
|
+
const srcPath = join(src, entry.name);
|
|
24
|
+
const destPath = join(dest, entry.name);
|
|
25
|
+
if (entry.isDirectory()) {
|
|
26
|
+
await copyInterpolated(srcPath, destPath, projectName);
|
|
27
|
+
}
|
|
28
|
+
else {
|
|
29
|
+
const resolvedDest = destPath.endsWith('.tpl')
|
|
30
|
+
? destPath.slice(0, -4)
|
|
31
|
+
: destPath;
|
|
32
|
+
const raw = await readFile(srcPath, 'utf8');
|
|
33
|
+
await writeFile(resolvedDest, interpolate(raw, projectName), 'utf8');
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Generates a Next.js 15 web app at `outDir/apps/web/` by copying
|
|
39
|
+
* `src/cli/templates/apps/web/` and interpolating tokens.
|
|
40
|
+
*
|
|
41
|
+
* Token substitutions applied to all file contents:
|
|
42
|
+
* - `{{projectName}}` → `projectName`
|
|
43
|
+
* - `{{scope}}` → `@monkilab`
|
|
44
|
+
*
|
|
45
|
+
* The generated `apps/web/package.json` declares:
|
|
46
|
+
* - `next@^15.0.0`, `tailwindcss@^4.0.0`, `jest` with `ts-jest`, `@playwright/test`
|
|
47
|
+
*
|
|
48
|
+
* Styling uses Tailwind's base reset only — no color values, design tokens,
|
|
49
|
+
* or layout CSS are added.
|
|
50
|
+
*/
|
|
51
|
+
export async function generateNextjsApp(projectName, outDir) {
|
|
52
|
+
const templateStat = await stat(TEMPLATE_DIR).catch(() => null);
|
|
53
|
+
if (!templateStat?.isDirectory()) {
|
|
54
|
+
throw new Error(`Next.js web template directory not found: ${TEMPLATE_DIR}`);
|
|
55
|
+
}
|
|
56
|
+
const destDir = join(outDir, 'apps', 'web');
|
|
57
|
+
await copyInterpolated(TEMPLATE_DIR, destDir, projectName);
|
|
58
|
+
}
|
|
59
|
+
//# sourceMappingURL=nextjs.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nextjs.js","sourceRoot":"","sources":["../../../src/cli/generators/nextjs.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAC7E,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,YAAY,GAAG,IAAI,CACvB,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EACvC,IAAI,EACJ,WAAW,EACX,MAAM,EACN,KAAK,CACN,CAAC;AAEF,MAAM,KAAK,GAAG,WAAW,CAAC;AAE1B;;GAEG;AACH,SAAS,WAAW,CAAC,OAAe,EAAE,WAAmB;IACvD,OAAO,OAAO;SACX,UAAU,CAAC,iBAAiB,EAAE,WAAW,CAAC;SAC1C,UAAU,CAAC,WAAW,EAAE,KAAK,CAAC,CAAC;AACpC,CAAC;AAED;;;;GAIG;AACH,KAAK,UAAU,gBAAgB,CAC7B,GAAW,EACX,IAAY,EACZ,WAAmB;IAEnB,MAAM,KAAK,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEvC,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAE5D,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;QAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QAExC,IAAI,KAAK,CAAC,WAAW,EAAE,EAAE,CAAC;YACxB,MAAM,gBAAgB,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC,CAAC;QACzD,CAAC;aAAM,CAAC;YACN,MAAM,YAAY,GAAG,QAAQ,CAAC,QAAQ,CAAC,MAAM,CAAC;gBAC5C,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;gBACvB,CAAC,CAAC,QAAQ,CAAC;YACb,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;YAC5C,MAAM,SAAS,CAAC,YAAY,EAAE,WAAW,CAAC,GAAG,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,CAAC;QACvE,CAAC;IACH,CAAC;AACH,CAAC;AAED;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,KAAK,UAAU,iBAAiB,CACrC,WAAmB,EACnB,MAAc;IAEd,MAAM,YAAY,GAAG,MAAM,IAAI,CAAC,YAAY,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC;IAChE,IAAI,CAAC,YAAY,EAAE,WAAW,EAAE,EAAE,CAAC;QACjC,MAAM,IAAI,KAAK,CACb,6CAA6C,YAAY,EAAE,CAC5D,CAAC;IACJ,CAAC;IAED,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,CAAC,CAAC;IAC5C,MAAM,gBAAgB,CAAC,YAAY,EAAE,OAAO,EAAE,WAAW,CAAC,CAAC;AAC7D,CAAC"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generate a new Nx workspace at `outDir` for the given `projectName`.
|
|
3
|
+
*
|
|
4
|
+
* Throws if `outDir` already exists to prevent accidental overwrites.
|
|
5
|
+
*/
|
|
6
|
+
export declare function generateNxWorkspace(projectName: string, outDir: string): Promise<void>;
|
|
7
|
+
//# sourceMappingURL=nx.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nx.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/nx.ts"],"names":[],"mappings":"AA+CA;;;;GAIG;AACH,wBAAsB,mBAAmB,CACvC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CAwBf"}
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, writeFile, stat } from 'node:fs/promises';
|
|
2
|
+
import { join, dirname } from 'node:path';
|
|
3
|
+
import { fileURLToPath } from 'node:url';
|
|
4
|
+
import { existsSync } from 'node:fs';
|
|
5
|
+
const TEMPLATE_DIR = join(dirname(fileURLToPath(import.meta.url)), '..', 'templates', 'nx');
|
|
6
|
+
const EMPTY_STUBS = ['apps', 'packages', 'templates', 'docs'];
|
|
7
|
+
/**
|
|
8
|
+
* Interpolates `{{projectName}}` placeholders in a string.
|
|
9
|
+
*/
|
|
10
|
+
function interpolate(content, projectName) {
|
|
11
|
+
return content.replaceAll('{{projectName}}', projectName);
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Recursively copy a directory tree, interpolating `{{projectName}}` in all
|
|
15
|
+
* text file contents.
|
|
16
|
+
*/
|
|
17
|
+
async function copyInterpolated(src, dest, projectName) {
|
|
18
|
+
await mkdir(dest, { recursive: true });
|
|
19
|
+
const entries = await readdir(src, { withFileTypes: true });
|
|
20
|
+
for (const entry of entries) {
|
|
21
|
+
const srcPath = join(src, entry.name);
|
|
22
|
+
const destPath = join(dest, entry.name);
|
|
23
|
+
if (entry.isDirectory()) {
|
|
24
|
+
await copyInterpolated(srcPath, destPath, projectName);
|
|
25
|
+
}
|
|
26
|
+
else {
|
|
27
|
+
const raw = await readFile(srcPath, 'utf8');
|
|
28
|
+
await writeFile(destPath, interpolate(raw, projectName), 'utf8');
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Generate a new Nx workspace at `outDir` for the given `projectName`.
|
|
34
|
+
*
|
|
35
|
+
* Throws if `outDir` already exists to prevent accidental overwrites.
|
|
36
|
+
*/
|
|
37
|
+
export async function generateNxWorkspace(projectName, outDir) {
|
|
38
|
+
if (existsSync(outDir)) {
|
|
39
|
+
throw new Error(`Output directory already exists: ${outDir}`);
|
|
40
|
+
}
|
|
41
|
+
await mkdir(outDir, { recursive: true });
|
|
42
|
+
// Check templates directory exists before attempting to copy
|
|
43
|
+
let templateExists = false;
|
|
44
|
+
try {
|
|
45
|
+
const s = await stat(TEMPLATE_DIR);
|
|
46
|
+
templateExists = s.isDirectory();
|
|
47
|
+
}
|
|
48
|
+
catch {
|
|
49
|
+
// template dir absent — skip file copy, stubs still created below
|
|
50
|
+
}
|
|
51
|
+
if (templateExists) {
|
|
52
|
+
await copyInterpolated(TEMPLATE_DIR, outDir, projectName);
|
|
53
|
+
}
|
|
54
|
+
// Ensure required empty stub directories always exist
|
|
55
|
+
for (const stub of EMPTY_STUBS) {
|
|
56
|
+
await mkdir(join(outDir, stub), { recursive: true });
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
//# sourceMappingURL=nx.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nx.js","sourceRoot":"","sources":["../../../src/cli/generators/nx.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAC7E,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AACzC,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAErC,MAAM,YAAY,GAAG,IAAI,CACvB,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EACvC,IAAI,EACJ,WAAW,EACX,IAAI,CACL,CAAC;AAEF,MAAM,WAAW,GAAG,CAAC,MAAM,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,CAAC,CAAC;AAE9D;;GAEG;AACH,SAAS,WAAW,CAAC,OAAe,EAAE,WAAmB;IACvD,OAAO,OAAO,CAAC,UAAU,CAAC,iBAAiB,EAAE,WAAW,CAAC,CAAC;AAC5D,CAAC;AAED;;;GAGG;AACH,KAAK,UAAU,gBAAgB,CAC7B,GAAW,EACX,IAAY,EACZ,WAAmB;IAEnB,MAAM,KAAK,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEvC,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAE5D,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;QAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;QAExC,IAAI,KAAK,CAAC,WAAW,EAAE,EAAE,CAAC;YACxB,MAAM,gBAAgB,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC,CAAC;QACzD,CAAC;aAAM,CAAC;YACN,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;YAC5C,MAAM,SAAS,CAAC,QAAQ,EAAE,WAAW,CAAC,GAAG,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,CAAC;QACnE,CAAC;IACH,CAAC;AACH,CAAC;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,mBAAmB,CACvC,WAAmB,EACnB,MAAc;IAEd,IAAI,UAAU,CAAC,MAAM,CAAC,EAAE,CAAC;QACvB,MAAM,IAAI,KAAK,CAAC,oCAAoC,MAAM,EAAE,CAAC,CAAC;IAChE,CAAC;IAED,MAAM,KAAK,CAAC,MAAM,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAEzC,6DAA6D;IAC7D,IAAI,cAAc,GAAG,KAAK,CAAC;IAC3B,IAAI,CAAC;QACH,MAAM,CAAC,GAAG,MAAM,IAAI,CAAC,YAAY,CAAC,CAAC;QACnC,cAAc,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;IACnC,CAAC;IAAC,MAAM,CAAC;QACP,kEAAkE;IACpE,CAAC;IAED,IAAI,cAAc,EAAE,CAAC;QACnB,MAAM,gBAAgB,CAAC,YAAY,EAAE,MAAM,EAAE,WAAW,CAAC,CAAC;IAC5D,CAAC;IAED,sDAAsD;IACtD,KAAK,MAAM,IAAI,IAAI,WAAW,EAAE,CAAC;QAC/B,MAAM,KAAK,CAAC,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IACvD,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generates a Supabase backend at `outDir/supabase/` and injects the Supabase
|
|
3
|
+
* client shim into `outDir/apps/web/src/lib/backend.ts`.
|
|
4
|
+
*
|
|
5
|
+
* Also adds `@supabase/supabase-js` to `outDir/apps/web/package.json` dependencies.
|
|
6
|
+
*/
|
|
7
|
+
export declare function generateSupabase(projectName: string, outDir: string): Promise<void>;
|
|
8
|
+
//# sourceMappingURL=supabase.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"supabase.d.ts","sourceRoot":"","sources":["../../../src/cli/generators/supabase.ts"],"names":[],"mappings":"AA6CA;;;;;GAKG;AACH,wBAAsB,gBAAgB,CACpC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC,CA0Bf"}
|