@iblai/mcp 1.0.0 → 1.1.3

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 (66) hide show
  1. package/README.md +95 -142
  2. package/dist/index.js +129 -97
  3. package/dist/index.js.map +1 -1
  4. package/dist/prompts/create-playwright-test.d.ts +2 -0
  5. package/dist/prompts/create-playwright-test.d.ts.map +1 -0
  6. package/dist/prompts/create-playwright-test.js +99 -0
  7. package/dist/prompts/create-playwright-test.js.map +1 -0
  8. package/dist/prompts/index.d.ts +4 -0
  9. package/dist/prompts/index.d.ts.map +1 -0
  10. package/dist/prompts/index.js +4 -0
  11. package/dist/prompts/index.js.map +1 -0
  12. package/dist/prompts/setup-e2e-testing.d.ts +2 -0
  13. package/dist/prompts/setup-e2e-testing.d.ts.map +1 -0
  14. package/dist/prompts/setup-e2e-testing.js +162 -0
  15. package/dist/prompts/setup-e2e-testing.js.map +1 -0
  16. package/dist/prompts/setup-new-app.d.ts +2 -0
  17. package/dist/prompts/setup-new-app.d.ts.map +1 -0
  18. package/dist/prompts/setup-new-app.js +226 -0
  19. package/dist/prompts/setup-new-app.js.map +1 -0
  20. package/dist/resources/data-layer.js +14 -14
  21. package/dist/resources/guides-layout.js +5 -5
  22. package/dist/resources/guides-playwright.d.ts +8 -0
  23. package/dist/resources/guides-playwright.d.ts.map +1 -0
  24. package/dist/resources/guides-playwright.js +235 -0
  25. package/dist/resources/guides-playwright.js.map +1 -0
  26. package/dist/resources/guides-rbac.js +2 -2
  27. package/dist/resources/guides-theme.js +4 -4
  28. package/dist/resources/index.d.ts +3 -1
  29. package/dist/resources/index.d.ts.map +1 -1
  30. package/dist/resources/index.js +5 -1
  31. package/dist/resources/index.js.map +1 -1
  32. package/dist/resources/packages-overview.d.ts.map +1 -1
  33. package/dist/resources/packages-overview.js +12 -6
  34. package/dist/resources/packages-overview.js.map +1 -1
  35. package/dist/resources/packages-playwright.d.ts +8 -0
  36. package/dist/resources/packages-playwright.d.ts.map +1 -0
  37. package/dist/resources/packages-playwright.js +161 -0
  38. package/dist/resources/packages-playwright.js.map +1 -0
  39. package/dist/resources/web-containers.d.ts.map +1 -1
  40. package/dist/resources/web-containers.js +82 -22
  41. package/dist/resources/web-containers.js.map +1 -1
  42. package/dist/resources/web-utils.d.ts.map +1 -1
  43. package/dist/resources/web-utils.js +46 -9
  44. package/dist/resources/web-utils.js.map +1 -1
  45. package/dist/tools/api-query-info.d.ts.map +1 -1
  46. package/dist/tools/api-query-info.js +248 -238
  47. package/dist/tools/api-query-info.js.map +1 -1
  48. package/dist/tools/component-info.d.ts.map +1 -1
  49. package/dist/tools/component-info.js +945 -469
  50. package/dist/tools/component-info.js.map +1 -1
  51. package/dist/tools/hook-info.d.ts.map +1 -1
  52. package/dist/tools/hook-info.js +229 -98
  53. package/dist/tools/hook-info.js.map +1 -1
  54. package/dist/tools/index.d.ts +15 -1
  55. package/dist/tools/index.d.ts.map +1 -1
  56. package/dist/tools/index.js +3 -1
  57. package/dist/tools/index.js.map +1 -1
  58. package/dist/tools/page-template.js +8 -8
  59. package/dist/tools/page-template.js.map +1 -1
  60. package/dist/tools/playwright-helper-info.d.ts +16 -0
  61. package/dist/tools/playwright-helper-info.d.ts.map +1 -0
  62. package/dist/tools/playwright-helper-info.js +849 -0
  63. package/dist/tools/playwright-helper-info.js.map +1 -0
  64. package/dist/tools/provider-setup.js +4 -4
  65. package/dist/tools/provider-setup.js.map +1 -1
  66. package/package.json +19 -6
@@ -19,18 +19,17 @@ const components = {
19
19
  Button: `# Button Component
20
20
 
21
21
  \`\`\`typescript
22
- import { Button } from '@iblai/web-containers';
22
+ import { Button } from '@iblai/iblai-js/web-containers';
23
23
 
24
- interface ButtonProps {
25
- variant?: 'default' | 'destructive' | 'outline' | 'secondary' | 'ghost' | 'link';
26
- size?: 'default' | 'sm' | 'lg' | 'icon';
24
+ interface ButtonProps extends React.ButtonHTMLAttributes<HTMLButtonElement>,
25
+ VariantProps<typeof buttonVariants> {
27
26
  asChild?: boolean;
28
- disabled?: boolean;
29
- className?: string;
30
- onClick?: () => void;
31
- children: React.ReactNode;
32
27
  }
33
28
 
29
+ // Variants
30
+ // variant: 'default' | 'destructive' | 'outline' | 'secondary' | 'ghost' | 'link'
31
+ // size: 'default' | 'sm' | 'lg' | 'icon'
32
+
34
33
  // Examples
35
34
  <Button>Click me</Button>
36
35
  <Button variant="destructive">Delete</Button>
@@ -56,7 +55,7 @@ import {
56
55
  CardDescription,
57
56
  CardContent,
58
57
  CardFooter
59
- } from '@iblai/web-containers';
58
+ } from '@iblai/iblai-js/web-containers';
60
59
 
61
60
  <Card>
62
61
  <CardHeader>
@@ -70,14 +69,6 @@ import {
70
69
  <Button>Action</Button>
71
70
  </CardFooter>
72
71
  </Card>
73
-
74
- // With custom styling
75
- <Card className="w-[350px]">
76
- <CardHeader className="pb-2">
77
- <CardTitle className="text-lg">Compact Card</CardTitle>
78
- </CardHeader>
79
- <CardContent>Content</CardContent>
80
- </Card>
81
72
  \`\`\`
82
73
 
83
74
  **File Location**: \`packages/web-containers/src/components/ui/card.tsx\``,
@@ -88,13 +79,14 @@ import {
88
79
  Dialog,
89
80
  DialogTrigger,
90
81
  DialogPortal,
82
+ DialogOverlay,
91
83
  DialogClose,
92
84
  DialogContent,
93
85
  DialogHeader,
94
86
  DialogFooter,
95
87
  DialogTitle,
96
88
  DialogDescription,
97
- } from '@iblai/web-containers';
89
+ } from '@iblai/iblai-js/web-containers';
98
90
 
99
91
  // Controlled dialog
100
92
  <Dialog open={open} onOpenChange={setOpen}>
@@ -119,60 +111,34 @@ import {
119
111
  </DialogFooter>
120
112
  </DialogContent>
121
113
  </Dialog>
122
-
123
- // Uncontrolled dialog
124
- <Dialog>
125
- <DialogTrigger>Open</DialogTrigger>
126
- <DialogContent>
127
- <DialogHeader>
128
- <DialogTitle>Title</DialogTitle>
129
- </DialogHeader>
130
- Content here
131
- </DialogContent>
132
- </Dialog>
133
114
  \`\`\`
134
115
 
135
116
  **File Location**: \`packages/web-containers/src/components/ui/dialog.tsx\``,
136
117
  Input: `# Input Component
137
118
 
138
119
  \`\`\`typescript
139
- import { Input } from '@iblai/web-containers';
140
- import { Label } from '@iblai/web-containers';
120
+ import { Input } from '@iblai/iblai-js/web-containers';
121
+ import { Label } from '@iblai/iblai-js/web-containers';
141
122
 
142
- // Basic usage
143
- <Input
144
- type="text"
145
- placeholder="Enter text..."
146
- value={value}
147
- onChange={(e) => setValue(e.target.value)}
148
- />
123
+ // Extends React.ComponentProps<"input">
149
124
 
150
- // With label
151
125
  <div className="space-y-2">
152
126
  <Label htmlFor="email">Email</Label>
153
127
  <Input
154
128
  id="email"
155
129
  type="email"
156
130
  placeholder="name@example.com"
131
+ value={value}
132
+ onChange={(e) => setValue(e.target.value)}
157
133
  />
158
134
  </div>
159
-
160
- // Different types
161
- <Input type="password" placeholder="Password" />
162
- <Input type="number" placeholder="0" />
163
- <Input type="search" placeholder="Search..." />
164
- <Input type="file" />
165
-
166
- // States
167
- <Input disabled placeholder="Disabled input" />
168
- <Input className="border-red-500" placeholder="Error state" />
169
135
  \`\`\`
170
136
 
171
137
  **File Location**: \`packages/web-containers/src/components/ui/input.tsx\``,
172
138
  Label: `# Label Component
173
139
 
174
140
  \`\`\`typescript
175
- import { Label } from '@iblai/web-containers';
141
+ import { Label } from '@iblai/iblai-js/web-containers';
176
142
 
177
143
  <Label htmlFor="email">Email Address</Label>
178
144
 
@@ -180,30 +146,22 @@ import { Label } from '@iblai/web-containers';
180
146
  <Label htmlFor="name">
181
147
  Name <span className="text-red-500">*</span>
182
148
  </Label>
183
-
184
- // Disabled state
185
- <Label htmlFor="disabled" className="text-muted-foreground">
186
- Disabled Field
187
- </Label>
188
149
  \`\`\`
189
150
 
190
151
  **File Location**: \`packages/web-containers/src/components/ui/label.tsx\``,
191
152
  Textarea: `# Textarea Component
192
153
 
193
154
  \`\`\`typescript
194
- import { Textarea } from '@iblai/web-containers';
155
+ import { Textarea } from '@iblai/iblai-js/web-containers';
156
+
157
+ // Extends React.ComponentProps<"textarea">
195
158
 
196
159
  <Textarea
197
160
  placeholder="Type your message here..."
198
161
  value={value}
199
162
  onChange={(e) => setValue(e.target.value)}
163
+ rows={5}
200
164
  />
201
-
202
- // With rows
203
- <Textarea rows={5} placeholder="Longer text area" />
204
-
205
- // Disabled
206
- <Textarea disabled placeholder="Cannot edit" />
207
165
  \`\`\`
208
166
 
209
167
  **File Location**: \`packages/web-containers/src/components/ui/textarea.tsx\``,
@@ -221,55 +179,29 @@ import {
221
179
  SelectSeparator,
222
180
  SelectScrollUpButton,
223
181
  SelectScrollDownButton,
224
- } from '@iblai/web-containers';
182
+ } from '@iblai/iblai-js/web-containers';
225
183
 
226
- // Basic usage
227
184
  <Select value={value} onValueChange={setValue}>
228
185
  <SelectTrigger className="w-[200px]">
229
186
  <SelectValue placeholder="Select option" />
230
187
  </SelectTrigger>
231
- <SelectContent>
232
- <SelectItem value="option1">Option 1</SelectItem>
233
- <SelectItem value="option2">Option 2</SelectItem>
234
- <SelectItem value="option3">Option 3</SelectItem>
235
- </SelectContent>
236
- </Select>
237
-
238
- // With groups
239
- <Select>
240
- <SelectTrigger>
241
- <SelectValue placeholder="Select..." />
242
- </SelectTrigger>
243
188
  <SelectContent>
244
189
  <SelectGroup>
