@specverse/engines 4.1.5 → 4.1.6

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 (120) hide show
  1. package/dist/libs/instance-factories/applications/templates/generic/backend-env-generator.js +22 -0
  2. package/dist/libs/instance-factories/applications/templates/generic/backend-package-json-generator.js +66 -0
  3. package/dist/libs/instance-factories/applications/templates/generic/backend-tsconfig-generator.js +54 -0
  4. package/dist/libs/instance-factories/applications/templates/generic/main-generator.js +290 -0
  5. package/dist/libs/instance-factories/applications/templates/react/_view-components-source.js +530 -0
  6. package/dist/libs/instance-factories/applications/templates/react/api-client-generator.js +437 -0
  7. package/dist/libs/instance-factories/applications/templates/react/api-types-generator.js +146 -0
  8. package/dist/libs/instance-factories/applications/templates/react/app-tsx-generator.js +73 -0
  9. package/dist/libs/instance-factories/applications/templates/react/env-example-generator.js +18 -0
  10. package/dist/libs/instance-factories/applications/templates/react/field-helpers-generator.js +99 -0
  11. package/dist/libs/instance-factories/applications/templates/react/gitignore-generator.js +35 -0
  12. package/dist/libs/instance-factories/applications/templates/react/index-css-generator.js +9 -0
  13. package/dist/libs/instance-factories/applications/templates/react/index-html-generator.js +23 -0
  14. package/dist/libs/instance-factories/applications/templates/react/main-tsx-generator.js +29 -0
  15. package/dist/libs/instance-factories/applications/templates/react/package-json-generator.js +49 -0
  16. package/dist/libs/instance-factories/applications/templates/react/pattern-adapter-generator.js +156 -0
  17. package/dist/libs/instance-factories/applications/templates/react/react-pattern-adapter.js +935 -0
  18. package/dist/libs/instance-factories/applications/templates/react/relationship-field-generator.js +143 -0
  19. package/dist/libs/instance-factories/applications/templates/react/runtime-app-tsx-generator.js +101 -0
  20. package/dist/libs/instance-factories/applications/templates/react/runtime-package-json-generator.js +50 -0
  21. package/dist/libs/instance-factories/applications/templates/react/tailwind-adapter-generator.js +646 -0
  22. package/dist/libs/instance-factories/applications/templates/react/tailwind-adapter-wrapper-generator.js +65 -0
  23. package/dist/libs/instance-factories/applications/templates/react/tsconfig-generator.js +28 -0
  24. package/dist/libs/instance-factories/applications/templates/react/use-api-hooks-generator.js +132 -0
  25. package/dist/libs/instance-factories/applications/templates/react/view-dashboard-generator.js +143 -0
  26. package/dist/libs/instance-factories/applications/templates/react/view-detail-generator.js +143 -0
  27. package/dist/libs/instance-factories/applications/templates/react/view-form-generator.js +355 -0
  28. package/dist/libs/instance-factories/applications/templates/react/view-list-generator.js +91 -0
  29. package/dist/libs/instance-factories/applications/templates/react/view-router-generator.js +79 -0
  30. package/dist/libs/instance-factories/applications/templates/react/vite-config-generator.js +42 -0
  31. package/dist/libs/instance-factories/cli/templates/commander/cli-bin-wrapper-generator.js +11 -0
  32. package/dist/libs/instance-factories/cli/templates/commander/cli-entry-generator.js +111 -0
  33. package/dist/libs/instance-factories/cli/templates/commander/command-generator.js +928 -0
  34. package/dist/libs/instance-factories/communication/templates/eventemitter/bus-generator.js +83 -0
  35. package/dist/libs/instance-factories/communication/templates/eventemitter/publisher-generator.js +91 -0
  36. package/dist/libs/instance-factories/communication/templates/eventemitter/subscriber-generator.js +86 -0
  37. package/dist/libs/instance-factories/controllers/templates/fastify/meta-routes-generator.js +93 -0
  38. package/dist/libs/instance-factories/controllers/templates/fastify/routes-generator.js +280 -0
  39. package/dist/libs/instance-factories/controllers/templates/fastify/server-generator.js +125 -0
  40. package/dist/libs/instance-factories/infrastructure/templates/docker-k8s/infrastructure-generator.js +25 -0
  41. package/dist/libs/instance-factories/orms/templates/prisma/schema-generator.js +371 -0
  42. package/dist/libs/instance-factories/orms/templates/prisma/services-generator.js +266 -0
  43. package/dist/libs/instance-factories/scaffolding/templates/generic/env-example-generator.js +51 -0
  44. package/dist/libs/instance-factories/scaffolding/templates/generic/env-generator.js +61 -0
  45. package/dist/libs/instance-factories/scaffolding/templates/generic/gitignore-generator.js +59 -0
  46. package/dist/libs/instance-factories/scaffolding/templates/generic/package-json-generator.js +126 -0
  47. package/dist/libs/instance-factories/scaffolding/templates/generic/readme-generator.js +159 -0
  48. package/dist/libs/instance-factories/scaffolding/templates/generic/tsconfig-generator.js +56 -0
  49. package/dist/libs/instance-factories/scaffolding/templates/generic/tsconfig-react-generator.js +37 -0
  50. package/dist/libs/instance-factories/sdks/templates/python/sdk-generator.js +29 -0
  51. package/dist/libs/instance-factories/sdks/templates/typescript/sdk-generator.js +28 -0
  52. package/dist/libs/instance-factories/services/templates/memory/generate-interpreter.js +14 -0
  53. package/dist/libs/instance-factories/services/templates/memory/step-conventions-memory.js +415 -0
  54. package/dist/libs/instance-factories/services/templates/prisma/behavior-generator.js +177 -0
  55. package/dist/libs/instance-factories/services/templates/prisma/controller-generator.js +413 -0
  56. package/dist/libs/instance-factories/services/templates/prisma/service-generator.js +243 -0
  57. package/dist/libs/instance-factories/services/templates/prisma/step-conventions.js +264 -0
  58. package/dist/libs/instance-factories/services/templates/shared-patterns.js +24 -0
  59. package/dist/libs/instance-factories/shared/path-resolver.js +59 -0
  60. package/dist/libs/instance-factories/storage/templates/mongodb/config-generator.js +13 -0
  61. package/dist/libs/instance-factories/storage/templates/mongodb/docker-generator.js +16 -0
  62. package/dist/libs/instance-factories/storage/templates/postgresql/config-generator.js +45 -0
  63. package/dist/libs/instance-factories/storage/templates/postgresql/docker-generator.js +46 -0
  64. package/dist/libs/instance-factories/storage/templates/redis/config-generator.js +14 -0
  65. package/dist/libs/instance-factories/storage/templates/redis/docker-generator.js +16 -0
  66. package/dist/libs/instance-factories/test-generation.js +145 -0
  67. package/dist/libs/instance-factories/testing/templates/vitest/tests-generator.js +30 -0
  68. package/dist/libs/instance-factories/tools/templates/mcp/mcp-server-generator.js +149 -0
  69. package/dist/libs/instance-factories/tools/templates/mcp/static/src/controllers/MCPServerController.js +232 -0
  70. package/dist/libs/instance-factories/tools/templates/mcp/static/src/events/EventEmitter.js +49 -0
  71. package/dist/libs/instance-factories/tools/templates/mcp/static/src/index.js +18 -0
  72. package/dist/libs/instance-factories/tools/templates/mcp/static/src/interfaces/ResourceProvider.js +0 -0
  73. package/dist/libs/instance-factories/tools/templates/mcp/static/src/models/LibrarySuggestion.js +97 -0
  74. package/dist/libs/instance-factories/tools/templates/mcp/static/src/models/SpecVerseResource.js +64 -0
  75. package/dist/libs/instance-factories/tools/templates/mcp/static/src/server/mcp-server.js +182 -0
  76. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/CLIProxyService.js +1210 -0
  77. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/EmbeddedResourcesAdapter.js +172 -0
  78. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/EntityModuleService.js +240 -0
  79. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/HybridResourcesProvider.js +147 -0
  80. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/LibraryToolsService.js +281 -0
  81. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/OrchestratorBridge.js +409 -0
  82. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/OrchestratorToolsService.js +414 -0
  83. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/PromptToolsService.js +467 -0
  84. package/dist/libs/instance-factories/tools/templates/mcp/static/src/services/ResourcesProviderService.js +135 -0
  85. package/dist/libs/instance-factories/tools/templates/mcp/static/src/types/index.js +0 -0
  86. package/dist/libs/instance-factories/tools/templates/vscode/static/extension.js +965 -0
  87. package/dist/libs/instance-factories/tools/templates/vscode/vscode-extension-generator.js +238 -0
  88. package/dist/libs/instance-factories/validation/templates/zod/validation-generator.js +25 -0
  89. package/dist/libs/instance-factories/views/index.js +48 -0
  90. package/dist/libs/instance-factories/views/templates/react/adapters/antd-adapter.js +742 -0
  91. package/dist/libs/instance-factories/views/templates/react/adapters/mui-adapter.js +824 -0
  92. package/dist/libs/instance-factories/views/templates/react/adapters/shadcn-adapter.js +719 -0
  93. package/dist/libs/instance-factories/views/templates/react/app-generator.js +45 -0
  94. package/dist/libs/instance-factories/views/templates/react/components-generator.js +779 -0
  95. package/dist/libs/instance-factories/views/templates/react/forms-generator.js +285 -0
  96. package/dist/libs/instance-factories/views/templates/react/frontend-package-json-generator.js +46 -0
  97. package/dist/libs/instance-factories/views/templates/react/hooks-generator.js +111 -0
  98. package/dist/libs/instance-factories/views/templates/react/index-css-generator.js +9 -0
  99. package/dist/libs/instance-factories/views/templates/react/index-html-generator.js +23 -0
  100. package/dist/libs/instance-factories/views/templates/react/main-tsx-generator.js +21 -0
  101. package/dist/libs/instance-factories/views/templates/react/react-component-generator.js +299 -0
  102. package/dist/libs/instance-factories/views/templates/react/router-generator.js +136 -0
  103. package/dist/libs/instance-factories/views/templates/react/router-generic-generator.js +107 -0
  104. package/dist/libs/instance-factories/views/templates/react/shared-utils-generator.js +179 -0
  105. package/dist/libs/instance-factories/views/templates/react/spec-json-generator.js +7 -0
  106. package/dist/libs/instance-factories/views/templates/react/types-generator.js +56 -0
  107. package/dist/libs/instance-factories/views/templates/react/views-metadata-generator.js +27 -0
  108. package/dist/libs/instance-factories/views/templates/react/vite-config-generator.js +29 -0
  109. package/dist/libs/instance-factories/views/templates/runtime/runtime-view-renderer.js +261 -0
  110. package/dist/libs/instance-factories/views/templates/shared/adapter-types.js +34 -0
  111. package/dist/libs/instance-factories/views/templates/shared/atomic-components-registry.js +800 -0
  112. package/dist/libs/instance-factories/views/templates/shared/base-generator.js +305 -0
  113. package/dist/libs/instance-factories/views/templates/shared/component-metadata.js +517 -0
  114. package/dist/libs/instance-factories/views/templates/shared/composite-pattern-types.js +0 -0
  115. package/dist/libs/instance-factories/views/templates/shared/composite-patterns.js +445 -0
  116. package/dist/libs/instance-factories/views/templates/shared/index.js +80 -0
  117. package/dist/libs/instance-factories/views/templates/shared/pattern-validator.js +210 -0
  118. package/dist/libs/instance-factories/views/templates/shared/property-mapper.js +492 -0
  119. package/dist/libs/instance-factories/views/templates/shared/syntax-mapper.js +321 -0
  120. package/package.json +3 -2
