@hed-hog/operations 0.0.319 → 0.0.322

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 (38) hide show
  1. package/dist/controllers/operations-tasks.controller.d.ts +22 -0
  2. package/dist/controllers/operations-tasks.controller.d.ts.map +1 -1
  3. package/dist/controllers/operations-tasks.controller.js +37 -0
  4. package/dist/controllers/operations-tasks.controller.js.map +1 -1
  5. package/dist/dto/create-task.dto.d.ts.map +1 -1
  6. package/dist/dto/create-task.dto.js +0 -1
  7. package/dist/dto/create-task.dto.js.map +1 -1
  8. package/dist/dto/update-task.dto.d.ts.map +1 -1
  9. package/dist/dto/update-task.dto.js +0 -1
  10. package/dist/dto/update-task.dto.js.map +1 -1
  11. package/dist/operations.service.d.ts +22 -0
  12. package/dist/operations.service.d.ts.map +1 -1
  13. package/dist/operations.service.js +187 -132
  14. package/dist/operations.service.js.map +1 -1
  15. package/hedhog/data/operations_cost_type.yaml +95 -95
  16. package/hedhog/data/route.yaml +39 -0
  17. package/hedhog/frontend/app/_components/collaborator-costs-section.tsx.ejs +884 -884
  18. package/hedhog/frontend/app/_components/collaborator-details-screen.tsx.ejs +23 -23
  19. package/hedhog/frontend/app/_components/person-select-with-create.tsx.ejs +49 -22
  20. package/hedhog/frontend/app/_components/project-details-screen.tsx.ejs +2968 -624
  21. package/hedhog/frontend/app/_components/project-form-screen.tsx.ejs +62 -68
  22. package/hedhog/frontend/app/_components/task-file-attachments.tsx.ejs +388 -0
  23. package/hedhog/frontend/app/_lib/types.ts.ejs +179 -178
  24. package/hedhog/frontend/app/my-tasks/page.tsx.ejs +121 -11
  25. package/hedhog/frontend/app/projects/page.tsx.ejs +105 -22
  26. package/hedhog/frontend/app/reports/collaborators/page.tsx.ejs +771 -771
  27. package/hedhog/frontend/app/reports/projects/page.tsx.ejs +809 -809
  28. package/hedhog/frontend/messages/en.json +143 -2
  29. package/hedhog/frontend/messages/pt.json +143 -2
  30. package/hedhog/table/operations_task_file.yaml +23 -0
  31. package/package.json +5 -5
  32. package/src/controllers/operations-reports.controller.ts +32 -32
  33. package/src/controllers/operations-tasks.controller.ts +43 -9
  34. package/src/dto/create-task.dto.ts +0 -1
  35. package/src/dto/list-reports.dto.ts +51 -51
  36. package/src/dto/update-task.dto.ts +0 -1
  37. package/src/operations.module.ts +5 -5
  38. package/src/operations.service.ts +754 -632
@@ -723,7 +723,69 @@
723
723
  "loggedHours": "Logged hours",
724
724
  "loggedHoursDescription": "Total hours linked to this project.",
725
725
  "allocation": "Average allocation",
726
- "allocationDescription": "Average assignment allocation across linked collaborators."
726
+ "allocationDescription": "Average assignment allocation across linked collaborators.",
727
+ "lateTasks": "Late tasks",
728
+ "lateTasksDescription": "Open tasks with overdue deadlines.",
729
+ "weeklyVelocity": "Weekly velocity",
730
+ "weeklyVelocityDescription": "Recent or planned hours for the week.",
731
+ "projectHealth": "Project health",
732
+ "pendingTasks": "Pending tasks",
733
+ "pendingTasksDescription": "{overdue} overdue task(s) right now.",
734
+ "activeCollaborators": "Active collaborators",
735
+ "activeCollaboratorsDescription": "People with active allocation on this project."
736
+ },
737
+ "kpi": {
738
+ "indicator": "Indicator",
739
+ "subtitles": {
740
+ "health": "Visual blend of progress, pendencies, and allocation."
741
+ },
742
+ "trends": {
743
+ "hours": "{count} timesheet(s)",
744
+ "health": {
745
+ "good": "Positive",
746
+ "warning": "Warning",
747
+ "danger": "Critical"
748
+ },
749
+ "velocity": {
750
+ "active": "Moving",
751
+ "empty": "No recent pace"
752
+ },
753
+ "allocation": {
754
+ "good": "Balanced",
755
+ "warning": "High",
756
+ "critical": "Overloaded"
757
+ },
758
+ "tasks": {
759
+ "good": "No pendencies",
760
+ "warning": "Active backlog",
761
+ "critical": "{count} late"
762
+ },
763
+ "collaborators": {
764
+ "active": "Active team",
765
+ "empty": "No team"
766
+ }
767
+ }
768
+ },
769
+ "quickActions": {
770
+ "timesheet": "Timesheet",
771
+ "reports": "Reports",
772
+ "more": "More actions"
773
+ },
774
+ "executive": {
775
+ "team": "Team",
776
+ "activeTasks": "Active tasks",
777
+ "completedTasks": "Completed",
778
+ "fallbackDescription": "Track delivery, staffing, contract, and operational signals for this project.",
779
+ "membersCount": "{count} member(s)"
780
+ },
781
+ "breadcrumbTrail": {
782
+ "operations": "Operations",
783
+ "projects": "Projects"
784
+ },
785
+ "health": {
786
+ "good": "Healthy",
787
+ "warning": "Attention",
788
+ "danger": "Critical"
727
789
  },
