@mui/x-codemod 8.27.0 → 9.0.0-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,9 +1,379 @@
1
1
  # Changelog
2
2
 
3
- > For full v8 changelog, please refer to the [v.8x branch](https://github.com/mui/mui-x/blob/v8.x/CHANGELOG.md).
3
+ ## 9.0.0-alpha.1
4
4
 
5
- All notable changes to this project will be documented in this file.
6
- See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
+ _Feb 26, 2026_
6
+
7
+ We'd like to extend a big thank you to the 18 contributors who made this release possible. Here are some highlights ✨:
8
+
9
+ - ⚡️ Improved dynamic data support and cache invalidation in lazy loading for Data Grid Pro
10
+ - ⌨️ Keyboard support for selecting day, month, and year in Date Pickers
11
+ - 📊 Axis tooltip sorting and control improvements in Charts
12
+ - 🐞 Bugfixes and internal improvements
13
+
14
+ Special thanks go out to these community members for their valuable contributions:
15
+ @EllGree, @lion1963
16
+
17
+ The following team members contributed to this release:
18
+ @alexfauquette, @arminmeh, @brijeshb42, @cherniavskii, @dav-is, @flaviendelangle, @Janpot, @JCQuintas, @mapache-salvaje, @MBilalShafi, @michelengelen, @noraleonte, @rita-codes, @sai6855, @siriwatknp, @ZeeshanTamboli
19
+
20
+ ### Data Grid
21
+
22
+ #### `@mui/x-data-grid@9.0.0-alpha.1`
23
+
24
+ - [DataGrid] Forward rest props in `GridFilterInputMultipleValue` (#21407) @siriwatknp
25
+ - [DataGrid] Preserve key input during row edit when using `rowModesModel` (#20759) @michelengelen
26
+ - [DataGrid] Remove double rtl inversion logic for columns pinning (#21371) @siriwatknp
27
+
28
+ #### `@mui/x-data-grid-pro@9.0.0-alpha.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
29
+
30
+ Same changes as in `@mui/x-data-grid@9.0.0-alpha.1`, plus:
31
+
32
+ - [DataGridPro] Fix number input visibility in header filters (#21328) @michelengelen
33
+ - [DataGridPro] Improve dynamic data support and cache invalidation in lazy loading (#21282) @MBilalShafi
34
+
35
+ #### `@mui/x-data-grid-premium@9.0.0-alpha.1` [![premium](https://mui.com/r/x-premium-svg)](https://mui.com/r/x-premium-svg-link 'Premium plan')
36
+
37
+ Same changes as in `@mui/x-data-grid-pro@9.0.0-alpha.1`.
38
+
39
+ ### Date and Time Pickers
40
+
41
+ #### `@mui/x-date-pickers@9.0.0-alpha.1`
42
+
43
+ - [DatePicker] Add keyboard support for selecting day, month, and year (#20859) @michelengelen
44
+
45
+ #### `@mui/x-date-pickers-pro@9.0.0-alpha.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
46
+
47
+ Same changes as in `@mui/x-date-pickers@9.0.0-alpha.1`, plus:
48
+
49
+ - [DateRangePicker] Fix timezone update issue leading to `invalidRange` error (#20863) @michelengelen
50
+
51
+ ### Charts
52
+
53
+ #### `@mui/x-charts@9.0.0-alpha.1`
54
+
55
+ - [charts] Add `sort` props to the axis tooltip (#21293) @alexfauquette
56
+ - [charts] Controll axis tooltip (#21351) @alexfauquette
57
+ - [charts] De duplicate keyboard focus handler function (#21267) @sai6855
58
+ - [charts] Make `type` optional in identifiers (#21311) @alexfauquette
59
+ - [charts] Move ref to the root component (#21396) @alexfauquette
60
+ - [charts] Refactor loading and no data overlays to use a shared OverlayText component (#21414) @sai6855
61
+ - [charts] Require series ids to be unique (#21330) @alexfauquette
62
+ - [charts] Set `showMark` as `false` by default (#21373) @alexfauquette
63
+ - [charts] Use `createGetNextIndexFocusedItem()` util in Funnel and RangeBar charts (#21390) @sai6855
64
+ - [charts] Remove unnecessary string concatenation (#21418) @sai6855
65
+
66
+ #### `@mui/x-charts-pro@9.0.0-alpha.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
67
+
68
+ Same changes as in `@mui/x-charts@9.0.0-alpha.1`.
69
+
70
+ #### `@mui/x-charts-premium@9.0.0-alpha.1` [![premium](https://mui.com/r/x-premium-svg)](https://mui.com/r/x-premium-svg-link 'Premium plan')
71
+
72
+ Same changes as in `@mui/x-charts-pro@9.0.0-alpha.1`.
73
+
74
+ ### Tree View
75
+
76
+ #### `@mui/x-tree-view@9.0.0-alpha.1`
77
+
78
+ - [tree view] Focus item sibling on unmount instead of the 1st item (#21254) @flaviendelangle
79
+
80
+ #### `@mui/x-tree-view-pro@9.0.0-alpha.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
81
+
82
+ Same changes as in `@mui/x-tree-view@9.0.0-alpha.1`.
83
+
84
+ ### Codemod
85
+
86
+ #### `@mui/x-codemod@9.0.0-alpha.1`
87
+
88
+ Internal changes.
89
+
90
+ ### Docs
91
+
92
+ - [docs] Fix external 301s (#21377) @Janpot
93
+ - [docs] Show premium in the overview (#21343) @alexfauquette
94
+ - [docs][charts] Revise the useLegend hook doc (#21352) @mapache-salvaje
95
+ - [docs][charts] Revise the axis hooks doc (#21317) @mapache-salvaje
96
+ - [docs][charts] Revise the scale hooks doc (#21316) @mapache-salvaje
97
+ - [docs][charts] Revise the series hooks doc (#21353) @mapache-salvaje
98
+ - [docs][charts] Revise the useDataset doc (#21336) @mapache-salvaje
99
+ - [docs][charts] Revise the useDrawingArea doc (#21333) @mapache-salvaje
100
+
101
+ ### Core
102
+
103
+ - [core] Update docs deploy script to the `docs-next` branch (#21341) @siriwatknp
104
+ - [code-infra] Cleanup unused babel plugins (#21453) @brijeshb42
105
+ - [code-infra] Do not append `x` to the last version for the compare API (#21408) @arminmeh
106
+ - [code-infra] Upgrade react-docgen to v8 X (#21155) @JCQuintas
107
+ - [code-infra] Modernize codemod (#21096) @JCQuintas
108
+ - [docs-infra] Fix current version detection logic (#21417) @cherniavskii
109
+ - [docs-infra] Reapply Cookie Banner (#21281) @dav-is
110
+ - [internal] Headless filtering plugin (#21302) @arminmeh
111
+ - [internal] Headless pagination plugin (#21183) @arminmeh
112
+ - [internal] Headless virtualization followups (#21327) @cherniavskii
113
+ - [internal] Keep cached data for disabled pipe processors (#21348) @arminmeh
114
+ - [internal] Remove autoprefixer package (#21440) @ZeeshanTamboli
115
+
116
+ ### Miscellaneous
117
+
118
+ - [l10n] Fix Czech (csCZ) locale: sort/filter labels are swapped (#21400) @EllGree
119
+ - [l10n] Improve Ukrainian (uk-UA) locale (#21366) @lion1963
120
+
121
+ ## 9.0.0-alpha.0
122
+
123
+ _Feb 16, 2026_
124
+
125
+ We'd like to extend a big thank you to the 21 contributors who made this release possible. Here are some highlights ✨:
126
+
127
+ - Add support for virtualized items on `<RichTreeViewPro />`:
128
+
129
+ ```tsx
130
+ <RichTreeViewPro items={ITEMS} virtualization itemHeight={48} />
131
+ ```
132
+
133
+ - Add Thai (`thTH`) locale on the Data Grid and the Date and Time Pickers (#21116) @siriwatknp
134
+ - Add a new `AdapterDayjsBuddhist` adapter for Date and Time Pickers (#20984) @siriwatknp
135
+ - Add support for virtualization in the rich tree view (#20780) @flaviendelangle
136
+ - Add WebGL renderer to Heatmap (#20756) @bernardobelchior
137
+
138
+ Special thanks go out to these community members for their valuable contributions:
139
+ @jhe-iqbis
140
+
141
+ The following team members contributed to this release:
142
+ @alexfauquette, @arminmeh, @bernardobelchior, @brijeshb42, @cherniavskii, @dav-is, @flaviendelangle, @Janpot, @JCQuintas, @mapache-salvaje, @MBilalShafi, @michelengelen, @mj12albert, @noraleonte, @oliviertassinari, @rita-codes, @romgrk, @sai6855, @siriwatknp
143
+
144
+ ### Data Grid
145
+
146
+ #### `@mui/x-data-grid@9.0.0-alpha.0`
147
+
148
+ - [DataGrid] Update default `logicOperator` behavior in filtering docs (#21098) @michelengelen
149
+ - [DataGrid] Add `thTH` locale (#21116) @siriwatknp
150
+ - [DataGrid] Fix initial filter value state in CustomMultiValueOperator demo (#21217) @sai6855
151
+
152
+ #### `@mui/x-data-grid-pro@9.0.0-alpha.0` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
153
+
154
+ Same changes as in `@mui/x-data-grid@9.0.0-alpha.0`, plus:
155
+
156
+ - [DataGridPro] Cleanup outdated rows on `dataSource` reference update (#21138) @MBilalShafi
157
+
158
+ #### `@mui/x-data-grid-premium@9.0.0-alpha.0` [![premium](https://mui.com/r/x-premium-svg)](https://mui.com/r/x-premium-svg-link 'Premium plan')
159
+
160
+ Same changes as in `@mui/x-data-grid-pro@9.0.0-alpha.0`.
161
+
162
+ ### Date and Time Pickers
163
+
164
+ #### `@mui/x-date-pickers@9.0.0-alpha.0`
165
+
166
+ - [pickers] Add `AdapterDayjsBuddhist` adapter (#20984) @siriwatknp
167
+ - [pickers] Add `thTH` locale (#21116) @siriwatknp
168
+
169
+ #### `@mui/x-date-pickers-pro@9.0.0-alpha.0` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
170
+
171
+ Same changes as in `@mui/x-date-pickers@9.0.0-alpha.0`.
172
+
173
+ ### Charts
174
+
175
+ #### `@mui/x-charts@9.0.0-alpha.0`
176
+
177
+ - [charts] Add Legend actions (#20404) @JCQuintas
178
+ - [charts] Add `Chart` suffix to MUI Classes (#21042) @JCQuintas
179
+ - [charts] Add `axesGap` props to put space between axes (#20904) @alexfauquette
180
+ - [charts] Add `cleanIdentifier` function to charts series instance (#20832) @JCQuintas
181
+ - [charts] Add `initialHiddenItems` prop to set initial state (#20894) @JCQuintas
182
+ - [charts] Add `useXAxisCoordinates` and `useYAxisCoordinates` hooks (#20972) @bernardobelchior
183
+ - [charts] Add axis slots and expose axis ticks hooks (#20935) @bernardobelchior
184
+ - [charts] Change `line` legend marker to be a line (#21059) @JCQuintas
185
+ - [charts] Codemod test pattern with function (#21111) @JCQuintas
186
+ - [charts] Control the item tooltip (#20617) @alexfauquette
187
+ - [charts] Enable keyboard navigation in radar chart (#20765) @alexfauquette
188
+ - [charts] Export `CartesianChartSeriesType` and `StackableChartSeriesType` (#21012) @bernardobelchior
189
+ - [charts] Export plugins from premium (#20866) @JCQuintas
190
+ - [charts] Filter hidden series from axis tooltip (#21273) @Copilot
191
+ - [charts] Filter hidden series from axis tooltip (#21273) @Copilot
192
+ - [charts] Fix rename `getSVGPoint` to `getChartPoint` (#21335) @bernardobelchior
193
+ - [charts] Fix cleanup function in useChartInteractionListener to correctly remove event listeners with options (#21218) @sai6855
194
+ - [charts] Fix import rename in codemod (#21112) @JCQuintas
195
+ - [charts] Fix multiple exports of `HighlightScope` (#21270) @bernardobelchior
196
+ - [charts] Fix test inconsistency in charts (#20907) @JCQuintas
197
+ - [charts] Fix tooltip position for stacked line series (#20901) @alexfauquette
198
+ - [charts] Make Highlight scope a generic (#21189) @alexfauquette
199
+ - [charts] Make `LegendItemParams.type` required (#21003) @alexfauquette
200
+ - [charts] Make `seriesId` a string only (#20997) @alexfauquette
201
+ - [charts] Make the `useChartRootRef` support typing parameter (#21023) @alexfauquette
202
+ - [charts] Memoize HeatmapItem to avoid re-render when fading/highlighting (#20865) @bernardobelchior
203
+ - [charts] Move axis id to `data-axis-id` attribute instead of class (#21037) @JCQuintas
204
+ - [charts] Move `cleanIdentifier` and `serializeIdentifier` instance methods to `useChartSeriesConfig` plugin (#21025) @JCQuintas
205
+ - [charts] Move `seriesConfig` to `useChartSeriesConfig` plugin (#21004) @JCQuintas
206
+ - [charts] Move element refs to `useChartElementRef` plugin (#21099) @JCQuintas
207
+ - [charts] Move types related to `seriesConfig` into the `useChartSeriesConfig` plugin folder (#21026) @JCQuintas
208
+ - [charts] Remove `data-has-focused-item` from `ChartsSurface` (#21255) @bernardobelchior
209
+ - [charts] Remove default generic of item identifiers (#21182) @alexfauquette
210
+ - [charts] Remove deprecated `id` from `LegendItemParams` (#21055) @alexfauquette
211
+ - [charts] Remove deprecated `ChartApi` export from `ChartContainer` (#20975) @JCQuintas
212
+ - [charts] Remove deprecated `useAxisTooltip` in favor of `useAxesTooltip` (#20962) @Copilot
213
+ - [charts] Remove deprecated series type helpers and functions (#20998) @alexfauquette
214
+ - [charts] Rename `ChartContainer` to `ChartsContainer` (#21173) @JCQuintas
215
+ - [charts] Rename `getSVGPoint` to `getChartPoint` (#21322) @bernardobelchior
216
+ - [charts] Rename `TickItemType` to `TickItem` (#21008) @bernardobelchior
217
+ - [charts] Replace props `id` by `seriesId` when necessary (#21057) @alexfauquette
218
+ - [charts] Revert `touch-action: pan-y` removal when zoom is disabled (#20852) @bernardobelchior
219
+ - [charts] The `useXxxSeries([])` return empty array (#21001) @alexfauquette
220
+ - [charts] Use `NumberValue` in domain limit function (#21054) @JCQuintas
221
+
222
+ #### `@mui/x-charts-pro@9.0.0-alpha.0` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
223
+
224
+ Same changes as in `@mui/x-charts@9.0.0-alpha.0`, plus:
225
+
226
+ - [charts-pro] Add border radius to heatmap (#20931) @bernardobelchior
227
+ - [charts-pro] Add keyboard navigation to funnel (#20766) @alexfauquette
228
+ - [charts-pro] Add keyboard navigation to heatmap (#20786) @alexfauquette
229
+ - [charts-pro] Add keyboard navigation to sankey (#20777) @alexfauquette
230
+ - [charts-pro] Fix Heatmap's `onItemClick` not triggering (#21016) @bernardobelchior
231
+ - [charts-pro] Fix crash when two same-direction axes have a zoom preview (#20916) @bernardobelchior
232
+ - [charts-pro] Handle edge case in export image (#21190) @bernardobelchior
233
+ - [charts-pro] Prefer global pointer interaction tracker in Heatmap (#20697) @bernardobelchior
234
+ - [charts-pro] Support composition for Sankey (#20604) @alexfauquette
235
+ - [charts-pro] Update Heatmap identifier (#21124) @alexfauquette
236
+ - [charts-pro] Update default value of `hideLegend` prop in `Heatmap` (#20961) @Copilot
237
+
238
+ #### `@mui/x-charts-premium@9.0.0-alpha.0` [![premium](https://mui.com/r/x-premium-svg)](https://mui.com/r/x-premium-svg-link 'Premium plan')
239
+
240
+ Same changes as in `@mui/x-charts-pro@9.0.0-alpha.0`, plus:
241
+
242
+ - [charts-premium] Add WebGL renderer to Heatmap (#20756) @bernardobelchior
243
+ - [charts-premium] Add `ChartContainerPremium` (#20910) @bernardobelchior
244
+ - [charts-premium] Add `HeatmapPremium` (#20930) @bernardobelchior
245
+ - [charts-premium] Add keyboard navigation to range-bar (#21272) @alexfauquette
246
+ - [charts-premium] Extract `HeatmapSVGPlot` from `HeatmapPlot` component (#21015) @bernardobelchior
247
+ - [charts-premium] Fix `ChartDataProviderPremium` tests (#20868) @bernardobelchior
248
+ - [charts-premium] Fix links in comments for chart containers and data providers (#21105) @bernardobelchior
249
+
250
+ ### Tree View
251
+
252
+ #### `@mui/x-tree-view@9.0.0-alpha.0`
253
+
254
+ _No changes._
255
+
256
+ #### `@mui/x-tree-view-pro@9.0.0-alpha.0` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
257
+
258
+ Same changes as in `@mui/x-tree-view@9.0.0-alpha.0`, plus:
259
+
260
+ - [RichTreeViewPro] Add support for virtualization (#20780) @flaviendelangle
261
+
262
+ ### Codemod
263
+
264
+ #### `@mui/x-codemod@9.0.0-alpha.0`
265
+
266
+ - [codemod] Document and Clean the codemod utils (#21014) @alexfauquette
267
+
268
+ ### Docs
269
+
270
+ - [docs] Add focus highlight in composition snipets (#20614) @alexfauquette
271
+ - [docs] Add simple candlestick chart demo (#20912) @bernardobelchior
272
+ - [docs] Fix Waterfall Chart documentation badge from Pro to Premium (#20888) @Copilot
273
+ - [docs] Fix broken links on Data Grid Editing sub-pages (#20911) @arminmeh
274
+ - [docs] Fix docs API for HeatmapPremium (#21137) @alexfauquette
275
+ - [docs] Fix horizontal overflow in heatmap docs (#20968) @bernardobelchior
276
+ - [docs] Move Range Bar Chart to existing charts (#21120) @bernardobelchior
277
+ - [docs] Prepare the scheduler doc for the alpha (#21268) @flaviendelangle
278
+ - [docs] Rewording of the heatmap item click (#20987) @alexfauquette
279
+ - [scheduler][docs] Create the Quickstart page (#20913) @flaviendelangle
280
+ - [charts][docs] Revise the Charts CSP doc (#20906) @mapache-salvaje
281
+ - [charts][docs] Revise the Charts Composition doc (#20032) @mapache-salvaje
282
+ - [charts][docs] Revise the Charts Hooks Overview doc (#20921) @mapache-salvaje
283
+ - [charts][docs] Revise the Charts Legend doc (#20821) @mapache-salvaje
284
+ - [charts][docs] Revise the Charts Localization doc (#20800) @mapache-salvaje
285
+ - [charts][docs] Revise the Charts Plugins doc (#20933) @mapache-salvaje
286
+ - [charts][docs] Revise the Charts Stacking doc (#20830) @mapache-salvaje
287
+ - [charts][docs] Revise the Charts Styling doc (#20835) @mapache-salvaje
288
+ - [charts][docs] Revise the Charts Toolbar doc (#20867) @mapache-salvaje
289
+ - [charts][docs] Revise the Charts Tooltip doc (#20869) @mapache-salvaje
290
+ - [charts][docs] Revise the Charts Zoom and Pan doc (#20893) @mapache-salvaje
291
+ - [DataGrid][docs] Add a recipe for handling long text cell (#20754) @siriwatknp
292
+ - [DataGrid][docs] Add high-level competitor comparison to Overview doc (DX-117) (#20870) @mapache-salvaje
293
+ - [DataGrid][docs] Remove Bundling section from quickstart (#21177) @MBilalShafi
294
+
295
+ ### Core
296
+
297
+ - [code-infra] Add `MUI_TEST_ENV` global (#21187) @Janpot
298
+ - [code-infra] Fix `material-ui/disallow-react-api-in-server-components` (#20909) @JCQuintas
299
+ - [code-infra] Fix `renameImports` codemod not preserving comments (#20977) @JCQuintas
300
+ - [code-infra] Fix the label comparison to use lower case (#20934) @brijeshb42
301
+ - [code-infra] Github action to sync title and label (#20922) @brijeshb42
302
+ - [code-infra] Ignore scheduler demo with random data (#20982) @JCQuintas
303
+ - [code-infra] Improve `codemod` testing setup (#20981) @JCQuintas
304
+ - [code-infra] Only ignore renovate[bot] in changelog generation script (#21185) @bernardobelchior
305
+ - [code-infra] Prepare for v9 (#20860) @JCQuintas
306
+ - [code-infra] Set `rasterizehtml` version in pnpm catalog (#21175) @bernardobelchior
307
+ - [code-infra] Update codeowners (#20886) @JCQuintas
308
+ - [code-infra] V9 preparation (#20928) @JCQuintas
309
+ - [code-infra] eslint rule rename (#21172) @Janpot
310
+ - [code-infra][docs] V9 charts migration doc kickoff (#20973) @JCQuintas
311
+ - [docs-infra] Add Cookie Banner and Analytics Provider (#21228) @dav-is
312
+ - [docs-infra] Fix missing slots section on API page (#20915) @Janpot
313
+ - [docs-infra] Fix two broken links (#20914) @Janpot
314
+ - [docs-infra] Port demo changes (#20971) @Janpot
315
+ - [internal] Add information about codemods to AGENTS.md (#21011) @bernardobelchior
316
+ - [internal] Fix codemod versioning instructions in `AGENTS.md` (#21024) @bernardobelchior
317
+ - [internal] Fix missing generated props in master (#21142) @bernardobelchior
318
+ - [internal] Headless sorting plugin (#21089) @arminmeh
319
+ - [internal] Remove duplicate code (#20896) @oliviertassinari
320
+
321
+ ### Miscellaneous
322
+
323
+ - Bump next to ^15.5.11 (#21171) @Copilot
324
+ - [core] Fix CI (#21223) @flaviendelangle
325
+ - [PoC] Headless data grid (#20645) @cherniavskii
326
+
327
+ ## v8.27.1
328
+
329
+ _Feb 13, 2026_
330
+
331
+ We'd like to extend a big thank you to the 6 contributors who made this release possible. Here are some highlights ✨:
332
+
333
+ - 📝 CSS bundler support is no longer needed for the Data Grid
334
+ - 🐞 Bugfixes
335
+
336
+ Special thanks go out to these community members for their valuable contributions:
337
+ @sai6855
338
+
339
+ The following team members contributed to this release:
340
+ @arminmeh, @cherniavskii, @flaviendelangle, @mj12albert, @MBilalShafi
341
+
342
+ ### Data Grid
343
+
344
+ #### `@mui/x-data-grid@8.27.1`
345
+
346
+ - [DataGrid] Hide column menu icon when there are no items (#21303) @MBilalShafi
347
+ - [DataGrid] Migrate styled imports and remove `index.css` (#21176) @MBilalShafi
348
+ - [DataGrid] Optimize `GridRootStyles` overrides resolver (#21251) @sai6855
349
+
350
+ #### `@mui/x-data-grid-pro@8.27.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
351
+
352
+ Same changes as in `@mui/x-data-grid@8.27.1`, plus:
353
+
354
+ - [DataGridPro] Fix column pinning issue with `restoreState` (#21305) @MBilalShafi
355
+ - [DataGridPro] Fix lazy loading params for page with one row (#21238) @MBilalShafi
356
+ - [DataGridPro] Properly extract parent path (#21301) @arminmeh
357
+
358
+ #### `@mui/x-data-grid-premium@8.27.1` [![premium](https://mui.com/r/x-premium-svg)](https://mui.com/r/x-premium-svg-link 'Premium plan')
359
+
360
+ Same changes as in `@mui/x-data-grid-pro@8.27.1`, plus:
361
+
362
+ - [DataGridPremium] Fix aggregation display when `initialState` has both `sortModel` and `pinnedColumns` (#21152) @mj12albert
363
+
364
+ ### Tree View
365
+
366
+ #### `@mui/x-tree-view@8.27.1`
367
+
368
+ - [tree view] Fix `apiRef.current.setItemExpansion()` (#21095) @flaviendelangle
369
+
370
+ #### `@mui/x-tree-view-pro@8.27.1` [![pro](https://mui.com/r/x-pro-svg)](https://mui.com/r/x-pro-svg-link 'Pro plan')
371
+
372
+ Same changes as in `@mui/x-tree-view@8.27.1`.
373
+
374
+ ### Core
375
+
376
+ - [internal] Add CLI for translation using LLM (#21299) @cherniavskii
7
377
 
8
378
  ## v8.27.0
9
379
 
package/README.md CHANGED
@@ -57,6 +57,126 @@ through jscodeshift's `printOptions` command line argument
57
57
  npx @mui/x-codemod <transform> <path> --jscodeshift="--printOptions='{\"quote\":\"double\"}'"
58
58
  ```
59
59
 
60
+ ## v9.0.0
61
+
62
+ ### 🚀 `preset-safe` for v9.0.0
63
+
64
+ A combination of all important transformers for migrating v8 to v9.
65
+ ⚠️ This codemod should be run only once.
66
+ It runs codemods for all MUI X packages.
67
+ To run codemods for a specific package, refer to the respective section.
68
+
69
+ <!-- #npm-tag-reference -->
70
+
71
+ ```bash
72
+ npx @mui/x-codemod@next v9.0.0/preset-safe <path|folder>
73
+ ```
74
+
75
+ The corresponding sub-sections are listed below
76
+
77
+ <!-- - [`preset-safe-for-tree-view`](#preset-safe-for-tree-view-v900) -->
78
+ <!-- - [`preset-safe-for-data-grid`](#preset-safe-for-data-grid-v900) -->
79
+ <!-- - [`preset-safe-for-pickers`](#preset-safe-for-pickers-v900) -->
80
+
81
+ - [`preset-safe-for-charts`](#preset-safe-for-charts-v900)
82
+
83
+ ### Charts codemods
84
+
85
+ #### 🚀 `preset-safe` for Charts v9.0.0
86
+
87
+ The `preset-safe` codemods for Charts.
88
+
89
+ <!-- #npm-tag-reference -->
90
+
91
+ ```bash
92
+ npx @mui/x-codemod@next v9.0.0/charts/preset-safe <path|folder>
93
+ ```
94
+
95
+ The list includes these transformers
96
+
97
+ - [`replace-heatmap-hide-legend-false`](#replace-heatmap-hide-legend-false)
98
+ - [`rename-chart-api-import`](#rename-chart-api-import)
99
+ - [`rename-id-to-series-id`](#rename-id-to-series-id)
100
+ - [`replace-show-mark-default`](#replace-show-mark-default)
101
+
102
+ ### `replace-heatmap-hide-legend-false`
103
+
104
+ The default value of the `hideLegend` prop in the `Heatmap` component has changed from `true` to `false` in v9. This improves consistency across chart components and developer experience.
105
+
106
+ ```diff
107
+ <Heatmap
108
+ + hideLegend
109
+ />
110
+ ```
111
+
112
+ ### `rename-axis-tooltip-hook`
113
+
114
+ The `useAxisTooltip()` hook has been renamed to `useAxesTooltip()` to better reflect its functionality of handling multiple axes.
115
+
116
+ ```diff
117
+ -import { useAxisTooltip, UseAxisTooltipReturnValue, UseAxisTooltipParams } from '@mui/x-charts';
118
+ +import { useAxesTooltip, UseAxesTooltipReturnValue, UseAxesTooltipParams } from '@mui/x-charts';
119
+ ```
120
+
121
+ The hook now always returns an array of tooltip data (one entry per active axis) instead of a single object.
122
+ The `multipleAxes` parameter has been removed since the hook now always supports multiple axes.
123
+
124
+ After running the codemod to do the renaming make sure to adapt the hook returned value to your needs.
125
+
126
+ ```diff
127
+ function CustomTooltip() {
128
+ // If you want to keep only one axis
129
+ - const tooltipData = useAxisTooltip();
130
+ + const tooltipData = useAxesTooltip()[0] ?? null;
131
+ // If you use all the axes
132
+ - const tooltipData = useAxisTooltip({ multipleAxes: true });
133
+ + const tooltipData = useAxesTooltip();
134
+ }
135
+ ```
136
+
137
+ ### `rename-chart-api-import`
138
+
139
+ Moves the `ChartApi` type import from `@mui/x-charts/ChartContainer` to `@mui/x-charts/context`.
140
+
141
+ ```diff
142
+ -import type { ChartApi } from '@mui/x-charts/ChartContainer';
143
+ +import type { ChartApi } from '@mui/x-charts/context';
144
+ ```
145
+
146
+ #### `rename-id-to-series-id`
147
+
148
+ Rename the props `id` to `seriesId`.
149
+
150
+ ```diff
151
+ - <PieArc id='series-a' />
152
+ + <PieArc seriesId='series-a' />
153
+ ```
154
+
155
+ Here is the list of slots and components that are impacted by the renaming:
156
+
157
+ | slot | Component |
158
+ | :------------ | :--------------------------------------- |
159
+ | pieArc | PieArc |
160
+ | | PieArcPlot |
161
+ | pieArcLabel | PieArcLabel |
162
+ | | PieArcLabelPlot |
163
+ | bar | BarElement, AnimatedRangeBarElementProps |
164
+ | area | AnimatedArea, AreaElement |
165
+ | line | AnimatedLine, LineElement |
166
+ | mark | MarkElement |
167
+ | lineHighlight | LineHighlightElement |
168
+
169
+ #### `replace-show-mark-default`
170
+
171
+ Add `showMark: true` to line series when not defined to keep the same default behavior.
172
+
173
+ ```diff
174
+ - <LineChart series={[{ data: [/* ... */] }]} />
175
+ + <LineChart series={[{ data: [/* ... */] showMark: true }]} />
176
+ - <ChartDataProvider series={[{ type: 'line', data: [/* ... */] }]} />
177
+ + <ChartDataProvider series={[{ type: 'line', data: [/* ... */] showMark: true }]} />
178
+ ```
179
+
60
180
  ## v8.0.0
61
181
 
62
182
  ### 🚀 `preset-safe` for v8.0.0
package/codemod.js CHANGED
@@ -2,13 +2,11 @@
2
2
  "use strict";
3
3
 
4
4
  var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
5
- var _child_process = _interopRequireDefault(require("child_process"));
5
+ var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends"));
6
6
  var _fs = require("fs");
7
7
  var _path = _interopRequireDefault(require("path"));
8
8
  var _yargs = _interopRequireDefault(require("yargs"));
9
- const jscodeshiftPackage = require('jscodeshift/package.json');
10
- const jscodeshiftDirectory = _path.default.dirname(require.resolve('jscodeshift'));
11
- const jscodeshiftExecutable = _path.default.join(jscodeshiftDirectory, jscodeshiftPackage.bin.jscodeshift);
9
+ var _Runner = require("jscodeshift/src/Runner");
12
10
  async function runTransform(transform, files, flags, codemodFlags) {
13
11
  const transformerSrcPath = _path.default.resolve(__dirname, './src', transform);
14
12
  const transformerBuildPath = _path.default.resolve(__dirname, transform);
@@ -27,13 +25,25 @@ async function runTransform(transform, files, flags, codemodFlags) {
27
25
  throw buildPathError;
28
26
  }
29
27
  }
30
- const args = [
31
- // can't directly spawn `jscodeshiftExecutable` due to https://github.com/facebook/jscodeshift/issues/424
32
- jscodeshiftExecutable, '--transform', transformerPath, ...codemodFlags, '--extensions', 'js,ts,jsx,tsx', '--parser', flags.parser || 'tsx', '--ignore-pattern', '**/node_modules/**', ...flags.jscodeshift];
33
- args.push(...files);
28
+
29
+ // Parse additional jscodeshift options from flags
30
+ const additionalOptions = {};
31
+ [...codemodFlags, ...flags.jscodeshift].forEach(flag => {
32
+ const match = flag.match(/^--([^=]+)(?:=(.*))?$/);
33
+ if (match) {
34
+ const [, key, value] = match;
35
+ additionalOptions[key] = value ?? true;
36
+ }
37
+ });
38
+ const options = (0, _extends2.default)({
39
+ extensions: 'js,ts,jsx,tsx',
40
+ parser: flags.parser || 'tsx',
41
+ ignorePattern: ['**/node_modules/**', ...(additionalOptions.ignorePattern || [])],
42
+ verbose: 2
43
+ }, additionalOptions);
34
44
 
35
45
  // eslint-disable-next-line no-console -- debug information
36
- console.log(`Executing command: jscodeshift ${args.join(' ')}`);
46
+ console.log(`Running jscodeshift with transform: ${transformerPath}`);
37
47
  console.warn(`
38
48
  ====================================
39
49
  IMPORTANT NOTICE ABOUT CODEMOD USAGE
@@ -42,14 +52,12 @@ Not all use cases are covered by codemods. In some scenarios, like props spreadi
42
52
 
43
53
  For example, if a codemod tries to rename a prop, but this prop is hidden with the spread operator, it won't be transformed as expected.
44
54
  <DatePicker {...pickerProps} />
45
-
55
+
46
56
  After running the codemods, make sure to test your application and that you don't have any formatting or console errors.
47
57
  `);
48
- const jscodeshiftProcess = _child_process.default.spawnSync('node', args, {
49
- stdio: 'inherit'
50
- });
51
- if (jscodeshiftProcess.error) {
52
- throw jscodeshiftProcess.error;
58
+ const result = await (0, _Runner.run)(transformerPath, files, options);
59
+ if (result.error > 0) {
60
+ process.exit(1);
53
61
  }
54
62
  }
55
63
  function run(argv) {
package/package.json CHANGED
@@ -1,9 +1,8 @@
1
1
  {
2
2
  "name": "@mui/x-codemod",
3
- "version": "8.27.0",
3
+ "version": "9.0.0-alpha.1",
4
4
  "author": "MUI Team",
5
5
  "description": "Codemod scripts for MUI X.",
6
- "bin": "./codemod.js",
7
6
  "keywords": [
8
7
  "react",
9
8
  "react-component",
@@ -24,12 +23,12 @@
24
23
  "url": "https://opencollective.com/mui-org"
25
24
  },
26
25
  "dependencies": {
27
- "@babel/core": "^7.28.5",
28
- "@babel/runtime": "^7.28.4",
29
- "@babel/traverse": "^7.28.5",
26
+ "@babel/core": "^7.29.0",
27
+ "@babel/runtime": "^7.28.6",
28
+ "@babel/traverse": "^7.29.0",
30
29
  "jscodeshift": "17.3.0",
31
30
  "yargs": "^18.0.0",
32
- "@mui/x-internals": "8.26.0"
31
+ "@mui/x-internals": "9.0.0-alpha.0"
33
32
  },
34
33
  "sideEffects": false,
35
34
  "publishConfig": {
@@ -41,5 +40,6 @@
41
40
  "type": "commonjs",
42
41
  "exports": {
43
42
  "./package.json": "./package.json"
44
- }
43
+ },
44
+ "bin": "./codemod.js"
45
45
  }
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = addProp;
7
+ /**
8
+ * Adds a prop to specified JSX components in the AST.
9
+ *
10
+ * Can be configured to only add the prop if it is absent.
11
+ */
12
+ function addProp({
13
+ j,
14
+ root,
15
+ componentNames,
16
+ propName,
17
+ propValue,
18
+ position
19
+ }) {
20
+ return root.find(j.JSXElement).filter(path => {
21
+ return componentNames.includes(path.value.openingElement.name.name);
22
+ }).forEach(path => {
23
+ const hasProp = path.value.openingElement.attributes?.some(attr => {
24
+ return attr.type === 'JSXAttribute' && attr.name.name === propName;
25
+ });
26
+ if (!hasProp) {
27
+ const fn = position === 'start' ? 'unshift' : 'push';
28
+ path.value.openingElement.attributes?.[fn](j.jsxAttribute(j.jsxIdentifier(propName), typeof propValue === 'boolean' && propValue ? null : j.jsxExpressionContainer(j.literal(propValue))));
29
+ }
30
+ });
31
+ }
@@ -5,6 +5,10 @@ Object.defineProperty(exports, "__esModule", {
5
5
  });
6
6
  exports.default = removeObjectProperty;
7
7
  const getAttributeName = attribute => attribute.name.type === 'JSXIdentifier' ? attribute.name.name : attribute.name.name.name;
8
+ /**
9
+ * Removes a property from an object prop in specified components.
10
+ * If the object only contains that property, the whole prop is removed.
11
+ */
8
12
  function removeObjectProperty({
9
13
  root,
10
14
  propName,
@@ -4,6 +4,9 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = removeProps;
7
+ /**
8
+ * Removes specified props from given components.
9
+ */
7
10
  function removeProps({
8
11
  root,
9
12
  componentNames,
@@ -12,6 +12,11 @@ const getSlotsTranslation = translations => {
12
12
  });
13
13
  return lowercasedTranslation;
14
14
  };
15
+
16
+ /**
17
+ * Replace the components / componentsProps by their equivalent slots / slotProps.
18
+ * Only used for v6 -> v7 migration.
19
+ */
15
20
  function renameComponentsSlots({
16
21
  root,
17
22
  componentNames,
@@ -23,9 +23,13 @@ const getMatchingNestedImport = (path, parameters) => {
23
23
  };
24
24
  const getMatchingRootImport = (path, parameters) => {
25
25
  return parameters.imports.find(importConfig => {
26
- return !importConfig.skipRoot && importConfig.importsMapping.hasOwnProperty(path.node.imported.name);
26
+ return importConfig.importsMapping.hasOwnProperty(path.node.imported.name.toString());
27
27
  });
28
28
  };
29
+
30
+ /**
31
+ * Rename import paths, identifiers and usages based on a renaming configuration.
32
+ */
29
33
  function renameImports(parameters) {
30
34
  const {
31
35
  j,
@@ -105,15 +109,50 @@ function renameImports(parameters) {
105
109
  }
106
110
  return !!getMatchingNestedImport(path, parameters)?.newEndpoint;
107
111
  }).replaceWith(path => {
112
+ const importConfig = getMatchingNestedImport(path, parameters);
108
113
  const pathStr = getPathStrFromPath(path);
109
114
  const oldEndpoint = getRelativeEndpointFromPathStr(pathStr, parameters.packageNames);
110
- const newEndpoint = getMatchingNestedImport(path, parameters).newEndpoint;
115
+ const newEndpoint = importConfig.newEndpoint;
111
116
  const newPathStr = pathStr.replace(oldEndpoint, newEndpoint);
112
- return j.importDeclaration(
113
- // Copy over the existing import specifiers
114
- path.node.specifiers,
115
- // Replace the source with our new source
116
- j.stringLiteral(newPathStr));
117
+
118
+ // Handle splitting when splitUnmatchedSpecifiers is enabled
119
+ if (importConfig.splitUnmatchedSpecifiers) {
120
+ const specifiers = path.node.specifiers ?? [];
121
+ const specifiersToMove = [];
122
+ const specifiersToKeep = [];
123
+ for (const specifier of specifiers) {
124
+ if (specifier.type === 'ImportSpecifier' && importConfig.importsMapping.hasOwnProperty(specifier.imported.name)) {
125
+ specifiersToMove.push(specifier);
126
+ } else {
127
+ specifiersToKeep.push(specifier);
128
+ }
129
+ }
130
+
131
+ // If no specifiers match, don't change anything
132
+ if (specifiersToMove.length === 0) {
133
+ return path.node;
134
+ }
135
+
136
+ // If all specifiers match, just update the path in place (no split needed)
137
+ if (specifiersToKeep.length === 0) {
138
+ path.node.source = j.stringLiteral(newPathStr);
139
+ return path.node;
140
+ }
141
+
142
+ // Split: modify current node to keep unmatched specifiers, insert new node for matched ones
143
+ const moveNode = j.importDeclaration(specifiersToMove, j.stringLiteral(newPathStr));
144
+
145
+ // Insert the new import after the current one
146
+ j(path).insertAfter(moveNode);
147
+
148
+ // Update the current node in place to only keep the unmatched specifiers
149
+ path.node.specifiers = specifiersToKeep;
150
+ return path.node;
151
+ }
152
+
153
+ // Default behavior: move all specifiers to the new endpoint (modify in place)
154
+ path.node.source = j.stringLiteral(newPathStr);
155
+ return path.node;
117
156
  });
118
157
 
119
158
  // Rename the import usage
@@ -4,6 +4,9 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = renameNestedProps;
7
+ /**
8
+ * Allow to rename object properties inside props of specified components.
9
+ */
7
10
  function renameNestedProps({
8
11
  root,
9
12
  componentNames,
@@ -29,7 +29,7 @@ function transformer(file, api, options) {
29
29
  // Rename the import specifiers
30
30
  // - import { GridFilterMenuItem } from '@mui/x-data-grid'
31
31
  // + import { GridColumnMenuFilterItem } from '@mui/x-data-grid'
32
- matchingImports.find(j.ImportSpecifier).filter(path => VARIABLES.hasOwnProperty(path.node.imported.name)).replaceWith(path => j.importSpecifier(j.identifier(VARIABLES[path.node.imported.name])));
32
+ matchingImports.find(j.ImportSpecifier).filter(path => VARIABLES.hasOwnProperty(path.node.imported.name.toString())).replaceWith(path => j.importSpecifier(j.identifier(VARIABLES[path.node.imported.name.toString()])));
33
33
 
34
34
  // Rename the import usage
35
35
  // - <GridFilterMenuItem />
@@ -1,12 +1,10 @@
1
1
  "use strict";
2
2
 
3
3
  var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard").default;
4
- var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
5
4
  Object.defineProperty(exports, "__esModule", {
6
5
  value: true
7
6
  });
8
7
  exports.default = transform;
9
- var _renameCSSClasses = _interopRequireDefault(require("../../../util/renameCSSClasses"));
10
8
  var _renameIdentifiers = _interopRequireWildcard(require("../../../util/renameIdentifiers"));
11
9
  const renamedIdentifiers = {
12
10
  GridLinkOperator: 'GridLogicOperator',
@@ -51,10 +49,26 @@ const preRequisiteUsages = {
51
49
  const renamedLiterals = {
52
50
  filterPanelLinkOperator: 'filterPanelLogicOperator'
53
51
  };
54
- const renamedClasses = {
55
- 'MuiDataGrid-filterFormLinkOperatorInput': 'MuiDataGrid-filterFormLogicOperatorInput',
56
- 'MuiDataGrid-withBorder': 'MuiDataGrid-withBorderColor'
57
- };
52
+ /**
53
+ * Renames CSS classes when they are literals based on the provided mapping.
54
+ */
55
+ function renameCSSClasses({
56
+ root,
57
+ j
58
+ }) {
59
+ const renamedClasses = {
60
+ 'MuiDataGrid-filterFormLinkOperatorInput': 'MuiDataGrid-filterFormLogicOperatorInput',
61
+ 'MuiDataGrid-withBorder': 'MuiDataGrid-withBorderColor'
62
+ };
63
+ root.find(j.Literal).filter(path => !!Object.keys(renamedClasses).find(className => {
64
+ const literal = path.node.value;
65
+ return typeof literal === 'string' && literal.includes(className) && !literal.includes(renamedClasses[className]);
66
+ })).replaceWith(path => {
67
+ const literal = path.node.value;
68
+ const targetClassKey = Object.keys(renamedClasses).find(className => literal.includes(className));
69
+ return j.literal(literal.replace(targetClassKey, renamedClasses[targetClassKey]));
70
+ });
71
+ }
58
72
  function transform(file, api, options) {
59
73
  const j = api.jscodeshift;
60
74
  const root = j(file.source);
@@ -95,10 +109,9 @@ function transform(file, api, options) {
95
109
  // Rename the classes
96
110
  // - 'MuiDataGrid-filterFormLinkOperatorInput'
97
111
  // + 'MuiDataGrid-filterFormLogicOperatorInput'
98
- (0, _renameCSSClasses.default)({
112
+ renameCSSClasses({
99
113
  j,
100
- root,
101
- renamedClasses
114
+ root
102
115
  });
103
116
  }
104
117
  return root.toSource(printOptions);
@@ -124,7 +124,7 @@ function transformer(file, api, options) {
124
124
  // Rename the import specifiers
125
125
  // - import { DayCalendarSlotsComponent } from '@mui/x-date-pickers'
126
126
  // + import { DayCalendarSlots } from '@mui/x-date-pickers'
127
- matchingImports.find(j.ImportSpecifier).filter(path => Object.keys(rename).includes(path.node.imported.name)).replaceWith(path => j.importSpecifier(j.identifier(rename[path.node.imported.name]), path.value.local));
127
+ matchingImports.find(j.ImportSpecifier).filter(path => Object.keys(rename).includes(path.node.imported.name.toString())).replaceWith(path => j.importSpecifier(j.identifier(rename[path.node.imported.name.toString()]), path.value.local));
128
128
 
129
129
  // Rename the import usage
130
130
  // - DayCalendarSlotsComponent
@@ -19,7 +19,7 @@ function transformer(file, api, options) {
19
19
  return typeof node.source.value === 'string' && node.source.value.startsWith('@mui/x-charts');
20
20
  }).forEach(path => {
21
21
  path.node.specifiers?.forEach(node => {
22
- root.findJSXElements(node.local?.name).forEach(elementPath => {
22
+ root.findJSXElements(node.local?.name.toString()).forEach(elementPath => {
23
23
  if (elementPath.node.type !== 'JSXElement') {
24
24
  return;
25
25
  }
@@ -19,7 +19,7 @@ function transformer(file, api, options) {
19
19
  return typeof node.source.value === 'string' && node.source.value.startsWith('@mui/x-charts');
20
20
  }).forEach(path => {
21
21
  path.node.specifiers?.forEach(node => {
22
- root.findJSXElements(node.local?.name).forEach(elementPath => {
22
+ root.findJSXElements(node.local?.name.toString()).forEach(elementPath => {
23
23
  if (elementPath.node.type !== 'JSXElement') {
24
24
  return;
25
25
  }
@@ -19,7 +19,7 @@ function transformer(file, api, options) {
19
19
  return typeof node.source.value === 'string' && node.source.value.startsWith('@mui/x-charts');
20
20
  }).forEach(path => {
21
21
  path.node.specifiers?.forEach(node => {
22
- root.findJSXElements(node.local?.name).forEach(elementPath => {
22
+ root.findJSXElements(node.local?.name.toString()).forEach(elementPath => {
23
23
  if (elementPath.node.type !== 'JSXElement') {
24
24
  return;
25
25
  }
@@ -18,7 +18,7 @@ function transformer(file, api, options) {
18
18
  return typeof node.source.value === 'string' && node.source.value.startsWith('@mui/x-charts');
19
19
  }).forEach(path => {
20
20
  path.node.specifiers?.forEach(node => {
21
- root.findJSXElements(node.local?.name).forEach(elementPath => {
21
+ root.findJSXElements(node.local?.name.toString()).forEach(elementPath => {
22
22
  if (elementPath.node.type !== 'JSXElement') {
23
23
  return;
24
24
  }
@@ -19,7 +19,7 @@ function transformer(file, api, options) {
19
19
  return typeof node.source.value === 'string' && node.source.value.startsWith('@mui/x-charts');
20
20
  }).forEach(path => {
21
21
  path.node.specifiers?.forEach(node => {
22
- root.findJSXElements(node.local?.name).forEach(elementPath => {
22
+ root.findJSXElements(node.local?.name.toString()).forEach(elementPath => {
23
23
  if (elementPath.node.type !== 'JSXElement') {
24
24
  return;
25
25
  }
@@ -16,9 +16,9 @@ function transformer(file, api, options) {
16
16
  // Find relevant DataGrid imports
17
17
  const importedDataGrids = new Set();
18
18
  root.find(j.ImportDeclaration).forEach(path => {
19
- if (dataGridSources.has(path.node.source.value)) {
19
+ if (dataGridSources.has(path.node.source.value?.toString() ?? '')) {
20
20
  path.node.specifiers?.forEach(specifier => {
21
- if (specifier.type === 'ImportSpecifier' && dataGridComponents.has(specifier.imported.name)) {
21
+ if (specifier.type === 'ImportSpecifier' && dataGridComponents.has(specifier.imported.name.toString())) {
22
22
  const localName = specifier.local?.name;
23
23
  if (localName) {
24
24
  importedDataGrids.add(localName);
@@ -0,0 +1,24 @@
1
+ "use strict";
2
+
3
+ var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var renameIdToSeriesId = _interopRequireWildcard(require("../rename-id-to-series-id"));
10
+ var renameChartApiImport = _interopRequireWildcard(require("../rename-chart-api-import"));
11
+ var replaceHeatmapHideLegend = _interopRequireWildcard(require("../replace-heatmap-hide-legend-false"));
12
+ var replaceShowMarkDefault = _interopRequireWildcard(require("../replace-show-mark-default"));
13
+ const allModules = [
14
+ // Add other transforms here as they are created
15
+ replaceHeatmapHideLegend, replaceShowMarkDefault, renameIdToSeriesId, renameChartApiImport];
16
+ function transformer(file, api, options) {
17
+ allModules.forEach(module => {
18
+ file.source = module.default(file, api, options);
19
+ });
20
+ return file.source;
21
+ }
22
+ const testConfig = exports.testConfig = {
23
+ allModules
24
+ };
@@ -0,0 +1,53 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var _path = _interopRequireDefault(require("path"));
10
+ var _readFile = _interopRequireDefault(require("../../../util/readFile"));
11
+ var _renameImports = require("../../../util/renameImports");
12
+ function transformer(file, api, options) {
13
+ const j = api.jscodeshift;
14
+ const root = j(file.source);
15
+ const printOptions = options.printOptions || {
16
+ quote: 'single',
17
+ trailingComma: true,
18
+ wrapColumn: 40
19
+ };
20
+ (0, _renameImports.renameImports)({
21
+ j,
22
+ root,
23
+ packageNames: ['@mui/x-charts', '@mui/x-charts-pro', '@mui/x-charts-premium'],
24
+ imports: [{
25
+ oldEndpoint: 'ChartsTooltip',
26
+ importsMapping: {
27
+ useAxisTooltip: 'useAxesTooltip',
28
+ UseAxisTooltipReturnValue: 'UseAxesTooltipReturnValue',
29
+ UseAxisTooltipParams: 'UseAxesTooltipParams'
30
+ }
31
+ }, {
32
+ importsMapping: {
33
+ useAxisTooltip: 'useAxesTooltip',
34
+ UseAxisTooltipReturnValue: 'UseAxesTooltipReturnValue',
35
+ UseAxisTooltipParams: 'UseAxesTooltipParams'
36
+ }
37
+ }]
38
+ });
39
+ return root.toSource(printOptions);
40
+ }
41
+ const testConfig = () => ({
42
+ name: 'rename-axis-tooltip-hook',
43
+ specFiles: [{
44
+ name: 'nested',
45
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual-nested-imports.spec.tsx')),
46
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected-nested-imports.spec.tsx'))
47
+ }, {
48
+ name: 'root',
49
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual-root-imports.spec.tsx')),
50
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected-root-imports.spec.tsx'))
51
+ }]
52
+ });
53
+ exports.testConfig = testConfig;
@@ -0,0 +1,42 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var _path = _interopRequireDefault(require("path"));
10
+ var _readFile = _interopRequireDefault(require("../../../util/readFile"));
11
+ var _renameImports = require("../../../util/renameImports");
12
+ function transformer(file, api, options) {
13
+ const j = api.jscodeshift;
14
+ const root = j(file.source);
15
+ const printOptions = options.printOptions || {
16
+ quote: 'single',
17
+ trailingComma: true
18
+ };
19
+ (0, _renameImports.renameImports)({
20
+ j,
21
+ root,
22
+ packageNames: ['@mui/x-charts', '@mui/x-charts-pro', '@mui/x-charts-premium'],
23
+ imports: [{
24
+ oldEndpoint: 'ChartContainer',
25
+ newEndpoint: 'context',
26
+ importsMapping: {
27
+ ChartApi: 'ChartApi'
28
+ },
29
+ splitUnmatchedSpecifiers: true
30
+ }]
31
+ });
32
+ return root.toSource(printOptions);
33
+ }
34
+ const testConfig = () => ({
35
+ name: 'rename-chart-api-import',
36
+ specFiles: [{
37
+ name: 'imports',
38
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual-imports.spec.tsx')),
39
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected-imports.spec.tsx'))
40
+ }]
41
+ });
42
+ exports.testConfig = testConfig;
@@ -0,0 +1,37 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var _path = _interopRequireDefault(require("path"));
10
+ var _readFile = _interopRequireDefault(require("../../../util/readFile"));
11
+ var _renameProps = _interopRequireDefault(require("../../../util/renameProps"));
12
+ function transformer(file, api, options) {
13
+ const j = api.jscodeshift;
14
+ const root = j(file.source);
15
+ const printOptions = options.printOptions || {
16
+ quote: 'single',
17
+ trailingComma: true
18
+ };
19
+ (0, _renameProps.default)({
20
+ j,
21
+ root,
22
+ componentNames: ['PieArc', 'PieArcPlot', 'PieArcLabel', 'PieArcLabelPlot', 'BarElement', 'AnimatedRangeBarElement', 'AnimatedArea', 'AnimatedLine', 'MarkElement', 'AreaElement', 'LineElement', 'LineHighlightElement'],
23
+ props: {
24
+ id: 'seriesId'
25
+ }
26
+ });
27
+ return root.toSource(printOptions);
28
+ }
29
+ const testConfig = () => ({
30
+ name: 'rename-id-to-series-id',
31
+ specFiles: [{
32
+ name: 'rename id to seriesId',
33
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual-imports.spec.tsx')),
34
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected-imports.spec.tsx'))
35
+ }]
36
+ });
37
+ exports.testConfig = testConfig;
@@ -0,0 +1,41 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var _path = _interopRequireDefault(require("path"));
10
+ var _addProp = _interopRequireDefault(require("../../../util/addProp"));
11
+ var _readFile = _interopRequireDefault(require("../../../util/readFile"));
12
+ /**
13
+ * Codemod for v9.0.0: Updates <Heatmap /> usages to explicitly set hideLegend={true}
14
+ * if the prop is missing, to preserve v8 behavior after the default changes to false.
15
+ */
16
+
17
+ function transformer(file, api, options) {
18
+ const j = api.jscodeshift;
19
+ const root = j(file.source);
20
+ const printOptions = options.printOptions || {
21
+ quote: 'single',
22
+ trailingComma: true
23
+ };
24
+ return (0, _addProp.default)({
25
+ root,
26
+ j,
27
+ componentNames: ['Heatmap', 'HeatmapPremium'],
28
+ propName: 'hideLegend',
29
+ propValue: true,
30
+ position: 'start'
31
+ }).toSource(printOptions);
32
+ }
33
+ const testConfig = () => ({
34
+ name: 'replace-heatmap-hide-legend-false',
35
+ specFiles: [{
36
+ name: 'imports',
37
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual.spec.tsx')),
38
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected.spec.tsx'))
39
+ }]
40
+ });
41
+ exports.testConfig = testConfig;
@@ -0,0 +1,91 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ exports.testConfig = void 0;
9
+ var _path = _interopRequireDefault(require("path"));
10
+ var _readFile = _interopRequireDefault(require("../../../util/readFile"));
11
+ const COMPONENT_NAMES = ['LineChart', 'LineChartPro', 'LineChartPremium'];
12
+ const PROVIDER_NAMES = ['ChartDataProvider', 'ChartDataProviderPro', 'ChartDataProviderPremium',
13
+ // With the new naming to be sure codemod order does not matter
14
+ 'ChartsDataProvider', 'ChartsDataProviderPro', 'ChartsDataProviderPremium',
15
+ // The component that includes the data provider.
16
+ 'ChartsContainer', 'ChartsContainerPro', 'ChartsContainerPremium'];
17
+
18
+ /**
19
+ * Codemod for v9.0.0: Updates line series objects to preserve v8 behavior after the `showMark` default changes from true to false.
20
+ *
21
+ * If `showMark` is not defined, adds `showMark: true` to preserve v8 behavior.
22
+ *
23
+ * The `showmMark: false` cases are left unchanged to stay idempotent.
24
+ *
25
+ * Ths codemod applies on LineChart components and providers when series type is set to 'line'.
26
+ */
27
+ function transformer(file, api, options) {
28
+ const j = api.jscodeshift;
29
+ const root = j(file.source);
30
+ const printOptions = options.printOptions || {
31
+ quote: 'single',
32
+ trailingComma: true
33
+ };
34
+ root.find(j.JSXElement).filter(p => COMPONENT_NAMES.includes(p.value.openingElement.name.name)).forEach(p => {
35
+ const seriesAttr = p.value.openingElement.attributes?.find(attr => attr.type === 'JSXAttribute' && attr.name.name === 'series');
36
+ if (!seriesAttr || seriesAttr.type !== 'JSXAttribute') {
37
+ return;
38
+ }
39
+ const seriesValue = seriesAttr.value;
40
+ if (!seriesValue || seriesValue.type !== 'JSXExpressionContainer') {
41
+ return;
42
+ }
43
+ const expr = seriesValue.expression;
44
+ if (expr.type !== 'ArrayExpression') {
45
+ return;
46
+ }
47
+ expr.elements.forEach(element => {
48
+ if (!element || element.type !== 'ObjectExpression') {
49
+ return;
50
+ }
51
+ const hasShowMark = element.properties.some(prop => prop.type === 'ObjectProperty' && prop.key.type === 'Identifier' && prop.key.name === 'showMark');
52
+ if (!hasShowMark) {
53
+ element.properties.push(j.objectProperty(j.identifier('showMark'), j.booleanLiteral(true)));
54
+ }
55
+ });
56
+ });
57
+ root.find(j.JSXElement).filter(p => PROVIDER_NAMES.includes(p.value.openingElement.name.name)).forEach(p => {
58
+ const seriesAttr = p.value.openingElement.attributes?.find(attr => attr.type === 'JSXAttribute' && attr.name.name === 'series');
59
+ if (!seriesAttr || seriesAttr.type !== 'JSXAttribute') {
60
+ return;
61
+ }
62
+ const seriesValue = seriesAttr.value;
63
+ if (!seriesValue || seriesValue.type !== 'JSXExpressionContainer') {
64
+ return;
65
+ }
66
+ const expr = seriesValue.expression;
67
+ if (expr.type !== 'ArrayExpression') {
68
+ return;
69
+ }
70
+ expr.elements.forEach(element => {
71
+ if (!element || element.type !== 'ObjectExpression') {
72
+ return;
73
+ }
74
+ const lineSeriesType = element.properties.some(prop => prop.type === 'ObjectProperty' && prop.key.type === 'Identifier' && prop.key.name === 'type' && prop.value.type === 'StringLiteral' && prop.value.value === 'line');
75
+ const hasShowMark = element.properties.some(prop => prop.type === 'ObjectProperty' && prop.key.type === 'Identifier' && prop.key.name === 'showMark');
76
+ if (lineSeriesType && !hasShowMark) {
77
+ element.properties.push(j.objectProperty(j.identifier('showMark'), j.booleanLiteral(true)));
78
+ }
79
+ });
80
+ });
81
+ return root.toSource(printOptions);
82
+ }
83
+ const testConfig = () => ({
84
+ name: 'replace-show-mark-default',
85
+ specFiles: [{
86
+ name: 'imports',
87
+ actual: (0, _readFile.default)(_path.default.join(__dirname, 'actual.spec.tsx')),
88
+ expected: (0, _readFile.default)(_path.default.join(__dirname, 'expected.spec.tsx'))
89
+ }]
90
+ });
91
+ exports.testConfig = testConfig;
@@ -0,0 +1,16 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = transformer;
8
+ var _presetSafe = _interopRequireDefault(require("../charts/preset-safe"));
9
+ function transformer(file, api, options) {
10
+ [
11
+ // Add others here as they are created
12
+ _presetSafe.default].forEach(transform => {
13
+ file.source = transform(file, api, options);
14
+ });
15
+ return file.source;
16
+ }
@@ -1,54 +0,0 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.default = propsToObject;
7
- function propsToObject({
8
- j,
9
- root,
10
- componentName,
11
- aliasName,
12
- propName,
13
- props
14
- }) {
15
- function buildObject(node, value) {
16
- const shorthand = node.value.expression && node.value.expression.name === node.name.name;
17
- const property = j.objectProperty(j.identifier(node.name.name), node.value.expression ? node.value.expression : node.value);
18
- property.shorthand = shorthand;
19
- value.push(property);
20
- return value;
21
- }
22
- const result = aliasName ? root.find(j.JSXElement, {
23
- openingElement: {
24
- name: {
25
- property: {
26
- name: componentName
27
- }
28
- }
29
- }
30
- }) : root.findJSXElements(componentName);
31
- return result.forEach(path => {
32
- // @ts-expect-error
33
- if (!aliasName || aliasName && path.node.openingElement.name.object.name === aliasName) {
34
- let propValue = [];
35
- const attributes = path.node.openingElement.attributes;
36
- attributes?.forEach((node, index) => {
37
- // Only transform whitelisted props
38
- if (node.type === 'JSXAttribute' && props.includes(node.name.name)) {
39
- propValue = buildObject(node, propValue);
40
- delete attributes[index];
41
- }
42
- });
43
- if (propValue.length > 0) {
44
- const propNameAttr = attributes?.find(attr => attr.type === 'JSXAttribute' && attr.name.name === propName);
45
- if (propNameAttr && propNameAttr.type === 'JSXAttribute') {
46
- // @ts-expect-error
47
- (propNameAttr.value.expression?.properties || []).push(...j.objectExpression(propValue).properties);
48
- } else {
49
- attributes?.push(j.jsxAttribute(j.jsxIdentifier(propName), j.jsxExpressionContainer(j.objectExpression(propValue))));
50
- }
51
- }
52
- }
53
- });
54
- }
@@ -1,20 +0,0 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.default = renameCSSClasses;
7
- function renameCSSClasses({
8
- root,
9
- j,
10
- renamedClasses
11
- }) {
12
- root.find(j.Literal).filter(path => !!Object.keys(renamedClasses).find(className => {
13
- const literal = path.node.value;
14
- return typeof literal === 'string' && literal.includes(className) && !literal.includes(renamedClasses[className]);
15
- })).replaceWith(path => {
16
- const literal = path.node.value;
17
- const targetClassKey = Object.keys(renamedClasses).find(className => literal.includes(className));
18
- return j.literal(literal.replace(targetClassKey, renamedClasses[targetClassKey]));
19
- });
20
- }