@things-factory/kpi 9.0.31 → 9.0.32

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 (324) hide show
  1. package/README.md +1 -2
  2. package/client/charts/kpi-boxplot-chart.ts +182 -42
  3. package/client/charts/kpi-radar-chart.ts +9 -9
  4. package/client/pages/kpi/kpi-list-page.ts +196 -32
  5. package/client/pages/kpi/kpi-overview.ts +9 -11
  6. package/client/pages/kpi/kpi-tree-page.ts +409 -0
  7. package/client/pages/kpi/kpi-view.ts +187 -0
  8. package/client/pages/kpi-dashboard/cards/kpi-level1-card.ts +1 -1
  9. package/client/pages/kpi-dashboard/cards/kpi-level2-comparison.ts +1 -1
  10. package/client/pages/kpi-dashboard/cards/kpi-level3-comparison.ts +1 -1
  11. package/client/pages/kpi-dashboard/components/kpi-left-panel.ts +198 -160
  12. package/client/pages/kpi-dashboard/components/kpi-map-panel.ts +133 -0
  13. package/client/pages/kpi-dashboard/components/kpi-region-popup.ts +3 -2
  14. package/client/pages/kpi-dashboard/kpi-dashboard-map.ts +4 -3
  15. package/client/pages/kpi-dashboard/kpi-dashboard.ts +28 -30
  16. package/client/pages/kpi-history/kpi-history-list-page.ts +11 -11
  17. package/client/pages/kpi-metric/kpi-metric-list-page.ts +10 -2
  18. package/client/pages/kpi-metric-value/kpi-metric-value-editor-page.ts +7 -7
  19. package/client/pages/kpi-metric-value/kpi-metric-value-importer.ts +2 -2
  20. package/client/pages/kpi-metric-value/kpi-metric-value-list-page.ts +16 -8
  21. package/client/pages/kpi-metric-value/kpi-metric-value-manual-entry-form.ts +5 -5
  22. package/client/pages/kpi-statistic/kpi-statistic-editor-page.ts +1 -2
  23. package/client/pages/kpi-statistic/kpi-statistic-list-page.ts +10 -2
  24. package/client/pages/kpi-value/kpi-value-editor-page.ts +11 -7
  25. package/client/pages/kpi-value/kpi-value-list-page.ts +31 -7
  26. package/client/route.ts +2 -9
  27. package/design-entities.md +8 -12
  28. package/dist-client/charts/kpi-boxplot-chart.d.ts +2 -0
  29. package/dist-client/charts/kpi-boxplot-chart.js +168 -42
  30. package/dist-client/charts/kpi-boxplot-chart.js.map +1 -1
  31. package/dist-client/charts/kpi-radar-chart.js +9 -9
  32. package/dist-client/charts/kpi-radar-chart.js.map +1 -1
  33. package/dist-client/pages/kpi/kpi-list-page.d.ts +19 -3
  34. package/dist-client/pages/kpi/kpi-list-page.js +188 -32
  35. package/dist-client/pages/kpi/kpi-list-page.js.map +1 -1
  36. package/dist-client/pages/kpi/kpi-overview.js +9 -11
  37. package/dist-client/pages/kpi/kpi-overview.js.map +1 -1
  38. package/dist-client/pages/kpi/kpi-tree-page.d.ts +59 -0
  39. package/dist-client/pages/kpi/kpi-tree-page.js +403 -0
  40. package/dist-client/pages/kpi/kpi-tree-page.js.map +1 -0
  41. package/dist-client/pages/kpi/kpi-view.d.ts +12 -0
  42. package/dist-client/pages/kpi/kpi-view.js +191 -0
  43. package/dist-client/pages/kpi/kpi-view.js.map +1 -0
  44. package/dist-client/pages/kpi-dashboard/cards/kpi-level1-card.js +1 -1
  45. package/dist-client/pages/kpi-dashboard/cards/kpi-level1-card.js.map +1 -1
  46. package/dist-client/pages/kpi-dashboard/cards/kpi-level2-comparison.js +1 -1
  47. package/dist-client/pages/kpi-dashboard/cards/kpi-level2-comparison.js.map +1 -1
  48. package/dist-client/pages/kpi-dashboard/cards/kpi-level3-comparison.js +1 -1
  49. package/dist-client/pages/kpi-dashboard/cards/kpi-level3-comparison.js.map +1 -1
  50. package/dist-client/pages/kpi-dashboard/components/kpi-left-panel.d.ts +3 -1
  51. package/dist-client/pages/kpi-dashboard/components/kpi-left-panel.js +197 -161
  52. package/dist-client/pages/kpi-dashboard/components/kpi-left-panel.js.map +1 -1
  53. package/dist-client/pages/kpi-dashboard/components/kpi-map-panel.d.ts +5 -0
  54. package/dist-client/pages/kpi-dashboard/components/kpi-map-panel.js +146 -0
  55. package/dist-client/pages/kpi-dashboard/components/kpi-map-panel.js.map +1 -1
  56. package/dist-client/pages/kpi-dashboard/components/kpi-region-popup.js +3 -2
  57. package/dist-client/pages/kpi-dashboard/components/kpi-region-popup.js.map +1 -1
  58. package/dist-client/pages/kpi-dashboard/kpi-dashboard-map.js +4 -3
  59. package/dist-client/pages/kpi-dashboard/kpi-dashboard-map.js.map +1 -1
  60. package/dist-client/pages/kpi-dashboard/kpi-dashboard.js +28 -30
  61. package/dist-client/pages/kpi-dashboard/kpi-dashboard.js.map +1 -1
  62. package/dist-client/pages/kpi-history/kpi-history-list-page.d.ts +6 -1
  63. package/dist-client/pages/kpi-history/kpi-history-list-page.js +11 -11
  64. package/dist-client/pages/kpi-history/kpi-history-list-page.js.map +1 -1
  65. package/dist-client/pages/kpi-metric/kpi-metric-list-page.d.ts +5 -0
  66. package/dist-client/pages/kpi-metric/kpi-metric-list-page.js +10 -2
  67. package/dist-client/pages/kpi-metric/kpi-metric-list-page.js.map +1 -1
  68. package/dist-client/pages/kpi-metric-value/kpi-metric-value-editor-page.d.ts +1 -1
  69. package/dist-client/pages/kpi-metric-value/kpi-metric-value-editor-page.js +8 -8
  70. package/dist-client/pages/kpi-metric-value/kpi-metric-value-editor-page.js.map +1 -1
  71. package/dist-client/pages/kpi-metric-value/kpi-metric-value-importer.js +2 -2
  72. package/dist-client/pages/kpi-metric-value/kpi-metric-value-importer.js.map +1 -1
  73. package/dist-client/pages/kpi-metric-value/kpi-metric-value-list-page.d.ts +5 -0
  74. package/dist-client/pages/kpi-metric-value/kpi-metric-value-list-page.js +16 -8
  75. package/dist-client/pages/kpi-metric-value/kpi-metric-value-list-page.js.map +1 -1
  76. package/dist-client/pages/kpi-metric-value/kpi-metric-value-manual-entry-form.d.ts +1 -1
  77. package/dist-client/pages/kpi-metric-value/kpi-metric-value-manual-entry-form.js +6 -6
  78. package/dist-client/pages/kpi-metric-value/kpi-metric-value-manual-entry-form.js.map +1 -1
  79. package/dist-client/pages/kpi-statistic/kpi-statistic-editor-page.js +1 -2
  80. package/dist-client/pages/kpi-statistic/kpi-statistic-editor-page.js.map +1 -1
  81. package/dist-client/pages/kpi-statistic/kpi-statistic-list-page.d.ts +5 -0
  82. package/dist-client/pages/kpi-statistic/kpi-statistic-list-page.js +10 -2
  83. package/dist-client/pages/kpi-statistic/kpi-statistic-list-page.js.map +1 -1
  84. package/dist-client/pages/kpi-value/kpi-value-editor-page.d.ts +2 -1
  85. package/dist-client/pages/kpi-value/kpi-value-editor-page.js +16 -8
  86. package/dist-client/pages/kpi-value/kpi-value-editor-page.js.map +1 -1
  87. package/dist-client/pages/kpi-value/kpi-value-list-page.d.ts +5 -0
  88. package/dist-client/pages/kpi-value/kpi-value-list-page.js +31 -7
  89. package/dist-client/pages/kpi-value/kpi-value-list-page.js.map +1 -1
  90. package/dist-client/route.d.ts +1 -1
  91. package/dist-client/route.js +2 -8
  92. package/dist-client/route.js.map +1 -1
  93. package/dist-client/tsconfig.tsbuildinfo +1 -1
  94. package/dist-server/controllers/kpi-metric-value-provider.d.ts +1 -1
  95. package/dist-server/controllers/kpi-metric-value-provider.js +4 -4
  96. package/dist-server/controllers/kpi-metric-value-provider.js.map +1 -1
  97. package/dist-server/controllers/kpi-value-provider.d.ts +1 -1
  98. package/dist-server/controllers/kpi-value-provider.js +3 -3
  99. package/dist-server/controllers/kpi-value-provider.js.map +1 -1
  100. package/dist-server/migrations/1752190849680-seed-kpi-metrics.d.ts +6 -0
  101. package/dist-server/migrations/1752190849680-seed-kpi-metrics.js +101 -0
  102. package/dist-server/migrations/1752190849680-seed-kpi-metrics.js.map +1 -0
  103. package/dist-server/migrations/1752190849681-seed-kpi.d.ts +5 -0
  104. package/dist-server/migrations/1752190849681-seed-kpi.js +315 -0
  105. package/dist-server/migrations/1752190849681-seed-kpi.js.map +1 -0
  106. package/dist-server/migrations/1752192090123-add-grades-to-kpi.d.ts +7 -0
  107. package/dist-server/migrations/1752192090123-add-grades-to-kpi.js +51 -0
  108. package/dist-server/migrations/1752192090123-add-grades-to-kpi.js.map +1 -0
  109. package/dist-server/migrations/1752192090124-add-kpi-statistics.d.ts +5 -0
  110. package/dist-server/migrations/1752192090124-add-kpi-statistics.js +710 -0
  111. package/dist-server/migrations/1752192090124-add-kpi-statistics.js.map +1 -0
  112. package/dist-server/migrations/1752192090128-seed-kpi-org-scope.d.ts +6 -0
  113. package/dist-server/migrations/1752192090128-seed-kpi-org-scope.js +111 -0
  114. package/dist-server/migrations/1752192090128-seed-kpi-org-scope.js.map +1 -0
  115. package/dist-server/migrations/1752192090129-seed-kpi-values.d.ts +6 -0
  116. package/dist-server/migrations/1752192090129-seed-kpi-values.js +187 -0
  117. package/dist-server/migrations/1752192090129-seed-kpi-values.js.map +1 -0
  118. package/dist-server/migrations/grade-data/x11-performance-table.json +962 -0
  119. package/dist-server/migrations/grade-data/x12-performance-table.json +611 -0
  120. package/dist-server/migrations/grade-data/x14-performance-table.json +42 -0
  121. package/dist-server/migrations/grade-data/x21-performance-table.json +889 -0
  122. package/dist-server/migrations/grade-data/x22-performance-table.json +1064 -0
  123. package/dist-server/migrations/grade-data/x23-performance-table.json +42 -0
  124. package/dist-server/migrations/grade-data/x31-performance-table.json +644 -0
  125. package/dist-server/migrations/grade-data/x32-performance-table.json +993 -0
  126. package/dist-server/migrations/grade-data/x33-performance-table.json +195 -0
  127. package/dist-server/migrations/grade-data/x34-performance-table.json +12 -0
  128. package/dist-server/migrations/grade-data/x35-performance-table.json +42 -0
  129. package/dist-server/migrations/grade-data/x41-performance-table.json +825 -0
  130. package/dist-server/migrations/grade-data/x42-performance-table.json +786 -0
  131. package/dist-server/migrations/grade-data/x43-performance-table.json +12 -0
  132. package/dist-server/migrations/grade-data/x44-performance-table.json +42 -0
  133. package/dist-server/migrations/grade-data/x51-performance-table.json +924 -0
  134. package/dist-server/migrations/grade-data/x52-performance-table.json +42 -0
  135. package/dist-server/migrations/grade-data/x61-performance-table.json +261 -0
  136. package/dist-server/migrations/grade-data/x62-performance-table.json +42 -0
  137. package/dist-server/migrations/seed-data/kpi-metrics-seed.json +454 -0
  138. package/dist-server/migrations/seed-data/kpi-org-scope-seed.json +1676 -0
  139. package/dist-server/migrations/seed-data/kpi-values-seed.json +402 -0
  140. package/dist-server/migrations/seed-data/kpis-seed.json +488 -0
  141. package/dist-server/service/index.d.ts +3 -7
  142. package/dist-server/service/index.js +5 -12
  143. package/dist-server/service/index.js.map +1 -1
  144. package/dist-server/service/kpi/aggregate-kpi.js +30 -13
  145. package/dist-server/service/kpi/aggregate-kpi.js.map +1 -1
  146. package/dist-server/service/kpi/kpi-formula.service.d.ts +15 -0
  147. package/dist-server/service/kpi/kpi-formula.service.js +90 -0
  148. package/dist-server/service/kpi/kpi-formula.service.js.map +1 -1
  149. package/dist-server/service/kpi/kpi-history.d.ts +0 -3
  150. package/dist-server/service/kpi/kpi-history.js +0 -10
  151. package/dist-server/service/kpi/kpi-history.js.map +1 -1
  152. package/dist-server/service/kpi/kpi-mutation.d.ts +1 -1
  153. package/dist-server/service/kpi/kpi-mutation.js +57 -20
  154. package/dist-server/service/kpi/kpi-mutation.js.map +1 -1
  155. package/dist-server/service/kpi/kpi-query.d.ts +7 -3
  156. package/dist-server/service/kpi/kpi-query.js +126 -10
  157. package/dist-server/service/kpi/kpi-query.js.map +1 -1
  158. package/dist-server/service/kpi/kpi-type.d.ts +4 -2
  159. package/dist-server/service/kpi/kpi-type.js +12 -4
  160. package/dist-server/service/kpi/kpi-type.js.map +1 -1
  161. package/dist-server/service/kpi/kpi.d.ts +4 -3
  162. package/dist-server/service/kpi/kpi.js +20 -8
  163. package/dist-server/service/kpi/kpi.js.map +1 -1
  164. package/dist-server/service/kpi-metric/aggregate-kpi-metric.js +46 -11
  165. package/dist-server/service/kpi-metric/aggregate-kpi-metric.js.map +1 -1
  166. package/dist-server/service/kpi-metric-value/kpi-metric-value-mutation.d.ts +1 -1
  167. package/dist-server/service/kpi-metric-value/kpi-metric-value-mutation.js +6 -6
  168. package/dist-server/service/kpi-metric-value/kpi-metric-value-mutation.js.map +1 -1
  169. package/dist-server/service/kpi-metric-value/kpi-metric-value-type.d.ts +2 -2
  170. package/dist-server/service/kpi-metric-value/kpi-metric-value-type.js +4 -4
  171. package/dist-server/service/kpi-metric-value/kpi-metric-value-type.js.map +1 -1
  172. package/dist-server/service/kpi-metric-value/kpi-metric-value.d.ts +1 -1
  173. package/dist-server/service/kpi-metric-value/kpi-metric-value.js +3 -3
  174. package/dist-server/service/kpi-metric-value/kpi-metric-value.js.map +1 -1
  175. package/dist-server/service/kpi-org-scope/index.d.ts +9 -0
  176. package/dist-server/service/kpi-org-scope/index.js +14 -0
  177. package/dist-server/service/kpi-org-scope/index.js.map +1 -0
  178. package/dist-server/service/kpi-org-scope/kpi-org-scope-mutation.d.ts +8 -0
  179. package/dist-server/service/kpi-org-scope/kpi-org-scope-mutation.js +170 -0
  180. package/dist-server/service/kpi-org-scope/kpi-org-scope-mutation.js.map +1 -0
  181. package/dist-server/service/kpi-org-scope/kpi-org-scope-query.d.ts +14 -0
  182. package/dist-server/service/kpi-org-scope/kpi-org-scope-query.js +152 -0
  183. package/dist-server/service/kpi-org-scope/kpi-org-scope-query.js.map +1 -0
  184. package/dist-server/service/kpi-org-scope/kpi-org-scope-type.d.ts +26 -0
  185. package/dist-server/service/kpi-org-scope/kpi-org-scope-type.js +101 -0
  186. package/dist-server/service/kpi-org-scope/kpi-org-scope-type.js.map +1 -0
  187. package/dist-server/service/kpi-org-scope/kpi-org-scope.d.ts +26 -0
  188. package/dist-server/service/kpi-org-scope/kpi-org-scope.js +135 -0
  189. package/dist-server/service/kpi-org-scope/kpi-org-scope.js.map +1 -0
  190. package/dist-server/service/kpi-statistic/kpi-statistic.d.ts +1 -0
  191. package/dist-server/service/kpi-statistic/kpi-statistic.js +11 -0
  192. package/dist-server/service/kpi-statistic/kpi-statistic.js.map +1 -1
  193. package/dist-server/service/kpi-value/kpi-value-mutation.js +71 -7
  194. package/dist-server/service/kpi-value/kpi-value-mutation.js.map +1 -1
  195. package/dist-server/service/kpi-value/kpi-value-type.d.ts +4 -2
  196. package/dist-server/service/kpi-value/kpi-value-type.js +12 -4
  197. package/dist-server/service/kpi-value/kpi-value-type.js.map +1 -1
  198. package/dist-server/service/kpi-value/kpi-value.d.ts +3 -1
  199. package/dist-server/service/kpi-value/kpi-value.js +11 -5
  200. package/dist-server/service/kpi-value/kpi-value.js.map +1 -1
  201. package/dist-server/service/utils/value-date-util.d.ts +1 -0
  202. package/dist-server/service/utils/value-date-util.js +41 -0
  203. package/dist-server/service/utils/value-date-util.js.map +1 -1
  204. package/dist-server/tsconfig.json +10 -0
  205. package/dist-server/tsconfig.tsbuildinfo +1 -1
  206. package/package.json +7 -6
  207. package/server/@types/index.d.ts +11 -0
  208. package/server/controllers/kpi-metric-value-provider.ts +5 -5
  209. package/server/controllers/kpi-value-provider.ts +4 -4
  210. package/server/migrations/1752190849680-seed-kpi-metrics.ts +124 -0
  211. package/server/migrations/1752190849681-seed-kpi.ts +356 -0
  212. package/server/migrations/1752192090123-add-grades-to-kpi.ts +67 -0
  213. package/server/migrations/1752192090124-add-kpi-statistics.ts +719 -0
  214. package/server/migrations/1752192090128-seed-kpi-org-scope.ts +132 -0
  215. package/server/migrations/1752192090129-seed-kpi-values.ts +207 -0
  216. package/server/migrations/grade-data/x11-performance-table.json +962 -0
  217. package/server/migrations/grade-data/x12-performance-table.json +611 -0
  218. package/server/migrations/grade-data/x14-performance-table.json +42 -0
  219. package/server/migrations/grade-data/x21-performance-table.json +889 -0
  220. package/server/migrations/grade-data/x22-performance-table.json +1064 -0
  221. package/server/migrations/grade-data/x23-performance-table.json +42 -0
  222. package/server/migrations/grade-data/x31-performance-table.json +644 -0
  223. package/server/migrations/grade-data/x32-performance-table.json +993 -0
  224. package/server/migrations/grade-data/x33-performance-table.json +195 -0
  225. package/server/migrations/grade-data/x34-performance-table.json +12 -0
  226. package/server/migrations/grade-data/x35-performance-table.json +42 -0
  227. package/server/migrations/grade-data/x41-performance-table.json +825 -0
  228. package/server/migrations/grade-data/x42-performance-table.json +786 -0
  229. package/server/migrations/grade-data/x43-performance-table.json +12 -0
  230. package/server/migrations/grade-data/x44-performance-table.json +42 -0
  231. package/server/migrations/grade-data/x51-performance-table.json +924 -0
  232. package/server/migrations/grade-data/x52-performance-table.json +42 -0
  233. package/server/migrations/grade-data/x61-performance-table.json +261 -0
  234. package/server/migrations/grade-data/x62-performance-table.json +42 -0
  235. package/server/migrations/seed-data/kpi-metrics-seed.json +454 -0
  236. package/server/migrations/seed-data/kpi-org-scope-seed.json +1676 -0
  237. package/server/migrations/seed-data/kpi-values-seed.json +402 -0
  238. package/server/migrations/seed-data/kpis-seed.json +488 -0
  239. package/server/service/index.ts +5 -12
  240. package/server/service/kpi/aggregate-kpi.ts +31 -13
  241. package/server/service/kpi/kpi-formula.service.ts +101 -0
  242. package/server/service/kpi/kpi-history.ts +0 -8
  243. package/server/service/kpi/kpi-mutation.ts +59 -19
  244. package/server/service/kpi/kpi-query.ts +118 -8
  245. package/server/service/kpi/kpi-type.ts +10 -4
  246. package/server/service/kpi/kpi.ts +17 -7
  247. package/server/service/kpi-metric/aggregate-kpi-metric.ts +55 -11
  248. package/server/service/kpi-metric-value/kpi-metric-value-mutation.ts +6 -6
  249. package/server/service/kpi-metric-value/kpi-metric-value-type.ts +4 -4
  250. package/server/service/kpi-metric-value/kpi-metric-value.ts +3 -3
  251. package/server/service/kpi-org-scope/index.ts +11 -0
  252. package/server/service/kpi-org-scope/kpi-org-scope-mutation.ts +173 -0
  253. package/server/service/kpi-org-scope/kpi-org-scope-query.ts +127 -0
  254. package/server/service/kpi-org-scope/kpi-org-scope-type.ts +68 -0
  255. package/server/service/kpi-org-scope/kpi-org-scope.ts +123 -0
  256. package/server/service/kpi-statistic/kpi-statistic.ts +10 -0
  257. package/server/service/kpi-value/kpi-value-mutation.ts +73 -7
  258. package/server/service/kpi-value/kpi-value-type.ts +10 -4
  259. package/server/service/kpi-value/kpi-value.ts +10 -5
  260. package/server/service/utils/value-date-util.ts +47 -0
  261. package/server/types/global.d.ts +8 -0
  262. package/things-factory.config.js +1 -0
  263. package/translations/en.json +15 -3
  264. package/translations/ja.json +13 -3
  265. package/translations/ko.json +15 -3
  266. package/translations/ms.json +13 -3
  267. package/translations/zh.json +13 -3
  268. package/client/pages/kpi-category/kpi-category-importer.ts +0 -90
  269. package/client/pages/kpi-category/kpi-category-list-page.ts +0 -537
  270. package/client/pages/kpi-category/kpi-category-value-calculator.ts +0 -233
  271. package/client/pages/kpi-category-value/kpi-category-value-list-page.ts +0 -404
  272. package/dist-client/pages/kpi-category/kpi-category-importer.d.ts +0 -23
  273. package/dist-client/pages/kpi-category/kpi-category-importer.js +0 -92
  274. package/dist-client/pages/kpi-category/kpi-category-importer.js.map +0 -1
  275. package/dist-client/pages/kpi-category/kpi-category-list-page.d.ts +0 -74
  276. package/dist-client/pages/kpi-category/kpi-category-list-page.js +0 -517
  277. package/dist-client/pages/kpi-category/kpi-category-list-page.js.map +0 -1
  278. package/dist-client/pages/kpi-category/kpi-category-value-calculator.d.ts +0 -13
  279. package/dist-client/pages/kpi-category/kpi-category-value-calculator.js +0 -256
  280. package/dist-client/pages/kpi-category/kpi-category-value-calculator.js.map +0 -1
  281. package/dist-client/pages/kpi-category-value/kpi-category-value-list-page.d.ts +0 -63
  282. package/dist-client/pages/kpi-category-value/kpi-category-value-list-page.js +0 -393
  283. package/dist-client/pages/kpi-category-value/kpi-category-value-list-page.js.map +0 -1
  284. package/dist-server/service/kpi-category/index.d.ts +0 -6
  285. package/dist-server/service/kpi-category/index.js +0 -10
  286. package/dist-server/service/kpi-category/index.js.map +0 -1
  287. package/dist-server/service/kpi-category/kpi-category-mutation.d.ts +0 -9
  288. package/dist-server/service/kpi-category/kpi-category-mutation.js +0 -221
  289. package/dist-server/service/kpi-category/kpi-category-mutation.js.map +0 -1
  290. package/dist-server/service/kpi-category/kpi-category-query.d.ts +0 -18
  291. package/dist-server/service/kpi-category/kpi-category-query.js +0 -115
  292. package/dist-server/service/kpi-category/kpi-category-query.js.map +0 -1
  293. package/dist-server/service/kpi-category/kpi-category-type.d.ts +0 -24
  294. package/dist-server/service/kpi-category/kpi-category-type.js +0 -100
  295. package/dist-server/service/kpi-category/kpi-category-type.js.map +0 -1
  296. package/dist-server/service/kpi-category/kpi-category.d.ts +0 -22
  297. package/dist-server/service/kpi-category/kpi-category.js +0 -106
  298. package/dist-server/service/kpi-category/kpi-category.js.map +0 -1
  299. package/dist-server/service/kpi-category-value/index.d.ts +0 -6
  300. package/dist-server/service/kpi-category-value/index.js +0 -10
  301. package/dist-server/service/kpi-category-value/index.js.map +0 -1
  302. package/dist-server/service/kpi-category-value/kpi-category-value-mutation.d.ts +0 -8
  303. package/dist-server/service/kpi-category-value/kpi-category-value-mutation.js +0 -102
  304. package/dist-server/service/kpi-category-value/kpi-category-value-mutation.js.map +0 -1
  305. package/dist-server/service/kpi-category-value/kpi-category-value-query.d.ts +0 -13
  306. package/dist-server/service/kpi-category-value/kpi-category-value-query.js +0 -91
  307. package/dist-server/service/kpi-category-value/kpi-category-value-query.js.map +0 -1
  308. package/dist-server/service/kpi-category-value/kpi-category-value-type.d.ts +0 -19
  309. package/dist-server/service/kpi-category-value/kpi-category-value-type.js +0 -73
  310. package/dist-server/service/kpi-category-value/kpi-category-value-type.js.map +0 -1
  311. package/dist-server/service/kpi-category-value/kpi-category-value.d.ts +0 -19
  312. package/dist-server/service/kpi-category-value/kpi-category-value.js +0 -91
  313. package/dist-server/service/kpi-category-value/kpi-category-value.js.map +0 -1
  314. package/helps/kpi/kpi-category.md +0 -160
  315. package/server/service/kpi-category/index.ts +0 -7
  316. package/server/service/kpi-category/kpi-category-mutation.ts +0 -217
  317. package/server/service/kpi-category/kpi-category-query.ts +0 -87
  318. package/server/service/kpi-category/kpi-category-type.ts +0 -73
  319. package/server/service/kpi-category/kpi-category.ts +0 -95
  320. package/server/service/kpi-category-value/index.ts +0 -7
  321. package/server/service/kpi-category-value/kpi-category-value-mutation.ts +0 -88
  322. package/server/service/kpi-category-value/kpi-category-value-query.ts +0 -62
  323. package/server/service/kpi-category-value/kpi-category-value-type.ts +0 -48
  324. package/server/service/kpi-category-value/kpi-category-value.ts +0 -79
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@things-factory/kpi",
3
- "version": "9.0.31",
3
+ "version": "9.0.32",
4
4
  "main": "dist-server/index.js",
