@hed-hog/core 0.0.298 → 0.0.300

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 (123) hide show
  1. package/dist/dashboard/dashboard/dashboard.controller.d.ts +9 -0
  2. package/dist/dashboard/dashboard/dashboard.controller.d.ts.map +1 -1
  3. package/dist/dashboard/dashboard/dashboard.service.d.ts +9 -0
  4. package/dist/dashboard/dashboard/dashboard.service.d.ts.map +1 -1
  5. package/dist/dashboard/dashboard-component/dashboard-component.controller.d.ts +14 -1
  6. package/dist/dashboard/dashboard-component/dashboard-component.controller.d.ts.map +1 -1
  7. package/dist/dashboard/dashboard-component/dashboard-component.controller.js +28 -3
  8. package/dist/dashboard/dashboard-component/dashboard-component.controller.js.map +1 -1
  9. package/dist/dashboard/dashboard-component/dashboard-component.service.d.ts +22 -1
  10. package/dist/dashboard/dashboard-component/dashboard-component.service.d.ts.map +1 -1
  11. package/dist/dashboard/dashboard-component/dashboard-component.service.js +185 -35
  12. package/dist/dashboard/dashboard-component/dashboard-component.service.js.map +1 -1
  13. package/dist/dashboard/dashboard-component/dto/create.dto.d.ts +1 -0
  14. package/dist/dashboard/dashboard-component/dto/create.dto.d.ts.map +1 -1
  15. package/dist/dashboard/dashboard-component/dto/create.dto.js +5 -0
  16. package/dist/dashboard/dashboard-component/dto/create.dto.js.map +1 -1
  17. package/dist/dashboard/dashboard-component/dto/update.dto.d.ts +1 -0
  18. package/dist/dashboard/dashboard-component/dto/update.dto.d.ts.map +1 -1
  19. package/dist/dashboard/dashboard-component/dto/update.dto.js +5 -0
  20. package/dist/dashboard/dashboard-component/dto/update.dto.js.map +1 -1
  21. package/dist/dashboard/dashboard-component-role/dashboard-component-role.controller.d.ts +1 -0
  22. package/dist/dashboard/dashboard-component-role/dashboard-component-role.controller.d.ts.map +1 -1
  23. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.d.ts +1 -0
  24. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.d.ts.map +1 -1
  25. package/dist/dashboard/dashboard-core/dashboard-core.controller.d.ts +72 -1
  26. package/dist/dashboard/dashboard-core/dashboard-core.controller.d.ts.map +1 -1
  27. package/dist/dashboard/dashboard-core/dashboard-core.controller.js +111 -0
  28. package/dist/dashboard/dashboard-core/dashboard-core.controller.js.map +1 -1
  29. package/dist/dashboard/dashboard-core/dashboard-core.service.d.ts +76 -1
  30. package/dist/dashboard/dashboard-core/dashboard-core.service.d.ts.map +1 -1
  31. package/dist/dashboard/dashboard-core/dashboard-core.service.js +614 -23
  32. package/dist/dashboard/dashboard-core/dashboard-core.service.js.map +1 -1
  33. package/dist/dashboard/dashboard-item/dashboard-item.controller.d.ts +3 -0
  34. package/dist/dashboard/dashboard-item/dashboard-item.controller.d.ts.map +1 -1
  35. package/dist/dashboard/dashboard-item/dashboard-item.service.d.ts +3 -0
  36. package/dist/dashboard/dashboard-item/dashboard-item.service.d.ts.map +1 -1
  37. package/dist/dashboard/dashboard-role/dashboard-role.controller.d.ts +2 -0
  38. package/dist/dashboard/dashboard-role/dashboard-role.controller.d.ts.map +1 -1
  39. package/dist/dashboard/dashboard-role/dashboard-role.service.d.ts +2 -0
  40. package/dist/dashboard/dashboard-role/dashboard-role.service.d.ts.map +1 -1
  41. package/hedhog/data/dashboard.yaml +12 -6
  42. package/hedhog/data/dashboard_component_role.yaml +66 -0
  43. package/hedhog/data/dashboard_item.yaml +1 -1
  44. package/hedhog/data/dashboard_role.yaml +2 -8
  45. package/hedhog/data/route.yaml +84 -0
  46. package/hedhog/frontend/app/dashboard/[slug]/dashboard-content.tsx.ejs +457 -135
  47. package/hedhog/frontend/app/dashboard/[slug]/types.ts.ejs +3 -0
  48. package/hedhog/frontend/app/dashboard/[slug]/widget-renderer.tsx.ejs +365 -28
  49. package/hedhog/frontend/app/dashboard/components/add-widget-selector-dialog.tsx.ejs +376 -247
  50. package/hedhog/frontend/app/dashboard/components/draggable-grid.tsx.ejs +64 -18
  51. package/hedhog/frontend/app/dashboard/dashboard-home-tabs.tsx.ejs +1389 -0
  52. package/hedhog/frontend/app/dashboard/dashboard.css.ejs +37 -0
  53. package/hedhog/frontend/app/dashboard/management/page.tsx.ejs +1 -1
  54. package/hedhog/frontend/app/dashboard/management/tabs/components-tab.tsx.ejs +6 -6
  55. package/hedhog/frontend/app/dashboard/management/tabs/dashboards-tab.tsx.ejs +8 -8
  56. package/hedhog/frontend/app/dashboard/management/tabs/items-tab.tsx.ejs +3 -3
  57. package/hedhog/frontend/app/dashboard/page.tsx.ejs +3 -25
  58. package/hedhog/frontend/messages/en.json +115 -2
  59. package/hedhog/frontend/messages/pt.json +114 -1
  60. package/hedhog/frontend/public/dashboard-previews/.gitkeep +12 -0
  61. package/hedhog/frontend/public/dashboard-previews/account-security.png +0 -0
  62. package/hedhog/frontend/public/dashboard-previews/active-users-card.png +0 -0
  63. package/hedhog/frontend/public/dashboard-previews/activity-timeline.png +0 -0
  64. package/hedhog/frontend/public/dashboard-previews/cash-balance-kpi.png +0 -0
  65. package/hedhog/frontend/public/dashboard-previews/cash-flow-chart.png +0 -0
  66. package/hedhog/frontend/public/dashboard-previews/default-kpi.png +0 -0
  67. package/hedhog/frontend/public/dashboard-previews/email-notifications.png +0 -0
  68. package/hedhog/frontend/public/dashboard-previews/financial-alerts.png +0 -0
  69. package/hedhog/frontend/public/dashboard-previews/login-history-chart.png +0 -0
  70. package/hedhog/frontend/public/dashboard-previews/mail-sent-card.png +0 -0
  71. package/hedhog/frontend/public/dashboard-previews/mail-sent-chart.png +0 -0
  72. package/hedhog/frontend/public/dashboard-previews/menus-card.png +0 -0
  73. package/hedhog/frontend/public/dashboard-previews/payable-30d-kpi.png +0 -0
  74. package/hedhog/frontend/public/dashboard-previews/permissions-card.png +0 -0
  75. package/hedhog/frontend/public/dashboard-previews/permissions-chart.png +0 -0
  76. package/hedhog/frontend/public/dashboard-previews/profile-card.png +0 -0
  77. package/hedhog/frontend/public/dashboard-previews/receivable-30d-kpi.png +0 -0
  78. package/hedhog/frontend/public/dashboard-previews/routes-card.png +0 -0
  79. package/hedhog/frontend/public/dashboard-previews/session-activity-chart.png +0 -0
  80. package/hedhog/frontend/public/dashboard-previews/sessions-today-card.png +0 -0
  81. package/hedhog/frontend/public/dashboard-previews/stat-access-level.png +0 -0
  82. package/hedhog/frontend/public/dashboard-previews/stat-actions-today.png +0 -0
  83. package/hedhog/frontend/public/dashboard-previews/stat-consecutive-days.png +0 -0
  84. package/hedhog/frontend/public/dashboard-previews/stat-online-time.png +0 -0
  85. package/hedhog/frontend/public/dashboard-previews/upcoming-payable.png +0 -0
  86. package/hedhog/frontend/public/dashboard-previews/upcoming-receivable.png +0 -0
  87. package/hedhog/frontend/public/dashboard-previews/user-growth-chart.png +0 -0
  88. package/hedhog/frontend/public/dashboard-previews/user-roles.png +0 -0
  89. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/account-security.tsx.ejs +34 -30
  90. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/active-users-card.tsx.ejs +2 -2
  91. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/activity-timeline.tsx.ejs +1 -1
  92. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/email-notifications.tsx.ejs +1 -1
  93. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/locale-config.tsx.ejs +1 -1
  94. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/login-history-chart.tsx.ejs +1 -1
  95. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/mail-config.tsx.ejs +1 -1
  96. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/mail-sent-card.tsx.ejs +2 -2
  97. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/mail-sent-chart.tsx.ejs +1 -1
  98. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/menus-card.tsx.ejs +2 -2
  99. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/oauth-config.tsx.ejs +1 -1
  100. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/permissions-card.tsx.ejs +2 -2
  101. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/permissions-chart.tsx.ejs +1 -1
  102. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/profile-card.tsx.ejs +1 -1
  103. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/routes-card.tsx.ejs +2 -2
  104. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/session-activity-chart.tsx.ejs +1 -1
  105. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/sessions-today-card.tsx.ejs +2 -2
  106. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/stat-access-level.tsx.ejs +1 -1
  107. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/stat-actions-today.tsx.ejs +1 -1
  108. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/stat-consecutive-days.tsx.ejs +1 -1
  109. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/stat-online-time.tsx.ejs +1 -1
  110. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/storage-config.tsx.ejs +1 -1
  111. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/theme-config.tsx.ejs +1 -1
  112. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/user-growth-chart.tsx.ejs +1 -1
  113. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/user-roles.tsx.ejs +1 -1
  114. package/hedhog/frontend/{app/dashboard/components/widgets → widgets}/user-sessions.tsx.ejs +2 -2
  115. package/hedhog/table/dashboard.yaml +6 -0
  116. package/hedhog/table/dashboard_component.yaml +7 -0
  117. package/package.json +5 -5
  118. package/src/dashboard/dashboard-component/dashboard-component.controller.ts +51 -14
  119. package/src/dashboard/dashboard-component/dashboard-component.service.ts +254 -43
  120. package/src/dashboard/dashboard-component/dto/create.dto.ts +4 -0
  121. package/src/dashboard/dashboard-component/dto/update.dto.ts +4 -0
  122. package/src/dashboard/dashboard-core/dashboard-core.controller.ts +112 -1
  123. package/src/dashboard/dashboard-core/dashboard-core.service.ts +782 -24
