@designcrowd/fe-shared-lib 1.5.20-dts-upgrades-2 → 1.5.20
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/dist/css/tailwind-brandCrowd.css +2595 -0
- package/dist/css/tailwind-brandPage.css +2275 -0
- package/dist/css/tailwind-crazyDomains.css +2595 -0
- package/dist/css/tailwind-designCom.css +2595 -0
- package/dist/css/tailwind-designCrowd.css +2595 -0
- package/package.json +1 -2
- package/.claude/settings.local.json +0 -34
- package/.npm-publish-token +0 -1
- package/MODERNIZATION_ROADMAP.md +0 -264
- package/docs/plans/2026-01-19-typescript-declarations-design.md +0 -114
- package/docs/plans/2026-01-19-typescript-declarations-tdd-plan.md +0 -953
- package/index.d.ts +0 -309
- package/types-test/all-components.test.ts +0 -81
- package/types-test/basic-imports.test.ts +0 -16
- package/types-test/button-props.test.ts +0 -63
- package/types-test/checkbox-toggle-props.test.ts +0 -78
- package/types-test/dropdown-props.test.ts +0 -36
- package/types-test/icon-props.test.ts +0 -42
- package/types-test/loader-props.test.ts +0 -7
- package/types-test/modal-props.test.ts +0 -39
- package/types-test/select-props.test.ts +0 -97
- package/types-test/text-input-props.test.ts +0 -80
- package/types-test/textarea-props.test.ts +0 -72
- package/types-test/tsconfig.json +0 -12
|
@@ -1,953 +0,0 @@
|
|
|
1
|
-
# TypeScript Declarations TDD Implementation Plan
|
|
2
|
-
|
|
3
|
-
> **For Claude:** REQUIRED SUB-SKILL: Use superpowers:executing-plans to implement this plan task-by-task.
|
|
4
|
-
|
|
5
|
-
**Goal:** Add TypeScript declaration files to `@designcrowd/fe-shared-lib` so consumers get type checking and IDE autocomplete without converting the library to TypeScript.
|
|
6
|
-
|
|
7
|
-
**Architecture:** Create a single `index.d.ts` file at package root that declares all exports from `index.js`. Use detailed prop interfaces for the 10 most-used components and generic `DefineComponent<{}, {}, any>` stubs for the rest. Update `package.json` exports to include the types field.
|
|
8
|
-
|
|
9
|
-
**Tech Stack:** TypeScript declarations, Vue 3 `DefineComponent` type from `vue`
|
|
10
|
-
|
|
11
|
-
---
|
|
12
|
-
|
|
13
|
-
## TDD Approach for Type Declarations
|
|
14
|
-
|
|
15
|
-
For TypeScript declarations, "tests" are **compilation tests** - TypeScript files that:
|
|
16
|
-
- Import from the package
|
|
17
|
-
- Use the types in ways that should succeed (positive tests)
|
|
18
|
-
- Optionally test that invalid usage fails to compile (negative tests)
|
|
19
|
-
|
|
20
|
-
**RED** = Test file fails to compile (because types don't exist yet)
|
|
21
|
-
**GREEN** = Test file compiles successfully (types are correct)
|
|
22
|
-
|
|
23
|
-
---
|
|
24
|
-
|
|
25
|
-
## Task 1: Set Up Type Test Infrastructure
|
|
26
|
-
|
|
27
|
-
**Files:**
|
|
28
|
-
- Create: `types-test/tsconfig.json`
|
|
29
|
-
- Create: `types-test/basic-imports.test.ts`
|
|
30
|
-
|
|
31
|
-
**Step 1: Create tsconfig for type tests**
|
|
32
|
-
|
|
33
|
-
```json
|
|
34
|
-
{
|
|
35
|
-
"compilerOptions": {
|
|
36
|
-
"target": "ES2020",
|
|
37
|
-
"module": "ESNext",
|
|
38
|
-
"moduleResolution": "bundler",
|
|
39
|
-
"strict": true,
|
|
40
|
-
"noEmit": true,
|
|
41
|
-
"skipLibCheck": true,
|
|
42
|
-
"types": ["node"]
|
|
43
|
-
},
|
|
44
|
-
"include": ["*.test.ts"],
|
|
45
|
-
"references": [{ "path": ".." }]
|
|
46
|
-
}
|
|
47
|
-
```
|
|
48
|
-
|
|
49
|
-
**Step 2: Write failing test for basic imports**
|
|
50
|
-
|
|
51
|
-
```typescript
|
|
52
|
-
// types-test/basic-imports.test.ts
|
|
53
|
-
// This file tests that basic imports work - compilation = pass
|
|
54
|
-
|
|
55
|
-
import { Button, Modal, Icon, setSharedLibLocaleAsync, tr } from '..';
|
|
56
|
-
|
|
57
|
-
// If this file compiles, the basic exports are typed
|
|
58
|
-
const _button: typeof Button = Button;
|
|
59
|
-
const _modal: typeof Modal = Modal;
|
|
60
|
-
const _icon: typeof Icon = Icon;
|
|
61
|
-
|
|
62
|
-
// Test utility function types
|
|
63
|
-
async function testUtils() {
|
|
64
|
-
await setSharedLibLocaleAsync('en-US');
|
|
65
|
-
const translated: string = tr('key');
|
|
66
|
-
const translatedWithParams: string = tr('key', { name: 'test' });
|
|
67
|
-
}
|
|
68
|
-
```
|
|
69
|
-
|
|
70
|
-
**Step 3: Run test to verify it fails (RED)**
|
|
71
|
-
|
|
72
|
-
```bash
|
|
73
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
74
|
-
```
|
|
75
|
-
|
|
76
|
-
Expected: FAIL with `TS7016: Could not find a declaration file for module`
|
|
77
|
-
|
|
78
|
-
**Step 4: Commit test infrastructure**
|
|
79
|
-
|
|
80
|
-
```bash
|
|
81
|
-
git add types-test/
|
|
82
|
-
git commit -m "$(cat <<'EOF'
|
|
83
|
-
test: add type test infrastructure for TDD
|
|
84
|
-
|
|
85
|
-
Sets up TypeScript compilation tests to verify declaration files work correctly.
|
|
86
|
-
|
|
87
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
88
|
-
EOF
|
|
89
|
-
)"
|
|
90
|
-
```
|
|
91
|
-
|
|
92
|
-
---
|
|
93
|
-
|
|
94
|
-
## Task 2: Create Minimal index.d.ts Skeleton
|
|
95
|
-
|
|
96
|
-
**Files:**
|
|
97
|
-
- Create: `index.d.ts`
|
|
98
|
-
|
|
99
|
-
**Step 1: The test from Task 1 is already failing (RED)**
|
|
100
|
-
|
|
101
|
-
Verify it still fails:
|
|
102
|
-
```bash
|
|
103
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
104
|
-
```
|
|
105
|
-
|
|
106
|
-
**Step 2: Write minimal declaration file to make test pass (GREEN)**
|
|
107
|
-
|
|
108
|
-
```typescript
|
|
109
|
-
// index.d.ts
|
|
110
|
-
import { DefineComponent } from 'vue';
|
|
111
|
-
|
|
112
|
-
// ============ Utility Functions ============
|
|
113
|
-
export function setSharedLibLocaleAsync(locale?: string): Promise<void>;
|
|
114
|
-
export function tr(key: string, params?: Record<string, unknown>): string;
|
|
115
|
-
|
|
116
|
-
// ============ API Clients ============
|
|
117
|
-
export const brandPageApiClient: unknown;
|
|
118
|
-
export const brandCrowdApiClient: unknown;
|
|
119
|
-
|
|
120
|
-
// ============ Constants ============
|
|
121
|
-
export const WEBSITE_UPGRADE_CONTEXT_TYPES: Record<string, string>;
|
|
122
|
-
|
|
123
|
-
// ============ Components (Stubs) ============
|
|
124
|
-
// These will be refined in subsequent tasks
|
|
125
|
-
|
|
126
|
-
export const Button: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
127
|
-
export const Modal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
128
|
-
export const Icon: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
129
|
-
|
|
130
|
-
// ... all other components as stubs (added in Task 3)
|
|
131
|
-
```
|
|
132
|
-
|
|
133
|
-
**Step 3: Run test to verify it passes (GREEN)**
|
|
134
|
-
|
|
135
|
-
```bash
|
|
136
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
137
|
-
```
|
|
138
|
-
|
|
139
|
-
Expected: PASS (no output, exit code 0)
|
|
140
|
-
|
|
141
|
-
**Step 4: Commit**
|
|
142
|
-
|
|
143
|
-
```bash
|
|
144
|
-
git add index.d.ts
|
|
145
|
-
git commit -m "$(cat <<'EOF'
|
|
146
|
-
feat: add minimal TypeScript declaration skeleton
|
|
147
|
-
|
|
148
|
-
Initial index.d.ts with utility functions and component stubs.
|
|
149
|
-
|
|
150
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
151
|
-
EOF
|
|
152
|
-
)"
|
|
153
|
-
```
|
|
154
|
-
|
|
155
|
-
---
|
|
156
|
-
|
|
157
|
-
## Task 3: Add All Component Stub Declarations
|
|
158
|
-
|
|
159
|
-
**Files:**
|
|
160
|
-
- Modify: `index.d.ts`
|
|
161
|
-
- Create: `types-test/all-components.test.ts`
|
|
162
|
-
|
|
163
|
-
**Step 1: Write failing test for all component imports (RED)**
|
|
164
|
-
|
|
165
|
-
```typescript
|
|
166
|
-
// types-test/all-components.test.ts
|
|
167
|
-
import {
|
|
168
|
-
// Experiences
|
|
169
|
-
UploadYourLogoDropzone,
|
|
170
|
-
UploadYourLogoApplication,
|
|
171
|
-
UploadedLogoSearchResultCard,
|
|
172
|
-
SignUpModal,
|
|
173
|
-
SignUp,
|
|
174
|
-
SignIn,
|
|
175
|
-
ForgotPasswordModal,
|
|
176
|
-
ForgotPassword,
|
|
177
|
-
ResetPasswordModal,
|
|
178
|
-
ResetPassword,
|
|
179
|
-
ResetPasswordSuccessModal,
|
|
180
|
-
PaymentConfigList,
|
|
181
|
-
PaymentConfigDropdown,
|
|
182
|
-
SellDomainNameListModal,
|
|
183
|
-
SellDomainNameList,
|
|
184
|
-
SellDomainNameWidget,
|
|
185
|
-
PublishBrandPageModal,
|
|
186
|
-
PublishBrandPageCard,
|
|
187
|
-
WebsiteContextualUpgradeModal,
|
|
188
|
-
// Atoms
|
|
189
|
-
Button,
|
|
190
|
-
ButtonGroup,
|
|
191
|
-
Dropdown,
|
|
192
|
-
DropdownItem,
|
|
193
|
-
Icon,
|
|
194
|
-
DcomIcon,
|
|
195
|
-
Modal,
|
|
196
|
-
Loader,
|
|
197
|
-
Tooltip,
|
|
198
|
-
Picture,
|
|
199
|
-
HelloBar,
|
|
200
|
-
PromoCard,
|
|
201
|
-
SearchBar,
|
|
202
|
-
StarRating,
|
|
203
|
-
TabMenu,
|
|
204
|
-
TextInput,
|
|
205
|
-
TextCopyField,
|
|
206
|
-
Textarea,
|
|
207
|
-
Toggle,
|
|
208
|
-
Checkbox,
|
|
209
|
-
ColorPicker,
|
|
210
|
-
Carousel,
|
|
211
|
-
Checktile,
|
|
212
|
-
Pill,
|
|
213
|
-
PillBar,
|
|
214
|
-
Notice,
|
|
215
|
-
Masonry,
|
|
216
|
-
CollapsiblePanel,
|
|
217
|
-
Slider,
|
|
218
|
-
Price,
|
|
219
|
-
HashRouteModal,
|
|
220
|
-
Select,
|
|
221
|
-
NumberStepper,
|
|
222
|
-
CopyToClipboardText,
|
|
223
|
-
SparkleIcon,
|
|
224
|
-
// Utilities
|
|
225
|
-
setSharedLibLocaleAsync,
|
|
226
|
-
tr,
|
|
227
|
-
brandPageApiClient,
|
|
228
|
-
brandCrowdApiClient,
|
|
229
|
-
WEBSITE_UPGRADE_CONTEXT_TYPES,
|
|
230
|
-
} from '..';
|
|
231
|
-
|
|
232
|
-
// All imports should be defined
|
|
233
|
-
const components = [
|
|
234
|
-
UploadYourLogoDropzone,
|
|
235
|
-
UploadYourLogoApplication,
|
|
236
|
-
UploadedLogoSearchResultCard,
|
|
237
|
-
SignUpModal,
|
|
238
|
-
SignUp,
|
|
239
|
-
SignIn,
|
|
240
|
-
ForgotPasswordModal,
|
|
241
|
-
ForgotPassword,
|
|
242
|
-
ResetPasswordModal,
|
|
243
|
-
ResetPassword,
|
|
244
|
-
ResetPasswordSuccessModal,
|
|
245
|
-
PaymentConfigList,
|
|
246
|
-
PaymentConfigDropdown,
|
|
247
|
-
SellDomainNameListModal,
|
|
248
|
-
SellDomainNameList,
|
|
249
|
-
SellDomainNameWidget,
|
|
250
|
-
PublishBrandPageModal,
|
|
251
|
-
PublishBrandPageCard,
|
|
252
|
-
WebsiteContextualUpgradeModal,
|
|
253
|
-
Button,
|
|
254
|
-
ButtonGroup,
|
|
255
|
-
Dropdown,
|
|
256
|
-
DropdownItem,
|
|
257
|
-
Icon,
|
|
258
|
-
DcomIcon,
|
|
259
|
-
Modal,
|
|
260
|
-
Loader,
|
|
261
|
-
Tooltip,
|
|
262
|
-
Picture,
|
|
263
|
-
HelloBar,
|
|
264
|
-
PromoCard,
|
|
265
|
-
SearchBar,
|
|
266
|
-
StarRating,
|
|
267
|
-
TabMenu,
|
|
268
|
-
TextInput,
|
|
269
|
-
TextCopyField,
|
|
270
|
-
Textarea,
|
|
271
|
-
Toggle,
|
|
272
|
-
Checkbox,
|
|
273
|
-
ColorPicker,
|
|
274
|
-
Carousel,
|
|
275
|
-
Checktile,
|
|
276
|
-
Pill,
|
|
277
|
-
PillBar,
|
|
278
|
-
Notice,
|
|
279
|
-
Masonry,
|
|
280
|
-
CollapsiblePanel,
|
|
281
|
-
Slider,
|
|
282
|
-
Price,
|
|
283
|
-
HashRouteModal,
|
|
284
|
-
Select,
|
|
285
|
-
NumberStepper,
|
|
286
|
-
CopyToClipboardText,
|
|
287
|
-
SparkleIcon,
|
|
288
|
-
];
|
|
289
|
-
```
|
|
290
|
-
|
|
291
|
-
**Step 2: Run test to verify it fails (RED)**
|
|
292
|
-
|
|
293
|
-
```bash
|
|
294
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
295
|
-
```
|
|
296
|
-
|
|
297
|
-
Expected: FAIL with errors for missing exports
|
|
298
|
-
|
|
299
|
-
**Step 3: Add all component stubs to index.d.ts (GREEN)**
|
|
300
|
-
|
|
301
|
-
Add to `index.d.ts`:
|
|
302
|
-
|
|
303
|
-
```typescript
|
|
304
|
-
// ============ Experience Components (Stubs) ============
|
|
305
|
-
export const UploadYourLogoDropzone: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
306
|
-
export const UploadYourLogoApplication: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
307
|
-
export const UploadedLogoSearchResultCard: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
308
|
-
export const SignUpModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
309
|
-
export const SignUp: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
310
|
-
export const SignIn: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
311
|
-
export const ForgotPasswordModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
312
|
-
export const ForgotPassword: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
313
|
-
export const ResetPasswordModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
314
|
-
export const ResetPassword: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
315
|
-
export const ResetPasswordSuccessModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
316
|
-
export const PaymentConfigList: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
317
|
-
export const PaymentConfigDropdown: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
318
|
-
export const SellDomainNameListModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
319
|
-
export const SellDomainNameList: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
320
|
-
export const SellDomainNameWidget: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
321
|
-
export const PublishBrandPageModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
322
|
-
export const PublishBrandPageCard: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
323
|
-
export const WebsiteContextualUpgradeModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
324
|
-
|
|
325
|
-
// ============ Atom Components (Stubs) ============
|
|
326
|
-
export const ButtonGroup: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
327
|
-
export const Dropdown: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
328
|
-
export const DropdownItem: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
329
|
-
export const DcomIcon: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
330
|
-
export const Loader: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
331
|
-
export const Tooltip: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
332
|
-
export const Picture: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
333
|
-
export const HelloBar: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
334
|
-
export const PromoCard: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
335
|
-
export const SearchBar: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
336
|
-
export const StarRating: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
337
|
-
export const TabMenu: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
338
|
-
export const TextCopyField: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
339
|
-
export const ColorPicker: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
340
|
-
export const Carousel: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
341
|
-
export const Checktile: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
342
|
-
export const Pill: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
343
|
-
export const PillBar: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
344
|
-
export const Notice: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
345
|
-
export const Masonry: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
346
|
-
export const CollapsiblePanel: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
347
|
-
export const Slider: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
348
|
-
export const Price: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
349
|
-
export const HashRouteModal: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
350
|
-
export const NumberStepper: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
351
|
-
export const CopyToClipboardText: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
352
|
-
export const SparkleIcon: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
353
|
-
|
|
354
|
-
// Detailed components (will be typed in subsequent tasks)
|
|
355
|
-
export const TextInput: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
356
|
-
export const Textarea: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
357
|
-
export const Toggle: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
358
|
-
export const Checkbox: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
359
|
-
export const Select: DefineComponent<Record<string, unknown>, Record<string, unknown>, unknown>;
|
|
360
|
-
```
|
|
361
|
-
|
|
362
|
-
**Step 4: Run test to verify it passes (GREEN)**
|
|
363
|
-
|
|
364
|
-
```bash
|
|
365
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
366
|
-
```
|
|
367
|
-
|
|
368
|
-
Expected: PASS
|
|
369
|
-
|
|
370
|
-
**Step 5: Commit**
|
|
371
|
-
|
|
372
|
-
```bash
|
|
373
|
-
git add index.d.ts types-test/all-components.test.ts
|
|
374
|
-
git commit -m "$(cat <<'EOF'
|
|
375
|
-
feat: add stub declarations for all components
|
|
376
|
-
|
|
377
|
-
All 55 exported components now have TypeScript declarations (as generic stubs).
|
|
378
|
-
|
|
379
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
380
|
-
EOF
|
|
381
|
-
)"
|
|
382
|
-
```
|
|
383
|
-
|
|
384
|
-
---
|
|
385
|
-
|
|
386
|
-
## Task 4: Add Detailed Button Props Interface
|
|
387
|
-
|
|
388
|
-
**Files:**
|
|
389
|
-
- Modify: `index.d.ts`
|
|
390
|
-
- Create: `types-test/button-props.test.ts`
|
|
391
|
-
|
|
392
|
-
**Step 1: Write failing test for Button props (RED)**
|
|
393
|
-
|
|
394
|
-
```typescript
|
|
395
|
-
// types-test/button-props.test.ts
|
|
396
|
-
import { Button } from '..';
|
|
397
|
-
import type { ComponentProps } from 'vue';
|
|
398
|
-
|
|
399
|
-
// Test that Button accepts specific props
|
|
400
|
-
// This will fail until we add detailed ButtonProps
|
|
401
|
-
|
|
402
|
-
type ButtonProps = ComponentProps<typeof Button>;
|
|
403
|
-
|
|
404
|
-
// These should all be valid
|
|
405
|
-
const validProps: ButtonProps = {
|
|
406
|
-
label: 'Click me',
|
|
407
|
-
variant: 'primary',
|
|
408
|
-
size: 'medium',
|
|
409
|
-
disabled: false,
|
|
410
|
-
isBusy: true,
|
|
411
|
-
fullWidth: false,
|
|
412
|
-
icon: 'chevron-right',
|
|
413
|
-
url: 'https://example.com',
|
|
414
|
-
theme: 'brandCrowd',
|
|
415
|
-
};
|
|
416
|
-
|
|
417
|
-
// Test specific prop types
|
|
418
|
-
const label: ButtonProps['label'] = 'test';
|
|
419
|
-
const variant: ButtonProps['variant'] = 'primary';
|
|
420
|
-
const disabled: ButtonProps['disabled'] = true;
|
|
421
|
-
```
|
|
422
|
-
|
|
423
|
-
**Step 2: Run test to verify it fails (RED)**
|
|
424
|
-
|
|
425
|
-
```bash
|
|
426
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
427
|
-
```
|
|
428
|
-
|
|
429
|
-
Expected: FAIL - props are typed as `unknown` so specific assignments fail
|
|
430
|
-
|
|
431
|
-
**Step 3: Add detailed ButtonProps interface (GREEN)**
|
|
432
|
-
|
|
433
|
-
Update `index.d.ts` - replace the Button stub with:
|
|
434
|
-
|
|
435
|
-
```typescript
|
|
436
|
-
// ============ Detailed Component Types ============
|
|
437
|
-
|
|
438
|
-
export interface ButtonProps {
|
|
439
|
-
attrs?: Record<string, unknown>;
|
|
440
|
-
label?: string;
|
|
441
|
-
url?: string;
|
|
442
|
-
theme?: 'brandCrowd' | 'crazyDomains' | string;
|
|
443
|
-
variant?: 'primary' | 'secondary' | 'success' | 'outline' | 'outline-primary' | 'outline-success' | 'outline-no-hover' | 'warning' | 'info' | 'info-filled' | 'gray' | 'no-border' | 'flat' | 'pill' | 'dark-mode-pill' | 'ai' | 'primary-with-icon' | string;
|
|
444
|
-
size?: 'small' | 'small-wide' | 'small-medium' | 'medium' | 'large' | string | null;
|
|
445
|
-
iconSize?: 'xs' | 'sm' | 'md' | 'lg' | 'xl' | string;
|
|
446
|
-
icon?: string;
|
|
447
|
-
iconViewBox?: string;
|
|
448
|
-
iconLeft?: string;
|
|
449
|
-
iconLeftSize?: string;
|
|
450
|
-
iconRight?: string;
|
|
451
|
-
iconRightSize?: string;
|
|
452
|
-
iconTop?: string;
|
|
453
|
-
iconTopSize?: string;
|
|
454
|
-
iconColor?: string;
|
|
455
|
-
fullWidth?: boolean;
|
|
456
|
-
fullHeight?: boolean;
|
|
457
|
-
classes?: string | Record<string, boolean>;
|
|
458
|
-
containerClasses?: string;
|
|
459
|
-
greyOutLeft?: boolean;
|
|
460
|
-
white?: boolean;
|
|
461
|
-
rounded?: boolean;
|
|
462
|
-
roundedLeft?: boolean;
|
|
463
|
-
roundedRight?: boolean;
|
|
464
|
-
disabled?: boolean;
|
|
465
|
-
isBusy?: boolean;
|
|
466
|
-
isBusyLabel?: string;
|
|
467
|
-
download?: string;
|
|
468
|
-
active?: boolean;
|
|
469
|
-
target?: '_self' | '_blank' | '_parent' | '_top' | string;
|
|
470
|
-
justify?: 'center' | 'between' | string;
|
|
471
|
-
type?: 'button' | 'submit' | 'reset' | string;
|
|
472
|
-
showLabel?: boolean;
|
|
473
|
-
dataAttribute?: string;
|
|
474
|
-
altText?: string;
|
|
475
|
-
}
|
|
476
|
-
|
|
477
|
-
export interface ButtonEmits {
|
|
478
|
-
'on-click': [event: Event];
|
|
479
|
-
}
|
|
480
|
-
|
|
481
|
-
export const Button: DefineComponent<ButtonProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, ButtonEmits>;
|
|
482
|
-
```
|
|
483
|
-
|
|
484
|
-
**Step 4: Run test to verify it passes (GREEN)**
|
|
485
|
-
|
|
486
|
-
```bash
|
|
487
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
488
|
-
```
|
|
489
|
-
|
|
490
|
-
Expected: PASS
|
|
491
|
-
|
|
492
|
-
**Step 5: Commit**
|
|
493
|
-
|
|
494
|
-
```bash
|
|
495
|
-
git add index.d.ts types-test/button-props.test.ts
|
|
496
|
-
git commit -m "$(cat <<'EOF'
|
|
497
|
-
feat: add detailed ButtonProps interface
|
|
498
|
-
|
|
499
|
-
Button component now has full prop type definitions with IDE autocomplete.
|
|
500
|
-
|
|
501
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
502
|
-
EOF
|
|
503
|
-
)"
|
|
504
|
-
```
|
|
505
|
-
|
|
506
|
-
---
|
|
507
|
-
|
|
508
|
-
## Task 5: Add Detailed Modal Props Interface
|
|
509
|
-
|
|
510
|
-
**Files:**
|
|
511
|
-
- Modify: `index.d.ts`
|
|
512
|
-
- Create: `types-test/modal-props.test.ts`
|
|
513
|
-
|
|
514
|
-
**Step 1: Write failing test for Modal props (RED)**
|
|
515
|
-
|
|
516
|
-
```typescript
|
|
517
|
-
// types-test/modal-props.test.ts
|
|
518
|
-
import { Modal } from '..';
|
|
519
|
-
import type { ComponentProps } from 'vue';
|
|
520
|
-
|
|
521
|
-
type ModalProps = ComponentProps<typeof Modal>;
|
|
522
|
-
|
|
523
|
-
const validProps: ModalProps = {
|
|
524
|
-
visible: true,
|
|
525
|
-
mandatory: false,
|
|
526
|
-
size: 'md',
|
|
527
|
-
closeOnEsc: true,
|
|
528
|
-
};
|
|
529
|
-
|
|
530
|
-
const visible: ModalProps['visible'] = true;
|
|
531
|
-
const size: ModalProps['size'] = 'xl';
|
|
532
|
-
```
|
|
533
|
-
|
|
534
|
-
**Step 2: Run test to verify RED, then add ModalProps (GREEN)**
|
|
535
|
-
|
|
536
|
-
```typescript
|
|
537
|
-
export interface ModalProps {
|
|
538
|
-
simple?: boolean;
|
|
539
|
-
removeHorizontalMargin?: boolean;
|
|
540
|
-
removeHorizontalPadding?: boolean;
|
|
541
|
-
visible?: boolean;
|
|
542
|
-
mandatory?: boolean;
|
|
543
|
-
mode?: 'image' | string;
|
|
544
|
-
classes?: string | Record<string, boolean>;
|
|
545
|
-
contentClasses?: string[];
|
|
546
|
-
size?: 'md' | 'xl' | string;
|
|
547
|
-
fullScreenBreakpoint?: 'sm' | string;
|
|
548
|
-
closeOnEsc?: boolean;
|
|
549
|
-
hideScrollbar?: boolean;
|
|
550
|
-
showModalBackgroundImage?: boolean;
|
|
551
|
-
disableBodyScrollOnVisible?: boolean;
|
|
552
|
-
darkOverlay?: boolean;
|
|
553
|
-
transparentModal?: boolean;
|
|
554
|
-
}
|
|
555
|
-
|
|
556
|
-
export interface ModalEmits {
|
|
557
|
-
'close-modal': [event?: Event];
|
|
558
|
-
}
|
|
559
|
-
|
|
560
|
-
export const Modal: DefineComponent<ModalProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, ModalEmits>;
|
|
561
|
-
```
|
|
562
|
-
|
|
563
|
-
**Step 3: Run test, verify pass, commit**
|
|
564
|
-
|
|
565
|
-
```bash
|
|
566
|
-
git add index.d.ts types-test/modal-props.test.ts
|
|
567
|
-
git commit -m "$(cat <<'EOF'
|
|
568
|
-
feat: add detailed ModalProps interface
|
|
569
|
-
|
|
570
|
-
Modal component now has full prop type definitions.
|
|
571
|
-
|
|
572
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
573
|
-
EOF
|
|
574
|
-
)"
|
|
575
|
-
```
|
|
576
|
-
|
|
577
|
-
---
|
|
578
|
-
|
|
579
|
-
## Task 6: Add Detailed Icon Props Interface
|
|
580
|
-
|
|
581
|
-
**Files:**
|
|
582
|
-
- Modify: `index.d.ts`
|
|
583
|
-
- Create: `types-test/icon-props.test.ts`
|
|
584
|
-
|
|
585
|
-
**Step 1: Write failing test, then implement (RED → GREEN)**
|
|
586
|
-
|
|
587
|
-
```typescript
|
|
588
|
-
// types-test/icon-props.test.ts
|
|
589
|
-
import { Icon } from '..';
|
|
590
|
-
import type { ComponentProps } from 'vue';
|
|
591
|
-
|
|
592
|
-
type IconProps = ComponentProps<typeof Icon>;
|
|
593
|
-
|
|
594
|
-
const validProps: IconProps = {
|
|
595
|
-
name: 'chevron-right',
|
|
596
|
-
size: 'md',
|
|
597
|
-
color: 'primary-500',
|
|
598
|
-
};
|
|
599
|
-
```
|
|
600
|
-
|
|
601
|
-
**Step 2: Add IconProps interface**
|
|
602
|
-
|
|
603
|
-
```typescript
|
|
604
|
-
export interface IconProps {
|
|
605
|
-
viewBox?: string;
|
|
606
|
-
name: string;
|
|
607
|
-
altText?: string | null;
|
|
608
|
-
color?: string;
|
|
609
|
-
size?: 'xs' | 'sm' | 'md' | 'lg' | 'xl' | '2xl' | '3xl' | '4xl' | '5xl' | 'full' | 'button-icon' | string;
|
|
610
|
-
classes?: string;
|
|
611
|
-
}
|
|
612
|
-
|
|
613
|
-
export const Icon: DefineComponent<IconProps>;
|
|
614
|
-
```
|
|
615
|
-
|
|
616
|
-
**Step 3: Commit**
|
|
617
|
-
|
|
618
|
-
---
|
|
619
|
-
|
|
620
|
-
## Task 7: Add Detailed TextInput Props Interface
|
|
621
|
-
|
|
622
|
-
**Files:**
|
|
623
|
-
- Modify: `index.d.ts`
|
|
624
|
-
- Create: `types-test/text-input-props.test.ts`
|
|
625
|
-
|
|
626
|
-
**Step 1: Write test then implement**
|
|
627
|
-
|
|
628
|
-
```typescript
|
|
629
|
-
export interface TextInputProps {
|
|
630
|
-
// From FormControlMixin
|
|
631
|
-
attrs?: Record<string, unknown>;
|
|
632
|
-
modelValue?: string | number;
|
|
633
|
-
id?: string;
|
|
634
|
-
placeholder?: string;
|
|
635
|
-
size?: 'sm' | string;
|
|
636
|
-
label?: string;
|
|
637
|
-
showLabelScreenReaderOnly?: boolean;
|
|
638
|
-
icon?: string;
|
|
639
|
-
required?: boolean;
|
|
640
|
-
error?: boolean;
|
|
641
|
-
warning?: boolean;
|
|
642
|
-
success?: boolean;
|
|
643
|
-
disabled?: boolean;
|
|
644
|
-
readonly?: boolean;
|
|
645
|
-
name?: string;
|
|
646
|
-
maxlength?: number;
|
|
647
|
-
minlength?: number;
|
|
648
|
-
isSpaceDisabled?: boolean;
|
|
649
|
-
requiredMessage?: string;
|
|
650
|
-
// TextInput-specific
|
|
651
|
-
type?: 'text' | 'password' | 'email' | 'number' | 'tel' | 'url' | string;
|
|
652
|
-
enableClear?: boolean;
|
|
653
|
-
enableClearConfirmation?: boolean;
|
|
654
|
-
borderLeft?: boolean;
|
|
655
|
-
borderRight?: boolean;
|
|
656
|
-
prefixText?: string;
|
|
657
|
-
elementClasses?: string;
|
|
658
|
-
}
|
|
659
|
-
|
|
660
|
-
export interface TextInputEmits {
|
|
661
|
-
'update:modelValue': [value: string | number];
|
|
662
|
-
'input': [value: string | number];
|
|
663
|
-
'keyup': [value: string | number];
|
|
664
|
-
'keydown': [value: string | number];
|
|
665
|
-
'focus': [value: string | number];
|
|
666
|
-
'blur': [value: string | number];
|
|
667
|
-
'enter-key-up': [value: string | number];
|
|
668
|
-
'on-clear': [];
|
|
669
|
-
'on-clear-confirmation': [];
|
|
670
|
-
}
|
|
671
|
-
|
|
672
|
-
export const TextInput: DefineComponent<TextInputProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, TextInputEmits>;
|
|
673
|
-
```
|
|
674
|
-
|
|
675
|
-
---
|
|
676
|
-
|
|
677
|
-
## Task 8: Add Detailed Textarea Props Interface
|
|
678
|
-
|
|
679
|
-
**Step 1: Add TextareaProps (extends FormControlMixin props + textarea-specific)**
|
|
680
|
-
|
|
681
|
-
```typescript
|
|
682
|
-
export interface TextareaProps {
|
|
683
|
-
// From FormControlMixin (same as TextInput)
|
|
684
|
-
attrs?: Record<string, unknown>;
|
|
685
|
-
modelValue?: string | number;
|
|
686
|
-
id?: string;
|
|
687
|
-
placeholder?: string;
|
|
688
|
-
size?: 'sm' | 'md' | 'lg' | string;
|
|
689
|
-
label?: string;
|
|
690
|
-
showLabelScreenReaderOnly?: boolean;
|
|
691
|
-
icon?: string;
|
|
692
|
-
required?: boolean;
|
|
693
|
-
error?: boolean;
|
|
694
|
-
warning?: boolean;
|
|
695
|
-
success?: boolean;
|
|
696
|
-
disabled?: boolean;
|
|
697
|
-
readonly?: boolean;
|
|
698
|
-
name?: string;
|
|
699
|
-
maxlength?: number;
|
|
700
|
-
minlength?: number;
|
|
701
|
-
isSpaceDisabled?: boolean;
|
|
702
|
-
requiredMessage?: string;
|
|
703
|
-
// Textarea-specific
|
|
704
|
-
resize?: boolean;
|
|
705
|
-
shouldAutoFitContent?: boolean;
|
|
706
|
-
elementClasses?: string;
|
|
707
|
-
}
|
|
708
|
-
|
|
709
|
-
export const Textarea: DefineComponent<TextareaProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, TextInputEmits>;
|
|
710
|
-
```
|
|
711
|
-
|
|
712
|
-
---
|
|
713
|
-
|
|
714
|
-
## Task 9: Add Detailed Checkbox and Toggle Props Interfaces
|
|
715
|
-
|
|
716
|
-
```typescript
|
|
717
|
-
export interface CheckboxProps {
|
|
718
|
-
modelValue: boolean;
|
|
719
|
-
id: string;
|
|
720
|
-
label?: string;
|
|
721
|
-
showLabelScreenReaderOnly?: boolean;
|
|
722
|
-
inline?: boolean;
|
|
723
|
-
required?: boolean;
|
|
724
|
-
disabled?: boolean;
|
|
725
|
-
color?: 'success' | 'info' | 'error' | 'warning' | 'primary' | string;
|
|
726
|
-
size?: 'sm' | 'md' | string;
|
|
727
|
-
showBorder?: boolean;
|
|
728
|
-
classes?: string | Record<string, boolean>;
|
|
729
|
-
}
|
|
730
|
-
|
|
731
|
-
export interface CheckboxEmits {
|
|
732
|
-
'update:modelValue': [value: boolean];
|
|
733
|
-
}
|
|
734
|
-
|
|
735
|
-
export const Checkbox: DefineComponent<CheckboxProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, CheckboxEmits>;
|
|
736
|
-
|
|
737
|
-
// Toggle uses same props as Checkbox
|
|
738
|
-
export const Toggle: DefineComponent<CheckboxProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, CheckboxEmits>;
|
|
739
|
-
```
|
|
740
|
-
|
|
741
|
-
---
|
|
742
|
-
|
|
743
|
-
## Task 10: Add Detailed Dropdown Props Interface
|
|
744
|
-
|
|
745
|
-
```typescript
|
|
746
|
-
export interface DropdownProps {
|
|
747
|
-
menuAlign?: 'left' | 'right' | string;
|
|
748
|
-
title?: string;
|
|
749
|
-
elementClasses?: string;
|
|
750
|
-
menuElementClasses?: string;
|
|
751
|
-
disabled?: boolean;
|
|
752
|
-
show?: boolean;
|
|
753
|
-
iconSize?: 'xs' | 'sm' | 'md' | 'lg' | string;
|
|
754
|
-
tooltip?: string;
|
|
755
|
-
}
|
|
756
|
-
|
|
757
|
-
export interface DropdownEmits {
|
|
758
|
-
'update:show': [value: boolean];
|
|
759
|
-
}
|
|
760
|
-
|
|
761
|
-
export const Dropdown: DefineComponent<DropdownProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, DropdownEmits>;
|
|
762
|
-
```
|
|
763
|
-
|
|
764
|
-
---
|
|
765
|
-
|
|
766
|
-
## Task 11: Add Detailed Select Props Interface
|
|
767
|
-
|
|
768
|
-
```typescript
|
|
769
|
-
export interface SelectOption {
|
|
770
|
-
$isDisabled?: boolean;
|
|
771
|
-
isCustom?: boolean;
|
|
772
|
-
label?: string;
|
|
773
|
-
[key: string]: unknown;
|
|
774
|
-
}
|
|
775
|
-
|
|
776
|
-
export interface SelectProps {
|
|
777
|
-
// From selectMixin
|
|
778
|
-
isInternalSearch?: boolean;
|
|
779
|
-
options: SelectOption[] | string[];
|
|
780
|
-
modelValue?: string | SelectOption | null;
|
|
781
|
-
trackBy?: string | null;
|
|
782
|
-
label?: string;
|
|
783
|
-
imageUrlField?: string | null;
|
|
784
|
-
isSearchable?: boolean;
|
|
785
|
-
shouldHideSelected?: boolean;
|
|
786
|
-
placeholder?: string;
|
|
787
|
-
shouldAllowEmpty?: boolean;
|
|
788
|
-
shouldResetAfter?: boolean;
|
|
789
|
-
shouldCloseOnSelect?: boolean;
|
|
790
|
-
customLabel?: (option: SelectOption | string, label?: string) => string;
|
|
791
|
-
shouldAllowCustom?: boolean;
|
|
792
|
-
customPlaceholder?: string;
|
|
793
|
-
customPosition?: 'top' | 'bottom' | string;
|
|
794
|
-
id?: string | null;
|
|
795
|
-
optionsLimit?: number;
|
|
796
|
-
shouldPreserveSearch?: boolean;
|
|
797
|
-
shouldPreselectFirst?: boolean;
|
|
798
|
-
shouldPreventAutofocus?: boolean;
|
|
799
|
-
isDisabled?: boolean;
|
|
800
|
-
// From Select.vue
|
|
801
|
-
name?: string;
|
|
802
|
-
selectLabel?: string;
|
|
803
|
-
selectedLabel?: string;
|
|
804
|
-
deselectLabel?: string;
|
|
805
|
-
shouldShowLabels?: boolean;
|
|
806
|
-
maxHeight?: number;
|
|
807
|
-
isLoading?: boolean;
|
|
808
|
-
openDirection?: 'above' | 'below' | 'top' | 'bottom' | string;
|
|
809
|
-
shouldShowNoResults?: boolean;
|
|
810
|
-
tabindex?: number;
|
|
811
|
-
shouldSelectExactMatchOnBlur?: boolean;
|
|
812
|
-
isInvalid?: boolean;
|
|
813
|
-
}
|
|
814
|
-
|
|
815
|
-
export interface SelectEmits {
|
|
816
|
-
'update:modelValue': [option: SelectOption | string | null, id?: string | null];
|
|
817
|
-
'search-change': [search: string, id?: string | null];
|
|
818
|
-
'remove': [option: SelectOption | string, id?: string | null];
|
|
819
|
-
'open': [id?: string | null];
|
|
820
|
-
'close': [value: SelectOption | string | null, id?: string | null];
|
|
821
|
-
'custom': [label: string, id?: string | null];
|
|
822
|
-
}
|
|
823
|
-
|
|
824
|
-
export const Select: DefineComponent<SelectProps, Record<string, unknown>, unknown, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, Record<string, unknown>, SelectEmits>;
|
|
825
|
-
```
|
|
826
|
-
|
|
827
|
-
---
|
|
828
|
-
|
|
829
|
-
## Task 12: Add Loader Props Interface
|
|
830
|
-
|
|
831
|
-
```typescript
|
|
832
|
-
// Loader has no props - it's a simple SVG spinner
|
|
833
|
-
export interface LoaderProps {}
|
|
834
|
-
|
|
835
|
-
export const Loader: DefineComponent<LoaderProps>;
|
|
836
|
-
```
|
|
837
|
-
|
|
838
|
-
---
|
|
839
|
-
|
|
840
|
-
## Task 13: Update package.json Exports
|
|
841
|
-
|
|
842
|
-
**Files:**
|
|
843
|
-
- Modify: `package.json`
|
|
844
|
-
|
|
845
|
-
**Step 1: Write failing test that verifies types field is recognized**
|
|
846
|
-
|
|
847
|
-
The test infrastructure already validates this - if the types field is missing, the imports would fail.
|
|
848
|
-
|
|
849
|
-
**Step 2: Update package.json exports**
|
|
850
|
-
|
|
851
|
-
Add `"types"` field to the exports:
|
|
852
|
-
|
|
853
|
-
```json
|
|
854
|
-
{
|
|
855
|
-
"exports": {
|
|
856
|
-
".": {
|
|
857
|
-
"types": "./index.d.ts",
|
|
858
|
-
"require": "./index.cjs",
|
|
859
|
-
"import": "./index.js"
|
|
860
|
-
},
|
|
861
|
-
"./src/*.vue": {
|
|
862
|
-
"import": "./src/*.vue"
|
|
863
|
-
},
|
|
864
|
-
"./src/*.js": {
|
|
865
|
-
"import": "./src/*.js"
|
|
866
|
-
}
|
|
867
|
-
}
|
|
868
|
-
}
|
|
869
|
-
```
|
|
870
|
-
|
|
871
|
-
**Step 3: Run all type tests to verify (GREEN)**
|
|
872
|
-
|
|
873
|
-
```bash
|
|
874
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
875
|
-
```
|
|
876
|
-
|
|
877
|
-
**Step 4: Commit**
|
|
878
|
-
|
|
879
|
-
```bash
|
|
880
|
-
git add package.json
|
|
881
|
-
git commit -m "$(cat <<'EOF'
|
|
882
|
-
feat: add types field to package.json exports
|
|
883
|
-
|
|
884
|
-
Consumers will now automatically get TypeScript declarations.
|
|
885
|
-
|
|
886
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
887
|
-
EOF
|
|
888
|
-
)"
|
|
889
|
-
```
|
|
890
|
-
|
|
891
|
-
---
|
|
892
|
-
|
|
893
|
-
## Task 14: Final Verification and Cleanup
|
|
894
|
-
|
|
895
|
-
**Step 1: Run full type check**
|
|
896
|
-
|
|
897
|
-
```bash
|
|
898
|
-
cd /home/zknowles/repos/fe-shared-lib && npx tsc -p types-test/tsconfig.json --noEmit
|
|
899
|
-
```
|
|
900
|
-
|
|
901
|
-
**Step 2: Verify lint passes**
|
|
902
|
-
|
|
903
|
-
```bash
|
|
904
|
-
npm run lint
|
|
905
|
-
```
|
|
906
|
-
|
|
907
|
-
**Step 3: Final commit combining all declaration files**
|
|
908
|
-
|
|
909
|
-
```bash
|
|
910
|
-
git add -A
|
|
911
|
-
git commit -m "$(cat <<'EOF'
|
|
912
|
-
feat: complete TypeScript declarations for fe-shared-lib
|
|
913
|
-
|
|
914
|
-
- Full prop interfaces for 10 most-used components (Button, Modal, Icon,
|
|
915
|
-
TextInput, Textarea, Checkbox, Toggle, Dropdown, Select, Loader)
|
|
916
|
-
- Generic stubs for remaining 45+ components
|
|
917
|
-
- Type-safe utility functions (setSharedLibLocaleAsync, tr)
|
|
918
|
-
- Comprehensive type tests validating all exports
|
|
919
|
-
|
|
920
|
-
Resolves TS7016 errors in consuming projects like BrandCrowd.Nuxt.
|
|
921
|
-
|
|
922
|
-
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
|
|
923
|
-
EOF
|
|
924
|
-
)"
|
|
925
|
-
```
|
|
926
|
-
|
|
927
|
-
---
|
|
928
|
-
|
|
929
|
-
## Verification Checklist
|
|
930
|
-
|
|
931
|
-
Before marking complete:
|
|
932
|
-
|
|
933
|
-
- [ ] `index.d.ts` exists at package root
|
|
934
|
-
- [ ] All 55 exports from `index.js` have declarations
|
|
935
|
-
- [ ] 10 most-used components have detailed prop interfaces
|
|
936
|
-
- [ ] `package.json` has `"types": "./index.d.ts"` in exports
|
|
937
|
-
- [ ] All type tests pass: `npx tsc -p types-test/tsconfig.json --noEmit`
|
|
938
|
-
- [ ] Lint passes: `npm run lint`
|
|
939
|
-
- [ ] Each task had a failing test before implementation
|
|
940
|
-
|
|
941
|
-
---
|
|
942
|
-
|
|
943
|
-
## Post-Implementation: Consumer Testing
|
|
944
|
-
|
|
945
|
-
After publishing, verify in BrandCrowd.Nuxt:
|
|
946
|
-
|
|
947
|
-
```bash
|
|
948
|
-
# In BrandCrowd.Nuxt directory
|
|
949
|
-
npm link ../fe-shared-lib
|
|
950
|
-
npx vue-tsc --noEmit
|
|
951
|
-
```
|
|
952
|
-
|
|
953
|
-
Expected: TS7016 errors for `@designcrowd/fe-shared-lib` should be resolved.
|