@sei-js/create-sei 1.0.1 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +5 -4
  3. package/dist/extensions/precompiles/src/components/default/index.tsx +44 -51
  4. package/dist/main.js +112 -34
  5. package/dist/templates/next-template/.env.example +1 -1
  6. package/dist/templates/next-template/README.md +55 -27
  7. package/dist/templates/next-template/biome.json +3 -4
  8. package/dist/templates/next-template/gitignore +41 -0
  9. package/dist/templates/next-template/next.config.mjs +9 -6
  10. package/dist/templates/next-template/package.json +36 -27
  11. package/dist/templates/next-template/public/brand/powered-by-sei-light.png +0 -0
  12. package/dist/templates/next-template/public/brand/sei-lockup-light.svg +7 -0
  13. package/dist/templates/next-template/public/brand/sei-mark.png +0 -0
  14. package/dist/templates/next-template/src/app/development/page.tsx +29 -30
  15. package/dist/templates/next-template/src/app/favicon.ico/route.ts +3 -0
  16. package/dist/templates/next-template/src/app/globals.css +40 -3
  17. package/dist/templates/next-template/src/app/layout.tsx +14 -13
  18. package/dist/templates/next-template/src/app/page.tsx +3 -3
  19. package/dist/templates/next-template/src/app/resources/page.tsx +34 -51
  20. package/dist/templates/next-template/src/app/resources/resources.ts +19 -32
  21. package/dist/templates/next-template/src/components/default/examples.ts +4 -7
  22. package/dist/templates/next-template/src/components/default/index.tsx +46 -46
  23. package/dist/templates/next-template/src/components/index.ts +3 -3
  24. package/dist/templates/next-template/src/components/landing/index.tsx +19 -97
  25. package/dist/templates/next-template/src/components/providers/index.ts +1 -1
  26. package/dist/templates/next-template/src/components/providers/providers.tsx +19 -25
  27. package/dist/templates/next-template/src/components/shell/index.ts +1 -1
  28. package/dist/templates/next-template/src/components/shell/shell.tsx +14 -7
  29. package/dist/templates/next-template/src/theme.ts +1 -0
  30. package/package.json +20 -9
  31. package/.rsyncignore +0 -11
  32. package/CHANGELOG.md +0 -131
  33. package/biome.json +0 -8
  34. package/dist/extensions/precompiles/package.json +0 -44
  35. package/dist/main.test.js +0 -34
  36. package/dist/templates/next-template/public/favicon.ico +0 -0
  37. package/extensions/precompiles/package.json +0 -44
  38. package/extensions/precompiles/src/components/default/index.tsx +0 -201
  39. package/jest.config.js +0 -14
  40. package/src/main.test.ts +0 -38
  41. package/src/main.ts +0 -159
  42. package/templates/next-template/.env.example +0 -8
  43. package/templates/next-template/.eslintrc.json +0 -1
  44. package/templates/next-template/.nvmrc +0 -1
  45. package/templates/next-template/README.md +0 -54
  46. package/templates/next-template/biome.json +0 -56
  47. package/templates/next-template/next-env.d.ts +0 -5
  48. package/templates/next-template/next.config.mjs +0 -17
  49. package/templates/next-template/package.json +0 -46
  50. package/templates/next-template/postcss.config.mjs +0 -6
  51. package/templates/next-template/public/favicon.ico +0 -0
  52. package/templates/next-template/src/app/development/page.tsx +0 -260
  53. package/templates/next-template/src/app/globals.css +0 -16
  54. package/templates/next-template/src/app/layout.tsx +0 -30
  55. package/templates/next-template/src/app/page.tsx +0 -10
  56. package/templates/next-template/src/app/resources/page.tsx +0 -175
  57. package/templates/next-template/src/app/resources/resources.ts +0 -56
  58. package/templates/next-template/src/components/default/examples.ts +0 -63
  59. package/templates/next-template/src/components/default/index.tsx +0 -402
  60. package/templates/next-template/src/components/index.ts +0 -3
  61. package/templates/next-template/src/components/landing/index.tsx +0 -155
  62. package/templates/next-template/src/components/providers/index.ts +0 -1
  63. package/templates/next-template/src/components/providers/providers.tsx +0 -108
  64. package/templates/next-template/src/components/shell/index.ts +0 -1
  65. package/templates/next-template/src/components/shell/shell.tsx +0 -88
  66. package/templates/next-template/tailwind.config.js +0 -5
  67. package/templates/next-template/tsconfig.json +0 -27
  68. package/tsconfig.json +0 -19