245
- <SelectLabel>Fruits</SelectLabel>
246
- <SelectItem value="apple">Apple</SelectItem>
247
- <SelectItem value="banana">Banana</SelectItem>
248
- </SelectGroup>
249
- <SelectSeparator />
250
- <SelectGroup>
251
- <SelectLabel>Vegetables</SelectLabel>
252
- <SelectItem value="carrot">Carrot</SelectItem>
190
+ <SelectLabel>Group</SelectLabel>
191
+ <SelectItem value="option1">Option 1</SelectItem>
192
+ <SelectItem value="option2">Option 2</SelectItem>
253
193
  </SelectGroup>
254
194
  </SelectContent>
255
195
  </Select>
256
-
257
- // Disabled state
258
- <Select disabled>
259
- <SelectTrigger>
260
- <SelectValue placeholder="Disabled" />
261
- </SelectTrigger>
262
- </Select>
263
196
  \`\`\`
264
197
 
265
198
  **File Location**: \`packages/web-containers/src/components/ui/select.tsx\``,
266
199
  Checkbox: `# Checkbox Component
267
200
 
268
201
  \`\`\`typescript
269
- import { Checkbox } from '@iblai/web-containers';
270
- import { Label } from '@iblai/web-containers';
202
+ import { Checkbox } from '@iblai/iblai-js/web-containers';
203
+ import { Label } from '@iblai/iblai-js/web-containers';
271
204
 
272
- // Basic usage
273
205
  <div className="flex items-center space-x-2">
274
206
  <Checkbox
275
207
  id="terms"
@@ -278,20 +210,14 @@ import { Label } from '@iblai/web-containers';
278
210
  />
279
211
  <Label htmlFor="terms">Accept terms and conditions</Label>
280
212
  </div>
281
-
282
- // Disabled
283
- <Checkbox disabled />
284
-
285
- // Indeterminate state
286
- <Checkbox checked="indeterminate" />
287
213
  \`\`\`
288
214
 
289
215
  **File Location**: \`packages/web-containers/src/components/ui/checkbox.tsx\``,
290
216
  RadioGroup: `# RadioGroup Component
291
217
 
292
218
  \`\`\`typescript
293
- import { RadioGroup, RadioGroupItem } from '@iblai/web-containers';
294
- import { Label } from '@iblai/web-containers';
219
+ import { RadioGroup, RadioGroupItem } from '@iblai/iblai-js/web-containers';
220
+ import { Label } from '@iblai/iblai-js/web-containers';
295
221
 
296
222
  <RadioGroup value={value} onValueChange={setValue}>
297
223
  <div className="flex items-center space-x-2">
@@ -302,10 +228,6 @@ import { Label } from '@iblai/web-containers';
302
228
  <RadioGroupItem value="option2" id="r2" />
303
229
  <Label htmlFor="r2">Option 2</Label>
304
230
  </div>
305
- <div className="flex items-center space-x-2">
306
- <RadioGroupItem value="option3" id="r3" />
307
- <Label htmlFor="r3">Option 3</Label>
308
- </div>
309
231
  </RadioGroup>
310
232
  \`\`\`
311
233
 
@@ -313,8 +235,8 @@ import { Label } from '@iblai/web-containers';
313
235
  Switch: `# Switch Component
314
236
 
315
237
  \`\`\`typescript
316
- import { Switch } from '@iblai/web-containers';
317
- import { Label } from '@iblai/web-containers';
238
+ import { Switch } from '@iblai/iblai-js/web-containers';
239
+ import { Label } from '@iblai/iblai-js/web-containers';
318
240
 
319
241
  <div className="flex items-center space-x-2">
320
242
  <Switch
@@ -324,12 +246,6 @@ import { Label } from '@iblai/web-containers';
324
246
  />
325
247
  <Label htmlFor="airplane-mode">Airplane Mode</Label>
326
248
  </div>
327
-
328
- // Disabled
329
- <Switch disabled />
330
-
331
- // With different sizes via className
332
- <Switch className="scale-75" />
333
249
  \`\`\`
334
250
 
335
251
  **File Location**: \`packages/web-containers/src/components/ui/switch.tsx\``,
@@ -341,30 +257,15 @@ import {
341
257
  TabsList,
342
258
  TabsTrigger,
343
259
  TabsContent,
344
- } from '@iblai/web-containers';
260
+ } from '@iblai/iblai-js/web-containers';
345
261
 
346
- // Controlled
347
262
  <Tabs value={tab} onValueChange={setTab}>
348
263
  <TabsList>
349
264
  <TabsTrigger value="tab1">Tab 1</TabsTrigger>
350
265
  <TabsTrigger value="tab2">Tab 2</TabsTrigger>
351
- <TabsTrigger value="tab3">Tab 3</TabsTrigger>
352
266
  </TabsList>
353
267
  <TabsContent value="tab1">Content for Tab 1</TabsContent>
354
268
  <TabsContent value="tab2">Content for Tab 2</TabsContent>
355
- <TabsContent value="tab3">Content for Tab 3</TabsContent>
356
- </Tabs>
357
-
358
- // Uncontrolled with default
359
- <Tabs defaultValue="tab1" className="w-full">
360
- <TabsList className="grid w-full grid-cols-3">
361
- <TabsTrigger value="tab1">Account</TabsTrigger>
362
- <TabsTrigger value="tab2">Password</TabsTrigger>
363
- <TabsTrigger value="tab3">Settings</TabsTrigger>
364
- </TabsList>
365
- <TabsContent value="tab1">...</TabsContent>
366
- <TabsContent value="tab2">...</TabsContent>
367
- <TabsContent value="tab3">...</TabsContent>
368
269
  </Tabs>
369
270
  \`\`\`
370
271
 
@@ -372,59 +273,40 @@ import {
372
273
  Avatar: `# Avatar Component
373
274
 
374
275
  \`\`\`typescript
375
- import { Avatar, AvatarImage, AvatarFallback, AvatarImageBordered } from '@iblai/web-containers';
276
+ import { Avatar, AvatarImage, AvatarImageBordered, AvatarFallback } from '@iblai/iblai-js/web-containers';
277
+
278
+ // All accept onClick?: () => void
376
279
 
377
- // Basic usage
378
280
  <Avatar>
379
281
  <AvatarImage src={user.avatar} alt={user.name} />
380
282
  <AvatarFallback>{user.initials}</AvatarFallback>
381
283
  </Avatar>
382
284
 
383
- // With custom size
384
- <Avatar className="h-12 w-12">
385
- <AvatarImage src={user.avatar} />
386
- <AvatarFallback>JD</AvatarFallback>
387
- </Avatar>
388
-
389
285
  // Bordered variant
390
286
  <Avatar>
391
287
  <AvatarImageBordered src={user.avatar} alt={user.name} />
392
288
  <AvatarFallback>AB</AvatarFallback>
393
289
  </Avatar>
394
290
 
395
- // Multiple avatars (avatar group)
396
- <div className="flex -space-x-4">
397
- <Avatar className="border-2 border-background">
398
- <AvatarImage src="/user1.jpg" />
399
- <AvatarFallback>U1</AvatarFallback>
400
- </Avatar>
401
- <Avatar className="border-2 border-background">
402
- <AvatarImage src="/user2.jpg" />
403
- <AvatarFallback>U2</AvatarFallback>
404
- </Avatar>
405
- </div>
291
+ // Custom size
292
+ <Avatar className="h-12 w-12">
293
+ <AvatarImage src={user.avatar} />
294
+ <AvatarFallback>JD</AvatarFallback>
295
+ </Avatar>
406
296
  \`\`\`
407
297
 
408
298
  **File Location**: \`packages/web-containers/src/components/ui/avatar.tsx\``,
409
299
  Badge: `# Badge Component
410
300
 
411
301
  \`\`\`typescript
412
- import { Badge, badgeVariants } from '@iblai/web-containers';
302
+ import { Badge, badgeVariants } from '@iblai/iblai-js/web-containers';
303
+
304
+ // Variants: 'default' | 'secondary' | 'destructive' | 'outline'
413
305
 
414
- // Variants
415
306
  <Badge>Default</Badge>
416
307
  <Badge variant="secondary">Secondary</Badge>
417
308
  <Badge variant="destructive">Destructive</Badge>
418
309
  <Badge variant="outline">Outline</Badge>
419
-
420
- // As link
421
- <Badge className={badgeVariants({ variant: "outline" })} asChild>
422
- <a href="/link">Link Badge</a>
423
- </Badge>
424
-
425
- // Custom colors
426
- <Badge className="bg-green-500">Success</Badge>
427
- <Badge className="bg-yellow-500">Warning</Badge>
428
310
  \`\`\`
429
311
 
430
312
  **File Location**: \`packages/web-containers/src/components/ui/badge.tsx\``,
@@ -436,35 +318,18 @@ import {
436
318
  TooltipContent,
437
319
  TooltipProvider,
438
320
  TooltipTrigger,
439
- } from '@iblai/web-containers';
321
+ } from '@iblai/iblai-js/web-containers';
440
322
 
441
- // Wrap your app or component tree with TooltipProvider
442
- <TooltipProvider>
323
+ <TooltipProvider delayDuration={0}>
443
324
  <Tooltip>
444
325
  <TooltipTrigger asChild>
445
326
  <Button variant="outline">Hover me</Button>
446
327
  </TooltipTrigger>
447
- <TooltipContent>
448
- <p>Tooltip content here</p>
328
+ <TooltipContent side="right" sideOffset={0}>
329
+ <p>Tooltip content</p>
449
330
  </TooltipContent>
450
331
  </Tooltip>
451
332
  </TooltipProvider>
452
-
453
- // With delay
454
- <TooltipProvider delayDuration={300}>
455
- <Tooltip>
456
- <TooltipTrigger>Delayed</TooltipTrigger>
457
- <TooltipContent>Shows after 300ms</TooltipContent>
458
- </Tooltip>
459
- </TooltipProvider>
460
-
461
- // Positioning
462
- <Tooltip>
463
- <TooltipTrigger>Trigger</TooltipTrigger>
464
- <TooltipContent side="right" align="start">
465
- Right aligned tooltip
466
- </TooltipContent>
467
- </Tooltip>
468
333
  \`\`\`
469
334
 
470
335
  **File Location**: \`packages/web-containers/src/components/ui/tooltip.tsx\``,
@@ -475,35 +340,19 @@ import {
475
340
  Popover,
476
341
  PopoverTrigger,
477
342
  PopoverContent,
478
- } from '@iblai/web-containers';
343
+ } from '@iblai/iblai-js/web-containers';
479
344
 
480
345
  <Popover>
481
346
  <PopoverTrigger asChild>
482
347
  <Button variant="outline">Open Popover</Button>
483
348
  </PopoverTrigger>
484
- <PopoverContent className="w-80">
349
+ <PopoverContent className="w-80" side="right" align="start">
485
350
  <div className="grid gap-4">
486
- <div className="space-y-2">
487
- <h4 className="font-medium">Dimensions</h4>
488
- <p className="text-sm text-muted-foreground">
489
- Set the dimensions for the layer.
490
- </p>
491
- </div>
492
- <div className="grid gap-2">
493
- <Input placeholder="Width" />
494
- <Input placeholder="Height" />
495
- </div>
351
+ <h4 className="font-medium">Title</h4>
352
+ <Input placeholder="Value" />
496
353
  </div>
497
354
  </PopoverContent>
498
355
  </Popover>
499
-
500
- // With positioning
501
- <Popover>
502
- <PopoverTrigger>Click</PopoverTrigger>
503
- <PopoverContent side="right" align="start">
504
- Content
505
- </PopoverContent>
506
- </Popover>
507
356
  \`\`\`
508
357
 
509
358
  **File Location**: \`packages/web-containers/src/components/ui/popover.tsx\``,
