adminforth 1.2.10 → 1.2.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -104,8 +104,8 @@ class AdminForth {
104
104
  });
105
105
  }
106
106
  bundleNow(_b) {
107
- return __awaiter(this, arguments, void 0, function* ({ hotReload = false, verbose = false }) {
108
- yield this.codeInjector.bundleNow({ hotReload, verbose });
107
+ return __awaiter(this, arguments, void 0, function* ({ hotReload = false }) {
108
+ yield this.codeInjector.bundleNow({ hotReload });
109
109
  });
110
110
  }
111
111
  getUserByPk(pk) {
@@ -51,7 +51,7 @@ class CodeInjector {
51
51
  process.exit();
52
52
  }));
53
53
  }
54
- // async runShell({command, verbose = false}) {
54
+ // async runShell({ command }) {
55
55
  // console.log(`⚙️ Running shell ${command}...`);
56
56
  // console.time(`${command} done in`);
57
57
  // const { stdout: out, stderr: err } = await execAsync(command);
@@ -59,22 +59,20 @@ class CodeInjector {
59
59
  // console.log(`Command ${command} output:`, out, err);
60
60
  // }
61
61
  runNpmShell(_a) {
62
- return __awaiter(this, arguments, void 0, function* ({ command, verbose = false, cwd }) {
62
+ return __awaiter(this, arguments, void 0, function* ({ command, cwd }) {
63
63
  const nodeBinary = process.execPath; // Path to the Node.js binary running this script
64
64
  const npmPath = path.join(path.dirname(nodeBinary), 'npm'); // Path to the npm executable
65
65
  const env = Object.assign({ VITE_ADMINFORTH_PUBLIC_PATH: this.adminforth.config.baseUrl, FORCE_COLOR: '1' }, process.env);
66
- console.log(`⚙️ Running npm ${command}...`);
66
+ console.log(`⚙️ exec: npm ${command}...`);
67
67
  console.time(`npm ${command} done in`);
68
68
  const { stdout: out, stderr: err } = yield execAsync(`${nodeBinary} ${npmPath} ${command}`, {
69
69
  cwd,
70
70
  env,
71
71
  });
72
72
  console.timeEnd(`npm ${command} done in`);
73
- if (verbose) {
74
- console.log(`npm ${command} output:`, out);
75
- }
73
+ process.env.HEAVY_DEBUG && console.log(`🪲 npm ${command} output:`, out);
76
74
  if (err) {
77
- console.error(`npm ${command} errors/warnings:`, err);
75
+ process.env.HEAVY_DEBUG && console.error(`🪲npm ${command} errors/warnings:`, err);
78
76
  }
79
77
  });
80
78
  }
@@ -90,7 +88,7 @@ class CodeInjector {
90
88
  });
91
89
  }
92
90
  prepareSources(_a) {
93
- return __awaiter(this, arguments, void 0, function* ({ filesUpdated, verbose = false }) {
91
+ return __awaiter(this, arguments, void 0, function* ({ filesUpdated }) {
94
92
  var _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m;
95
93
  // check SPA_TMP_PATH exists and create if not
96
94
  try {
@@ -387,22 +385,18 @@ class CodeInjector {
387
385
  try {
388
386
  const existingHash = yield fs.promises.readFile(hashPath, 'utf-8');
389
387
  if (existingHash === fullHash) {
390
- console.log('Hashes match, skipping npm ci/install');
388
+ process.env.HEAVY_DEBUG && console.log(`🪲Hashes match, skipping npm ci/install, from file: ${existingHash}, actual: ${fullHash}`);
391
389
  return;
392
390
  }
393
391
  else {
394
- if (verbose) {
395
- console.log(`Hashes do not match: existing ${existingHash} new ${fullHash}, proceeding with npm ci/install`);
396
- }
392
+ process.env.HEAVY_DEBUG && console.log(`🪲 Hashes do not match: from file: ${existingHash} actual: ${fullHash}, proceeding with npm ci/install`);
397
393
  }
398
394
  }
399
395
  catch (e) {
400
396
  // ignore
401
- if (verbose) {
402
- console.log('Hash file does not exist, proceeding with npm ci/install');
403
- }
397
+ process.env.HEAVY_DEBUG && console.log('🪲Hash file does not exist, proceeding with npm ci/install');
404
398
  }
405
- yield this.runNpmShell({ command: 'ci', verbose, cwd: CodeInjector.SPA_TMP_PATH });
399
+ yield this.runNpmShell({ command: 'ci', cwd: CodeInjector.SPA_TMP_PATH });
406
400
  let customPackgeNames = [];
407
401
  if (usersPackage && usersLock) {
408
402
  customPackgeNames = [
@@ -423,7 +417,7 @@ class CodeInjector {
423
417
  });
424
418
  }
425
419
  watchForReprepare(_a) {
426
- return __awaiter(this, arguments, void 0, function* ({ verbose }) {
420
+ return __awaiter(this, arguments, void 0, function* ({}) {
427
421
  const spaPath = path.join(ADMIN_FORTH_ABSOLUTE_PATH, 'spa');
428
422
  // get list of all subdirectories in spa recursively
429
423
  const directories = [];
@@ -456,7 +450,7 @@ class CodeInjector {
456
450
  });
457
451
  }
458
452
  watchCustomComponentsForCopy(_a) {
459
- return __awaiter(this, arguments, void 0, function* ({ verbose, customComponentsDir, destination }) {
453
+ return __awaiter(this, arguments, void 0, function* ({ customComponentsDir, destination }) {
460
454
  if (!customComponentsDir) {
461
455
  return;
462
456
  }
@@ -465,9 +459,7 @@ class CodeInjector {
465
459
  yield fs.promises.access(customComponentsDir, fs.constants.F_OK);
466
460
  }
467
461
  catch (e) {
468
- if (verbose) {
469
- console.log(`Custom components dir ${customComponentsDir} does not exist, skipping watching`);
470
- }
462
+ process.env.HEAVY_DEBUG && console.log(`🪲Custom components dir ${customComponentsDir} does not exist, skipping watching`);
471
463
  return;
472
464
  }
473
465
  // get all subdirs
@@ -520,16 +512,15 @@ class CodeInjector {
520
512
  });
521
513
  }
522
514
  bundleNow(_a) {
523
- return __awaiter(this, arguments, void 0, function* ({ hotReload = false, verbose = false }) {
515
+ return __awaiter(this, arguments, void 0, function* ({ hotReload = false }) {
524
516
  console.log(`AdminForth bundling ${hotReload ? ' and listening for changes (🔥 Hotreload)' : ' (no hot reload)'}`);
525
517
  this.adminforth.runningHotReload = hotReload;
526
- yield this.prepareSources({ verbose });
518
+ yield this.prepareSources({});
527
519
  if (hotReload) {
528
520
  yield Promise.all([
529
- this.watchForReprepare({ verbose }),
521
+ this.watchForReprepare({}),
530
522
  ...Object.entries(this.srcFoldersToSync).map((_b) => __awaiter(this, [_b], void 0, function* ([src, dest]) {
531
523
  yield this.watchCustomComponentsForCopy({
532
- verbose,
533
524
  customComponentsDir: src,
534
525
  destination: dest,
535
526
  });
@@ -540,11 +531,11 @@ class CodeInjector {
540
531
  const cwd = CodeInjector.SPA_TMP_PATH;
541
532
  if (!hotReload) {
542
533
  // probably add option to build with tsh check (plain 'build')
543
- yield this.runNpmShell({ command: 'run build-only', verbose, cwd });
534
+ yield this.runNpmShell({ command: 'run build-only', cwd });
544
535
  }
545
536
  else {
546
537
  const command = 'run dev';
547
- console.log(`⚙️ Running npm ${command}...`);
538
+ console.log(`⚙️ spawn: npm ${command}...`);
548
539
  const nodeBinary = process.execPath;
549
540
  const npmPath = path.join(path.dirname(nodeBinary), 'npm');
550
541
  const env = Object.assign({ VITE_ADMINFORTH_PUBLIC_PATH: this.adminforth.config.baseUrl, FORCE_COLOR: '1' }, process.env);
@@ -339,15 +339,6 @@ export default class AdminForthRestAPI {
339
339
  item[col.name] = targetDataMap[item[col.name]];
340
340
  });
341
341
  })));
342
- for (const hook of listify((_t = (_s = resource.hooks) === null || _s === void 0 ? void 0 : _s[source]) === null || _t === void 0 ? void 0 : _t.afterDatasourceResponse)) {
343
- const resp = yield hook({ resource, response: data.data, adminUser });
344
- if (!resp || (!resp.ok && !resp.error)) {
345
- throw new Error(`Hook must return object with {ok: true} or { error: 'Error' } `);
346
- }
347
- if (resp.error) {
348
- return { error: resp.error };
349
- }
350
- }
351
342
  // remove all columns which are not defined in resources, or defined but backendOnly
352
343
  data.data.forEach((item) => {
353
344
  Object.keys(item).forEach((key) => {
@@ -359,6 +350,16 @@ export default class AdminForthRestAPI {
359
350
  data.data.forEach((item) => {
360
351
  item._label = resource.recordLabel(item);
361
352
  });
353
+ // only after adminforth made all post processing, give user ability to edit it
354
+ for (const hook of listify((_t = (_s = resource.hooks) === null || _s === void 0 ? void 0 : _s[source]) === null || _t === void 0 ? void 0 : _t.afterDatasourceResponse)) {
355
+ const resp = yield hook({ resource, response: data.data, adminUser });
356
+ if (!resp || (!resp.ok && !resp.error)) {
357
+ throw new Error(`Hook must return object with {ok: true} or { error: 'Error' } `);
358
+ }
359
+ if (resp.error) {
360
+ return { error: resp.error };
361
+ }
362
+ }
362
363
  return Object.assign(Object.assign({}, data), { options: resource === null || resource === void 0 ? void 0 : resource.options });
363
364
  }),
364
365
  });
@@ -28,8 +28,7 @@ export const useUserStore = defineStore('user', () => {
28
28
  await router.isReady();
29
29
  await coreStore.fetchMenuAndResource();
30
30
  setTimeout(() => {
31
- initFlowbite();
32
-
31
+ initFlowbite();
33
32
  });
34
33
  }
35
34
 
package/index.ts CHANGED
@@ -138,8 +138,8 @@ class AdminForth implements IAdminForth {
138
138
  // console.log('⚙️⚙️⚙️ Database discovery done', JSON.stringify(this.config.resources, null, 2));
139
139
  }
140
140
 
141
- async bundleNow({ hotReload=false, verbose=false }) {
142
- await this.codeInjector.bundleNow({ hotReload, verbose });
141
+ async bundleNow({ hotReload=false }) {
142
+ await this.codeInjector.bundleNow({ hotReload });
143
143
  }
144
144
 
145
145
  async getUserByPk(pk: string) {
@@ -62,7 +62,7 @@ class CodeInjector implements ICodeInjector {
62
62
 
63
63
  }
64
64
 
65
- // async runShell({command, verbose = false}) {
65
+ // async runShell({ command }) {
66
66
  // console.log(`⚙️ Running shell ${command}...`);
67
67
  // console.time(`${command} done in`);
68
68
  // const { stdout: out, stderr: err } = await execAsync(command);
@@ -70,7 +70,7 @@ class CodeInjector implements ICodeInjector {
70
70
  // console.log(`Command ${command} output:`, out, err);
71
71
  // }
72
72
 
73
- async runNpmShell({command, verbose = false, cwd}) {
73
+ async runNpmShell({command, cwd}) {
74
74
  const nodeBinary = process.execPath; // Path to the Node.js binary running this script
75
75
  const npmPath = path.join(path.dirname(nodeBinary), 'npm'); // Path to the npm executable
76
76
 
@@ -80,7 +80,7 @@ class CodeInjector implements ICodeInjector {
80
80
  ...process.env,
81
81
  };
82
82
 
83
- console.log(`⚙️ Running npm ${command}...`);
83
+ console.log(`⚙️ exec: npm ${command}...`);
84
84
  console.time(`npm ${command} done in`);
85
85
  const { stdout: out, stderr: err } = await execAsync(`${nodeBinary} ${npmPath} ${command}`, {
86
86
  cwd,
@@ -88,11 +88,9 @@ class CodeInjector implements ICodeInjector {
88
88
  });
89
89
  console.timeEnd(`npm ${command} done in`);
90
90
 
91
- if (verbose) {
92
- console.log(`npm ${command} output:`, out);
93
- }
91
+ process.env.HEAVY_DEBUG && console.log(`🪲 npm ${command} output:`, out);
94
92
  if (err) {
95
- console.error(`npm ${command} errors/warnings:`, err);
93
+ process.env.HEAVY_DEBUG && console.error(`🪲npm ${command} errors/warnings:`, err);
96
94
  }
97
95
  }
98
96
 
@@ -105,7 +103,7 @@ class CodeInjector implements ICodeInjector {
105
103
  }
106
104
  }
107
105
 
108
- async prepareSources({ filesUpdated, verbose = false }: { filesUpdated?: string[], verbose?: boolean }) {
106
+ async prepareSources({ filesUpdated }: { filesUpdated?: string[] }) {
109
107
  // check SPA_TMP_PATH exists and create if not
110
108
  try {
111
109
  await fs.promises.access(CodeInjector.SPA_TMP_PATH, fs.constants.F_OK);
@@ -386,7 +384,6 @@ class CodeInjector implements ICodeInjector {
386
384
  await fs.promises.writeFile(indexHtmlPath, indexHtmlContent);
387
385
 
388
386
 
389
-
390
387
  /* generate custom routes */
391
388
  const homepageMenuItem = this.adminforth.config.menu.find((mi)=>mi.homepage);
392
389
  let childrenHomePageMenuItem = this.adminforth.config.menu.find((mi)=>mi.children && mi.children?.find((mi)=>mi.homepage));
@@ -441,21 +438,17 @@ class CodeInjector implements ICodeInjector {
441
438
  try {
442
439
  const existingHash = await fs.promises.readFile(hashPath, 'utf-8');
443
440
  if (existingHash === fullHash) {
444
- console.log('Hashes match, skipping npm ci/install');
441
+ process.env.HEAVY_DEBUG && console.log(`🪲Hashes match, skipping npm ci/install, from file: ${existingHash}, actual: ${fullHash}`);
445
442
  return;
446
443
  } else {
447
- if (verbose) {
448
- console.log(`Hashes do not match: existing ${existingHash} new ${fullHash}, proceeding with npm ci/install`);
449
- }
444
+ process.env.HEAVY_DEBUG && console.log(`🪲 Hashes do not match: from file: ${existingHash} actual: ${fullHash}, proceeding with npm ci/install`);
450
445
  }
451
446
  } catch (e) {
452
447
  // ignore
453
- if (verbose) {
454
- console.log('Hash file does not exist, proceeding with npm ci/install');
455
- }
448
+ process.env.HEAVY_DEBUG && console.log('🪲Hash file does not exist, proceeding with npm ci/install');
456
449
  }
457
450
 
458
- await this.runNpmShell({command: 'ci', verbose, cwd: CodeInjector.SPA_TMP_PATH});
451
+ await this.runNpmShell({command: 'ci', cwd: CodeInjector.SPA_TMP_PATH});
459
452
 
460
453
  let customPackgeNames = [];
461
454
  if (usersPackage && usersLock) {
@@ -481,7 +474,7 @@ class CodeInjector implements ICodeInjector {
481
474
  }
482
475
  }
483
476
 
484
- async watchForReprepare({ verbose }) {
477
+ async watchForReprepare({}) {
485
478
  const spaPath = path.join(ADMIN_FORTH_ABSOLUTE_PATH, 'spa');
486
479
  // get list of all subdirectories in spa recursively
487
480
  const directories = [];
@@ -519,7 +512,7 @@ async watchForReprepare({ verbose }) {
519
512
  this.allWatchers.push(watcher);
520
513
  }
521
514
 
522
- async watchCustomComponentsForCopy({ verbose, customComponentsDir, destination }) {
515
+ async watchCustomComponentsForCopy({ customComponentsDir, destination }) {
523
516
  if (!customComponentsDir) {
524
517
  return;
525
518
  }
@@ -527,9 +520,7 @@ async watchForReprepare({ verbose }) {
527
520
  try {
528
521
  await fs.promises.access(customComponentsDir, fs.constants.F_OK);
529
522
  } catch (e) {
530
- if (verbose) {
531
- console.log(`Custom components dir ${customComponentsDir} does not exist, skipping watching`);
532
- }
523
+ process.env.HEAVY_DEBUG && console.log(`🪲Custom components dir ${customComponentsDir} does not exist, skipping watching`);
533
524
  return;
534
525
  }
535
526
 
@@ -594,19 +585,18 @@ async watchForReprepare({ verbose }) {
594
585
  this.allWatchers.push(watcher);
595
586
  }
596
587
 
597
- async bundleNow({hotReload = false, verbose = false}: {hotReload: boolean, verbose: boolean}) {
588
+ async bundleNow({ hotReload = false }: { hotReload: boolean }) {
598
589
  console.log(`AdminForth bundling ${hotReload ? ' and listening for changes (🔥 Hotreload)' : ' (no hot reload)'}`);
599
590
  this.adminforth.runningHotReload = hotReload;
600
591
 
601
- await this.prepareSources({ verbose });
592
+ await this.prepareSources({});
602
593
 
603
594
  if (hotReload) {
604
595
  await Promise.all([
605
- this.watchForReprepare({ verbose }),
596
+ this.watchForReprepare({}),
606
597
  ...Object.entries(this.srcFoldersToSync).map(async ([src, dest]) => {
607
598
 
608
599
  await this.watchCustomComponentsForCopy({
609
- verbose,
610
600
  customComponentsDir: src,
611
601
  destination: dest,
612
602
  });
@@ -620,10 +610,10 @@ async watchForReprepare({ verbose }) {
620
610
 
621
611
  if (!hotReload) {
622
612
  // probably add option to build with tsh check (plain 'build')
623
- await this.runNpmShell({command: 'run build-only', verbose, cwd});
613
+ await this.runNpmShell({command: 'run build-only', cwd});
624
614
  } else {
625
615
  const command = 'run dev';
626
- console.log(`⚙️ Running npm ${command}...`);
616
+ console.log(`⚙️ spawn: npm ${command}...`);
627
617
  const nodeBinary = process.execPath;
628
618
  const npmPath = path.join(path.dirname(nodeBinary), 'npm');
629
619
  const env = {
@@ -391,17 +391,6 @@ export default class AdminForthRestAPI {
391
391
  })
392
392
  );
393
393
 
394
- for (const hook of listify(resource.hooks?.[source]?.afterDatasourceResponse)) {
395
- const resp = await hook({ resource, response: data.data, adminUser });
396
- if (!resp || (!resp.ok && !resp.error)) {
397
- throw new Error(`Hook must return object with {ok: true} or { error: 'Error' } `);
398
- }
399
-
400
- if (resp.error) {
401
- return { error: resp.error };
402
- }
403
- }
404
-
405
394
  // remove all columns which are not defined in resources, or defined but backendOnly
406
395
  data.data.forEach((item) => {
407
396
  Object.keys(item).forEach((key) => {
@@ -415,6 +404,18 @@ export default class AdminForthRestAPI {
415
404
  item._label = resource.recordLabel(item);
416
405
  });
417
406
 
407
+ // only after adminforth made all post processing, give user ability to edit it
408
+ for (const hook of listify(resource.hooks?.[source]?.afterDatasourceResponse)) {
409
+ const resp = await hook({ resource, response: data.data, adminUser });
410
+ if (!resp || (!resp.ok && !resp.error)) {
411
+ throw new Error(`Hook must return object with {ok: true} or { error: 'Error' } `);
412
+ }
413
+
414
+ if (resp.error) {
415
+ return { error: resp.error };
416
+ }
417
+ }
418
+
418
419
  return {
419
420
  ...data,
420
421
  options: resource?.options,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "adminforth",
3
- "version": "1.2.10",
3
+ "version": "1.2.11",
4
4
  "description": "OpenSource Vue3 powered forth-generation admin panel",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -28,8 +28,7 @@ export const useUserStore = defineStore('user', () => {
28
28
  await router.isReady();
29
29
  await coreStore.fetchMenuAndResource();
30
30
  setTimeout(() => {
31
- initFlowbite();
32
-
31
+ initFlowbite();
33
32
  });
34
33
  }
35
34