@hed-hog/operations 0.0.3 → 0.0.285

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 (108) hide show
  1. package/README.md +122 -0
  2. package/dist/index.d.ts +1 -0
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +1 -0
  5. package/dist/index.js.map +1 -1
  6. package/dist/operations-data.controller.d.ts +139 -0
  7. package/dist/operations-data.controller.d.ts.map +1 -0
  8. package/dist/operations-data.controller.js +113 -0
  9. package/dist/operations-data.controller.js.map +1 -0
  10. package/dist/operations-growth.controller.d.ts +48 -0
  11. package/dist/operations-growth.controller.d.ts.map +1 -0
  12. package/dist/operations-growth.controller.js +90 -0
  13. package/dist/operations-growth.controller.js.map +1 -0
  14. package/dist/operations.module.d.ts.map +1 -1
  15. package/dist/operations.module.js +10 -4
  16. package/dist/operations.module.js.map +1 -1
  17. package/dist/operations.service.d.ts +178 -0
  18. package/dist/operations.service.d.ts.map +1 -0
  19. package/dist/operations.service.js +134 -0
  20. package/dist/operations.service.js.map +1 -0
  21. package/hedhog/data/menu.yaml +251 -132
  22. package/hedhog/data/operations_career_level.yaml +102 -0
  23. package/hedhog/data/operations_career_track.yaml +8 -0
  24. package/hedhog/data/operations_certification.yaml +38 -0
  25. package/hedhog/data/operations_evaluation_cycle.yaml +18 -0
  26. package/hedhog/data/operations_performance_criterion.yaml +48 -0
  27. package/hedhog/data/role.yaml +14 -7
  28. package/hedhog/data/route.yaml +143 -80
  29. package/hedhog/frontend/app/_components/allocation-calendar.tsx.ejs +56 -56
  30. package/hedhog/frontend/app/_components/kanban-board.tsx.ejs +83 -83
  31. package/hedhog/frontend/app/_components/operations-header.tsx.ejs +29 -29
  32. package/hedhog/frontend/app/_components/section-card.tsx.ejs +32 -32
  33. package/hedhog/frontend/app/_components/status-badge.tsx.ejs +15 -15
  34. package/hedhog/frontend/app/_components/timesheet-entry-dialog.tsx.ejs +142 -142
  35. package/hedhog/frontend/app/_lib/hooks/use-operations-data.ts.ejs +41 -41
  36. package/hedhog/frontend/app/_lib/hooks/use-operations-growth-data.ts.ejs +63 -0
  37. package/hedhog/frontend/app/_lib/mocks/allocations.mock.ts.ejs +74 -74
  38. package/hedhog/frontend/app/_lib/mocks/contracts.mock.ts.ejs +74 -74
  39. package/hedhog/frontend/app/_lib/mocks/operations-growth.mock.ts.ejs +824 -0
  40. package/hedhog/frontend/app/_lib/mocks/projects.mock.ts.ejs +60 -60
  41. package/hedhog/frontend/app/_lib/mocks/tasks.mock.ts.ejs +88 -88
  42. package/hedhog/frontend/app/_lib/mocks/timesheets.mock.ts.ejs +84 -84
  43. package/hedhog/frontend/app/_lib/mocks/users.mock.ts.ejs +67 -67
  44. package/hedhog/frontend/app/_lib/services/contracts.service.ts.ejs +10 -10
  45. package/hedhog/frontend/app/_lib/services/operations-growth.service.ts.ejs +31 -0
  46. package/hedhog/frontend/app/_lib/services/projects.service.ts.ejs +10 -10
  47. package/hedhog/frontend/app/_lib/services/tasks.service.ts.ejs +10 -10
  48. package/hedhog/frontend/app/_lib/services/timesheets.service.ts.ejs +10 -10
  49. package/hedhog/frontend/app/_lib/types/operations-growth.ts.ejs +209 -0
  50. package/hedhog/frontend/app/_lib/types/operations.ts.ejs +95 -95
  51. package/hedhog/frontend/app/_lib/utils/format.ts.ejs +25 -25
  52. package/hedhog/frontend/app/_lib/utils/growth.ts.ejs +62 -0
  53. package/hedhog/frontend/app/_lib/utils/metrics.ts.ejs +103 -103
  54. package/hedhog/frontend/app/_lib/utils/status.ts.ejs +80 -80
  55. package/hedhog/frontend/app/allocations/page.tsx.ejs +154 -99
  56. package/hedhog/frontend/app/approvals/page.tsx.ejs +147 -147
  57. package/hedhog/frontend/app/career/page.tsx.ejs +143 -0
  58. package/hedhog/frontend/app/certifications/page.tsx.ejs +201 -0
  59. package/hedhog/frontend/app/contracts/[id]/page.tsx.ejs +108 -108
  60. package/hedhog/frontend/app/contracts/page.tsx.ejs +180 -124
  61. package/hedhog/frontend/app/evaluations/page.tsx.ejs +277 -0
  62. package/hedhog/frontend/app/goals/page.tsx.ejs +170 -0
  63. package/hedhog/frontend/app/growth/page.tsx.ejs +288 -0
  64. package/hedhog/frontend/app/layout.tsx.ejs +9 -9
  65. package/hedhog/frontend/app/manager/page.tsx.ejs +175 -0
  66. package/hedhog/frontend/app/page.tsx.ejs +177 -177
  67. package/hedhog/frontend/app/projects/[id]/page.tsx.ejs +186 -186
  68. package/hedhog/frontend/app/projects/page.tsx.ejs +111 -111
  69. package/hedhog/frontend/app/rewards/page.tsx.ejs +195 -0
  70. package/hedhog/frontend/app/tasks/page.tsx.ejs +47 -47
  71. package/hedhog/frontend/app/timesheets/page.tsx.ejs +126 -126
  72. package/hedhog/frontend/messages/en.json +152 -142
  73. package/hedhog/frontend/messages/pt.json +152 -142
  74. package/hedhog/table/operations_allocation.yaml +52 -0
  75. package/hedhog/table/operations_calibration_item.yaml +61 -0
  76. package/hedhog/table/operations_calibration_session.yaml +25 -0
  77. package/hedhog/table/operations_career_level.yaml +75 -0
  78. package/hedhog/table/operations_career_track.yaml +21 -0
  79. package/hedhog/table/operations_certification.yaml +48 -0
  80. package/hedhog/table/operations_contract.yaml +57 -0
  81. package/hedhog/table/operations_employee.yaml +64 -0
  82. package/hedhog/table/operations_employee_certification.yaml +43 -0
  83. package/hedhog/table/operations_employee_connect.yaml +61 -0
  84. package/hedhog/table/operations_employee_evaluation.yaml +113 -0
  85. package/hedhog/table/operations_employee_evaluation_item.yaml +39 -0
  86. package/hedhog/table/operations_employee_profile.yaml +80 -0
  87. package/hedhog/table/operations_employee_skill_matrix.yaml +30 -0
  88. package/hedhog/table/operations_evaluation_cycle.yaml +31 -0
  89. package/hedhog/table/operations_goal.yaml +67 -0
  90. package/hedhog/table/operations_goal_progress.yaml +31 -0
  91. package/hedhog/table/operations_performance_criterion.yaml +29 -0
  92. package/hedhog/table/operations_project.yaml +66 -0
  93. package/hedhog/table/operations_promotion_readiness.yaml +49 -0
  94. package/hedhog/table/operations_promotion_recommendation.yaml +63 -0
  95. package/hedhog/table/operations_public_recognition.yaml +46 -0
  96. package/hedhog/table/operations_reward.yaml +100 -0
  97. package/hedhog/table/operations_score_event.yaml +81 -0
  98. package/hedhog/table/operations_task.yaml +60 -0
  99. package/hedhog/table/operations_timesheet.yaml +49 -0
  100. package/hedhog/table/operations_timesheet_entry.yaml +51 -0
  101. package/package.json +4 -4
  102. package/src/index.ts +2 -1
  103. package/src/language/en.json +8 -8
  104. package/src/language/pt.json +8 -8
  105. package/src/operations-data.controller.ts +54 -0
  106. package/src/operations-growth.controller.ts +44 -0
  107. package/src/operations.module.ts +21 -15
  108. package/src/operations.service.ts +137 -0