5
5
  "browser": "dist-client/index.js",
6
6
  "things-factory": true,
@@ -18,9 +18,10 @@
18
18
  },
19
19
  "scripts": {
20
20
  "build": "npm run build:server && npm run build:client",
21
- "copy:files": "copyfiles -e \"./client/**/*.{ts,js,json}\" -u 1 \"./client/**/*\" dist-client",
22
- "build:client": "npm run copy:files && npx tsc --p ./client/tsconfig.json",
23
- "build:server": "npx tsc --p ./server/tsconfig.json",
21
+ "copy:files:client": "copyfiles -e \"./client/**/*.{ts,js,json}\" -u 1 \"./client/**/*\" dist-client",
22
+ "copy:files:server": "copyfiles -e \"./server/**/*.{ts,js}\" -u 1 \"./server/**/*\" dist-server",
23
+ "build:client": "npm run copy:files:client && npx tsc --p ./client/tsconfig.json",
24
+ "build:server": "npm run copy:files:server && npx tsc --p ./server/tsconfig.json",
24
25
  "clean:client": "npx rimraf dist-client",
25
26
  "clean:server": "npx rimraf dist-server",
26
27
  "clean": "npm run clean:server && npm run clean:client",
@@ -41,8 +42,8 @@
41
42
  "@operato/styles": "^9.0.0",
42
43
  "@operato/utils": "^9.0.0",
43
44
  "@things-factory/auth-base": "^9.0.25",
44
- "@things-factory/dataset": "^9.0.28",
45
+ "@things-factory/dataset": "^9.0.32",
45
46
  "@things-factory/shell": "^9.0.25"
46
47
  },