@@ -2,15 +2,24 @@ import { getLocaleText } from '@hed-hog/api-locale';
2
2
  import { PaginationDTO, PaginationService } from '@hed-hog/api-pagination';
3
3
  import { PrismaService } from '@hed-hog/api-prisma';
4
4
  import {
5
- forwardRef,
6
- Inject,
7
- Injectable,
8
- NotFoundException
5
+ BadRequestException,
6
+ ForbiddenException,
7
+ forwardRef,
8
+ Inject,
9
+ Injectable,
10
+ NotFoundException,
9
11
  } from '@nestjs/common';
12
+ import { existsSync, promises as fs } from 'fs';
13
+ import { join, resolve } from 'path';
10
14
  import {
11
- CreateDashboardComponentDTO,
12
- UpdateDashboardComponentDTO,
15
+ CreateDashboardComponentDTO,
16
+ UpdateDashboardComponentDTO,
13
17
  } from './dto';
18
+ type DashboardComponentUserPagination = PaginationDTO & {
19
+ librarySlug?: string;
20
+ exclude?: string;
21
+ };
22
+
14
23
  @Injectable()
15
24
  export class DashboardComponentService {
16
25
  constructor(
@@ -21,7 +30,7 @@ export class DashboardComponentService {
21
30
  ) {}
22
31
 
23
32
  async getAllComponents(paginationParams: PaginationDTO) {
24
- const fields = ['slug']
33
+ const fields = ['slug', 'library_slug']
25
34
  const OR = this.prismaService.createInsensitiveSearch(
26
35
  fields,
27
36
  paginationParams,
@@ -75,7 +84,10 @@ export class DashboardComponentService {
75
84
  );
76
85
  }
77
86
 
78
- async getAllComponentsByUserRole(paginationParams: PaginationDTO, userId: number) {
87
+ async getAllComponentsByUserRole(
88
+ paginationParams: DashboardComponentUserPagination,
89
+ userId: number,
90
+ ) {
79
91
  const userRoles = await this.prismaService.role_user.findMany({
80
92
  where: { user_id: userId },
81
93
  select: { role_id: true },
@@ -83,7 +95,64 @@ export class DashboardComponentService {
83
95
 
84
96
  const userRoleIds = userRoles.map((ur) => ur.role_id);
85
97
 
86
- const fields = ['slug']
98
+ if (userRoleIds.length === 0) {
99
+ const emptyResult = await this.paginationService.paginate(
100
+ this.prismaService.dashboard_component,
101
+ paginationParams,
102
+ {
103
+ include: {
104
+ dashboard_component_locale: {
105
+ include: {
106
+ locale: true,
107
+ },
108
+ },
109
+ dashboard_component_role: {
110
+ include: {
111
+ role: {
112
+ include: {
113
+ role_locale: {
114
+ include: {
115
+ locale: true,
116
+ },
117
+ },
118
+ },
119
+ },
120
+ },
121
+ },
122
+ },
123
+ where: {
124
+ id: -1,
125
+ },
126
+ orderBy: {
127
+ created_at: 'desc',
128
+ },
129
+ },
130
+ 'dashboardComponent',
131
+ );
132
+
133
+ return {
134
+ ...emptyResult,
135
+ modules: [],
136
+ };
137
+ }
138
+
139
+ const requestedLibrarySlug = paginationParams.librarySlug?.trim();
140
+ const excludedComponents = (paginationParams.exclude ?? '')
141
+ .split(',')
142
+ .map((value) => value.trim())
143
+ .filter(Boolean)
144
+ .map((value) => {
145
+ const slugParts = value.split('.').filter(Boolean);
146
+ const baseSlug = slugParts[slugParts.length - 1] || value;
147
+ const librarySlug = slugParts.length > 1 ? slugParts[0] : undefined;
148
+
149
+ return {
150
+ slug: baseSlug,
151
+ ...(librarySlug ? { library_slug: librarySlug } : {}),
152
+ };
153
+ });
154
+
155
+ const fields = ['slug', 'library_slug'];
87
156
  const OR = this.prismaService.createInsensitiveSearch(
88
157
  fields,
89
158
  paginationParams,
@@ -102,52 +171,87 @@ export class DashboardComponentService {
102
171
  });
103
172
  }
104
173
 
105
- return this.paginationService.paginate(
106
- this.prismaService.dashboard_component,
107
- paginationParams,
174
+ const baseFilters = [
108
175
  {
109
- include: {
110
- dashboard_component_locale: {
111
- include: {
112
- locale: true,
176
+ dashboard_component_role: {
177
+ some: {
178
+ role_id: {
179
+ in: userRoleIds,
113
180
  },
114
181
  },
115
- dashboard_component_role: {
116
- include: {
117
- role: {
118
- include: {
119
- role_locale: {
120
- include: {
121
- locale: true,
182
+ },
183
+ },
184
+ ...(OR.length > 0 ? [{ OR }] : []),
185
+ ...(excludedComponents.length > 0
186
+ ? [
187
+ {
188
+ NOT: {
189
+ OR: excludedComponents,
190
+ },
191
+ },
192
+ ]
193
+ : []),
194
+ ];
195
+
196
+ const [paginatedResult, modules] = await Promise.all([
197
+ this.paginationService.paginate(
198
+ this.prismaService.dashboard_component,
199
+ paginationParams,
200
+ {
201
+ include: {
202
+ dashboard_component_locale: {
203
+ include: {
204
+ locale: true,
205
+ },
206
+ },
207
+ dashboard_component_role: {
208
+ include: {
209
+ role: {
210
+ include: {
211
+ role_locale: {
212
+ include: {
213
+ locale: true,
214
+ },
122
215
  },
123
216
  },
124
217
  },
125
218
  },
126
219
  },
127
220
  },
221
+ where: {
222
+ AND: [
223
+ ...baseFilters,
224
+ ...(requestedLibrarySlug
225
+ ? [{ library_slug: requestedLibrarySlug }]
226
+ : []),
227
+ ],
228
+ },
229
+ orderBy: {
230
+ created_at: 'desc',
231
+ },
128
232
  },
233
+ 'dashboardComponent',
234
+ ),
235
+ this.prismaService.dashboard_component.findMany({
129
236
  where: {
130
- AND: [
131
- {
132
- dashboard_component_role: {
133
- some: {
134
- role_id: {
135
- in: userRoleIds,
136
- },
137
- },
138
- },
139
- },
140
- {
141
- OR,
142
- },
143
- ],
237
+ AND: baseFilters,
144
238
  },
239
+ select: {
240
+ library_slug: true,
241
+ },
242
+ distinct: ['library_slug'],
145
243
  orderBy: {
146
- created_at: 'desc',
244
+ library_slug: 'asc',
147
245
  },
148
- },
149
- 'dashboardComponent',
150
- );
246
+ }),
247
+ ]);
248
+
249
+ return {
250
+ ...paginatedResult,
251
+ modules: modules
252
+ .map((component) => component.library_slug)
253
+ .filter((value): value is string => Boolean(value)),
254
+ };
151
255
  }
152
256
 
153
257
  async getComponent(id: number, locale: string, userId?: number) {
@@ -221,9 +325,15 @@ export class DashboardComponentService {
221
325
  }
222
326
 
223
327
  async createComponent(data: CreateDashboardComponentDTO, locale: string) {
328
+ const normalized = this.normalizeComponentIdentity(
329
+ data.slug,
330
+ data.library_slug,
331
+ );
332
+
224
333
  const component = await this.prismaService.dashboard_component.create({
225
334
  data: {
226
- slug: data.slug,
335
+ slug: normalized.slug,
336
+ library_slug: normalized.library_slug,
227
337
  min_width: data.min_width,
228
338
  max_width: data.max_width,
229
339
  min_height: data.min_height,
@@ -257,10 +367,18 @@ export class DashboardComponentService {
257
367
  }
258
368
 
259
369
  async updateComponent(id: number, data: UpdateDashboardComponentDTO, locale: string) {
370
+ const normalized = data.slug
371
+ ? this.normalizeComponentIdentity(data.slug, data.library_slug)
372
+ : {
373
+ slug: undefined,
374
+ library_slug: data.library_slug,
375
+ };
376
+
260
377
  await this.prismaService.dashboard_component.update({
261
378
  where: { id },
262
379
  data: {
263
- slug: data.slug,
380
+ slug: normalized.slug,
381
+ library_slug: normalized.library_slug,
264
382
  min_width: data.min_width,
265
383
  max_width: data.max_width,
266
384
  min_height: data.min_height,
@@ -312,4 +430,97 @@ export class DashboardComponentService {
312
430
  where: { id },
313
431
  });
314
432
  }
433
+
434
+ private normalizeComponentIdentity(slug: string, librarySlug?: string | null) {
435
+ const slugParts = slug.split('.').filter(Boolean);
436
+ const baseSlug =
437
+ slugParts.length > 0 ? slugParts[slugParts.length - 1]! : slug;
438
+ const resolvedLibrarySlug =
439
+ librarySlug || (slugParts.length > 1 ? slugParts[0]! : 'core');
440
+
441
+ return {
442
+ slug: baseSlug,
443
+ library_slug: resolvedLibrarySlug,
444
+ };
445
+ }
446
+
447
+ private buildWidgetAssetSlug(slug: string, librarySlug?: string | null) {
448
+ const normalized = this.normalizeComponentIdentity(slug, librarySlug);
449
+
450
+ return normalized.slug;
451
+ }
452
+
453
+ private resolvePreviewDirectory(): string {
454
+ const cwd = process.cwd();
455
+ const candidates = [
456
+ resolve(cwd, 'libraries/core/hedhog/frontend/public/dashboard-previews'),
457
+ resolve(cwd, '../libraries/core/hedhog/frontend/public/dashboard-previews'),
458
+ resolve(cwd, '../../libraries/core/hedhog/frontend/public/dashboard-previews'),
459
+ ];
460
+
461
+ for (const candidate of candidates) {
462
+ const parentDirectory = resolve(candidate, '..');
463
+ if (existsSync(parentDirectory)) {
464
+ return candidate;
465
+ }
466
+ }
467
+
468
+ return candidates[0];
469
+ }
470
+
471
+ async savePreview(id: number, file: MulterFile, locale: string) {
472
+ const isDevelopment = process.env.NODE_ENV !== 'production';
473
+ if (!isDevelopment) {
474
+ throw new ForbiddenException(
475
+ getLocaleText('dashboardPreviewOnlyInDevelopment', locale, 'Preview capture is only available in development environment'),
476
+ );
477
+ }
478
+
479
+ if (!file || !file.buffer) {
480
+ throw new BadRequestException(
481
+ getLocaleText('dashboardPreviewFileRequired', locale, 'Preview image file is required'),
482
+ );
483
+ }
484
+
485
+ if (!file.mimetype?.startsWith('image/')) {
486
+ throw new BadRequestException(
487
+ getLocaleText('dashboardPreviewInvalidFileType', locale, 'Preview file must be an image'),
488
+ );
489
+ }
490
+
491
+ const component = await this.prismaService.dashboard_component.findUnique({
492
+ where: { id },
493
+ select: {
494
+ id: true,
495
+ slug: true,
496
+ library_slug: true,
497
+ },
498
+ });
499
+
500
+ if (!component) {
501
+ throw new NotFoundException(
502
+ getLocaleText('dashboardComponentNotFound', locale, 'Dashboard component not found'),
503
+ );
504
+ }
505
+
506
+ const previewDirectory = this.resolvePreviewDirectory();
507
+ await fs.mkdir(previewDirectory, { recursive: true });
508
+
509
+ const assetSlug = this.buildWidgetAssetSlug(
510
+ component.slug,
511
+ component.library_slug,
512
+ );
513
+ const fileName = `${assetSlug}.png`;
514
+ const outputPath = join(previewDirectory, fileName);
515
+ await fs.writeFile(outputPath, file.buffer);
516
+
517
+ return {
518
+ success: true,
519
+ componentId: component.id,
520
+ slug: component.slug,
521
+ library_slug: component.library_slug,
522
+ fileName,
523
+ relativeUrl: `/libraries/${component.library_slug}/dashboard-previews/${fileName}`,
524
+ };
525
+ }
315
526
  }
@@ -5,6 +5,10 @@ export class CreateDTO {
5
5
  @IsString({ message: (args) => getLocaleText('validation.stringRequired', args.value) })
6
6
  slug: string;
7
7
 
8
+ @IsOptional()
9
+ @IsString({ message: (args) => getLocaleText('validation.stringRequired', args.value) })
10
+ library_slug?: string;
11
+
8
12
  @IsOptional()
9
13
  @IsNumber({}, { message: (args) => getLocaleText('validation.numberRequired', args.value) })
10
14
  min_width?: number;
@@ -6,6 +6,10 @@ export class UpdateDTO {
6
6
  @IsString({ message: (args) => getLocaleText('validation.stringRequired', args.value) })
7
7
  slug?: string;
8
8
 
9
+ @IsOptional()
10
+ @IsString({ message: (args) => getLocaleText('validation.stringRequired', args.value) })
11
+ library_slug?: string;
12
+
9
13
  @IsOptional()
10
14
  @IsNumber({}, { message: (args) => getLocaleText('validation.numberRequired', args.value) })
11
15
  min_width?: number;
@@ -1,6 +1,16 @@
1
1
  import { Role, User } from '@hed-hog/api';
2
2
  import { Locale } from '@hed-hog/api-locale';
3
- import { Body, Controller, Delete, Get, Param, Post } from '@nestjs/common';
3
+ import {
4
+ Body,
5
+ Controller,
6
+ Delete,
7
+ Get,
8
+ Param,
9
+ ParseIntPipe,
10
+ Patch,
11
+ Post,
12
+ Query,
13
+ } from '@nestjs/common';
4
14
  import { DashboardCoreService } from './dashboard-core.service';
5
15
 
6
16
  @Role()
@@ -43,6 +53,107 @@ export class DashboardCoreController {
43
53
  return this.dashboardCoreService.getUserDashboards(user.id, locale);
44
54
  }
45
55
 
56
+ @Get('templates')
57
+ getAvailableTemplates(@User() user, @Locale() locale: string) {
58
+ return this.dashboardCoreService.getAvailableTemplates(user.id, locale);
59
+ }
60
+
61
+ @Post('dashboard')
62
+ createUserDashboard(
63
+ @User() user,
64
+ @Body() body: { name?: string; slug?: string; icon?: string | null; templateSlug?: string },
65
+ @Locale() locale: string,
66
+ ) {
67
+ return this.dashboardCoreService.createUserDashboard(user.id, body, locale);
68
+ }
69
+
70
+ @Patch('dashboard/:slug')
71
+ renameUserDashboard(
72
+ @User() user,
73
+ @Param('slug') slug: string,
74
+ @Body() body: { name?: string; icon?: string | null },
75
+ @Locale() locale: string,
76
+ ) {
77
+ return this.dashboardCoreService.renameUserDashboard(
78
+ user.id,
79
+ slug,
80
+ body,
81
+ locale,
82
+ );
83
+ }
84
+
85
+ @Post('dashboard/:slug/home')
86
+ setHomeDashboard(
87
+ @User() user,
88
+ @Param('slug') slug: string,
89
+ @Locale() locale: string,
90
+ ) {
91
+ return this.dashboardCoreService.setHomeDashboard(user.id, slug, locale);
92
+ }
93
+
94
+ @Get('dashboard/:slug/shares')
95
+ getDashboardShares(
96
+ @User() user,
97
+ @Param('slug') slug: string,
98
+ @Locale() locale: string,
99
+ ) {
100
+ return this.dashboardCoreService.getDashboardShares(user.id, slug, locale);
101
+ }
102
+
103
+ @Get('shareable-users/:slug')
104
+ getShareableUsers(
105
+ @User() user,
106
+ @Param('slug') slug: string,
107
+ @Query('search') search: string | undefined,
108
+ @Locale() locale: string,
109
+ ) {
110
+ return this.dashboardCoreService.getShareableUsers(
111
+ user.id,
112
+ slug,
113
+ search,
114
+ locale,
115
+ );
116
+ }
117
+
118
+ @Post('dashboard/:slug/share')
119
+ shareDashboard(
120
+ @User() user,
121
+ @Param('slug') slug: string,
122
+ @Body() body: { userId?: number },
123
+ @Locale() locale: string,
124
+ ) {
125
+ return this.dashboardCoreService.shareDashboard(
126
+ user.id,
127
+ slug,
128
+ body.userId,
129
+ locale,
130
+ );
131
+ }
132
+
133
+ @Delete('dashboard/:slug/share/:sharedUserId')
134
+ revokeDashboardShare(
135
+ @User() user,
136
+ @Param('slug') slug: string,
137
+ @Param('sharedUserId', ParseIntPipe) sharedUserId: number,
138
+ @Locale() locale: string,
139
+ ) {
140
+ return this.dashboardCoreService.revokeDashboardShare(
141
+ user.id,
142
+ slug,
143
+ sharedUserId,
144
+ locale,
145
+ );
146
+ }
147
+
148
+ @Delete('dashboard/:slug')
149
+ removeUserDashboard(
150
+ @User() user,
151
+ @Param('slug') slug: string,
152
+ @Locale() locale: string,
153
+ ) {
154
+ return this.dashboardCoreService.removeUserDashboard(user.id, slug, locale);
155
+ }
156
+
46
157
  @Get('access/:slug')
47
158
  checkAccess(@User() user, @Param('slug') slug: string, @Locale() locale: string) {
48
159
  return this.dashboardCoreService.checkDashboardAccess(user.id, slug, locale);