728
790
  "sections": {
729
791
  "overview": "Overview",
@@ -752,14 +814,92 @@
752
814
  "deliveryHealthDescription": "Visual overview of team allocation and operational pace.",
753
815
  "quickRadar": "Quick radar",
754
816
  "quickRadarDescription": "Short-term decision signals.",
817
+ "timeline": "Operational timeline",
818
+ "timelineDescription": "Recent activity grouped by day, ready for filters and incremental loading.",
755
819
  "taskBoard": "Task board",
756
820
  "taskBoardDescription": "Kanban-style board with drag between columns and task side panel.",
757
821
  "archivedTasks": "Archived tasks",
758
822
  "archivedTasksDescription": "Review archived project tasks, open details, restore them, or delete them permanently."
759
823
  },
760
824
  "charts": {
825
+ "projectProgress": "Progress",
826
+ "burnup": "Burnup / progress",
827
+ "burnupDescription": "Accumulated logged hours against the planned operating pace.",
761
828
  "allocationByCollaborator": "Allocation by collaborator",
762
- "weeklyVelocity": "Weekly velocity"
829
+ "allocationDescription": "Capacity distribution across project collaborators.",
830
+ "weeklyVelocity": "Weekly velocity",
831
+ "weeklyVelocityDescription": "Recent pace of hours logged by the team.",
832
+ "taskDistribution": "Task distribution",
833
+ "taskDistributionDescription": "Task volume by board stage.",
834
+ "operationalHealth": "Operational health",
835
+ "operationalHealthDescription": "Visual score calculated from progress, pendencies, and allocation.",
836
+ "healthScore": "Operational score",
837
+ "start": "Start",
838
+ "current": "Current",
839
+ "emptyTitle": "Not enough data",
840
+ "emptyBurnup": "The burnup will appear once there is progress or logged hours.",
841
+ "emptyVelocity": "No weekly velocity has been returned for this project yet.",
842
+ "emptyAllocation": "Allocation will appear when collaborators are assigned.",
843
+ "emptyTasks": "Tasks will appear once the board has items."
844
+ },
845
+ "kanban": {
846
+ "items": "items",
847
+ "progress": "Progress",
848
+ "searchPlaceholder": "Search task, tag, assignee...",
849
+ "filters": "Filters",
850
+ "allPriorities": "All priorities",
851
+ "groupStatus": "Group by status",
852
+ "noEstimate": "No est.",
853
+ "emptyColumn": "No tasks in this column.",
854
+ "noFilteredTasks": "No tasks match the filters."
855
+ },
856
+ "timeline": {
857
+ "projectStarted": "Project started",
858
+ "projectStartedDescription": "{project} entered execution.",
859
+ "taskCreated": "Task created",
860
+ "taskCompleted": "Task completed",
861
+ "commentAdded": "Comment recorded",
862
+ "timesheetLogged": "Timesheet logged",
863
+ "timesheetLoggedDescription": "{count} timesheet(s), totaling {hours}.",
864
+ "approvalPending": "Approval pending",
865
+ "approvalPendingDescription": "{count} item(s) waiting for review.",
866
+ "completedTasks": "Completed tasks",
867
+ "completedTasksDescription": "{count} task(s) completed",
868
+ "pendingTimesheets": "Pending timesheets",
869
+ "pendingTimesheetsDescription": "{count} timesheet(s) waiting for review",
870
+ "targetDate": "Target date",
871
+ "targetDateDescription": "Operational project deadline.",
872
+ "loadMore": "Load more events",
873
+ "emptyTitle": "No activity to show",
874
+ "empty": "There is not enough operational activity yet to build a timeline.",
875
+ "filters": {
876
+ "all": "All events",
877
+ "task": "Tasks",
878
+ "status": "Status",
879
+ "timesheet": "Timesheets",
880
+ "approval": "Approvals",
881
+ "comment": "Comments"
882
+ },
883
+ "types": {
884
+ "task": "Task",
885
+ "timesheet": "Timesheet",
886
+ "approval": "Approval",
887
+ "comment": "Comment",
888
+ "status": "Status"
889
+ }
890
+ },
891
+ "teamPanel": {
892
+ "available": "Available",
893
+ "highAllocation": "High allocation",
894
+ "overload": "Overload",
895
+ "usedHours": "Used hours",
896
+ "availability": "Availability",
897
+ "overloadWarning": "{value}% above recommended capacity.",
898
+ "status": {
899
+ "available": "Available",
900
+ "high": "High load",
901
+ "overload": "Overload"
902
+ }
763
903
  },
