@daawoonkim/create-arch-app 0.1.0 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,440 @@
1
+ import path from 'path';
2
+ import { ensureDir, createFile } from './fileSystem.js';
3
+ export async function generateApiFiles(config, basePath) {
4
+ if (config.apiClient === 'none' && config.dataFetching === 'none') {
5
+ return;
6
+ }
7
+ switch (config.architecture) {
8
+ case 'ddd':
9
+ await generateDddApiFiles(config, basePath);
10
+ break;
11
+ case 'clean':
12
+ await generateCleanApiFiles(config, basePath);
13
+ break;
14
+ case 'atomic':
15
+ await generateAtomicApiFiles(config, basePath);
16
+ break;
17
+ case 'default':
18
+ default:
19
+ await generateDefaultApiFiles(config, basePath);
20
+ break;
21
+ }
22
+ }
23
+ async function generateDddApiFiles(config, basePath) {
24
+ const apiPath = path.join(basePath, 'infrastructure/api');
25
+ await ensureDir(apiPath);
26
+ // API Client
27
+ if (config.apiClient !== 'none') {
28
+ await createFile(path.join(apiPath, 'client.ts'), generateApiClientContent(config));
29
+ // Example endpoint
30
+ await createFile(path.join(apiPath, 'endpoints', 'example.ts'), generateExampleEndpointContent(config));
31
+ }
32
+ // React Query or SWR setup
33
+ if (config.dataFetching !== 'none') {
34
+ await createFile(path.join(apiPath, 'queryClient.ts'), generateQueryClientContent(config));
35
+ }
36
+ }
37
+ async function generateCleanApiFiles(config, basePath) {
38
+ const libPath = path.join(basePath, 'shared/lib');
39
+ await ensureDir(libPath);
40
+ if (config.apiClient !== 'none') {
41
+ await createFile(path.join(libPath, 'apiClient.ts'), generateApiClientContent(config));
42
+ }
43
+ if (config.dataFetching !== 'none') {
44
+ await createFile(path.join(libPath, 'queryClient.ts'), generateQueryClientContent(config));
45
+ // Example query hooks in feature
46
+ const featurePath = path.join(basePath, 'features/example/data');
47
+ await ensureDir(featurePath);
48
+ await createFile(path.join(featurePath, 'queries.ts'), generateExampleQueryHookContent(config));
49
+ }
50
+ }
51
+ async function generateAtomicApiFiles(config, basePath) {
52
+ const libPath = path.join(basePath, 'lib');
53
+ await ensureDir(libPath);
54
+ if (config.apiClient !== 'none') {
55
+ const apiPath = path.join(libPath, 'api');
56
+ await ensureDir(apiPath);
57
+ await createFile(path.join(apiPath, 'client.ts'), generateApiClientContent(config));
58
+ await createFile(path.join(apiPath, 'endpoints', 'example.ts'), generateExampleEndpointContent(config));
59
+ }
60
+ if (config.dataFetching !== 'none') {
61
+ await createFile(path.join(libPath, 'queryClient.ts'), generateQueryClientContent(config));
62
+ // Example hooks
63
+ const hooksPath = path.join(basePath, 'hooks/queries');
64
+ await ensureDir(hooksPath);
65
+ await createFile(path.join(hooksPath, 'useExample.ts'), generateExampleQueryHookContent(config));
66
+ }
67
+ }
68
+ async function generateDefaultApiFiles(config, basePath) {
69
+ const libPath = path.join(basePath, 'lib');
70
+ await ensureDir(libPath);
71
+ if (config.apiClient !== 'none') {
72
+ await createFile(path.join(libPath, 'api.ts'), generateApiClientContent(config));
73
+ }
74
+ if (config.dataFetching !== 'none') {
75
+ await createFile(path.join(libPath, 'queryClient.ts'), generateQueryClientContent(config));
76
+ // Example hooks
77
+ const hooksPath = path.join(basePath, 'hooks/queries');
78
+ await ensureDir(hooksPath);
79
+ await createFile(path.join(hooksPath, 'useExample.ts'), generateExampleQueryHookContent(config));
80
+ }
81
+ }
82
+ function generateApiClientContent(config) {
83
+ if (config.apiClient === 'axios') {
84
+ return `import axios from 'axios';
85
+
86
+ export const apiClient = axios.create({
87
+ baseURL: process.env.NEXT_PUBLIC_API_URL || process.env.VITE_API_URL || '/api',
88
+ timeout: 10000,
89
+ headers: {
90
+ 'Content-Type': 'application/json',
91
+ },
92
+ });
93
+
94
+ // Request interceptor
95
+ apiClient.interceptors.request.use(
96
+ (config) => {
97
+ // Add authentication token if exists
98
+ const token = localStorage.getItem('token');
99
+ if (token) {
100
+ config.headers.Authorization = \`Bearer \${token}\`;
101
+ }
102
+ return config;
103
+ },
104
+ (error) => {
105
+ return Promise.reject(error);
106
+ }
107
+ );
108
+
109
+ // Response interceptor
110
+ apiClient.interceptors.response.use(
111
+ (response) => response,
112
+ (error) => {
113
+ // Handle common errors
114
+ if (error.response?.status === 401) {
115
+ // Handle unauthorized
116
+ localStorage.removeItem('token');
117
+ }
118
+ return Promise.reject(error);
119
+ }
120
+ );
121
+ `;
122
+ }
123
+ else if (config.apiClient === 'fetch') {
124
+ return `const API_BASE_URL = process.env.NEXT_PUBLIC_API_URL || process.env.VITE_API_URL || '/api';
125
+
126
+ interface RequestConfig extends RequestInit {
127
+ timeout?: number;
128
+ }
129
+
130
+ export const apiClient = {
131
+ async request<T>(endpoint: string, config?: RequestConfig): Promise<T> {
132
+ const { timeout = 10000, ...fetchConfig } = config || {};
133
+
134
+ const controller = new AbortController();
135
+ const timeoutId = setTimeout(() => controller.abort(), timeout);
136
+
137
+ try {
138
+ // Add authentication token if exists
139
+ const token = localStorage.getItem('token');
140
+ const headers = {
141
+ 'Content-Type': 'application/json',
142
+ ...(token && { Authorization: \`Bearer \${token}\` }),
143
+ ...fetchConfig.headers,
144
+ };
145
+
146
+ const response = await fetch(\`\${API_BASE_URL}\${endpoint}\`, {
147
+ ...fetchConfig,
148
+ headers,
149
+ signal: controller.signal,
150
+ });
151
+
152
+ clearTimeout(timeoutId);
153
+
154
+ if (!response.ok) {
155
+ if (response.status === 401) {
156
+ localStorage.removeItem('token');
157
+ }
158
+ throw new Error(\`HTTP error! status: \${response.status}\`);
159
+ }
160
+
161
+ return await response.json();
162
+ } catch (error) {
163
+ clearTimeout(timeoutId);
164
+ throw error;
165
+ }
166
+ },
167
+
168
+ get<T>(endpoint: string, config?: RequestConfig): Promise<T> {
169
+ return this.request<T>(endpoint, { ...config, method: 'GET' });
170
+ },
171
+
172
+ post<T>(endpoint: string, data?: unknown, config?: RequestConfig): Promise<T> {
173
+ return this.request<T>(endpoint, {
174
+ ...config,
175
+ method: 'POST',
176
+ body: JSON.stringify(data),
177
+ });
178
+ },
179
+
180
+ put<T>(endpoint: string, data?: unknown, config?: RequestConfig): Promise<T> {
181
+ return this.request<T>(endpoint, {
182
+ ...config,
183
+ method: 'PUT',
184
+ body: JSON.stringify(data),
185
+ });
186
+ },
187
+
188
+ delete<T>(endpoint: string, config?: RequestConfig): Promise<T> {
189
+ return this.request<T>(endpoint, { ...config, method: 'DELETE' });
190
+ },
191
+ };
192
+ `;
193
+ }
194
+ return '';
195
+ }
196
+ function generateQueryClientContent(config) {
197
+ if (config.dataFetching === 'react-query') {
198
+ return `import { QueryClient } from '@tanstack/react-query';
199
+
200
+ export const queryClient = new QueryClient({
201
+ defaultOptions: {
202
+ queries: {
203
+ refetchOnWindowFocus: false,
204
+ retry: 1,
205
+ staleTime: 5 * 60 * 1000, // 5 minutes
206
+ },
207
+ },
208
+ });
209
+ `;
210
+ }
211
+ else if (config.dataFetching === 'swr') {
212
+ return `import { SWRConfig } from 'swr';
213
+
214
+ export const swrConfig = {
215
+ revalidateOnFocus: false,
216
+ revalidateOnReconnect: true,
217
+ shouldRetryOnError: true,
218
+ errorRetryCount: 1,
219
+ dedupingInterval: 2000,
220
+ };
221
+
222
+ // Default fetcher for SWR
223
+ export const fetcher = async (url: string) => {
224
+ const response = await fetch(url);
225
+ if (!response.ok) {
226
+ throw new Error('An error occurred while fetching the data.');
227
+ }
228
+ return response.json();
229
+ };
230
+ `;
231
+ }
232
+ return '';
233
+ }
234
+ function generateExampleEndpointContent(config) {
235
+ const clientImport = config.apiClient === 'axios' ? 'apiClient' : 'apiClient';
236
+ const clientPath = config.architecture === 'ddd' ? '../client' : './client';
237
+ if (config.apiClient === 'axios') {
238
+ return `import { ${clientImport} } from '${clientPath}';
239
+
240
+ export interface ExampleData {
241
+ id: number;
242
+ title: string;
243
+ description: string;
244
+ }
245
+
246
+ export const exampleApi = {
247
+ getAll: async (): Promise<ExampleData[]> => {
248
+ const { data } = await apiClient.get<ExampleData[]>('/examples');
249
+ return data;
250
+ },
251
+
252
+ getById: async (id: number): Promise<ExampleData> => {
253
+ const { data } = await apiClient.get<ExampleData>(\`/examples/\${id}\`);
254
+ return data;
255
+ },
256
+
257
+ create: async (payload: Omit<ExampleData, 'id'>): Promise<ExampleData> => {
258
+ const { data } = await apiClient.post<ExampleData>('/examples', payload);
259
+ return data;
260
+ },
261
+
262
+ update: async (id: number, payload: Partial<ExampleData>): Promise<ExampleData> => {
263
+ const { data } = await apiClient.put<ExampleData>(\`/examples/\${id}\`, payload);
264
+ return data;
265
+ },
266
+
267
+ delete: async (id: number): Promise<void> => {
268
+ await apiClient.delete(\`/examples/\${id}\`);
269
+ },
270
+ };
271
+ `;
272
+ }
273
+ else if (config.apiClient === 'fetch') {
274
+ return `import { ${clientImport} } from '${clientPath}';
275
+
276
+ export interface ExampleData {
277
+ id: number;
278
+ title: string;
279
+ description: string;
280
+ }
281
+
282
+ export const exampleApi = {
283
+ getAll: (): Promise<ExampleData[]> => {
284
+ return apiClient.get<ExampleData[]>('/examples');
285
+ },
286
+
287
+ getById: (id: number): Promise<ExampleData> => {
288
+ return apiClient.get<ExampleData>(\`/examples/\${id}\`);
289
+ },
290
+
291
+ create: (payload: Omit<ExampleData, 'id'>): Promise<ExampleData> => {
292
+ return apiClient.post<ExampleData>('/examples', payload);
293
+ },
294
+
295
+ update: (id: number, payload: Partial<ExampleData>): Promise<ExampleData> => {
296
+ return apiClient.put<ExampleData>(\`/examples/\${id}\`, payload);
297
+ },
298
+
299
+ delete: (id: number): Promise<void> => {
300
+ return apiClient.delete<void>(\`/examples/\${id}\`);
301
+ },
302
+ };
303
+ `;
304
+ }
305
+ return '';
306
+ }
307
+ function generateExampleQueryHookContent(config) {
308
+ if (config.dataFetching === 'react-query') {
309
+ const importPath = config.architecture === 'clean'
310
+ ? '@/shared/lib/apiClient'
311
+ : config.architecture === 'atomic' || config.architecture === 'default'
312
+ ? '@/lib/api'
313
+ : '@/infrastructure/api/endpoints/example';
314
+ return `import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
315
+ import { exampleApi, ExampleData } from '${importPath}';
316
+
317
+ // Query Keys
318
+ export const exampleKeys = {
319
+ all: ['examples'] as const,
320
+ lists: () => [...exampleKeys.all, 'list'] as const,
321
+ list: (filters: string) => [...exampleKeys.lists(), { filters }] as const,
322
+ details: () => [...exampleKeys.all, 'detail'] as const,
323
+ detail: (id: number) => [...exampleKeys.details(), id] as const,
324
+ };
325
+
326
+ // Get all examples
327
+ export function useExamples() {
328
+ return useQuery({
329
+ queryKey: exampleKeys.lists(),
330
+ queryFn: () => exampleApi.getAll(),
331
+ });
332
+ }
333
+
334
+ // Get example by ID
335
+ export function useExample(id: number) {
336
+ return useQuery({
337
+ queryKey: exampleKeys.detail(id),
338
+ queryFn: () => exampleApi.getById(id),
339
+ enabled: !!id,
340
+ });
341
+ }
342
+
343
+ // Create example
344
+ export function useCreateExample() {
345
+ const queryClient = useQueryClient();
346
+
347
+ return useMutation({
348
+ mutationFn: (data: Omit<ExampleData, 'id'>) => exampleApi.create(data),
349
+ onSuccess: () => {
350
+ queryClient.invalidateQueries({ queryKey: exampleKeys.lists() });
351
+ },
352
+ });
353
+ }
354
+
355
+ // Update example
356
+ export function useUpdateExample() {
357
+ const queryClient = useQueryClient();
358
+
359
+ return useMutation({
360
+ mutationFn: ({ id, data }: { id: number; data: Partial<ExampleData> }) =>
361
+ exampleApi.update(id, data),
362
+ onSuccess: (_, variables) => {
363
+ queryClient.invalidateQueries({ queryKey: exampleKeys.detail(variables.id) });
364
+ queryClient.invalidateQueries({ queryKey: exampleKeys.lists() });
365
+ },
366
+ });
367
+ }
368
+
369
+ // Delete example
370
+ export function useDeleteExample() {
371
+ const queryClient = useQueryClient();
372
+
373
+ return useMutation({
374
+ mutationFn: (id: number) => exampleApi.delete(id),
375
+ onSuccess: () => {
376
+ queryClient.invalidateQueries({ queryKey: exampleKeys.lists() });
377
+ },
378
+ });
379
+ }
380
+ `;
381
+ }
382
+ else if (config.dataFetching === 'swr') {
383
+ return `import useSWR from 'swr';
384
+ import { fetcher } from '@/lib/queryClient';
385
+
386
+ export interface ExampleData {
387
+ id: number;
388
+ title: string;
389
+ description: string;
390
+ }
391
+
392
+ // Get all examples
393
+ export function useExamples() {
394
+ const { data, error, isLoading } = useSWR<ExampleData[]>('/api/examples', fetcher);
395
+
396
+ return {
397
+ data,
398
+ isLoading,
399
+ isError: error,
400
+ };
401
+ }
402
+
403
+ // Get example by ID
404
+ export function useExample(id: number) {
405
+ const { data, error, isLoading } = useSWR<ExampleData>(
406
+ id ? \`/api/examples/\${id}\` : null,
407
+ fetcher
408
+ );
409
+
410
+ return {
411
+ data,
412
+ isLoading,
413
+ isError: error,
414
+ };
415
+ }
416
+
417
+ // For mutations, you can use SWR's mutate function
418
+ // Example usage:
419
+ // import { mutate } from 'swr';
420
+ // await mutate('/api/examples', updatedData, { revalidate: true });
421
+ `;
422
+ }
423
+ return '';
424
+ }
425
+ export async function generateEnvFile(config, projectPath) {
426
+ if (config.apiClient === 'none' && config.dataFetching === 'none') {
427
+ return;
428
+ }
429
+ const isNextJs = config.framework === 'nextjs';
430
+ const prefix = isNextJs ? 'NEXT_PUBLIC_API_URL' : 'VITE_API_URL';
431
+ const envContent = `# API Configuration
432
+ ${prefix}=http://localhost:3000/api
433
+ `;
434
+ const envExampleContent = `# API Configuration
435
+ ${prefix}=http://localhost:3000/api
436
+ `;
437
+ await createFile(path.join(projectPath, '.env.local'), envContent);
438
+ await createFile(path.join(projectPath, '.env.example'), envExampleContent);
439
+ }
440
+ //# sourceMappingURL=apiGenerator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"apiGenerator.js","sourceRoot":"","sources":["../../src/utils/apiGenerator.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"dependencies.d.ts","sourceRoot":"","sources":["../../src/utils/dependencies.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C,wBAAgB,eAAe,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAyC7E;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAmChF;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAoBxE"}
1
+ {"version":3,"file":"dependencies.d.ts","sourceRoot":"","sources":["../../src/utils/dependencies.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C,wBAAgB,eAAe,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAqD7E;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAwChF;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,aAAa,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAoBxE"}
@@ -35,6 +35,17 @@ export function getDependencies(config) {
35
35
  if (config.formLibrary === 'react-hook-form') {
36
36
  deps['react-hook-form'] = '^7.49.3';
37
37
  }
38
+ // API Client
39
+ if (config.apiClient === 'axios') {
40
+ deps.axios = '^1.6.5';
41
+ }
42
+ // Data Fetching
43
+ if (config.dataFetching === 'react-query') {
44
+ deps['@tanstack/react-query'] = '^5.17.19';
45
+ }
46
+ else if (config.dataFetching === 'swr') {
47
+ deps.swr = '^2.2.4';
48
+ }
38
49
  return deps;
39
50
  }
40
51
  export function getDevDependencies(config) {
@@ -58,6 +69,10 @@ export function getDevDependencies(config) {
58
69
  devDeps.autoprefixer = '^10.4.16';
59
70
  devDeps.postcss = '^8.4.33';
60
71
  }
72
+ // Data Fetching DevTools
73
+ if (config.dataFetching === 'react-query') {
74
+ devDeps['@tanstack/react-query-devtools'] = '^5.17.19';
75
+ }
61
76
  // Testing
62
77
  if (config.testing) {
63
78
  devDeps.vitest = '^1.2.0';
@@ -1 +1 @@
1
- {"version":3,"file":"dependencies.js","sourceRoot":"","sources":["../../src/utils/dependencies.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"dependencies.js","sourceRoot":"","sources":["../../src/utils/dependencies.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@daawoonkim/create-arch-app",
3
- "version": "0.1.0",
3
+ "version": "0.2.1",
4
4
  "description": "CLI tool to scaffold React/Next.js projects with DDD, Clean Architecture, and Atomic Design patterns",
5
5
  "type": "module",
6
6
  "bin": {