create-ern-boilerplate 0.0.38 → 0.0.39
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/create.js +10 -8
- package/package.json +1 -1
- package/templates/agent-generator/AI_GUIDE.md +162 -10
- package/templates/agent-generator/CONVENTIONS.md +63 -10
- package/templates/agent-generator/GENERATE_RULES.md +68 -11
- package/templates/agent-generator/README.md +64 -13
- package/templates/agent-generator/TEMPLATE_VARIANTS.md +474 -0
- package/templates/agent-generator/ai-context.json +4 -0
- package/templates/agent-generator/examples/apps/dashboard-with-auth/README.md +417 -0
- package/templates/agent-generator/examples/apps/news-no-auth/README.md +350 -0
- package/templates/agent-generator/examples/apps/todo-offline/README.md +197 -0
- package/templates/agent-generator/examples/screens/detail-screen.example.tsx +288 -0
- package/templates/agent-generator/examples/screens/form-screen.example.tsx +369 -0
- package/templates/agent-generator/examples/screens/list-screen-no-auth.example.tsx +195 -0
- package/templates/agent-generator/examples/screens/list-screen-with-auth.example.tsx +251 -0
- package/templates/agent-generator/examples/services/offline-service.example.ts +259 -0
- package/templates/agent-generator/examples/services/service-with-mock.example.ts +156 -0
- package/templates/agent-generator/examples/services/service-without-mock.example.ts +121 -0
|
@@ -0,0 +1,474 @@
|
|
|
1
|
+
# Template Variants Guide
|
|
2
|
+
|
|
3
|
+
How to customize this template for different app types and requirements.
|
|
4
|
+
|
|
5
|
+
## 📋 Overview
|
|
6
|
+
|
|
7
|
+
This template is **intentionally general** and includes both auth and mock API infrastructure. Depending on your app needs, you may want to:
|
|
8
|
+
|
|
9
|
+
1. **Remove authentication** - For apps with public content
|
|
10
|
+
2. **Remove mock API** - For apps connecting directly to real API
|
|
11
|
+
3. **Remove API entirely** - For offline-only apps
|
|
12
|
+
4. **Keep everything** - For full-featured apps with auth and API
|
|
13
|
+
|
|
14
|
+
## 🎯 Quick Decision Tree
|
|
15
|
+
|
|
16
|
+
```
|
|
17
|
+
Does your app need user accounts?
|
|
18
|
+
├─ YES → Keep authentication
|
|
19
|
+
│ ├─ Does it need API?
|
|
20
|
+
│ │ ├─ YES → Keep mock API for development
|
|
21
|
+
│ │ └─ NO → Remove API, use local storage
|
|
22
|
+
│ └─ Continue to final setup
|
|
23
|
+
└─ NO → Remove authentication
|
|
24
|
+
├─ Does it need API?
|
|
25
|
+
│ ├─ YES → Remove auth, keep API
|
|
26
|
+
│ └─ NO → Remove both auth and API
|
|
27
|
+
└─ Continue to final setup
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
## 📁 Template Variants
|
|
31
|
+
|
|
32
|
+
### Variant 1: Offline-Only App (No Auth, No API)
|
|
33
|
+
|
|
34
|
+
**Use for:** Todo lists, calculators, notes, offline utilities
|
|
35
|
+
|
|
36
|
+
**Example:** See `examples/apps/todo-offline/`
|
|
37
|
+
|
|
38
|
+
#### What to Remove:
|
|
39
|
+
|
|
40
|
+
```bash
|
|
41
|
+
# 1. Remove auth folder
|
|
42
|
+
rm -rf app/(auth)/
|
|
43
|
+
|
|
44
|
+
# 2. Remove auth components
|
|
45
|
+
rm -rf src/components/auth/
|
|
46
|
+
|
|
47
|
+
# 3. Remove auth store
|
|
48
|
+
rm src/store/authStore.ts
|
|
49
|
+
|
|
50
|
+
# 4. Remove auth service
|
|
51
|
+
rm src/services/authService.ts
|
|
52
|
+
|
|
53
|
+
# 5. Remove API infrastructure
|
|
54
|
+
rm src/services/api.ts
|
|
55
|
+
rm -rf src/services/mockApi/
|
|
56
|
+
|
|
57
|
+
# 6. Remove server mock data
|
|
58
|
+
rm -rf server/
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
#### Files to Update:
|
|
62
|
+
|
|
63
|
+
**1. `app/_layout.tsx`** - Remove auth check:
|
|
64
|
+
```typescript
|
|
65
|
+
export default function RootLayout() {
|
|
66
|
+
const systemColorScheme = useColorScheme();
|
|
67
|
+
const setColorScheme = useThemeStore((state) => state.setColorScheme);
|
|
68
|
+
|
|
69
|
+
useEffect(() => {
|
|
70
|
+
setColorScheme(systemColorScheme);
|
|
71
|
+
}, [systemColorScheme]);
|
|
72
|
+
|
|
73
|
+
return (
|
|
74
|
+
<SafeAreaProvider>
|
|
75
|
+
<Stack screenOptions={{ headerShown: false }}>
|
|
76
|
+
<Stack.Screen name="(tabs)" />
|
|
77
|
+
</Stack>
|
|
78
|
+
</SafeAreaProvider>
|
|
79
|
+
);
|
|
80
|
+
}
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
**2. `src/utils/constants.ts`** - Remove API config:
|
|
84
|
+
```typescript
|
|
85
|
+
export const APP_CONFIG = {
|
|
86
|
+
NAME: extra.APP_NAME || Constants.expoConfig?.name || 'Default App',
|
|
87
|
+
};
|
|
88
|
+
|
|
89
|
+
// Remove API_CONFIG entirely
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
#### What to Use Instead:
|
|
93
|
+
|
|
94
|
+
- **Storage:** AsyncStorage or Zustand with persistence
|
|
95
|
+
- **Example service:** `examples/services/offline-service.example.ts`
|
|
96
|
+
- **Example screens:** Use standard list/form screens
|
|
97
|
+
|
|
98
|
+
---
|
|
99
|
+
|
|
100
|
+
### Variant 2: Public Content App (No Auth, With API)
|
|
101
|
+
|
|
102
|
+
**Use for:** News apps, blogs, recipes, educational content
|
|
103
|
+
|
|
104
|
+
**Example:** See `examples/apps/news-no-auth/`
|
|
105
|
+
|
|
106
|
+
#### What to Remove:
|
|
107
|
+
|
|
108
|
+
```bash
|
|
109
|
+
# 1. Remove auth folder
|
|
110
|
+
rm -rf app/(auth)/
|
|
111
|
+
|
|
112
|
+
# 2. Remove auth components
|
|
113
|
+
rm -rf src/components/auth/
|
|
114
|
+
|
|
115
|
+
# 3. Remove auth store
|
|
116
|
+
rm src/store/authStore.ts
|
|
117
|
+
|
|
118
|
+
# 4. Remove auth service (but keep mockApi for auth if exists)
|
|
119
|
+
rm src/services/authService.ts
|
|
120
|
+
rm src/services/mockApi/auth.mock.ts
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
#### Files to Update:
|
|
124
|
+
|
|
125
|
+
**1. `app/_layout.tsx`** - Remove auth check:
|
|
126
|
+
```typescript
|
|
127
|
+
export default function RootLayout() {
|
|
128
|
+
const systemColorScheme = useColorScheme();
|
|
129
|
+
const setColorScheme = useThemeStore((state) => state.setColorScheme);
|
|
130
|
+
|
|
131
|
+
useEffect(() => {
|
|
132
|
+
setColorScheme(systemColorScheme);
|
|
133
|
+
}, [systemColorScheme]);
|
|
134
|
+
|
|
135
|
+
return (
|
|
136
|
+
<SafeAreaProvider>
|
|
137
|
+
<Stack screenOptions={{ headerShown: false }}>
|
|
138
|
+
<Stack.Screen name="(tabs)" />
|
|
139
|
+
</Stack>
|
|
140
|
+
</SafeAreaProvider>
|
|
141
|
+
);
|
|
142
|
+
}
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
**2. `src/services/api.ts`** - Remove auth token handling:
|
|
146
|
+
```typescript
|
|
147
|
+
// Remove this from interceptor:
|
|
148
|
+
private setupInterceptors() {
|
|
149
|
+
this.api.interceptors.request.use(
|
|
150
|
+
async (config: InternalAxiosRequestConfig) => {
|
|
151
|
+
// REMOVE: Token injection
|
|
152
|
+
// const token = await storage.getToken();
|
|
153
|
+
// if (token && config.headers) {
|
|
154
|
+
// config.headers.Authorization = `Bearer ${token}`;
|
|
155
|
+
// }
|
|
156
|
+
return config;
|
|
157
|
+
},
|
|
158
|
+
(error) => Promise.reject(error)
|
|
159
|
+
);
|
|
160
|
+
|
|
161
|
+
this.api.interceptors.response.use(
|
|
162
|
+
(response) => response,
|
|
163
|
+
async (error: AxiosError) => {
|
|
164
|
+
// REMOVE: 401 handling
|
|
165
|
+
// if (error.response?.status === 401) {
|
|
166
|
+
// await storage.removeToken();
|
|
167
|
+
// }
|
|
168
|
+
return Promise.reject(this.handleError(error));
|
|
169
|
+
}
|
|
170
|
+
);
|
|
171
|
+
}
|
|
172
|
+
```
|
|
173
|
+
|
|
174
|
+
**3. `server/db.json`** - Remove users array:
|
|
175
|
+
```json
|
|
176
|
+
{
|
|
177
|
+
"articles": [...],
|
|
178
|
+
"categories": [...]
|
|
179
|
+
// Remove "users" array
|
|
180
|
+
}
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
#### What to Keep:
|
|
184
|
+
|
|
185
|
+
- ✅ API infrastructure (`src/services/api.ts`)
|
|
186
|
+
- ✅ Mock API system (`src/services/mockApi/`)
|
|
187
|
+
- ✅ `API_CONFIG.MOCK_API` flag
|
|
188
|
+
- ✅ Server mock data (except users)
|
|
189
|
+
|
|
190
|
+
---
|
|
191
|
+
|
|
192
|
+
### Variant 3: Protected App (With Auth, With API)
|
|
193
|
+
|
|
194
|
+
**Use for:** Dashboards, business apps, SaaS, team tools
|
|
195
|
+
|
|
196
|
+
**Example:** See `examples/apps/dashboard-with-auth/`
|
|
197
|
+
|
|
198
|
+
#### What to Keep:
|
|
199
|
+
|
|
200
|
+
**Everything!** This variant uses the template as-is.
|
|
201
|
+
|
|
202
|
+
- ✅ Authentication system
|
|
203
|
+
- ✅ Protected routes
|
|
204
|
+
- ✅ Mock API for development
|
|
205
|
+
- ✅ Real API for production
|
|
206
|
+
|
|
207
|
+
#### What to Add:
|
|
208
|
+
|
|
209
|
+
1. **User-specific data models** in `src/types/`
|
|
210
|
+
2. **Protected screens** in `app/(tabs)/`
|
|
211
|
+
3. **User services** in `src/services/`
|
|
212
|
+
4. **Auth middleware** for protected routes
|
|
213
|
+
|
|
214
|
+
#### Example Protected Route:
|
|
215
|
+
|
|
216
|
+
```typescript
|
|
217
|
+
// app/(tabs)/dashboard.tsx
|
|
218
|
+
export default function DashboardScreen() {
|
|
219
|
+
const { user, isAuthenticated } = useAuthStore();
|
|
220
|
+
const router = useRouter();
|
|
221
|
+
|
|
222
|
+
useEffect(() => {
|
|
223
|
+
if (!isAuthenticated) {
|
|
224
|
+
router.replace('/(auth)/login');
|
|
225
|
+
}
|
|
226
|
+
}, [isAuthenticated]);
|
|
227
|
+
|
|
228
|
+
if (!isAuthenticated) return null;
|
|
229
|
+
|
|
230
|
+
// Dashboard content for logged-in user
|
|
231
|
+
return (
|
|
232
|
+
<View>
|
|
233
|
+
<Text>Welcome, {user?.name}!</Text>
|
|
234
|
+
</View>
|
|
235
|
+
);
|
|
236
|
+
}
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
---
|
|
240
|
+
|
|
241
|
+
### Variant 4: Hybrid App (Optional Auth, With API)
|
|
242
|
+
|
|
243
|
+
**Use for:** Apps with both public and private content
|
|
244
|
+
|
|
245
|
+
**Example:** E-commerce (browse without login, checkout requires login)
|
|
246
|
+
|
|
247
|
+
#### What to Keep:
|
|
248
|
+
|
|
249
|
+
- ✅ Keep all auth infrastructure
|
|
250
|
+
- ✅ Keep all API infrastructure
|
|
251
|
+
- ✅ Mix of public and protected routes
|
|
252
|
+
|
|
253
|
+
#### App Structure:
|
|
254
|
+
|
|
255
|
+
```
|
|
256
|
+
app/
|
|
257
|
+
├── (auth)/ # Login/register
|
|
258
|
+
├── (public)/ # Public routes (no auth required)
|
|
259
|
+
│ ├── products.tsx # Browse products
|
|
260
|
+
│ ├── [id].tsx # Product detail
|
|
261
|
+
│ └── search.tsx # Search
|
|
262
|
+
└── (protected)/ # Protected routes (auth required)
|
|
263
|
+
├── cart.tsx # Shopping cart
|
|
264
|
+
├── checkout.tsx # Checkout
|
|
265
|
+
├── orders.tsx # Order history
|
|
266
|
+
└── profile.tsx # User profile
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
#### Route Guard Example:
|
|
270
|
+
|
|
271
|
+
```typescript
|
|
272
|
+
// app/(protected)/_layout.tsx
|
|
273
|
+
export default function ProtectedLayout() {
|
|
274
|
+
const { isAuthenticated } = useAuthStore();
|
|
275
|
+
const router = useRouter();
|
|
276
|
+
|
|
277
|
+
useEffect(() => {
|
|
278
|
+
if (!isAuthenticated) {
|
|
279
|
+
router.replace('/(auth)/login');
|
|
280
|
+
}
|
|
281
|
+
}, [isAuthenticated]);
|
|
282
|
+
|
|
283
|
+
if (!isAuthenticated) return null;
|
|
284
|
+
|
|
285
|
+
return <Stack />;
|
|
286
|
+
}
|
|
287
|
+
```
|
|
288
|
+
|
|
289
|
+
---
|
|
290
|
+
|
|
291
|
+
## 🔧 Configuration Guide
|
|
292
|
+
|
|
293
|
+
### Disable Mock API
|
|
294
|
+
|
|
295
|
+
If you want to connect directly to real API (skip mock):
|
|
296
|
+
|
|
297
|
+
**Update `src/utils/constants.ts`:**
|
|
298
|
+
```typescript
|
|
299
|
+
export const API_CONFIG = {
|
|
300
|
+
BASE_URL: APP_CONFIG.BASE_URL,
|
|
301
|
+
TIMEOUT: 10000,
|
|
302
|
+
MOCK_API: false, // Set to false to always use real API
|
|
303
|
+
};
|
|
304
|
+
```
|
|
305
|
+
|
|
306
|
+
Or use environment-based config:
|
|
307
|
+
```typescript
|
|
308
|
+
export const APP_CONFIG = {
|
|
309
|
+
BASE_URL: extra.BASE_URL,
|
|
310
|
+
MOCK_API: __DEV__ ? false : false, // Never use mock
|
|
311
|
+
};
|
|
312
|
+
```
|
|
313
|
+
|
|
314
|
+
### Remove Mock API Completely
|
|
315
|
+
|
|
316
|
+
If you don't need mock API at all:
|
|
317
|
+
|
|
318
|
+
```bash
|
|
319
|
+
# 1. Remove mock API folder
|
|
320
|
+
rm -rf src/services/mockApi/
|
|
321
|
+
|
|
322
|
+
# 2. Remove mock data
|
|
323
|
+
rm -rf server/
|
|
324
|
+
```
|
|
325
|
+
|
|
326
|
+
**Update all services:**
|
|
327
|
+
```typescript
|
|
328
|
+
// Before:
|
|
329
|
+
async getProducts() {
|
|
330
|
+
if (API_CONFIG.MOCK_API) {
|
|
331
|
+
return await mockApi.get('/products');
|
|
332
|
+
}
|
|
333
|
+
return await api.get('/products');
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
// After:
|
|
337
|
+
async getProducts() {
|
|
338
|
+
return await api.get('/products');
|
|
339
|
+
}
|
|
340
|
+
```
|
|
341
|
+
|
|
342
|
+
---
|
|
343
|
+
|
|
344
|
+
## 📚 Examples Reference
|
|
345
|
+
|
|
346
|
+
### Screen Examples
|
|
347
|
+
|
|
348
|
+
Located in `examples/screens/`:
|
|
349
|
+
|
|
350
|
+
1. **`list-screen-no-auth.example.tsx`**
|
|
351
|
+
- Public content list
|
|
352
|
+
- No authentication required
|
|
353
|
+
- Pull to refresh
|
|
354
|
+
- Use for: News, products, recipes
|
|
355
|
+
|
|
356
|
+
2. **`list-screen-with-auth.example.tsx`**
|
|
357
|
+
- User-specific content list
|
|
358
|
+
- Authentication required
|
|
359
|
+
- User greeting
|
|
360
|
+
- Use for: Tasks, orders, notifications
|
|
361
|
+
|
|
362
|
+
3. **`form-screen.example.tsx`**
|
|
363
|
+
- Create/edit data
|
|
364
|
+
- Form validation
|
|
365
|
+
- Works with or without auth
|
|
366
|
+
- Use for: Create product, edit profile
|
|
367
|
+
|
|
368
|
+
4. **`detail-screen.example.tsx`**
|
|
369
|
+
- Single item display
|
|
370
|
+
- Detail with actions
|
|
371
|
+
- Works with or without auth
|
|
372
|
+
- Use for: Product detail, article detail
|
|
373
|
+
|
|
374
|
+
### Service Examples
|
|
375
|
+
|
|
376
|
+
Located in `examples/services/`:
|
|
377
|
+
|
|
378
|
+
1. **`service-with-mock.example.ts`**
|
|
379
|
+
- Switches between mock and real API
|
|
380
|
+
- Use for: Apps with backend
|
|
381
|
+
|
|
382
|
+
2. **`service-without-mock.example.ts`**
|
|
383
|
+
- Direct API connection only
|
|
384
|
+
- Use for: Third-party APIs
|
|
385
|
+
|
|
386
|
+
3. **`offline-service.example.ts`**
|
|
387
|
+
- AsyncStorage-based service
|
|
388
|
+
- Use for: Offline apps
|
|
389
|
+
|
|
390
|
+
### Mini App Examples
|
|
391
|
+
|
|
392
|
+
Located in `examples/apps/`:
|
|
393
|
+
|
|
394
|
+
1. **`todo-offline/`**
|
|
395
|
+
- No auth, no API
|
|
396
|
+
- Complete offline app
|
|
397
|
+
- AsyncStorage for data
|
|
398
|
+
|
|
399
|
+
2. **`news-no-auth/`**
|
|
400
|
+
- No auth, with API
|
|
401
|
+
- Public content
|
|
402
|
+
- Mock API support
|
|
403
|
+
|
|
404
|
+
3. **`dashboard-with-auth/`**
|
|
405
|
+
- With auth, with API
|
|
406
|
+
- Protected routes
|
|
407
|
+
- User-specific data
|
|
408
|
+
|
|
409
|
+
---
|
|
410
|
+
|
|
411
|
+
## 🎯 Quick Start by App Type
|
|
412
|
+
|
|
413
|
+
### Todo/Notes App
|
|
414
|
+
```bash
|
|
415
|
+
1. Remove: app/(auth)/, src/store/authStore.ts, src/services/api.ts
|
|
416
|
+
2. Use: examples/services/offline-service.example.ts
|
|
417
|
+
3. Reference: examples/apps/todo-offline/
|
|
418
|
+
```
|
|
419
|
+
|
|
420
|
+
### News/Blog App
|
|
421
|
+
```bash
|
|
422
|
+
1. Remove: app/(auth)/, src/store/authStore.ts
|
|
423
|
+
2. Keep: API infrastructure
|
|
424
|
+
3. Reference: examples/apps/news-no-auth/
|
|
425
|
+
```
|
|
426
|
+
|
|
427
|
+
### Dashboard/SaaS App
|
|
428
|
+
```bash
|
|
429
|
+
1. Keep: Everything as-is
|
|
430
|
+
2. Add: User-specific data models
|
|
431
|
+
3. Reference: examples/apps/dashboard-with-auth/
|
|
432
|
+
```
|
|
433
|
+
|
|
434
|
+
### E-commerce App
|
|
435
|
+
```bash
|
|
436
|
+
1. Keep: Everything
|
|
437
|
+
2. Add: Public + protected route groups
|
|
438
|
+
3. Mix: Public browsing + protected checkout
|
|
439
|
+
```
|
|
440
|
+
|
|
441
|
+
---
|
|
442
|
+
|
|
443
|
+
## ✅ Checklist After Customization
|
|
444
|
+
|
|
445
|
+
- [ ] Removed unused folders (auth, mockApi, etc.)
|
|
446
|
+
- [ ] Updated `app/_layout.tsx` (removed auth check if needed)
|
|
447
|
+
- [ ] Updated `src/utils/constants.ts` (removed API config if needed)
|
|
448
|
+
- [ ] Updated services (removed mock API switching if needed)
|
|
449
|
+
- [ ] Updated `server/db.json` (removed unused collections)
|
|
450
|
+
- [ ] Tested app startup
|
|
451
|
+
- [ ] Tested navigation flow
|
|
452
|
+
- [ ] Updated `package.json` name and version
|
|
453
|
+
- [ ] Removed unused dependencies (if any)
|
|
454
|
+
|
|
455
|
+
---
|
|
456
|
+
|
|
457
|
+
## 💡 Pro Tips
|
|
458
|
+
|
|
459
|
+
1. **Start with the full template** - Easier to remove than to add
|
|
460
|
+
2. **Use examples as reference** - Don't reinvent patterns
|
|
461
|
+
3. **Test after each removal** - Make sure app still works
|
|
462
|
+
4. **Keep documentation** - Update README with your changes
|
|
463
|
+
5. **Commit before major changes** - Easy to revert if needed
|
|
464
|
+
|
|
465
|
+
---
|
|
466
|
+
|
|
467
|
+
## 🆘 Need Help?
|
|
468
|
+
|
|
469
|
+
Check these files:
|
|
470
|
+
- `AI_GUIDE.md` - AI agent instructions
|
|
471
|
+
- `README.md` - General project overview
|
|
472
|
+
- `SERVER_GUIDE.md` - Mock API documentation
|
|
473
|
+
- `CONVENTIONS.md` - Coding standards
|
|
474
|
+
- `examples/` - Working code examples
|
|
@@ -10,8 +10,12 @@
|
|
|
10
10
|
"themePath": "src/theme",
|
|
11
11
|
"mockDataPath": "server/db.json",
|
|
12
12
|
"examples": "examples",
|
|
13
|
+
"examplesScreens": "examples/screens",
|
|
14
|
+
"examplesServices": "examples/services",
|
|
15
|
+
"examplesApps": "examples/apps",
|
|
13
16
|
"aiGuide": "AI_GUIDE.md",
|
|
14
17
|
"serverGuide": "SERVER_GUIDE.md",
|
|
18
|
+
"templateVariants": "TEMPLATE_VARIANTS.md",
|
|
15
19
|
"rules": "GENERATE_RULES.md",
|
|
16
20
|
"conventions": "CONVENTIONS.md"
|
|
17
21
|
}
|