@@ -26,7 +26,6 @@ async function findResourceFilePath(resourceId) {
26
26
throw new Error ( `Failed to read resources directory ${ resourcesDir } : ${ error . message } ` ) ;
27
27
}
28
28
29
- console . log ( chalk . dim ( `Found .ts files to scan: ${ tsFiles . join ( ', ' ) || 'None' } ` ) ) ;
30
29
31
30
for ( const file of tsFiles ) {
32
31
const filePath = path . resolve ( resourcesDir , file ) ;
@@ -94,6 +93,7 @@ export async function updateResourceConfig(resourceId, columnName, fieldType, co
94
93
console . log ( chalk . dim ( `Attempting to update resource config: ${ filePath } ` ) ) ;
95
94
96
95
let content ;
96
+ let injectionLine = null ;
97
97
try {
98
98
content = await fs . readFile ( filePath , 'utf-8' ) ;
99
99
} catch ( error ) {
@@ -176,11 +176,16 @@ export async function updateResourceConfig(resourceId, columnName, fieldType, co
176
176
const newComponentValue = b . stringLiteral ( componentPathForConfig ) ;
177
177
178
178
if ( fieldTypeProperty ) {
179
+ injectionLine = fieldTypeProperty . loc ?. start . line ?? null ;
179
180
fieldTypeProperty . value = newComponentValue ;
180
181
console . log ( chalk . dim ( `Updated '${ fieldType } ' component path in column '${ columnName } '.` ) ) ;
181
182
} else {
182
183
fieldTypeProperty = b . objectProperty ( b . identifier ( fieldType ) , newComponentValue ) ;
183
184
componentsObject . properties . push ( fieldTypeProperty ) ;
185
+ fieldTypeProperty = componentsObject . properties . find ( p =>
186
+ n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === fieldType
187
+ ) ;
188
+ injectionLine = fieldTypeProperty . loc ?. start . line ?? null ;
184
189
console . log ( chalk . dim ( `Added '${ fieldType } ' component path to column '${ columnName } '.` ) ) ;
185
190
}
186
191
@@ -197,7 +202,7 @@ export async function updateResourceConfig(resourceId, columnName, fieldType, co
197
202
const outputCode = recast . print ( ast ) . code ;
198
203
199
204
await fs . writeFile ( filePath , outputCode , 'utf-8' ) ;
200
- console . log ( chalk . dim ( `Successfully updated resource configuration file (preserving formatting): ${ filePath } ` ) ) ;
205
+ console . log ( chalk . dim ( `Successfully updated resource configuration file (preserving formatting): ${ filePath } : ${ injectionLine } ` ) ) ;
201
206
202
207
} catch ( error ) {
203
208
console . error ( chalk . red ( `❌ Error processing resource file: ${ filePath } ` ) ) ;
@@ -211,78 +216,101 @@ export async function injectLoginComponent(indexFilePath, componentPath) {
211
216
console . log ( chalk . dim ( `Reading file: ${ indexFilePath } ` ) ) ;
212
217
const content = await fs . readFile ( indexFilePath , 'utf-8' ) ;
213
218
const ast = recast . parse ( content , {
214
- parser : typescriptParser ,
219
+ parser : typescriptParser ,
215
220
} ) ;
216
-
221
+
217
222
let updated = false ;
218
-
223
+ let injectionLine = null ;
224
+
219
225
recast . visit ( ast , {
220
- visitNewExpression ( path ) {
221
- if (
222
- n . Identifier . check ( path . node . callee ) &&
223
- path . node . callee . name === 'AdminForth' &&
224
- path . node . arguments . length > 0 &&
225
- n . ObjectExpression . check ( path . node . arguments [ 0 ] )
226
- ) {
227
- const configObject = path . node . arguments [ 0 ] ;
228
-
229
- let customizationProp = configObject . properties . find (
230
- p => n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === 'customization'
231
- ) ;
232
-
233
- if ( ! customizationProp ) {
234
- const customizationObj = b . objectExpression ( [ ] ) ;
235
- customizationProp = b . objectProperty ( b . identifier ( 'customization' ) , customizationObj ) ;
236
- configObject . properties . push ( customizationProp ) ;
237
- console . log ( chalk . dim ( `Added missing 'customization' property.` ) ) ;
238
- }
239
-
240
- const customizationValue = customizationProp . value ;
241
- if ( ! n . ObjectExpression . check ( customizationValue ) ) return false ;
242
-
243
- let loginPageInjections = customizationValue . properties . find (
244
- p => n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === 'loginPageInjections'
245
- ) ;
246
-
247
- if ( ! loginPageInjections ) {
248
- const injectionsObj = b . objectExpression ( [ ] ) ;
249
- loginPageInjections = b . objectProperty ( b . identifier ( 'loginPageInjections' ) , injectionsObj ) ;
250
- customizationValue . properties . push ( loginPageInjections ) ;
251
- console . log ( chalk . dim ( `Added missing 'loginPageInjections'.` ) ) ;
252
- }
253
-
254
- const injectionsValue = loginPageInjections . value ;
255
- if ( ! n . ObjectExpression . check ( injectionsValue ) ) return false ;
256
-
257
- let underInputsProp = injectionsValue . properties . find (
258
- p => n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === 'underInputs'
259
- ) ;
260
-
261
- if ( underInputsProp ) {
262
- underInputsProp . value = b . stringLiteral ( componentPath ) ;
263
- console . log ( chalk . dim ( `Updated 'underInputs' to ${ componentPath } ` ) ) ;
264
- } else {
265
- injectionsValue . properties . push (
266
- b . objectProperty ( b . identifier ( 'underInputs' ) , b . stringLiteral ( componentPath ) )
267
- ) ;
268
- console . log ( chalk . dim ( `Added 'underInputs': ${ componentPath } ` ) ) ;
269
- }
270
-
271
- updated = true ;
272
- this . abort ( ) ;
226
+ visitNewExpression ( path ) {
227
+ if (
228
+ n . Identifier . check ( path . node . callee ) &&
229
+ path . node . callee . name === 'AdminForth' &&
230
+ path . node . arguments . length > 0 &&
231
+ n . ObjectExpression . check ( path . node . arguments [ 0 ] )
232
+ ) {
233
+ const configObject = path . node . arguments [ 0 ] ;
234
+
235
+ const getOrCreateProp = ( obj , name ) => {
236
+ let prop = obj . properties . find (
237
+ p => n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === name
238
+ ) ;
239
+ if ( ! prop ) {
240
+ const newObj = b . objectExpression ( [ ] ) ;
241
+ prop = b . objectProperty ( b . identifier ( name ) , newObj ) ;
242
+ obj . properties . push ( prop ) ;
243
+ console . log ( chalk . dim ( `Added missing '${ name } ' property.` ) ) ;
273
244
}
274
- return false ;
245
+ return prop . value ;
246
+ } ;
247
+
248
+ const customization = getOrCreateProp ( configObject , 'customization' ) ;
249
+ if ( ! n . ObjectExpression . check ( customization ) ) return false ;
250
+
251
+ const loginPageInjections = getOrCreateProp ( customization , 'loginPageInjections' ) ;
252
+ if ( ! n . ObjectExpression . check ( loginPageInjections ) ) return false ;
253
+
254
+ let underInputsProp = loginPageInjections . properties . find (
255
+ p => n . ObjectProperty . check ( p ) && n . Identifier . check ( p . key ) && p . key . name === 'underInputs'
256
+ ) ;
257
+
258
+ if ( underInputsProp ) {
259
+ const currentVal = underInputsProp . value ;
260
+ injectionLine = underInputsProp . loc ?. start . line ?? null ;
261
+ if ( n . StringLiteral . check ( currentVal ) ) {
262
+ if ( currentVal . value !== componentPath ) {
263
+ underInputsProp . value = b . arrayExpression ( [
264
+ b . stringLiteral ( currentVal . value ) ,
265
+ b . stringLiteral ( componentPath ) ,
266
+ ] ) ;
267
+ console . log ( chalk . dim ( `Converted 'underInputs' to array with existing + new path.` ) ) ;
268
+ } else {
269
+ console . log ( chalk . dim ( `Component path already present as string. Skipping.` ) ) ;
270
+ }
271
+ } else if ( n . ArrayExpression . check ( currentVal ) ) {
272
+ const exists = currentVal . elements . some (
273
+ el => n . StringLiteral . check ( el ) && el . value === componentPath
274
+ ) ;
275
+ if ( ! exists ) {
276
+ currentVal . elements . push ( b . stringLiteral ( componentPath ) ) ;
277
+ console . log ( chalk . dim ( `Appended new component path to existing 'underInputs' array.` ) ) ;
278
+ } else {
279
+ console . log ( chalk . dim ( `Component path already present in array. Skipping.` ) ) ;
280
+ }
281
+ } else {
282
+ console . warn ( chalk . yellow ( `⚠️ 'underInputs' is not a string or array. Skipping.` ) ) ;
283
+ return false ;
284
+ }
285
+ } else {
286
+ const newProperty = b . objectProperty (
287
+ b . identifier ( 'underInputs' ) ,
288
+ b . stringLiteral ( componentPath )
289
+ ) ;
290
+
291
+ if ( newProperty . loc ) {
292
+ console . log ( chalk . dim ( `Adding 'underInputs' at line: ${ newProperty . loc . start . line } ` ) ) ;
293
+ }
294
+
295
+ loginPageInjections . properties . push ( newProperty ) ;
296
+ console . log ( chalk . dim ( `Added 'underInputs': ${ componentPath } ` ) ) ;
297
+ }
298
+
299
+ updated = true ;
300
+ this . abort ( ) ;
275
301
}
302
+ return false ;
303
+ }
276
304
} ) ;
277
-
305
+
278
306
if ( ! updated ) {
279
- throw new Error ( `Could not find AdminForth configuration in file: ${ indexFilePath } ` ) ;
307
+ throw new Error ( `Could not find AdminForth configuration in file: ${ indexFilePath } ` ) ;
280
308
}
281
-
309
+
282
310
const outputCode = recast . print ( ast ) . code ;
283
311
await fs . writeFile ( indexFilePath , outputCode , 'utf-8' ) ;
284
- console . log ( chalk . green ( `✅ Successfully updated login injection in: ${ indexFilePath } ` ) ) ;
285
- }
312
+ console . log ( chalk . green ( `✅ Successfully updated login injection in: ${ indexFilePath } : ${ injectionLine } ` ) ) ;
313
+ }
286
314
287
315
288
316
export async function injectGlobalComponent ( indexFilePath , injectionType , componentPath ) {
@@ -293,7 +321,7 @@ export async function injectGlobalComponent(indexFilePath, injectionType, compon
293
321
} ) ;
294
322
295
323
let updated = false ;
296
-
324
+ let injectionLine = null ;
297
325
console . log ( JSON . stringify ( injectionType ) ) ;
298
326
recast . visit ( ast , {
299
327
visitNewExpression ( path ) {
@@ -315,7 +343,7 @@ export async function injectGlobalComponent(indexFilePath, injectionType, compon
315
343
configObject . properties . push ( customizationProp ) ;
316
344
console . log ( chalk . dim ( `Added missing 'customization' property.` ) ) ;
317
345
}
318
-
346
+
319
347
const customizationValue = customizationProp . value ;
320
348
if ( ! n . ObjectExpression . check ( customizationValue ) ) return false ;
321
349
@@ -338,7 +366,7 @@ export async function injectGlobalComponent(indexFilePath, injectionType, compon
338
366
) ;
339
367
if ( injectionProp ) {
340
368
const currentValue = injectionProp . value ;
341
-
369
+ injectionLine = injectionProp . loc ?. start . line ?? null ;
342
370
if ( n . ArrayExpression . check ( currentValue ) ) {
343
371
currentValue . elements . push ( b . stringLiteral ( componentPath ) ) ;
344
372
console . log ( chalk . dim ( `Added '${ componentPath } ' to existing array in '${ injectionType } '` ) ) ;
@@ -374,14 +402,15 @@ export async function injectGlobalComponent(indexFilePath, injectionType, compon
374
402
375
403
const outputCode = recast . print ( ast ) . code ;
376
404
await fs . writeFile ( indexFilePath , outputCode , 'utf-8' ) ;
377
- console . log ( chalk . green ( `✅ Successfully updated global injection '${ injectionType } ' in: ${ indexFilePath } ` ) ) ;
405
+ console . log ( chalk . green ( `✅ Successfully updated global injection '${ injectionType } ' in: ${ indexFilePath } : ${ injectionLine } ` ) ) ;
378
406
}
379
407
380
408
export async function updateCrudInjectionConfig ( resourceId , crudType , injectionPosition , componentPathForConfig , isThin ) {
381
409
const filePath = await findResourceFilePath ( resourceId ) ;
382
410
console . log ( chalk . dim ( `Attempting to update resource CRUD injection: ${ filePath } ` ) ) ;
383
411
384
412
let content ;
413
+ let injectionLine = null ;
385
414
try {
386
415
content = await fs . readFile ( filePath , 'utf-8' ) ;
387
416
} catch ( error ) {
@@ -439,7 +468,7 @@ export async function updateCrudInjectionConfig(resourceId, crudType, injectionP
439
468
) ;
440
469
pageInjections . properties . push ( crudProp ) ;
441
470
}
442
-
471
+ injectionLine = crudProp . loc ?. start . line ?? null ;
443
472
const crudValue = crudProp . value ;
444
473
if ( ! n . ObjectExpression . check ( crudValue ) ) return false ;
445
474
@@ -477,7 +506,7 @@ export async function updateCrudInjectionConfig(resourceId, crudType, injectionP
477
506
478
507
const outputCode = recast . print ( ast ) . code ;
479
508
await fs . writeFile ( filePath , outputCode , 'utf-8' ) ;
480
- console . log ( chalk . dim ( `✅ Successfully updated CRUD injection in resource file: ${ filePath } ` ) ) ;
509
+ console . log ( chalk . dim ( `✅ Successfully updated CRUD injection in resource file: ${ filePath } : ${ injectionLine } ` ) ) ;
481
510
482
511
} catch ( error ) {
483
512
console . error ( chalk . red ( `❌ Error processing resource file: ${ filePath } ` ) ) ;
0 commit comments