764
904
  "quickRadar": {
765
905
  "activeAssignments": "Active assignments",
@@ -779,6 +919,7 @@
779
919
  "estimateLabel": "Estimate (h)",
780
920
  "tagsLabel": "Tags",
781
921
  "tagsPlaceholder": "planning, client, design (comma-separated)",
922
+ "attachmentsLabel": "Attachments",
782
923
  "saving": "Saving..."
783
924
  },
784
925
  "dialogs": {
@@ -721,7 +721,69 @@
721
721
  "loggedHours": "Horas lançadas",
722
722
  "loggedHoursDescription": "Total de horas vinculadas a este projeto.",
723
723
  "allocation": "Alocação média",
724
- "allocationDescription": "Média de alocação das atribuições do projeto."
724
+ "allocationDescription": "Média de alocação das atribuições do projeto.",
725
+ "lateTasks": "Tasks atrasadas",
726
+ "lateTasksDescription": "Tarefas abertas com prazo vencido.",
727
+ "weeklyVelocity": "Velocidade semanal",
728
+ "weeklyVelocityDescription": "Horas recentes ou planejadas na semana.",
729
+ "projectHealth": "Saúde do projeto",
730
+ "pendingTasks": "Tasks pendentes",
731
+ "pendingTasksDescription": "{overdue} tarefa(s) atrasada(s) no momento.",
732
+ "activeCollaborators": "Colaboradores ativos",
733
+ "activeCollaboratorsDescription": "Pessoas com alocação ativa neste projeto."
734
+ },
735
+ "kpi": {
736
+ "indicator": "Indicador",
737
+ "subtitles": {
738
+ "health": "Composição visual de progresso, pendências e alocação."
739
+ },
740
+ "trends": {
741
+ "hours": "{count} timesheet(s)",
742
+ "health": {
743
+ "good": "Positivo",
744
+ "warning": "Warning",
745
+ "danger": "Crítico"
746
+ },
747
+ "velocity": {
748
+ "active": "Em movimento",
749
+ "empty": "Sem ritmo recente"
750
+ },
751
+ "allocation": {
752
+ "good": "Equilibrada",
753
+ "warning": "Alta",
754
+ "critical": "Sobrecarga"
755
+ },
756
+ "tasks": {
757
+ "good": "Sem pendências",
758
+ "warning": "Backlog ativo",
759
+ "critical": "{count} atrasada(s)"
760
+ },
761
+ "collaborators": {
762
+ "active": "Equipe ativa",
763
+ "empty": "Sem equipe"
764
+ }
765
+ }
766
+ },
767
+ "quickActions": {
768
+ "timesheet": "Timesheet",
769
+ "reports": "Relatórios",
770
+ "more": "Mais ações"
771
+ },
772
+ "executive": {
773
+ "team": "Equipe",
774
+ "activeTasks": "Tasks ativas",
775
+ "completedTasks": "Concluídas",
776
+ "fallbackDescription": "Acompanhe entrega, equipe, contrato e sinais operacionais deste projeto.",
777
+ "membersCount": "{count} membro(s)"
778
+ },
779
+ "breadcrumbTrail": {
780
+ "operations": "Operations",
781
+ "projects": "Projetos"
782
+ },
783
+ "health": {
784
+ "good": "Saudável",
785
+ "warning": "Atenção",
786
+ "danger": "Crítico"
725
787
  },