47
- "gitHead": "3edffaba43578c71e33389fa27696de99a006049"
48
+ "gitHead": "a0418d09e6d7d514349d04d1725bd1d17e41f374"
48
49
  }
@@ -0,0 +1,11 @@
1
+ // Things Factory Global Types
2
+ // auth-base의 글로벌 타입들을 자동으로 사용할 수 있게 함
3
+
4
+ /// <reference types="@things-factory/auth-base/server/types" />
5
+
6
+ declare global {
7
+ // 추가적인 KPI 모듈만의 글로벌 타입이 필요하면 여기에 선언
8
+ // 예: KpiContext, KpiFormula 등
9
+ }
10
+
11
+ export {}
@@ -8,7 +8,7 @@ export class KpiMetricValueProvider implements ValueProvider {
8
8
  constructor(
9
9
  private options: {
10
10
  valueDate: string
11
- group?: string
11
+ org?: string
12
12
  domainId: string
13
13
  tx?: any
14
14
  }
@@ -25,13 +25,13 @@ export class KpiMetricValueProvider implements ValueProvider {
25
25
  const value = await valueRepo.findOne({
26
26
  where: {
27
27
  metric: { id: metric.id },
28
- group: this.options.group ?? '',
28
+ org: this.options.org ?? '',
29
29
  domain: { id: this.options.domainId }
30
30
  },
31
31
  order: { createdAt: 'DESC' }
32
32
  })
33
33
  if (!value) {
34
- throw new Error(`Metric value not found: metric='${name}', group='${this.options.group ?? ''}' (ALLTIME type)`)
34
+ throw new Error(`Metric value not found: metric='${name}', org='${this.options.org ?? ''}' (ALLTIME type)`)
35
35
  }
36
36
  return value.value
37
37
  }
@@ -52,13 +52,13 @@ export class KpiMetricValueProvider implements ValueProvider {
52
52
  where: {
53
53
  metric: { id: metric.id },
54
54
  valueDate,
55
- group: this.options.group ?? '',
55
+ org: this.options.org ?? '',
56
56
  domain: { id: this.options.domainId }
57
57
  }
58
58
  })
59
59
  if (!value) {
60
60
  throw new Error(
61
- `Metric value not found: metric='${name}', group='${this.options.group ?? ''}', valueDate='${valueDate}', periodType='${metric.periodType}'`
61
+ `Metric value not found: metric='${name}', org='${this.options.org ?? ''}', valueDate='${valueDate}', periodType='${metric.periodType}'`
62
62
  )
63
63
  }
64
64
  return value.value
@@ -7,7 +7,7 @@ export class KpiValueProvider implements ValueProvider {
7
7
  constructor(
8
8
  private options: {
9
9
  valueDate: string
10
- group?: string
10
+ org?: string
11
11
  domainId: string
12
12
  tx?: any
13
13
  }
@@ -22,7 +22,7 @@ export class KpiValueProvider implements ValueProvider {
22
22
  // SINGLE 타입인 경우 valueDate 무시하고 최신 값 조회
23
23
  const whereCondition: any = {
24
24
  kpi: { id: kpi.id },
25
- group: this.options.group ?? '',
25
+ org: this.options.org ?? '',
26
26
  domain: { id: this.options.domainId }
27
27
  }
28
28
 
@@ -33,7 +33,7 @@ export class KpiValueProvider implements ValueProvider {
33
33
  order: { createdAt: 'DESC' }
34
34
  })
35
35
  if (!value) {
36
- throw new Error(`KPI value not found: kpi='${name}', group='${this.options.group ?? ''}' (ALLTIME type)`)
36
+ throw new Error(`KPI value not found: kpi='${name}', org='${this.options.org ?? ''}' (ALLTIME type)`)
37
37
  }
38
38
  return value.value
39
39
  } else {
@@ -42,7 +42,7 @@ export class KpiValueProvider implements ValueProvider {
42
42
  const value = await valueRepo.findOne({ where: whereCondition })
43
43
  if (!value) {
44
44
  throw new Error(
45
- `KPI value not found: kpi='${name}', group='${this.options.group ?? ''}', valueDate='${this.options.valueDate}'`
45
+ `KPI value not found: kpi='${name}', org='${this.options.org ?? ''}', valueDate='${this.options.valueDate}'`
46
46
  )
47
47
  }
48
48
  return value.value
@@ -0,0 +1,124 @@
1
+ import { MigrationInterface, QueryRunner } from 'typeorm'
2
+ import { Domain, getRepository } from '@things-factory/shell'
3
+ import { KpiPeriodType } from '../service/kpi/kpi'
4
+ import { KpiMetric, KpiMetricCollectType } from '../service/kpi-metric/kpi-metric'
5
+ import * as fs from 'fs'
6
+ import * as path from 'path'
7
+
8
+ interface KpiMetricSeedData {
9
+ name: string
10
+ description: string
11
+ unit?: string | null
12
+ source?: string | null
13
+ field_name?: string | null
14
+ active: boolean
15
+ schedule_id?: string | null
16
+ timezone: string
17
+ data_set_id?: string | null
18
+ period_type: string
19
+ collect_type: string
20
+ schedule?: string | null
21
+ created_at?: string
22
+ updated_at?: string
23
+ }
24
+
25
+ export class SeedKpiMetrics1752190849680 implements MigrationInterface {
26
+ name = 'SeedKpiMetrics1752190849680'
27
+
28
+ public async up(queryRunner: QueryRunner): Promise<void> {
29
+ try {
30
+ const repository = getRepository(KpiMetric)
31
+ const domainRepository = getRepository(Domain)
32
+
33
+ // SYSTEM 도메인 확인
34
+ const domain: Domain = await domainRepository.findOneBy({ name: 'SYSTEM' })
35
+ if (!domain) {
36
+ console.log('❌ SYSTEM domain not found')
37
+ return
38
+ }
39
+
40
+ // JSON 파일 읽기
41
+ const seedFilePath = path.join(__dirname, 'seed-data', 'kpi-metrics-seed.json')
42
+ const seedData: KpiMetricSeedData[] = JSON.parse(fs.readFileSync(seedFilePath, 'utf8'))
43
+
44
+ console.log(`📊 Processing ${seedData.length} KPI metrics from JSON seed`)
45
+
46
+ for (const metricData of seedData) {
47
+ try {
48
+ const existingMetric = await repository.findOne({
49
+ where: { name: metricData.name, domain: { id: domain.id } }
50
+ })
51
+
52
+ if (existingMetric) {
53
+ console.log(`⚠️ KPI Metric already exists: ${metricData.name}`)
54
+ continue
55
+ }
56
+
57
+ const metric = await repository.save({
58
+ name: metricData.name,
59
+ description: metricData.description,
60
+ unit: metricData.unit,
61
+ source: metricData.source,
62
+ fieldName: metricData.field_name,
63
+ active: metricData.active,
64
+ scheduleId: metricData.schedule_id,
65
+ timezone: metricData.timezone,
66
+ dataSetId: metricData.data_set_id,
67
+ periodType: KpiPeriodType[metricData.period_type as keyof typeof KpiPeriodType],
68
+ collectType: KpiMetricCollectType[metricData.collect_type as keyof typeof KpiMetricCollectType],
69
+ schedule: metricData.schedule,
70
+ domain
71
+ })
72
+
73
+ console.log(`✅ Created KPI Metric: ${metric.name}`)
74
+ } catch (error) {
75
+ console.error(`❌ Error creating KPI Metric "${metricData.name}":`, error)
76
+ }
77
+ }
78
+
79
+ console.log(`🎉 Successfully processed KPI metrics from JSON seed`)
80
+ } catch (error) {
81
+ console.error('❌ Error seeding KPI metrics from JSON:', error)
82
+ throw error
83
+ }
84
+ }
85
+
86
+ public async down(queryRunner: QueryRunner): Promise<void> {
87
+ try {
88
+ const repository = getRepository(KpiMetric)
89
+ const domainRepository = getRepository(Domain)
90
+
91
+ const domain: Domain = await domainRepository.findOneBy({ name: 'SYSTEM' })
92
+ if (!domain) {
93
+ console.log('⚠️ SYSTEM domain not found. Nothing to delete.')
94
+ return
95
+ }
96
+
97
+ // JSON 파일 읽기
98
+ const seedFilePath = path.join(__dirname, 'seed-data', 'kpi-metrics-seed.json')
99
+ const seedData: KpiMetricSeedData[] = JSON.parse(fs.readFileSync(seedFilePath, 'utf8'))
100
+
101
+ console.log(`🗑️ Cleaning up ${seedData.length} KPI metrics`)
102
+
103
+ for (const metricData of seedData.reverse()) {
104
+ try {
105
+ const metric = await repository.findOne({
106
+ where: { name: metricData.name, domain: { id: domain.id } }
107
+ })
108
+
109
+ if (metric) {
110
+ await repository.delete(metric.id)
111
+ console.log(`✅ Deleted KPI Metric: ${metricData.name}`)
112
+ }
113
+ } catch (error) {
114
+ console.error(`❌ Error deleting KPI Metric "${metricData.name}":`, error)
115
+ }
116
+ }
117
+
118
+ console.log(`🎉 Successfully cleaned up KPI metrics`)
119
+ } catch (error) {
120
+ console.error('❌ Error cleaning up KPI metrics:', error)
121
+ throw error
122
+ }
123
+ }
124
+ }
@@ -0,0 +1,356 @@
1
+ import { MigrationInterface, QueryRunner } from 'typeorm'
2
+ import { Domain, getRepository } from '@things-factory/shell'
3
+ import { Kpi, KpiStatus, KpiPeriodType, KpiVizType } from '../service/kpi/kpi'
4
+ import * as fs from 'fs'
5
+ import * as path from 'path'
6
+
7
+ const SEED = [
8
+ // 일정성과 (Y1) - Schedule Performance
9
+ {
10
+ name: '연면적 대비 공사기간',
11
+ description: '연면적 대비 공사기간 평가',
12
+ categoryName: '일정성과',
13
+ formula: 'Eq. 활용',
14
+ scoreType: 'equation',
15
+ dataType: 'ratio'
16
+ },
17
+ {
18
+ name: '설계변경에 따른 공기 증감률',
19
+ description: '설계변경에 따른 공기 증감률 평가',
20
+ categoryName: '일정성과',
21
+ formula: 'Eq. 활용',
22
+ scoreType: 'equation',
23
+ dataType: 'ratio'
24
+ },
25
+ {
26
+ name: '일정 이탈 수준',
27
+ description: '프로젝트 일정 이탈 수준 평가',
28
+ categoryName: '일정성과',
29
+ formula: 'Table(DART 등) 활용(1~5점)',
30
+ scoreType: 'table',
31
+ dataType: 'score'
32
+ },
33
+ {
34
+ name: '일정성과 수준 평가',
35
+ description: '일정성과 종합 평가',
36
+ categoryName: '일정성과',
37
+ formula: '감리자 1~5점 척도',
38
+ scoreType: 'inspector',
39
+ dataType: 'score'
40
+ },
41
+
42
+ // 비용성과 (Y2) - Cost Performance
43
+ {
44
+ name: '연면적 대비 공사비',
45
+ description: '연면적 대비 공사비 평가',
46
+ categoryName: '비용성과',
47
+ formula: 'Eq. 활용',
48
+ scoreType: 'equation',
49
+ dataType: 'ratio'
50
+ },
51
+ {
52
+ name: '설계변경에 따른 공사비 증감률',
53
+ description: '설계변경에 따른 공사비 증감률 평가',
54
+ categoryName: '비용성과',
55
+ formula: 'Eq. 활용',
56
+ scoreType: 'equation',
57
+ dataType: 'ratio'
58
+ },
59
+ {
60
+ name: '비용성과 수준 평가',
61
+ description: '비용성과 종합 평가',
62
+ categoryName: '비용성과',
63
+ formula: '감리자 1~5점 척도',
64
+ scoreType: 'inspector',
65
+ dataType: 'score'
66
+ },
67
+
68
+ // 품질성과 (Y3) - Quality Performance
69
+ {
70
+ name: '품질시험 불합격률',
71
+ description: '품질시험 불합격률 평가',
72
+ categoryName: '품질성과',
73
+ formula: 'Eq. 활용',
74
+ scoreType: 'equation',
75
+ dataType: 'ratio'
76
+ },
77
+ {
78
+ name: '검수자재 불합격률',
79
+ description: '검수자재 불합격률 평가',
80
+ categoryName: '품질성과',
81
+ formula: 'Eq. 활용',
82
+ scoreType: 'equation',
83
+ dataType: 'ratio'
84
+ },
85
+ {
86
+ name: '검측 불합격률',
87
+ description: '검측 불합격률 평가',
88
+ categoryName: '품질성과',
89
+ formula: 'Table 활용',
90
+ scoreType: 'table',
91
+ dataType: 'score'
92
+ },
93
+ {
94
+ name: '품질 SL-PA 결과값',
95
+ description: '품질 SL-PA 결과',
96
+ categoryName: '품질성과',
97
+ formula: 'Python 활용(1~5점)',
98
+ scoreType: 'python',
99
+ dataType: 'score'
100
+ },
101
+ {
102
+ name: '품질성과 수준 평가',
103
+ description: '품질성과 종합 평가',
104
+ categoryName: '품질성과',
105
+ formula: '감리자 1~5점 척도',
106
+ scoreType: 'inspector',
107
+ dataType: 'score'
108
+ },
109
+
110
+ // 안전성과 (Y4) - Safety Performance
111
+ {
112
+ name: '재해율',
113
+ description: '재해율 평가',
114
+ categoryName: '안전성과',
115
+ formula: 'Eq. 활용',
116
+ scoreType: 'equation',
117
+ dataType: 'ratio'
118
+ },
119
+ {
120
+ name: '재해강도율',
121
+ description: '재해강도율 평가',
122
+ categoryName: '안전성과',
123
+ formula: 'Table 활용',
124
+ scoreType: 'table',
125
+ dataType: 'score'
126
+ },
127
+ {
128
+ name: '안전 SL-PA 결과값',
129
+ description: '안전 SL-PA 결과',
130
+ categoryName: '안전성과',
131
+ formula: 'Python 활용(1~5점)',
132
+ scoreType: 'python',
133
+ dataType: 'score'
134
+ },
135
+ {
136
+ name: '안전성과 수준 평가',
137
+ description: '안전성과 종합 평가',
138
+ categoryName: '안전성과',
139
+ formula: '감리자 1~5점 척도',
140
+ scoreType: 'inspector',
141
+ dataType: 'score'
142
+ },
143
+
144
+ // 환경성과 (Y5) - Environmental Performance
145
+ {
146
+ name: '건설폐기물 발생량',
147
+ description: '건설폐기물 발생량 평가',
148
+ categoryName: '환경성과',
149
+ formula: 'Table 활용',
150
+ scoreType: 'table',
151
+ dataType: 'score'
152
+ },
153
+ {
154
+ name: '환경성과 수준 평가',
155
+ description: '환경성과 종합 평가',
156
+ categoryName: '환경성과',
157
+ formula: '감리자 1~5점 척도',
158
+ scoreType: 'inspector',
159
+ dataType: 'score'
160
+ },
161
+
162
+ // 생산성성과 (Y6) - Productivity Performance
163
+ {
164
+ name: '투입인력 생산성',
165
+ description: '투입인력 생산성 평가',
166
+ categoryName: '생산성과',
167
+ formula: 'Eq. 활용',
168
+ scoreType: 'equation',
169
+ dataType: 'ratio'
170
+ },
171
+ {
172
+ name: '생산성성과 수준 평가',
173
+ description: '생산성과 종합 평가',
174
+ categoryName: '생산성과',
175
+ formula: '감리자 1~5점 척도',
176
+ scoreType: 'inspector',
177
+ dataType: 'score'
178
+ }
179
+ ]
180
+
181
+ interface KpiSeedData {
182
+ name: string
183
+ description: string
184
+ formula?: string | null
185
+ active: boolean
186
+ state?: string | null
187
+ viz_type?: string | null
188
+ viz_meta?: any | null
189
+ schedule?: string | null
190
+ schedule_id?: string | null
191
+ timezone?: string | null
192
+ grades?: any | null
193
+ period_type: string
194
+ weight: number
195
+ score_formula?: string | null
196
+ is_leaf: boolean
197
+ parent_name?: string | null
198
+ }
199
+
200
+ export class SeedKpi1752190849681 implements MigrationInterface {
201
+ public async up(queryRunner: QueryRunner): Promise<any> {
202
+ try {
203
+ const repository = getRepository(Kpi)
204
+ const domainRepository = getRepository(Domain)
205
+
206
+ // SYSTEM 도메인 확인
207
+ const domain: Domain = await domainRepository.findOneBy({ name: 'SYSTEM' })
208
+ if (!domain) {
209
+ console.log('❌ SYSTEM domain not found')
210
+ return
211
+ }
212
+
213
+ // JSON 파일 읽기
214
+ const seedFilePath = path.join(__dirname, 'seed-data', 'kpis-seed.json')
215
+ const seedData: KpiSeedData[] = JSON.parse(fs.readFileSync(seedFilePath, 'utf8'))
216
+
217
+ // 이름으로 KPI를 찾을 수 있는 맵 생성
218
+ const kpiNameMap = new Map<string, Kpi>()
219
+
220
+ // 1단계: parent_name이 null인 루트 KPI들 먼저 생성
221
+ const rootKpis = seedData.filter(kpi => kpi.parent_name === null)
222
+
223
+ for (const kpiData of rootKpis) {
224
+ const existingKpi = await repository.findOne({
225
+ where: { name: kpiData.name, domain: { id: domain.id } }
226
+ })
227
+
228
+ if (existingKpi) {
229
+ console.log(`⚠️ KPI already exists: ${kpiData.name}`)
230
+ kpiNameMap.set(kpiData.name, existingKpi)
231
+ continue
232
+ }
233
+
234
+ const kpi = await repository.save({
235
+ name: kpiData.name,
236
+ description: kpiData.description,
237
+ formula: kpiData.formula,
238
+ active: kpiData.active,
239
+ state: kpiData.state ? KpiStatus[kpiData.state as keyof typeof KpiStatus] : KpiStatus.DRAFT,
240
+ vizType: kpiData.viz_type ? KpiVizType[kpiData.viz_type as keyof typeof KpiVizType] : null,
241
+ vizMeta: kpiData.viz_meta,
242
+ schedule: kpiData.schedule,
243
+ scheduleId: kpiData.schedule_id,
244
+ timezone: kpiData.timezone,
245
+ grades: kpiData.grades ? JSON.parse(kpiData.grades) : null,
246
+ periodType: KpiPeriodType[kpiData.period_type as keyof typeof KpiPeriodType],
247
+ weight: kpiData.weight,
248
+ scoreFormula: kpiData.score_formula,
249
+ isLeaf: kpiData.is_leaf,
250
+ parent: null,
251
+ domain
252
+ })
253
+
254
+ kpiNameMap.set(kpi.name, kpi)
255
+ console.log(`✅ Created root KPI: ${kpi.name}`)
256
+ }
257
+
258
+ // 2단계: 자식 KPI들 생성 (parent_name이 있는 KPI들)
259
+ const childKpis = seedData.filter(kpi => kpi.parent_name !== null)
260
+
261
+ for (const kpiData of childKpis) {
262
+ const existingKpi = await repository.findOne({
263
+ where: { name: kpiData.name, domain: { id: domain.id } }
264
+ })
265
+
266
+ if (existingKpi) {
267
+ console.log(`⚠️ KPI already exists: ${kpiData.name}`)
268
+ continue
269
+ }
270
+
271
+ // 부모 KPI 찾기
272
+ const parentKpi = kpiNameMap.get(kpiData.parent_name!)
273
+ if (!parentKpi) {
274
+ console.log(`❌ Parent KPI not found: ${kpiData.parent_name} for ${kpiData.name}`)
275
+ continue
276
+ }
277
+
278
+ const kpi = await repository.save({
279
+ name: kpiData.name,
280
+ description: kpiData.description,
281
+ formula: kpiData.formula,
282
+ active: kpiData.active,
283
+ state: kpiData.state ? KpiStatus[kpiData.state as keyof typeof KpiStatus] : KpiStatus.DRAFT,
284
+ vizType: kpiData.viz_type ? KpiVizType[kpiData.viz_type as keyof typeof KpiVizType] : null,
285
+ vizMeta: kpiData.viz_meta,
286
+ schedule: kpiData.schedule,
287
+ scheduleId: kpiData.schedule_id,
288
+ timezone: kpiData.timezone,
289
+ grades: kpiData.grades ? JSON.parse(kpiData.grades) : null,
290
+ periodType: KpiPeriodType[kpiData.period_type as keyof typeof KpiPeriodType],
291
+ weight: kpiData.weight,
292
+ scoreFormula: kpiData.score_formula,
293
+ isLeaf: kpiData.is_leaf,
294
+ parent: parentKpi,
295
+ domain
296
+ })
297
+
298
+ kpiNameMap.set(kpi.name, kpi)
299
+ console.log(`✅ Created child KPI: ${kpi.name} (parent: ${parentKpi.name})`)
300
+ }
301
+
302
+ console.log(`🎉 Successfully processed ${seedData.length} KPIs from JSON seed`)
303
+ } catch (error) {
304
+ console.error('❌ Error seeding KPIs from JSON:', error)
305
+ throw error
306
+ }
307
+ }
308
+
309
+ public async down(queryRunner: QueryRunner): Promise<any> {
310
+ try {
311
+ const repository = getRepository(Kpi)
312
+ const domainRepository = getRepository(Domain)
313
+
314
+ const domain: Domain = await domainRepository.findOneBy({ name: 'SYSTEM' })
315
+ if (!domain) {
316
+ console.log('⚠️ SYSTEM domain not found. Nothing to delete.')
317
+ return
318
+ }
319
+
320
+ // JSON 파일 읽기
321
+ const seedFilePath = path.join(__dirname, 'seed-data', 'kpis-seed.json')
322
+ const seedData: KpiSeedData[] = JSON.parse(fs.readFileSync(seedFilePath, 'utf8'))
323
+
324
+ // 자식부터 삭제 (역순으로)
325
+ const childKpis = seedData.filter(kpi => kpi.parent_name !== null).reverse()
326
+ const rootKpis = seedData.filter(kpi => kpi.parent_name === null).reverse()
327
+
328
+ // 자식 KPI들 먼저 삭제
329
+ for (const kpiData of childKpis) {
330
+ const kpi = await repository.findOne({
331
+ where: { name: kpiData.name, domain: { id: domain.id } }
332
+ })
333
+ if (kpi) {
334
+ await repository.delete(kpi.id)
335
+ console.log(`✅ Deleted child KPI: ${kpiData.name}`)
336
+ }
337
+ }
338
+
339
+ // 루트 KPI들 삭제
340
+ for (const kpiData of rootKpis) {
341
+ const kpi = await repository.findOne({
342
+ where: { name: kpiData.name, domain: { id: domain.id } }
343
+ })
344
+ if (kpi) {
345
+ await repository.delete(kpi.id)
346
+ console.log(`✅ Deleted root KPI: ${kpiData.name}`)
347
+ }
348
+ }
349
+
350
+ console.log(`🎉 Successfully cleaned up KPIs from JSON seed`)
351
+ } catch (error) {
352
+ console.error('❌ Error cleaning up KPIs:', error)
353
+ throw error
354
+ }
355
+ }
356
+ }
@@ -0,0 +1,67 @@
1
+ import { MigrationInterface, QueryRunner } from 'typeorm'
2
+ import { getRepository } from '@things-factory/shell'
3
+ import { Kpi } from '../service/kpi/kpi'
4
+
5
+ import * as fs from 'fs'
6
+ import * as path from 'path'
7
+
8
+ interface GradeData {
9
+ kpiName: string
10
+ version: number
11
+ description: string
12
+ grades: Array<{
13
+ name: string
14
+ minValue: number
15
+ maxValue: number
16
+ score?: number
17
+ color?: string
18
+ description?: string
19
+ }>
20
+ }
21
+
22
+ export class AddGradesToKpi1752192090123 implements MigrationInterface {
23
+ name = 'AddGradesToKpi1752192090123'
24
+
25
+ public async up(queryRunner: QueryRunner): Promise<void> {
26
+ // grade-data 폴더의 JSON 파일들을 읽어서 해당 KPI의 grades 컬럼에 넣기
27
+ await this.loadGradeDataToKpi()
28
+ }
29
+
30
+ public async down(queryRunner: QueryRunner): Promise<void> {}
31
+
32
+ private async loadGradeDataToKpi(): Promise<void> {
33
+ const gradeDataPath = path.join(__dirname, 'grade-data')
34
+ const kpiRepository = getRepository(Kpi)
35
+
36
+ try {
37
+ // grade-data 폴더의 모든 JSON 파일 읽기
38
+ const files = fs.readdirSync(gradeDataPath).filter(file => file.endsWith('.json'))
39
+
40
+ for (const file of files) {
41
+ const filePath = path.join(gradeDataPath, file)
42
+ const fileContent = fs.readFileSync(filePath, 'utf8')
43
+ const gradeData: GradeData = JSON.parse(fileContent)
44
+
45
+ // KPI 이름으로 해당 KPI 찾기
46
+ const kpi = await kpiRepository.findOne({
47
+ where: { name: gradeData.kpiName, domain: { name: 'SYSTEM' } }
48
+ })
49
+
50
+ if (kpi) {
51
+ // grades 데이터를 업데이트
52
+ kpi.grades = gradeData.grades
53
+ await kpiRepository.save(kpi)
54
+
55
+ console.log(`✅ Loaded grades for KPI: ${gradeData.kpiName} (${gradeData.grades.length} grades)`)
56
+ } else {
57
+ console.log(`⚠️ KPI not found: ${gradeData.kpiName}`)
58
+ }
59
+ }
60
+
61
+ console.log(`🎉 Successfully loaded grades data for ${files.length} files`)
62
+ } catch (error) {
63
+ console.error('❌ Error loading grade data:', error)
64
+ throw error
65
+ }
66
+ }
67
+ }