package/CHANGELOG.md DELETED
@@ -1,131 +0,0 @@
1
- # @sei-js/create-sei-app
2
-
3
- ## 1.0.1
4
-
5
- ### Patch Changes
6
-
7
- - 2666156: Harden the workspace against the 2026-07-14 "Miasma RAT" AsyncAPI supply-chain incident by pinning `@asyncapi/*` packages to non-compromised versions via root `pnpm.overrides`.
8
-
9
- This stops a fresh install or lockfile regeneration from floating `@asyncapi/specs` up into the compromised `6.11.2` through the `mint` docs toolchain (`mint` → `@asyncapi/parser`). Resolved change: `@asyncapi/specs` `6.10.0` → `6.11.1`; `@asyncapi/generator`, `@asyncapi/generator-helpers`, and `@asyncapi/generator-components` are pinned preventively.
10
-
11
- No shipped code or public API changes in this package — this is a repository/CI hardening release.
12
-
13
- - 9168186: Improve the `next-template` runtime defaults generated by `create-sei`.
14
-
15
- - Add a `prebuild` Biome check and include Biome in template dev dependencies.
16
- - Configure Next.js to allow Sei CDN images and skip ESLint during builds.
17
- - Update provider and shell setup for improved chain/image handling.
18
- - Align template config/docs with current defaults (`.env.example`, `README`, Biome, Tailwind v4 config).
19
-
20
- ## 1.0.0
21
-
22
- ### Major Changes
23
-
24
- - 92fd8fd: Updated default template and added extensions
25
-
26
- ## 0.0.4
27
-
28
- ### Patch Changes
29
-
30
- - 848c236: Remove cosmos from templates
31
-
32
- ## 0.0.3
33
-
34
- ### Patch Changes
35
-
36
- - a64da08: Update README files in NPM
37
-
38
- ## 0.0.2
39
-
40
- ### Patch Changes
41
-
42
- - cd65a51: Fix broken NPM publish for all packages
43
-
44
- ## 0.0.1
45
-
46
- ### Patch Changes
47
-
48
- - d6e74ed: Update package structure and building of all @sei-js packages
49
-
50
- ## 0.0.0
51
-
52
- ### Major Changes
53
-
54
- - e3a4c8e: First release
55
-
56
- ## 0.0.0-internal-20240718212746
57
-
58
- ### Major Changes
59
-
60
- - test
61
-
62
- ## 0.0.0-internal-20240718212405
63
-
64
- ### Major Changes
65
-
66
- - test ver final
67
-
68
- ## 0.0.0-internal-20240717005255
69
-
70
- ### Major Changes
71
-
72
- - edit
73
-
74
- ## 0.0.0-internal-20240717005002
75
-
76
- ### Major Changes
77
-
78
- - with options
79
-
80
- ## 0.0.0-internal-20240717003256
81
-
82
- ### Major Changes
83
-
84
- - First version
85
-
86
- ## 0.0.0-internal-20240716075531
87
-
88
- ### Major Changes
89
-
90
- - first v
91
-
92
- ## 0.0.0-internal-20240716074905
93
-
94
- ### Major Changes
95
-
96
- - First version
97
-
98
- ## 0.0.0-internal-20240708205128
99
-
100
- ### Major Changes
101
-
102
- - first release
103
-
104
- ## 0.0.0-internal-20240708184136
105
-
106
- ### Major Changes
107
-
108
- - First release
109
-
110
- ## 0.0.0-internal-20240708170805
111
-
112
- ### Major Changes
113
-
114
- - release create sei
115
-
116
- ## 0.0.0-internal-20240708163140
117
-
118
- ### Major Changes
119
-
120
- - Update Templates
121
- - 0917789: Major release
122
-
123
- ## 0.0.0-internal-20240701161539
124
-
125
- ### Major Changes
126
-
127
- - 6b3cf5a: Instantiates the Create Sei App package
128
-
129
- ### Minor Changes
130
-
131
- - changes
package/biome.json DELETED
@@ -1,8 +0,0 @@
1
- {
2
- "$schema": "https://biomejs.dev/schemas/1.9.4/schema.json",
3
- "extends": ["../../biome.json"],
4
- "files": {
5
- "ignoreUnknown": false,
6
- "ignore": ["templates/**"]
7
- }
8
- }
@@ -1,44 +0,0 @@
1
- {
2
- "name": "template-next-create-sei-app-precompiles",
3
- "version": "0.1.0",
4
- "private": true,
5
- "scripts": {
6
- "dev": "next dev",
7
- "build": "next build",
8
- "start": "next start",
9
- "lint": "biome lint .",
10
- "lint:fix": "biome lint --write .",
11
- "format": "biome format --write .",
12
- "format:check": "biome format .",
13
- "check": "biome check .",
14
- "check:fix": "biome check --write .",
15
- "deploy": "vercel --prod"
16
- },
17
- "dependencies": {
18
- "@mantine/code-highlight": "^8.2.5",
19
- "@mantine/core": "^8.2.5",
20
- "@mantine/hooks": "^8.2.5",
21
- "@mantine/notifications": "^8.2.5",
22
- "@rainbow-me/rainbowkit": "^2.2.8",
23
- "@sei-js/precompiles": "^2.1.2",
24
- "@tabler/icons-react": "^3.34.1",
25
- "@tailwindcss/postcss": "^4.1.12",
26
- "@tanstack/react-query": "^5.85.3",
27
- "ethers": "^6.15.0",
28
- "next": "15.4.7",
29
- "pino-pretty": "^13.1.1",
30
- "react": "^19.1.1",
31
- "react-dom": "^19.1.1",
32
- "viem": "^2.34.0",
33
- "wagmi": "^2.16.4"
34
- },
35
- "devDependencies": {
36
- "@types/node": "^24.3.0",
37
- "@types/react": "^19.1.10",
38
- "@types/react-dom": "^19.1.7",
39
- "autoprefixer": "^10.4.21",
40
- "postcss": "^8.4.45",
41
- "tailwindcss": "^4.1.12",
42
- "typescript": "^5.9.2"
43
- }
44
- }
package/dist/main.test.js DELETED
@@ -1,34 +0,0 @@
1
- import { describe, test, expect, beforeEach, afterEach } from '@jest/globals';
2
- import { promises as fs } from 'node:fs';
3
- import path from 'node:path';
4
- describe('Extension System', () => {
5
- const testDir = path.join(process.cwd(), 'test-output');
6
- const extensionsDir = path.join(process.cwd(), 'extensions');
7
- beforeEach(async () => {
8
- // Clean up test directory
9
- try {
10
- await fs.rm(testDir, { recursive: true, force: true });
11
- }
12
- catch (e) {
13
- // Directory might not exist
14
- }
15
- await fs.mkdir(testDir, { recursive: true });
16
- });
17
- afterEach(async () => {
18
- // Clean up test directory
19
- try {
20
- await fs.rm(testDir, { recursive: true, force: true });
21
- }
22
- catch (e) {
23
- // Directory might not exist
24
- }
25
- });
26
- test('should list available extensions', async () => {
27
- const extensionExists = await fs.access(path.join(extensionsDir, 'precompiles'))
28
- .then(() => true)
29
- .catch(() => false);
30
- expect(extensionExists).toBe(true);
31
- const extensionFiles = await fs.readdir(extensionsDir);
32
- expect(extensionFiles).toContain('precompiles');
33
- });
34
- });
@@ -1,44 +0,0 @@
1
- {
2
- "name": "template-next-create-sei-app-precompiles",
3
- "version": "0.1.0",
4
- "private": true,
5
- "scripts": {
6
- "dev": "next dev",
7
- "build": "next build",
8
- "start": "next start",
9
- "lint": "biome lint .",
10
- "lint:fix": "biome lint --write .",
11
- "format": "biome format --write .",
12
- "format:check": "biome format .",
13
- "check": "biome check .",
14
- "check:fix": "biome check --write .",
15
- "deploy": "vercel --prod"
16
- },
17
- "dependencies": {
18
- "@mantine/code-highlight": "^8.2.5",
19
- "@mantine/core": "^8.2.5",
20
- "@mantine/hooks": "^8.2.5",
21
- "@mantine/notifications": "^8.2.5",
22
- "@rainbow-me/rainbowkit": "^2.2.8",
23
- "@sei-js/precompiles": "^2.1.2",
24
- "@tabler/icons-react": "^3.34.1",
25
- "@tailwindcss/postcss": "^4.1.12",
26
- "@tanstack/react-query": "^5.85.3",
27
- "ethers": "^6.15.0",
28
- "next": "15.4.7",
29
- "pino-pretty": "^13.1.1",
30
- "react": "^19.1.1",
31
- "react-dom": "^19.1.1",
32
- "viem": "^2.34.0",
33
- "wagmi": "^2.16.4"
34
- },
35
- "devDependencies": {
36
- "@types/node": "^24.3.0",
37
- "@types/react": "^19.1.10",
38
- "@types/react-dom": "^19.1.7",
39
- "autoprefixer": "^10.4.21",
40
- "postcss": "^8.4.45",
41
- "tailwindcss": "^4.1.12",
42
- "typescript": "^5.9.2"
43
- }
44
- }
@@ -1,201 +0,0 @@
1
- 'use client';
2
-
3
- import React from 'react';
4
- import { CodeHighlight } from '@mantine/code-highlight';
5
- import { ActionIcon, Badge, Button, Card, Collapse, Container, Flex, Group, Paper, Stack, Text, ThemeIcon, Title } from '@mantine/core';
6
- import { notifications } from '@mantine/notifications';
7
- import { BANK_PRECOMPILE_ADDRESS, VIEM_BANK_PRECOMPILE_ABI } from '@sei-js/precompiles';
8
- import { IconBulb, IconChevronDown, IconChevronUp, IconCopy, IconDatabase } from '@tabler/icons-react';
9
- import { useState } from 'react';
10
- import { type ReadContractParameters, formatEther } from 'viem';
11
- import { useAccount, usePublicClient } from 'wagmi';
12
-
13
- function Examples() {
14
- const [supply, setSupply] = useState('');
15
- const [showCode, setShowCode] = useState(false);
16
-
17
- const publicClient = usePublicClient();
18
- const { address } = useAccount();
19
-
20
- const formatLargeSeiNumber = (num: string, decimals: number): string => {
21
- if (num.length > 10) {
22
- return `${(Number(num) / 1000000 / 1000000000).toLocaleString(navigator.language, {
23
- minimumFractionDigits: decimals,
24
- maximumFractionDigits: decimals
25
- })} B`;
26
- }
27
- return (Number(num) / 1000000).toLocaleString(navigator.language);
28
- };
29
-
30
- const copyToClipboard = (text: string) => {
31
- try {
32
- navigator.clipboard.writeText(text).then(() => {
33
- notifications.show({
34
- title: 'Copied!',
35
- message: 'Code copied to clipboard',
36
- color: 'green'
37
- });
38
- });
39
- } catch (err) {
40
- console.error('Failed to copy text: ', err);
41
- notifications.show({
42
- title: 'Error',
43
- message: 'Failed to copy to clipboard',
44
- color: 'red'
45
- });
46
- }
47
- };
48
-
49
- const getSeiSupply = async () => {
50
- if (!publicClient) {
51
- return undefined;
52
- }
53
-
54
- const readContractParams: ReadContractParameters = {
55
- abi: VIEM_BANK_PRECOMPILE_ABI,
56
- address: BANK_PRECOMPILE_ADDRESS,
57
- functionName: 'supply',
58
- args: ['usei']
59
- };
60
-
61
- try {
62
- const result = await publicClient.readContract(readContractParams);
63
- setSupply((result as bigint).toString());
64
- } catch (error) {
65
- console.error('Error fetching supply:', error);
66
- notifications.show({
67
- title: 'Error',
68
- message: 'Failed to fetch SEI supply',
69
- color: 'red'
70
- });
71
- }
72
- };
73
-
74
- const codeExample = `// Sei Precompile Example - Bank Precompile
75
- import { BANK_PRECOMPILE_ADDRESS, VIEM_BANK_PRECOMPILE_ABI } from '@sei-js/precompiles';
76
- import { usePublicClient } from 'wagmi';
77
-
78
- const publicClient = usePublicClient();
79
-
80
- const getSeiSupply = async () => {
81
- const readContractParams = {
82
- abi: VIEM_BANK_PRECOMPILE_ABI,
83
- address: BANK_PRECOMPILE_ADDRESS,
84
- functionName: 'supply',
85
- args: ['usei'],
86
- };
87
-
88
- const result = await publicClient?.readContract(readContractParams);
89
- return (result as bigint).toString();
90
- };`;
91
-
92
- return (
93
- <Container size="xl" py="xl" pos="relative">
94
- <Stack gap="xl">
95
- {/* Header */}
96
- <div>
97
- <Group gap="md" align="center" mb="lg">
98
- <ThemeIcon size={48} radius="md" c="orange" variant="light">
99
- <IconBulb size={24} />
100
- </ThemeIcon>
101
- <div>
102
- <Title order={1} fw={700} c="gray.9">
103
- Sei Precompiles
104
- </Title>
105
- <Text size="lg" c="gray.6" mt={4}>
106
- Access native Sei blockchain functionality through EVM precompiles
107
- </Text>
108
- </div>
109
- </Group>
110
- </div>
111
-
112
- {/* Precompile Example Card */}
113
- <Card shadow="xs" p="lg" radius="md" withBorder>
114
- <Stack gap="md">
115
- <Flex justify="space-between" align="flex-start">
116
- <Stack gap="xs">
117
- <Group gap="md">
118
- <ThemeIcon size={40} radius="md" color="orange" variant="light">
119
- <IconDatabase size={20} />
120
- </ThemeIcon>
121
- <Title order={3} fw={600} c="gray.9">
122
- Bank Precompile
123
- </Title>
124
- </Group>
125
- <Text size="sm" c="gray.6">
126
- Query total SEI supply using Sei's native{' '}
127
- <Text component="a" href="https://www.docs.sei.io/dev-interoperability/precompiles/bank" target="_blank" c="orange" td="underline">
128
- Bank precompile
129
- </Text>
130
- </Text>
131
- </Stack>
132
- <Badge color="orange" variant="light" size="md" radius="md">
133
- precompiles
134
- </Badge>
135
- </Flex>
136
-
137
- <Paper p="md" radius="md" withBorder bg="gray.0">
138
- <Text size="xs" fw={500} c="gray.6">
139
- Total Supply
140
- </Text>
141
- <Flex justify="space-between" align="center">
142
- <Flex align="baseline" gap="xs">
143
- {supply ? (
144
- <>
145
- <Text fw={700} size="xl" c="gray.9" ff="monospace">
146
- {formatLargeSeiNumber(supply, 2)}
147
- </Text>
148
- <Text size="sm" c="gray.6" fw={500}>
149
- SEI
150
- </Text>
151
- </>
152
- ) : (
153
- <Paper px="sm" py={4} bg="white" radius="md" withBorder>
154
- <Flex align="baseline" gap="xs">
155
- <Text fw={700} size="xl" c="gray.5" ff="monospace">
156
- —
157
- </Text>
158
- <Text size="sm" c="gray.6" fw={500}>
159
- SEI
160
- </Text>
161
- </Flex>
162
- </Paper>
163
- )}
164
- </Flex>
165
- <Button onClick={getSeiSupply} size="sm" radius="md" variant="light" color="orange" leftSection={<IconDatabase size={14} />}>
166
- {supply ? 'Refresh' : 'Query Supply'}
167
- </Button>
168
- </Flex>
169
- </Paper>
170
-
171
- <Group justify="space-between" align="center" mt="sm">
172
- <Button
173
- variant="subtle"
174
- color="gray"
175
- size="sm"
176
- radius="md"
177
- leftSection={showCode ? <IconChevronUp size={14} /> : <IconChevronDown size={14} />}
178
- onClick={() => setShowCode(!showCode)}
179
- >
180
- {showCode ? 'Hide' : 'View'} Implementation
181
- </Button>
182
- {showCode && (
183
- <ActionIcon variant="subtle" color="gray" size="sm" radius="md" onClick={() => copyToClipboard(codeExample)}>
184
- <IconCopy size={14} />
185
- </ActionIcon>
186
- )}
187
- </Group>
188
-
189
- <Collapse in={showCode}>
190
- <Paper mt="sm" p="md" bg="gray.0" radius="md" withBorder>
191
- <CodeHighlight code={codeExample} language="tsx" withCopyButton={false} expandCodeLabel="" collapseCodeLabel="" />
192
- </Paper>
193
- </Collapse>
194
- </Stack>
195
- </Card>
196
- </Stack>
197
- </Container>
198
- );
199
- }
200
-
201
- export default Examples;
package/jest.config.js DELETED
@@ -1,14 +0,0 @@
1
- export default {
2
- preset: 'ts-jest',
3
- testEnvironment: 'node',
4
- transform: {
5
- '^.+\\.ts$': ['ts-jest', {
6
- useESM: true
7
- }]
8
- },
9
- extensionsToTreatAsEsm: ['.ts'],
10
- moduleNameMapper: {
11
- '^(\\.{1,2}/.*)\\.js$': '$1'
12
- },
13
- testPathIgnorePatterns: ['/node_modules/', '/dist/', '/templates/', '/test-smart-contract-app/']
14
- };
package/src/main.test.ts DELETED
@@ -1,38 +0,0 @@
1
- import { describe, test, expect, beforeEach, afterEach } from '@jest/globals';
2
- import { promises as fs } from 'node:fs';
3
- import path from 'node:path';
4
-
5
- describe('Extension System', () => {
6
- const testDir = path.join(process.cwd(), 'test-output');
7
- const extensionsDir = path.join(process.cwd(), 'extensions');
8
-
9
- beforeEach(async () => {
10
- // Clean up test directory
11
- try {
12
- await fs.rm(testDir, { recursive: true, force: true });
13
- } catch (e) {
14
- // Directory might not exist
15
- }
16
- await fs.mkdir(testDir, { recursive: true });
17
- });
18
-
19
- afterEach(async () => {
20
- // Clean up test directory
21
- try {
22
- await fs.rm(testDir, { recursive: true, force: true });
23
- } catch (e) {
24
- // Directory might not exist
25
- }
26
- });
27
-
28
- test('should list available extensions', async () => {
29
- const extensionExists = await fs.access(path.join(extensionsDir, 'precompiles'))
30
- .then(() => true)
31
- .catch(() => false);
32
-
33
- expect(extensionExists).toBe(true);
34
-
35
- const extensionFiles = await fs.readdir(extensionsDir);
36
- expect(extensionFiles).toContain('precompiles');
37
- });
38
- });
package/src/main.ts DELETED
@@ -1,159 +0,0 @@
1
- #!/usr/bin/env node
2
- import boxen from 'boxen';
3
- import inquirer from 'inquirer';
4
-
5
- import fs from 'node:fs';
6
- import path from 'node:path';
7
- import { dirname } from 'node:path';
8
- import { fileURLToPath } from 'node:url';
9
- import { Command } from 'commander';
10
-
11
- const __filename = fileURLToPath(import.meta.url);
12
- const __dirname = dirname(__filename);
13
-
14
- const program = new Command();
15
-
16
- // Print welcome message
17
- const printWelcomeMessage = () => {
18
- console.log(
19
- boxen('Welcome to the SEI DApp Generator!', {
20
- padding: 1,
21
- margin: 1,
22
- borderStyle: 'double',
23
- borderColor: '#932C23'
24
- })
25
- );
26
- };
27
-
28
- interface WizardOptions {
29
- name?: string;
30
- extension?: string;
31
- }
32
-
33
- function isValidDirectoryName(dirName) {
34
- const illegalRe = /[<>:"/\\|?*]/g;
35
- const windowsReservedRe = /^(con|prn|aux|nul|com[1-9]|lpt[1-9])$/i;
36
- const trailingRe = /[. ]+$/;
37
- const validNpmPackageRe = /^(?:@[a-z0-9-*~][a-z0-9-*._~]*)?[a-z0-9-~][a-z0-9-._~]*$/;
38
-
39
- if (typeof dirName !== 'string' || dirName.length === 0) {
40
- return false;
41
- }
42
-
43
- // Check for illegal characters, Windows reserved names, trailing spaces/dots
44
- if (illegalRe.test(dirName) || windowsReservedRe.test(dirName) || trailingRe.test(dirName) || !validNpmPackageRe.test(dirName)) {
45
- return false;
46
- }
47
-
48
- return true;
49
- }
50
-
51
- const validateOptions = (options: WizardOptions): boolean => {
52
- let valid = true;
53
-
54
- if (options.name) {
55
- if (!isValidDirectoryName(options.name)) {
56
- console.log('Invalid package name. Please use a valid npm package name.');
57
- valid = false;
58
- }
59
- }
60
-
61
- return valid;
62
- };
63
-
64
- async function listExtensions(): Promise<void> {
65
- const extensionsPath = path.join(__dirname, 'extensions');
66
-
67
- try {
68
- const extensions = await fs.promises.readdir(extensionsPath, { withFileTypes: true });
69
- const extensionDirs = extensions.filter((dirent) => dirent.isDirectory()).map((dirent) => dirent.name);
70
-
71
- if (extensionDirs.length === 0) {
72
- console.log('No extensions available.');
73
- return;
74
- }
75
-
76
- console.log('Available extensions:');
77
- for (const ext of extensionDirs) {
78
- console.log(` - ${ext}`);
79
- }
80
- } catch (error) {
81
- console.log('No extensions directory found.');
82
- }
83
- }
84
-
85
- async function runWizard(options: WizardOptions): Promise<void> {
86
- if (!validateOptions(options)) {
87
- return;
88
- }
89
-
90
- printWelcomeMessage();
91
-
92
- let dAppName = '';
93
- if (options.name) {
94
- dAppName = options.name;
95
- } else {
96
- const promptResult = await inquirer.prompt([
97
- {
98
- type: 'input',
99
- name: 'dAppName',
100
- message: 'What is your dApp (project) name?',
101
- validate: (input: string) => {
102
- return isValidDirectoryName(input) || 'Invalid package name. Please use a valid npm package name.';
103
- }
104
- }
105
- ]);
106
-
107
- dAppName = promptResult.dAppName;
108
- }
109
-
110
- // Copy base template
111
- const templateName = 'next-template';
112
- const templatePath = path.join(__dirname, 'templates', templateName);
113
- const dst = path.join(process.cwd(), dAppName);
114
- await fs.promises.cp(templatePath, dst, { recursive: true });
115
-
116
- // Apply extension if specified
117
- if (options.extension) {
118
- const extensionPath = path.join(__dirname, 'extensions', options.extension);
119
-
120
- try {
121
- await fs.promises.access(extensionPath);
122
- await fs.promises.cp(extensionPath, dst, { recursive: true });
123
- console.log(`Applied extension: ${options.extension}`);
124
- } catch (error) {
125
- console.log(`Warning: Extension '${options.extension}' not found. Continuing with base template.`);
126
- }
127
- }
128
-
129
- const extensionText = options.extension ? ` with ${options.extension} extension` : '';
130
- console.log(`Project setup complete! Using template ${templateName}${extensionText}\n`);
131
- console.log(`To start your app, run: \n > cd ${dAppName} \n > pnpm \n > pnpm dev\n`);
132
- }
133
-
134
- program
135
- .command('app')
136
- .description('Create a new SEI dApp')
137
- .option('--name <name>', 'Specify the name of your dApp. Name must be a valid package name.')
138
- .option('--extension <extension>', 'Specify an extension to apply to the base template')
139
-
140
- .action(async (options: WizardOptions) => {
141
- try {
142
- await runWizard(options);
143
- } catch (error) {
144
- console.error('An error occurred:', error);
145
- }
146
- });
147
-
148
- program
149
- .command('list-extensions')
150
- .description('List all available extensions')
151
- .action(async () => {
152
- try {
153
- await listExtensions();
154
- } catch (error) {
155
- console.error('An error occurred:', error);
156
- }
157
- });
158
-
159
- program.parse(process.argv);
@@ -1,8 +0,0 @@
1
- # Chain configuration
2
- # Options: mainnet, testnet, devnet
3
- # Defaults to mainnet if not set; this example overrides it to testnet
4
- NEXT_PUBLIC_CHAIN=testnet
5
-
6
- # WalletConnect Project ID (optional)
7
- # Get your project ID from https://cloud.walletconnect.com
8
- NEXT_PUBLIC_WALLETCONNECT_PROJECT_ID=your-project-id
@@ -1 +0,0 @@
1
- {}
@@ -1 +0,0 @@
1
- v20