@@ -512,6 +361,7 @@ import {
512
361
  \`\`\`typescript
513
362
  import {
514
363
  DropdownMenu,
364
+ DropdownMenuPortal,
515
365
  DropdownMenuTrigger,
516
366
  DropdownMenuContent,
517
367
  DropdownMenuItem,
@@ -525,7 +375,11 @@ import {
525
375
  DropdownMenuSubContent,
526
376
  DropdownMenuSubTrigger,
527
377
  DropdownMenuRadioGroup,
528
- } from '@iblai/web-containers';
378
+ } from '@iblai/iblai-js/web-containers';
379
+
380
+ // DropdownMenuItem has extra props: inset?: boolean, variant?: 'default' | 'destructive'
381
+ // DropdownMenuLabel has extra props: inset?: boolean
382
+ // DropdownMenuSubTrigger has extra props: inset?: boolean
529
383
 
530
384
  <DropdownMenu>
531
385
  <DropdownMenuTrigger asChild>
@@ -535,24 +389,11 @@ import {
535
389
  <DropdownMenuLabel>My Account</DropdownMenuLabel>
536
390
  <DropdownMenuSeparator />
537
391
  <DropdownMenuGroup>
538
- <DropdownMenuItem>
539
- Profile
540
- <DropdownMenuShortcut>⇧⌘P</DropdownMenuShortcut>
541
- </DropdownMenuItem>
392
+ <DropdownMenuItem>Profile</DropdownMenuItem>
542
393
  <DropdownMenuItem>Settings</DropdownMenuItem>
543
394
  </DropdownMenuGroup>
544
395
  <DropdownMenuSeparator />
545
- <DropdownMenuSub>
546
- <DropdownMenuSubTrigger>Invite users</DropdownMenuSubTrigger>
547
- <DropdownMenuSubContent>
548
- <DropdownMenuItem>Email</DropdownMenuItem>
549
- <DropdownMenuItem>Message</DropdownMenuItem>
550
- </DropdownMenuSubContent>
551
- </DropdownMenuSub>
552
- <DropdownMenuSeparator />
553
- <DropdownMenuItem className="text-red-600">
554
- Log out
555
- </DropdownMenuItem>
396
+ <DropdownMenuItem variant="destructive">Log out</DropdownMenuItem>
556
397
  </DropdownMenuContent>
557
398
  </DropdownMenu>
558
399
  \`\`\`
@@ -570,15 +411,14 @@ import {
570
411
  TableRow,
571
412
  TableCell,
572
413
  TableCaption,
573
- } from '@iblai/web-containers';
414
+ } from '@iblai/iblai-js/web-containers';
574
415
 
575
416
  <Table>
576
- <TableCaption>A list of your recent invoices.</TableCaption>
417
+ <TableCaption>A list of recent invoices.</TableCaption>
577
418
  <TableHeader>
578
419
  <TableRow>
579
- <TableHead className="w-[100px]">Invoice</TableHead>
420
+ <TableHead>Invoice</TableHead>
580
421
  <TableHead>Status</TableHead>
581
- <TableHead>Method</TableHead>
582
422
  <TableHead className="text-right">Amount</TableHead>
583
423
  </TableRow>
584
424
  </TableHeader>
@@ -587,17 +427,10 @@ import {
587
427
  <TableRow key={invoice.id}>
588
428
  <TableCell className="font-medium">{invoice.id}</TableCell>
589
429
  <TableCell>{invoice.status}</TableCell>
590
- <TableCell>{invoice.method}</TableCell>
591
430
  <TableCell className="text-right">{invoice.amount}</TableCell>
592
431
  </TableRow>
593
432
  ))}
594
433
  </TableBody>
595
- <TableFooter>
596
- <TableRow>
597
- <TableCell colSpan={3}>Total</TableCell>
598
- <TableCell className="text-right">$2,500.00</TableCell>
599
- </TableRow>
600
- </TableFooter>
601
434
  </Table>
602
435
  \`\`\`
603
436
 
@@ -605,30 +438,14 @@ import {
605
438
  Skeleton: `# Skeleton Component
606
439
 
607
440
  \`\`\`typescript
608
- import { Skeleton } from '@iblai/web-containers';
441
+ import { Skeleton } from '@iblai/iblai-js/web-containers';
442
+
443
+ // Extends React.ComponentProps<"div">
609
444
 
610
- // Loading card
611
445
  <div className="space-y-3">
612
446
  <Skeleton className="h-[125px] w-[250px] rounded-xl" />
613
- <div className="space-y-2">
614
- <Skeleton className="h-4 w-[250px]" />
615
- <Skeleton className="h-4 w-[200px]" />
616
- </div>
617
- </div>
618
-
619
- // Loading text
620
- <div className="space-y-2">
621
- <Skeleton className="h-4 w-full" />
622
- <Skeleton className="h-4 w-3/4" />
623
- </div>
624
-
625
- // Loading avatar
626
- <div className="flex items-center space-x-4">
627
- <Skeleton className="h-12 w-12 rounded-full" />
628
- <div className="space-y-2">
629
- <Skeleton className="h-4 w-[200px]" />
630
- <Skeleton className="h-4 w-[150px]" />
631
- </div>
447
+ <Skeleton className="h-4 w-[250px]" />
448
+ <Skeleton className="h-4 w-[200px]" />
632
449
  </div>
633
450
  \`\`\`
634
451
 
@@ -636,32 +453,41 @@ import { Skeleton } from '@iblai/web-containers';
636
453
  Separator: `# Separator Component
637
454
 
638
455
  \`\`\`typescript
639
- import { Separator } from '@iblai/web-containers';
456
+ import { Separator } from '@iblai/iblai-js/web-containers';
640
457
 
641
- // Horizontal (default)
642
- <div>
643
- <p>Above</p>
644
- <Separator className="my-4" />
645
- <p>Below</p>
646
- </div>
458
+ // Default: orientation="horizontal", decorative=true
459
+
460
+ <Separator className="my-4" />
647
461
 
648
462
  // Vertical
649
463
  <div className="flex h-5 items-center space-x-4">
650
464
  <span>Item 1</span>
651
465
  <Separator orientation="vertical" />
652
466
  <span>Item 2</span>
653
- <Separator orientation="vertical" />
654
- <span>Item 3</span>
655
467
  </div>
656
468
  \`\`\`
657
469
 
658
470
  **File Location**: \`packages/web-containers/src/components/ui/separator.tsx\``,
471
+ Progress: `# Progress Component
472
+
473
+ \`\`\`typescript
474
+ import { Progress } from '@iblai/iblai-js/web-containers';
475
+
476
+ // Extends Radix ProgressPrimitive.Root props
477
+
478
+ <Progress value={33} className="w-[60%]" />
479
+ <Progress value={66} />
480
+ <Progress value={100} />
481
+ \`\`\`
482
+
483
+ **File Location**: \`packages/web-containers/src/components/ui/progress.tsx\``,
659
484
  Calendar: `# Calendar Component
660
485
 
661
486
  \`\`\`typescript
662
- import { Calendar, CalendarDayButton } from '@iblai/web-containers';
487
+ import { Calendar, CalendarDayButton } from '@iblai/iblai-js/web-containers';
488
+
489
+ // Extends react-day-picker DayPicker props + buttonVariant
663
490
 
664
- // Single date selection
665
491
  <Calendar
666
492
  mode="single"
667
493
  selected={date}
@@ -676,13 +502,6 @@ import { Calendar, CalendarDayButton } from '@iblai/web-containers';
676
502
  onSelect={setDateRange}
677
503
  />
678
504
 
679
- // Multiple dates
680
- <Calendar
681
- mode="multiple"
682
- selected={dates}
683
- onSelect={setDates}
684
- />
685
-
686
505
  // With disabled dates
687
506
  <Calendar
688
507
  mode="single"
@@ -704,7 +523,9 @@ import {
704
523
  PaginationNext,
705
524
  PaginationPrevious,
706
525
  PaginationEllipsis,
707
- } from '@iblai/web-containers';
526
+ } from '@iblai/iblai-js/web-containers';
527
+
528
+ // PaginationLink has isActive?: boolean and size prop
708
529
 
709
530
  <Pagination>
710
531
  <PaginationContent>
@@ -712,13 +533,10 @@ import {
712
533
  <PaginationPrevious href="#" />
713
534
  </PaginationItem>
714
535
  <PaginationItem>
715
- <PaginationLink href="#">1</PaginationLink>
716
- </PaginationItem>
717
- <PaginationItem>
718
- <PaginationLink href="#" isActive>2</PaginationLink>
536
+ <PaginationLink href="#" isActive>1</PaginationLink>
719
537
  </PaginationItem>
720
538
  <PaginationItem>
721
- <PaginationLink href="#">3</PaginationLink>
539
+ <PaginationLink href="#">2</PaginationLink>
722
540
  </PaginationItem>
723
541
  <PaginationItem>
724
542
  <PaginationEllipsis />
@@ -734,39 +552,23 @@ import {
734
552
  Toggle: `# Toggle Component
735
553
 
736
554
  \`\`\`typescript
737
- import { Toggle, toggleVariants } from '@iblai/web-containers';
738
- import { Bold, Italic, Underline } from 'lucide-react';
555
+ import { Toggle, toggleVariants } from '@iblai/iblai-js/web-containers';
739
556
 
740
- // Basic toggle
741
- <Toggle aria-label="Toggle bold">
742
- <Bold className="h-4 w-4" />
743
- </Toggle>
744
-
745
- // With variants
746
- <Toggle variant="outline" aria-label="Toggle">
747
- Toggle
748
- </Toggle>
557
+ // Variants: variant ('default' | 'outline'), size ('default' | 'sm' | 'lg')
749
558
 
750
- // Controlled
751
- <Toggle pressed={bold} onPressedChange={setBold}>
559
+ <Toggle pressed={bold} onPressedChange={setBold} aria-label="Toggle bold">
752
560
  <Bold className="h-4 w-4" />
753
561
  </Toggle>
754
562
 
755
- // Toggle group (using multiple toggles)
756
- <div className="flex gap-1">
757
- <Toggle><Bold className="h-4 w-4" /></Toggle>
758
- <Toggle><Italic className="h-4 w-4" /></Toggle>
759
- <Toggle><Underline className="h-4 w-4" /></Toggle>
760
- </div>
563
+ <Toggle variant="outline">Toggle</Toggle>
761
564
  \`\`\`
762
565
 
763
566
  **File Location**: \`packages/web-containers/src/components/ui/toggle.tsx\``,
764
567
  Toast: `# Toast / Toaster Component
765
568
 
766
569
  \`\`\`typescript
767
- import { Toaster, toast } from '@iblai/web-containers';
768
- // OR using sonner directly
769
- import { Toaster } from '@iblai/web-containers';
570
+ // Sonner integration (recommended)
571
+ import { Toaster } from '@iblai/iblai-js/web-containers';
770
572
  import { toast } from 'sonner';
771
573
 
772
574
  // Add Toaster to your layout
@@ -776,22 +578,12 @@ import { toast } from 'sonner';
776
578
  toast('Event has been created');
777
579
  toast.success('Successfully saved!');
778
580
  toast.error('Something went wrong');
779
- toast.warning('Warning message');
780
- toast.info('Information');
781
581
 
782
582
  // With description
783
583
  toast('Event created', {
784
584
  description: 'Your event has been scheduled.',
785
585
  });
786
586
 
787
- // With action
788
- toast('Event created', {
789
- action: {
790
- label: 'Undo',
791
- onClick: () => console.log('Undo'),
792
- },
793
- });
794
-
795
587
  // Promise toast
796
588
  toast.promise(saveData(), {
797
589
  loading: 'Saving...',
@@ -800,6 +592,8 @@ toast.promise(saveData(), {
800
592
  });
801
593
  \`\`\`
802
594
 
595
+ Also exports Radix-based toast primitives: \`ToastProvider\`, \`ToastViewport\`, \`Toast\`, \`ToastTitle\`, \`ToastDescription\`, \`ToastClose\`, \`ToastAction\`.
596
+
803
597
  **File Location**: \`packages/web-containers/src/components/ui/sonner.tsx\``,
804
598
  Chart: `# Chart Components (Recharts wrapper)
805
599
 
@@ -811,9 +605,17 @@ import {
811
605
  ChartTooltipContent,
812
606
  ChartLegend,
813
607
  ChartLegendContent,
814
- } from '@iblai/web-containers';
608
+ useChart,
609
+ } from '@iblai/iblai-js/web-containers';
815
610
  import { Bar, BarChart, XAxis, YAxis } from 'recharts';
816
611
 
612
+ type ChartConfig = {
613
+ [k: string]: {
614
+ label?: React.ReactNode;
615
+ icon?: React.ComponentType;
616
+ } & ({ color?: string } | { theme: Record<string, string> });
617
+ };
618
+
817
619
  const chartConfig: ChartConfig = {
818
620
  desktop: { label: 'Desktop', color: '#2563eb' },
819
621
  mobile: { label: 'Mobile', color: '#60a5fa' },
@@ -833,38 +635,46 @@ const chartConfig: ChartConfig = {
833
635
 
834
636
  **File Location**: \`packages/web-containers/src/components/ui/chart.tsx\``,
835
637
  // ============================================================================
836
- // FEATURE COMPONENTS
638
+ // FEATURE COMPONENTS (main export: @iblai/iblai-js/web-containers)
837
639
  // ============================================================================
838
640
  Profile: `# Profile Component
839
641
 
840
642
  Complete user profile management with multiple tabs.
841
643
 
842
644
  \`\`\`typescript
843
- import { Profile } from '@iblai/web-containers';
645
+ import { Profile } from '@iblai/iblai-js/web-containers';
646
+
647
+ interface UserProfileModalProps {
648
+ tenant: string;
649
+ username: string;
650
+ onClose: () => void;
651
+ customization?: {
652
+ showMentorAIDisplayCheckbox?: boolean;
653
+ showLeaderboardDisplayCheckbox?: boolean;
654
+ showUsernameField?: boolean;
655
+ showPlatformName?: boolean;
656
+ useGravatarPicFallback?: boolean;
657
+ };
658
+ isAdmin?: boolean;
659
+ targetTab?: string;
660
+ localLLMProps?: { /* LocalLLMTab props */ };
661
+ }
844
662
 
845
663
  <Profile
664
+ tenant={tenantKey}
846
665
  username={username}
847
- tenantKey={tenantKey}
848
- tabs={['basic', 'social', 'education', 'experience', 'resume', 'security', 'advanced']}
849
- onSave={handleSave}
666
+ onClose={() => setOpen(false)}
667
+ isAdmin={isAdmin}
668
+ customization={{ showUsernameField: true }}
850
669
  />
851
670
  \`\`\`
852
671
 
853
- **Available Tabs**:
854
- - \`basic\`: Name, title, about, profile image
855
- - \`social\`: Social media links (LinkedIn, Twitter, etc.)
856
- - \`education\`: Education history with institutions
857
- - \`experience\`: Work experience with companies
858
- - \`resume\`: Resume/CV upload
859
- - \`security\`: Password change
860
- - \`advanced\`: Custom domain, SMTP, API settings
672
+ **Available Tabs**: basic, social, education, experience, resume, security, advanced
861
673
 
862
674
  **Related Components**:
863
675
  - \`InviteUserDialog\` - Dialog to invite users
864
676
  - \`InvitedUsersDialog\` - View invited users
865
677
  - \`LocalLLMTab\` - Local LLM settings (Tauri desktop only)
866
- - \`IntegrationsTab\` - API integrations
867
- - \`UsersTab\`, \`CoursesTab\`, \`ProgramsTab\` - Invite management
868
678
 
869
679
  **File Location**: \`packages/web-containers/src/components/profile/index.tsx\``,
870
680
  InviteUserDialog: `# InviteUserDialog Component
@@ -872,26 +682,68 @@ import { Profile } from '@iblai/web-containers';
872
682
  Dialog for inviting new users to the platform.
873
683
 
874
684
  \`\`\`typescript
875
- import { InviteUserDialog } from '@iblai/web-containers';
685
+ import { InviteUserDialog } from '@iblai/iblai-js/web-containers';
686
+
687
+ interface InviteUserDialogProps {
688
+ tenant: string;
689
+ onClose: () => void;
690
+ isOpen: boolean;
691
+ enableCatalogInvite?: boolean;
692
+ hasManageUsersPermission?: boolean;
693
+ }
876
694
 
877
695
  <InviteUserDialog
878
- open={open}
879
- onOpenChange={setOpen}
880
- tenantKey={tenantKey}
881
- onSuccess={() => {
882
- toast.success('User invited successfully');
883
- refetch();
884
- }}
696
+ tenant={tenantKey}
697
+ isOpen={open}
698
+ onClose={() => setOpen(false)}
699
+ enableCatalogInvite={true}
700
+ hasManageUsersPermission={isAdmin}
885
701
  />
886
702
  \`\`\`
887
703
 
888
704
  **File Location**: \`packages/web-containers/src/components/profile/invite-user.tsx\``,
705
+ InvitedUsersDialog: `# InvitedUsersDialog Component
706
+
707
+ Dialog showing list of invited users pending confirmation.
708
+
709
+ \`\`\`typescript
710
+ import { InvitedUsersDialog } from '@iblai/iblai-js/web-containers';
711
+
712
+ interface InvitedUsersDialogProps {
713
+ tenant: string;
714
+ onClose: () => void;
715
+ }
716
+
717
+ <InvitedUsersDialog
718
+ tenant={tenantKey}
719
+ onClose={() => setOpen(false)}
720
+ />
721
+ \`\`\`
722
+
723
+ **File Location**: \`packages/web-containers/src/components/profile/invited-users.tsx\``,
889
724
  LocalLLMTab: `# LocalLLMTab Component
890
725
 
891
- Settings for local LLM (Ollama) in Tauri desktop app.
726
+ Settings for local LLM (Ollama/Foundry) in Tauri desktop app.
892
727
 
893
728
  \`\`\`typescript
894
- import { LocalLLMTab, isLocalLLMEnabled, setLocalLLMEnabled } from '@iblai/web-containers';
729
+ import { LocalLLMTab, isLocalLLMEnabled, setLocalLLMEnabled } from '@iblai/iblai-js/web-containers';
730
+
731
+ interface LocalLLMTabProps {
732
+ isAvailable: boolean;
733
+ state: ModelDownloadState;
734
+ ollamaStatus: OllamaStatus | null;
735
+ isUsingFoundry?: boolean;
736
+ foundryModels?: FoundryModel[];
737
+ selectedFoundryModel?: string | null;
738
+ foundryStatus?: FoundryStatus | null;
739
+ onStartDownload: () => void;
740
+ onCancelDownload: () => void;
741
+ onInstallOllama: () => void;
742
+ onInstallFoundry?: () => void;
743
+ onCheckStatus: () => void;
744
+ onResetState: () => void;
745
+ onSelectFoundryModel?: (modelId: string) => void;
746
+ }
895
747
 
896
748
  <LocalLLMTab
897
749
  isAvailable={isTauriApp}
@@ -903,12 +755,6 @@ import { LocalLLMTab, isLocalLLMEnabled, setLocalLLMEnabled } from '@iblai/web-c
903
755
  onCheckStatus={checkStatus}
904
756
  onResetState={resetState}
905
757
  />
906
-
907
- // Check if local LLM is enabled
908
- const enabled = isLocalLLMEnabled();
909
-
910
- // Enable/disable
911
- setLocalLLMEnabled(true);
912
758
  \`\`\`
913
759
 
914
760
  **File Location**: \`packages/web-containers/src/components/profile/local-llm/local-llm-tab.tsx\``,
@@ -917,41 +763,80 @@ setLocalLLMEnabled(true);
917
763
  Notification bell dropdown with unread count.
918
764
 
919
765
  \`\`\`typescript
920
- import { NotificationDropdown } from '@iblai/web-containers';
766
+ import { NotificationDropdown } from '@iblai/iblai-js/web-containers';
767
+
768
+ interface NotificationDropdownProps {
769
+ org: string;
770
+ userId: string;
771
+ isAdmin?: boolean;
772
+ className?: string;
773
+ onViewNotifications?: (notificationId?: string) => void;
774
+ }
921
775
 
922
776
  <NotificationDropdown
923
777
  org={tenantKey}
924
778
  userId={username}
925
779
  isAdmin={isAdmin}
926
- onViewNotifications={() => router.push('/notifications')}
780
+ onViewNotifications={(id) => router.push(\`/notifications\${id ? \`?id=\${id}\` : ''}\`)}
927
781
  />
928
782
  \`\`\`
929
783
 
930
- **Props**:
931
- - \`org\`: Tenant/organization key
932
- - \`userId\`: Current user's username
933
- - \`isAdmin\`: Whether user is admin (shows admin features)
934
- - \`onViewNotifications\`: Callback when "View All" is clicked
935
-
936
784
  **Related Components**:
937
- - \`NotificationDisplay\` - Individual notification item
785
+ - \`NotificationDisplay\` - Full notification management
938
786
  - \`SendNotificationDialog\` - Send notifications (admin)
939
787
  - \`AlertsTab\` - Manage notification alerts
940
788
  - \`EditAlertDialog\` - Edit alert settings
941
789
 
942
- **File Location**: \`packages/web-containers/src/components/notifications/index.ts\``,
790
+ **File Location**: \`packages/web-containers/src/components/notifications/notification-dropdown.tsx\``,
791
+ NotificationDisplay: `# NotificationDisplay Component
792
+
793
+ Full notification management interface with inbox and alerts tabs.
794
+
795
+ \`\`\`typescript
796
+ import { NotificationDisplay } from '@iblai/iblai-js/web-containers';
797
+
798
+ interface NotificationDisplayProps {
799
+ org: string;
800
+ userId: string;
801
+ isAdmin?: boolean;
802
+ selectedNotificationId?: string;
803
+ enableRbac?: boolean;
804
+ rbacPermissions?: object;
805
+ tenant?: string;
806
+ className?: string;
807
+ }
808
+
809
+ <NotificationDisplay
810
+ org={tenantKey}
811
+ userId={username}
812
+ isAdmin={isAdmin}
813
+ enableRbac={true}
814
+ rbacPermissions={permissions}
815
+ />
816
+ \`\`\`
817
+
818
+ **File Location**: \`packages/web-containers/src/components/notifications/notification-display.tsx\``,
943
819
  SendNotificationDialog: `# SendNotificationDialog Component
944
820
 
945
821
  Dialog for admins to send notifications to users.
946
822
 
947
823
  \`\`\`typescript
948
- import { SendNotificationDialog } from '@iblai/web-containers';
824
+ import { SendNotificationDialog } from '@iblai/iblai-js/web-containers';
825
+
826
+ interface SendNotificationDialogProps {
827
+ open: boolean;
828
+ onOpenChange: (open: boolean) => void;
829
+ tenant: string;
830
+ onNotificationSent?: () => void;
831
+ hasManageUsersPermission?: boolean;
832
+ }
949
833
 
950
834
  <SendNotificationDialog
951
835
  open={open}
952
836
  onOpenChange={setOpen}
953
- tenantKey={tenantKey}
954
- onSuccess={() => toast.success('Notification sent')}
837
+ tenant={tenantKey}
838
+ onNotificationSent={() => toast.success('Notification sent')}
839
+ hasManageUsersPermission={isAdmin}
955
840
  />
956
841
  \`\`\`
957
842
 
@@ -961,12 +846,43 @@ import { SendNotificationDialog } from '@iblai/web-containers';
961
846
  Manage notification alert configurations.
962
847
 
963
848
  \`\`\`typescript
964
- import { AlertsTab } from '@iblai/web-containers';
849
+ import { AlertsTab } from '@iblai/iblai-js/web-containers';
965
850
 
966
- <AlertsTab tenantKey={tenantKey} />
851
+ interface AlertsTabProps {
852
+ platformKey: string;
853
+ }
854
+
855
+ <AlertsTab platformKey={tenantKey} />
967
856
  \`\`\`
968
857
 
969
858
  **File Location**: \`packages/web-containers/src/components/notifications/alerts-tab.tsx\``,
859
+ EditAlertDialog: `# EditAlertDialog Component
860
+
861
+ Dialog for editing notification template content and settings.
862
+
863
+ \`\`\`typescript
864
+ import { EditAlertDialog } from '@iblai/iblai-js/web-containers';
865
+
866
+ interface EditAlertDialogProps {
867
+ open: boolean;
868
+ onOpenChange: (open: boolean) => void;
869
+ template: NotificationTemplate | null;
870
+ platformKey: string;
871
+ templateType: string | null;
872
+ onSave?: (template: NotificationTemplate) => void;
873
+ }
874
+
875
+ <EditAlertDialog
876
+ open={open}
877
+ onOpenChange={setOpen}
878
+ template={selectedTemplate}
879
+ platformKey={tenantKey}
880
+ templateType="email"
881
+ onSave={handleSave}
882
+ />
883
+ \`\`\`
884
+
885
+ **File Location**: \`packages/web-containers/src/components/notifications/edit-alert-dialog.tsx\``,
970
886
  AnalyticsLayout: `# Analytics Components
971
887
 
972
888
  Complete analytics dashboard with charts and filters.
@@ -980,6 +896,11 @@ import {
980
896
  AnalyticsFinancialStats,
981
897
  AnalyticsTranscriptsStats,
982
898
  AnalyticsReports,
899
+ AnalyticsReportDownload,
900
+ AnalyticsCourses,
901
+ AnalyticsCourseDetail,
902
+ AnalyticsPrograms,
903
+ AnalyticsProgramDetail,
983
904
  ChartFiltersProvider,
984
905
  useChartFilters,
985
906
  AnalyticsSettingsProvider,
@@ -991,7 +912,7 @@ import {
991
912
  CustomDateRangePicker,
992
913
  AccessTimeHeatmap,
993
914
  GroupsFilterDropdown,
994
- } from '@iblai/web-containers';
915
+ } from '@iblai/iblai-js/web-containers';
995
916
 
996
917
  // Usage
997
918
  <ChartFiltersProvider>
@@ -1002,18 +923,12 @@ import {
1002
923
  </AnalyticsSettingsProvider>
1003
924
  </ChartFiltersProvider>
1004
925
 
1005
- // Using hooks for custom analytics
926
+ // Using hooks
1006
927
  const { filters, setFilters, dateRange, setDateRange } = useChartFilters();
1007
928
  const { settings, updateSettings } = useAnalyticsSettings();
1008
929
  \`\`\`
1009
930
 
1010
- **Analytics Hooks**:
1011
- - \`useOverview()\` - Overview data
1012
- - \`useUsers()\` - User statistics
1013
- - \`useTopics()\` - Topic statistics
1014
- - \`useFinancial()\` - Financial data
1015
- - \`useTranscripts()\` - Transcript data
1016
- - \`useReports()\` - Reports data
931
+ **Analytics Hooks**: \`useOverview\`, \`useUsers\`, \`useTopics\`, \`useFinancial\`, \`useTranscripts\`, \`useReports\`, \`useCourses\`, \`usePrograms\`
1017
932
 
1018
933
  **File Location**: \`packages/web-containers/src/components/analytics/index.ts\``,
1019
934
  LoginButton: `# LoginButton Component
@@ -1021,7 +936,18 @@ const { settings, updateSettings } = useAnalyticsSettings();
1021
936
  Button that redirects to Auth SPA for login.
1022
937
 
1023
938
  \`\`\`typescript
1024
- import { LoginButton } from '@iblai/web-containers';
939
+ import { LoginButton } from '@iblai/iblai-js/web-containers';
940
+
941
+ interface LoginButtonProps extends Omit<ButtonProps, 'onClick'> {
942
+ authUrl: string;
943
+ appName: string;
944
+ platformKey?: string;
945
+ redirectTo?: string;
946
+ isJoinTenant?: boolean;
947
+ label?: string;
948
+ onClick?: () => void;
949
+ redirectOptions?: Partial<RedirectToAuthSpaOptions>;
950
+ }
1025
951
 
1026
952
  <LoginButton
1027
953
  authUrl="https://auth.example.com"
@@ -1032,68 +958,77 @@ import { LoginButton } from '@iblai/web-containers';
1032
958
  />
1033
959
  \`\`\`
1034
960
 
1035
- **Props**:
1036
- - \`authUrl\`: Auth SPA base URL
1037
- - \`appName\`: App identifier for redirect
1038
- - \`platformKey\`: Tenant key
1039
- - \`label\`: Button text (default: "Login")
1040
- - \`variant\`: Button variant
1041
-
1042
961
  **File Location**: \`packages/web-containers/src/components/auth-buttons/login-button.tsx\``,
1043
962
  SignupButton: `# SignupButton Component
1044
963
 
1045
964
  Button that redirects to tenant join/signup flow.
1046
965
 
1047
966
  \`\`\`typescript
1048
- import { SignupButton } from '@iblai/web-containers';
967
+ import { SignupButton } from '@iblai/iblai-js/web-containers';
968
+
969
+ interface SignupButtonProps extends Omit<ButtonProps, 'onClick'> {
970
+ authUrl: string;
971
+ tenantKey?: string;
972
+ redirectTo?: string;
973
+ label?: string;
974
+ onClick?: () => void;
975
+ openInNewTab?: boolean;
976
+ }
1049
977
 
1050
978
  <SignupButton
1051
979
  authUrl="https://auth.example.com"
1052
980
  tenantKey={tenantKey}
1053
981
  label="Create Account"
1054
982
  variant="outline"
983
+ openInNewTab={true}
1055
984
  />
1056
985
  \`\`\`
1057
986
 
1058
- **Props**:
1059
- - \`authUrl\`: Auth SPA base URL
1060
- - \`tenantKey\`: Tenant to join
1061
- - \`label\`: Button text (default: "Sign Up")
1062
- - \`variant\`: Button variant
1063
-
1064
987
  **File Location**: \`packages/web-containers/src/components/auth-buttons/signup-button.tsx\``,
1065
988
  Markdown: `# Markdown Component
1066
989
 
1067
990
  Render markdown content with custom styling.
1068
991
 
1069
992
  \`\`\`typescript
1070
- import { Markdown, markdownComponents, CopyButtonIcon } from '@iblai/web-containers';
1071
-
1072
- <Markdown content={markdownString} />
1073
-
1074
- // With custom components
1075
- <Markdown
1076
- content={content}
1077
- components={{
1078
- ...markdownComponents,
1079
- // Override specific elements
1080
- h1: ({ children }) => <h1 className="custom-h1">{children}</h1>,
1081
- }}
1082
- />
993
+ import { Markdown, markdownComponents, CopyButtonIcon } from '@iblai/iblai-js/web-containers';
994
+
995
+ interface MarkdownProps {
996
+ children: string;
997
+ }
998
+
999
+ <Markdown>{markdownString}</Markdown>
1083
1000
  \`\`\`
1084
1001
 
1085
1002
  **File Location**: \`packages/web-containers/src/components/markdown/index.tsx\``,
1086
1003
  RichTextEditor: `# RichTextEditor Component
1087
1004
 
1088
- TipTap-based rich text editor.
1005
+ TipTap-based rich text editor with HTML and Markdown support.
1089
1006
 
1090
1007
  \`\`\`typescript
1091
- import { RichTextEditor } from '@iblai/web-containers';
1008
+ import { RichTextEditor } from '@iblai/iblai-js/web-containers';
1009
+
1010
+ interface RichTextEditorProps {
1011
+ value: string;
1012
+ onChange: (value: string) => void;
1013
+ exportFormat?: 'html' | 'markdown';
1014
+ disabled?: boolean;
1015
+ placeholder?: string;
1016
+ minHeight?: string;
1017
+ className?: string;
1018
+ id?: string;
1019
+ ariaLabel?: string;
1020
+ ariaLabelledBy?: string;
1021
+ ariaDescribedBy?: string;
1022
+ ariaRequired?: boolean;
1023
+ ariaInvalid?: boolean;
1024
+ }
1092
1025
 
1093
1026
  <RichTextEditor
1094
- content={content}
1027
+ value={content}
1095
1028
  onChange={setContent}
1029
+ exportFormat="html"
1096
1030
  placeholder="Start typing..."
1031
+ minHeight="200px"
1097
1032
  />
1098
1033
  \`\`\`
1099
1034
 
@@ -1103,17 +1038,37 @@ import { RichTextEditor } from '@iblai/web-containers';
1103
1038
  Searchable dropdown with multiple selection.
1104
1039
 
1105
1040
  \`\`\`typescript
1106
- import { SearchableMultiSelect } from '@iblai/web-containers';
1041
+ import { SearchableMultiSelect } from '@iblai/iblai-js/web-containers';
1042
+
1043
+ interface SearchableMultiSelectProps<T = any> {
1044
+ items: T[];
1045
+ selectedItems: { label: string; value: string }[];
1046
+ onSelectionChange: (items: { label: string; value: string }[]) => void;
1047
+ searchQuery: string;
1048
+ onSearchChange: (query: string) => void;
1049
+ isLoading: boolean;
1050
+ placeholder?: string;
1051
+ getItemValue: (item: T) => string;
1052
+ getItemLabel: (item: T) => string;
1053
+ className?: string;
1054
+ maxHeight?: string;
1055
+ inputId?: string;
1056
+ ariaDescribedBy?: string;
1057
+ onSelectedItemAction?: (item: { label: string; value: string }) => void;
1058
+ selectedItemActionIcon?: React.ReactNode;
1059
+ selectedItemActionAriaLabel?: string;
1060
+ }
1107
1061
 
1108
1062
  <SearchableMultiSelect
1109
- options={[
1110
- { value: '1', label: 'Option 1' },
1111
- { value: '2', label: 'Option 2' },
1112
- ]}
1113
- selected={selectedValues}
1114
- onChange={setSelectedValues}
1115
- placeholder="Select options..."
1116
- searchPlaceholder="Search..."
1063
+ items={users}
1064
+ selectedItems={selectedUsers}
1065
+ onSelectionChange={setSelectedUsers}
1066
+ searchQuery={search}
1067
+ onSearchChange={setSearch}
1068
+ isLoading={loading}
1069
+ getItemValue={(u) => u.id}
1070
+ getItemLabel={(u) => u.name}
1071
+ placeholder="Select users..."
1117
1072
  />
1118
1073
  \`\`\`
1119
1074
 
@@ -1123,55 +1078,81 @@ import { SearchableMultiSelect } from '@iblai/web-containers';
1123
1078
  Dropdown to switch between tenants/organizations.
1124
1079
 
1125
1080
  \`\`\`typescript
1126
- import { TenantSwitcher } from '@iblai/web-containers';
1081
+ import { TenantSwitcher } from '@iblai/iblai-js/web-containers';
1082
+
1083
+ interface TenantSwitcherProps {
1084
+ currentTenantKey: string | null;
1085
+ tenants: Tenant[];
1086
+ visitingTenant?: Tenant;
1087
+ onTenantChange: (tenantKey: string, saveRedirect?: boolean) => Promise<void>;
1088
+ setHideTenantSwitcher?: (hide: boolean) => void;
1089
+ setOpenAccount?: (tab: 'basic' | 'organization') => void;
1090
+ setLoadingTenantInfo?: (loading: boolean) => void;
1091
+ rbacPermissions: object;
1092
+ enableRbac?: boolean;
1093
+ }
1127
1094
 
1128
1095
  <TenantSwitcher
1129
- currentTenant={currentTenant}
1096
+ currentTenantKey={currentTenant}
1130
1097
  tenants={userTenants}
1131
- onSwitch={handleTenantSwitch}
1098
+ onTenantChange={handleTenantSwitch}
1099
+ rbacPermissions={permissions}
1100
+ enableRbac={true}
1132
1101
  />
1133
1102
  \`\`\`
1134
1103
 
1135
1104
  **File Location**: \`packages/web-containers/src/components/tenant-switch/index.tsx\``,
1136
1105
  TopBanner: `# TopBanner Component
1137
1106
 
1138
- Sticky banner at the top of the page.
1107
+ Notification banner at the top of the page.
1139
1108
 
1140
1109
  \`\`\`typescript
1141
- import { TopBanner, TopBannerProps } from '@iblai/web-containers';
1110
+ import { TopBanner } from '@iblai/iblai-js/web-containers';
1111
+
1112
+ interface TopBannerProps {
1113
+ parentContainerSelector: string;
1114
+ bannerText?: string;
1115
+ loading?: boolean;
1116
+ tooltipText?: string;
1117
+ buttonLabel?: string;
1118
+ buttonHandler?: () => void;
1119
+ onLoad?: () => void;
1120
+ onClose?: () => void;
1121
+ }
1142
1122
 
1143
1123
  <TopBanner
1144
- message="Your trial expires in 7 days"
1145
- type="warning"
1146
- action={{
1147
- label: "Upgrade",
1148
- onClick: handleUpgrade,
1149
- }}
1150
- onDismiss={handleDismiss}
1124
+ parentContainerSelector="#main-content"
1125
+ bannerText="Your trial expires in 7 days"
1126
+ buttonLabel="Upgrade"
1127
+ buttonHandler={handleUpgrade}
1128
+ onClose={handleDismiss}
1151
1129
  />
1152
1130
  \`\`\`
1153
1131
 
1154
1132
  **File Location**: \`packages/web-containers/src/components/top-banner/index.tsx\``,
1155
1133
  Loader: `# Loader Component
1156
1134
 
1157
- Spinning loader with gradient animation.
1135
+ Full-screen animated loading spinner.
1158
1136
 
1159
1137
  \`\`\`typescript
1160
- import { Loader } from '@iblai/web-containers';
1138
+ import { Loader } from '@iblai/iblai-js/web-containers';
1161
1139
 
1140
+ // No props required
1162
1141
  <Loader />
1163
-
1164
- // Custom size
1165
- <Loader className="h-8 w-8" />
1166
1142
  \`\`\`
1167
1143
 
1168
1144
  **File Location**: \`packages/web-containers/src/components/loader.tsx\``,
1169
1145
  Spinner: `# Spinner Component
1170
1146
 
1171
- Alternative spinner component.
1147
+ Compact animated spinner icon.
1172
1148
 
1173
1149
  \`\`\`typescript
1174
- import { Spinner } from '@iblai/web-containers';
1150
+ import { Spinner } from '@iblai/iblai-js/web-containers';
1151
+
1152
+ interface SpinnerProps {
1153
+ size?: 'sm' | 'md' | 'lg';
1154
+ className?: string;
1155
+ }
1175
1156
 
1176
1157
  <Spinner />
1177
1158
  <Spinner size="sm" />
@@ -1181,63 +1162,70 @@ import { Spinner } from '@iblai/web-containers';
1181
1162
  **File Location**: \`packages/web-containers/src/components/spinner/index.tsx\``,
1182
1163
  TimeTrackingProvider: `# TimeTrackingProvider Component
1183
1164
 
1184
- Context provider for time tracking functionality.
1165
+ Context provider for automatic time tracking on pages.
1185
1166
 
1186
1167
  \`\`\`typescript
1187
- import { TimeTrackingProvider } from '@iblai/web-containers';
1168
+ import { TimeTrackingProvider } from '@iblai/iblai-js/web-containers';
1169
+
1170
+ interface TimeTrackingProviderProps {
1171
+ intervalSeconds?: number;
1172
+ enabled?: boolean;
1173
+ sessionUuid?: string;
1174
+ getSessionUuid?: () => string | undefined;
1175
+ getTenantKey?: () => string;
1176
+ getMentorId?: () => string | undefined;
1177
+ getCurrentUrl?: () => string;
1178
+ onRouteChange?: (callback: () => void) => () => void;
1179
+ }
1188
1180
 
1189
1181
  <TimeTrackingProvider
1190
1182
  intervalSeconds={30}
1191
1183
  enabled={true}
1192
- onTimeUpdate={(url, timeSpent) => {
1193
- // Send to analytics
1194
- }}
1184
+ getTenantKey={() => tenantKey}
1185
+ getMentorId={() => mentorId}
1195
1186
  >
1196
1187
  {children}
1197
1188
  </TimeTrackingProvider>
1198
1189
  \`\`\`
1199
1190
 
1200
1191
  **File Location**: \`packages/web-containers/src/components/time-tracking-provider.tsx\``,
1201
- UserProfileDropdown: `# UserProfileDropdown Component
1202
-
1203
- User menu dropdown with profile and logout options.
1204
-
1205
- \`\`\`typescript
1206
- import { UserProfileDropdown } from '@iblai/web-containers';
1207
-
1208
- <UserProfileDropdown
1209
- user={userData}
1210
- onProfileClick={() => router.push('/profile')}
1211
- onLogout={handleLogout}
1212
- />
1213
- \`\`\`
1214
-
1215
- **File Location**: \`packages/web-containers/src/components/user-profile-dropdown/index.tsx\``,
1216
1192
  AdvancedPagination: `# AdvancedPagination Component
1217
1193
 
1218
- Enhanced pagination with page size selector.
1194
+ Pagination with ellipsis for large page ranges.
1219
1195
 
1220
1196
  \`\`\`typescript
1221
- import { AdvancedPagination } from '@iblai/web-containers';
1197
+ import { AdvancedPagination } from '@iblai/iblai-js/web-containers';
1198
+
1199
+ interface AdvancedPaginationProps {
1200
+ currentPage: number;
1201
+ totalPages: number;
1202
+ onPageChange: (page: number) => void;
1203
+ siblingCount?: number;
1204
+ }
1222
1205
 
1223
1206
  <AdvancedPagination
1224
1207
  currentPage={page}
1225
1208
  totalPages={totalPages}
1226
- pageSize={pageSize}
1227
1209
  onPageChange={setPage}
1228
- onPageSizeChange={setPageSize}
1210
+ siblingCount={1}
1229
1211
  />
1230
1212
  \`\`\`
1231
1213
 
1232
1214
  **File Location**: \`packages/web-containers/src/components/advance-pagination.tsx\``,
1233
1215
  ContentViewWrapper: `# ContentViewWrapper Component
1234
1216
 
1235
- Container wrapper for page content.
1217
+ Conditional wrapper that only renders children if the current SPA matches.
1236
1218
 
1237
1219
  \`\`\`typescript
1238
- import { ContentViewWrapper } from '@iblai/web-containers';
1220
+ import { ContentViewWrapper } from '@iblai/iblai-js/web-containers';
1239
1221
 
1240
- <ContentViewWrapper>
1222
+ interface Props {
1223
+ children: React.ReactNode;
1224
+ currentSPA: string | undefined;
1225
+ spas: string[];
1226
+ }
1227
+
1228
+ <ContentViewWrapper currentSPA={currentSPA} spas={['mentor', 'skills']}>
1241
1229
  {children}
1242
1230
  </ContentViewWrapper>
1243
1231
  \`\`\`
@@ -1248,41 +1236,319 @@ import { ContentViewWrapper } from '@iblai/web-containers';
1248
1236
  Display app version information.
1249
1237
 
1250
1238
  \`\`\`typescript
1251
- import { Version } from '@iblai/web-containers';
1239
+ import { Version } from '@iblai/iblai-js/web-containers';
1240
+
1241
+ interface VersionProps {
1242
+ appName: string;
1243
+ appVersion: string;
1244
+ poweredBy: React.ReactNode;
1245
+ }
1252
1246
 
1253
- <Version />
1247
+ <Version
1248
+ appName="Mentor"
1249
+ appVersion="1.0.0"
1250
+ poweredBy={<span>Powered by IBL.ai</span>}
1251
+ />
1254
1252
  \`\`\`
1255
1253
 
1256
1254
  **File Location**: \`packages/web-containers/src/components/version.tsx\``,
1255
+ // ============================================================================
1256
+ // NEXT.JS COMPONENTS (import from @iblai/iblai-js/web-containers/next)
1257
+ // ============================================================================
1258
+ UserProfileDropdown: `# UserProfileDropdown Component
1259
+
1260
+ User avatar dropdown menu with profile, account, tenant switching, and help.
1261
+
1262
+ \`\`\`typescript
1263
+ import { UserProfileDropdown } from '@iblai/iblai-js/web-containers/next';
1264
+
1265
+ interface UserProfileDropdownProps {
1266
+ username?: string;
1267
+ userIsAdmin?: boolean;
1268
+ userIsStudent?: boolean;
1269
+ userIsVisiting?: boolean;
1270
+ tenantKey?: string;
1271
+ currentTenant?: Tenant;
1272
+ userTenants?: Tenant[];
1273
+ showProfileTab?: boolean;
1274
+ showAccountTab?: boolean;
1275
+ showTenantSwitcher?: boolean;
1276
+ showHelpLink?: boolean;
1277
+ showLogoutButton?: boolean;
1278
+ showLearnerModeSwitch?: boolean;
1279
+ helpCenterUrl?: string;
1280
+ enableGravatarOnProfilePic?: boolean;
1281
+ onProfileClick?: (tab: string) => void;
1282
+ onLogout?: () => void;
1283
+ onTenantChange?: (tenantKey: string) => void;
1284
+ billingEnabled?: boolean;
1285
+ billingURL?: string;
1286
+ topUpEnabled?: boolean;
1287
+ topUpURL?: string;
1288
+ authURL: string;
1289
+ onTenantUpdate: (tenant: Tenant) => void;
1290
+ rbacPermissions?: object;
1291
+ enableRbac?: boolean;
1292
+ localLLMProps?: { /* LocalLLMTab props */ };
1293
+ isModalOpen?: boolean;
1294
+ onModalOpenChange?: (open: boolean) => void;
1295
+ defaultActiveTab?: string;
1296
+ // ... more optional props
1297
+ }
1298
+
1299
+ <UserProfileDropdown
1300
+ username={username}
1301
+ userIsAdmin={isAdmin}
1302
+ tenantKey={tenantKey}
1303
+ currentTenant={currentTenant}
1304
+ userTenants={tenants}
1305
+ authURL={authUrl}
1306
+ onTenantUpdate={handleTenantUpdate}
1307
+ onLogout={handleLogout}
1308
+ />
1309
+ \`\`\`
1310
+
1311
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1312
+
1313
+ **File Location**: \`packages/web-containers/src/components/user-profile-dropdown/index.tsx\``,
1314
+ UserProfileModal: `# UserProfileModal Component
1315
+
1316
+ Modal wrapper for Profile component with additional tabs (organization, management, integrations, billing).
1317
+
1318
+ \`\`\`typescript
1319
+ import { UserProfileModal } from '@iblai/iblai-js/web-containers/next';
1320
+
1321
+ interface UserProfileModalProps {
1322
+ isOpen: boolean;
1323
+ onClose: () => void;
1324
+ params: {
1325
+ tenantKey: string;
1326
+ mentorId?: string;
1327
+ isAdmin?: boolean;
1328
+ };
1329
+ tenants?: Tenant[];
1330
+ billingEnabled?: boolean;
1331
+ billingURL?: string;
1332
+ topUpEnabled?: boolean;
1333
+ topUpURL?: string;
1334
+ showMentorAIDisplayCheckbox?: boolean;
1335
+ showLeaderboardDisplayCheckbox?: boolean;
1336
+ showUsernameField?: boolean;
1337
+ showPlatformName?: boolean;
1338
+ useGravatarPicFallback?: boolean;
1339
+ targetTab?: string;
1340
+ currentPlan?: string;
1341
+ authURL: string;
1342
+ onTenantUpdate?: (tenant: Tenant) => void;
1343
+ rbacPermissions?: object;
1344
+ enableRbac?: boolean;
1345
+ localLLMProps?: { /* LocalLLMTab props */ };
1346
+ }
1347
+
1348
+ <UserProfileModal
1349
+ isOpen={open}
1350
+ onClose={() => setOpen(false)}
1351
+ params={{ tenantKey, isAdmin }}
1352
+ authURL={authUrl}
1353
+ />
1354
+ \`\`\`
1355
+
1356
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1357
+
1358
+ **File Location**: \`packages/web-containers/src/components/modals/user-profile-modal.tsx\``,
1257
1359
  SsoLogin: `# SsoLogin Component
1258
1360
 
1259
1361
  SSO callback handler for authentication.
1260
1362
 
1261
1363
  \`\`\`typescript
1262
- import { SsoLogin } from '@iblai/web-containers';
1364
+ import { SsoLogin, initializeLocalStorageWithObject } from '@iblai/iblai-js/web-containers/next';
1365
+
1366
+ interface SsoLoginProps {
1367
+ localStorageKeys: {
1368
+ CURRENT_TENANT: string;
1369
+ USER_DATA: string;
1370
+ TENANTS: string;
1371
+ AXD_TOKEN?: string;
1372
+ AXD_TOKEN_EXPIRES?: string;
1373
+ DM_TOKEN?: string;
1374
+ DM_TOKEN_EXPIRES?: string;
1375
+ EDX_TOKEN_KEY?: string;
1376
+ };
1377
+ redirectPathKey?: string;
1378
+ defaultRedirectPath?: string;
1379
+ onLoginSuccess?: (data: Record<string, string>) => void;
1380
+ }
1263
1381
 
1264
1382
  // In your sso-login page
1265
1383
  export default function SsoLoginPage() {
1266
- return <SsoLogin onSuccess={handleSuccess} onError={handleError} />;
1384
+ return (
1385
+ <SsoLogin
1386
+ localStorageKeys={{
1387
+ CURRENT_TENANT: 'current_tenant',
1388
+ USER_DATA: 'user_data',
1389
+ TENANTS: 'tenants',
1390
+ }}
1391
+ defaultRedirectPath="/home"
1392
+ onLoginSuccess={handleSuccess}
1393
+ />
1394
+ );
1267
1395
  }
1268
1396
  \`\`\`
1269
1397
 
1398
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1399
+
1270
1400
  **File Location**: \`packages/web-containers/src/components/sso-login.tsx\``,
1271
1401
  ErrorPage: `# ErrorPage Component
1272
1402
 
1273
- Full-page error display.
1403
+ Full-page error display with customizable messaging.
1274
1404
 
1275
1405
  \`\`\`typescript
1276
- import { ErrorPage } from '@iblai/web-containers/next';
1406
+ import { ErrorPage } from '@iblai/iblai-js/web-containers/next';
1407
+
1408
+ interface ErrorPageProps {
1409
+ errorCode: string;
1410
+ supportEmail?: string;
1411
+ showSupportButton?: boolean;
1412
+ supportButtonText?: string;
1413
+ customTitle?: string;
1414
+ customDescription?: string;
1415
+ customIcon?: React.ReactNode;
1416
+ showHomeButton?: boolean;
1417
+ homeButtonText?: string;
1418
+ homeButtonHref?: string;
1419
+ showReset?: boolean;
1420
+ resetButtonText?: string;
1421
+ reset?: () => void;
1422
+ }
1277
1423
 
1278
1424
  <ErrorPage
1279
- statusCode={404}
1280
- title="Page Not Found"
1281
- description="The page you're looking for doesn't exist."
1425
+ errorCode="404"
1426
+ customTitle="Page Not Found"
1427
+ customDescription="The page you're looking for doesn't exist."
1428
+ showHomeButton={true}
1282
1429
  />
1283
1430
  \`\`\`
1284
1431
 
1432
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1433
+
1285
1434
  **File Location**: \`packages/web-containers/src/components/error/error-page.tsx\``,
1435
+ AppSidebar: `# AppSidebar Component
1436
+
1437
+ Collapsible sidebar for the Mentor app with configurable content and footer menu items.
1438
+
1439
+ \`\`\`typescript
1440
+ import { AppSidebar } from '@iblai/iblai-js/web-containers/next';
1441
+
1442
+ interface MenuItem {
1443
+ icon: React.ComponentType<{ className?: string }>;
1444
+ label: string;
1445
+ onClick: () => void;
1446
+ hasBorder?: boolean;
1447
+ }
1448
+
1449
+ interface AppSidebarProps {
1450
+ logo?: React.ReactNode;
1451
+ contentItems: MenuItem[];
1452
+ footerItems: MenuItem[];
1453
+ showProjects?: boolean;
1454
+ showPinnedMessages?: boolean;
1455
+ showRecentMessages?: boolean;
1456
+ }
1457
+
1458
+ <AppSidebar
1459
+ logo={<img src="/logo.svg" alt="Logo" />}
1460
+ contentItems={[
1461
+ { icon: MessageSquare, label: 'Chat', onClick: () => navigate('/chat') },
1462
+ { icon: Compass, label: 'Explore', onClick: () => navigate('/explore'), hasBorder: true },
1463
+ ]}
1464
+ footerItems={[
1465
+ { icon: Settings, label: 'Settings', onClick: openSettings },
1466
+ { icon: LogOut, label: 'Logout', onClick: handleLogout },
1467
+ ]}
1468
+ showProjects={false}
1469
+ showPinnedMessages={false}
1470
+ showRecentMessages={false}
1471
+ />
1472
+ \`\`\`
1473
+
1474
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1475
+
1476
+ **File Location**: \`packages/web-containers/src/components/mentor-ui/app-sidebar/index.tsx\``,
1477
+ NavBar: `# NavBar Component
1478
+
1479
+ Top navigation bar with user menu, new chat button, and optional mentor dropdown.
1480
+
1481
+ \`\`\`typescript
1482
+ import { NavBar } from '@iblai/iblai-js/web-containers/next';
1483
+
1484
+ interface NavBarProps {
1485
+ username?: string | null;
1486
+ isAuthenticated?: boolean;
1487
+ onNewChat?: () => void;
1488
+ onSettings?: () => void;
1489
+ onLogout?: () => void;
1490
+ onLogin?: () => void;
1491
+ mentorName?: string;
1492
+ showMentorDropdown?: boolean;
1493
+ additionalMenuItems?: Array<{
1494
+ icon: React.ComponentType<{ className?: string }>;
1495
+ label: string;
1496
+ onClick: () => void;
1497
+ separator?: boolean;
1498
+ }>;
1499
+ }
1500
+
1501
+ <NavBar
1502
+ username={username}
1503
+ isAuthenticated={true}
1504
+ onNewChat={() => startNewChat()}
1505
+ onSettings={() => openSettings()}
1506
+ onLogout={() => handleLogout()}
1507
+ onLogin={() => redirectToLogin()}
1508
+ mentorName="My Mentor"
1509
+ showMentorDropdown={false}
1510
+ additionalMenuItems={[
1511
+ { icon: User, label: 'Profile', onClick: openProfile },
1512
+ ]}
1513
+ />
1514
+ \`\`\`
1515
+
1516
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1517
+
1518
+ **File Location**: \`packages/web-containers/src/components/mentor-ui/navbar/index.tsx\``,
1519
+ ConversationStarters: `# ConversationStarters Component
1520
+
1521
+ Displays guided prompt cards that users can click to start a chat session.
1522
+
1523
+ \`\`\`typescript
1524
+ import { ConversationStarters } from '@iblai/iblai-js/web-containers/next';
1525
+
1526
+ interface GuidedPrompt {
1527
+ prompt: string;
1528
+ icon?: string; // Lucide icon name (e.g., 'book-open', 'lightbulb')
1529
+ }
1530
+
1531
+ interface ConversationStartersProps {
1532
+ onTemplateSelect: (template: string) => void;
1533
+ guidedPrompts?: GuidedPrompt[];
1534
+ disabled?: boolean;
1535
+ className?: string;
1536
+ }
1537
+
1538
+ <ConversationStarters
1539
+ onTemplateSelect={(prompt) => sendMessage(prompt)}
1540
+ guidedPrompts={[
1541
+ { prompt: 'Help me study for my exam', icon: 'book-open' },
1542
+ { prompt: 'Explain this concept', icon: 'lightbulb' },
1543
+ ]}
1544
+ disabled={isStreaming}
1545
+ className="mt-4"
1546
+ />
1547
+ \`\`\`
1548
+
1549
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1550
+
1551
+ **File Location**: \`packages/web-containers/src/components/mentor-ui/welcome-chat/conversation-starters.tsx\``,
1286
1552
  ClientErrorPage: `# ClientErrorPage Component
1287
1553
 
1288
1554
  Client-side error boundary page.
@@ -1291,7 +1557,7 @@ Client-side error boundary page.
1291
1557
  // app/error.tsx
1292
1558
  'use client';
1293
1559
 
1294
- import { ClientErrorPage } from '@iblai/web-containers/next';
1560
+ import { ClientErrorPage } from '@iblai/iblai-js/web-containers/next';
1295
1561
 
1296
1562
  export default function Error({
1297
1563
  error,
@@ -1300,24 +1566,234 @@ export default function Error({
1300
1566
  error: Error & { digest?: string };
1301
1567
  reset: () => void;
1302
1568
  }) {
1303
- return <ClientErrorPage error={error} reset={reset} />;
1569
+ return (
1570
+ <ClientErrorPage
1571
+ handleError={(err) => console.error(err)}
1572
+ errorCode="500"
1573
+ showHomeButton={true}
1574
+ />
1575
+ );
1576
+ }
1577
+
1578
+ interface ClientErrorPageProps {
1579
+ header?: string;
1580
+ message?: string;
1581
+ errorCode?: string;
1582
+ showHomeButton?: boolean;
1583
+ supportEmail?: string;
1584
+ handleError: (error: any) => void;
1304
1585
  }
1305
1586
  \`\`\`
1306
1587
 
1588
+ > **Import from \`@iblai/iblai-js/web-containers/next\`** — requires Next.js
1589
+
1307
1590
  **File Location**: \`packages/web-containers/src/components/error/client-error-page.tsx\``,
1591
+ // ============================================================================
1592
+ // WORKFLOW COMPONENTS
1593
+ // ============================================================================
1594
+ ConnectorManagementDialog: `# ConnectorManagementDialog Component
1595
+
1596
+ Dialog for browsing and adding MCP (Model Context Protocol) connectors to a workflow. Displays featured and third-party connectors in a searchable, tabbed interface.
1597
+
1598
+ \`\`\`typescript
1599
+ import { ConnectorManagementDialog } from '@iblai/iblai-js/web-containers';
1600
+
1601
+ interface ConnectorManagementDialogProps {
1602
+ open: boolean;
1603
+ onClose: () => void;
1604
+ onAddConnector?: (connector: { name: string; icon?: string }) => void;
1605
+ }
1606
+
1607
+ <ConnectorManagementDialog
1608
+ open={isOpen}
1609
+ onClose={() => setIsOpen(false)}
1610
+ onAddConnector={(connector) => handleAdd(connector)}
1611
+ />
1612
+ \`\`\`
1613
+
1614
+ **File Location**: \`packages/web-containers/src/components/workflows/connector-management-dialog.tsx\``,
1615
+ CreateWorkflowModal: `# CreateWorkflowModal Component
1616
+
1617
+ Modal dialog for creating a new workflow. Provides a text input for the workflow name with Enter key support and loading state.
1618
+
1619
+ \`\`\`typescript
1620
+ import { CreateWorkflowModal } from '@iblai/iblai-js/web-containers';
1621
+
1622
+ interface CreateWorkflowModalProps {
1623
+ open: boolean;
1624
+ onOpenChange: (open: boolean) => void;
1625
+ onCreateWorkflow: (name: string) => void;
1626
+ isCreating?: boolean;
1627
+ }
1628
+
1629
+ <CreateWorkflowModal
1630
+ open={showCreate}
1631
+ onOpenChange={setShowCreate}
1632
+ onCreateWorkflow={(name) => createWorkflow(name)}
1633
+ isCreating={isCreating}
1634
+ />
1635
+ \`\`\`
1636
+
1637
+ **File Location**: \`packages/web-containers/src/components/workflows/create-workflow-modal.tsx\``,
1638
+ DeleteWorkflowModal: `# DeleteWorkflowModal Component
1639
+
1640
+ Alert dialog for confirming workflow deletion. Shows the workflow name and manages loading state during deletion.
1641
+
1642
+ \`\`\`typescript
1643
+ import { DeleteWorkflowModal } from '@iblai/iblai-js/web-containers';
1644
+
1645
+ interface DeleteWorkflowModalProps {
1646
+ isOpen: boolean;
1647
+ onClose: () => void;
1648
+ onConfirm: () => void;
1649
+ isDeleting: boolean;
1650
+ workflowName?: string;
1651
+ }
1652
+
1653
+ <DeleteWorkflowModal
1654
+ isOpen={showDelete}
1655
+ onClose={() => setShowDelete(false)}
1656
+ onConfirm={handleDelete}
1657
+ isDeleting={isDeleting}
1658
+ workflowName={workflow.name}
1659
+ />
1660
+ \`\`\`
1661
+
1662
+ **File Location**: \`packages/web-containers/src/components/workflows/delete-workflow-modal.tsx\``,
1663
+ NodeTypeItem: `# NodeTypeItem Type
1664
+
1665
+ Type interface representing a workflow node that can be placed in a workflow canvas.
1666
+
1667
+ \`\`\`typescript
1668
+ import type { NodeTypeItem } from '@iblai/iblai-js/web-containers';
1669
+
1670
+ interface NodeTypeItem {
1671
+ id: string; // Node type identifier (e.g., 'mentor', 'end', 'if-else')
1672
+ label: string; // Display label
1673
+ category?: string; // Optional category grouping
1674
+ }
1675
+ \`\`\`
1676
+
1677
+ **File Location**: \`packages/web-containers/src/components/workflows/workflow-sidebar.tsx\``,
1678
+ NodeTypeSection: `# NodeTypeSection Type
1679
+
1680
+ Type interface representing a group of related node types for display in the WorkflowSidebar.
1681
+
1682
+ \`\`\`typescript
1683
+ import type { NodeTypeSection, NodeTypeItem } from '@iblai/iblai-js/web-containers';
1684
+
1685
+ interface NodeTypeSection {
1686
+ title: string; // Section heading (e.g., 'Core', 'Tools', 'Logic')
1687
+ items: NodeTypeItem[]; // Node types in this section
1688
+ }
1689
+
1690
+ const sections: NodeTypeSection[] = [
1691
+ { title: 'Core', items: [{ id: 'mentor', label: 'Mentor' }, { id: 'end', label: 'End' }] },
1692
+ { title: 'Logic', items: [{ id: 'if-else', label: 'If/Else' }] },
1693
+ ];
1694
+ \`\`\`
1695
+
1696
+ **File Location**: \`packages/web-containers/src/components/workflows/workflow-sidebar.tsx\``,
1697
+ ToolDialogs: `# ToolDialogs Component
1698
+
1699
+ Dialog system for adding and configuring various tool types in a workflow. Supports MCP, Web Search, Code Interpreter, Guardrails, If/Else, While loops, User Approval, Transform, and Set State tools.
1700
+
1701
+ \`\`\`typescript
1702
+ import { ToolDialogs } from '@iblai/iblai-js/web-containers';
1703
+
1704
+ interface ToolDialogsProps {
1705
+ trigger: React.ReactNode;
1706
+ onAddTool?: (toolType: string, toolName: string, config?: Record<string, unknown>) => void;
1707
+ }
1708
+
1709
+ <ToolDialogs
1710
+ trigger={<Button>Add Tool</Button>}
1711
+ onAddTool={(type, name, config) => handleAddTool(type, name, config)}
1712
+ />
1713
+ \`\`\`
1714
+
1715
+ **File Location**: \`packages/web-containers/src/components/workflows/tool-dialogs.tsx\``,
1716
+ WorkflowSidebar: `# WorkflowSidebar Component
1717
+
1718
+ Sidebar displaying available workflow node types organized into sections. Supports drag-and-drop for adding nodes to a workflow canvas.
1719
+
1720
+ \`\`\`typescript
1721
+ import { WorkflowSidebar } from '@iblai/iblai-js/web-containers';
1722
+ import type { NodeTypeSection } from '@iblai/iblai-js/web-containers';
1723
+
1724
+ interface WorkflowSidebarProps {
1725
+ onDragStart: (item: { id: string; label: string; type: string }) => void;
1726
+ onItemClick: (item: { id: string; label: string; type: string }) => void;
1727
+ nodeTypes?: NodeTypeSection[]; // Custom sections (optional)
1728
+ }
1729
+
1730
+ <WorkflowSidebar
1731
+ onDragStart={(item) => handleDragStart(item)}
1732
+ onItemClick={(item) => handleAddNode(item)}
1733
+ nodeTypes={customSections}
1734
+ />
1735
+ \`\`\`
1736
+
1737
+ **File Location**: \`packages/web-containers/src/components/workflows/workflow-sidebar.tsx\``,
1308
1738
  };