@@ -0,0 +1,824 @@
1
+ function renderProps(properties, exclude = []) {
2
+ return Object.entries(properties).filter(([key]) => !exclude.includes(key)).map(([key, value]) => {
3
+ if (typeof value === "boolean") return value ? key : "";
4
+ if (typeof value === "string") return `${key}="${value}"`;
5
+ return `${key}={${JSON.stringify(value)}}`;
6
+ }).filter(Boolean).join(" ");
7
+ }
8
+ const muiAdapter = {
9
+ name: "Material-UI",
10
+ version: "5.x",
11
+ description: "Material-UI (MUI) component library adapter",
12
+ baseDependencies: [
13
+ { name: "@mui/material", version: "^5.15.0" },
14
+ { name: "@mui/icons-material", version: "^5.15.0" },
15
+ { name: "@emotion/react", version: "^11.11.0" },
16
+ { name: "@emotion/styled", version: "^11.11.0" }
17
+ ],
18
+ config: {
19
+ importPrefix: "@mui/material",
20
+ importStyle: "named"
21
+ },
22
+ components: {
23
+ // ====================================================================
24
+ // DATA DISPLAY (9 types)
25
+ // ====================================================================
26
+ table: {
27
+ imports: [
28
+ "import { Table, TableBody, TableCell, TableContainer, TableHead, TableRow, Paper, TablePagination, TableSortLabel } from '@mui/material'"
29
+ ],
30
+ render: (ctx) => {
31
+ const { properties, model } = ctx;
32
+ const columns = properties.columns || ["id"];
33
+ const modelVar = model?.name?.toLowerCase() || "item";
34
+ const sortable = properties.sortable !== false;
35
+ const pagination = properties.pagination !== false;
36
+ return `<TableContainer component={Paper}>
37
+ <Table ${properties.size ? `size="${properties.size}"` : ""}>
38
+ <TableHead>
39
+ <TableRow>
40
+ ${columns.map(
41
+ (col) => sortable ? `<TableCell><TableSortLabel>{${JSON.stringify(col)}}</TableSortLabel></TableCell>` : `<TableCell>{${JSON.stringify(col)}}</TableCell>`
42
+ ).join("\n ")}
43
+ </TableRow>
44
+ </TableHead>
45
+ <TableBody>
46
+ {${modelVar}s?.map((${modelVar}) => (
47
+ <TableRow key={${modelVar}.id}>
48
+ ${columns.map((col) => `<TableCell>{${modelVar}.${col}}</TableCell>`).join("\n ")}
49
+ </TableRow>
50
+ ))}
51
+ </TableBody>
52
+ </Table>
53
+ ${pagination ? `<TablePagination rowsPerPageOptions={[5, 10, 25]} component="div" count={total} rowsPerPage={rowsPerPage} page={page} onPageChange={handlePageChange} onRowsPerPageChange={handleRowsPerPageChange} />` : ""}
54
+ </TableContainer>`;
55
+ }
56
+ },
57
+ list: {
58
+ imports: ["import { List, ListItem, ListItemText, ListItemIcon, ListItemButton, Divider } from '@mui/material'"],
59
+ render: (ctx) => {
60
+ const { properties, model } = ctx;
61
+ const modelVar = model?.name?.toLowerCase() || "item";
62
+ return `<List ${properties.dense ? "dense" : ""}>
63
+ {${modelVar}s?.map((${modelVar}) => (
64
+ <React.Fragment key={${modelVar}.id}>
65
+ <ListItem${properties.clickable ? "Button" : ""}>
66
+ ${properties.showIcon ? `<ListItemIcon>{/* Icon */}</ListItemIcon>` : ""}
67
+ <ListItemText
68
+ primary={${modelVar}.${properties.primaryField || "name"}}
69
+ ${properties.secondaryField ? `secondary={${modelVar}.${properties.secondaryField}}` : ""}
70
+ />
71
+ </ListItem>
72
+ ${properties.dividers ? "<Divider />" : ""}
73
+ </React.Fragment>
74
+ ))}
75
+ </List>`;
76
+ }
77
+ },
78
+ grid: {
79
+ imports: ["import { Grid } from '@mui/material'"],
80
+ render: (ctx) => {
81
+ const { properties, children } = ctx;
82
+ const spacing = properties.spacing || 2;
83
+ return `<Grid container spacing={${spacing}}>
84
+ {items?.map((item) => (
85
+ <Grid item xs={${properties.xs || 12}} sm={${properties.sm || 6}} md={${properties.md || 4}} lg={${properties.lg || 3}} key={item.id}>
86
+ ${children || "{/* Item content */}"}
87
+ </Grid>
88
+ ))}
89
+ </Grid>`;
90
+ }
91
+ },
92
+ card: {
93
+ imports: ["import { Card, CardContent, CardMedia, CardActions, CardHeader, Typography } from '@mui/material'"],
94
+ render: (ctx) => {
95
+ const { properties, children } = ctx;
96
+ return `<Card ${properties.variant ? `variant="${properties.variant}"` : ""}>
97
+ ${properties.image ? `<CardMedia component="img" height="${properties.imageHeight || 140}" image={${properties.image}} alt="${properties.title || "Card"}" />` : ""}
98
+ ${properties.title ? `<CardHeader title="${properties.title}" ${properties.subtitle ? `subheader="${properties.subtitle}"` : ""} />` : ""}
99
+ <CardContent>
100
+ ${children || '<Typography variant="body2" color="text.secondary">{content}</Typography>'}
101
+ </CardContent>
102
+ ${properties.actions ? `<CardActions>{/* Actions */}</CardActions>` : ""}
103
+ </Card>`;
104
+ }
105
+ },
106
+ chart: {
107
+ imports: [
108
+ "import { Box } from '@mui/material'",
109
+ "// Note: MUI doesn't include charts. Use @mui/x-charts or recharts",
110
+ "// import { LineChart, Line, BarChart, Bar, PieChart, Pie, XAxis, YAxis, CartesianGrid, Tooltip, Legend, ResponsiveContainer } from 'recharts'"
111
+ ],
112
+ render: (ctx) => {
113
+ const { properties } = ctx;
114
+ const chartType = properties.chartType || "line";
115
+ return `<Box sx={{ width: '100%', height: ${properties.height || 400} }}>
116
+ {/* TODO: Integrate @mui/x-charts or recharts */}
117
+ {/* <ResponsiveContainer width="100%" height="100%">
118
+ <${chartType === "line" ? "LineChart" : chartType === "bar" ? "BarChart" : "PieChart"} data={data}>
119
+ ${chartType !== "pie" ? '<CartesianGrid strokeDasharray="3 3" /><XAxis dataKey="name" /><YAxis />' : ""}
120
+ <Tooltip />${properties.showLegend !== false ? "<Legend />" : ""}
121
+ <${chartType === "line" ? "Line" : chartType === "bar" ? "Bar" : "Pie"} dataKey="value" fill="#8884d8" />
122
+ </${chartType === "line" ? "LineChart" : chartType === "bar" ? "BarChart" : "PieChart"}>
123
+ </ResponsiveContainer> */}
124
+ </Box>`;
125
+ },
126
+ dependencies: [
127
+ { name: "@mui/x-charts", version: "^6.0.0" }
128
+ ]
129
+ },
130
+ tree: {
131
+ imports: ["import { TreeView, TreeItem } from '@mui/lab'", "import { ExpandMore, ChevronRight } from '@mui/icons-material'"],
132
+ render: (ctx) => {
133
+ const { properties } = ctx;
134
+ return `<TreeView
135
+ defaultCollapseIcon={<ExpandMore />}
136
+ defaultExpandIcon={<ChevronRight />}
137
+ ${properties.defaultExpanded ? "defaultExpanded={defaultExpanded}" : ""}
138
+ >
139
+ {renderTree(data)}
140
+ </TreeView>`;
141
+ },
142
+ dependencies: [
143
+ { name: "@mui/lab", version: "^5.0.0-alpha.170" }
144
+ ]
145
+ },
146
+ timeline: {
147
+ imports: ["import { Timeline, TimelineItem, TimelineSeparator, TimelineConnector, TimelineContent, TimelineDot, TimelineOppositeContent } from '@mui/lab'"],
148
+ render: (ctx) => {
149
+ const { properties } = ctx;
150
+ const position = properties.position || "right";
151
+ return `<Timeline position="${position}">
152
+ {events?.map((event) => (
153
+ <TimelineItem key={event.id}>
154
+ ${properties.showDateMarkers ? `<TimelineOppositeContent color="text.secondary">{event.date}</TimelineOppositeContent>` : ""}
155
+ <TimelineSeparator>
156
+ <TimelineDot />
157
+ <TimelineConnector />
158
+ </TimelineSeparator>
159
+ <TimelineContent>{event.title}</TimelineContent>
160
+ </TimelineItem>
161
+ ))}
162
+ </Timeline>`;
163
+ },
164
+ dependencies: [
165
+ { name: "@mui/lab", version: "^5.0.0-alpha.170" }
166
+ ]
167
+ },
168
+ avatar: {
169
+ imports: ["import { Avatar, AvatarGroup } from '@mui/material'"],
170
+ render: (ctx) => {
171
+ const { properties } = ctx;
172
+ const size = properties.size === "small" ? "small" : properties.size === "large" ? "large" : "medium";
173
+ return `<Avatar
174
+ src={${properties.src || "undefined"}}
175
+ alt="${properties.alt || ""}"
176
+ ${properties.variant ? `variant="${properties.variant}"` : ""}
177
+ sx={{ width: ${properties.size === "small" ? 32 : properties.size === "large" ? 56 : 40}, height: ${properties.size === "small" ? 32 : properties.size === "large" ? 56 : 40} }}
178
+ >
179
+ ${!properties.src ? "{initials}" : ""}
180
+ </Avatar>`;
181
+ }
182
+ },
183
+ image: {
184
+ imports: ["import { Box, CardMedia } from '@mui/material'"],
185
+ render: (ctx) => {
186
+ const { properties } = ctx;
187
+ return `<CardMedia
188
+ component="img"
189
+ image={${properties.src}}
190
+ alt="${properties.alt || "Image"}"
191
+ ${properties.height ? `height={${properties.height}}` : ""}
192
+ sx={{ objectFit: '${properties.objectFit || "cover"}', ${properties.rounded ? "borderRadius: 1" : ""} }}
193
+ />`;
194
+ }
195
+ },
196
+ // ====================================================================
197
+ // FORMS & INPUTS (11 types)
198
+ // ====================================================================
199
+ form: {
200
+ imports: ["import { Box } from '@mui/material'"],
201
+ render: (ctx) => {
202
+ const { properties, children } = ctx;
203
+ return `<Box component="form" onSubmit={handleSubmit} noValidate sx={{ mt: 1 }}>
204
+ ${children || "{/* Form fields */}"}
205
+ </Box>`;
206
+ }
207
+ },
208
+ input: {
209
+ imports: ["import { TextField } from '@mui/material'"],
210
+ render: (ctx) => {
211
+ const { properties } = ctx;
212
+ const variant = properties.variant || "outlined";
213
+ return `<TextField
214
+ label="${properties.label || ""}"
215
+ type="${properties.type || "text"}"
216
+ placeholder="${properties.placeholder || ""}"
217
+ variant="${variant}"
218
+ fullWidth={${properties.fullWidth !== false}}
219
+ required={${properties.required === true}}
220
+ disabled={${properties.disabled === true}}
221
+ ${properties.helperText ? `helperText="${properties.helperText}"` : ""}
222
+ ${properties.error ? "error" : ""}
223
+ />`;
224
+ }
225
+ },
226
+ textarea: {
227
+ imports: ["import { TextField } from '@mui/material'"],
228
+ render: (ctx) => {
229
+ const { properties } = ctx;
230
+ return `<TextField
231
+ label="${properties.label || ""}"
232
+ placeholder="${properties.placeholder || ""}"
233
+ multiline
234
+ rows={${properties.rows || 4}}
235
+ variant="${properties.variant || "outlined"}"
236
+ fullWidth={${properties.fullWidth !== false}}
237
+ required={${properties.required === true}}
238
+ />`;
239
+ }
240
+ },
241
+ select: {
242
+ imports: ["import { FormControl, InputLabel, Select, MenuItem } from '@mui/material'"],
243
+ render: (ctx) => {
244
+ const { properties } = ctx;
245
+ return `<FormControl fullWidth variant="${properties.variant || "outlined"}">
246
+ <InputLabel>${properties.label || "Select"}</InputLabel>
247
+ <Select
248
+ value={value}
249
+ label="${properties.label || "Select"}"
250
+ onChange={handleChange}
251
+ ${properties.multiple ? "multiple" : ""}
252
+ >
253
+ {${properties.options || "options"}?.map((option) => (
254
+ <MenuItem key={option.value} value={option.value}>
255
+ {option.label}
256
+ </MenuItem>
257
+ ))}
258
+ </Select>
259
+ </FormControl>`;
260
+ }
261
+ },
262
+ checkbox: {
263
+ imports: ["import { FormControlLabel, Checkbox } from '@mui/material'"],
264
+ render: (ctx) => {
265
+ const { properties } = ctx;
266
+ return `<FormControlLabel
267
+ control={<Checkbox ${properties.checked ? "checked" : ""} ${properties.disabled ? "disabled" : ""} />}
268
+ label="${properties.label || ""}"
269
+ />`;
270
+ }
271
+ },
272
+ radio: {
273
+ imports: ["import { FormControl, FormLabel, RadioGroup, FormControlLabel, Radio } from '@mui/material'"],
274
+ render: (ctx) => {
275
+ const { properties } = ctx;
276
+ return `<FormControl>
277
+ <FormLabel>${properties.label || "Options"}</FormLabel>
278
+ <RadioGroup row={${properties.orientation === "horizontal"}}>
279
+ {${properties.options || "options"}?.map((option) => (
280
+ <FormControlLabel key={option.value} value={option.value} control={<Radio />} label={option.label} />
281
+ ))}
282
+ </RadioGroup>
283
+ </FormControl>`;
284
+ }
285
+ },
286
+ slider: {
287
+ imports: ["import { Slider, Box, Typography } from '@mui/material'"],
288
+ render: (ctx) => {
289
+ const { properties } = ctx;
290
+ return `<Box sx={{ width: '100%' }}>
291
+ ${properties.label ? `<Typography gutterBottom>${properties.label}</Typography>` : ""}
292
+ <Slider
293
+ value={value}
294
+ onChange={handleChange}
295
+ min={${properties.min || 0}}
296
+ max={${properties.max || 100}}
297
+ step={${properties.step || 1}}
298
+ ${properties.marks ? "marks" : ""}
299
+ valueLabelDisplay="${properties.showValue ? "on" : "auto"}"
300
+ />
301
+ </Box>`;
302
+ }
303
+ },
304
+ switch: {
305
+ imports: ["import { FormControlLabel, Switch } from '@mui/material'"],
306
+ render: (ctx) => {
307
+ const { properties } = ctx;
308
+ return `<FormControlLabel
309
+ control={<Switch ${properties.checked ? "checked" : ""} ${properties.disabled ? "disabled" : ""} />}
310
+ label="${properties.label || ""}"
311
+ />`;
312
+ }
313
+ },
314
+ autocomplete: {
315
+ imports: ["import { Autocomplete, TextField } from '@mui/material'"],
316
+ render: (ctx) => {
317
+ const { properties } = ctx;
318
+ return `<Autocomplete
319
+ options={${properties.options || "options"}}
320
+ ${properties.multiple ? "multiple" : ""}
321
+ ${properties.freeSolo ? "freeSolo" : ""}
322
+ renderInput={(params) => (
323
+ <TextField {...params} label="${properties.label || "Search"}" placeholder="${properties.placeholder || ""}" />
324
+ )}
325
+ />`;
326
+ }
327
+ },
328
+ datepicker: {
329
+ imports: [
330
+ "import { DatePicker } from '@mui/x-date-pickers/DatePicker'",
331
+ "import { LocalizationProvider } from '@mui/x-date-pickers/LocalizationProvider'",
332
+ "import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs'"
333
+ ],
334
+ render: (ctx) => {
335
+ const { properties } = ctx;
336
+ return `<LocalizationProvider dateAdapter={AdapterDayjs}>
337
+ <DatePicker
338
+ label="${properties.label || "Select Date"}"
339
+ value={value}
340
+ onChange={handleChange}
341
+ />
342
+ </LocalizationProvider>`;
343
+ },
344
+ dependencies: [
345
+ { name: "@mui/x-date-pickers", version: "^6.0.0" },
346
+ { name: "dayjs", version: "^1.11.0" }
347
+ ]
348
+ },
349
+ timepicker: {
350
+ imports: [
351
+ "import { TimePicker } from '@mui/x-date-pickers/TimePicker'",
352
+ "import { LocalizationProvider } from '@mui/x-date-pickers/LocalizationProvider'",
353
+ "import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs'"
354
+ ],
355
+ render: (ctx) => {
356
+ const { properties } = ctx;
357
+ return `<LocalizationProvider dateAdapter={AdapterDayjs}>
358
+ <TimePicker
359
+ label="${properties.label || "Select Time"}"
360
+ value={value}
361
+ onChange={handleChange}
362
+ />
363
+ </LocalizationProvider>`;
364
+ },
365
+ dependencies: [
366
+ { name: "@mui/x-date-pickers", version: "^6.0.0" },
367
+ { name: "dayjs", version: "^1.11.0" }
368
+ ]
369
+ },
370
+ // ====================================================================
371
+ // ACTIONS (5 types)
372
+ // ====================================================================
373
+ button: {
374
+ imports: ["import { Button } from '@mui/material'"],
375
+ render: (ctx) => {
376
+ const { properties } = ctx;
377
+ const variant = { primary: "contained", secondary: "outlined", danger: "contained" }[properties.variant || "primary"] || "contained";
378
+ const color = properties.variant === "danger" ? "error" : "primary";
379
+ return `<Button
380
+ variant="${variant}"
381
+ color="${color}"
382
+ size="${properties.size || "medium"}"
383
+ ${properties.disabled ? "disabled" : ""}
384
+ ${properties.fullWidth ? "fullWidth" : ""}
385
+ startIcon={${properties.icon ? `<${properties.icon} />` : "undefined"}}
386
+ >
387
+ ${properties.label || "Button"}
388
+ </Button>`;
389
+ }
390
+ },
391
+ "button-group": {
392
+ imports: ["import { ButtonGroup, Button } from '@mui/material'"],
393
+ render: (ctx) => {
394
+ const { properties, children } = ctx;
395
+ return `<ButtonGroup
396
+ variant="${properties.variant || "outlined"}"
397
+ orientation="${properties.orientation || "horizontal"}"
398
+ size="${properties.size || "medium"}"
399
+ >
400
+ ${children || "{/* Buttons */}"}
401
+ </ButtonGroup>`;
402
+ }
403
+ },
404
+ link: {
405
+ imports: ["import { Link } from '@mui/material'"],
406
+ render: (ctx) => {
407
+ const { properties } = ctx;
408
+ return `<Link
409
+ href="${properties.href || "#"}"
410
+ underline="${properties.underline || "hover"}"
411
+ ${properties.color ? `color="${properties.color}"` : ""}
412
+ ${properties.external ? 'target="_blank" rel="noopener noreferrer"' : ""}
413
+ >
414
+ ${properties.label || "Link"}
415
+ </Link>`;
416
+ }
417
+ },
418
+ icon: {
419
+ imports: ["import { Icon } from '@mui/material'", "// Import specific icons: import { Home, Settings } from '@mui/icons-material'"],
420
+ render: (ctx) => {
421
+ const { properties } = ctx;
422
+ const size = properties.size === "small" ? "small" : properties.size === "large" ? "large" : "medium";
423
+ return `<${properties.name || "Icon"} fontSize="${size}" ${properties.color ? `color="${properties.color}"` : ""} />`;
424
+ }
425
+ },
426
+ menu: {
427
+ imports: ["import { Menu, MenuItem, IconButton } from '@mui/material'", "import { MoreVert } from '@mui/icons-material'"],
428
+ render: (ctx) => {
429
+ const { properties } = ctx;
430
+ return `<>
431
+ <IconButton onClick={handleClick}>
432
+ <MoreVert />
433
+ </IconButton>
434
+ <Menu anchorEl={anchorEl} open={open} onClose={handleClose}>
435
+ {${properties.items || "menuItems"}?.map((item) => (
436
+ <MenuItem key={item.id} onClick={handleClose}>
437
+ {item.label}
438
+ </MenuItem>
439
+ ))}
440
+ </Menu>
441
+ </>`;
442
+ }
443
+ },
444
+ // ====================================================================
445
+ // OVERLAYS & FEEDBACK (9 types)
446
+ // ====================================================================
447
+ modal: {
448
+ imports: ["import { Modal, Box, Typography } from '@mui/material'"],
449
+ render: (ctx) => {
450
+ const { properties, children } = ctx;
451
+ return `<Modal
452
+ open={open}
453
+ onClose={handleClose}
454
+ aria-labelledby="modal-title"
455
+ >
456
+ <Box sx={{
457
+ position: 'absolute',
458
+ top: '50%',
459
+ left: '50%',
460
+ transform: 'translate(-50%, -50%)',
461
+ width: ${properties.width || 400},
462
+ bgcolor: 'background.paper',
463
+ boxShadow: 24,
464
+ p: 4
465
+ }}>
466
+ ${properties.title ? `<Typography id="modal-title" variant="h6" component="h2">${properties.title}</Typography>` : ""}
467
+ ${children || "{/* Content */}"}
468
+ </Box>
469
+ </Modal>`;
470
+ }
471
+ },
472
+ dialog: {
473
+ imports: ["import { Dialog, DialogTitle, DialogContent, DialogActions, Button } from '@mui/material'"],
474
+ render: (ctx) => {
475
+ const { properties, children } = ctx;
476
+ return `<Dialog open={open} onClose={handleClose} maxWidth="${properties.size || "sm"}" fullWidth>
477
+ ${properties.title ? `<DialogTitle>${properties.title}</DialogTitle>` : ""}
478
+ <DialogContent>
479
+ ${children || "{/* Content */}"}
480
+ </DialogContent>
481
+ <DialogActions>
482
+ <Button onClick={handleClose}>Cancel</Button>
483
+ <Button onClick={handleConfirm} variant="contained">Confirm</Button>
484
+ </DialogActions>
485
+ </Dialog>`;
486
+ }
487
+ },
488
+ drawer: {
489
+ imports: ["import { Drawer, Box } from '@mui/material'"],
490
+ render: (ctx) => {
491
+ const { properties, children } = ctx;
492
+ const anchor = properties.position === "left" ? "left" : properties.position === "right" ? "right" : properties.position === "top" ? "top" : "bottom";
493
+ return `<Drawer
494
+ anchor="${anchor}"
495
+ open={open}
496
+ onClose={handleClose}
497
+ ${properties.variant === "persistent" ? 'variant="persistent"' : ""}
498
+ >
499
+ <Box sx={{ width: ${properties.width || 250}, p: 2 }}>
500
+ ${children || "{/* Content */}"}
501
+ </Box>
502
+ </Drawer>`;
503
+ }
504
+ },
505
+ popover: {
506
+ imports: ["import { Popover, Typography } from '@mui/material'"],
507
+ render: (ctx) => {
508
+ const { properties, children } = ctx;
509
+ return `<Popover
510
+ open={open}
511
+ anchorEl={anchorEl}
512
+ onClose={handleClose}
513
+ anchorOrigin={{ vertical: 'bottom', horizontal: 'left' }}
514
+ >
515
+ <Typography sx={{ p: 2 }}>
516
+ ${children || properties.content || "Popover content"}
517
+ </Typography>
518
+ </Popover>`;
519
+ }
520
+ },
521
+ tooltip: {
522
+ imports: ["import { Tooltip } from '@mui/material'"],
523
+ render: (ctx) => {
524
+ const { properties, children } = ctx;
525
+ const placement = properties.placement || "top";
526
+ return `<Tooltip title="${properties.content || ""}" placement="${placement}" ${properties.arrow ? "arrow" : ""}>
527
+ ${children || "<span>{children}</span>"}
528
+ </Tooltip>`;
529
+ }
530
+ },
531
+ alert: {
532
+ imports: ["import { Alert, AlertTitle } from '@mui/material'"],
533
+ render: (ctx) => {
534
+ const { properties } = ctx;
535
+ const severity = properties.variant === "error" ? "error" : properties.variant === "warning" ? "warning" : properties.variant === "success" ? "success" : "info";
536
+ return `<Alert severity="${severity}" ${properties.closable ? "onClose={handleClose}" : ""}>
537
+ ${properties.title ? `<AlertTitle>${properties.title}</AlertTitle>` : ""}
538
+ ${properties.message || "Alert message"}
539
+ </Alert>`;
540
+ }
541
+ },
542
+ snackbar: {
543
+ imports: ["import { Snackbar, Alert } from '@mui/material'"],
544
+ render: (ctx) => {
545
+ const { properties } = ctx;
546
+ const vertical = properties.position?.includes("top") ? "top" : "bottom";
547
+ const horizontal = properties.position?.includes("left") ? "left" : properties.position?.includes("right") ? "right" : "center";
548
+ return `<Snackbar
549
+ open={open}
550
+ autoHideDuration={${properties.duration || 6e3}}
551
+ onClose={handleClose}
552
+ anchorOrigin={{ vertical: '${vertical}', horizontal: '${horizontal}' }}
553
+ >
554
+ <Alert onClose={handleClose} severity="${properties.variant || "info"}" sx={{ width: '100%' }}>
555
+ ${properties.message || "Notification"}
556
+ </Alert>
557
+ </Snackbar>`;
558
+ }
559
+ },
560
+ badge: {
561
+ imports: ["import { Badge } from '@mui/material'"],
562
+ render: (ctx) => {
563
+ const { properties, children } = ctx;
564
+ return `<Badge
565
+ badgeContent={${properties.count || 0}}
566
+ color="${properties.color || "primary"}"
567
+ ${properties.variant === "dot" ? 'variant="dot"' : ""}
568
+ ${properties.max ? `max={${properties.max}}` : ""}
569
+ >
570
+ ${children || "{children}"}
571
+ </Badge>`;
572
+ }
573
+ },
574
+ spinner: {
575
+ imports: ["import { CircularProgress, Box } from '@mui/material'"],
576
+ render: (ctx) => {
577
+ const { properties } = ctx;
578
+ const size = properties.size === "small" ? 20 : properties.size === "large" ? 60 : 40;
579
+ return `<Box sx={{ display: 'flex', justifyContent: 'center', alignItems: 'center' }}>
580
+ <CircularProgress size={${size}} ${properties.color ? `color="${properties.color}"` : ""} />
581
+ </Box>`;
582
+ }
583
+ },
584
+ // ====================================================================
585
+ // NAVIGATION (5 types)
586
+ // ====================================================================
587
+ tabs: {
588
+ imports: ["import { Tabs, Tab, Box } from '@mui/material'"],
589
+ render: (ctx) => {
590
+ const { properties } = ctx;
591
+ return `<Box sx={{ borderBottom: 1, borderColor: 'divider' }}>
592
+ <Tabs
593
+ value={value}
594
+ onChange={handleChange}
595
+ ${properties.variant === "scrollable" ? 'variant="scrollable" scrollButtons="auto"' : ""}
596
+ ${properties.centered ? "centered" : ""}
597
+ >
598
+ {${properties.tabs || "tabs"}?.map((tab) => (
599
+ <Tab key={tab.value} label={tab.label} value={tab.value} />
600
+ ))}
601
+ </Tabs>
602
+ </Box>`;
603
+ }
604
+ },
605
+ breadcrumb: {
606
+ imports: ["import { Breadcrumbs, Link, Typography } from '@mui/material'", "import { NavigateNext } from '@mui/icons-material'"],
607
+ render: (ctx) => {
608
+ const { properties } = ctx;
609
+ return `<Breadcrumbs separator={<NavigateNext fontSize="small" />}>
610
+ {${properties.items || "breadcrumbs"}?.map((item, index) =>
611
+ index === breadcrumbs.length - 1 ? (
612
+ <Typography key={item.label} color="text.primary">{item.label}</Typography>
613
+ ) : (
614
+ <Link key={item.label} underline="hover" color="inherit" href={item.href}>{item.label}</Link>
615
+ )
616
+ )}
617
+ </Breadcrumbs>`;
618
+ }
619
+ },
620
+ navbar: {
621
+ imports: ["import { AppBar, Toolbar, Typography, Button, IconButton } from '@mui/material'", "import { Menu as MenuIcon } from '@mui/icons-material'"],
622
+ render: (ctx) => {
623
+ const { properties, children } = ctx;
624
+ const position = properties.fixed ? "fixed" : "static";
625
+ return `<AppBar position="${position}" color="${properties.color || "primary"}">
626
+ <Toolbar>
627
+ ${properties.showMenuButton ? '<IconButton edge="start" color="inherit" onClick={handleMenuClick}><MenuIcon /></IconButton>' : ""}
628
+ <Typography variant="h6" component="div" sx={{ flexGrow: 1 }}>
629
+ ${properties.brand || "App"}
630
+ </Typography>
631
+ ${children || "{/* Navigation items */}"}
632
+ </Toolbar>
633
+ </AppBar>`;
634
+ }
635
+ },
636
+ sidebar: {
637
+ imports: ["import { Drawer, List, ListItem, ListItemIcon, ListItemText, ListItemButton } from '@mui/material'"],
638
+ render: (ctx) => {
639
+ const { properties } = ctx;
640
+ const variant = properties.variant === "permanent" ? "permanent" : properties.variant === "persistent" ? "persistent" : "temporary";
641
+ return `<Drawer
642
+ variant="${variant}"
643
+ anchor="${properties.position || "left"}"
644
+ open={open}
645
+ ${variant === "temporary" ? "onClose={handleClose}" : ""}
646
+ sx={{ width: ${properties.width || 240}, flexShrink: 0, '& .MuiDrawer-paper': { width: ${properties.width || 240}, boxSizing: 'border-box' } }}
647
+ >
648
+ <List>
649
+ {${properties.items || "menuItems"}?.map((item) => (
650
+ <ListItemButton key={item.id}>
651
+ {item.icon && <ListItemIcon>{item.icon}</ListItemIcon>}
652
+ <ListItemText primary={item.label} />
653
+ </ListItemButton>
654
+ ))}
655
+ </List>
656
+ </Drawer>`;
657
+ }
658
+ },
659
+ pagination: {
660
+ imports: ["import { Pagination, Stack } from '@mui/material'"],
661
+ render: (ctx) => {
662
+ const { properties } = ctx;
663
+ return `<Stack spacing={2} alignItems="center">
664
+ <Pagination
665
+ count={${properties.total || 10}}
666
+ page={page}
667
+ onChange={handleChange}
668
+ color="${properties.color || "primary"}"
669
+ size="${properties.size || "medium"}"
670
+ ${properties.showFirstLast ? "showFirstButton showLastButton" : ""}
671
+ />
672
+ </Stack>`;
673
+ }
674
+ },
675
+ // ====================================================================
676
+ // LAYOUT (6 types)
677
+ // ====================================================================
678
+ accordion: {
679
+ imports: ["import { Accordion, AccordionSummary, AccordionDetails, Typography } from '@mui/material'", "import { ExpandMore } from '@mui/icons-material'"],
680
+ render: (ctx) => {
681
+ const { properties } = ctx;
682
+ return `{${properties.items || "accordionItems"}?.map((item) => (
683
+ <Accordion key={item.id} ${properties.multiple ? "" : "disableGutters"}>
684
+ <AccordionSummary expandIcon={<ExpandMore />}>
685
+ <Typography>{item.title}</Typography>
686
+ </AccordionSummary>
687
+ <AccordionDetails>
688
+ <Typography>{item.content}</Typography>
689
+ </AccordionDetails>
690
+ </Accordion>
691
+ ))}`;
692
+ }
693
+ },
694
+ carousel: {
695
+ imports: ["import { Box } from '@mui/material'", "// Note: MUI doesn't include carousel. Use react-material-ui-carousel or swiper"],
696
+ render: (ctx) => {
697
+ const { properties } = ctx;
698
+ return `<Box sx={{ maxWidth: '100%', flexGrow: 1 }}>
699
+ {/* TODO: Integrate react-material-ui-carousel or swiper */}
700
+ {/* <Carousel autoPlay={${properties.autoplay !== false}} interval={${properties.interval || 3e3}}>
701
+ {items?.map((item) => (
702
+ <Box key={item.id}>{item.content}</Box>
703
+ ))}
704
+ </Carousel> */}
705
+ </Box>`;
706
+ },
707
+ dependencies: [
708
+ { name: "react-material-ui-carousel", version: "^3.4.0" }
709
+ ]
710
+ },
711
+ container: {
712
+ imports: ["import { Container } from '@mui/material'"],
713
+ render: (ctx) => {
714
+ const { properties, children } = ctx;
715
+ return `<Container maxWidth="${properties.maxWidth || "lg"}" ${properties.fixed ? "fixed" : ""}>
716
+ ${children || "{/* Content */}"}
717
+ </Container>`;
718
+ }
719
+ },
720
+ divider: {
721
+ imports: ["import { Divider } from '@mui/material'"],
722
+ render: (ctx) => {
723
+ const { properties } = ctx;
724
+ return `<Divider ${properties.orientation === "vertical" ? 'orientation="vertical"' : ""} ${properties.variant ? `variant="${properties.variant}"` : ""} />`;
725
+ }
726
+ },
727
+ header: {
728
+ imports: ["import { Box, Typography } from '@mui/material'"],
729
+ render: (ctx) => {
730
+ const { properties, children } = ctx;
731
+ return `<Box component="header" sx={{ py: 2, borderBottom: 1, borderColor: 'divider' }}>
732
+ ${properties.title ? `<Typography variant="h4" component="h1">${properties.title}</Typography>` : ""}
733
+ ${properties.subtitle ? `<Typography variant="subtitle1" color="text.secondary">${properties.subtitle}</Typography>` : ""}
734
+ ${children || ""}
735
+ </Box>`;
736
+ }
737
+ },
738
+ footer: {
739
+ imports: ["import { Box, Container, Typography } from '@mui/material'"],
740
+ render: (ctx) => {
741
+ const { properties, children } = ctx;
742
+ return `<Box component="footer" sx={{ py: 3, px: 2, mt: 'auto', backgroundColor: 'background.paper', borderTop: 1, borderColor: 'divider' }}>
743
+ <Container maxWidth="lg">
744
+ ${properties.copyright ? `<Typography variant="body2" color="text.secondary" align="center">${properties.copyright}</Typography>` : ""}
745
+ ${children || ""}
746
+ </Container>
747
+ </Box>`;
748
+ }
749
+ },
750
+ // ====================================================================
751
+ // PROGRESS (2 types)
752
+ // ====================================================================
753
+ "progress-bar": {
754
+ imports: ["import { LinearProgress, Box, Typography } from '@mui/material'"],
755
+ render: (ctx) => {
756
+ const { properties } = ctx;
757
+ return `<Box sx={{ width: '100%' }}>
758
+ ${properties.label ? `<Typography variant="body2" color="text.secondary">${properties.label}</Typography>` : ""}
759
+ <LinearProgress
760
+ variant="${properties.indeterminate ? "indeterminate" : "determinate"}"
761
+ value={${properties.value || 0}}
762
+ color="${properties.color || "primary"}"
763
+ />
764
+ ${properties.showValue ? `<Typography variant="body2" color="text.secondary">{value}%</Typography>` : ""}
765
+ </Box>`;
766
+ }
767
+ },
768
+ "progress-circle": {
769
+ imports: ["import { CircularProgress, Box, Typography } from '@mui/material'"],
770
+ render: (ctx) => {
771
+ const { properties } = ctx;
772
+ return `<Box sx={{ position: 'relative', display: 'inline-flex' }}>
773
+ <CircularProgress
774
+ variant="${properties.indeterminate ? "indeterminate" : "determinate"}"
775
+ value={${properties.value || 0}}
776
+ size={${properties.size || 40}}
777
+ color="${properties.color || "primary"}"
778
+ />
779
+ ${properties.showValue ? `
780
+ <Box sx={{ top: 0, left: 0, bottom: 0, right: 0, position: 'absolute', display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
781
+ <Typography variant="caption" component="div" color="text.secondary">{value}%</Typography>
782
+ </Box>` : ""}
783
+ </Box>`;
784
+ }
785
+ },
786
+ // ====================================================================
787
+ // SPECIALIZED (2 types)
788
+ // ====================================================================
789
+ searchBar: {
790
+ imports: ["import { TextField, InputAdornment } from '@mui/material'", "import { Search } from '@mui/icons-material'"],
791
+ render: (ctx) => {
792
+ const { properties } = ctx;
793
+ return `<TextField
794
+ placeholder="${properties.placeholder || "Search..."}"
795
+ variant="${properties.variant || "outlined"}"
796
+ fullWidth={${properties.fullWidth !== false}}
797
+ InputProps={{
798
+ startAdornment: (
799
+ <InputAdornment position="start">
800
+ <Search />
801
+ </InputAdornment>
802
+ ),
803
+ }}
804
+ />`;
805
+ }
806
+ },
807
+ filterPanel: {
808
+ imports: ["import { Paper, Box, Typography, Divider } from '@mui/material'"],
809
+ render: (ctx) => {
810
+ const { properties, children } = ctx;
811
+ return `<Paper sx={{ p: 2, mb: 2 }}>
812
+ <Typography variant="h6" gutterBottom>Filters</Typography>
813
+ <Divider sx={{ mb: 2 }} />
814
+ <Box sx={{ display: 'flex', flexDirection: 'column', gap: 2 }}>
815
+ ${children || "{/* Filter controls */}"}
816
+ </Box>
817
+ </Paper>`;
818
+ }
819
+ }
820
+ }
821
+ };
822
+ export {
823
+ muiAdapter
824
+ };