726
788
  "sections": {
727
789
  "overview": "Visão geral",
@@ -750,14 +812,92 @@
750
812
  "deliveryHealthDescription": "Leitura visual de alocação e ritmo operacional da equipe.",
751
813
  "quickRadar": "Radar rápido",
752
814
  "quickRadarDescription": "Sinais para tomada de decisão no curto prazo.",
815
+ "timeline": "Timeline operacional",
816
+ "timelineDescription": "Atividade recente agrupada por dia, preparada para filtros e carregamento incremental.",
753
817
  "taskBoard": "Quadro de tarefas",
754
818
  "taskBoardDescription": "Board estilo Kanban com arraste entre colunas e detalhe lateral da tarefa.",
755
819
  "archivedTasks": "Tarefas arquivadas",
756
820
  "archivedTasksDescription": "Consulte tarefas arquivadas do projeto, veja detalhes, desarquive ou exclua definitivamente."
757
821
  },
758
822
  "charts": {
823
+ "projectProgress": "Progresso",
824
+ "burnup": "Burnup / progresso",
825
+ "burnupDescription": "Evolução acumulada de horas lançadas contra o ritmo planejado.",
759
826
  "allocationByCollaborator": "Alocação por colaborador",
760
- "weeklyVelocity": "Velocidade semanal"
827
+ "allocationDescription": "Distribuição de capacidade entre os colaboradores do projeto.",
828
+ "weeklyVelocity": "Velocidade semanal",
829
+ "weeklyVelocityDescription": "Ritmo recente de horas registradas pela equipe.",
830
+ "taskDistribution": "Distribuição de tasks",
831
+ "taskDistributionDescription": "Volume de tarefas por etapa do quadro.",
832
+ "operationalHealth": "Saúde operacional",
833
+ "operationalHealthDescription": "Score visual calculado a partir de progresso, pendências e alocação.",
834
+ "healthScore": "Score operacional",
835
+ "start": "Início",
836
+ "current": "Atual",
837
+ "emptyTitle": "Sem dados suficientes",
838
+ "emptyBurnup": "O burnup aparecerá quando houver progresso ou horas registradas.",
839
+ "emptyVelocity": "Ainda não há velocidade semanal retornada para este projeto.",
840
+ "emptyAllocation": "A alocação aparecerá quando colaboradores forem vinculados.",
841
+ "emptyTasks": "As tarefas aparecerão quando o quadro tiver itens."
842
+ },
843
+ "kanban": {
844
+ "items": "itens",
845
+ "progress": "Progresso",
846
+ "searchPlaceholder": "Buscar task, tag, responsável...",
847
+ "filters": "Filtros",
848
+ "allPriorities": "Todas prioridades",
849
+ "groupStatus": "Agrupar por status",
850
+ "noEstimate": "Sem estim.",
851
+ "emptyColumn": "Nenhuma task nesta coluna.",
852
+ "noFilteredTasks": "Nenhuma task corresponde aos filtros."
853
+ },
854
+ "timeline": {
855
+ "projectStarted": "Projeto iniciado",
856
+ "projectStartedDescription": "{project} entrou em execução.",
857
+ "taskCreated": "Task criada",
858
+ "taskCompleted": "Task concluída",
859
+ "commentAdded": "Comentário registrado",
860
+ "timesheetLogged": "Timesheet lançado",
861
+ "timesheetLoggedDescription": "{count} timesheet(s), totalizando {hours}.",
862
+ "approvalPending": "Aprovação pendente",
863
+ "approvalPendingDescription": "{count} item(ns) aguardando revisão.",
864
+ "completedTasks": "Tarefas concluídas",
865
+ "completedTasksDescription": "{count} tarefa(s) já concluída(s)",
866
+ "pendingTimesheets": "Timesheets pendentes",
867
+ "pendingTimesheetsDescription": "{count} timesheet(s) aguardando revisão",
868
+ "targetDate": "Data alvo",
869
+ "targetDateDescription": "Deadline operacional do projeto.",
870
+ "loadMore": "Carregar mais eventos",
871
+ "emptyTitle": "Sem atividade para exibir",
872
+ "empty": "Ainda não há eventos operacionais suficientes para montar uma timeline.",
873
+ "filters": {
874
+ "all": "Todos eventos",
875
+ "task": "Tasks",
876
+ "status": "Status",
877
+ "timesheet": "Timesheets",
878
+ "approval": "Aprovações",
879
+ "comment": "Comentários"
880
+ },
881
+ "types": {
882
+ "task": "Task",
883
+ "timesheet": "Timesheet",
884
+ "approval": "Aprovação",
885
+ "comment": "Comentário",
886
+ "status": "Status"
887
+ }
888
+ },
889
+ "teamPanel": {
890
+ "available": "Disponíveis",
891
+ "highAllocation": "Alocação alta",
892
+ "overload": "Sobrecarga",
893
+ "usedHours": "Horas utilizadas",
894
+ "availability": "Disponibilidade",
895
+ "overloadWarning": "{value}% acima da capacidade recomendada.",
896
+ "status": {
897
+ "available": "Disponível",
898
+ "high": "Alta carga",
899
+ "overload": "Sobrecarga"
900
+ }
761
901
  },
