@oneuptime/common 12.0.29 → 12.0.31

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 (664) hide show
  1. package/Models/AnalyticsModels/SecurityEvent.ts +48 -16
  2. package/Models/AnalyticsModels/ThreatIntelIndicator.ts +10 -5
  3. package/Models/DatabaseModels/AlertSeverity.ts +44 -0
  4. package/Models/DatabaseModels/DetectionRule.ts +16 -5
  5. package/Models/DatabaseModels/GoogleSecOpsConnection.ts +14 -5
  6. package/Models/DatabaseModels/IncidentSeverity.ts +44 -0
  7. package/Models/DatabaseModels/Index.ts +13 -0
  8. package/Models/DatabaseModels/NetworkDevice.ts +113 -3
  9. package/Models/DatabaseModels/NetworkDeviceAutoImportRule.ts +88 -0
  10. package/Models/DatabaseModels/NetworkDeviceDiscoveryScan.ts +22 -0
  11. package/Models/DatabaseModels/NetworkDeviceOidTemplate.ts +499 -0
  12. package/Models/DatabaseModels/OnCallDutyPolicySchedule.ts +43 -0
  13. package/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.ts +662 -0
  14. package/Models/DatabaseModels/ProjectOnCallCalendarFeed.ts +584 -0
  15. package/Models/DatabaseModels/ThreatIntelFeed.ts +16 -5
  16. package/Models/DatabaseModels/UserOnCallCalendarFeed.ts +546 -0
  17. package/Models/DatabaseModels/UserOnCallShiftReminder.ts +231 -0
  18. package/Models/DatabaseModels/UserOnCallShiftReminderLog.ts +331 -0
  19. package/Server/API/GlobalConfigAPI.ts +362 -183
  20. package/Server/API/OnCallCalendarAPI.ts +2194 -0
  21. package/Server/API/TelemetryAPI.ts +42 -4
  22. package/Server/EnvironmentConfig.ts +250 -0
  23. package/Server/Infrastructure/OnCallCalendarFeedCache.ts +1050 -0
  24. package/Server/Infrastructure/Postgres/SchemaMigrations/1790400000000-AddOnCallCalendarFeeds.ts +253 -0
  25. package/Server/Infrastructure/Postgres/SchemaMigrations/1790500000000-AddNetworkDeviceOidTemplate.ts +59 -0
  26. package/Server/Infrastructure/Postgres/SchemaMigrations/1790600000000-AddAutoImportRuleOidTemplate.ts +25 -0
  27. package/Server/Infrastructure/Postgres/SchemaMigrations/Index.ts +6 -0
  28. package/Server/Middleware/MultipartFormData.ts +118 -32
  29. package/Server/Middleware/OnCallCalendarFeedRateLimit.ts +487 -0
  30. package/Server/Services/AlertEpisodeLabelRuleEngineService.ts +9 -1
  31. package/Server/Services/AlertEpisodeOnCallRuleEngineService.ts +9 -1
  32. package/Server/Services/AlertEpisodeOwnerRuleEngineService.ts +9 -1
  33. package/Server/Services/AlertEpisodePrivacyRuleEngineService.ts +9 -1
  34. package/Server/Services/AlertGroupingEngineService.ts +9 -1
  35. package/Server/Services/AlertLabelRuleEngineService.ts +9 -1
  36. package/Server/Services/AlertOnCallRuleEngineService.ts +9 -1
  37. package/Server/Services/AlertOwnerRuleEngineService.ts +9 -1
  38. package/Server/Services/AlertPrivacyRuleEngineService.ts +9 -1
  39. package/Server/Services/AlertReminderRuleService.ts +9 -1
  40. package/Server/Services/AutoRemediationRuleEngineService.ts +9 -1
  41. package/Server/Services/CephClusterLabelRuleEngineService.ts +9 -1
  42. package/Server/Services/CephClusterOwnerRuleEngineService.ts +9 -1
  43. package/Server/Services/CloudResourceLabelRuleEngineService.ts +9 -1
  44. package/Server/Services/CloudResourceOwnerRuleEngineService.ts +9 -1
  45. package/Server/Services/DashboardLabelRuleEngineService.ts +9 -1
  46. package/Server/Services/DashboardOwnerRuleEngineService.ts +9 -1
  47. package/Server/Services/DockerHostLabelRuleEngineService.ts +9 -1
  48. package/Server/Services/DockerHostOwnerRuleEngineService.ts +9 -1
  49. package/Server/Services/DockerSwarmClusterLabelRuleEngineService.ts +9 -1
  50. package/Server/Services/DockerSwarmClusterOwnerRuleEngineService.ts +9 -1
  51. package/Server/Services/HostLabelRuleEngineService.ts +9 -1
  52. package/Server/Services/HostOwnerRuleEngineService.ts +9 -1
  53. package/Server/Services/IncidentEpisodeLabelRuleEngineService.ts +9 -1
  54. package/Server/Services/IncidentEpisodeOnCallRuleEngineService.ts +9 -1
  55. package/Server/Services/IncidentEpisodeOwnerRuleEngineService.ts +9 -1
  56. package/Server/Services/IncidentEpisodePrivacyRuleEngineService.ts +9 -1
  57. package/Server/Services/IncidentGroupingEngineService.ts +9 -1
  58. package/Server/Services/IncidentLabelRuleEngineService.ts +9 -1
  59. package/Server/Services/IncidentOnCallRuleEngineService.ts +9 -1
  60. package/Server/Services/IncidentOwnerRuleEngineService.ts +9 -1
  61. package/Server/Services/IncidentPrivacyRuleEngineService.ts +9 -1
  62. package/Server/Services/IncidentReminderRuleService.ts +9 -1
  63. package/Server/Services/IncidentSlaRuleService.ts +9 -1
  64. package/Server/Services/IncomingCallPolicyLabelRuleEngineService.ts +9 -1
  65. package/Server/Services/IncomingCallPolicyOwnerRuleEngineService.ts +9 -1
  66. package/Server/Services/Index.ts +14 -0
  67. package/Server/Services/IoTFleetLabelRuleEngineService.ts +9 -1
  68. package/Server/Services/IoTFleetOwnerRuleEngineService.ts +9 -1
  69. package/Server/Services/KubernetesClusterLabelRuleEngineService.ts +9 -1
  70. package/Server/Services/KubernetesClusterOwnerRuleEngineService.ts +9 -1
  71. package/Server/Services/KubernetesResourceService.ts +5 -1
  72. package/Server/Services/MonitorLabelRuleEngineService.ts +9 -1
  73. package/Server/Services/MonitorOwnerRuleEngineService.ts +9 -1
  74. package/Server/Services/NetworkDeviceAutoImportRuleEngineService.ts +35 -0
  75. package/Server/Services/NetworkDeviceAutoImportRuleService.ts +96 -0
  76. package/Server/Services/NetworkDeviceLabelRuleEngineService.ts +9 -1
  77. package/Server/Services/NetworkDeviceOidTemplateService.ts +201 -0
  78. package/Server/Services/NetworkDeviceOwnerRuleEngineService.ts +9 -1
  79. package/Server/Services/NetworkDeviceService.ts +209 -1
  80. package/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.ts +32 -0
  81. package/Server/Services/OnCallDutyPolicyLabelRuleEngineService.ts +9 -1
  82. package/Server/Services/OnCallDutyPolicyOwnerRuleEngineService.ts +9 -1
  83. package/Server/Services/OnCallDutyPolicyScheduleCalendarFeedService.ts +260 -0
  84. package/Server/Services/OnCallDutyPolicyScheduleLabelRuleEngineService.ts +9 -1
  85. package/Server/Services/OnCallDutyPolicyScheduleLayerService.ts +70 -3
  86. package/Server/Services/OnCallDutyPolicyScheduleLayerUserService.ts +138 -3
  87. package/Server/Services/OnCallDutyPolicyScheduleOwnerRuleEngineService.ts +9 -1
  88. package/Server/Services/OnCallDutyPolicyScheduleService.ts +1465 -134
  89. package/Server/Services/OnCallDutyPolicyUserOverrideService.ts +167 -31
  90. package/Server/Services/PodmanHostLabelRuleEngineService.ts +9 -1
  91. package/Server/Services/PodmanHostOwnerRuleEngineService.ts +9 -1
  92. package/Server/Services/ProjectOnCallCalendarFeedService.ts +192 -0
  93. package/Server/Services/ProxmoxClusterLabelRuleEngineService.ts +9 -1
  94. package/Server/Services/ProxmoxClusterOwnerRuleEngineService.ts +9 -1
  95. package/Server/Services/RumApplicationLabelRuleEngineService.ts +9 -1
  96. package/Server/Services/RumApplicationOwnerRuleEngineService.ts +9 -1
  97. package/Server/Services/RunbookLabelRuleEngineService.ts +9 -1
  98. package/Server/Services/RunbookOwnerRuleEngineService.ts +9 -1
  99. package/Server/Services/RunbookRuleEngineService.ts +9 -1
  100. package/Server/Services/ScheduledMaintenanceLabelRuleEngineService.ts +9 -1
  101. package/Server/Services/ScheduledMaintenanceOwnerRuleEngineService.ts +9 -1
  102. package/Server/Services/ScheduledMaintenanceReminderRuleService.ts +9 -1
  103. package/Server/Services/ServerlessFunctionLabelRuleEngineService.ts +9 -1
  104. package/Server/Services/ServerlessFunctionOwnerRuleEngineService.ts +9 -1
  105. package/Server/Services/ServiceLabelRuleEngineService.ts +9 -1
  106. package/Server/Services/ServiceOwnerRuleEngineService.ts +9 -1
  107. package/Server/Services/StatusPageLabelRuleEngineService.ts +9 -1
  108. package/Server/Services/StatusPageMonitorRuleEngineService.ts +7 -0
  109. package/Server/Services/StatusPageOwnerRuleEngineService.ts +9 -1
  110. package/Server/Services/TeamMemberService.ts +489 -1
  111. package/Server/Services/TeamService.ts +50 -0
  112. package/Server/Services/TelemetrySourceMapService.ts +266 -23
  113. package/Server/Services/UserNotificationSettingService.ts +44 -1
  114. package/Server/Services/UserOnCallCalendarFeedService.ts +159 -0
  115. package/Server/Services/UserOnCallShiftReminderLogService.ts +151 -0
  116. package/Server/Services/UserOnCallShiftReminderService.ts +112 -0
  117. package/Server/Services/UserService.ts +27 -0
  118. package/Server/Services/WorkflowLabelRuleEngineService.ts +9 -1
  119. package/Server/Services/WorkflowOwnerRuleEngineService.ts +9 -1
  120. package/Server/Utils/EnterpriseLicense/EnterpriseLicenseSeatUtil.ts +186 -0
  121. package/Server/Utils/Monitor/CapturedMetricAttributeUtil.ts +245 -0
  122. package/Server/Utils/Monitor/Criteria/SnmpMonitorCriteria.ts +21 -2
  123. package/Server/Utils/Monitor/MonitorMetricUtil.ts +55 -21
  124. package/Server/Utils/Monitor/MonitorTemplateUtil.ts +32 -0
  125. package/Server/Utils/Monitor/NetworkDeviceMetricUtil.ts +15 -2
  126. package/Server/Utils/Monitor/NetworkDeviceWalkUtil.ts +18 -1
  127. package/Server/Utils/Monitor/NetworkInventoryUtil.ts +10 -0
  128. package/Server/Utils/Monitor/SeriesResourceLabels.ts +34 -0
  129. package/Server/Utils/OnCall/CalendarFeedToken.ts +241 -0
  130. package/Server/Utils/OnCall/OnCallCalendarFeedRenderer.ts +1488 -0
  131. package/Server/Utils/OnCall/OnCallCalendarFeedUrls.ts +230 -0
  132. package/Server/Utils/OnCall/OnCallShiftChangeListeners.ts +227 -0
  133. package/Server/Utils/OnCall/OnCallShiftMaterializer.ts +1127 -0
  134. package/Server/Utils/OnCall/OnCallShiftReminderListener.ts +174 -0
  135. package/Server/Utils/OnCall/OnCallShiftReminderRunner.ts +2584 -0
  136. package/Server/Utils/Response.ts +134 -0
  137. package/Server/Utils/Rules/RuleEngineRuleRead.ts +48 -0
  138. package/Server/Utils/StartServer.ts +10 -0
  139. package/Server/Utils/Telemetry/AppMetrics.ts +51 -0
  140. package/Server/Utils/Telemetry/ExceptionSanitizer.ts +14 -1
  141. package/Server/Utils/Telemetry/LogExceptionExtractor.ts +14 -2
  142. package/Server/Utils/Telemetry/SourceMapResolver.ts +16 -5
  143. package/Server/Utils/Telemetry/StackTraceParser.ts +399 -0
  144. package/Tests/App/Dashboard/EventOverlayHook.test.tsx +125 -0
  145. package/Tests/App/Dashboard/HeaderImageAssets.test.tsx +93 -0
  146. package/Tests/App/Dashboard/OnCallCalendarFeedLinks.test.tsx +229 -0
  147. package/Tests/App/Dashboard/OnCallCalendarFeedPlanGate.test.tsx +489 -0
  148. package/Tests/App/Dashboard/OnCallCalendarFeedSideMenus.test.tsx +149 -0
  149. package/Tests/App/Dashboard/OnCallCalendarFeedUtil.test.ts +855 -0
  150. package/Tests/App/Dashboard/OnCallPersonalCalendarFeed.test.tsx +1209 -0
  151. package/Tests/App/Dashboard/OnCallReadinessSurfaces.test.tsx +3 -3
  152. package/Tests/App/Dashboard/OnCallSharedCalendarFeedCard.test.tsx +1019 -0
  153. package/Tests/App/Dashboard/OnCallShiftRemindersAndUpcomingShifts.test.tsx +655 -0
  154. package/Tests/App/Dashboard/UserElementEmail.test.tsx +12 -4
  155. package/Tests/App/Dashboard/UserEmailCallSites.test.tsx +1 -1
  156. package/Tests/App/Dashboard/UserSettingsSetupChecklistModel.test.ts +73 -0
  157. package/Tests/Models/DatabaseModels/DomainRoleTierCoverage.test.ts +14 -0
  158. package/Tests/Models/DatabaseModels/ModelRegistryInvariants.test.ts +469 -0
  159. package/Tests/Models/OnCallCalendarFeedModels.test.ts +642 -0
  160. package/Tests/Models/OnCallDutyPolicyScheduleCalendarFeed.test.ts +288 -0
  161. package/Tests/Models/OnCallDutyPolicyScheduleShiftConfigVersion.test.ts +88 -0
  162. package/Tests/Models/SecurityDomainAccessControl.test.ts +429 -0
  163. package/Tests/Models/UserOnCallShiftReminderModels.test.ts +368 -0
  164. package/Tests/Server/API/GlobalConfigLicense.test.ts +657 -0
  165. package/Tests/Server/API/Helpers.ts +8 -0
  166. package/Tests/Server/API/OnCallCalendarAPI.test.ts +4461 -0
  167. package/Tests/Server/API/SecurityEventAttributesAPI.test.ts +84 -6
  168. package/Tests/Server/API/TelemetryResolveStackTraceAPI.test.ts +805 -0
  169. package/Tests/Server/EnvironmentConfigOnCallCalendarFeed.test.ts +357 -0
  170. package/Tests/Server/Infrastructure/OnCallCalendarFeedCache.test.ts +1589 -0
  171. package/Tests/Server/Infrastructure/Postgres/AddOnCallCalendarFeedsMigration.test.ts +394 -0
  172. package/Tests/Server/Middleware/IdentityRateLimit.test.ts +1144 -0
  173. package/Tests/Server/Middleware/MultipartFormData.test.ts +618 -3
  174. package/Tests/Server/Middleware/OnCallCalendarFeedRateLimit.test.ts +1365 -0
  175. package/Tests/Server/Services/FeedRetentionConsistency.test.ts +70 -0
  176. package/Tests/Server/Services/MonitorLabelRuleEngineScale.test.ts +520 -0
  177. package/Tests/Server/Services/NetworkDeviceOidTemplateService.test.ts +332 -0
  178. package/Tests/Server/Services/NetworkDeviceOidTemplateWriteGuards.test.ts +409 -0
  179. package/Tests/Server/Services/OnCallCalendarFeedServices.test.ts +1103 -0
  180. package/Tests/Server/Services/OnCallDutyPolicyScheduleResolver.test.ts +1037 -0
  181. package/Tests/Server/Services/OnCallShiftConfigPropagation.test.ts +1270 -0
  182. package/Tests/Server/Services/RuleEngineRuleFetchLimit.test.ts +239 -0
  183. package/Tests/Server/Services/TeamDeleteMemberCleanup.test.ts +156 -0
  184. package/Tests/Server/Services/TeamMemberOnCallCleanup.test.ts +755 -0
  185. package/Tests/Server/Services/TelemetrySourceMapService.test.ts +1210 -2
  186. package/Tests/Server/Services/UserNotificationSettingShiftReminderDefaults.test.ts +267 -0
  187. package/Tests/Server/Services/UserOnCallShiftReminderServices.test.ts +583 -0
  188. package/Tests/Server/Services/UserServiceSeatLimit.test.ts +182 -0
  189. package/Tests/Server/Types/AnalyticsDatabase/SecurityEventModelPermission.test.ts +255 -0
  190. package/Tests/Server/Types/Database/Permissions/OnCallCalendarFeedPermissions.test.ts +254 -0
  191. package/Tests/Server/Types/Database/Permissions/ReadBlockPermission.test.ts +212 -0
  192. package/Tests/Server/Types/Database/Permissions/SecurityRoleAccess.test.ts +413 -0
  193. package/Tests/Server/Utils/CodeRepository.test.ts +689 -0
  194. package/Tests/Server/Utils/EnterpriseLicense/EnterpriseLicenseSeatUtil.test.ts +495 -0
  195. package/Tests/Server/Utils/ExceptionSanitizer.test.ts +77 -0
  196. package/Tests/Server/Utils/Monitor/CapturedMetricAttributeUtil.test.ts +284 -0
  197. package/Tests/Server/Utils/Monitor/MonitorCustomMetricAttributes.test.ts +503 -0
  198. package/Tests/Server/Utils/Monitor/MonitorTemplatePrototypePollution.test.ts +106 -0
  199. package/Tests/Server/Utils/Monitor/NetworkDeviceWalkLogWritePath.test.ts +33 -4
  200. package/Tests/Server/Utils/Monitor/NetworkDeviceWalkUtil.test.ts +14 -4
  201. package/Tests/Server/Utils/Monitor/NetworkInventoryUtil.test.ts +44 -0
  202. package/Tests/Server/Utils/OnCall/CalendarFeedToken.test.ts +467 -0
  203. package/Tests/Server/Utils/OnCall/OnCallCalendarFeedRenderer.test.ts +2142 -0
  204. package/Tests/Server/Utils/OnCall/OnCallCalendarFeedUrls.test.ts +278 -0
  205. package/Tests/Server/Utils/OnCall/OnCallResolverTestHarness.ts +440 -0
  206. package/Tests/Server/Utils/OnCall/OnCallShiftChangeListeners.test.ts +314 -0
  207. package/Tests/Server/Utils/OnCall/OnCallShiftMaterializer.test.ts +1502 -0
  208. package/Tests/Server/Utils/OnCall/OnCallShiftReminderListener.test.ts +491 -0
  209. package/Tests/Server/Utils/OnCall/OnCallShiftReminderRunner.test.ts +3088 -0
  210. package/Tests/Server/Utils/OnCall/OnCallShiftReminderTestHarness.ts +910 -0
  211. package/Tests/Server/Utils/OpenAPISpec.test.ts +536 -0
  212. package/Tests/Server/Utils/ResponseSendCalendarResponse.test.ts +561 -0
  213. package/Tests/Server/Utils/Rules/RuleEngineRuleRead.test.ts +115 -0
  214. package/Tests/Server/Utils/StackTraceParser.test.ts +610 -0
  215. package/Tests/Server/Utils/StartServerEncryptionSecretWarning.test.ts +64 -0
  216. package/Tests/Server/Utils/Telemetry/AppMetrics.test.ts +29 -0
  217. package/Tests/Server/Utils/Telemetry/LogExceptionExtractor.test.ts +0 -0
  218. package/Tests/Server/Utils/Telemetry/SourceMapLimits.test.ts +656 -0
  219. package/Tests/Server/Utils/Telemetry/SourceMapResolver.test.ts +100 -0
  220. package/Tests/Types/Calendar/ICalendar.test.ts +488 -0
  221. package/Tests/Types/Monitor/SnmpMonitor/SnmpOidListUtil.test.ts +454 -0
  222. package/Tests/Types/NotificationSetting/NotificationSettingEventType.test.ts +53 -0
  223. package/Tests/Types/OnCallDutyPolicy/CalendarFeedTestFixtures.ts +310 -0
  224. package/Tests/Types/OnCallDutyPolicy/CalendarFeedWindow.test.ts +205 -0
  225. package/Tests/Types/OnCallDutyPolicy/LayerUtilLayerMetaAndIterationCap.test.ts +458 -0
  226. package/Tests/Types/OnCallDutyPolicy/MaterializedShift.test.ts +197 -0
  227. package/Tests/Types/OnCallDutyPolicy/OnCallCalendarFeedUtil.test.ts +1986 -0
  228. package/Tests/Types/OnCallDutyPolicy/ScheduleShiftUtilGroupKey.test.ts +678 -0
  229. package/Tests/Types/OnCallDutyPolicy/ShiftSeamUtil.test.ts +417 -0
  230. package/Tests/Types/SecurityRolePermissions.test.ts +193 -0
  231. package/Tests/UI/Components/Charts/AnnotationLayout.test.ts +773 -0
  232. package/Tests/UI/Components/Charts/ChartAnnotationRail.test.tsx +789 -0
  233. package/Tests/UI/Components/Charts/ChartBucketIdentity.test.ts +254 -0
  234. package/Tests/UI/Components/Charts/TimeAnnotation.test.ts +471 -0
  235. package/Tests/UI/Components/EditionLabelLicenseRefresh.test.tsx +405 -0
  236. package/Tests/UI/Components/ErrorMessageRefreshControl.test.tsx +83 -0
  237. package/Tests/UI/Components/MarkdownConverters.test.ts +686 -0
  238. package/Tests/UI/Components/ModelTable/BaseModelTableDeleteAndEmptyStates.test.tsx +341 -0
  239. package/Tests/UI/Components/OrderedStatesList.test.tsx +5 -5
  240. package/Tests/UI/Components/PendingProjectInvitations.test.tsx +1 -1
  241. package/Tests/UI/Components/TableSortAndMobileColumns.test.tsx +195 -0
  242. package/Tests/UI/Components/XAxis.test.ts +270 -5
  243. package/Tests/UI/Components/XAxisDaylightSaving.test.ts +113 -0
  244. package/Tests/UI/Styles/ChartFocusRing.test.ts +153 -0
  245. package/Tests/UI/Styles/ChartFocusRingCoverage.test.tsx +377 -0
  246. package/Tests/UI/Styles/ThemeStylesheet.ts +162 -0
  247. package/Tests/UI/Utils/Breadcrumb/fixtures/RealBreadcrumbTrails.ts +10 -0
  248. package/Tests/UI/Utils/Breadcrumb/fixtures/RealRoutePatterns.ts +2 -0
  249. package/Tests/Utils/EnterpriseLicenseSeats.test.ts +507 -0
  250. package/Tests/Utils/NetworkDiscovery/DiscoveredDeviceBuilder.test.ts +951 -1
  251. package/Tests/Utils/NetworkDiscovery/DiscoveredHostUtil.test.ts +238 -0
  252. package/Tests/Utils/NetworkDiscovery/DiscoveryReverseDnsChain.test.ts +1056 -0
  253. package/Tests/Utils/NetworkDiscovery/ReverseDnsNameUtil.test.ts +882 -0
  254. package/Types/Calendar/ICalendar.ts +442 -0
  255. package/Types/Date.ts +39 -0
  256. package/Types/Email/EmailTemplateType.ts +2 -0
  257. package/Types/Monitor/SnmpMonitor/SnmpOidListUtil.ts +333 -0
  258. package/Types/NotificationSetting/NotificationSettingEventType.ts +4 -0
  259. package/Types/OnCallDutyPolicy/CalendarFeedWindow.ts +140 -0
  260. package/Types/OnCallDutyPolicy/Layer.ts +190 -35
  261. package/Types/OnCallDutyPolicy/MaterializedShift.ts +274 -0
  262. package/Types/OnCallDutyPolicy/OnCallCalendarFeedUtil.ts +1415 -0
  263. package/Types/OnCallDutyPolicy/ScheduleShiftUtil.ts +159 -4
  264. package/Types/OnCallDutyPolicy/ShiftSeamUtil.ts +106 -0
  265. package/Types/Permission.ts +96 -0
  266. package/Types/Rum/SessionReplay.ts +21 -0
  267. package/Types/Telemetry/SourceMap.ts +8 -0
  268. package/UI/Components/Charts/ChartLibrary/Annotations/AnnotationHoverCard.tsx +176 -0
  269. package/UI/Components/Charts/ChartLibrary/Annotations/AnnotationLayout.ts +745 -0
  270. package/UI/Components/Charts/ChartLibrary/Annotations/ChartAnnotationLayer.tsx +576 -0
  271. package/UI/Components/Charts/ChartLibrary/Annotations/UseChartAnnotations.tsx +204 -0
  272. package/UI/Components/Charts/ChartLibrary/AreaChart/AreaChart.tsx +491 -544
  273. package/UI/Components/Charts/ChartLibrary/BarChart/BarChart.tsx +324 -372
  274. package/UI/Components/Charts/ChartLibrary/LineChart/LineChart.tsx +487 -540
  275. package/UI/Components/Charts/ChartLibrary/Types/FormattedReferenceRegion.ts +7 -3
  276. package/UI/Components/Charts/ChartLibrary/Types/FormattedTimeReferenceLine.ts +14 -3
  277. package/UI/Components/Charts/Types/ChartEventKind.ts +13 -0
  278. package/UI/Components/Charts/Types/ReferenceRegionProps.ts +6 -0
  279. package/UI/Components/Charts/Types/TimeReferenceLineProps.ts +20 -3
  280. package/UI/Components/Charts/Utils/TimeAnnotation.ts +69 -35
  281. package/UI/Components/Charts/Utils/XAxis.ts +125 -18
  282. package/UI/Components/EditionLabel/EditionLabel.tsx +280 -26
  283. package/UI/Components/ErrorMessage/ErrorMessage.tsx +21 -10
  284. package/UI/Components/Feed/FeedItem.tsx +4 -5
  285. package/UI/Components/Header/HeaderIconDropdownButton.tsx +1 -2
  286. package/UI/Components/Header/UserProfile/UserProfile.tsx +1 -2
  287. package/UI/Components/Image/Image.tsx +20 -3
  288. package/UI/Components/Markdown.tsx/MarkdownConverters.ts +0 -0
  289. package/UI/Components/MemberRoleAssignment/MemberRoleAssignment.tsx +1 -2
  290. package/UI/Components/ModelTable/BaseModelTable.tsx +150 -24
  291. package/UI/Components/Table/TableHeader.tsx +64 -48
  292. package/UI/Components/Table/TableRow.tsx +13 -3
  293. package/UI/Styles/Theme.css +38 -0
  294. package/Utils/EnterpriseLicense/EnterpriseLicenseSeats.ts +271 -0
  295. package/Utils/NetworkDiscovery/AutoImportRuleMatcher.ts +6 -0
  296. package/Utils/NetworkDiscovery/DiscoveredDeviceBuilder.ts +141 -10
  297. package/Utils/NetworkDiscovery/DiscoveredHostUtil.ts +55 -3
  298. package/Utils/NetworkDiscovery/ReverseDnsNameUtil.ts +151 -0
  299. package/Utils/Rules/RuleEngineLimits.ts +32 -0
  300. package/build/dist/Models/AnalyticsModels/SecurityEvent.js +48 -16
  301. package/build/dist/Models/AnalyticsModels/SecurityEvent.js.map +1 -1
  302. package/build/dist/Models/AnalyticsModels/ThreatIntelIndicator.js +10 -5
  303. package/build/dist/Models/AnalyticsModels/ThreatIntelIndicator.js.map +1 -1
  304. package/build/dist/Models/DatabaseModels/AlertSeverity.js +46 -1
  305. package/build/dist/Models/DatabaseModels/AlertSeverity.js.map +1 -1
  306. package/build/dist/Models/DatabaseModels/DetectionRule.js +16 -5
  307. package/build/dist/Models/DatabaseModels/DetectionRule.js.map +1 -1
  308. package/build/dist/Models/DatabaseModels/GoogleSecOpsConnection.js +14 -5
  309. package/build/dist/Models/DatabaseModels/GoogleSecOpsConnection.js.map +1 -1
  310. package/build/dist/Models/DatabaseModels/IncidentSeverity.js +46 -1
  311. package/build/dist/Models/DatabaseModels/IncidentSeverity.js.map +1 -1
  312. package/build/dist/Models/DatabaseModels/Index.js +13 -0
  313. package/build/dist/Models/DatabaseModels/Index.js.map +1 -1
  314. package/build/dist/Models/DatabaseModels/NetworkDevice.js +115 -3
  315. package/build/dist/Models/DatabaseModels/NetworkDevice.js.map +1 -1
  316. package/build/dist/Models/DatabaseModels/NetworkDeviceAutoImportRule.js +88 -0
  317. package/build/dist/Models/DatabaseModels/NetworkDeviceAutoImportRule.js.map +1 -1
  318. package/build/dist/Models/DatabaseModels/NetworkDeviceDiscoveryScan.js.map +1 -1
  319. package/build/dist/Models/DatabaseModels/NetworkDeviceOidTemplate.js +519 -0
  320. package/build/dist/Models/DatabaseModels/NetworkDeviceOidTemplate.js.map +1 -0
  321. package/build/dist/Models/DatabaseModels/OnCallDutyPolicySchedule.js +44 -0
  322. package/build/dist/Models/DatabaseModels/OnCallDutyPolicySchedule.js.map +1 -1
  323. package/build/dist/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.js +699 -0
  324. package/build/dist/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.js.map +1 -0
  325. package/build/dist/Models/DatabaseModels/ProjectOnCallCalendarFeed.js +620 -0
  326. package/build/dist/Models/DatabaseModels/ProjectOnCallCalendarFeed.js.map +1 -0
  327. package/build/dist/Models/DatabaseModels/ThreatIntelFeed.js +16 -5
  328. package/build/dist/Models/DatabaseModels/ThreatIntelFeed.js.map +1 -1
  329. package/build/dist/Models/DatabaseModels/UserOnCallCalendarFeed.js +585 -0
  330. package/build/dist/Models/DatabaseModels/UserOnCallCalendarFeed.js.map +1 -0
  331. package/build/dist/Models/DatabaseModels/UserOnCallShiftReminder.js +247 -0
  332. package/build/dist/Models/DatabaseModels/UserOnCallShiftReminder.js.map +1 -0
  333. package/build/dist/Models/DatabaseModels/UserOnCallShiftReminderLog.js +355 -0
  334. package/build/dist/Models/DatabaseModels/UserOnCallShiftReminderLog.js.map +1 -0
  335. package/build/dist/Server/API/GlobalConfigAPI.js +293 -176
  336. package/build/dist/Server/API/GlobalConfigAPI.js.map +1 -1
  337. package/build/dist/Server/API/OnCallCalendarAPI.js +1371 -0
  338. package/build/dist/Server/API/OnCallCalendarAPI.js.map +1 -0
  339. package/build/dist/Server/API/TelemetryAPI.js +31 -3
  340. package/build/dist/Server/API/TelemetryAPI.js.map +1 -1
  341. package/build/dist/Server/EnvironmentConfig.js +185 -0
  342. package/build/dist/Server/EnvironmentConfig.js.map +1 -1
  343. package/build/dist/Server/Infrastructure/OnCallCalendarFeedCache.js +663 -0
  344. package/build/dist/Server/Infrastructure/OnCallCalendarFeedCache.js.map +1 -0
  345. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790400000000-AddOnCallCalendarFeeds.js +103 -0
  346. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790400000000-AddOnCallCalendarFeeds.js.map +1 -0
  347. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790500000000-AddNetworkDeviceOidTemplate.js +26 -0
  348. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790500000000-AddNetworkDeviceOidTemplate.js.map +1 -0
  349. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790600000000-AddAutoImportRuleOidTemplate.js +14 -0
  350. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1790600000000-AddAutoImportRuleOidTemplate.js.map +1 -0
  351. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js +6 -0
  352. package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js.map +1 -1
  353. package/build/dist/Server/Middleware/MultipartFormData.js +93 -28
  354. package/build/dist/Server/Middleware/MultipartFormData.js.map +1 -1
  355. package/build/dist/Server/Middleware/OnCallCalendarFeedRateLimit.js +342 -0
  356. package/build/dist/Server/Middleware/OnCallCalendarFeedRateLimit.js.map +1 -0
  357. package/build/dist/Server/Services/AlertEpisodeLabelRuleEngineService.js +8 -1
  358. package/build/dist/Server/Services/AlertEpisodeLabelRuleEngineService.js.map +1 -1
  359. package/build/dist/Server/Services/AlertEpisodeOnCallRuleEngineService.js +8 -1
  360. package/build/dist/Server/Services/AlertEpisodeOnCallRuleEngineService.js.map +1 -1
  361. package/build/dist/Server/Services/AlertEpisodeOwnerRuleEngineService.js +8 -1
  362. package/build/dist/Server/Services/AlertEpisodeOwnerRuleEngineService.js.map +1 -1
  363. package/build/dist/Server/Services/AlertEpisodePrivacyRuleEngineService.js +8 -1
  364. package/build/dist/Server/Services/AlertEpisodePrivacyRuleEngineService.js.map +1 -1
  365. package/build/dist/Server/Services/AlertGroupingEngineService.js +8 -1
  366. package/build/dist/Server/Services/AlertGroupingEngineService.js.map +1 -1
  367. package/build/dist/Server/Services/AlertLabelRuleEngineService.js +8 -1
  368. package/build/dist/Server/Services/AlertLabelRuleEngineService.js.map +1 -1
  369. package/build/dist/Server/Services/AlertOnCallRuleEngineService.js +8 -1
  370. package/build/dist/Server/Services/AlertOnCallRuleEngineService.js.map +1 -1
  371. package/build/dist/Server/Services/AlertOwnerRuleEngineService.js +8 -1
  372. package/build/dist/Server/Services/AlertOwnerRuleEngineService.js.map +1 -1
  373. package/build/dist/Server/Services/AlertPrivacyRuleEngineService.js +8 -1
  374. package/build/dist/Server/Services/AlertPrivacyRuleEngineService.js.map +1 -1
  375. package/build/dist/Server/Services/AlertReminderRuleService.js +8 -1
  376. package/build/dist/Server/Services/AlertReminderRuleService.js.map +1 -1
  377. package/build/dist/Server/Services/AutoRemediationRuleEngineService.js +8 -1
  378. package/build/dist/Server/Services/AutoRemediationRuleEngineService.js.map +1 -1
  379. package/build/dist/Server/Services/CephClusterLabelRuleEngineService.js +8 -1
  380. package/build/dist/Server/Services/CephClusterLabelRuleEngineService.js.map +1 -1
  381. package/build/dist/Server/Services/CephClusterOwnerRuleEngineService.js +8 -1
  382. package/build/dist/Server/Services/CephClusterOwnerRuleEngineService.js.map +1 -1
  383. package/build/dist/Server/Services/CloudResourceLabelRuleEngineService.js +8 -1
  384. package/build/dist/Server/Services/CloudResourceLabelRuleEngineService.js.map +1 -1
  385. package/build/dist/Server/Services/CloudResourceOwnerRuleEngineService.js +8 -1
  386. package/build/dist/Server/Services/CloudResourceOwnerRuleEngineService.js.map +1 -1
  387. package/build/dist/Server/Services/DashboardLabelRuleEngineService.js +8 -1
  388. package/build/dist/Server/Services/DashboardLabelRuleEngineService.js.map +1 -1
  389. package/build/dist/Server/Services/DashboardOwnerRuleEngineService.js +8 -1
  390. package/build/dist/Server/Services/DashboardOwnerRuleEngineService.js.map +1 -1
  391. package/build/dist/Server/Services/DockerHostLabelRuleEngineService.js +8 -1
  392. package/build/dist/Server/Services/DockerHostLabelRuleEngineService.js.map +1 -1
  393. package/build/dist/Server/Services/DockerHostOwnerRuleEngineService.js +8 -1
  394. package/build/dist/Server/Services/DockerHostOwnerRuleEngineService.js.map +1 -1
  395. package/build/dist/Server/Services/DockerSwarmClusterLabelRuleEngineService.js +8 -1
  396. package/build/dist/Server/Services/DockerSwarmClusterLabelRuleEngineService.js.map +1 -1
  397. package/build/dist/Server/Services/DockerSwarmClusterOwnerRuleEngineService.js +8 -1
  398. package/build/dist/Server/Services/DockerSwarmClusterOwnerRuleEngineService.js.map +1 -1
  399. package/build/dist/Server/Services/HostLabelRuleEngineService.js +8 -1
  400. package/build/dist/Server/Services/HostLabelRuleEngineService.js.map +1 -1
  401. package/build/dist/Server/Services/HostOwnerRuleEngineService.js +8 -1
  402. package/build/dist/Server/Services/HostOwnerRuleEngineService.js.map +1 -1
  403. package/build/dist/Server/Services/IncidentEpisodeLabelRuleEngineService.js +8 -1
  404. package/build/dist/Server/Services/IncidentEpisodeLabelRuleEngineService.js.map +1 -1
  405. package/build/dist/Server/Services/IncidentEpisodeOnCallRuleEngineService.js +8 -1
  406. package/build/dist/Server/Services/IncidentEpisodeOnCallRuleEngineService.js.map +1 -1
  407. package/build/dist/Server/Services/IncidentEpisodeOwnerRuleEngineService.js +8 -1
  408. package/build/dist/Server/Services/IncidentEpisodeOwnerRuleEngineService.js.map +1 -1
  409. package/build/dist/Server/Services/IncidentEpisodePrivacyRuleEngineService.js +8 -1
  410. package/build/dist/Server/Services/IncidentEpisodePrivacyRuleEngineService.js.map +1 -1
  411. package/build/dist/Server/Services/IncidentGroupingEngineService.js +8 -1
  412. package/build/dist/Server/Services/IncidentGroupingEngineService.js.map +1 -1
  413. package/build/dist/Server/Services/IncidentLabelRuleEngineService.js +8 -1
  414. package/build/dist/Server/Services/IncidentLabelRuleEngineService.js.map +1 -1
  415. package/build/dist/Server/Services/IncidentOnCallRuleEngineService.js +8 -1
  416. package/build/dist/Server/Services/IncidentOnCallRuleEngineService.js.map +1 -1
  417. package/build/dist/Server/Services/IncidentOwnerRuleEngineService.js +8 -1
  418. package/build/dist/Server/Services/IncidentOwnerRuleEngineService.js.map +1 -1
  419. package/build/dist/Server/Services/IncidentPrivacyRuleEngineService.js +8 -1
  420. package/build/dist/Server/Services/IncidentPrivacyRuleEngineService.js.map +1 -1
  421. package/build/dist/Server/Services/IncidentReminderRuleService.js +8 -1
  422. package/build/dist/Server/Services/IncidentReminderRuleService.js.map +1 -1
  423. package/build/dist/Server/Services/IncidentSlaRuleService.js +8 -1
  424. package/build/dist/Server/Services/IncidentSlaRuleService.js.map +1 -1
  425. package/build/dist/Server/Services/IncomingCallPolicyLabelRuleEngineService.js +8 -1
  426. package/build/dist/Server/Services/IncomingCallPolicyLabelRuleEngineService.js.map +1 -1
  427. package/build/dist/Server/Services/IncomingCallPolicyOwnerRuleEngineService.js +8 -1
  428. package/build/dist/Server/Services/IncomingCallPolicyOwnerRuleEngineService.js.map +1 -1
  429. package/build/dist/Server/Services/Index.js +14 -0
  430. package/build/dist/Server/Services/Index.js.map +1 -1
  431. package/build/dist/Server/Services/IoTFleetLabelRuleEngineService.js +8 -1
  432. package/build/dist/Server/Services/IoTFleetLabelRuleEngineService.js.map +1 -1
  433. package/build/dist/Server/Services/IoTFleetOwnerRuleEngineService.js +8 -1
  434. package/build/dist/Server/Services/IoTFleetOwnerRuleEngineService.js.map +1 -1
  435. package/build/dist/Server/Services/KubernetesClusterLabelRuleEngineService.js +8 -1
  436. package/build/dist/Server/Services/KubernetesClusterLabelRuleEngineService.js.map +1 -1
  437. package/build/dist/Server/Services/KubernetesClusterOwnerRuleEngineService.js +8 -1
  438. package/build/dist/Server/Services/KubernetesClusterOwnerRuleEngineService.js.map +1 -1
  439. package/build/dist/Server/Services/KubernetesResourceService.js +5 -1
  440. package/build/dist/Server/Services/KubernetesResourceService.js.map +1 -1
  441. package/build/dist/Server/Services/MonitorLabelRuleEngineService.js +8 -1
  442. package/build/dist/Server/Services/MonitorLabelRuleEngineService.js.map +1 -1
  443. package/build/dist/Server/Services/MonitorOwnerRuleEngineService.js +8 -1
  444. package/build/dist/Server/Services/MonitorOwnerRuleEngineService.js.map +1 -1
  445. package/build/dist/Server/Services/NetworkDeviceAutoImportRuleEngineService.js +30 -21
  446. package/build/dist/Server/Services/NetworkDeviceAutoImportRuleEngineService.js.map +1 -1
  447. package/build/dist/Server/Services/NetworkDeviceAutoImportRuleService.js +64 -0
  448. package/build/dist/Server/Services/NetworkDeviceAutoImportRuleService.js.map +1 -1
  449. package/build/dist/Server/Services/NetworkDeviceLabelRuleEngineService.js +8 -1
  450. package/build/dist/Server/Services/NetworkDeviceLabelRuleEngineService.js.map +1 -1
  451. package/build/dist/Server/Services/NetworkDeviceOidTemplateService.js +180 -0
  452. package/build/dist/Server/Services/NetworkDeviceOidTemplateService.js.map +1 -0
  453. package/build/dist/Server/Services/NetworkDeviceOwnerRuleEngineService.js +8 -1
  454. package/build/dist/Server/Services/NetworkDeviceOwnerRuleEngineService.js.map +1 -1
  455. package/build/dist/Server/Services/NetworkDeviceService.js +154 -1
  456. package/build/dist/Server/Services/NetworkDeviceService.js.map +1 -1
  457. package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.js +20 -0
  458. package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.js.map +1 -1
  459. package/build/dist/Server/Services/OnCallDutyPolicyLabelRuleEngineService.js +8 -1
  460. package/build/dist/Server/Services/OnCallDutyPolicyLabelRuleEngineService.js.map +1 -1
  461. package/build/dist/Server/Services/OnCallDutyPolicyOwnerRuleEngineService.js +8 -1
  462. package/build/dist/Server/Services/OnCallDutyPolicyOwnerRuleEngineService.js.map +1 -1
  463. package/build/dist/Server/Services/OnCallDutyPolicyScheduleCalendarFeedService.js +219 -0
  464. package/build/dist/Server/Services/OnCallDutyPolicyScheduleCalendarFeedService.js.map +1 -0
  465. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLabelRuleEngineService.js +8 -1
  466. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLabelRuleEngineService.js.map +1 -1
  467. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLayerService.js +47 -3
  468. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLayerService.js.map +1 -1
  469. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLayerUserService.js +112 -3
  470. package/build/dist/Server/Services/OnCallDutyPolicyScheduleLayerUserService.js.map +1 -1
  471. package/build/dist/Server/Services/OnCallDutyPolicyScheduleOwnerRuleEngineService.js +8 -1
  472. package/build/dist/Server/Services/OnCallDutyPolicyScheduleOwnerRuleEngineService.js.map +1 -1
  473. package/build/dist/Server/Services/OnCallDutyPolicyScheduleService.js +955 -9
  474. package/build/dist/Server/Services/OnCallDutyPolicyScheduleService.js.map +1 -1
  475. package/build/dist/Server/Services/OnCallDutyPolicyUserOverrideService.js +93 -6
  476. package/build/dist/Server/Services/OnCallDutyPolicyUserOverrideService.js.map +1 -1
  477. package/build/dist/Server/Services/PodmanHostLabelRuleEngineService.js +8 -1
  478. package/build/dist/Server/Services/PodmanHostLabelRuleEngineService.js.map +1 -1
  479. package/build/dist/Server/Services/PodmanHostOwnerRuleEngineService.js +8 -1
  480. package/build/dist/Server/Services/PodmanHostOwnerRuleEngineService.js.map +1 -1
  481. package/build/dist/Server/Services/ProjectOnCallCalendarFeedService.js +157 -0
  482. package/build/dist/Server/Services/ProjectOnCallCalendarFeedService.js.map +1 -0
  483. package/build/dist/Server/Services/ProxmoxClusterLabelRuleEngineService.js +8 -1
  484. package/build/dist/Server/Services/ProxmoxClusterLabelRuleEngineService.js.map +1 -1
  485. package/build/dist/Server/Services/ProxmoxClusterOwnerRuleEngineService.js +8 -1
  486. package/build/dist/Server/Services/ProxmoxClusterOwnerRuleEngineService.js.map +1 -1
  487. package/build/dist/Server/Services/RumApplicationLabelRuleEngineService.js +8 -1
  488. package/build/dist/Server/Services/RumApplicationLabelRuleEngineService.js.map +1 -1
  489. package/build/dist/Server/Services/RumApplicationOwnerRuleEngineService.js +8 -1
  490. package/build/dist/Server/Services/RumApplicationOwnerRuleEngineService.js.map +1 -1
  491. package/build/dist/Server/Services/RunbookLabelRuleEngineService.js +8 -1
  492. package/build/dist/Server/Services/RunbookLabelRuleEngineService.js.map +1 -1
  493. package/build/dist/Server/Services/RunbookOwnerRuleEngineService.js +8 -1
  494. package/build/dist/Server/Services/RunbookOwnerRuleEngineService.js.map +1 -1
  495. package/build/dist/Server/Services/RunbookRuleEngineService.js +8 -1
  496. package/build/dist/Server/Services/RunbookRuleEngineService.js.map +1 -1
  497. package/build/dist/Server/Services/ScheduledMaintenanceLabelRuleEngineService.js +8 -1
  498. package/build/dist/Server/Services/ScheduledMaintenanceLabelRuleEngineService.js.map +1 -1
  499. package/build/dist/Server/Services/ScheduledMaintenanceOwnerRuleEngineService.js +8 -1
  500. package/build/dist/Server/Services/ScheduledMaintenanceOwnerRuleEngineService.js.map +1 -1
  501. package/build/dist/Server/Services/ScheduledMaintenanceReminderRuleService.js +8 -1
  502. package/build/dist/Server/Services/ScheduledMaintenanceReminderRuleService.js.map +1 -1
  503. package/build/dist/Server/Services/ServerlessFunctionLabelRuleEngineService.js +8 -1
  504. package/build/dist/Server/Services/ServerlessFunctionLabelRuleEngineService.js.map +1 -1
  505. package/build/dist/Server/Services/ServerlessFunctionOwnerRuleEngineService.js +8 -1
  506. package/build/dist/Server/Services/ServerlessFunctionOwnerRuleEngineService.js.map +1 -1
  507. package/build/dist/Server/Services/ServiceLabelRuleEngineService.js +8 -1
  508. package/build/dist/Server/Services/ServiceLabelRuleEngineService.js.map +1 -1
  509. package/build/dist/Server/Services/ServiceOwnerRuleEngineService.js +8 -1
  510. package/build/dist/Server/Services/ServiceOwnerRuleEngineService.js.map +1 -1
  511. package/build/dist/Server/Services/StatusPageLabelRuleEngineService.js +8 -1
  512. package/build/dist/Server/Services/StatusPageLabelRuleEngineService.js.map +1 -1
  513. package/build/dist/Server/Services/StatusPageMonitorRuleEngineService.js +6 -0
  514. package/build/dist/Server/Services/StatusPageMonitorRuleEngineService.js.map +1 -1
  515. package/build/dist/Server/Services/StatusPageOwnerRuleEngineService.js +8 -1
  516. package/build/dist/Server/Services/StatusPageOwnerRuleEngineService.js.map +1 -1
  517. package/build/dist/Server/Services/TeamMemberService.js +396 -1
  518. package/build/dist/Server/Services/TeamMemberService.js.map +1 -1
  519. package/build/dist/Server/Services/TeamService.js +43 -0
  520. package/build/dist/Server/Services/TeamService.js.map +1 -1
  521. package/build/dist/Server/Services/TelemetrySourceMapService.js +213 -19
  522. package/build/dist/Server/Services/TelemetrySourceMapService.js.map +1 -1
  523. package/build/dist/Server/Services/UserNotificationSettingService.js +26 -1
  524. package/build/dist/Server/Services/UserNotificationSettingService.js.map +1 -1
  525. package/build/dist/Server/Services/UserOnCallCalendarFeedService.js +140 -0
  526. package/build/dist/Server/Services/UserOnCallCalendarFeedService.js.map +1 -0
  527. package/build/dist/Server/Services/UserOnCallShiftReminderLogService.js +116 -0
  528. package/build/dist/Server/Services/UserOnCallShiftReminderLogService.js.map +1 -0
  529. package/build/dist/Server/Services/UserOnCallShiftReminderService.js +92 -0
  530. package/build/dist/Server/Services/UserOnCallShiftReminderService.js.map +1 -0
  531. package/build/dist/Server/Services/UserService.js +25 -0
  532. package/build/dist/Server/Services/UserService.js.map +1 -1
  533. package/build/dist/Server/Services/WorkflowLabelRuleEngineService.js +8 -1
  534. package/build/dist/Server/Services/WorkflowLabelRuleEngineService.js.map +1 -1
  535. package/build/dist/Server/Services/WorkflowOwnerRuleEngineService.js +8 -1
  536. package/build/dist/Server/Services/WorkflowOwnerRuleEngineService.js.map +1 -1
  537. package/build/dist/Server/Utils/EnterpriseLicense/EnterpriseLicenseSeatUtil.js +145 -0
  538. package/build/dist/Server/Utils/EnterpriseLicense/EnterpriseLicenseSeatUtil.js.map +1 -0
  539. package/build/dist/Server/Utils/Monitor/CapturedMetricAttributeUtil.js +201 -0
  540. package/build/dist/Server/Utils/Monitor/CapturedMetricAttributeUtil.js.map +1 -0
  541. package/build/dist/Server/Utils/Monitor/Criteria/SnmpMonitorCriteria.js +19 -2
  542. package/build/dist/Server/Utils/Monitor/Criteria/SnmpMonitorCriteria.js.map +1 -1
  543. package/build/dist/Server/Utils/Monitor/MonitorMetricUtil.js +42 -23
  544. package/build/dist/Server/Utils/Monitor/MonitorMetricUtil.js.map +1 -1
  545. package/build/dist/Server/Utils/Monitor/MonitorTemplateUtil.js +29 -0
  546. package/build/dist/Server/Utils/Monitor/MonitorTemplateUtil.js.map +1 -1
  547. package/build/dist/Server/Utils/Monitor/NetworkDeviceMetricUtil.js +11 -2
  548. package/build/dist/Server/Utils/Monitor/NetworkDeviceMetricUtil.js.map +1 -1
  549. package/build/dist/Server/Utils/Monitor/NetworkDeviceWalkUtil.js +16 -1
  550. package/build/dist/Server/Utils/Monitor/NetworkDeviceWalkUtil.js.map +1 -1
  551. package/build/dist/Server/Utils/Monitor/NetworkInventoryUtil.js +10 -0
  552. package/build/dist/Server/Utils/Monitor/NetworkInventoryUtil.js.map +1 -1
  553. package/build/dist/Server/Utils/Monitor/SeriesResourceLabels.js +33 -0
  554. package/build/dist/Server/Utils/Monitor/SeriesResourceLabels.js.map +1 -1
  555. package/build/dist/Server/Utils/OnCall/CalendarFeedToken.js +161 -0
  556. package/build/dist/Server/Utils/OnCall/CalendarFeedToken.js.map +1 -0
  557. package/build/dist/Server/Utils/OnCall/OnCallCalendarFeedRenderer.js +983 -0
  558. package/build/dist/Server/Utils/OnCall/OnCallCalendarFeedRenderer.js.map +1 -0
  559. package/build/dist/Server/Utils/OnCall/OnCallCalendarFeedUrls.js +155 -0
  560. package/build/dist/Server/Utils/OnCall/OnCallCalendarFeedUrls.js.map +1 -0
  561. package/build/dist/Server/Utils/OnCall/OnCallShiftChangeListeners.js +145 -0
  562. package/build/dist/Server/Utils/OnCall/OnCallShiftChangeListeners.js.map +1 -0
  563. package/build/dist/Server/Utils/OnCall/OnCallShiftMaterializer.js +752 -0
  564. package/build/dist/Server/Utils/OnCall/OnCallShiftMaterializer.js.map +1 -0
  565. package/build/dist/Server/Utils/OnCall/OnCallShiftReminderListener.js +92 -0
  566. package/build/dist/Server/Utils/OnCall/OnCallShiftReminderListener.js.map +1 -0
  567. package/build/dist/Server/Utils/OnCall/OnCallShiftReminderRunner.js +1786 -0
  568. package/build/dist/Server/Utils/OnCall/OnCallShiftReminderRunner.js.map +1 -0
  569. package/build/dist/Server/Utils/Response.js +97 -0
  570. package/build/dist/Server/Utils/Response.js.map +1 -1
  571. package/build/dist/Server/Utils/Rules/RuleEngineRuleRead.js +37 -0
  572. package/build/dist/Server/Utils/Rules/RuleEngineRuleRead.js.map +1 -0
  573. package/build/dist/Server/Utils/StartServer.js +9 -1
  574. package/build/dist/Server/Utils/StartServer.js.map +1 -1
  575. package/build/dist/Server/Utils/Telemetry/AppMetrics.js +41 -0
  576. package/build/dist/Server/Utils/Telemetry/AppMetrics.js.map +1 -1
  577. package/build/dist/Server/Utils/Telemetry/ExceptionSanitizer.js +12 -1
  578. package/build/dist/Server/Utils/Telemetry/ExceptionSanitizer.js.map +1 -1
  579. package/build/dist/Server/Utils/Telemetry/LogExceptionExtractor.js +14 -2
  580. package/build/dist/Server/Utils/Telemetry/LogExceptionExtractor.js.map +1 -1
  581. package/build/dist/Server/Utils/Telemetry/SourceMapResolver.js +15 -5
  582. package/build/dist/Server/Utils/Telemetry/SourceMapResolver.js.map +1 -1
  583. package/build/dist/Server/Utils/Telemetry/StackTraceParser.js +307 -0
  584. package/build/dist/Server/Utils/Telemetry/StackTraceParser.js.map +1 -1
  585. package/build/dist/Types/Calendar/ICalendar.js +290 -0
  586. package/build/dist/Types/Calendar/ICalendar.js.map +1 -0
  587. package/build/dist/Types/Date.js +27 -0
  588. package/build/dist/Types/Date.js.map +1 -1
  589. package/build/dist/Types/Email/EmailTemplateType.js +2 -0
  590. package/build/dist/Types/Email/EmailTemplateType.js.map +1 -1
  591. package/build/dist/Types/Monitor/SnmpMonitor/SnmpOidListUtil.js +253 -0
  592. package/build/dist/Types/Monitor/SnmpMonitor/SnmpOidListUtil.js.map +1 -0
  593. package/build/dist/Types/NotificationSetting/NotificationSettingEventType.js +3 -0
  594. package/build/dist/Types/NotificationSetting/NotificationSettingEventType.js.map +1 -1
  595. package/build/dist/Types/OnCallDutyPolicy/CalendarFeedWindow.js +97 -0
  596. package/build/dist/Types/OnCallDutyPolicy/CalendarFeedWindow.js.map +1 -0
  597. package/build/dist/Types/OnCallDutyPolicy/Layer.js +113 -19
  598. package/build/dist/Types/OnCallDutyPolicy/Layer.js.map +1 -1
  599. package/build/dist/Types/OnCallDutyPolicy/MaterializedShift.js +134 -0
  600. package/build/dist/Types/OnCallDutyPolicy/MaterializedShift.js.map +1 -0
  601. package/build/dist/Types/OnCallDutyPolicy/OnCallCalendarFeedUtil.js +800 -0
  602. package/build/dist/Types/OnCallDutyPolicy/OnCallCalendarFeedUtil.js.map +1 -0
  603. package/build/dist/Types/OnCallDutyPolicy/ScheduleShiftUtil.js +97 -3
  604. package/build/dist/Types/OnCallDutyPolicy/ScheduleShiftUtil.js.map +1 -1
  605. package/build/dist/Types/OnCallDutyPolicy/ShiftSeamUtil.js +77 -0
  606. package/build/dist/Types/OnCallDutyPolicy/ShiftSeamUtil.js.map +1 -0
  607. package/build/dist/Types/Permission.js +86 -0
  608. package/build/dist/Types/Permission.js.map +1 -1
  609. package/build/dist/Types/Rum/SessionReplay.js +19 -0
  610. package/build/dist/Types/Rum/SessionReplay.js.map +1 -1
  611. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/AnnotationHoverCard.js +83 -0
  612. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/AnnotationHoverCard.js.map +1 -0
  613. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/AnnotationLayout.js +531 -0
  614. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/AnnotationLayout.js.map +1 -0
  615. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/ChartAnnotationLayer.js +264 -0
  616. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/ChartAnnotationLayer.js.map +1 -0
  617. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/UseChartAnnotations.js +122 -0
  618. package/build/dist/UI/Components/Charts/ChartLibrary/Annotations/UseChartAnnotations.js.map +1 -0
  619. package/build/dist/UI/Components/Charts/ChartLibrary/AreaChart/AreaChart.js +213 -233
  620. package/build/dist/UI/Components/Charts/ChartLibrary/AreaChart/AreaChart.js.map +1 -1
  621. package/build/dist/UI/Components/Charts/ChartLibrary/BarChart/BarChart.js +139 -152
  622. package/build/dist/UI/Components/Charts/ChartLibrary/BarChart/BarChart.js.map +1 -1
  623. package/build/dist/UI/Components/Charts/ChartLibrary/LineChart/LineChart.js +212 -232
  624. package/build/dist/UI/Components/Charts/ChartLibrary/LineChart/LineChart.js.map +1 -1
  625. package/build/dist/UI/Components/Charts/Types/ChartEventKind.js +14 -0
  626. package/build/dist/UI/Components/Charts/Types/ChartEventKind.js.map +1 -0
  627. package/build/dist/UI/Components/Charts/Utils/TimeAnnotation.js +57 -28
  628. package/build/dist/UI/Components/Charts/Utils/TimeAnnotation.js.map +1 -1
  629. package/build/dist/UI/Components/Charts/Utils/XAxis.js +103 -17
  630. package/build/dist/UI/Components/Charts/Utils/XAxis.js.map +1 -1
  631. package/build/dist/UI/Components/EditionLabel/EditionLabel.js +198 -23
  632. package/build/dist/UI/Components/EditionLabel/EditionLabel.js.map +1 -1
  633. package/build/dist/UI/Components/ErrorMessage/ErrorMessage.js +15 -5
  634. package/build/dist/UI/Components/ErrorMessage/ErrorMessage.js.map +1 -1
  635. package/build/dist/UI/Components/Feed/FeedItem.js +4 -5
  636. package/build/dist/UI/Components/Feed/FeedItem.js.map +1 -1
  637. package/build/dist/UI/Components/Header/HeaderIconDropdownButton.js +1 -2
  638. package/build/dist/UI/Components/Header/HeaderIconDropdownButton.js.map +1 -1
  639. package/build/dist/UI/Components/Header/UserProfile/UserProfile.js.map +1 -1
  640. package/build/dist/UI/Components/Image/Image.js +6 -1
  641. package/build/dist/UI/Components/Image/Image.js.map +1 -1
  642. package/build/dist/UI/Components/Markdown.tsx/MarkdownConverters.js +0 -0
  643. package/build/dist/UI/Components/Markdown.tsx/MarkdownConverters.js.map +1 -1
  644. package/build/dist/UI/Components/MemberRoleAssignment/MemberRoleAssignment.js +1 -2
  645. package/build/dist/UI/Components/MemberRoleAssignment/MemberRoleAssignment.js.map +1 -1
  646. package/build/dist/UI/Components/ModelTable/BaseModelTable.js +104 -23
  647. package/build/dist/UI/Components/ModelTable/BaseModelTable.js.map +1 -1
  648. package/build/dist/UI/Components/Table/TableHeader.js +20 -22
  649. package/build/dist/UI/Components/Table/TableHeader.js.map +1 -1
  650. package/build/dist/UI/Components/Table/TableRow.js +13 -4
  651. package/build/dist/UI/Components/Table/TableRow.js.map +1 -1
  652. package/build/dist/Utils/EnterpriseLicense/EnterpriseLicenseSeats.js +153 -0
  653. package/build/dist/Utils/EnterpriseLicense/EnterpriseLicenseSeats.js.map +1 -0
  654. package/build/dist/Utils/NetworkDiscovery/AutoImportRuleMatcher.js.map +1 -1
  655. package/build/dist/Utils/NetworkDiscovery/DiscoveredDeviceBuilder.js +127 -7
  656. package/build/dist/Utils/NetworkDiscovery/DiscoveredDeviceBuilder.js.map +1 -1
  657. package/build/dist/Utils/NetworkDiscovery/DiscoveredHostUtil.js +50 -3
  658. package/build/dist/Utils/NetworkDiscovery/DiscoveredHostUtil.js.map +1 -1
  659. package/build/dist/Utils/NetworkDiscovery/ReverseDnsNameUtil.js +132 -0
  660. package/build/dist/Utils/NetworkDiscovery/ReverseDnsNameUtil.js.map +1 -0
  661. package/build/dist/Utils/Rules/RuleEngineLimits.js +31 -0
  662. package/build/dist/Utils/Rules/RuleEngineLimits.js.map +1 -0
  663. package/jest.config.json +1 -0
  664. package/package.json +2 -2
