@oneuptime/common 13.0.7 → 13.0.8
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.
- package/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.ts +1 -1
- package/Models/DatabaseModels/ProjectOnCallCalendarFeed.ts +1 -1
- package/Models/DatabaseModels/UserOnCallCalendarFeed.ts +1 -1
- package/Server/API/AIBillingAPI.ts +1 -0
- package/Server/API/AIInsightAPI.ts +1 -4
- package/Server/API/AIInvestigationAPI.ts +1 -4
- package/Server/API/AIReadinessAPI.ts +4 -5
- package/Server/API/AlertAPI.ts +1 -0
- package/Server/API/AutoRemediationAPI.ts +1 -4
- package/Server/API/BaseAPI.ts +13 -0
- package/Server/API/BaseAnalyticsAPI.ts +80 -9
- package/Server/API/BillingAPI.ts +2 -0
- package/Server/API/BillingInvoiceAPI.ts +1 -0
- package/Server/API/BillingPaymentMethodAPI.ts +2 -0
- package/Server/API/CodeFixRunAPI.ts +1 -3
- package/Server/API/CommonAPI.ts +68 -4
- package/Server/API/DashboardAPI.ts +12 -12
- package/Server/API/GlobalConfigAPI.ts +17 -0
- package/Server/API/IncidentAPI.ts +2 -0
- package/Server/API/IncidentEpisodeAPI.ts +1 -0
- package/Server/API/NotificationAPI.ts +1 -0
- package/Server/API/OnCallCalendarAPI.ts +4 -5
- package/Server/API/OnCallDutyPolicyAPI.ts +7 -0
- package/Server/API/OnCallReadinessAPI.ts +4 -1
- package/Server/API/OnCallScheduleTimelineAPI.ts +731 -0
- package/Server/API/ProjectAPI.ts +1 -0
- package/Server/API/ScheduledMaintenanceAPI.ts +1 -0
- package/Server/API/StatusPageAPI.ts +161 -32
- package/Server/API/TeamMemberAPI.ts +3 -0
- package/Server/API/UserCallAPI.ts +2 -0
- package/Server/API/UserEmailAPI.ts +2 -0
- package/Server/API/UserIncomingCallNumberAPI.ts +2 -0
- package/Server/API/UserMicrosoftTeamsAPI.ts +1 -0
- package/Server/API/UserSlackAPI.ts +1 -0
- package/Server/API/UserSmsAPI.ts +2 -0
- package/Server/API/UserTotpAuthAPI.ts +1 -0
- package/Server/API/UserWebAuthnAPI.ts +2 -0
- package/Server/API/UserWebhookAPI.ts +1 -0
- package/Server/API/UserWhatsAppAPI.ts +2 -0
- package/Server/Middleware/MasterAdminAuthorization.ts +13 -2
- package/Server/Middleware/UserAuthorization.ts +79 -5
- package/Server/Services/ApiKeyPermissionService.ts +101 -4
- package/Server/Services/DatabaseService.ts +245 -0
- package/Server/Services/DetectionRuleService.ts +5 -4
- package/Server/Services/OnCallDutyPolicyChildService.ts +261 -0
- package/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.ts +2 -2
- package/Server/Services/OnCallDutyPolicyEscalationRuleService.ts +2 -2
- package/Server/Services/OnCallDutyPolicyEscalationRuleTeamService.ts +2 -2
- package/Server/Services/OnCallDutyPolicyEscalationRuleUserService.ts +2 -2
- package/Server/Services/PayAsYouGoBillingService.ts +23 -28
- package/Server/Services/ProjectService.ts +18 -0
- package/Server/Services/RumSessionPinService.ts +274 -22
- package/Server/Services/TeamPermissionService.ts +120 -26
- package/Server/Services/ThreatIntelFeedService.ts +6 -3
- package/Server/Types/Database/Permissions/BasePermission.ts +9 -7
- package/Server/Types/Database/Permissions/Index.ts +75 -11
- package/Server/Types/Database/Permissions/TablePermission.ts +24 -28
- package/Server/Utils/AI/AIChatPrivacyFilter.ts +8 -0
- package/Server/Utils/AI/AIRunPrivacyFilter.ts +8 -0
- package/Server/Utils/MasterAdminPageAccess.ts +61 -0
- package/Server/Utils/Monitor/MonitorAlert.ts +3 -1
- package/Server/Utils/Monitor/MonitorIncident.ts +3 -1
- package/Server/Utils/OnCall/OnCallCalendarFeedRenderer.ts +1 -1
- package/Server/Utils/Realtime.ts +163 -45
- package/Server/Utils/SecurityEvent/DetectionRuleEvaluator.ts +11 -28
- package/Server/Utils/SecurityEvent/GoogleSecOpsSeverityRepair.ts +170 -0
- package/Server/Utils/SecurityEvent/Sigma/SigmaClickhouseCompiler.ts +1 -1
- package/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelFeedPoller.ts +6 -2
- package/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelMatcher.ts +10 -9
- package/Tests/App/Dashboard/AffectedResourcesPicker.test.tsx +1059 -0
- package/Tests/App/Dashboard/AffectedResourcesPickerEditForm.test.tsx +376 -0
- package/Tests/App/Dashboard/AffectedResourcesPickerHiddenTypes.test.tsx +757 -0
- package/Tests/App/Dashboard/AffectedResourcesSummaryStep.test.tsx +307 -0
- package/Tests/App/Dashboard/ArgumentsFormGroupByUnlistedAttributes.test.tsx +131 -0
- package/Tests/App/Dashboard/DashboardHeaderRequests.test.tsx +1 -1
- package/Tests/App/Dashboard/DashboardMonitorLabelVariable.test.tsx +9 -1
- package/Tests/App/Dashboard/DashboardVariableAllContract.test.tsx +24 -0
- package/Tests/App/Dashboard/DashboardVariableSelector.test.tsx +162 -8
- package/Tests/App/Dashboard/EntityFilterDropdownArchivedSlos.test.tsx +105 -6
- package/Tests/App/Dashboard/EntityFilterDropdownUnlistedSelection.test.tsx +434 -0
- package/Tests/App/Dashboard/EscalationRuleReadiness.test.tsx +276 -1
- package/Tests/App/Dashboard/OnCallCalendarFeedSideMenus.test.tsx +9 -1
- package/Tests/App/Dashboard/PayAsYouGoConsentGate.test.tsx +58 -42
- package/Tests/App/Dashboard/PayAsYouGoNotices.test.tsx +42 -5
- package/Tests/App/Dashboard/ResourceAuditLogsSideMenus.test.tsx +34 -23
- package/Tests/App/Dashboard/ScheduleTimeline.test.tsx +1580 -0
- package/Tests/App/Dashboard/ScheduleTimelineAPI.test.ts +280 -0
- package/Tests/App/Dashboard/ScheduleTimelineModel.test.ts +673 -0
- package/Tests/App/Dashboard/SecurityEventConnectionDiagnostics.test.tsx +95 -68
- package/Tests/App/Dashboard/SecurityEventsDetectionRulesPage.test.tsx +86 -3
- package/Tests/App/Dashboard/SecurityEventsEmptyState.test.tsx +28 -3
- package/Tests/App/Dashboard/SecurityEventsExplorer.test.tsx +761 -0
- package/Tests/App/Dashboard/SecurityEventsGuideContent.test.ts +1313 -0
- package/Tests/App/Dashboard/SecurityEventsHowItWorksCard.test.tsx +536 -0
- package/Tests/App/Dashboard/SecurityEventsNoResults.test.tsx +222 -0
- package/Tests/App/Dashboard/SecurityEventsThreatIntelPage.test.tsx +199 -0
- package/Tests/App/Dashboard/SecurityEventsVolumeChart.test.tsx +321 -0
- package/Tests/App/Dashboard/SloOverviewHero.test.tsx +171 -36
- package/Tests/App/Dashboard/SloViewSideMenu.test.tsx +215 -0
- package/Tests/App/Dashboard/SloViewSideMenuCounts.test.tsx +40 -3
- package/Tests/App/PublicDashboard/DashboardVariableSelector.test.tsx +12 -4
- package/Tests/App/PublicDashboard/PublicDashboardWidgetListAuth.test.tsx +623 -0
- package/Tests/Models/OnCallCalendarFeedModels.test.ts +23 -1
- package/Tests/Server/API/AIChatRouteAuthorization.test.ts +138 -5
- package/Tests/Server/API/AIGenerationProjectAIToggle.test.ts +187 -0
- package/Tests/Server/API/AIInvestigationAvailabilityAuthorization.test.ts +51 -3
- package/Tests/Server/API/AIInvestigationEvidenceAPI.test.ts +55 -2
- package/Tests/Server/API/BaseAnalyticsAPIAggregateCache.test.ts +729 -0
- package/Tests/Server/API/BillingPayAsYouGoStatus.test.ts +93 -7
- package/Tests/Server/API/BillingPaymentMethodAPI.test.ts +36 -3
- package/Tests/Server/API/CommonAPIAuthGuard.test.ts +1003 -24
- package/Tests/Server/API/DashboardPublicRateLimit.test.ts +6 -3
- package/Tests/Server/API/ExpiredSessionAIRoutes.test.ts +708 -0
- package/Tests/Server/API/ExpiredSessionCustomRoutes.test.ts +928 -0
- package/Tests/Server/API/ExpiredSessionMonitorTemplate.test.ts +319 -0
- package/Tests/Server/API/ExpiredSessionOnCallDutyPolicy.test.ts +336 -0
- package/Tests/Server/API/ExpiredSessionRouteGuards.test.ts +820 -0
- package/Tests/Server/API/GlobalConfigLicense.test.ts +140 -0
- package/Tests/Server/API/NotificationChannelVerificationAPI.test.ts +115 -12
- package/Tests/Server/API/OnCallCalendarAPI.test.ts +375 -8
- package/Tests/Server/API/OnCallReadinessAPI.test.ts +175 -17
- package/Tests/Server/API/OnCallScheduleTimelineAPI.test.ts +1513 -0
- package/Tests/Server/API/OnCallSetupReminderAPI.test.ts +119 -7
- package/Tests/Server/API/ProjectScopedCustomRouteAuth.test.ts +111 -4
- package/Tests/Server/API/PublicRouteInvalidAccessToken.test.ts +615 -0
- package/Tests/Server/API/SecurityEventAttributesAPI.test.ts +89 -2
- package/Tests/Server/API/SessionReplayAPI.test.ts +121 -0
- package/Tests/Server/API/StatusPageMasterPasswordRateLimit.test.ts +4 -2
- package/Tests/Server/API/StatusPagePostmortemVisibility.test.ts +441 -0
- package/Tests/Server/API/StatusPageTestEmailReportAuth.test.ts +664 -0
- package/Tests/Server/API/TeamMemberRemoveUserFromProjectAPI.test.ts +7 -0
- package/Tests/Server/API/UserIncomingCallNumberApi.test.ts +6 -0
- package/Tests/Server/API/UserNotificationSettingAPI.test.ts +65 -4
- package/Tests/Server/API/UserProjectsAPI.test.ts +63 -3
- package/Tests/Server/API/UserTotpAuthAPI.test.ts +48 -2
- package/Tests/Server/API/UserWebAuthnAuthenticationOptionsRoute.test.ts +11 -2
- package/Tests/Server/API/UserWebAuthnBackupCodeMinting.test.ts +46 -3
- package/Tests/Server/API/UserWebAuthnPasskeyAPI.test.ts +18 -2
- package/Tests/Server/API/ZZVerifyChatsAuth.test.ts +24 -7
- package/Tests/Server/Middleware/ExpiredSessionUserMiddleware.test.ts +563 -0
- package/Tests/Server/Middleware/MasterAdminAuthorization.test.ts +299 -19
- package/Tests/Server/Middleware/PublicRouteUserMiddleware.test.ts +453 -0
- package/Tests/Server/Services/AIChatPrivacyPin.test.ts +24 -0
- package/Tests/Server/Services/ApiKeyPermissionSecurity.test.ts +2 -0
- package/Tests/Server/Services/ApiKeyPermissionService.test.ts +3 -3
- package/Tests/Server/Services/DatabaseServiceCreateSuppliedId.test.ts +147 -0
- package/Tests/Server/Services/DatabaseServiceLoginBeforeHooks.test.ts +1078 -0
- package/Tests/Server/Services/DatabaseServiceTenantRelationGuard.test.ts +259 -0
- package/Tests/Server/Services/DatabaseServiceWriteOperatorValues.test.ts +147 -0
- package/Tests/Server/Services/MonitorPayAsYouGoBilling.test.ts +115 -1
- package/Tests/Server/Services/OnCallChildCreateAuthorizationPostgres.test.ts +711 -0
- package/Tests/Server/Services/OnCallDutyPolicyChildService.test.ts +733 -0
- package/Tests/Server/Services/PayAsYouGoBillingService.test.ts +190 -140
- package/Tests/Server/Services/PayAsYouGoStripeRateLimitBudget.test.ts +4 -9
- package/Tests/Server/Services/PermissionBlockDeletion.test.ts +780 -0
- package/Tests/Server/Services/PermissionBlockDeletionPostgres.test.ts +628 -0
- package/Tests/Server/Services/ProjectServiceCreateSubscriptionStarted.test.ts +77 -1
- package/Tests/Server/Services/RumSessionPinCreatePermission.test.ts +715 -0
- package/Tests/Server/Services/TeamMemberMultiTenantReadPostgres.test.ts +394 -0
- package/Tests/Server/Services/TeamPrivilegeEscalation.test.ts +6 -0
- package/Tests/Server/Services/TelemetryPayAsYouGoBilling.test.ts +131 -0
- package/Tests/Server/Services/UserNotificationRuleAdminGuards.test.ts +13 -2
- package/Tests/Server/Types/Database/Permissions/ModelPermissionAnonymousRefusal.test.ts +518 -0
- package/Tests/Server/Types/Database/Permissions/MultiTenantPermissions.test.ts +350 -0
- package/Tests/Server/Types/Database/Permissions/OnCallCalendarFeedPermissions.test.ts +282 -25
- package/Tests/Server/Types/Database/Permissions/TableLevelBlockPermission.test.ts +459 -0
- package/Tests/Server/Utils/AI/AIRunPrivacyFilter.test.ts +101 -9
- package/Tests/Server/Utils/AI/ChatAgentHelpers.test.ts +88 -4
- package/Tests/Server/Utils/AI/Toolbox/ExceptionTools.test.ts +459 -0
- package/Tests/Server/Utils/AI/Toolbox/LogTools.test.ts +794 -0
- package/Tests/Server/Utils/AI/Toolbox/RecentChangesTools.test.ts +574 -0
- package/Tests/Server/Utils/AI/Toolbox/SecurityEventTools.test.ts +596 -0
- package/Tests/Server/Utils/CaptchaRequestAndLogging.test.ts +395 -0
- package/Tests/Server/Utils/MasterAdminPageAccess.test.ts +251 -0
- package/Tests/Server/Utils/Monitor/MonitorActionTimestamps.test.ts +616 -0
- package/Tests/Server/Utils/Realtime.test.ts +502 -0
- package/Tests/Server/Utils/SecurityEvent/Connectors/GoogleSecOps/GoogleSecOpsConnectorSeverity.test.ts +216 -0
- package/Tests/Server/Utils/SecurityEvent/DetectionRuleEvaluator.test.ts +142 -0
- package/Tests/Server/Utils/SecurityEvent/GoogleSecOpsSeverityRepair.test.ts +140 -0
- package/Tests/Server/Utils/SecurityEvent/GoogleSecOpsSeverityRepairClickhouseIntegration.test.ts +542 -0
- package/Tests/Server/Utils/Telemetry/ChangeEventRow.test.ts +743 -0
- package/Tests/Server/Utils/Telemetry/RuntimeMetrics.test.ts +465 -0
- package/Tests/Server/Utils/Workspace/MicrosoftTeams/Messages/Alert.test.ts +202 -0
- package/Tests/Server/Utils/Workspace/MicrosoftTeams/Messages/Incident.test.ts +194 -0
- package/Tests/Server/Utils/Workspace/MicrosoftTeams/Messages/ScheduledMaintenance.test.ts +231 -0
- package/Tests/Server/Utils/Workspace/Slack/Messages/Alert.test.ts +194 -0
- package/Tests/Server/Utils/Workspace/Slack/Messages/AlertEpisode.test.ts +194 -0
- package/Tests/Server/Utils/Workspace/Slack/Messages/Incident.test.ts +194 -0
- package/Tests/Server/Utils/Workspace/Slack/Messages/IncidentEpisode.test.ts +194 -0
- package/Tests/Server/Utils/Workspace/Slack/Messages/ScheduledMaintenance.test.ts +247 -0
- package/Tests/Types/AI/AIInsightEvidence.test.ts +206 -0
- package/Tests/Types/BaseDatabase/DatabaseCommonInteractionPropsUtilAnonymous.test.ts +144 -0
- package/Tests/Types/Call/CallProvider.test.ts +528 -0
- package/Tests/Types/Kubernetes/KubernetesCostIngest.test.ts +236 -0
- package/Tests/Types/OnCallDutyPolicy/ScheduleTimeline.test.ts +736 -0
- package/Tests/Types/OnCallDutyPolicy/ScheduleTimelineLayout.test.ts +996 -0
- package/Tests/Types/SecurityEvent/SigmaRule.test.ts +142 -0
- package/Tests/Types/Workflow/Components/JSON.test.ts +182 -0
- package/Tests/UI/Components/BasicFormDropdownNormalization.test.tsx +116 -1
- package/Tests/UI/Components/Dropdown/DropdownAsyncOptions.test.tsx +81 -0
- package/Tests/UI/Components/EditionLabelLicenseRefresh.test.tsx +89 -1
- package/Tests/UI/Components/EventAttachmentList.test.tsx +174 -0
- package/Tests/UI/Components/Forms/BasicFormBurnRateTemplateDefaults.test.tsx +395 -0
- package/Tests/UI/Components/Forms/BasicFormCollapsibleSections.test.tsx +286 -0
- package/Tests/UI/Components/Forms/FormSummary.test.tsx +128 -0
- package/Tests/UI/Components/ModelTable/BaseModelTableQueryChange.test.tsx +365 -0
- package/Tests/UI/Components/OpenAuthenticatedUrl.test.ts +358 -0
- package/Tests/UI/Components/SessionAwareImage.test.tsx +496 -0
- package/Tests/UI/Components/TelemetryHistogramZeroBuckets.test.tsx +190 -0
- package/Tests/UI/Components/TooltipInteractive.test.tsx +97 -0
- package/Tests/UI/MicrosoftTeams/MicrosoftTeamsChatsCardInstallGuidance.test.tsx +1 -1
- package/Tests/UI/Monitor/EvaluationLogListTimestamps.test.tsx +367 -0
- package/Tests/UI/Utils/API/BaseAPIRefreshSession.test.ts +1087 -0
- package/Tests/UI/Utils/API/DashboardHost.ts +12 -0
- package/Tests/UI/Utils/API/FakeAxiosServer.ts +183 -0
- package/Tests/UI/Utils/Breadcrumb/fixtures/RealBreadcrumbTrails.ts +10 -0
- package/Tests/UI/Utils/Breadcrumb/fixtures/RealRoutePatterns.ts +2 -0
- package/Tests/UI/Utils/Cookie.test.ts +440 -0
- package/Tests/UI/Utils/ModelAPIRequestClient.test.ts +278 -0
- package/Tests/UI/Utils/Navigation.test.ts +33 -0
- package/Tests/UI/Utils/PricingPlan.test.ts +295 -0
- package/Tests/UI/Utils/Realtime.test.ts +759 -0
- package/Tests/UI/Utils/Telemetry/Telemetry.test.ts +500 -0
- package/Tests/Utils/APIInstanceDispatch.test.ts +311 -0
- package/Tests/Utils/SecurityEvent/GoogleSecOpsAlertNormalizerSeverity.test.ts +565 -0
- package/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.ts +40 -0
- package/Types/Monitor/MonitorEvaluationSummary.ts +3 -0
- package/Types/OnCallDutyPolicy/ScheduleTimeline.ts +507 -0
- package/Types/OnCallDutyPolicy/ScheduleTimelineLayout.ts +589 -0
- package/Types/Realtime/EventName.ts +11 -0
- package/Types/SecurityEvent/DetectionFindingConstants.ts +14 -0
- package/Types/SecurityEvent/OcsfSeverity.ts +31 -26
- package/Types/SecurityEvent/SigmaRule.ts +51 -0
- package/Types/SecurityEvent/ThreatIntelConstants.ts +18 -0
- package/UI/Components/AttachmentList/EventAttachmentList.tsx +30 -2
- package/UI/Components/Dashboard/DashboardVariableControl.tsx +12 -2
- package/UI/Components/Dropdown/Dropdown.tsx +6 -1
- package/UI/Components/EditionLabel/EditionLabel.tsx +12 -0
- package/UI/Components/EventItem/EventItem.tsx +12 -1
- package/UI/Components/Forms/BasicForm.tsx +151 -126
- package/UI/Components/Forms/CollapsibleFormSection.tsx +63 -0
- package/UI/Components/Forms/Fields/FormField.tsx +10 -4
- package/UI/Components/Forms/FormSummary.tsx +7 -0
- package/UI/Components/Forms/Types/Field.ts +10 -0
- package/UI/Components/Markdown.tsx/MarkdownViewer.tsx +2 -1
- package/UI/Components/Markdown.tsx/SessionAwareImage.tsx +122 -0
- package/UI/Components/ModelTable/BaseModelTable.tsx +34 -5
- package/UI/Components/ModelTable/TableView.tsx +1 -1
- package/UI/Components/TelemetryViewer/components/TelemetryHistogram.tsx +8 -1
- package/UI/Components/Tooltip/Tooltip.tsx +8 -1
- package/UI/Utils/API/API.ts +173 -12
- package/UI/Utils/API/RequestOptions.ts +11 -0
- package/UI/Utils/AnalyticsModelAPI/AnalyticsModelAPI.ts +31 -7
- package/UI/Utils/ModelAPI/ModelAPI.ts +30 -9
- package/UI/Utils/Navigation.ts +9 -0
- package/UI/Utils/OpenAuthenticatedUrl.ts +154 -0
- package/UI/Utils/Realtime.ts +176 -30
- package/Utils/API.ts +14 -5
- package/Utils/SecurityEvent/GoogleSecOpsAlertNormalizer.ts +157 -7
- package/Utils/SecurityEvent/Sigma/SigmaRuleParser.ts +9 -17
- package/Utils/Slo/SloBurnRateTemplate.ts +2 -2
- package/build/dist/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.js +1 -1
- package/build/dist/Models/DatabaseModels/OnCallDutyPolicyScheduleCalendarFeed.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ProjectOnCallCalendarFeed.js +1 -1
- package/build/dist/Models/DatabaseModels/ProjectOnCallCalendarFeed.js.map +1 -1
- package/build/dist/Models/DatabaseModels/UserOnCallCalendarFeed.js +1 -1
- package/build/dist/Models/DatabaseModels/UserOnCallCalendarFeed.js.map +1 -1
- package/build/dist/Server/API/AIBillingAPI.js +1 -1
- package/build/dist/Server/API/AIBillingAPI.js.map +1 -1
- package/build/dist/Server/API/AIInsightAPI.js +1 -4
- package/build/dist/Server/API/AIInsightAPI.js.map +1 -1
- package/build/dist/Server/API/AIInvestigationAPI.js +1 -4
- package/build/dist/Server/API/AIInvestigationAPI.js.map +1 -1
- package/build/dist/Server/API/AIReadinessAPI.js +1 -3
- package/build/dist/Server/API/AIReadinessAPI.js.map +1 -1
- package/build/dist/Server/API/AlertAPI.js +1 -1
- package/build/dist/Server/API/AlertAPI.js.map +1 -1
- package/build/dist/Server/API/AutoRemediationAPI.js +1 -4
- package/build/dist/Server/API/AutoRemediationAPI.js.map +1 -1
- package/build/dist/Server/API/BaseAPI.js +12 -0
- package/build/dist/Server/API/BaseAPI.js.map +1 -1
- package/build/dist/Server/API/BaseAnalyticsAPI.js +55 -10
- package/build/dist/Server/API/BaseAnalyticsAPI.js.map +1 -1
- package/build/dist/Server/API/BillingAPI.js +2 -2
- package/build/dist/Server/API/BillingAPI.js.map +1 -1
- package/build/dist/Server/API/BillingInvoiceAPI.js +1 -1
- package/build/dist/Server/API/BillingInvoiceAPI.js.map +1 -1
- package/build/dist/Server/API/BillingPaymentMethodAPI.js +2 -2
- package/build/dist/Server/API/BillingPaymentMethodAPI.js.map +1 -1
- package/build/dist/Server/API/CodeFixRunAPI.js +1 -3
- package/build/dist/Server/API/CodeFixRunAPI.js.map +1 -1
- package/build/dist/Server/API/CommonAPI.js +50 -5
- package/build/dist/Server/API/CommonAPI.js.map +1 -1
- package/build/dist/Server/API/DashboardAPI.js +12 -12
- package/build/dist/Server/API/DashboardAPI.js.map +1 -1
- package/build/dist/Server/API/GlobalConfigAPI.js +12 -0
- package/build/dist/Server/API/GlobalConfigAPI.js.map +1 -1
- package/build/dist/Server/API/IncidentAPI.js +2 -2
- package/build/dist/Server/API/IncidentAPI.js.map +1 -1
- package/build/dist/Server/API/IncidentEpisodeAPI.js +1 -1
- package/build/dist/Server/API/IncidentEpisodeAPI.js.map +1 -1
- package/build/dist/Server/API/NotificationAPI.js +1 -1
- package/build/dist/Server/API/NotificationAPI.js.map +1 -1
- package/build/dist/Server/API/OnCallCalendarAPI.js +1 -4
- package/build/dist/Server/API/OnCallCalendarAPI.js.map +1 -1
- package/build/dist/Server/API/OnCallDutyPolicyAPI.js +6 -0
- package/build/dist/Server/API/OnCallDutyPolicyAPI.js.map +1 -1
- package/build/dist/Server/API/OnCallReadinessAPI.js +4 -1
- package/build/dist/Server/API/OnCallReadinessAPI.js.map +1 -1
- package/build/dist/Server/API/OnCallScheduleTimelineAPI.js +494 -0
- package/build/dist/Server/API/OnCallScheduleTimelineAPI.js.map +1 -0
- package/build/dist/Server/API/ProjectAPI.js +1 -1
- package/build/dist/Server/API/ProjectAPI.js.map +1 -1
- package/build/dist/Server/API/ScheduledMaintenanceAPI.js +1 -1
- package/build/dist/Server/API/ScheduledMaintenanceAPI.js.map +1 -1
- package/build/dist/Server/API/StatusPageAPI.js +125 -33
- package/build/dist/Server/API/StatusPageAPI.js.map +1 -1
- package/build/dist/Server/API/TeamMemberAPI.js +3 -3
- package/build/dist/Server/API/TeamMemberAPI.js.map +1 -1
- package/build/dist/Server/API/UserCallAPI.js +2 -2
- package/build/dist/Server/API/UserCallAPI.js.map +1 -1
- package/build/dist/Server/API/UserEmailAPI.js +2 -2
- package/build/dist/Server/API/UserEmailAPI.js.map +1 -1
- package/build/dist/Server/API/UserIncomingCallNumberAPI.js +2 -2
- package/build/dist/Server/API/UserIncomingCallNumberAPI.js.map +1 -1
- package/build/dist/Server/API/UserMicrosoftTeamsAPI.js +1 -1
- package/build/dist/Server/API/UserMicrosoftTeamsAPI.js.map +1 -1
- package/build/dist/Server/API/UserSlackAPI.js +1 -1
- package/build/dist/Server/API/UserSlackAPI.js.map +1 -1
- package/build/dist/Server/API/UserSmsAPI.js +2 -2
- package/build/dist/Server/API/UserSmsAPI.js.map +1 -1
- package/build/dist/Server/API/UserTotpAuthAPI.js +1 -1
- package/build/dist/Server/API/UserTotpAuthAPI.js.map +1 -1
- package/build/dist/Server/API/UserWebAuthnAPI.js +2 -2
- package/build/dist/Server/API/UserWebAuthnAPI.js.map +1 -1
- package/build/dist/Server/API/UserWebhookAPI.js +1 -1
- package/build/dist/Server/API/UserWebhookAPI.js.map +1 -1
- package/build/dist/Server/API/UserWhatsAppAPI.js +2 -2
- package/build/dist/Server/API/UserWhatsAppAPI.js.map +1 -1
- package/build/dist/Server/Middleware/MasterAdminAuthorization.js +11 -2
- package/build/dist/Server/Middleware/MasterAdminAuthorization.js.map +1 -1
- package/build/dist/Server/Middleware/UserAuthorization.js +64 -4
- package/build/dist/Server/Middleware/UserAuthorization.js.map +1 -1
- package/build/dist/Server/Services/ApiKeyPermissionService.js +80 -4
- package/build/dist/Server/Services/ApiKeyPermissionService.js.map +1 -1
- package/build/dist/Server/Services/DatabaseService.js +171 -0
- package/build/dist/Server/Services/DatabaseService.js.map +1 -1
- package/build/dist/Server/Services/DetectionRuleService.js +4 -4
- package/build/dist/Server/Services/DetectionRuleService.js.map +1 -1
- package/build/dist/Server/Services/OnCallDutyPolicyChildService.js +170 -0
- package/build/dist/Server/Services/OnCallDutyPolicyChildService.js.map +1 -0
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.js +2 -2
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleScheduleService.js.map +1 -1
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleService.js +2 -2
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleService.js.map +1 -1
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleTeamService.js +2 -2
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleTeamService.js.map +1 -1
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleUserService.js +2 -2
- package/build/dist/Server/Services/OnCallDutyPolicyEscalationRuleUserService.js.map +1 -1
- package/build/dist/Server/Services/PayAsYouGoBillingService.js +20 -27
- package/build/dist/Server/Services/PayAsYouGoBillingService.js.map +1 -1
- package/build/dist/Server/Services/ProjectService.js +17 -0
- package/build/dist/Server/Services/ProjectService.js.map +1 -1
- package/build/dist/Server/Services/RumSessionPinService.js +180 -16
- package/build/dist/Server/Services/RumSessionPinService.js.map +1 -1
- package/build/dist/Server/Services/TeamPermissionService.js +89 -27
- package/build/dist/Server/Services/TeamPermissionService.js.map +1 -1
- package/build/dist/Server/Services/ThreatIntelFeedService.js +5 -4
- package/build/dist/Server/Services/ThreatIntelFeedService.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/BasePermission.js +9 -6
- package/build/dist/Server/Types/Database/Permissions/BasePermission.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/Index.js +60 -6
- package/build/dist/Server/Types/Database/Permissions/Index.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/TablePermission.js +14 -13
- package/build/dist/Server/Types/Database/Permissions/TablePermission.js.map +1 -1
- package/build/dist/Server/Utils/AI/AIChatPrivacyFilter.js +7 -0
- package/build/dist/Server/Utils/AI/AIChatPrivacyFilter.js.map +1 -1
- package/build/dist/Server/Utils/AI/AIRunPrivacyFilter.js +7 -0
- package/build/dist/Server/Utils/AI/AIRunPrivacyFilter.js.map +1 -1
- package/build/dist/Server/Utils/MasterAdminPageAccess.js +39 -0
- package/build/dist/Server/Utils/MasterAdminPageAccess.js.map +1 -0
- package/build/dist/Server/Utils/Monitor/MonitorAlert.js +3 -1
- package/build/dist/Server/Utils/Monitor/MonitorAlert.js.map +1 -1
- package/build/dist/Server/Utils/Monitor/MonitorIncident.js +3 -1
- package/build/dist/Server/Utils/Monitor/MonitorIncident.js.map +1 -1
- package/build/dist/Server/Utils/Realtime.js +126 -37
- package/build/dist/Server/Utils/Realtime.js.map +1 -1
- package/build/dist/Server/Utils/SecurityEvent/DetectionRuleEvaluator.js +7 -25
- package/build/dist/Server/Utils/SecurityEvent/DetectionRuleEvaluator.js.map +1 -1
- package/build/dist/Server/Utils/SecurityEvent/GoogleSecOpsSeverityRepair.js +127 -0
- package/build/dist/Server/Utils/SecurityEvent/GoogleSecOpsSeverityRepair.js.map +1 -0
- package/build/dist/Server/Utils/SecurityEvent/Sigma/SigmaClickhouseCompiler.js +1 -1
- package/build/dist/Server/Utils/SecurityEvent/Sigma/SigmaClickhouseCompiler.js.map +1 -1
- package/build/dist/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelFeedPoller.js +3 -2
- package/build/dist/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelFeedPoller.js.map +1 -1
- package/build/dist/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelMatcher.js +4 -8
- package/build/dist/Server/Utils/SecurityEvent/ThreatIntel/ThreatIntelMatcher.js.map +1 -1
- package/build/dist/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.js +31 -1
- package/build/dist/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.js.map +1 -1
- package/build/dist/Types/OnCallDutyPolicy/ScheduleTimeline.js +321 -0
- package/build/dist/Types/OnCallDutyPolicy/ScheduleTimeline.js.map +1 -0
- package/build/dist/Types/OnCallDutyPolicy/ScheduleTimelineLayout.js +372 -0
- package/build/dist/Types/OnCallDutyPolicy/ScheduleTimelineLayout.js.map +1 -0
- package/build/dist/Types/Realtime/EventName.js +10 -0
- package/build/dist/Types/Realtime/EventName.js.map +1 -1
- package/build/dist/Types/SecurityEvent/DetectionFindingConstants.js +11 -0
- package/build/dist/Types/SecurityEvent/DetectionFindingConstants.js.map +1 -1
- package/build/dist/Types/SecurityEvent/OcsfSeverity.js +30 -25
- package/build/dist/Types/SecurityEvent/OcsfSeverity.js.map +1 -1
- package/build/dist/Types/SecurityEvent/SigmaRule.js +47 -0
- package/build/dist/Types/SecurityEvent/SigmaRule.js.map +1 -1
- package/build/dist/Types/SecurityEvent/ThreatIntelConstants.js +14 -0
- package/build/dist/Types/SecurityEvent/ThreatIntelConstants.js.map +1 -1
- package/build/dist/UI/Components/AttachmentList/EventAttachmentList.js +9 -4
- package/build/dist/UI/Components/AttachmentList/EventAttachmentList.js.map +1 -1
- package/build/dist/UI/Components/Dashboard/DashboardVariableControl.js +10 -2
- package/build/dist/UI/Components/Dashboard/DashboardVariableControl.js.map +1 -1
- package/build/dist/UI/Components/Dropdown/Dropdown.js +5 -1
- package/build/dist/UI/Components/Dropdown/Dropdown.js.map +1 -1
- package/build/dist/UI/Components/EditionLabel/EditionLabel.js +11 -0
- package/build/dist/UI/Components/EditionLabel/EditionLabel.js.map +1 -1
- package/build/dist/UI/Components/EventItem/EventItem.js +2 -2
- package/build/dist/UI/Components/EventItem/EventItem.js.map +1 -1
- package/build/dist/UI/Components/Forms/BasicForm.js +70 -64
- package/build/dist/UI/Components/Forms/BasicForm.js.map +1 -1
- package/build/dist/UI/Components/Forms/CollapsibleFormSection.js +27 -0
- package/build/dist/UI/Components/Forms/CollapsibleFormSection.js.map +1 -0
- package/build/dist/UI/Components/Forms/Fields/FormField.js +10 -7
- package/build/dist/UI/Components/Forms/Fields/FormField.js.map +1 -1
- package/build/dist/UI/Components/Forms/FormSummary.js +7 -0
- package/build/dist/UI/Components/Forms/FormSummary.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownViewer.js +2 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownViewer.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/SessionAwareImage.js +84 -0
- package/build/dist/UI/Components/Markdown.tsx/SessionAwareImage.js.map +1 -0
- package/build/dist/UI/Components/ModelTable/BaseModelTable.js +14 -1
- package/build/dist/UI/Components/ModelTable/BaseModelTable.js.map +1 -1
- package/build/dist/UI/Components/ModelTable/TableView.js +1 -1
- package/build/dist/UI/Components/ModelTable/TableView.js.map +1 -1
- package/build/dist/UI/Components/TelemetryViewer/components/TelemetryHistogram.js +8 -1
- package/build/dist/UI/Components/TelemetryViewer/components/TelemetryHistogram.js.map +1 -1
- package/build/dist/UI/Components/Tooltip/Tooltip.js +2 -1
- package/build/dist/UI/Components/Tooltip/Tooltip.js.map +1 -1
- package/build/dist/UI/Utils/API/API.js +143 -19
- package/build/dist/UI/Utils/API/API.js.map +1 -1
- package/build/dist/UI/Utils/AnalyticsModelAPI/AnalyticsModelAPI.js +21 -7
- package/build/dist/UI/Utils/AnalyticsModelAPI/AnalyticsModelAPI.js.map +1 -1
- package/build/dist/UI/Utils/ModelAPI/ModelAPI.js +26 -9
- package/build/dist/UI/Utils/ModelAPI/ModelAPI.js.map +1 -1
- package/build/dist/UI/Utils/Navigation.js +8 -0
- package/build/dist/UI/Utils/Navigation.js.map +1 -1
- package/build/dist/UI/Utils/OpenAuthenticatedUrl.js +92 -0
- package/build/dist/UI/Utils/OpenAuthenticatedUrl.js.map +1 -0
- package/build/dist/UI/Utils/Realtime.js +120 -15
- package/build/dist/UI/Utils/Realtime.js.map +1 -1
- package/build/dist/Utils/API.js +13 -5
- package/build/dist/Utils/API.js.map +1 -1
- package/build/dist/Utils/SecurityEvent/GoogleSecOpsAlertNormalizer.js +123 -6
- package/build/dist/Utils/SecurityEvent/GoogleSecOpsAlertNormalizer.js.map +1 -1
- package/build/dist/Utils/SecurityEvent/Sigma/SigmaRuleParser.js +4 -18
- package/build/dist/Utils/SecurityEvent/Sigma/SigmaRuleParser.js.map +1 -1
- package/build/dist/Utils/Slo/SloBurnRateTemplate.js +2 -2
- package/package.json +1 -1
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import Dictionary from "../Dictionary";
|
|
2
2
|
import { JSONValue } from "../JSON";
|
|
3
|
+
import OcsfSeverity from "./OcsfSeverity";
|
|
3
4
|
|
|
4
5
|
/*
|
|
5
6
|
* Typed representation of a parsed Sigma rule — the subset OneUptime's
|
|
@@ -17,6 +18,56 @@ export enum SigmaLevel {
|
|
|
17
18
|
Critical = "critical",
|
|
18
19
|
}
|
|
19
20
|
|
|
21
|
+
/*
|
|
22
|
+
* The level a rule gets when its YAML has no `level:` or one outside the
|
|
23
|
+
* enum above. The parser applies it; the dashboard's rule guide states it.
|
|
24
|
+
*/
|
|
25
|
+
export const SIGMA_DEFAULT_LEVEL: SigmaLevel = SigmaLevel.Medium;
|
|
26
|
+
|
|
27
|
+
/*
|
|
28
|
+
* Sigma level -> OCSF severity stamped on a rule's Detection Finding rows.
|
|
29
|
+
* Lives here rather than in the evaluator so the dashboard's rule guide
|
|
30
|
+
* renders its severity table from the same map the engine writes with.
|
|
31
|
+
*/
|
|
32
|
+
export const SIGMA_LEVEL_TO_OCSF_SEVERITY: Record<SigmaLevel, OcsfSeverity> = {
|
|
33
|
+
[SigmaLevel.Informational]: OcsfSeverity.Informational,
|
|
34
|
+
[SigmaLevel.Low]: OcsfSeverity.Low,
|
|
35
|
+
[SigmaLevel.Medium]: OcsfSeverity.Medium,
|
|
36
|
+
[SigmaLevel.High]: OcsfSeverity.High,
|
|
37
|
+
[SigmaLevel.Critical]: OcsfSeverity.Critical,
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
/*
|
|
41
|
+
* Levels that rank onto a project's MOST severe alert/incident severity
|
|
42
|
+
* when no severity is set on the rule and none is named after the level;
|
|
43
|
+
* every other level ranks onto the least severe.
|
|
44
|
+
*/
|
|
45
|
+
export function isSevereSigmaLevel(level: SigmaLevel): boolean {
|
|
46
|
+
return level === SigmaLevel.Critical || level === SigmaLevel.High;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/*
|
|
50
|
+
* Field modifiers (`field|modifier: value`) the parser accepts. Anything
|
|
51
|
+
* else is rejected at save time — listed here so the dashboard's rule
|
|
52
|
+
* guide cannot advertise a modifier the parser refuses, or miss one it
|
|
53
|
+
* takes.
|
|
54
|
+
*/
|
|
55
|
+
export const SIGMA_SUPPORTED_MODIFIERS: ReadonlyArray<string> = [
|
|
56
|
+
"contains",
|
|
57
|
+
"startswith",
|
|
58
|
+
"endswith",
|
|
59
|
+
"all",
|
|
60
|
+
"re",
|
|
61
|
+
"cased",
|
|
62
|
+
"gt",
|
|
63
|
+
"gte",
|
|
64
|
+
"lt",
|
|
65
|
+
"lte",
|
|
66
|
+
"cidr",
|
|
67
|
+
"exists",
|
|
68
|
+
"windash",
|
|
69
|
+
];
|
|
70
|
+
|
|
20
71
|
/*
|
|
21
72
|
* One `field|modifier: value` requirement inside a selection map. `values`
|
|
22
73
|
* always has at least one entry; multiple entries are OR-ed (AND-ed when
|
|
@@ -105,6 +105,24 @@ export function ocsfSeverityForConfidence(confidence: number): OcsfSeverity {
|
|
|
105
105
|
export const THREAT_INTEL_MINIMUM_CONFIDENCE_MIN: number = 0;
|
|
106
106
|
export const THREAT_INTEL_MINIMUM_CONFIDENCE_MAX: number = 100;
|
|
107
107
|
|
|
108
|
+
/*
|
|
109
|
+
* Save-time bounds and default for ThreatIntelFeed.pollIntervalInMinutes —
|
|
110
|
+
* shared by the server validator, the poller's fallback and the dashboard
|
|
111
|
+
* form, so the three cannot drift apart.
|
|
112
|
+
*/
|
|
113
|
+
export const THREAT_INTEL_POLL_INTERVAL_MIN_IN_MINUTES: number = 1;
|
|
114
|
+
export const THREAT_INTEL_POLL_INTERVAL_MAX_IN_MINUTES: number = 1440;
|
|
115
|
+
export const THREAT_INTEL_DEFAULT_POLL_INTERVAL_IN_MINUTES: number = 60;
|
|
116
|
+
|
|
117
|
+
// Cap on one match evaluation's scan, whatever lastEvaluatedAt says.
|
|
118
|
+
export const THREAT_INTEL_MATCH_MAX_LOOKBACK_IN_MINUTES: number = 24 * 60;
|
|
119
|
+
|
|
120
|
+
// First-ever match evaluation window for a feed.
|
|
121
|
+
export const THREAT_INTEL_FIRST_MATCH_WINDOW_IN_MINUTES: number = 15;
|
|
122
|
+
|
|
123
|
+
// One alert per distinct indicator value per cycle, at most.
|
|
124
|
+
export const THREAT_INTEL_MAX_INDICATORS_PER_EVALUATION: number = 100;
|
|
125
|
+
|
|
108
126
|
/*
|
|
109
127
|
* Indicators whose STIX object carries no valid_until stay active this
|
|
110
128
|
* long after valid_from. STIX says "valid until revoked"; unbounded
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { handleAuthenticatedLinkClick } from "../../Utils/OpenAuthenticatedUrl";
|
|
1
2
|
import React, { FunctionComponent, ReactElement } from "react";
|
|
2
3
|
|
|
3
4
|
export interface EventAttachment {
|
|
@@ -12,6 +13,14 @@ export interface EventAttachmentListProps {
|
|
|
12
13
|
showHeader?: boolean;
|
|
13
14
|
showCount?: boolean;
|
|
14
15
|
className?: string;
|
|
16
|
+
/*
|
|
17
|
+
* Set when the download URLs are behind a session that can lapse while the
|
|
18
|
+
* page is open (a private status page). A click then refreshes the session
|
|
19
|
+
* before the new tab loads the file, so a reader who has had the page open
|
|
20
|
+
* past the access token's lifetime gets the attachment, not a 401. Left
|
|
21
|
+
* unset, the cards are plain links.
|
|
22
|
+
*/
|
|
23
|
+
refreshSession?: (() => Promise<boolean>) | undefined;
|
|
15
24
|
}
|
|
16
25
|
|
|
17
26
|
function getAttachmentExtensionLabel(fileName?: string | null): string | null {
|
|
@@ -31,12 +40,13 @@ function getAttachmentExtensionLabel(fileName?: string | null): string | null {
|
|
|
31
40
|
|
|
32
41
|
type AttachmentCardProps = {
|
|
33
42
|
attachment: EventAttachment;
|
|
43
|
+
refreshSession?: (() => Promise<boolean>) | undefined;
|
|
34
44
|
};
|
|
35
45
|
|
|
36
46
|
const AttachmentCard: FunctionComponent<AttachmentCardProps> = (
|
|
37
47
|
props: AttachmentCardProps,
|
|
38
48
|
): ReactElement => {
|
|
39
|
-
const { attachment } = props;
|
|
49
|
+
const { attachment, refreshSession } = props;
|
|
40
50
|
const extensionLabel: string | null = getAttachmentExtensionLabel(
|
|
41
51
|
attachment.name,
|
|
42
52
|
);
|
|
@@ -47,6 +57,17 @@ const AttachmentCard: FunctionComponent<AttachmentCardProps> = (
|
|
|
47
57
|
href={attachment.downloadUrl}
|
|
48
58
|
target="_blank"
|
|
49
59
|
rel="noopener noreferrer"
|
|
60
|
+
onClick={
|
|
61
|
+
refreshSession
|
|
62
|
+
? (event: React.MouseEvent<HTMLAnchorElement>): void => {
|
|
63
|
+
handleAuthenticatedLinkClick(
|
|
64
|
+
event,
|
|
65
|
+
attachment.downloadUrl,
|
|
66
|
+
refreshSession,
|
|
67
|
+
);
|
|
68
|
+
}
|
|
69
|
+
: undefined
|
|
70
|
+
}
|
|
50
71
|
title={attachment.name}
|
|
51
72
|
className="group flex items-center justify-between gap-3 rounded-lg border border-gray-200 bg-white px-3 py-2 text-sm text-gray-900 transition hover:border-gray-300 hover:bg-gray-50 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-gray-200"
|
|
52
73
|
>
|
|
@@ -81,6 +102,7 @@ const EventAttachmentList: FunctionComponent<EventAttachmentListProps> = (
|
|
|
81
102
|
showHeader = true,
|
|
82
103
|
showCount = true,
|
|
83
104
|
className = "",
|
|
105
|
+
refreshSession,
|
|
84
106
|
} = props;
|
|
85
107
|
|
|
86
108
|
if (!attachments || attachments.length === 0) {
|
|
@@ -90,7 +112,13 @@ const EventAttachmentList: FunctionComponent<EventAttachmentListProps> = (
|
|
|
90
112
|
const attachmentsList: ReactElement = (
|
|
91
113
|
<ul className="space-y-2">
|
|
92
114
|
{attachments.map((attachment: EventAttachment, index: number) => {
|
|
93
|
-
return
|
|
115
|
+
return (
|
|
116
|
+
<AttachmentCard
|
|
117
|
+
attachment={attachment}
|
|
118
|
+
refreshSession={refreshSession}
|
|
119
|
+
key={index}
|
|
120
|
+
/>
|
|
121
|
+
);
|
|
94
122
|
})}
|
|
95
123
|
</ul>
|
|
96
124
|
);
|
|
@@ -193,8 +193,16 @@ const DashboardVariableControl: FunctionComponent<ComponentProps> = (
|
|
|
193
193
|
});
|
|
194
194
|
const selectedValue: string =
|
|
195
195
|
variable.selectedValue ?? variable.defaultValue ?? "";
|
|
196
|
+
/*
|
|
197
|
+
* With no option for its value the browser would show "All", while
|
|
198
|
+
* VariableInterpolation still filters every widget by that value. A project
|
|
199
|
+
* label can be deleted or disallowed. A telemetry attribute only lists the
|
|
200
|
+
* first 100 values seen in the last day, and its default is free text, so
|
|
201
|
+
* its value can be missing from the list and still match data. Skipped
|
|
202
|
+
* while those values load: the select reads "Loading…" until they arrive.
|
|
203
|
+
*/
|
|
196
204
|
const isUnavailableSelection: boolean = Boolean(
|
|
197
|
-
isProjectLabel &&
|
|
205
|
+
(isProjectLabel || (isTelemetryAttribute && !props.isLoadingOptions)) &&
|
|
198
206
|
selectedValue &&
|
|
199
207
|
!options.some((option: DashboardVariableOption) => {
|
|
200
208
|
return option.value === selectedValue;
|
|
@@ -253,7 +261,9 @@ const DashboardVariableControl: FunctionComponent<ComponentProps> = (
|
|
|
253
261
|
{props.isLoadingOptions ? "Loading…" : "All"}
|
|
254
262
|
</option>
|
|
255
263
|
{isUnavailableSelection && (
|
|
256
|
-
<option value={selectedValue}>
|
|
264
|
+
<option value={selectedValue}>
|
|
265
|
+
{isProjectLabel ? "Unavailable label" : selectedValue}
|
|
266
|
+
</option>
|
|
257
267
|
)}
|
|
258
268
|
{options.map((option: DashboardVariableOption) => {
|
|
259
269
|
return (
|
|
@@ -569,13 +569,18 @@ const Dropdown: FunctionComponent<ComponentProps> = (
|
|
|
569
569
|
return;
|
|
570
570
|
}
|
|
571
571
|
|
|
572
|
+
// Uncontrolled selections belong to this component, even if options refresh.
|
|
573
|
+
if (!("value" in props)) {
|
|
574
|
+
return;
|
|
575
|
+
}
|
|
576
|
+
|
|
572
577
|
const value: DropdownOption | Array<DropdownOption> | undefined =
|
|
573
578
|
getDropdownOptionFromValue(
|
|
574
579
|
props.value === null ? undefined : props.value,
|
|
575
580
|
);
|
|
576
581
|
|
|
577
582
|
setValue(value);
|
|
578
|
-
}, [props.value]);
|
|
583
|
+
}, [props.value, props.options]);
|
|
579
584
|
|
|
580
585
|
const menuPortalTarget: HTMLElement | null =
|
|
581
586
|
typeof document === "undefined" ? null : document.body;
|
|
@@ -240,6 +240,18 @@ const EditionLabel: FunctionComponent<ComponentProps> = (
|
|
|
240
240
|
new Route("/global-config/license"),
|
|
241
241
|
);
|
|
242
242
|
|
|
243
|
+
/*
|
|
244
|
+
* The route also serves the login page, so on its own it answers a
|
|
245
|
+
* caller with no session with the reduced anonymous payload and a 200.
|
|
246
|
+
* Inside a signed-in app that caller is us with an expired session,
|
|
247
|
+
* and the reduced payload reads as "no license, no instances". Saying
|
|
248
|
+
* we expect to be signed in makes the server answer 401 instead,
|
|
249
|
+
* which the API client refreshes and replays.
|
|
250
|
+
*/
|
|
251
|
+
if (UserUtil.isLoggedIn()) {
|
|
252
|
+
licenseUrl.addQueryParam("signedIn", "true");
|
|
253
|
+
}
|
|
254
|
+
|
|
243
255
|
const response: HTTPResponse<JSONObject> | HTTPErrorResponse =
|
|
244
256
|
await API.fetch<JSONObject>({
|
|
245
257
|
method: HTTPMethod.GET,
|
|
@@ -58,6 +58,11 @@ export interface ComponentProps {
|
|
|
58
58
|
eventSecondDescription: string;
|
|
59
59
|
labels?: Array<EventItemLabel> | undefined;
|
|
60
60
|
eventAttachments?: Array<TimelineAttachment> | undefined;
|
|
61
|
+
/*
|
|
62
|
+
* Handed to every EventAttachmentList this item renders: the event's own
|
|
63
|
+
* attachments and each timeline note's. See EventAttachmentList.
|
|
64
|
+
*/
|
|
65
|
+
attachmentRefreshSession?: (() => Promise<boolean>) | undefined;
|
|
61
66
|
}
|
|
62
67
|
|
|
63
68
|
const EventItem: FunctionComponent<ComponentProps> = (
|
|
@@ -116,7 +121,10 @@ const EventItem: FunctionComponent<ComponentProps> = (
|
|
|
116
121
|
)}
|
|
117
122
|
|
|
118
123
|
{props.eventAttachments && props.eventAttachments.length > 0 && (
|
|
119
|
-
<EventAttachmentList
|
|
124
|
+
<EventAttachmentList
|
|
125
|
+
attachments={props.eventAttachments}
|
|
126
|
+
refreshSession={props.attachmentRefreshSession}
|
|
127
|
+
/>
|
|
120
128
|
)}
|
|
121
129
|
|
|
122
130
|
{props.eventSecondDescription && (
|
|
@@ -320,6 +328,9 @@ const EventItem: FunctionComponent<ComponentProps> = (
|
|
|
320
328
|
item.attachments.length > 0 && (
|
|
321
329
|
<EventAttachmentList
|
|
322
330
|
attachments={item.attachments}
|
|
331
|
+
refreshSession={
|
|
332
|
+
props.attachmentRefreshSession
|
|
333
|
+
}
|
|
323
334
|
variant="inline"
|
|
324
335
|
showHeader={false}
|
|
325
336
|
showCount={false}
|
|
@@ -11,6 +11,7 @@ import {
|
|
|
11
11
|
DropdownValue,
|
|
12
12
|
} from "../Dropdown/Dropdown";
|
|
13
13
|
import ErrorMessage from "../ErrorMessage/ErrorMessage";
|
|
14
|
+
import CollapsibleFormSection from "./CollapsibleFormSection";
|
|
14
15
|
import FormField from "./Fields/FormField";
|
|
15
16
|
import FormSummary from "./FormSummary";
|
|
16
17
|
import Steps from "./Steps/Steps";
|
|
@@ -222,6 +223,7 @@ const BasicForm: ForwardRefExoticComponent<any> = forwardRef(
|
|
|
222
223
|
|
|
223
224
|
const [errors, setErrors] = useState<Dictionary<string>>({});
|
|
224
225
|
const [touched, setTouched] = useState<Dictionary<boolean>>({});
|
|
226
|
+
const [validationAttempt, setValidationAttempt] = useState<number>(0);
|
|
225
227
|
|
|
226
228
|
useEffect(() => {
|
|
227
229
|
setFormSteps(getVisibleFormSteps());
|
|
@@ -402,6 +404,9 @@ const BasicForm: ForwardRefExoticComponent<any> = forwardRef(
|
|
|
402
404
|
const submitForm: () => void = (): void => {
|
|
403
405
|
// check for any boolean values and if they don't exist in values - mark them as false.
|
|
404
406
|
|
|
407
|
+
setValidationAttempt((attempt: number) => {
|
|
408
|
+
return attempt + 1;
|
|
409
|
+
});
|
|
405
410
|
setAllTouched();
|
|
406
411
|
|
|
407
412
|
const validationErrors: Dictionary<string> = validate(
|
|
@@ -592,41 +597,16 @@ const BasicForm: ForwardRefExoticComponent<any> = forwardRef(
|
|
|
592
597
|
field.fieldType === FormFieldSchemaType.MultiSelectDropdown &&
|
|
593
598
|
(values as any)[fieldName]
|
|
594
599
|
) {
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
},
|
|
606
|
-
) || [];
|
|
607
|
-
|
|
608
|
-
const dropdownOptions: Array<DropdownOption> =
|
|
609
|
-
flatDropdownOptions.filter((option: DropdownOption) => {
|
|
610
|
-
let valueToCompare: Array<DropdownValue> = [
|
|
611
|
-
...(values as any)[fieldName],
|
|
612
|
-
];
|
|
613
|
-
|
|
614
|
-
valueToCompare = valueToCompare.map((item: DropdownValue) => {
|
|
615
|
-
if ((item as any) instanceof ObjectID) {
|
|
616
|
-
return item.toString();
|
|
617
|
-
}
|
|
618
|
-
|
|
619
|
-
return item;
|
|
620
|
-
});
|
|
621
|
-
|
|
622
|
-
return valueToCompare.includes(option.value);
|
|
623
|
-
});
|
|
624
|
-
|
|
625
|
-
(values as any)[fieldName] = dropdownOptions.map(
|
|
626
|
-
(option: DropdownOption) => {
|
|
627
|
-
return option.value;
|
|
628
|
-
},
|
|
629
|
-
);
|
|
600
|
+
/*
|
|
601
|
+
* Options can be loaded lazily for a later step or omit entities the
|
|
602
|
+
* user cannot browse. Preserve every stored selection just as a single
|
|
603
|
+
* dropdown does; an option list is not an authorization to clear IDs.
|
|
604
|
+
*/
|
|
605
|
+
(values as any)[fieldName] = (
|
|
606
|
+
(values as any)[fieldName] as Array<DropdownValue | ObjectID>
|
|
607
|
+
).map((value: DropdownValue | ObjectID): DropdownValue => {
|
|
608
|
+
return value instanceof ObjectID ? value.toString() : value;
|
|
609
|
+
});
|
|
630
610
|
}
|
|
631
611
|
|
|
632
612
|
// if the field is still null but has a default value then... have the default initial value
|
|
@@ -742,102 +722,147 @@ const BasicForm: ForwardRefExoticComponent<any> = forwardRef(
|
|
|
742
722
|
const activeColumns: number =
|
|
743
723
|
currentStep?.columns || props.showAsColumns || 1;
|
|
744
724
|
const fullRowSpan: string = `md:col-span-${activeColumns}`;
|
|
725
|
+
const visibleFields: Fields<T> = formFields.filter(
|
|
726
|
+
(field: Field<T>): boolean => {
|
|
727
|
+
return (
|
|
728
|
+
(!currentFormStepId ||
|
|
729
|
+
field.stepId === currentFormStepId) &&
|
|
730
|
+
(!field.showIf ||
|
|
731
|
+
field.showIf(refCurrentValue.current))
|
|
732
|
+
);
|
|
733
|
+
},
|
|
734
|
+
);
|
|
735
|
+
const fieldGroups: Array<Fields<T>> = [];
|
|
736
|
+
|
|
737
|
+
for (const field of visibleFields) {
|
|
738
|
+
const previousGroup: Fields<T> | undefined =
|
|
739
|
+
fieldGroups[fieldGroups.length - 1];
|
|
740
|
+
if (
|
|
741
|
+
field.collapsibleSection &&
|
|
742
|
+
previousGroup?.[0]?.collapsibleSection?.id ===
|
|
743
|
+
field.collapsibleSection.id
|
|
744
|
+
) {
|
|
745
|
+
previousGroup.push(field);
|
|
746
|
+
} else {
|
|
747
|
+
fieldGroups.push([field]);
|
|
748
|
+
}
|
|
749
|
+
}
|
|
750
|
+
|
|
751
|
+
const renderField: (
|
|
752
|
+
field: Field<T>,
|
|
753
|
+
index: number,
|
|
754
|
+
) => ReactElement = (
|
|
755
|
+
field: Field<T>,
|
|
756
|
+
index: number,
|
|
757
|
+
): ReactElement => {
|
|
758
|
+
const fieldName: string = getFieldName(field);
|
|
759
|
+
return (
|
|
760
|
+
<Fragment key={fieldName}>
|
|
761
|
+
{field.sectionTitle && (
|
|
762
|
+
<div
|
|
763
|
+
className={`${fullRowSpan} mt-4 pt-5 first:mt-0 first:pt-0 border-t first:border-t-0 border-gray-200`}
|
|
764
|
+
>
|
|
765
|
+
<h3 className="text-base font-semibold text-gray-900">
|
|
766
|
+
{translateString(field.sectionTitle) ??
|
|
767
|
+
field.sectionTitle}
|
|
768
|
+
</h3>
|
|
769
|
+
{field.sectionDescription && (
|
|
770
|
+
<p className="mt-1 text-sm text-gray-500">
|
|
771
|
+
{typeof field.sectionDescription === "string"
|
|
772
|
+
? translateString(
|
|
773
|
+
field.sectionDescription,
|
|
774
|
+
) ?? field.sectionDescription
|
|
775
|
+
: field.sectionDescription}
|
|
776
|
+
</p>
|
|
777
|
+
)}
|
|
778
|
+
</div>
|
|
779
|
+
)}
|
|
780
|
+
<div
|
|
781
|
+
className={
|
|
782
|
+
field.spanFullRow ? fullRowSpan : undefined
|
|
783
|
+
}
|
|
784
|
+
>
|
|
785
|
+
<FormField<T>
|
|
786
|
+
field={field}
|
|
787
|
+
fieldName={fieldName}
|
|
788
|
+
index={index}
|
|
789
|
+
error={errors[fieldName] || ""}
|
|
790
|
+
touched={touched[fieldName] || false}
|
|
791
|
+
isDisabled={
|
|
792
|
+
isLoading ||
|
|
793
|
+
(isDropdownOptionsLoading &&
|
|
794
|
+
isDropdownField(field)) ||
|
|
795
|
+
false
|
|
796
|
+
}
|
|
797
|
+
currentValues={refCurrentValue.current}
|
|
798
|
+
setFieldValue={setFieldValue}
|
|
799
|
+
setFieldTouched={setFieldTouched}
|
|
800
|
+
submitForm={submitForm}
|
|
801
|
+
disableAutofocus={props.disableAutofocus || false}
|
|
802
|
+
setFormValues={(values: FormValues<T>) => {
|
|
803
|
+
refCurrentValue.current = values;
|
|
804
|
+
setCurrentValue(refCurrentValue.current);
|
|
805
|
+
}}
|
|
806
|
+
/>
|
|
807
|
+
{field.footerElement}
|
|
808
|
+
{field.getFooterElement &&
|
|
809
|
+
field.getFooterElement(
|
|
810
|
+
refCurrentValue.current,
|
|
811
|
+
touched[fieldName]
|
|
812
|
+
? errors[fieldName] || undefined
|
|
813
|
+
: undefined,
|
|
814
|
+
)}
|
|
815
|
+
</div>
|
|
816
|
+
</Fragment>
|
|
817
|
+
);
|
|
818
|
+
};
|
|
819
|
+
let fieldIndex: number = 0;
|
|
820
|
+
|
|
745
821
|
return (
|
|
746
822
|
<div
|
|
747
823
|
className={`grid md:grid-cols-${activeColumns} grid-cols-1 gap-x-4 gap-y-3`}
|
|
748
824
|
>
|
|
749
|
-
{
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
|
|
825
|
+
{fieldGroups.map((group: Fields<T>): ReactElement => {
|
|
826
|
+
const firstField: Field<T> = group[0]!;
|
|
827
|
+
const fields: Array<ReactElement> = group.map(
|
|
828
|
+
(field: Field<T>): ReactElement => {
|
|
829
|
+
return renderField(field, fieldIndex++);
|
|
830
|
+
},
|
|
831
|
+
);
|
|
832
|
+
|
|
833
|
+
if (!firstField.collapsibleSection) {
|
|
834
|
+
return fields[0]!;
|
|
835
|
+
}
|
|
836
|
+
|
|
837
|
+
return (
|
|
838
|
+
<CollapsibleFormSection
|
|
839
|
+
key={`${firstField.collapsibleSection.id}-${getFieldName(firstField)}`}
|
|
840
|
+
title={firstField.collapsibleSection.title}
|
|
841
|
+
description={
|
|
842
|
+
firstField.collapsibleSection.description
|
|
754
843
|
}
|
|
755
|
-
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
}
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
>
|
|
778
|
-
<h3 className="text-base font-semibold text-gray-900">
|
|
779
|
-
{translateString(field.sectionTitle) ??
|
|
780
|
-
field.sectionTitle}
|
|
781
|
-
</h3>
|
|
782
|
-
{field.sectionDescription && (
|
|
783
|
-
<p className="mt-1 text-sm text-gray-500">
|
|
784
|
-
{typeof field.sectionDescription ===
|
|
785
|
-
"string"
|
|
786
|
-
? translateString(
|
|
787
|
-
field.sectionDescription,
|
|
788
|
-
) ?? field.sectionDescription
|
|
789
|
-
: field.sectionDescription}
|
|
790
|
-
</p>
|
|
791
|
-
)}
|
|
792
|
-
</div>
|
|
793
|
-
)}
|
|
794
|
-
<div
|
|
795
|
-
className={
|
|
796
|
-
field.spanFullRow
|
|
797
|
-
? fullRowSpan
|
|
798
|
-
: undefined
|
|
799
|
-
}
|
|
800
|
-
>
|
|
801
|
-
<FormField<T>
|
|
802
|
-
field={field}
|
|
803
|
-
fieldName={fieldName}
|
|
804
|
-
index={i}
|
|
805
|
-
error={errors[fieldName] || ""}
|
|
806
|
-
touched={touched[fieldName] || false}
|
|
807
|
-
isDisabled={
|
|
808
|
-
isLoading ||
|
|
809
|
-
(isDropdownOptionsLoading &&
|
|
810
|
-
isDropdownField(field)) ||
|
|
811
|
-
false
|
|
812
|
-
}
|
|
813
|
-
currentValues={refCurrentValue.current}
|
|
814
|
-
setFieldValue={setFieldValue}
|
|
815
|
-
setFieldTouched={setFieldTouched}
|
|
816
|
-
submitForm={submitForm}
|
|
817
|
-
disableAutofocus={
|
|
818
|
-
props.disableAutofocus || false
|
|
819
|
-
}
|
|
820
|
-
setFormValues={(
|
|
821
|
-
values: FormValues<T>,
|
|
822
|
-
) => {
|
|
823
|
-
refCurrentValue.current = values;
|
|
824
|
-
setCurrentValue(
|
|
825
|
-
refCurrentValue.current,
|
|
826
|
-
);
|
|
827
|
-
}}
|
|
828
|
-
/>
|
|
829
|
-
{field.footerElement}
|
|
830
|
-
{field.getFooterElement &&
|
|
831
|
-
field.getFooterElement(
|
|
832
|
-
refCurrentValue.current,
|
|
833
|
-
touched[fieldName]
|
|
834
|
-
? errors[fieldName] || undefined
|
|
835
|
-
: undefined,
|
|
836
|
-
)}
|
|
837
|
-
</div>
|
|
838
|
-
</Fragment>
|
|
839
|
-
);
|
|
840
|
-
})}
|
|
844
|
+
isConfigured={firstField.collapsibleSection.isConfigured(
|
|
845
|
+
refCurrentValue.current,
|
|
846
|
+
)}
|
|
847
|
+
hasError={group.some(
|
|
848
|
+
(field: Field<T>): boolean => {
|
|
849
|
+
const fieldName: string = getFieldName(field);
|
|
850
|
+
return Boolean(
|
|
851
|
+
touched[fieldName] && errors[fieldName],
|
|
852
|
+
);
|
|
853
|
+
},
|
|
854
|
+
)}
|
|
855
|
+
validationAttempt={validationAttempt}
|
|
856
|
+
className={fullRowSpan}
|
|
857
|
+
>
|
|
858
|
+
<div
|
|
859
|
+
className={`grid md:grid-cols-${activeColumns} grid-cols-1 gap-x-4 gap-y-3`}
|
|
860
|
+
>
|
|
861
|
+
{fields}
|
|
862
|
+
</div>
|
|
863
|
+
</CollapsibleFormSection>
|
|
864
|
+
);
|
|
865
|
+
})}
|
|
841
866
|
|
|
842
867
|
{/* If Summary, show Model detail */}
|
|
843
868
|
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import useTranslateValue from "../../Utils/Translation";
|
|
2
|
+
import CollapsibleSection from "../CollapsibleSection/CollapsibleSection";
|
|
3
|
+
import React, {
|
|
4
|
+
FunctionComponent,
|
|
5
|
+
ReactElement,
|
|
6
|
+
useEffect,
|
|
7
|
+
useState,
|
|
8
|
+
} from "react";
|
|
9
|
+
|
|
10
|
+
export interface ComponentProps {
|
|
11
|
+
title: string;
|
|
12
|
+
description?: string | undefined;
|
|
13
|
+
isConfigured: boolean;
|
|
14
|
+
hasError: boolean;
|
|
15
|
+
validationAttempt: number;
|
|
16
|
+
className: string;
|
|
17
|
+
children: ReactElement;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
const CollapsibleFormSection: FunctionComponent<ComponentProps> = (
|
|
21
|
+
props: ComponentProps,
|
|
22
|
+
): ReactElement => {
|
|
23
|
+
const { translateString } = useTranslateValue();
|
|
24
|
+
const [isCollapsed, setIsCollapsed] = useState<boolean>(!props.isConfigured);
|
|
25
|
+
|
|
26
|
+
useEffect(() => {
|
|
27
|
+
// Field defaults can arrive after the form has loaded its field definitions.
|
|
28
|
+
if (props.isConfigured) {
|
|
29
|
+
setIsCollapsed(false);
|
|
30
|
+
}
|
|
31
|
+
}, [props.isConfigured]);
|
|
32
|
+
|
|
33
|
+
useEffect(() => {
|
|
34
|
+
if (props.hasError) {
|
|
35
|
+
setIsCollapsed(false);
|
|
36
|
+
}
|
|
37
|
+
}, [props.hasError, props.validationAttempt]);
|
|
38
|
+
|
|
39
|
+
return (
|
|
40
|
+
<CollapsibleSection
|
|
41
|
+
title={translateString(props.title) ?? props.title}
|
|
42
|
+
description={
|
|
43
|
+
props.description
|
|
44
|
+
? translateString(props.description) ?? props.description
|
|
45
|
+
: undefined
|
|
46
|
+
}
|
|
47
|
+
variant="bordered"
|
|
48
|
+
className={props.className}
|
|
49
|
+
isCollapsed={isCollapsed}
|
|
50
|
+
onToggle={setIsCollapsed}
|
|
51
|
+
badge={
|
|
52
|
+
props.isConfigured
|
|
53
|
+
? translateString("Configured") ?? "Configured"
|
|
54
|
+
: undefined
|
|
55
|
+
}
|
|
56
|
+
>
|
|
57
|
+
{/* Keep editors mounted without leaving collapsed controls focusable. */}
|
|
58
|
+
<div hidden={isCollapsed}>{props.children}</div>
|
|
59
|
+
</CollapsibleSection>
|
|
60
|
+
);
|
|
61
|
+
};
|
|
62
|
+
|
|
63
|
+
export default CollapsibleFormSection;
|