762
902
  "quickRadar": {
763
903
  "activeAssignments": "Atribuições ativas",
@@ -777,6 +917,7 @@
777
917
  "estimateLabel": "Estimativa (h)",
778
918
  "tagsLabel": "Etiquetas",
779
919
  "tagsPlaceholder": "planejamento, cliente, design (separadas por vírgula)",
920
+ "attachmentsLabel": "Anexos",
780
921
  "saving": "Salvando..."
781
922
  },
782
923
  "dialogs": {
@@ -0,0 +1,23 @@
1
+ columns:
2
+ - type: pk
3
+ - name: operations_task_id
4
+ type: fk
5
+ references:
6
+ table: operations_task
7
+ column: id
8
+ onDelete: CASCADE
9
+ onUpdate: CASCADE
10
+ - name: file_id
11
+ type: fk
12
+ isNullable: true
13
+ references:
14
+ table: file
15
+ column: id
16
+ onDelete: SET NULL
17
+ onUpdate: CASCADE
18
+ - type: created_at
19
+ - type: updated_at
20
+
21
+ indices:
22
+ - columns: [operations_task_id]
23
+ - columns: [file_id]
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hed-hog/operations",
3
- "version": "0.0.319",
3
+ "version": "0.0.322",
4
4
  "main": "dist/index.js",
5
5
  "types": "dist/index.d.ts",
6
6
  "dependencies": {
@@ -10,12 +10,12 @@
10
10
  "@nestjs/jwt": "^11",
11
11
  "@nestjs/mapped-types": "*",
12
12
  "@hed-hog/api": "0.0.8",
13
+ "@hed-hog/api-locale": "0.0.14",
13
14
  "@hed-hog/api-prisma": "0.0.6",
15
+ "@hed-hog/api-types": "0.0.1",
14
16
  "@hed-hog/api-pagination": "0.0.7",
15
- "@hed-hog/api-locale": "0.0.14",
16
- "@hed-hog/core": "0.0.319",
17
- "@hed-hog/contact": "0.0.319",
18
- "@hed-hog/api-types": "0.0.1"
17
+ "@hed-hog/core": "0.0.322",
18
+ "@hed-hog/contact": "0.0.322"
19
19
  },
20
20
  "exports": {
21
21
  ".": {
@@ -1,32 +1,32 @@
1
- import { Role, User } from '@hed-hog/api';
2
- import { Controller, Get, Query } from '@nestjs/common';
3
- import {
4
- ListCollaboratorsReportDto,
5
- ListProjectsReportDto,
6
- } from '../dto/list-reports.dto';
7
- import { OperationsService } from '../operations.service';
8
-
9
- @Role()
10
- @Controller('operations')
11
- export class OperationsReportsController {
12
- constructor(private readonly operationsService: OperationsService) {}
13
-
14
- @Get('reports/projects')
15
- getProjectsReport(@User() user, @Query() filters: ListProjectsReportDto) {
16
- return this.operationsService.getProjectsReport(
17
- Number(user?.id || 0),
18
- filters,
19
- );
20
- }
21
-
22
- @Get('reports/collaborators')
23
- getCollaboratorsReport(
24
- @User() user,
25
- @Query() filters: ListCollaboratorsReportDto,
26
- ) {
27
- return this.operationsService.getCollaboratorsReport(
28
- Number(user?.id || 0),
29
- filters,
30
- );
31
- }
32
- }
1
+ import { Role, User } from '@hed-hog/api';
2
+ import { Controller, Get, Query } from '@nestjs/common';
3
+ import {
4
+ ListCollaboratorsReportDto,
5
+ ListProjectsReportDto,
6
+ } from '../dto/list-reports.dto';
7
+ import { OperationsService } from '../operations.service';
8
+
9
+ @Role()
10
+ @Controller('operations')
11
+ export class OperationsReportsController {
12
+ constructor(private readonly operationsService: OperationsService) {}
13
+
14
+ @Get('reports/projects')
15
+ getProjectsReport(@User() user, @Query() filters: ListProjectsReportDto) {
16
+ return this.operationsService.getProjectsReport(
17
+ Number(user?.id || 0),
18
+ filters,
19
+ );
20
+ }
21
+
22
+ @Get('reports/collaborators')
23
+ getCollaboratorsReport(
24
+ @User() user,
25
+ @Query() filters: ListCollaboratorsReportDto,
26
+ ) {
27
+ return this.operationsService.getCollaboratorsReport(
28
+ Number(user?.id || 0),
29
+ filters,
30
+ );
31
+ }
32
+ }
@@ -1,15 +1,18 @@
1
1
  import { Role, User } from '@hed-hog/api';
2
2
  import {
3
- Body,
4
- Controller,
5
- Delete,
6
- Get,
7
- Param,
8
- ParseIntPipe,
9
- Patch,
10
- Post,
11
- Query,
3
+ Body,
4
+ Controller,
5
+ Delete,
6
+ Get,
7
+ Param,
8
+ ParseIntPipe,
9
+ Patch,
10
+ Post,
11
+ Query,
12
+ UploadedFile,
13
+ UseInterceptors,
12
14
  } from '@nestjs/common';
15
+ import { FileInterceptor } from '@nestjs/platform-express';
13
16
  import { CreateOperationsTaskDto } from '../dto/create-task.dto';
14
17
  import { ListMyTasksDto } from '../dto/list-my-tasks.dto';
15
18
  import { ListOperationsTasksDto } from '../dto/list-tasks.dto';
@@ -80,4 +83,35 @@ export class OperationsTasksController {
80
83
  permanent === 'true'
81
84
  );
82
85
  }
86
+
87
+ @Get('tasks/:id/files')
88
+ listTaskFiles(
89
+ @User() user,
90
+ @Param('id', ParseIntPipe) id: number,
91
+ ) {
92
+ return this.operationsService.listTaskFiles(Number(user?.id || 0), id);
93
+ }
94
+
95
+ @Post('tasks/:id/files')
96
+ @UseInterceptors(FileInterceptor('file'))
97
+ addTaskFile(
98
+ @User() user,
99
+ @Param('id', ParseIntPipe) id: number,
100
+ @UploadedFile() file: MulterFile,
101
+ ) {
102
+ return this.operationsService.addTaskFile(Number(user?.id || 0), id, file);
103
+ }
104
+
105
+ @Delete('tasks/:id/files/:fileRelationId')
106
+ removeTaskFile(
107
+ @User() user,
108
+ @Param('id', ParseIntPipe) id: number,
109
+ @Param('fileRelationId', ParseIntPipe) fileRelationId: number,
110
+ ) {
111
+ return this.operationsService.removeTaskFile(
112
+ Number(user?.id || 0),
113
+ id,
114
+ fileRelationId
115
+ );
116
+ }
83
117
  }
@@ -36,7 +36,6 @@ export class CreateOperationsTaskDto {
36
36
 
37
37
  @IsOptional()
38
38
  @IsString({ message: 'description must be a string' })
39
- @MaxLength(2000, { message: 'description must have at most 2000 characters' })
40
39
  description?: string;
41
40
 
42
41
  @IsOptional()
@@ -1,51 +1,51 @@
1
- import { IsIn, IsOptional, IsString } from 'class-validator';
2
-
3
- export const OPERATIONS_REPORT_SCENARIOS = [
4
- 'base',
5
- 'growth',
6
- 'conservative',
7
- ] as const;
8
-
9
- export class ListProjectsReportDto {
10
- @IsOptional()
11
- @IsString()
12
- from?: string;
13
-
14
- @IsOptional()
15
- @IsString()
16
- to?: string;
17
-
18
- @IsOptional()
19
- @IsString()
20
- status?: string;
21
-
22
- @IsOptional()
23
- @IsString()
24
- client?: string;
25
-
26
- @IsOptional()
27
- @IsIn(OPERATIONS_REPORT_SCENARIOS)
28
- scenario?: string;
29
- }
30
-
31
- export class ListCollaboratorsReportDto {
32
- @IsOptional()
33
- @IsString()
34
- from?: string;
35
-
36
- @IsOptional()
37
- @IsString()
38
- to?: string;
39
-
40
- @IsOptional()
41
- @IsString()
42
- department?: string;
43
-
44
- @IsOptional()
45
- @IsString()
46
- contractType?: string;
47
-
48
- @IsOptional()
49
- @IsIn(OPERATIONS_REPORT_SCENARIOS)
50
- scenario?: string;
51
- }
1
+ import { IsIn, IsOptional, IsString } from 'class-validator';
2
+
3
+ export const OPERATIONS_REPORT_SCENARIOS = [
4
+ 'base',
5
+ 'growth',
6
+ 'conservative',
7
+ ] as const;
8
+
9
+ export class ListProjectsReportDto {
10
+ @IsOptional()
11
+ @IsString()
12
+ from?: string;
13
+
14
+ @IsOptional()
15
+ @IsString()
16
+ to?: string;
17
+
18
+ @IsOptional()
19
+ @IsString()
20
+ status?: string;
21
+
22
+ @IsOptional()
23
+ @IsString()
24
+ client?: string;
25
+
26
+ @IsOptional()
27
+ @IsIn(OPERATIONS_REPORT_SCENARIOS)
28
+ scenario?: string;
29
+ }
30
+
31
+ export class ListCollaboratorsReportDto {
32
+ @IsOptional()
33
+ @IsString()
34
+ from?: string;
35
+
36
+ @IsOptional()
37
+ @IsString()
38
+ to?: string;
39
+
40
+ @IsOptional()
41
+ @IsString()
42
+ department?: string;
43
+
44
+ @IsOptional()
45
+ @IsString()
46
+ contractType?: string;
47
+
48
+ @IsOptional()
49
+ @IsIn(OPERATIONS_REPORT_SCENARIOS)
50
+ scenario?: string;
51
+ }
@@ -38,7 +38,6 @@ export class UpdateOperationsTaskDto {
38
38
 
39
39
  @IsOptional()
40
40
  @IsString({ message: 'description must be a string' })
41
- @MaxLength(2000, { message: 'description must have at most 2000 characters' })
42
41
  description?: string;
43
42
 
44
43
  @IsOptional()
@@ -9,9 +9,9 @@ import { OperationsCollaboratorCostsController } from './controllers/operations-
9
9
  import { OperationsCollaboratorsController } from './controllers/operations-collaborators.controller';
10
10
  import { OperationsContractsController } from './controllers/operations-contracts.controller';
11
11
  import { OperationsOrgStructureController } from './controllers/operations-org-structure.controller';
12
- import { OperationsProjectsController } from './controllers/operations-projects.controller';
13
- import { OperationsReportsController } from './controllers/operations-reports.controller';
14
- import { OperationsTasksController } from './controllers/operations-tasks.controller';
12
+ import { OperationsProjectsController } from './controllers/operations-projects.controller';
13
+ import { OperationsReportsController } from './controllers/operations-reports.controller';
14
+ import { OperationsTasksController } from './controllers/operations-tasks.controller';
15
15
  import { OperationsTimesheetsController } from './controllers/operations-timesheets.controller';
16
16
  import { OperationsController } from './operations.controller';
17
17
  import { OperationsProposalSubscriber } from './operations.proposal.subscriber';
@@ -34,8 +34,8 @@ import { OperationsAccessService } from './services/shared/operations-access.ser
34
34
  OperationsCollaboratorsController,
35
35
  OperationsCollaboratorCostsController,
36
36
  OperationsOrgStructureController,
37
- OperationsProjectsController,
38
- OperationsReportsController,
37
+ OperationsProjectsController,
38
+ OperationsReportsController,
39
39
  OperationsTasksController,
40
40
  OperationsContractsController,
41
41
  OperationsTimesheetsController,