@@ -0,0 +1,910 @@
1
+ import { jest } from "@jest/globals";
2
+ import DatabaseConfig from "../../../../Server/DatabaseConfig";
3
+ import GlobalCache from "../../../../Server/Infrastructure/GlobalCache";
4
+ import Semaphore, {
5
+ SemaphoreMutex,
6
+ } from "../../../../Server/Infrastructure/Semaphore";
7
+ import OnCallDutyPolicyScheduleService from "../../../../Server/Services/OnCallDutyPolicyScheduleService";
8
+ import UserNotificationSettingService from "../../../../Server/Services/UserNotificationSettingService";
9
+ import UserOnCallShiftReminderLogService from "../../../../Server/Services/UserOnCallShiftReminderLogService";
10
+ import UserOnCallShiftReminderService from "../../../../Server/Services/UserOnCallShiftReminderService";
11
+ import UserService from "../../../../Server/Services/UserService";
12
+ import logger from "../../../../Server/Utils/Logger";
13
+ import Telemetry from "../../../../Server/Utils/Telemetry";
14
+ import OnCallShiftMaterializer, {
15
+ MaterializeResult,
16
+ MaterializedScheduleInfo,
17
+ MaterializedUserInfo,
18
+ } from "../../../../Server/Utils/OnCall/OnCallShiftMaterializer";
19
+ import UserOnCallShiftReminderLog, {
20
+ UserOnCallShiftReminderLogKind,
21
+ } from "../../../../Models/DatabaseModels/UserOnCallShiftReminderLog";
22
+ import URL from "../../../../Types/API/URL";
23
+ import OneUptimeDate from "../../../../Types/Date";
24
+ import NotificationSettingEventType from "../../../../Types/NotificationSetting/NotificationSettingEventType";
25
+ import ObjectID from "../../../../Types/ObjectID";
26
+ import {
27
+ MaterializedShift,
28
+ MaterializedShiftPolicy,
29
+ } from "../../../../Types/OnCallDutyPolicy/MaterializedShift";
30
+ import { matchesQuery } from "./OnCallResolverTestHarness";
31
+
32
+ /*
33
+ * In-memory stand-ins for everything OnCallShiftReminderRunner touches, so
34
+ * the REAL runner code runs end to end (watermark, lateness cap, claim ->
35
+ * send -> stamp, change pass) against rows the tests can inspect:
36
+ *
37
+ * - UserOnCallShiftReminder rows (the configured lead times),
38
+ * - the UserOnCallShiftReminderLog ledger, with the UNIQUE index enforced
39
+ * the way Postgres would (a duplicate insert throws a unique violation),
40
+ * - the materializer (answered from fixture MaterializedShifts),
41
+ * - UserNotificationSetting rows (present / absent per event type) and
42
+ * sendUserNotification (recorded, optionally failing),
43
+ * - GlobalCache (the watermark), Semaphore (the sweep lock), the dashboard
44
+ * URL and the telemetry counter.
45
+ *
46
+ * Every collaborator is a jest.spyOn on the module singleton; restore with
47
+ * jest.restoreAllMocks().
48
+ */
49
+
50
+ export interface FakeReminder {
51
+ projectId: ObjectID;
52
+ userId: ObjectID;
53
+ minutesBeforeShift: number;
54
+ }
55
+
56
+ export interface FakeLedgerRow {
57
+ _id: ObjectID;
58
+ id: ObjectID;
59
+ projectId: ObjectID;
60
+ userId: ObjectID;
61
+ onCallDutyPolicyScheduleId: ObjectID;
62
+ shiftStartsAt: Date;
63
+ minutesBeforeShift: number;
64
+ kind: UserOnCallShiftReminderLogKind;
65
+ claimedAt: Date;
66
+ sentAt: Date | null;
67
+ }
68
+
69
+ export interface SentNotification {
70
+ userId: string;
71
+ projectId: string;
72
+ eventType: NotificationSettingEventType;
73
+ templateType: string;
74
+ subject: string;
75
+ vars: Record<string, string>;
76
+ smsText: string;
77
+ pushTitle: string;
78
+ pushBody: string;
79
+ // undefined when the runner sent no WhatsApp payload at all.
80
+ whatsAppTemplateKey: string | undefined;
81
+ whatsAppBody: string | undefined;
82
+ onCallScheduleId: string | undefined;
83
+ onCallPolicyId: string | undefined;
84
+ onCallPolicyEscalationRuleId: string | undefined;
85
+ }
86
+
87
+ export interface MaterializeCall {
88
+ scheduleIds: Array<string>;
89
+ windowStart: Date;
90
+ windowEnd: Date;
91
+ now: Date | undefined;
92
+ }
93
+
94
+ export interface MetricRecord {
95
+ value: number;
96
+ attributes: Record<string, unknown>;
97
+ }
98
+
99
+ export interface ReminderHarness {
100
+ reminders: Array<FakeReminder>;
101
+ ledger: Array<FakeLedgerRow>;
102
+ shifts: Array<MaterializedShift>;
103
+ schedules: Map<string, MaterializedScheduleInfo>;
104
+ users: Array<MaterializedUserInfo>;
105
+ // userId -> candidate schedule ids; absent = derived from `shifts`.
106
+ candidateSchedules: Map<string, Array<string>>;
107
+ // "userId|projectId|eventType" for every settings row that exists.
108
+ settings: Set<string>;
109
+ cache: Map<string, string>;
110
+ sent: Array<SentNotification>;
111
+ materializeCalls: Array<MaterializeCall>;
112
+ candidateCalls: Array<{ userIds: Array<string>; projectIds: Array<string> }>;
113
+ /*
114
+ * Users UserService can resolve that materialization does NOT return —
115
+ * somebody just removed from the layer, or from the project. The change
116
+ * pass looks them up so their notice is formatted in their own timezone.
117
+ */
118
+ directory: Array<MaterializedUserInfo>;
119
+ // One entry per UserService.findBy the runner made, with the ids it asked for.
120
+ userLookupCalls: Array<Array<string>>;
121
+ metrics: Array<MetricRecord>;
122
+ // Return an Error to make the NEXT send throw; null to deliver.
123
+ failSend: (call: SentNotification) => Error | null;
124
+ // Throw from every reminder-table read.
125
+ remindersReadError: Error | null;
126
+ // Throw from materializeForSchedules for these schedule ids.
127
+ materializeErrorForSchedules: Set<string>;
128
+ // Whether Semaphore.lock succeeds.
129
+ lockAvailable: boolean;
130
+ lockCalls: Array<Record<string, unknown>>;
131
+ releasedMutexes: Array<SemaphoreMutex>;
132
+ cacheReadError: Error | null;
133
+ cacheWriteError: Error | null;
134
+ // Schedules known to OnCallDutyPolicyScheduleService (id -> projectId).
135
+ scheduleProjects: Map<string, ObjectID>;
136
+ warnings: Array<string>;
137
+ errors: Array<unknown>;
138
+ nextLedgerId: number;
139
+ // Runs before the fake ledger insert; lets a test inject a concurrent row.
140
+ beforeLedgerInsert: (() => void) | null;
141
+ reclaimUpdateOverride: number | null;
142
+ }
143
+
144
+ export const HARNESS_DASHBOARD_URL: string =
145
+ "https://oneuptime.example.com/dashboard";
146
+
147
+ /*
148
+ * The runner caches its telemetry counter in a static field the first time
149
+ * it records anything, so the fake counter must resolve the CURRENT harness
150
+ * on every add rather than closing over the one that happened to be
151
+ * installed when the counter was created.
152
+ */
153
+ let activeHarness: ReminderHarness | null = null;
154
+
155
+ export function settingsKey(data: {
156
+ userId: ObjectID | string;
157
+ projectId: ObjectID | string;
158
+ eventType: NotificationSettingEventType;
159
+ }): string {
160
+ return `${data.userId.toString()}|${data.projectId.toString()}|${data.eventType}`;
161
+ }
162
+
163
+ export function scheduleInfo(data: {
164
+ scheduleId: string;
165
+ scheduleName?: string | undefined;
166
+ projectId: string;
167
+ scheduleTimezone?: string | undefined;
168
+ truncated?: boolean | undefined;
169
+ attachedPolicies?: Array<MaterializedShiftPolicy> | undefined;
170
+ }): MaterializedScheduleInfo {
171
+ const info: MaterializedScheduleInfo = {
172
+ scheduleId: data.scheduleId,
173
+ scheduleName: data.scheduleName ?? "Payments",
174
+ projectId: data.projectId,
175
+ shiftConfigVersion: 1,
176
+ lastModifiedAt: OneUptimeDate.fromString("2026-08-01T10:00:00Z"),
177
+ truncated: data.truncated ?? false,
178
+ attachedPolicies: data.attachedPolicies ?? [],
179
+ layerProps: [],
180
+ scheduleUserIds: [],
181
+ };
182
+
183
+ if (data.scheduleTimezone !== undefined) {
184
+ info.scheduleTimezone = data.scheduleTimezone;
185
+ }
186
+
187
+ return info;
188
+ }
189
+
190
+ export function emptyHarness(): ReminderHarness {
191
+ return {
192
+ reminders: [],
193
+ ledger: [],
194
+ shifts: [],
195
+ schedules: new Map<string, MaterializedScheduleInfo>(),
196
+ users: [],
197
+ candidateSchedules: new Map<string, Array<string>>(),
198
+ settings: new Set<string>(),
199
+ cache: new Map<string, string>(),
200
+ sent: [],
201
+ materializeCalls: [],
202
+ candidateCalls: [],
203
+ directory: [],
204
+ userLookupCalls: [],
205
+ metrics: [],
206
+ failSend: (): Error | null => {
207
+ return null;
208
+ },
209
+ remindersReadError: null,
210
+ materializeErrorForSchedules: new Set<string>(),
211
+ lockAvailable: true,
212
+ lockCalls: [],
213
+ releasedMutexes: [],
214
+ cacheReadError: null,
215
+ cacheWriteError: null,
216
+ scheduleProjects: new Map<string, ObjectID>(),
217
+ warnings: [],
218
+ errors: [],
219
+ nextLedgerId: 1,
220
+ beforeLedgerInsert: null,
221
+ reclaimUpdateOverride: null,
222
+ };
223
+ }
224
+
225
+ function toKey(value: unknown): string {
226
+ if (value === null || value === undefined) {
227
+ return "";
228
+ }
229
+
230
+ return String(value);
231
+ }
232
+
233
+ function truncateToMinute(date: Date): Date {
234
+ const copy: Date = new Date(date.getTime());
235
+ copy.setUTCSeconds(0, 0);
236
+ return copy;
237
+ }
238
+
239
+ function uniqueKeyOf(row: {
240
+ userId: ObjectID | string;
241
+ onCallDutyPolicyScheduleId: ObjectID | string;
242
+ shiftStartsAt: Date;
243
+ minutesBeforeShift: number;
244
+ kind: string;
245
+ }): string {
246
+ return [
247
+ toKey(row.userId),
248
+ toKey(row.onCallDutyPolicyScheduleId),
249
+ truncateToMinute(row.shiftStartsAt).getTime(),
250
+ row.minutesBeforeShift,
251
+ row.kind,
252
+ ].join("|");
253
+ }
254
+
255
+ export class UniqueViolationError extends Error {
256
+ public postgresErrorCode: string = "23505";
257
+
258
+ public constructor() {
259
+ super("duplicate key value violates unique constraint");
260
+ }
261
+ }
262
+
263
+ /** Inserts a ledger row directly (a pre-existing claim, another replica's work). */
264
+ export function seedLedgerRow(
265
+ harness: ReminderHarness,
266
+ data: {
267
+ projectId: ObjectID;
268
+ userId: ObjectID;
269
+ scheduleId: ObjectID | string;
270
+ shiftStartsAt: Date;
271
+ minutesBeforeShift: number;
272
+ kind: UserOnCallShiftReminderLogKind;
273
+ claimedAt: Date;
274
+ sentAt: Date | null;
275
+ },
276
+ ): FakeLedgerRow {
277
+ const id: ObjectID = new ObjectID(`ledger-${harness.nextLedgerId++}`);
278
+ const row: FakeLedgerRow = {
279
+ _id: id,
280
+ id,
281
+ projectId: data.projectId,
282
+ userId: data.userId,
283
+ onCallDutyPolicyScheduleId: new ObjectID(data.scheduleId.toString()),
284
+ shiftStartsAt: truncateToMinute(data.shiftStartsAt),
285
+ minutesBeforeShift: data.minutesBeforeShift,
286
+ kind: data.kind,
287
+ claimedAt: data.claimedAt,
288
+ sentAt: data.sentAt,
289
+ };
290
+
291
+ const key: string = uniqueKeyOf(row);
292
+
293
+ for (const existing of harness.ledger) {
294
+ if (uniqueKeyOf(existing) === key) {
295
+ throw new UniqueViolationError();
296
+ }
297
+ }
298
+
299
+ harness.ledger.push(row);
300
+
301
+ return row;
302
+ }
303
+
304
+ function fakeCreate(
305
+ harness: ReminderHarness,
306
+ ): (args: {
307
+ data: UserOnCallShiftReminderLog;
308
+ }) => Promise<UserOnCallShiftReminderLog> {
309
+ return (args: {
310
+ data: UserOnCallShiftReminderLog;
311
+ }): Promise<UserOnCallShiftReminderLog> => {
312
+ const data: UserOnCallShiftReminderLog = args.data;
313
+
314
+ if (
315
+ !data.projectId ||
316
+ !data.userId ||
317
+ !data.onCallDutyPolicyScheduleId ||
318
+ !data.shiftStartsAt ||
319
+ !data.kind
320
+ ) {
321
+ return Promise.reject(new Error("fake ledger: missing required column"));
322
+ }
323
+
324
+ if (harness.beforeLedgerInsert) {
325
+ harness.beforeLedgerInsert();
326
+ }
327
+
328
+ try {
329
+ const row: FakeLedgerRow = seedLedgerRow(harness, {
330
+ projectId: data.projectId,
331
+ userId: data.userId,
332
+ scheduleId: data.onCallDutyPolicyScheduleId,
333
+ shiftStartsAt: data.shiftStartsAt,
334
+ minutesBeforeShift: data.minutesBeforeShift ?? 0,
335
+ kind: data.kind,
336
+ claimedAt: data.claimedAt || new Date(),
337
+ sentAt: null,
338
+ });
339
+
340
+ const created: UserOnCallShiftReminderLog =
341
+ new UserOnCallShiftReminderLog();
342
+ created.id = row.id;
343
+
344
+ return Promise.resolve(created);
345
+ } catch (err) {
346
+ return Promise.reject(err);
347
+ }
348
+ };
349
+ }
350
+
351
+ function fakeLedgerFindBy(
352
+ harness: ReminderHarness,
353
+ ): (args: {
354
+ query?: Record<string, unknown>;
355
+ }) => Promise<Array<UserOnCallShiftReminderLog>> {
356
+ return (args: {
357
+ query?: Record<string, unknown>;
358
+ }): Promise<Array<UserOnCallShiftReminderLog>> => {
359
+ const rows: Array<FakeLedgerRow> = harness.ledger.filter(
360
+ (row: FakeLedgerRow) => {
361
+ return matchesQuery(
362
+ args.query,
363
+ row as unknown as Record<string, unknown>,
364
+ );
365
+ },
366
+ );
367
+
368
+ // Copies: the runner must not be able to mutate the "database" by reference.
369
+ return Promise.resolve(
370
+ rows.map((row: FakeLedgerRow) => {
371
+ return { ...row } as unknown as UserOnCallShiftReminderLog;
372
+ }),
373
+ );
374
+ };
375
+ }
376
+
377
+ function fakeUpdateOneBy(
378
+ harness: ReminderHarness,
379
+ ): (args: {
380
+ query: Record<string, unknown>;
381
+ data: Record<string, unknown>;
382
+ }) => Promise<number> {
383
+ return (args: {
384
+ query: Record<string, unknown>;
385
+ data: Record<string, unknown>;
386
+ }): Promise<number> => {
387
+ if (harness.reclaimUpdateOverride !== null) {
388
+ return Promise.resolve(harness.reclaimUpdateOverride);
389
+ }
390
+
391
+ let count: number = 0;
392
+
393
+ for (const row of harness.ledger) {
394
+ if (matchesQuery(args.query, row as unknown as Record<string, unknown>)) {
395
+ Object.assign(row, args.data);
396
+ count++;
397
+ }
398
+ }
399
+
400
+ return Promise.resolve(count);
401
+ };
402
+ }
403
+
404
+ function fakeUpdateOneById(
405
+ harness: ReminderHarness,
406
+ ): (args: { id: ObjectID; data: Record<string, unknown> }) => Promise<void> {
407
+ return (args: {
408
+ id: ObjectID;
409
+ data: Record<string, unknown>;
410
+ }): Promise<void> => {
411
+ for (const row of harness.ledger) {
412
+ if (toKey(row._id) === toKey(args.id)) {
413
+ Object.assign(row, args.data);
414
+ }
415
+ }
416
+
417
+ return Promise.resolve();
418
+ };
419
+ }
420
+
421
+ function fakeDeleteOneBy(
422
+ harness: ReminderHarness,
423
+ ): (args: { query: Record<string, unknown> }) => Promise<void> {
424
+ return (args: { query: Record<string, unknown> }): Promise<void> => {
425
+ harness.ledger = harness.ledger.filter((row: FakeLedgerRow) => {
426
+ return !matchesQuery(
427
+ args.query,
428
+ row as unknown as Record<string, unknown>,
429
+ );
430
+ });
431
+
432
+ return Promise.resolve();
433
+ };
434
+ }
435
+
436
+ function fakeDeleteBy(
437
+ harness: ReminderHarness,
438
+ ): (args: {
439
+ query: Record<string, unknown>;
440
+ limit?: number;
441
+ }) => Promise<number> {
442
+ return (args: {
443
+ query: Record<string, unknown>;
444
+ limit?: number;
445
+ }): Promise<number> => {
446
+ const limit: number = args.limit ?? Number.MAX_SAFE_INTEGER;
447
+ let deleted: number = 0;
448
+
449
+ harness.ledger = harness.ledger.filter((row: FakeLedgerRow) => {
450
+ if (
451
+ deleted < limit &&
452
+ matchesQuery(args.query, row as unknown as Record<string, unknown>)
453
+ ) {
454
+ deleted++;
455
+ return false;
456
+ }
457
+
458
+ return true;
459
+ });
460
+
461
+ return Promise.resolve(deleted);
462
+ };
463
+ }
464
+
465
+ function fakeMaterialize(
466
+ harness: ReminderHarness,
467
+ ): (args: {
468
+ scheduleIds: Array<ObjectID>;
469
+ windowStart: Date;
470
+ windowEnd: Date;
471
+ now?: Date | undefined;
472
+ }) => Promise<MaterializeResult> {
473
+ return (args: {
474
+ scheduleIds: Array<ObjectID>;
475
+ windowStart: Date;
476
+ windowEnd: Date;
477
+ now?: Date | undefined;
478
+ }): Promise<MaterializeResult> => {
479
+ const ids: Array<string> = args.scheduleIds.map((id: ObjectID) => {
480
+ return id.toString();
481
+ });
482
+
483
+ harness.materializeCalls.push({
484
+ scheduleIds: ids,
485
+ windowStart: args.windowStart,
486
+ windowEnd: args.windowEnd,
487
+ now: args.now,
488
+ });
489
+
490
+ for (const id of ids) {
491
+ if (harness.materializeErrorForSchedules.has(id)) {
492
+ return Promise.reject(new Error(`materialize failed for ${id}`));
493
+ }
494
+ }
495
+
496
+ const shifts: Array<MaterializedShift> = harness.shifts.filter(
497
+ (shift: MaterializedShift) => {
498
+ return (
499
+ ids.includes(shift.scheduleId) &&
500
+ shift.start.getTime() < args.windowEnd.getTime() &&
501
+ shift.end.getTime() > args.windowStart.getTime()
502
+ );
503
+ },
504
+ );
505
+
506
+ const schedules: Array<MaterializedScheduleInfo> = [];
507
+
508
+ for (const id of ids) {
509
+ const info: MaterializedScheduleInfo | undefined =
510
+ harness.schedules.get(id);
511
+
512
+ if (info) {
513
+ schedules.push(info);
514
+ }
515
+ }
516
+
517
+ return Promise.resolve({
518
+ shifts,
519
+ truncated: schedules.some((schedule: MaterializedScheduleInfo) => {
520
+ return schedule.truncated;
521
+ }),
522
+ schedules,
523
+ users: harness.users,
524
+ generatedAt: args.now || new Date(),
525
+ });
526
+ };
527
+ }
528
+
529
+ function candidatesOf(
530
+ harness: ReminderHarness,
531
+ userKey: string,
532
+ ): Array<ObjectID> {
533
+ const explicit: Array<string> | undefined =
534
+ harness.candidateSchedules.get(userKey);
535
+
536
+ if (explicit) {
537
+ return explicit.map((id: string) => {
538
+ return new ObjectID(id);
539
+ });
540
+ }
541
+
542
+ const derived: Set<string> = new Set<string>();
543
+
544
+ for (const shift of harness.shifts) {
545
+ if (shift.userId === userKey) {
546
+ derived.add(shift.scheduleId);
547
+ }
548
+ }
549
+
550
+ return Array.from(derived).map((id: string) => {
551
+ return new ObjectID(id);
552
+ });
553
+ }
554
+
555
+ /*
556
+ * The batched lookup the runner uses: ONE call per project, every reminded
557
+ * user in it. `candidateCalls` records what it was asked for so the tests can
558
+ * pin that the sweep never goes back to a per-user query.
559
+ */
560
+ function fakeCandidatesForUsers(
561
+ harness: ReminderHarness,
562
+ ): (args: {
563
+ userIds: Array<ObjectID>;
564
+ projectIds?: Array<ObjectID> | undefined;
565
+ }) => Promise<Map<string, Array<ObjectID>>> {
566
+ return (args: {
567
+ userIds: Array<ObjectID>;
568
+ projectIds?: Array<ObjectID> | undefined;
569
+ }): Promise<Map<string, Array<ObjectID>>> => {
570
+ const userKeys: Array<string> = args.userIds.map((id: ObjectID) => {
571
+ return id.toString();
572
+ });
573
+
574
+ harness.candidateCalls.push({
575
+ userIds: userKeys,
576
+ projectIds: (args.projectIds || []).map((id: ObjectID) => {
577
+ return id.toString();
578
+ }),
579
+ });
580
+
581
+ const result: Map<string, Array<ObjectID>> = new Map<
582
+ string,
583
+ Array<ObjectID>
584
+ >();
585
+
586
+ for (const userKey of userKeys) {
587
+ result.set(userKey, candidatesOf(harness, userKey));
588
+ }
589
+
590
+ return Promise.resolve(result);
591
+ };
592
+ }
593
+
594
+ function reminderRows(
595
+ harness: ReminderHarness,
596
+ query: Record<string, unknown> | undefined,
597
+ ): Array<Record<string, unknown>> {
598
+ return harness.reminders
599
+ .map((reminder: FakeReminder, index: number) => {
600
+ return {
601
+ _id: new ObjectID(`reminder-${index}`),
602
+ id: new ObjectID(`reminder-${index}`),
603
+ projectId: reminder.projectId,
604
+ userId: reminder.userId,
605
+ minutesBeforeShift: reminder.minutesBeforeShift,
606
+ };
607
+ })
608
+ .filter((row: Record<string, unknown>) => {
609
+ return matchesQuery(query, row);
610
+ });
611
+ }
612
+
613
+ function fakeSend(
614
+ harness: ReminderHarness,
615
+ ): (args: Record<string, unknown>) => Promise<void> {
616
+ return (args: Record<string, unknown>): Promise<void> => {
617
+ const emailEnvelope: Record<string, unknown> = (args["emailEnvelope"] ||
618
+ {}) as Record<string, unknown>;
619
+ const smsMessage: Record<string, unknown> = (args["smsMessage"] ||
620
+ {}) as Record<string, unknown>;
621
+ const push: Record<string, unknown> = (args["pushNotificationMessage"] ||
622
+ {}) as Record<string, unknown>;
623
+ const whatsApp: Record<string, unknown> | undefined = args[
624
+ "whatsAppMessage"
625
+ ] as Record<string, unknown> | undefined;
626
+
627
+ const call: SentNotification = {
628
+ userId: toKey(args["userId"]),
629
+ projectId: toKey(args["projectId"]),
630
+ eventType: args["eventType"] as NotificationSettingEventType,
631
+ templateType: toKey(emailEnvelope["templateType"]),
632
+ subject: toKey(emailEnvelope["subject"]),
633
+ vars: (emailEnvelope["vars"] || {}) as Record<string, string>,
634
+ smsText: toKey(smsMessage["message"]),
635
+ pushTitle: toKey(push["title"]),
636
+ pushBody: toKey(push["body"]),
637
+ whatsAppTemplateKey: whatsApp
638
+ ? toKey(whatsApp["templateKey"])
639
+ : undefined,
640
+ whatsAppBody: whatsApp ? toKey(whatsApp["body"]) : undefined,
641
+ onCallScheduleId: args["onCallScheduleId"]
642
+ ? toKey(args["onCallScheduleId"])
643
+ : undefined,
644
+ onCallPolicyId: args["onCallPolicyId"]
645
+ ? toKey(args["onCallPolicyId"])
646
+ : undefined,
647
+ onCallPolicyEscalationRuleId: args["onCallPolicyEscalationRuleId"]
648
+ ? toKey(args["onCallPolicyEscalationRuleId"])
649
+ : undefined,
650
+ };
651
+
652
+ const failure: Error | null = harness.failSend(call);
653
+
654
+ if (failure) {
655
+ return Promise.reject(failure);
656
+ }
657
+
658
+ harness.sent.push(call);
659
+
660
+ return Promise.resolve();
661
+ };
662
+ }
663
+
664
+ /**
665
+ * Spy every collaborator of the runner and answer from `harness`. Call in a
666
+ * test or beforeEach; restore with jest.restoreAllMocks().
667
+ */
668
+ export function installReminderHarness(harness: ReminderHarness): void {
669
+ // Logger: silent, but captured.
670
+ jest.spyOn(logger, "debug").mockImplementation((): void => {
671
+ return undefined;
672
+ });
673
+ jest.spyOn(logger, "info").mockImplementation((): void => {
674
+ return undefined;
675
+ });
676
+ jest.spyOn(logger, "warn").mockImplementation((message: unknown): void => {
677
+ harness.warnings.push(toKey(message));
678
+ return undefined;
679
+ });
680
+ jest.spyOn(logger, "error").mockImplementation((message: unknown): void => {
681
+ harness.errors.push(message);
682
+ return undefined;
683
+ });
684
+
685
+ // Reminder lead times.
686
+ jest
687
+ .spyOn(UserOnCallShiftReminderService, "findAllBy")
688
+ .mockImplementation(((args: { query?: Record<string, unknown> }) => {
689
+ if (harness.remindersReadError) {
690
+ return Promise.reject(harness.remindersReadError);
691
+ }
692
+
693
+ return Promise.resolve(reminderRows(harness, args.query));
694
+ }) as never);
695
+
696
+ jest
697
+ .spyOn(UserOnCallShiftReminderService, "findBy")
698
+ .mockImplementation(((args: { query?: Record<string, unknown> }) => {
699
+ if (harness.remindersReadError) {
700
+ return Promise.reject(harness.remindersReadError);
701
+ }
702
+
703
+ return Promise.resolve(reminderRows(harness, args.query));
704
+ }) as never);
705
+
706
+ // The ledger.
707
+ jest
708
+ .spyOn(UserOnCallShiftReminderLogService, "create")
709
+ .mockImplementation(fakeCreate(harness) as never);
710
+ jest
711
+ .spyOn(UserOnCallShiftReminderLogService, "findBy")
712
+ .mockImplementation(fakeLedgerFindBy(harness) as never);
713
+ jest
714
+ .spyOn(UserOnCallShiftReminderLogService, "updateOneBy")
715
+ .mockImplementation(fakeUpdateOneBy(harness) as never);
716
+ jest
717
+ .spyOn(UserOnCallShiftReminderLogService, "updateOneById")
718
+ .mockImplementation(fakeUpdateOneById(harness) as never);
719
+ jest
720
+ .spyOn(UserOnCallShiftReminderLogService, "deleteOneBy")
721
+ .mockImplementation(fakeDeleteOneBy(harness) as never);
722
+ jest
723
+ .spyOn(UserOnCallShiftReminderLogService, "deleteBy")
724
+ .mockImplementation(fakeDeleteBy(harness) as never);
725
+
726
+ // The materializer.
727
+ jest
728
+ .spyOn(OnCallShiftMaterializer, "materializeForSchedules")
729
+ .mockImplementation(fakeMaterialize(harness) as never);
730
+ jest
731
+ .spyOn(OnCallShiftMaterializer, "getCandidateScheduleIdsForUsers")
732
+ .mockImplementation(fakeCandidatesForUsers(harness) as never);
733
+ jest
734
+ .spyOn(OnCallShiftMaterializer, "getCandidateScheduleIdsForUser")
735
+ .mockImplementation(((args: { userId: ObjectID }) => {
736
+ return Promise.resolve(candidatesOf(harness, args.userId.toString()));
737
+ }) as never);
738
+
739
+ // The user directory, for recipients materialization does not return.
740
+ jest.spyOn(UserService, "findBy").mockImplementation(((args: {
741
+ query?: Record<string, unknown>;
742
+ }) => {
743
+ const rows: Array<Record<string, unknown>> = harness.directory.map(
744
+ (user: MaterializedUserInfo) => {
745
+ return {
746
+ _id: new ObjectID(user.userId),
747
+ id: new ObjectID(user.userId),
748
+ name: user.userName,
749
+ email: user.email,
750
+ timezone: user.timezone,
751
+ };
752
+ },
753
+ );
754
+
755
+ const matched: Array<Record<string, unknown>> = rows.filter(
756
+ (row: Record<string, unknown>) => {
757
+ return matchesQuery(args.query, row);
758
+ },
759
+ );
760
+
761
+ harness.userLookupCalls.push(
762
+ matched.map((row: Record<string, unknown>) => {
763
+ return toKey(row["_id"]);
764
+ }),
765
+ );
766
+
767
+ return Promise.resolve(matched);
768
+ }) as never);
769
+
770
+ // Notification settings + delivery.
771
+ jest
772
+ .spyOn(UserNotificationSettingService, "findOneBy")
773
+ .mockImplementation(((args: { query: Record<string, unknown> }) => {
774
+ const key: string = settingsKey({
775
+ userId: toKey(args.query["userId"]),
776
+ projectId: toKey(args.query["projectId"]),
777
+ eventType: args.query["eventType"] as NotificationSettingEventType,
778
+ });
779
+
780
+ if (harness.settings.has(key)) {
781
+ return Promise.resolve({ _id: "setting", id: new ObjectID("setting") });
782
+ }
783
+
784
+ return Promise.resolve(null);
785
+ }) as never);
786
+ jest
787
+ .spyOn(UserNotificationSettingService, "sendUserNotification")
788
+ .mockImplementation(fakeSend(harness) as never);
789
+
790
+ // Watermark.
791
+ jest.spyOn(GlobalCache, "getString").mockImplementation(((
792
+ namespace: string,
793
+ key: string,
794
+ ) => {
795
+ if (harness.cacheReadError) {
796
+ return Promise.reject(harness.cacheReadError);
797
+ }
798
+
799
+ return Promise.resolve(harness.cache.get(`${namespace}:${key}`) ?? null);
800
+ }) as never);
801
+ jest.spyOn(GlobalCache, "setString").mockImplementation(((
802
+ namespace: string,
803
+ key: string,
804
+ value: string,
805
+ ) => {
806
+ if (harness.cacheWriteError) {
807
+ return Promise.reject(harness.cacheWriteError);
808
+ }
809
+
810
+ harness.cache.set(`${namespace}:${key}`, value);
811
+ return Promise.resolve();
812
+ }) as never);
813
+
814
+ // Sweep lock.
815
+ jest.spyOn(Semaphore, "lock").mockImplementation(((
816
+ options: Record<string, unknown>,
817
+ ) => {
818
+ harness.lockCalls.push(options);
819
+
820
+ if (!harness.lockAvailable) {
821
+ return Promise.reject(new Error("lock held"));
822
+ }
823
+
824
+ return Promise.resolve({
825
+ fake: true,
826
+ key: options["key"],
827
+ } as unknown as SemaphoreMutex);
828
+ }) as never);
829
+ jest.spyOn(Semaphore, "release").mockImplementation(((
830
+ mutex: SemaphoreMutex,
831
+ ) => {
832
+ harness.releasedMutexes.push(mutex);
833
+ return Promise.resolve();
834
+ }) as never);
835
+
836
+ // Dashboard URL.
837
+ jest
838
+ .spyOn(DatabaseConfig, "getDashboardUrl")
839
+ .mockImplementation((): Promise<URL> => {
840
+ return Promise.resolve(URL.fromString(HARNESS_DASHBOARD_URL));
841
+ });
842
+
843
+ // Schedule -> project lookup (change pass without a project id).
844
+ jest
845
+ .spyOn(OnCallDutyPolicyScheduleService, "findBy")
846
+ .mockImplementation(((args: { query?: Record<string, unknown> }) => {
847
+ const rows: Array<Record<string, unknown>> = [];
848
+
849
+ for (const [scheduleId, projectId] of harness.scheduleProjects) {
850
+ rows.push({
851
+ _id: new ObjectID(scheduleId),
852
+ id: new ObjectID(scheduleId),
853
+ projectId,
854
+ });
855
+ }
856
+
857
+ return Promise.resolve(
858
+ rows.filter((row: Record<string, unknown>) => {
859
+ return matchesQuery(args.query, row);
860
+ }),
861
+ );
862
+ }) as never);
863
+
864
+ // Metrics.
865
+ activeHarness = harness;
866
+ jest.spyOn(Telemetry, "getCounter").mockImplementation(((): unknown => {
867
+ return {
868
+ add: (value: number, attributes: Record<string, unknown>): void => {
869
+ if (activeHarness) {
870
+ activeHarness.metrics.push({ value, attributes });
871
+ }
872
+ },
873
+ };
874
+ }) as never);
875
+ }
876
+
877
+ export function ledgerRowsOfKind(
878
+ harness: ReminderHarness,
879
+ kind: UserOnCallShiftReminderLogKind,
880
+ ): Array<FakeLedgerRow> {
881
+ return harness.ledger.filter((row: FakeLedgerRow) => {
882
+ return row.kind === kind;
883
+ });
884
+ }
885
+
886
+ export function watermarkOf(harness: ReminderHarness): string | undefined {
887
+ return harness.cache.get("OnCallShiftReminders:watermark");
888
+ }
889
+
890
+ export function grantSettings(
891
+ harness: ReminderHarness,
892
+ data: { userId: ObjectID; projectId: ObjectID },
893
+ ): void {
894
+ harness.settings.add(
895
+ settingsKey({
896
+ userId: data.userId,
897
+ projectId: data.projectId,
898
+ eventType:
899
+ NotificationSettingEventType.SEND_BEFORE_USER_ON_CALL_SHIFT_STARTS,
900
+ }),
901
+ );
902
+ harness.settings.add(
903
+ settingsKey({
904
+ userId: data.userId,
905
+ projectId: data.projectId,
906
+ eventType:
907
+ NotificationSettingEventType.SEND_WHEN_USER_ON_CALL_SHIFT_IS_REASSIGNED,
908
+ }),
909
+ );
910
+ }