@@ -1,10 +1,10 @@
1
- import { projectsMock } from '../mocks/projects.mock';
2
-
3
- export const projectsService = {
4
- list() {
5
- return projectsMock;
6
- },
7
- getById(id: string) {
8
- return projectsMock.find((project) => project.id === id) ?? null;
9
- },
10
- };
1
+ import { projectsMock } from '../mocks/projects.mock';
2
+
3
+ export const projectsService = {
4
+ list() {
5
+ return projectsMock;
6
+ },
7
+ getById(id: string) {
8
+ return projectsMock.find((project) => project.id === id) ?? null;
9
+ },
10
+ };
@@ -1,10 +1,10 @@
1
- import { tasksMock } from '../mocks/tasks.mock';
2
-
3
- export const tasksService = {
4
- list() {
5
- return tasksMock;
6
- },
7
- byProject(projectId: string) {
8
- return tasksMock.filter((task) => task.projectId === projectId);
9
- },
10
- };
1
+ import { tasksMock } from '../mocks/tasks.mock';
2
+
3
+ export const tasksService = {
4
+ list() {
5
+ return tasksMock;
6
+ },
7
+ byProject(projectId: string) {
8
+ return tasksMock.filter((task) => task.projectId === projectId);
9
+ },
10
+ };
@@ -1,10 +1,10 @@
1
- import { timesheetsMock } from '../mocks/timesheets.mock';
2
-
3
- export const timesheetsService = {
4
- list() {
5
- return timesheetsMock;
6
- },
7
- byProject(projectId: string) {
8
- return timesheetsMock.filter((entry) => entry.projectId === projectId);
9
- },
10
- };
1
+ import { timesheetsMock } from '../mocks/timesheets.mock';
2
+
3
+ export const timesheetsService = {
4
+ list() {
5
+ return timesheetsMock;
6
+ },
7
+ byProject(projectId: string) {
8
+ return timesheetsMock.filter((entry) => entry.projectId === projectId);
9
+ },
10
+ };
@@ -0,0 +1,209 @@
1
+ export type GrowthPromotionStatus =
2
+ | 'not_ready'
3
+ | 'developing'
4
+ | 'eligible'
5
+ | 'recommended';
6
+
7
+ export type GrowthEvaluationStatus =
8
+ | 'draft'
9
+ | 'submitted'
10
+ | 'acknowledged'
11
+ | 'finalized';
12
+
13
+ export type GrowthGoalStatus =
14
+ | 'draft'
15
+ | 'active'
16
+ | 'at_risk'
17
+ | 'completed'
18
+ | 'canceled';
19
+
20
+ export type GrowthRewardStatus = 'planned' | 'granted' | 'canceled';
21
+
22
+ export type GrowthRewardType =
23
+ | 'financial'
24
+ | 'bonus'
25
+ | 'recognition'
26
+ | 'badge'
27
+ | 'gift'
28
+ | 'other';
29
+
30
+ export type GrowthRewardOrigin =
31
+ | 'goal'
32
+ | 'evaluation'
33
+ | 'certification'
34
+ | 'spot'
35
+ | 'manual'
36
+ | 'project';
37
+
38
+ export type GrowthCertificationStatus =
39
+ | 'planned'
40
+ | 'in_progress'
41
+ | 'achieved'
42
+ | 'expired';
43
+
44
+ export interface CareerTrackSummary {
45
+ id: string;
46
+ slug: string;
47
+ name: string;
48
+ description: string;
49
+ }
50
+
51
+ export interface CareerLevelPlan {
52
+ id: string;
53
+ trackId: string;
54
+ slug: string;
55
+ name: string;
56
+ code: string;
57
+ order: number;
58
+ minScore: number;
59
+ maxScore: number;
60
+ salaryMin: number;
61
+ salaryMax: number;
62
+ summaryCriteria: string[];
63
+ }
64
+
65
+ export interface EmployeeGrowthProfile {
66
+ employeeId: string;
67
+ trackId: string;
68
+ currentLevelId: string;
69
+ nextLevelId?: string;
70
+ currentScore: number;
71
+ nextLevelScore: number;
72
+ promotionProgress: number;
73
+ promotionStatus: GrowthPromotionStatus;
74
+ admissionDate: string;
75
+ story: string;
76
+ strengths: string[];
77
+ gaps: string[];
78
+ }
79
+
80
+ export interface EvaluationCycleSummary {
81
+ id: string;
82
+ name: string;
83
+ type: 'monthly' | 'quarterly' | 'semiannual' | 'annual' | 'custom';
84
+ startDate: string;
85
+ endDate: string;
86
+ status: 'draft' | 'active' | 'closed' | 'archived';
87
+ }
88
+
89
+ export interface PerformanceCriterionSummary {
90
+ id: string;
91
+ slug: string;
92
+ name: string;
93
+ weight: number;
94
+ }
95
+
96
+ export interface EvaluationCriterionScore {
97
+ criterionId: string;
98
+ rating: number;
99
+ appliedWeight: number;
100
+ generatedScore: number;
101
+ notes?: string;
102
+ }
103
+
104
+ export interface EmployeeEvaluationRecord {
105
+ id: string;
106
+ employeeId: string;
107
+ evaluatorId: string;
108
+ projectId?: string;
109
+ taskId?: string;
110
+ timesheetId?: string;
111
+ cycleId: string;
112
+ evaluationDate: string;
113
+ totalRating: number;
114
+ generatedScore: number;
115
+ publicComment: string;
116
+ privateComment: string;
117
+ status: GrowthEvaluationStatus;
118
+ criteria: EvaluationCriterionScore[];
119
+ }
120
+
121
+ export interface GoalRecord {
122
+ id: string;
123
+ employeeId?: string;
124
+ projectId?: string;
125
+ teamName?: string;
126
+ title: string;
127
+ description: string;
128
+ type: 'individual' | 'team' | 'cycle' | 'project';
129
+ periodLabel: string;
130
+ targetScore: number;
131
+ currentScore: number;
132
+ progressPercent: number;
133
+ completionRule: string;
134
+ status: GrowthGoalStatus;
135
+ }
136
+
137
+ export interface CertificationCatalogItem {
138
+ id: string;
139
+ slug: string;
140
+ name: string;
141
+ provider: string;
142
+ category: string;
143
+ defaultScore: number;
144
+ requiredLevelId?: string;
145
+ description: string;
146
+ }
147
+
148
+ export interface EmployeeCertificationRecord {
149
+ id: string;
150
+ employeeId: string;
151
+ certificationId: string;
152
+ obtainedAt?: string;
153
+ validUntil?: string;
154
+ grantedScore: number;
155
+ status: GrowthCertificationStatus;
156
+ }
157
+
158
+ export interface RewardRecord {
159
+ id: string;
160
+ employeeId: string;
161
+ type: GrowthRewardType;
162
+ origin: GrowthRewardOrigin;
163
+ amount?: number;
164
+ currency?: string;
165
+ relatedScore?: number;
166
+ description: string;
167
+ rewardDate: string;
168
+ status: GrowthRewardStatus;
169
+ }
170
+
171
+ export interface RecognitionRecord {
172
+ id: string;
173
+ employeeId: string;
174
+ authorId: string;
175
+ projectId?: string;
176
+ message: string;
177
+ relatedScore?: number;
178
+ date: string;
179
+ visible: boolean;
180
+ }
181
+
182
+ export interface ScoreEventRecord {
183
+ id: string;
184
+ employeeId: string;
185
+ sourceType:
186
+ | 'evaluation'
187
+ | 'certification'
188
+ | 'goal'
189
+ | 'recognition'
190
+ | 'manual_adjustment'
191
+ | 'project';
192
+ sourceId: string;
193
+ scoreDelta: number;
194
+ description: string;
195
+ referenceDate: string;
196
+ }
197
+
198
+ export interface PromotionRecommendationRecord {
199
+ id: string;
200
+ employeeId: string;
201
+ currentLevelId: string;
202
+ suggestedLevelId: string;
203
+ cycleId: string;
204
+ currentScore: number;
205
+ requiredScore: number;
206
+ eligible: boolean;
207
+ justification: string;
208
+ status: 'draft' | 'under_review' | 'approved' | 'rejected';
209
+ }
@@ -1,95 +1,95 @@
1
- export type ApprovalStatus = 'approved' | 'pending' | 'rejected';
2
-
3
- export type ProjectStatus =
4
- | 'planning'
5
- | 'active'
6
- | 'at-risk'
7
- | 'paused'
8
- | 'completed';
9
-
10
- export type ContractType = 'tm' | 'monthly' | 'fixed';
11
-
12
- export type ContractStatus = 'active' | 'draft' | 'expired' | 'renewal';
13
-
14
- export type TaskStatus =
15
- | 'backlog'
16
- | 'todo'
17
- | 'in-progress'
18
- | 'review'
19
- | 'done';
20
-
21
- export interface OperationsUser {
22
- id: string;
23
- name: string;
24
- role: string;
25
- seniority: string;
26
- department: string;
27
- hourlyRate: number;
28
- utilizationTarget: number;
29
- }
30
-
31
- export interface Contract {
32
- id: string;
33
- name: string;
34
- client: string;
35
- type: ContractType;
36
- startDate: string;
37
- endDate: string;
38
- hourlyRate: number;
39
- hourLimit: number;
40
- status: ContractStatus;
41
- billingRules: string[];
42
- sla: string;
43
- revisions: string[];
44
- linkedProjectIds: string[];
45
- }
46
-
47
- export interface Project {
48
- id: string;
49
- name: string;
50
- client: string;
51
- progress: number;
52
- status: ProjectStatus;
53
- teamMemberIds: string[];
54
- hoursLogged: number;
55
- startDate: string;
56
- endDate: string;
57
- description: string;
58
- contractId: string;
59
- budget: number;
60
- }
61
-
62
- export interface Task {
63
- id: string;
64
- title: string;
65
- projectId: string;
66
- projectName: string;
67
- status: TaskStatus;
68
- labels: string[];
69
- assignedUserId: string;
70
- dueDate: string;
71
- estimatedHours: number;
72
- description: string;
73
- }
74
-
75
- export interface TimesheetEntry {
76
- id: string;
77
- date: string;
78
- userId: string;
79
- projectId: string;
80
- taskId: string;
81
- hours: number;
82
- description: string;
83
- status: ApprovalStatus;
84
- }
85
-
86
- export interface Allocation {
87
- id: string;
88
- userId: string;
89
- role: string;
90
- projectId: string;
91
- weeklyHours: number;
92
- allocationPercent: number;
93
- startDate: string;
94
- endDate: string;
95
- }
1
+ export type ApprovalStatus = 'approved' | 'pending' | 'rejected';
2
+
3
+ export type ProjectStatus =
4
+ | 'planning'
5
+ | 'active'
6
+ | 'at-risk'
7
+ | 'paused'
8
+ | 'completed';
9
+
10
+ export type ContractType = 'tm' | 'monthly' | 'fixed';
11
+
12
+ export type ContractStatus = 'active' | 'draft' | 'expired' | 'renewal';
13
+
14
+ export type TaskStatus =
15
+ | 'backlog'
16
+ | 'todo'
17
+ | 'in-progress'
18
+ | 'review'
19
+ | 'done';
20
+
21
+ export interface OperationsUser {
22
+ id: string;
23
+ name: string;
24
+ role: string;
25
+ seniority: string;
26
+ department: string;
27
+ hourlyRate: number;
28
+ utilizationTarget: number;
29
+ }
30
+
31
+ export interface Contract {
32
+ id: string;
33
+ name: string;
34
+ client: string;
35
+ type: ContractType;
36
+ startDate: string;
37
+ endDate: string;
38
+ hourlyRate: number;
39
+ hourLimit: number;
40
+ status: ContractStatus;
41
+ billingRules: string[];
42
+ sla: string;
43
+ revisions: string[];
44
+ linkedProjectIds: string[];
45
+ }
46
+
47
+ export interface Project {
48
+ id: string;
49
+ name: string;
50
+ client: string;
51
+ progress: number;
52
+ status: ProjectStatus;
53
+ teamMemberIds: string[];
54
+ hoursLogged: number;
55
+ startDate: string;
56
+ endDate: string;
57
+ description: string;
58
+ contractId: string;
59
+ budget: number;
60
+ }
61
+
62
+ export interface Task {
63
+ id: string;
64
+ title: string;
65
+ projectId: string;
66
+ projectName: string;
67
+ status: TaskStatus;
68
+ labels: string[];
69
+ assignedUserId: string;
70
+ dueDate: string;
71
+ estimatedHours: number;
72
+ description: string;
73
+ }
74
+
75
+ export interface TimesheetEntry {
76
+ id: string;
77
+ date: string;
78
+ userId: string;
79
+ projectId: string;
80
+ taskId: string;
81
+ hours: number;
82
+ description: string;
83
+ status: ApprovalStatus;
84
+ }
85
+
86
+ export interface Allocation {
87
+ id: string;
88
+ userId: string;
89
+ role: string;
90
+ projectId: string;
91
+ weeklyHours: number;
92
+ allocationPercent: number;
93
+ startDate: string;
94
+ endDate: string;
95
+ }
@@ -1,25 +1,25 @@
1
- export const operationsCurrency = new Intl.NumberFormat('en-US', {
2
- style: 'currency',
3
- currency: 'USD',
4
- maximumFractionDigits: 0,
5
- });
6
-
7
- export function formatCurrency(value: number) {
8
- return operationsCurrency.format(value);
9
- }
10
-
11
- export function formatDate(value: string) {
12
- return new Date(`${value}T00:00:00`).toLocaleDateString('en-US', {
13
- month: 'short',
14
- day: 'numeric',
15
- year: 'numeric',
16
- });
17
- }
18
-
19
- export function formatPercent(value: number) {
20
- return `${value}%`;
21
- }
22
-
23
- export function formatHours(value: number) {
24
- return `${value.toFixed(1)}h`;
25
- }
1
+ export const operationsCurrency = new Intl.NumberFormat('en-US', {
2
+ style: 'currency',
3
+ currency: 'USD',
4
+ maximumFractionDigits: 0,
5
+ });
6
+
7
+ export function formatCurrency(value: number) {
8
+ return operationsCurrency.format(value);
9
+ }
10
+
11
+ export function formatDate(value: string) {
12
+ return new Date(`${value}T00:00:00`).toLocaleDateString('en-US', {
13
+ month: 'short',
14
+ day: 'numeric',
15
+ year: 'numeric',
16
+ });
17
+ }
18
+
19
+ export function formatPercent(value: number) {
20
+ return `${value}%`;
21
+ }
22
+
23
+ export function formatHours(value: number) {
24
+ return `${value.toFixed(1)}h`;
25
+ }
@@ -0,0 +1,62 @@
1
+ import type {
2
+ GrowthCertificationStatus,
3
+ GrowthEvaluationStatus,
4
+ GrowthGoalStatus,
5
+ GrowthPromotionStatus,
6
+ GrowthRewardStatus,
7
+ } from '../types/operations-growth';
8
+
9
+ export function getGrowthPromotionBadgeClasses(status: GrowthPromotionStatus) {
10
+ return {
11
+ not_ready: 'bg-slate-100 text-slate-700',
12
+ developing: 'bg-cyan-100 text-cyan-700',
13
+ eligible: 'bg-amber-100 text-amber-700',
14
+ recommended: 'bg-emerald-100 text-emerald-700',
15
+ }[status];
16
+ }
17
+
18
+ export function getGrowthGoalBadgeClasses(status: GrowthGoalStatus) {
19
+ return {
20
+ draft: 'bg-slate-100 text-slate-700',
21
+ active: 'bg-blue-100 text-blue-700',
22
+ at_risk: 'bg-orange-100 text-orange-700',
23
+ completed: 'bg-emerald-100 text-emerald-700',
24
+ canceled: 'bg-zinc-200 text-zinc-700',
25
+ }[status];
26
+ }
27
+
28
+ export function getGrowthEvaluationBadgeClasses(
29
+ status: GrowthEvaluationStatus
30
+ ) {
31
+ return {
32
+ draft: 'bg-slate-100 text-slate-700',
33
+ submitted: 'bg-blue-100 text-blue-700',
34
+ acknowledged: 'bg-violet-100 text-violet-700',
35
+ finalized: 'bg-emerald-100 text-emerald-700',
36
+ }[status];
37
+ }
38
+
39
+ export function getGrowthCertificationBadgeClasses(
40
+ status: GrowthCertificationStatus
41
+ ) {
42
+ return {
43
+ planned: 'bg-slate-100 text-slate-700',
44
+ in_progress: 'bg-amber-100 text-amber-700',
45
+ achieved: 'bg-emerald-100 text-emerald-700',
46
+ expired: 'bg-rose-100 text-rose-700',
47
+ }[status];
48
+ }
49
+
50
+ export function getGrowthRewardBadgeClasses(status: GrowthRewardStatus) {
51
+ return {
52
+ planned: 'bg-slate-100 text-slate-700',
53
+ granted: 'bg-emerald-100 text-emerald-700',
54
+ canceled: 'bg-rose-100 text-rose-700',
55
+ }[status];
56
+ }
57
+
58
+ export function humanizeGrowthStatus(value: string) {
59
+ return value
60
+ .replace(/_/g, ' ')
61
+ .replace(/\b\w/g, (char) => char.toUpperCase());
62
+ }