1739
+ const UI_PRIMITIVES = [
1740
+ 'Button',
1741
+ 'Card',
1742
+ 'Dialog',
1743
+ 'Input',
1744
+ 'Label',
1745
+ 'Textarea',
1746
+ 'Select',
1747
+ 'Checkbox',
1748
+ 'RadioGroup',
1749
+ 'Switch',
1750
+ 'Tabs',
1751
+ 'Avatar',
1752
+ 'Badge',
1753
+ 'Tooltip',
1754
+ 'Popover',
1755
+ 'DropdownMenu',
1756
+ 'Table',
1757
+ 'Skeleton',
1758
+ 'Separator',
1759
+ 'Progress',
1760
+ 'Calendar',
1761
+ 'Pagination',
1762
+ 'Toggle',
1763
+ 'Toast',
1764
+ 'Chart',
1765
+ ];
1309
1766
  export function getComponentInfo(componentName) {
1310
1767
  const info = components[componentName];
1311
- if (!info) {
1312
- const allComponents = Object.keys(components).sort();
1313
- return `Component "${componentName}" not found.
1314
-
1315
- **Available UI Primitives (${allComponents.filter((c) => ['Button', 'Card', 'Dialog', 'Input', 'Label', 'Textarea', 'Select', 'Checkbox', 'RadioGroup', 'Switch', 'Tabs', 'Avatar', 'Badge', 'Tooltip', 'Popover', 'DropdownMenu', 'Table', 'Skeleton', 'Separator', 'Calendar', 'Pagination', 'Toggle', 'Toast', 'Chart'].includes(c)).length}):**
1316
- Button, Card, Dialog, Input, Label, Textarea, Select, Checkbox, RadioGroup, Switch, Tabs, Avatar, Badge, Tooltip, Popover, DropdownMenu, Table, Skeleton, Separator, Calendar, Pagination, Toggle, Toast, Chart
1317
-
1318
- **Available Feature Components (${allComponents.filter((c) => !['Button', 'Card', 'Dialog', 'Input', 'Label', 'Textarea', 'Select', 'Checkbox', 'RadioGroup', 'Switch', 'Tabs', 'Avatar', 'Badge', 'Tooltip', 'Popover', 'DropdownMenu', 'Table', 'Skeleton', 'Separator', 'Calendar', 'Pagination', 'Toggle', 'Toast', 'Chart'].includes(c)).length}):**
1319
- Profile, InviteUserDialog, LocalLLMTab, NotificationDropdown, SendNotificationDialog, AlertsTab, AnalyticsLayout, LoginButton, SignupButton, Markdown, RichTextEditor, SearchableMultiSelect, TenantSwitcher, TopBanner, Loader, Spinner, TimeTrackingProvider, UserProfileDropdown, AdvancedPagination, ContentViewWrapper, Version, SsoLogin, ErrorPage, ClientErrorPage`;
1320
- }
1321
- return info;
1768
+ if (info)
1769
+ return info;
1770
+ // Fuzzy match
1771
+ const lower = componentName.toLowerCase();
1772
+ const match = Object.keys(components).find((k) => k.toLowerCase() === lower);
1773
+ if (match)
1774
+ return components[match];
1775
+ const allComponents = Object.keys(components).sort();
1776
+ const featureComponents = allComponents.filter((c) => !UI_PRIMITIVES.includes(c));
1777
+ const nextComponents = [
1778
+ 'UserProfileDropdown',
1779
+ 'UserProfileModal',
1780
+ 'SsoLogin',
1781
+ 'ErrorPage',
1782
+ 'ClientErrorPage',
1783
+ 'AppSidebar',
1784
+ 'NavBar',
1785
+ 'ConversationStarters',
1786
+ ,
1787
+ ];
1788
+ return `Component "${componentName}" not found.
1789
+
1790
+ **UI Primitives (${UI_PRIMITIVES.length}):**
1791
+ ${UI_PRIMITIVES.join(', ')}
1792
+
1793
+ **Feature Components (${featureComponents.filter((c) => !nextComponents.includes(c)).length}):**
1794
+ ${featureComponents.filter((c) => !nextComponents.includes(c)).join(', ')}
1795
+
1796
+ **Next.js Components (${nextComponents.length}) — import from @iblai/iblai-js/web-containers/next:**
1797
+ ${nextComponents.join(', ')}`;
1322
1798
  }
1323
1799
  //# sourceMappingURL=component-info.js.map