@oneuptime/common 14.0.10 → 14.0.11
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/AIConversation.ts +127 -1
- package/Models/DatabaseModels/CephCluster.ts +12 -0
- package/Models/DatabaseModels/CloudResource.ts +12 -0
- package/Models/DatabaseModels/DatabaseServer.ts +12 -0
- package/Models/DatabaseModels/DockerHost.ts +12 -0
- package/Models/DatabaseModels/DockerSwarmCluster.ts +12 -0
- package/Models/DatabaseModels/GlobalOidc.ts +0 -4
- package/Models/DatabaseModels/GlobalOidcProject.ts +0 -4
- package/Models/DatabaseModels/GlobalSso.ts +0 -4
- package/Models/DatabaseModels/GlobalSsoProject.ts +0 -4
- package/Models/DatabaseModels/Host.ts +12 -0
- package/Models/DatabaseModels/IncidentForm.ts +594 -0
- package/Models/DatabaseModels/IncidentFormSubmission.ts +283 -0
- package/Models/DatabaseModels/IncidentTemplate.ts +59 -0
- package/Models/DatabaseModels/Index.ts +14 -0
- package/Models/DatabaseModels/IoTFleet.ts +12 -0
- package/Models/DatabaseModels/KubernetesCluster.ts +12 -0
- package/Models/DatabaseModels/MessageQueue.ts +1102 -0
- package/Models/DatabaseModels/MessageQueueLabelRule.ts +553 -0
- package/Models/DatabaseModels/MessageQueueOwnerRule.ts +633 -0
- package/Models/DatabaseModels/MessageQueueOwnerTeam.ts +491 -0
- package/Models/DatabaseModels/MessageQueueOwnerUser.ts +490 -0
- package/Models/DatabaseModels/PodmanHost.ts +12 -0
- package/Models/DatabaseModels/Project.ts +59 -0
- package/Models/DatabaseModels/ProjectOidc.ts +0 -4
- package/Models/DatabaseModels/ProjectSso.ts +0 -4
- package/Models/DatabaseModels/ProxmoxCluster.ts +12 -0
- package/Models/DatabaseModels/RumApplication.ts +12 -0
- package/Models/DatabaseModels/ServerlessFunction.ts +12 -0
- package/Models/DatabaseModels/Service.ts +12 -0
- package/Models/DatabaseModels/StatusPageOidc.ts +0 -4
- package/Models/DatabaseModels/StatusPageSso.ts +0 -4
- package/Models/DatabaseModels/TeamComplianceSetting.ts +47 -2
- package/Models/DatabaseModels/VMwareVCenter.ts +12 -0
- package/Server/API/AIChatAPI.ts +13 -114
- package/Server/API/AIInvestigationAPI.ts +3 -3
- package/Server/API/AIInvestigationConversationAPI.ts +266 -0
- package/Server/API/IncidentFormAPI.ts +376 -0
- package/Server/API/ProjectOIDC.ts +16 -25
- package/Server/API/ProjectSSO.ts +16 -24
- package/Server/API/StatusPageAPI.ts +42 -77
- package/Server/Enterprise/EnterpriseEdition.ts +93 -28
- package/Server/Enterprise/EnterpriseFeature.ts +25 -3
- package/Server/Enterprise/EnterpriseLicenseSnapshot.ts +1 -1
- package/Server/Enterprise/EnterpriseServerModule.ts +4 -1
- package/Server/EnvironmentConfig.ts +1 -1
- package/Server/Infrastructure/Postgres/SchemaMigrations/1796400000000-AddIncidentForms.ts +129 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1796500000000-AddTeamComplianceRuleNotificationChannels.ts +52 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1796600000000-AddAIInvestigationConversationAndTimeLimits.ts +75 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1796700000000-AddMessageQueueTables.ts +477 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/Index.ts +8 -0
- package/Server/Middleware/IncidentFormRateLimit.ts +847 -0
- package/Server/Middleware/UserAuthorization.ts +16 -38
- package/Server/Services/AIService.ts +10 -13
- package/Server/Services/IncidentCustomFieldService.ts +112 -2
- package/Server/Services/IncidentEpisodeMemberService.ts +24 -4
- package/Server/Services/IncidentEpisodeService.ts +10 -1
- package/Server/Services/IncidentFormService.ts +1566 -0
- package/Server/Services/IncidentFormSubmissionService.ts +97 -0
- package/Server/Services/IncidentGroupingEngineService.ts +45 -8
- package/Server/Services/IncidentService.ts +123 -5
- package/Server/Services/IncidentTemplateService.ts +22 -0
- package/Server/Services/Index.ts +14 -0
- package/Server/Services/MessageQueueLabelRuleEngineService.ts +321 -0
- package/Server/Services/MessageQueueLabelRuleService.ts +14 -0
- package/Server/Services/MessageQueueOwnerRuleEngineService.ts +412 -0
- package/Server/Services/MessageQueueOwnerRuleService.ts +14 -0
- package/Server/Services/MessageQueueOwnerTeamService.ts +62 -0
- package/Server/Services/MessageQueueOwnerUserService.ts +62 -0
- package/Server/Services/MessageQueueService.ts +1463 -0
- package/Server/Services/OpenTelemetryIngestService.ts +37 -4
- package/Server/Services/ProjectService.ts +0 -59
- package/Server/Services/StatusPagePrivateUserService.ts +1 -4
- package/Server/Services/StatusPageService.ts +1 -51
- package/Server/Services/TeamComplianceSettingService.ts +163 -42
- package/Server/Services/UserNotificationRuleService.ts +8 -1
- package/Server/Services/WorkspaceNotificationSummaryService.ts +12 -3
- package/Server/Types/Database/Permissions/CreatePermission.ts +17 -3
- package/Server/Types/Database/Permissions/EditionPermission.ts +140 -38
- package/Server/Types/Database/Permissions/OwnerTableRegistry.ts +16 -0
- package/Server/Types/Database/Permissions/TablePermission.ts +3 -3
- package/Server/Types/Database/Permissions/UpdatePermission.ts +20 -6
- package/Server/Utils/AI/Chat/AgentContextCompactor.ts +200 -0
- package/Server/Utils/AI/Chat/ChatAgentRunner.ts +307 -48
- package/Server/Utils/AI/Chat/ChatRunCancellation.ts +156 -0
- package/Server/Utils/AI/Chat/ObservabilityAssistant.ts +78 -18
- package/Server/Utils/AI/Chat/ObservabilityChatPrompt.ts +1 -1
- package/Server/Utils/AI/Chat/ToolOutputPager.ts +322 -0
- package/Server/Utils/AI/ClusterAccess/KubectlInvestigationToolkit.ts +88 -30
- package/Server/Utils/AI/ClusterAccess/KubectlJobRunner.ts +13 -1
- package/Server/Utils/AI/CodeFix/CodeFixReadiness.ts +0 -32
- package/Server/Utils/AI/CodeFix/FixRunBudget.ts +27 -25
- package/Server/Utils/AI/Remediation/RemediationCommandTools.ts +7 -1
- package/Server/Utils/AI/Remediation/RemediationExecutionRunner.ts +34 -14
- package/Server/Utils/AI/ResourceAccess/InfrastructureInvestigationToolkit.ts +69 -24
- package/Server/Utils/AI/ResourceAccess/ResourceCommandJobRunner.ts +9 -0
- package/Server/Utils/AI/SRE/AIInvestigationEngine.ts +53 -10
- package/Server/Utils/AI/SRE/AlertInvestigationRunner.ts +27 -10
- package/Server/Utils/AI/SRE/IncidentInvestigationRunner.ts +27 -10
- package/Server/Utils/AI/SRE/InvestigationQueue.ts +16 -19
- package/Server/Utils/AI/SRE/InvestigationThread.ts +646 -0
- package/Server/Utils/AI/SRE/InvestigationThreadService.ts +715 -0
- package/Server/Utils/AI/Toolbox/Serializer.ts +10 -3
- package/Server/Utils/EditionEnforcement.ts +19 -202
- package/Server/Utils/LLM/LLMService.ts +259 -63
- package/Server/Utils/RelaxedScimTeamLocksReport.ts +245 -0
- package/Server/Utils/Rules/RuleRun/RuleRunRegistry.ts +25 -0
- package/Server/Utils/SameOriginRequest.ts +203 -0
- package/Server/Utils/TeamMember/ProjectLeaveResourceCleanup.ts +2 -0
- package/Server/Utils/Telemetry/EntityRegistry.ts +4 -1
- package/Server/Utils/Telemetry/MessageQueueDiscovery.ts +1402 -0
- package/Server/Utils/Telemetry/ResourceEntityFilter.ts +4 -1
- package/Server/Utils/VendorAssets.ts +3 -3
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.ts +3 -1
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/IncidentEpisode.ts +3 -1
- package/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.ts +10 -1
- package/Tests/App/Accounts/IncidentFormPage.test.tsx +2036 -0
- package/Tests/App/Accounts/IncidentFormServerMessages.test.ts +119 -0
- package/Tests/App/Accounts/IncidentFormUtils.test.ts +1157 -0
- package/Tests/App/Accounts/LoginPasskey.test.tsx +6 -4
- package/Tests/App/Accounts/LoginSso.test.tsx +724 -0
- package/Tests/App/AdminDashboard/AdminAuthenticationRequireSso.test.tsx +338 -0
- package/Tests/App/AdminDashboard/AdminAuthenticationSsoCardLocales.test.tsx +331 -0
- package/Tests/App/AdminDashboard/AdminEnterprisePluginPage.test.tsx +47 -33
- package/Tests/App/AdminDashboard/GlobalSsoOidcPages.test.tsx +1021 -0
- package/Tests/App/Dashboard/AffectedResourcesDisplay.test.tsx +876 -78
- package/Tests/App/Dashboard/AffectedResourcesSlo.test.tsx +20 -3
- package/Tests/App/Dashboard/CephProxmoxVMwareDocumentationCards.test.tsx +359 -0
- package/Tests/App/Dashboard/CephSetupGuide.test.ts +961 -0
- package/Tests/App/Dashboard/CloudDocumentationCard.test.tsx +381 -95
- package/Tests/App/Dashboard/CloudSetupGuide.test.ts +1463 -0
- package/Tests/App/Dashboard/ClusterAccessNotice.test.tsx +174 -12
- package/Tests/App/Dashboard/ContainerSetupGuideCards.test.tsx +345 -0
- package/Tests/App/Dashboard/CoreListEmptyStates.test.tsx +501 -0
- package/Tests/App/Dashboard/DashboardLazyPages.test.tsx +0 -1
- package/Tests/App/Dashboard/DatabaseDocumentationCard.test.tsx +400 -0
- package/Tests/App/Dashboard/DatabaseDocumentationMarkdown.test.ts +5 -0
- package/Tests/App/Dashboard/DatabaseSetupGuide.test.ts +1869 -0
- package/Tests/App/Dashboard/DatabaseTelemetryScope.test.ts +44 -0
- package/Tests/App/Dashboard/DatabaseTelemetryTabs.test.tsx +50 -9
- package/Tests/App/Dashboard/DockerSetupGuide.test.ts +899 -0
- package/Tests/App/Dashboard/DockerSwarmSetupGuide.test.ts +964 -0
- package/Tests/App/Dashboard/EnterpriseFeatureUpgrade.test.tsx +141 -7
- package/Tests/App/Dashboard/EnterprisePluginPage.test.tsx +52 -39
- package/Tests/App/Dashboard/EventOverviewPages.test.tsx +7 -1
- package/Tests/App/Dashboard/GettingStartedTaskRoutes.test.tsx +331 -0
- package/Tests/App/Dashboard/HomeOverviewStatsFirstRun.test.tsx +925 -0
- package/Tests/App/Dashboard/HostDocumentationCard.test.tsx +225 -0
- package/Tests/App/Dashboard/HostSetupGuide.test.ts +1183 -0
- package/Tests/App/Dashboard/IdentityEnterpriseShells.test.tsx +69 -45
- package/Tests/App/Dashboard/IncidentCreateTemplateCustomFieldSettings.test.tsx +745 -0
- package/Tests/App/Dashboard/IncidentCreateTemplateOwners.test.tsx +414 -0
- package/Tests/App/Dashboard/IncidentCustomFieldCreateSettingsForm.test.ts +1042 -0
- package/Tests/App/Dashboard/IncidentCustomFieldSettingsCard.test.tsx +1816 -0
- package/Tests/App/Dashboard/IncidentFormPlan.test.ts +89 -0
- package/Tests/App/Dashboard/IncidentFormShareLinkCard.test.tsx +846 -0
- package/Tests/App/Dashboard/IncidentFormsPages.test.tsx +1324 -0
- package/Tests/App/Dashboard/IncidentTemplateCustomFieldSettings.test.tsx +630 -0
- package/Tests/App/Dashboard/IncidentsSideMenu.test.tsx +13 -0
- package/Tests/App/Dashboard/IncomingEmailMonitorLinkVerifyHint.test.tsx +104 -0
- package/Tests/App/Dashboard/InvestigationConversation.test.tsx +1107 -0
- package/Tests/App/Dashboard/InvestigationConversationData.test.ts +546 -0
- package/Tests/App/Dashboard/InvestigationEvidenceList.test.tsx +170 -5
- package/Tests/App/Dashboard/InvestigationNotStarted.test.tsx +207 -2
- package/Tests/App/Dashboard/InvestigationPanel.test.tsx +729 -34
- package/Tests/App/Dashboard/InvestigationPanelStatus.test.tsx +9 -21
- package/Tests/App/Dashboard/InvestigationReportView.test.tsx +274 -37
- package/Tests/App/Dashboard/InvestigationStatusBadge.test.tsx +130 -0
- package/Tests/App/Dashboard/IoTDocumentationCard.test.tsx +218 -0
- package/Tests/App/Dashboard/IoTSetupGuide.test.ts +1124 -0
- package/Tests/App/Dashboard/KubernetesClusterAiAccessSettings.test.ts +20 -6
- package/Tests/App/Dashboard/KubernetesClusterAiDocumentationMarkdown.test.ts +107 -83
- package/Tests/App/Dashboard/KubernetesSetupGuide.test.ts +787 -0
- package/Tests/App/Dashboard/MessageQueueBreadcrumbs.test.tsx +228 -0
- package/Tests/App/Dashboard/MessageQueueBrokerHealth.test.tsx +1538 -0
- package/Tests/App/Dashboard/MessageQueueBrokerHealthMetricChart.test.tsx +969 -0
- package/Tests/App/Dashboard/MessageQueueBrokerHealthReads.test.ts +889 -0
- package/Tests/App/Dashboard/MessageQueueBrokerMetricsReach.test.ts +236 -0
- package/Tests/App/Dashboard/MessageQueueDocumentationCard.test.tsx +479 -0
- package/Tests/App/Dashboard/MessageQueueListPages.test.tsx +1232 -0
- package/Tests/App/Dashboard/MessageQueueMetricDescriptions.test.ts +244 -0
- package/Tests/App/Dashboard/MessageQueueMonitorLink.test.ts +952 -0
- package/Tests/App/Dashboard/MessageQueueMonitorLinkMonitorCreate.test.tsx +859 -0
- package/Tests/App/Dashboard/MessageQueueOverview.test.tsx +1773 -0
- package/Tests/App/Dashboard/MessageQueueOverviewPresentation.test.ts +196 -0
- package/Tests/App/Dashboard/MessageQueuePresentation.test.ts +799 -0
- package/Tests/App/Dashboard/MessageQueueProducersConsumers.test.tsx +680 -0
- package/Tests/App/Dashboard/MessageQueueRoutes.test.tsx +383 -0
- package/Tests/App/Dashboard/MessageQueueRulePages.test.tsx +278 -0
- package/Tests/App/Dashboard/MessageQueueSetupGuide.test.ts +2778 -0
- package/Tests/App/Dashboard/MessageQueueSideMenus.test.tsx +273 -0
- package/Tests/App/Dashboard/MessageQueueSpanPopulations.test.ts +930 -0
- package/Tests/App/Dashboard/MessageQueueSpanStore.ts +351 -0
- package/Tests/App/Dashboard/MessageQueueTelemetryScope.test.ts +375 -0
- package/Tests/App/Dashboard/MessageQueueTelemetryScopeTabs.test.tsx +668 -0
- package/Tests/App/Dashboard/MessageQueueViewPages.test.tsx +685 -0
- package/Tests/App/Dashboard/MonitorAndHomeNotOperationalMenus.test.tsx +342 -0
- package/Tests/App/Dashboard/MonitorCreateFirstRunDefaults.test.tsx +623 -0
- package/Tests/App/Dashboard/MonitorCreateFromMonitorBackedDevice.test.tsx +442 -0
- package/Tests/App/Dashboard/MonitorLogsPageViewSummary.test.tsx +814 -0
- package/Tests/App/Dashboard/MonitorSetupCardBodies.test.tsx +246 -0
- package/Tests/App/Dashboard/NavigationSearchKeywords.test.tsx +8 -0
- package/Tests/App/Dashboard/OnboardingSsoEmptyState.test.tsx +27 -12
- package/Tests/App/Dashboard/PlanGatedPage.test.tsx +292 -0
- package/Tests/App/Dashboard/PodmanSetupGuide.test.ts +948 -0
- package/Tests/App/Dashboard/ProductOrientation.test.tsx +5 -4
- package/Tests/App/Dashboard/ProductSettingsSectionCollapsed.test.tsx +266 -0
- package/Tests/App/Dashboard/ProxmoxSetupGuide.test.ts +1318 -0
- package/Tests/App/Dashboard/ResourceAiAgentAttentionServerParity.test.ts +555 -0
- package/Tests/App/Dashboard/ResourceAiAgentPage.test.tsx +298 -9
- package/Tests/App/Dashboard/ResourceAiAgentStatus.test.ts +453 -0
- package/Tests/App/Dashboard/ResourceArchiveSettings.test.tsx +16 -0
- package/Tests/App/Dashboard/ResourceConnectionGuideCard.test.tsx +444 -0
- package/Tests/App/Dashboard/ResourceConnectionGuideOverviewsInfra.test.tsx +798 -0
- package/Tests/App/Dashboard/ResourceConnectionGuideOverviewsPlatforms.test.tsx +717 -0
- package/Tests/App/Dashboard/ResourceConnectionGuides.test.ts +981 -0
- package/Tests/App/Dashboard/ResourceConnectionState.test.ts +132 -0
- package/Tests/App/Dashboard/RumDocumentationCard.test.tsx +293 -0
- package/Tests/App/Dashboard/RumSessionReplayRetentionSettings.test.tsx +467 -0
- package/Tests/App/Dashboard/RumSetupGuide.test.ts +758 -0
- package/Tests/App/Dashboard/ScheduledMaintenanceOverviewPage.test.tsx +25 -0
- package/Tests/App/Dashboard/ServerlessDocumentationCard.test.tsx +254 -0
- package/Tests/App/Dashboard/ServerlessSetupGuide.test.ts +1074 -0
- package/Tests/App/Dashboard/SetupGuide.test.ts +246 -0
- package/Tests/App/Dashboard/SetupGuideCard.test.tsx +756 -0
- package/Tests/App/Dashboard/SloListSideMenu.test.tsx +120 -0
- package/Tests/App/Dashboard/SsoPages.test.tsx +833 -0
- package/Tests/App/Dashboard/TelemetryDocumentation.test.tsx +253 -0
- package/Tests/App/Dashboard/TelemetryRetentionShells.test.tsx +730 -0
- package/Tests/App/Dashboard/VMwareSetupGuide.test.ts +1033 -0
- package/Tests/App/StatusPage/StatusPageSsoEmptyState.test.tsx +87 -7
- package/Tests/Models/DatabaseModels/DatabaseServerModels.test.ts +28 -9
- package/Tests/Models/DatabaseModels/IncidentFormModel.test.ts +1250 -0
- package/Tests/Models/DatabaseModels/MessageQueueModels.test.ts +1983 -0
- package/Tests/Models/DatabaseModels/StaticRuleCriteriaInheritance.test.ts +4 -2
- package/Tests/Models/DatabaseModels/TeamComplianceSettingModel.test.ts +190 -14
- package/Tests/Models/IncidentTemplateCustomFieldSettingsColumn.test.ts +291 -0
- package/Tests/Server/API/AIInvestigationConversationAPI.test.ts +412 -0
- package/Tests/Server/API/GlobalConfigLicense.test.ts +38 -9
- package/Tests/Server/API/IncidentFormAPI.test.ts +942 -0
- package/Tests/Server/API/IncidentFormPublicRoutes.test.ts +1653 -0
- package/Tests/Server/API/KubernetesClusterAiAccessAPI.test.ts +2 -1
- package/Tests/Server/API/{SsoProviderListingsEdition.test.ts → SsoProviderListings.test.ts} +164 -110
- package/Tests/Server/Enterprise/EnterpriseEdition.test.ts +76 -54
- package/Tests/Server/Enterprise/EnterpriseFeatureActive.test.ts +125 -42
- package/Tests/Server/Enterprise/EnterpriseLicenseSnapshot.test.ts +36 -10
- package/Tests/Server/Enterprise/EnterpriseModelFeatureMap.test.ts +51 -9
- package/Tests/Server/Enterprise/FakeEnterpriseModule.ts +13 -8
- package/Tests/Server/Enterprise/SsoInCommunityEdition.test.ts +540 -0
- package/Tests/Server/Infrastructure/Postgres/AddConfigurableRuleCriteriaMigration.test.ts +3 -0
- package/Tests/Server/Infrastructure/Postgres/AddIncidentFormsMigration.test.ts +438 -0
- package/Tests/Server/Infrastructure/Postgres/AddTeamComplianceRuleNotificationChannelsMigration.test.ts +255 -0
- package/Tests/Server/Infrastructure/Postgres/MessageQueueTablesMigration.test.ts +637 -0
- package/Tests/Server/Middleware/IncidentFormRateLimit.test.ts +1630 -0
- package/Tests/Server/Middleware/UserAuthorization.test.ts +16 -17
- package/Tests/Server/Middleware/UserAuthorizationSsoEnforcement.test.ts +544 -0
- package/Tests/Server/Services/AIServiceDailyBudget.test.ts +37 -8
- package/Tests/Server/Services/IncidentCreatedFeedTitle.test.ts +212 -0
- package/Tests/Server/Services/IncidentCustomFieldDeleteFormQuestions.test.ts +297 -0
- package/Tests/Server/Services/IncidentFormOwnersCreatedNotification.test.ts +497 -0
- package/Tests/Server/Services/IncidentFormPostgres.test.ts +958 -0
- package/Tests/Server/Services/IncidentFormPublicForm.test.ts +1260 -0
- package/Tests/Server/Services/IncidentFormPublicSubmission.test.ts +2520 -0
- package/Tests/Server/Services/IncidentFormRegistration.test.ts +159 -0
- package/Tests/Server/Services/IncidentFormService.test.ts +663 -0
- package/Tests/Server/Services/IncidentFormSubmissionService.test.ts +430 -0
- package/Tests/Server/Services/IncidentFormSubmissionTemplateBranch.test.ts +473 -0
- package/Tests/Server/Services/IncidentGroupingTemplateSubstitution.test.ts +81 -0
- package/Tests/Server/Services/IncidentTemplateCustomFieldSettings.test.ts +262 -0
- package/Tests/Server/Services/IncidentTemplateOwnersOnDeclare.test.ts +566 -0
- package/Tests/Server/Services/IncidentTitleMarkdownSinks.test.ts +640 -0
- package/Tests/Server/Services/LlmLogServiceTokenAggregateParams.test.ts +3 -3
- package/Tests/Server/Services/MessageQueueOwnerServices.test.ts +440 -0
- package/Tests/Server/Services/MessageQueueRegistries.test.ts +577 -0
- package/Tests/Server/Services/MessageQueueRuleEngines.test.ts +900 -0
- package/Tests/Server/Services/MessageQueueService.test.ts +2210 -0
- package/Tests/Server/Services/MessageQueueSqlPostgres.test.ts +1271 -0
- package/Tests/Server/Services/OpenTelemetryResourceRetentionMemo.test.ts +28 -1
- package/Tests/Server/Services/OpenTelemetryRetentionOverrideEdition.test.ts +474 -0
- package/Tests/Server/Services/OpenTelemetryServiceResolutionCache.test.ts +21 -0
- package/Tests/Server/Services/OwnerRowUniqueness.test.ts +3 -0
- package/Tests/Server/Services/ProjectServiceAuditLogLicense.test.ts +0 -1
- package/Tests/Server/Services/RuleRun/LabelRuleEnginesGroupBRun.test.ts +56 -6
- package/Tests/Server/Services/RuleRun/OwnerRuleEnginesGroupBRun.test.ts +30 -1
- package/Tests/Server/Services/SsoRequirementReads.test.ts +454 -0
- package/Tests/Server/Services/SsoRequirementWrites.test.ts +529 -0
- package/Tests/Server/Services/StaticRuleCriteriaRuntimeCoverage.test.ts +3 -3
- package/Tests/Server/Services/StatusPagePrivateUserInvitationPolicy.test.ts +107 -89
- package/Tests/Server/Services/TeamComplianceSettingPostgres.test.ts +1068 -176
- package/Tests/Server/Services/TeamComplianceSettingService.test.ts +1962 -200
- package/Tests/Server/Types/Database/Permissions/EditionPermission.test.ts +654 -297
- package/Tests/Server/Types/Database/Permissions/RetentionOverrideColumns.test.ts +784 -0
- package/Tests/Server/Types/Database/Permissions/SsoScalePlanGate.test.ts +418 -0
- package/Tests/Server/Utils/AI/AIAlertGating.test.ts +0 -1
- package/Tests/Server/Utils/AI/AIInvestigationEngineRunLimits.test.ts +136 -0
- package/Tests/Server/Utils/AI/AIInvestigationQueue.test.ts +15 -14
- package/Tests/Server/Utils/AI/AgentContextCompactor.test.ts +351 -0
- package/Tests/Server/Utils/AI/ChatAgentRunnerSharedThread.test.ts +842 -0
- package/Tests/Server/Utils/AI/ChatRunCancellation.test.ts +195 -0
- package/Tests/Server/Utils/AI/CodeFixReadiness.test.ts +10 -57
- package/Tests/Server/Utils/AI/FixRunBudget.test.ts +20 -24
- package/Tests/Server/Utils/AI/Insights/InvestigationQueueInsightSubject.test.ts +7 -30
- package/Tests/Server/Utils/AI/InvestigationClusterAccessWiring.test.ts +225 -29
- package/Tests/Server/Utils/AI/InvestigationInfrastructureAccessWiring.test.ts +266 -25
- package/Tests/Server/Utils/AI/InvestigationThread.test.ts +580 -0
- package/Tests/Server/Utils/AI/InvestigationThreadService.test.ts +801 -0
- package/Tests/Server/Utils/AI/KubectlInvestigationToolkit.test.ts +525 -43
- package/Tests/Server/Utils/AI/KubectlJobRunner.test.ts +4 -2
- package/Tests/Server/Utils/AI/LLMServiceUnreachableProvider.test.ts +435 -0
- package/Tests/Server/Utils/AI/ObservabilityAssistantLimits.test.ts +462 -0
- package/Tests/Server/Utils/AI/RemediationExecutionRunner.test.ts +14 -25
- package/Tests/Server/Utils/AI/RemediationExecutionRunnerResourceMode.test.ts +2 -0
- package/Tests/Server/Utils/AI/ResourceAccess/InfrastructureInvestigationToolkit.test.ts +297 -15
- package/Tests/Server/Utils/AI/ResourceAccess/ResourceCommandJobRunner.test.ts +10 -6
- package/Tests/Server/Utils/AI/ToolOutputPager.test.ts +382 -0
- package/Tests/Server/Utils/AI/ToolResultSerializer.test.ts +23 -4
- package/Tests/Server/Utils/AI/Toolbox/LogTools.test.ts +25 -6
- package/Tests/Server/Utils/AI/Toolbox/Serializer.test.ts +14 -3
- package/Tests/Server/Utils/EditionEnforcement.test.ts +107 -147
- package/Tests/Server/Utils/{CommunityEditionSsoReport.test.ts → RelaxedScimTeamLocksReport.test.ts} +212 -208
- package/Tests/Server/Utils/SameOriginRequest.test.ts +372 -0
- package/Tests/Server/Utils/Telemetry/EntityRegistry.test.ts +20 -0
- package/Tests/Server/Utils/Telemetry/MessageQueueDiscovery.test.ts +2590 -0
- package/Tests/Server/Utils/Telemetry/MessageQueueSpanQueryTwin.ts +246 -0
- package/Tests/Server/Utils/Telemetry/TelemetryEntity.test.ts +23 -0
- package/Tests/Types/AI/AIAgentRunLimits.test.ts +255 -0
- package/Tests/Types/Code/JsonSyntax.test.ts +1300 -0
- package/Tests/Types/CustomField/CustomFieldCreateSettings.test.ts +1113 -0
- package/Tests/Types/CustomField/CustomFieldMappingCatalog.test.ts +91 -0
- package/Tests/Types/CustomField/CustomFieldValueValidator.test.ts +30 -0
- package/Tests/Types/Incident/IncidentFormIpAllowlist.test.ts +227 -0
- package/Tests/Types/Incident/IncidentFormPublic.test.ts +1916 -0
- package/Tests/Types/MessageQueue/MessageQueueEntityKey.test.ts +916 -0
- package/Tests/Types/MessageQueue/MessageQueueIdentity.test.ts +567 -0
- package/Tests/Types/MessageQueue/MessageQueueManualIdentity.test.ts +686 -0
- package/Tests/Types/MessageQueue/MessageQueueMetricCatalog.test.ts +1726 -0
- package/Tests/Types/MessageQueue/MessageQueueMetricResolution.test.ts +1758 -0
- package/Tests/Types/MessageQueue/MessagingInstrumentationFixtures.test.ts +4686 -0
- package/Tests/Types/MessageQueue/MessagingSystem.test.ts +840 -0
- package/Tests/Types/MessageQueue/MessagingTelemetryFixtures.ts +3287 -0
- package/Tests/Types/MessageQueue/MessagingTelemetryResolver.test.ts +2966 -0
- package/Tests/Types/Monitor/MessageQueueAlertTemplates.test.ts +5401 -0
- package/Tests/Types/Monitor/MetricEngineFold.ts +154 -0
- package/Tests/Types/ResourceAiAgent/ResourceAiAccess.test.ts +5 -3
- package/Tests/Types/Team/ComplianceRule.test.ts +588 -37
- package/Tests/Types/Team/TeamComplianceStatus.test.ts +64 -11
- package/Tests/Types/XML.test.ts +51 -0
- package/Tests/UI/Components/CodeEditor/CodeEditor.test.tsx +2362 -0
- package/Tests/UI/Components/CodeEditor/CodeEditorCommands.test.ts +810 -0
- package/Tests/UI/Components/CodeEditor/CodeEditorHighlight.test.ts +338 -0
- package/Tests/UI/Components/CodeEditor/CodeEditorLanguages.test.ts +222 -0
- package/Tests/UI/Components/CodeEditor/CodeEditorStyles.test.ts +807 -0
- package/Tests/UI/Components/CodeEditor/NoMonaco.test.ts +245 -0
- package/Tests/UI/Components/CodeEditor/YamlEditor.test.tsx +729 -0
- package/Tests/UI/Components/CopyTextButton.test.tsx +76 -0
- package/Tests/UI/Components/EditionLabelLapseCopy.ts +51 -14
- package/Tests/UI/Components/EditionLabelLicenseStatus.test.tsx +131 -23
- package/Tests/UI/Components/ErrorMessageAction.test.tsx +142 -0
- package/Tests/UI/Components/FacetSidebarInScope.test.tsx +459 -0
- package/Tests/UI/Components/FacetValuesInScope.test.ts +270 -0
- package/Tests/UI/Components/Forms/FormFieldCodeEditors.test.tsx +294 -0
- package/Tests/UI/Components/Forms/FormFieldMarkdown.test.tsx +126 -0
- package/Tests/UI/Components/Forms/FormFieldYaml.test.tsx +22 -75
- package/Tests/UI/Components/Forms/ModelFormOnBeforeCreateMiscData.test.tsx +254 -0
- package/Tests/UI/Components/Icon.test.tsx +32 -0
- package/Tests/UI/Components/Input.test.tsx +31 -0
- package/Tests/UI/Components/LockedFilterChipScope.test.tsx +501 -0
- package/Tests/UI/Components/MarkdownConverters.test.ts +253 -1
- package/Tests/UI/Components/MarkdownEditor.test.tsx +2785 -2
- package/Tests/UI/Components/MarkdownEditorHistory.test.ts +243 -0
- package/Tests/UI/Components/MarkdownListEditing.test.ts +1118 -0
- package/Tests/UI/Components/MarkdownPaste.test.ts +1180 -0
- package/Tests/UI/Components/MarkdownViewerCopy.test.tsx +466 -0
- package/Tests/UI/Components/MarkdownVisualEditing.test.ts +1089 -0
- package/Tests/UI/Components/ModelTable/BaseModelTableEmptyStateAction.test.tsx +623 -0
- package/Tests/UI/Components/ResetObjectID.test.tsx +282 -0
- package/Tests/UI/Components/RuleCriteria/RuleCriteriaModelTable.test.tsx +3 -3
- package/Tests/UI/Components/Table/EmptyTableMessage.test.ts +439 -0
- package/Tests/UI/Components/Table/TableEmptyState.test.tsx +352 -0
- package/Tests/UI/Components/TableRowMobileTitles.test.tsx +78 -0
- package/Tests/UI/Components/TextArea.test.tsx +19 -0
- package/Tests/UI/Components/Workflow/ModelColumnEditor.render.test.tsx +12 -29
- package/Tests/UI/Components/fixtures/MarkdownPasteFixtures.ts +460 -0
- package/Tests/UI/EsbuildConfig.test.ts +115 -39
- package/Tests/UI/EsbuildEnterpriseAlias.test.ts +4 -4
- package/Tests/UI/Monitor/MonitorLogSummaryRender.test.tsx +377 -0
- package/Tests/UI/Utils/Breadcrumb/fixtures/RealBreadcrumbTrails.ts +81 -1
- package/Tests/UI/Utils/Breadcrumb/fixtures/RealRoutePatterns.ts +17 -0
- package/Tests/Utils/LabelRuleImportExport.test.ts +5 -0
- package/Tests/Utils/Markdown/DashboardMarkdownRenderer.ts +81 -0
- package/Tests/Utils/Markdown/UntrustedMarkdown.test.ts +1339 -0
- package/Tests/Utils/Monitor/MonitorLogSummaryUtil.test.ts +862 -0
- package/Types/AI/AIAgentRunLimits.ts +146 -0
- package/Types/Code/CodeType.ts +2 -0
- package/Types/Code/JsonSyntax.ts +923 -0
- package/Types/CustomField/CustomFieldCreateSettings.ts +549 -0
- package/Types/CustomField/CustomFieldMappingCatalog.ts +77 -0
- package/Types/CustomField/CustomFieldValueValidator.ts +10 -7
- package/Types/EnterpriseLicense/EnterpriseLicensePeriods.ts +1 -1
- package/Types/Icon/IconProp.ts +2 -0
- package/Types/Incident/IncidentFormIpAllowlist.ts +206 -0
- package/Types/Incident/IncidentFormPublic.ts +1145 -0
- package/Types/Kubernetes/KubernetesClusterAiAccess.ts +10 -3
- package/Types/MessageQueue/MessageQueueIdentity.ts +256 -0
- package/Types/MessageQueue/MessageQueueManualIdentity.ts +325 -0
- package/Types/MessageQueue/MessageQueueMetricCatalog.ts +1357 -0
- package/Types/MessageQueue/MessagingSystem.ts +518 -0
- package/Types/MessageQueue/MessagingTelemetryResolver.ts +2311 -0
- package/Types/Monitor/MessageQueueAlertTemplates.ts +2128 -0
- package/Types/Permission.ts +310 -0
- package/Types/ResourceAiAgent/ResourceAiAccess.ts +10 -4
- package/Types/Rules/RuleCriteriaFieldRegistry.ts +12 -0
- package/Types/Rules/RuleRun.ts +4 -0
- package/Types/Team/ComplianceNotificationChannel.ts +4 -3
- package/Types/Team/ComplianceRule.ts +71 -18
- package/Types/Team/ComplianceRuleType.ts +2 -2
- package/Types/Team/TeamComplianceStatus.ts +6 -2
- package/Types/Telemetry/EntityType.ts +16 -0
- package/Types/Telemetry/LockedFilterDetail.ts +22 -0
- package/Types/XML.ts +26 -0
- package/UI/Components/CodeEditor/CodeEditor.css +379 -0
- package/UI/Components/CodeEditor/CodeEditor.tsx +1128 -294
- package/UI/Components/CodeEditor/CodeEditorCommands.ts +774 -0
- package/UI/Components/CodeEditor/CodeEditorHighlight.ts +106 -0
- package/UI/Components/CodeEditor/CodeEditorLanguages.ts +164 -0
- package/UI/Components/CodeEditor/YamlEditor.tsx +28 -326
- package/UI/Components/CopyTextButton/CopyTextButton.tsx +5 -1
- package/UI/Components/CustomFields/CustomFieldModelFormFields.tsx +6 -25
- package/UI/Components/EditionLabel/EditionLabel.tsx +14 -13
- package/UI/Components/ErrorMessage/ErrorMessage.tsx +11 -1
- package/UI/Components/Forms/Fields/FormField.tsx +8 -0
- package/UI/Components/Forms/Types/Field.ts +8 -0
- package/UI/Components/Icon/Icon.tsx +18 -0
- package/UI/Components/Input/Input.tsx +11 -4
- package/UI/Components/LogsViewer/LogsViewer.tsx +4 -0
- package/UI/Components/LogsViewer/components/LogsFacetSidebar.tsx +21 -3
- package/UI/Components/Markdown.tsx/MarkdownConverters.ts +0 -0
- package/UI/Components/Markdown.tsx/MarkdownEditor.tsx +877 -79
- package/UI/Components/Markdown.tsx/MarkdownEditorHistory.ts +284 -0
- package/UI/Components/Markdown.tsx/MarkdownListEditing.ts +1362 -0
- package/UI/Components/Markdown.tsx/MarkdownPaste.ts +1326 -0
- package/UI/Components/Markdown.tsx/MarkdownViewer.tsx +106 -10
- package/UI/Components/Markdown.tsx/MarkdownVisualEditing.ts +1032 -0
- package/UI/Components/ModelTable/BaseModelTable.tsx +85 -7
- package/UI/Components/ResetObjectID/ResetObjectID.tsx +35 -9
- package/UI/Components/Table/EmptyTableMessage.ts +81 -0
- package/UI/Components/Table/Table.tsx +50 -21
- package/UI/Components/Table/TableRow.tsx +9 -1
- package/UI/Components/TelemetryViewer/FacetVisibility.ts +97 -2
- package/UI/Components/TelemetryViewer/TelemetryViewer.tsx +13 -0
- package/UI/Components/TelemetryViewer/components/LockedFilterChip.tsx +214 -7
- package/UI/Components/TelemetryViewer/components/TelemetryFacetSidebar.tsx +21 -3
- package/UI/Components/TextArea/TextArea.tsx +9 -2
- package/UI/Components/Workflow/ModelFieldPicker.tsx +10 -12
- package/UI/Styles/Theme.css +8 -0
- package/UI/esbuild-config.js +2 -32
- package/Utils/LabelRuleImportExport.ts +2 -0
- package/Utils/Markdown/UntrustedMarkdown.ts +1513 -0
- package/Utils/Monitor/IncomingEmailMonitorRequestUtil.ts +41 -0
- package/Utils/Monitor/MonitorLogSummaryUtil.ts +212 -0
- package/Utils/Telemetry/EntityKey.ts +48 -0
- package/build/dist/Models/DatabaseModels/AIConversation.js +125 -1
- package/build/dist/Models/DatabaseModels/AIConversation.js.map +1 -1
- package/build/dist/Models/DatabaseModels/CephCluster.js +12 -0
- package/build/dist/Models/DatabaseModels/CephCluster.js.map +1 -1
- package/build/dist/Models/DatabaseModels/CloudResource.js +12 -0
- package/build/dist/Models/DatabaseModels/CloudResource.js.map +1 -1
- package/build/dist/Models/DatabaseModels/DatabaseServer.js +12 -0
- package/build/dist/Models/DatabaseModels/DatabaseServer.js.map +1 -1
- package/build/dist/Models/DatabaseModels/DockerHost.js +12 -0
- package/build/dist/Models/DatabaseModels/DockerHost.js.map +1 -1
- package/build/dist/Models/DatabaseModels/DockerSwarmCluster.js +12 -0
- package/build/dist/Models/DatabaseModels/DockerSwarmCluster.js.map +1 -1
- package/build/dist/Models/DatabaseModels/GlobalOidc.js +0 -4
- package/build/dist/Models/DatabaseModels/GlobalOidc.js.map +1 -1
- package/build/dist/Models/DatabaseModels/GlobalOidcProject.js +0 -4
- package/build/dist/Models/DatabaseModels/GlobalOidcProject.js.map +1 -1
- package/build/dist/Models/DatabaseModels/GlobalSso.js +0 -4
- package/build/dist/Models/DatabaseModels/GlobalSso.js.map +1 -1
- package/build/dist/Models/DatabaseModels/GlobalSsoProject.js +0 -4
- package/build/dist/Models/DatabaseModels/GlobalSsoProject.js.map +1 -1
- package/build/dist/Models/DatabaseModels/Host.js +12 -0
- package/build/dist/Models/DatabaseModels/Host.js.map +1 -1
- package/build/dist/Models/DatabaseModels/IncidentForm.js +605 -0
- package/build/dist/Models/DatabaseModels/IncidentForm.js.map +1 -0
- package/build/dist/Models/DatabaseModels/IncidentFormSubmission.js +299 -0
- package/build/dist/Models/DatabaseModels/IncidentFormSubmission.js.map +1 -0
- package/build/dist/Models/DatabaseModels/IncidentTemplate.js +60 -0
- package/build/dist/Models/DatabaseModels/IncidentTemplate.js.map +1 -1
- package/build/dist/Models/DatabaseModels/Index.js +14 -0
- package/build/dist/Models/DatabaseModels/Index.js.map +1 -1
- package/build/dist/Models/DatabaseModels/IoTFleet.js +12 -0
- package/build/dist/Models/DatabaseModels/IoTFleet.js.map +1 -1
- package/build/dist/Models/DatabaseModels/KubernetesCluster.js +12 -0
- package/build/dist/Models/DatabaseModels/KubernetesCluster.js.map +1 -1
- package/build/dist/Models/DatabaseModels/MessageQueue.js +1106 -0
- package/build/dist/Models/DatabaseModels/MessageQueue.js.map +1 -0
- package/build/dist/Models/DatabaseModels/MessageQueueLabelRule.js +562 -0
- package/build/dist/Models/DatabaseModels/MessageQueueLabelRule.js.map +1 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerRule.js +643 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerRule.js.map +1 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerTeam.js +506 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerTeam.js.map +1 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerUser.js +505 -0
- package/build/dist/Models/DatabaseModels/MessageQueueOwnerUser.js.map +1 -0
- package/build/dist/Models/DatabaseModels/PodmanHost.js +12 -0
- package/build/dist/Models/DatabaseModels/PodmanHost.js.map +1 -1
- package/build/dist/Models/DatabaseModels/Project.js +61 -0
- package/build/dist/Models/DatabaseModels/Project.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ProjectOidc.js +0 -4
- package/build/dist/Models/DatabaseModels/ProjectOidc.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ProjectSso.js +0 -4
- package/build/dist/Models/DatabaseModels/ProjectSso.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ProxmoxCluster.js +12 -0
- package/build/dist/Models/DatabaseModels/ProxmoxCluster.js.map +1 -1
- package/build/dist/Models/DatabaseModels/RumApplication.js +12 -0
- package/build/dist/Models/DatabaseModels/RumApplication.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ServerlessFunction.js +12 -0
- package/build/dist/Models/DatabaseModels/ServerlessFunction.js.map +1 -1
- package/build/dist/Models/DatabaseModels/Service.js +12 -0
- package/build/dist/Models/DatabaseModels/Service.js.map +1 -1
- package/build/dist/Models/DatabaseModels/StatusPageOidc.js +0 -4
- package/build/dist/Models/DatabaseModels/StatusPageOidc.js.map +1 -1
- package/build/dist/Models/DatabaseModels/StatusPageSso.js +0 -4
- package/build/dist/Models/DatabaseModels/StatusPageSso.js.map +1 -1
- package/build/dist/Models/DatabaseModels/TeamComplianceSetting.js +49 -3
- package/build/dist/Models/DatabaseModels/TeamComplianceSetting.js.map +1 -1
- package/build/dist/Models/DatabaseModels/VMwareVCenter.js +12 -0
- package/build/dist/Models/DatabaseModels/VMwareVCenter.js.map +1 -1
- package/build/dist/Server/API/AIChatAPI.js +9 -103
- package/build/dist/Server/API/AIChatAPI.js.map +1 -1
- package/build/dist/Server/API/AIInvestigationAPI.js +3 -3
- package/build/dist/Server/API/AIInvestigationAPI.js.map +1 -1
- package/build/dist/Server/API/AIInvestigationConversationAPI.js +162 -0
- package/build/dist/Server/API/AIInvestigationConversationAPI.js.map +1 -0
- package/build/dist/Server/API/IncidentFormAPI.js +245 -0
- package/build/dist/Server/API/IncidentFormAPI.js.map +1 -0
- package/build/dist/Server/API/ProjectOIDC.js +16 -24
- package/build/dist/Server/API/ProjectOIDC.js.map +1 -1
- package/build/dist/Server/API/ProjectSSO.js +16 -24
- package/build/dist/Server/API/ProjectSSO.js.map +1 -1
- package/build/dist/Server/API/StatusPageAPI.js +42 -75
- package/build/dist/Server/API/StatusPageAPI.js.map +1 -1
- package/build/dist/Server/Enterprise/EnterpriseEdition.js +79 -25
- package/build/dist/Server/Enterprise/EnterpriseEdition.js.map +1 -1
- package/build/dist/Server/Enterprise/EnterpriseFeature.js +24 -3
- package/build/dist/Server/Enterprise/EnterpriseFeature.js.map +1 -1
- package/build/dist/Server/Enterprise/EnterpriseLicenseSnapshot.js +1 -1
- package/build/dist/Server/Enterprise/EnterpriseServerModule.js.map +1 -1
- package/build/dist/Server/EnvironmentConfig.js +1 -1
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796400000000-AddIncidentForms.js +63 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796400000000-AddIncidentForms.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796500000000-AddTeamComplianceRuleNotificationChannels.js +41 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796500000000-AddTeamComplianceRuleNotificationChannels.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796600000000-AddAIInvestigationConversationAndTimeLimits.js +40 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796600000000-AddAIInvestigationConversationAndTimeLimits.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796700000000-AddMessageQueueTables.js +183 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1796700000000-AddMessageQueueTables.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js +8 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js.map +1 -1
- package/build/dist/Server/Middleware/IncidentFormRateLimit.js +559 -0
- package/build/dist/Server/Middleware/IncidentFormRateLimit.js.map +1 -0
- package/build/dist/Server/Middleware/UserAuthorization.js +11 -30
- package/build/dist/Server/Middleware/UserAuthorization.js.map +1 -1
- package/build/dist/Server/Services/AIService.js +10 -13
- package/build/dist/Server/Services/AIService.js.map +1 -1
- package/build/dist/Server/Services/IncidentCustomFieldService.js +83 -0
- package/build/dist/Server/Services/IncidentCustomFieldService.js.map +1 -1
- package/build/dist/Server/Services/IncidentEpisodeMemberService.js +8 -4
- package/build/dist/Server/Services/IncidentEpisodeMemberService.js.map +1 -1
- package/build/dist/Server/Services/IncidentEpisodeService.js +10 -1
- package/build/dist/Server/Services/IncidentEpisodeService.js.map +1 -1
- package/build/dist/Server/Services/IncidentFormService.js +1202 -0
- package/build/dist/Server/Services/IncidentFormService.js.map +1 -0
- package/build/dist/Server/Services/IncidentFormSubmissionService.js +91 -0
- package/build/dist/Server/Services/IncidentFormSubmissionService.js.map +1 -0
- package/build/dist/Server/Services/IncidentGroupingEngineService.js +20 -8
- package/build/dist/Server/Services/IncidentGroupingEngineService.js.map +1 -1
- package/build/dist/Server/Services/IncidentService.js +106 -4
- package/build/dist/Server/Services/IncidentService.js.map +1 -1
- package/build/dist/Server/Services/IncidentTemplateService.js +18 -0
- package/build/dist/Server/Services/IncidentTemplateService.js.map +1 -1
- package/build/dist/Server/Services/Index.js +14 -0
- package/build/dist/Server/Services/Index.js.map +1 -1
- package/build/dist/Server/Services/MessageQueueLabelRuleEngineService.js +262 -0
- package/build/dist/Server/Services/MessageQueueLabelRuleEngineService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueLabelRuleService.js +13 -0
- package/build/dist/Server/Services/MessageQueueLabelRuleService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueOwnerRuleEngineService.js +334 -0
- package/build/dist/Server/Services/MessageQueueOwnerRuleEngineService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueOwnerRuleService.js +13 -0
- package/build/dist/Server/Services/MessageQueueOwnerRuleService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueOwnerTeamService.js +62 -0
- package/build/dist/Server/Services/MessageQueueOwnerTeamService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueOwnerUserService.js +62 -0
- package/build/dist/Server/Services/MessageQueueOwnerUserService.js.map +1 -0
- package/build/dist/Server/Services/MessageQueueService.js +1140 -0
- package/build/dist/Server/Services/MessageQueueService.js.map +1 -0
- package/build/dist/Server/Services/OpenTelemetryIngestService.js +25 -4
- package/build/dist/Server/Services/OpenTelemetryIngestService.js.map +1 -1
- package/build/dist/Server/Services/ProjectService.js +0 -54
- package/build/dist/Server/Services/ProjectService.js.map +1 -1
- package/build/dist/Server/Services/StatusPagePrivateUserService.js +1 -4
- package/build/dist/Server/Services/StatusPagePrivateUserService.js.map +1 -1
- package/build/dist/Server/Services/StatusPageService.js +0 -46
- package/build/dist/Server/Services/StatusPageService.js.map +1 -1
- package/build/dist/Server/Services/TeamComplianceSettingService.js +120 -31
- package/build/dist/Server/Services/TeamComplianceSettingService.js.map +1 -1
- package/build/dist/Server/Services/UserNotificationRuleService.js +8 -1
- package/build/dist/Server/Services/UserNotificationRuleService.js.map +1 -1
- package/build/dist/Server/Services/WorkspaceNotificationSummaryService.js +12 -3
- package/build/dist/Server/Services/WorkspaceNotificationSummaryService.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/CreatePermission.js +6 -3
- package/build/dist/Server/Types/Database/Permissions/CreatePermission.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/EditionPermission.js +109 -37
- package/build/dist/Server/Types/Database/Permissions/EditionPermission.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/OwnerTableRegistry.js +16 -0
- package/build/dist/Server/Types/Database/Permissions/OwnerTableRegistry.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/TablePermission.js +3 -3
- package/build/dist/Server/Types/Database/Permissions/UpdatePermission.js +9 -6
- package/build/dist/Server/Types/Database/Permissions/UpdatePermission.js.map +1 -1
- package/build/dist/Server/Utils/AI/Chat/AgentContextCompactor.js +128 -0
- package/build/dist/Server/Utils/AI/Chat/AgentContextCompactor.js.map +1 -0
- package/build/dist/Server/Utils/AI/Chat/ChatAgentRunner.js +192 -50
- package/build/dist/Server/Utils/AI/Chat/ChatAgentRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/Chat/ChatRunCancellation.js +133 -0
- package/build/dist/Server/Utils/AI/Chat/ChatRunCancellation.js.map +1 -0
- package/build/dist/Server/Utils/AI/Chat/ObservabilityAssistant.js +53 -13
- package/build/dist/Server/Utils/AI/Chat/ObservabilityAssistant.js.map +1 -1
- package/build/dist/Server/Utils/AI/Chat/ObservabilityChatPrompt.js +1 -1
- package/build/dist/Server/Utils/AI/Chat/ToolOutputPager.js +206 -0
- package/build/dist/Server/Utils/AI/Chat/ToolOutputPager.js.map +1 -0
- package/build/dist/Server/Utils/AI/ClusterAccess/KubectlInvestigationToolkit.js +53 -26
- package/build/dist/Server/Utils/AI/ClusterAccess/KubectlInvestigationToolkit.js.map +1 -1
- package/build/dist/Server/Utils/AI/ClusterAccess/KubectlJobRunner.js +4 -2
- package/build/dist/Server/Utils/AI/ClusterAccess/KubectlJobRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/CodeFix/CodeFixReadiness.js +1 -29
- package/build/dist/Server/Utils/AI/CodeFix/CodeFixReadiness.js.map +1 -1
- package/build/dist/Server/Utils/AI/CodeFix/FixRunBudget.js +24 -24
- package/build/dist/Server/Utils/AI/CodeFix/FixRunBudget.js.map +1 -1
- package/build/dist/Server/Utils/AI/Remediation/RemediationCommandTools.js +7 -2
- package/build/dist/Server/Utils/AI/Remediation/RemediationCommandTools.js.map +1 -1
- package/build/dist/Server/Utils/AI/Remediation/RemediationExecutionRunner.js +29 -14
- package/build/dist/Server/Utils/AI/Remediation/RemediationExecutionRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/ResourceAccess/InfrastructureInvestigationToolkit.js +38 -14
- package/build/dist/Server/Utils/AI/ResourceAccess/InfrastructureInvestigationToolkit.js.map +1 -1
- package/build/dist/Server/Utils/AI/ResourceAccess/ResourceCommandJobRunner.js +2 -0
- package/build/dist/Server/Utils/AI/ResourceAccess/ResourceCommandJobRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/SRE/AIInvestigationEngine.js +40 -10
- package/build/dist/Server/Utils/AI/SRE/AIInvestigationEngine.js.map +1 -1
- package/build/dist/Server/Utils/AI/SRE/AlertInvestigationRunner.js +19 -7
- package/build/dist/Server/Utils/AI/SRE/AlertInvestigationRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/SRE/IncidentInvestigationRunner.js +19 -7
- package/build/dist/Server/Utils/AI/SRE/IncidentInvestigationRunner.js.map +1 -1
- package/build/dist/Server/Utils/AI/SRE/InvestigationQueue.js +15 -18
- package/build/dist/Server/Utils/AI/SRE/InvestigationQueue.js.map +1 -1
- package/build/dist/Server/Utils/AI/SRE/InvestigationThread.js +412 -0
- package/build/dist/Server/Utils/AI/SRE/InvestigationThread.js.map +1 -0
- package/build/dist/Server/Utils/AI/SRE/InvestigationThreadService.js +495 -0
- package/build/dist/Server/Utils/AI/SRE/InvestigationThreadService.js.map +1 -0
- package/build/dist/Server/Utils/AI/Toolbox/Serializer.js +10 -3
- package/build/dist/Server/Utils/AI/Toolbox/Serializer.js.map +1 -1
- package/build/dist/Server/Utils/EditionEnforcement.js +20 -158
- package/build/dist/Server/Utils/EditionEnforcement.js.map +1 -1
- package/build/dist/Server/Utils/LLM/LLMService.js +193 -54
- package/build/dist/Server/Utils/LLM/LLMService.js.map +1 -1
- package/build/dist/Server/Utils/RelaxedScimTeamLocksReport.js +160 -0
- package/build/dist/Server/Utils/RelaxedScimTeamLocksReport.js.map +1 -0
- package/build/dist/Server/Utils/Rules/RuleRun/RuleRunRegistry.js +25 -0
- package/build/dist/Server/Utils/Rules/RuleRun/RuleRunRegistry.js.map +1 -1
- package/build/dist/Server/Utils/SameOriginRequest.js +151 -0
- package/build/dist/Server/Utils/SameOriginRequest.js.map +1 -0
- package/build/dist/Server/Utils/TeamMember/ProjectLeaveResourceCleanup.js +2 -0
- package/build/dist/Server/Utils/TeamMember/ProjectLeaveResourceCleanup.js.map +1 -1
- package/build/dist/Server/Utils/Telemetry/EntityRegistry.js +4 -1
- package/build/dist/Server/Utils/Telemetry/EntityRegistry.js.map +1 -1
- package/build/dist/Server/Utils/Telemetry/MessageQueueDiscovery.js +1015 -0
- package/build/dist/Server/Utils/Telemetry/MessageQueueDiscovery.js.map +1 -0
- package/build/dist/Server/Utils/Telemetry/ResourceEntityFilter.js +4 -1
- package/build/dist/Server/Utils/Telemetry/ResourceEntityFilter.js.map +1 -1
- package/build/dist/Server/Utils/VendorAssets.js +3 -3
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.js +3 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/IncidentEpisode.js +3 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/IncidentEpisode.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.js +10 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.js.map +1 -1
- package/build/dist/Types/AI/AIAgentRunLimits.js +91 -0
- package/build/dist/Types/AI/AIAgentRunLimits.js.map +1 -0
- package/build/dist/Types/Code/CodeType.js +2 -0
- package/build/dist/Types/Code/CodeType.js.map +1 -1
- package/build/dist/Types/Code/JsonSyntax.js +604 -0
- package/build/dist/Types/Code/JsonSyntax.js.map +1 -0
- package/build/dist/Types/CustomField/CustomFieldCreateSettings.js +310 -0
- package/build/dist/Types/CustomField/CustomFieldCreateSettings.js.map +1 -0
- package/build/dist/Types/CustomField/CustomFieldMappingCatalog.js +38 -0
- package/build/dist/Types/CustomField/CustomFieldMappingCatalog.js.map +1 -1
- package/build/dist/Types/CustomField/CustomFieldValueValidator.js +10 -7
- package/build/dist/Types/CustomField/CustomFieldValueValidator.js.map +1 -1
- package/build/dist/Types/EnterpriseLicense/EnterpriseLicensePeriods.js +1 -1
- package/build/dist/Types/Icon/IconProp.js +2 -0
- package/build/dist/Types/Icon/IconProp.js.map +1 -1
- package/build/dist/Types/Incident/IncidentFormIpAllowlist.js +119 -0
- package/build/dist/Types/Incident/IncidentFormIpAllowlist.js.map +1 -0
- package/build/dist/Types/Incident/IncidentFormPublic.js +678 -0
- package/build/dist/Types/Incident/IncidentFormPublic.js.map +1 -0
- package/build/dist/Types/Kubernetes/KubernetesClusterAiAccess.js +10 -3
- package/build/dist/Types/Kubernetes/KubernetesClusterAiAccess.js.map +1 -1
- package/build/dist/Types/MessageQueue/MessageQueueIdentity.js +184 -0
- package/build/dist/Types/MessageQueue/MessageQueueIdentity.js.map +1 -0
- package/build/dist/Types/MessageQueue/MessageQueueManualIdentity.js +190 -0
- package/build/dist/Types/MessageQueue/MessageQueueManualIdentity.js.map +1 -0
- package/build/dist/Types/MessageQueue/MessageQueueMetricCatalog.js +1057 -0
- package/build/dist/Types/MessageQueue/MessageQueueMetricCatalog.js.map +1 -0
- package/build/dist/Types/MessageQueue/MessagingSystem.js +394 -0
- package/build/dist/Types/MessageQueue/MessagingSystem.js.map +1 -0
- package/build/dist/Types/MessageQueue/MessagingTelemetryResolver.js +1768 -0
- package/build/dist/Types/MessageQueue/MessagingTelemetryResolver.js.map +1 -0
- package/build/dist/Types/Monitor/MessageQueueAlertTemplates.js +1207 -0
- package/build/dist/Types/Monitor/MessageQueueAlertTemplates.js.map +1 -0
- package/build/dist/Types/Permission.js +274 -0
- package/build/dist/Types/Permission.js.map +1 -1
- package/build/dist/Types/ResourceAiAgent/ResourceAiAccess.js +10 -4
- package/build/dist/Types/ResourceAiAgent/ResourceAiAccess.js.map +1 -1
- package/build/dist/Types/Rules/RuleCriteriaFieldRegistry.js +12 -0
- package/build/dist/Types/Rules/RuleCriteriaFieldRegistry.js.map +1 -1
- package/build/dist/Types/Rules/RuleRun.js +4 -0
- package/build/dist/Types/Rules/RuleRun.js.map +1 -1
- package/build/dist/Types/Team/ComplianceNotificationChannel.js +4 -3
- package/build/dist/Types/Team/ComplianceNotificationChannel.js.map +1 -1
- package/build/dist/Types/Team/ComplianceRule.js +48 -14
- package/build/dist/Types/Team/ComplianceRule.js.map +1 -1
- package/build/dist/Types/Team/ComplianceRuleType.js +2 -2
- package/build/dist/Types/Telemetry/EntityType.js +16 -0
- package/build/dist/Types/Telemetry/EntityType.js.map +1 -1
- package/build/dist/Types/XML.js +23 -0
- package/build/dist/Types/XML.js.map +1 -1
- package/build/dist/UI/Components/CodeEditor/CodeEditor.js +641 -266
- package/build/dist/UI/Components/CodeEditor/CodeEditor.js.map +1 -1
- package/build/dist/UI/Components/CodeEditor/CodeEditorCommands.js +464 -0
- package/build/dist/UI/Components/CodeEditor/CodeEditorCommands.js.map +1 -0
- package/build/dist/UI/Components/CodeEditor/CodeEditorHighlight.js +69 -0
- package/build/dist/UI/Components/CodeEditor/CodeEditorHighlight.js.map +1 -0
- package/build/dist/UI/Components/CodeEditor/CodeEditorLanguages.js +108 -0
- package/build/dist/UI/Components/CodeEditor/CodeEditorLanguages.js.map +1 -0
- package/build/dist/UI/Components/CodeEditor/YamlEditor.js +14 -186
- package/build/dist/UI/Components/CodeEditor/YamlEditor.js.map +1 -1
- package/build/dist/UI/Components/CopyTextButton/CopyTextButton.js +5 -1
- package/build/dist/UI/Components/CopyTextButton/CopyTextButton.js.map +1 -1
- package/build/dist/UI/Components/CustomFields/CustomFieldModelFormFields.js +5 -14
- package/build/dist/UI/Components/CustomFields/CustomFieldModelFormFields.js.map +1 -1
- package/build/dist/UI/Components/EditionLabel/EditionLabel.js +14 -13
- package/build/dist/UI/Components/EditionLabel/EditionLabel.js.map +1 -1
- package/build/dist/UI/Components/ErrorMessage/ErrorMessage.js +1 -1
- package/build/dist/UI/Components/ErrorMessage/ErrorMessage.js.map +1 -1
- package/build/dist/UI/Components/Forms/Fields/FormField.js +8 -3
- package/build/dist/UI/Components/Forms/Fields/FormField.js.map +1 -1
- package/build/dist/UI/Components/Icon/Icon.js +8 -0
- package/build/dist/UI/Components/Icon/Icon.js.map +1 -1
- package/build/dist/UI/Components/Input/Input.js +11 -3
- package/build/dist/UI/Components/Input/Input.js.map +1 -1
- package/build/dist/UI/Components/LogsViewer/LogsViewer.js +2 -1
- package/build/dist/UI/Components/LogsViewer/LogsViewer.js.map +1 -1
- package/build/dist/UI/Components/LogsViewer/components/LogsFacetSidebar.js +14 -4
- package/build/dist/UI/Components/LogsViewer/components/LogsFacetSidebar.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownConverters.js +0 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownConverters.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownEditor.js +710 -65
- package/build/dist/UI/Components/Markdown.tsx/MarkdownEditor.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownEditorHistory.js +238 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownEditorHistory.js.map +1 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownListEditing.js +1028 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownListEditing.js.map +1 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownPaste.js +1088 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownPaste.js.map +1 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownViewer.js +70 -10
- package/build/dist/UI/Components/Markdown.tsx/MarkdownViewer.js.map +1 -1
- package/build/dist/UI/Components/Markdown.tsx/MarkdownVisualEditing.js +887 -0
- package/build/dist/UI/Components/Markdown.tsx/MarkdownVisualEditing.js.map +1 -0
- package/build/dist/UI/Components/ModelTable/BaseModelTable.js +57 -6
- package/build/dist/UI/Components/ModelTable/BaseModelTable.js.map +1 -1
- package/build/dist/UI/Components/ResetObjectID/ResetObjectID.js +7 -5
- package/build/dist/UI/Components/ResetObjectID/ResetObjectID.js.map +1 -1
- package/build/dist/UI/Components/Table/EmptyTableMessage.js +51 -0
- package/build/dist/UI/Components/Table/EmptyTableMessage.js.map +1 -0
- package/build/dist/UI/Components/Table/Table.js +30 -11
- package/build/dist/UI/Components/Table/Table.js.map +1 -1
- package/build/dist/UI/Components/Table/TableRow.js +9 -2
- package/build/dist/UI/Components/Table/TableRow.js.map +1 -1
- package/build/dist/UI/Components/TelemetryViewer/FacetVisibility.js +63 -1
- package/build/dist/UI/Components/TelemetryViewer/FacetVisibility.js.map +1 -1
- package/build/dist/UI/Components/TelemetryViewer/TelemetryViewer.js +4 -2
- package/build/dist/UI/Components/TelemetryViewer/TelemetryViewer.js.map +1 -1
- package/build/dist/UI/Components/TelemetryViewer/components/LockedFilterChip.js +91 -10
- package/build/dist/UI/Components/TelemetryViewer/components/LockedFilterChip.js.map +1 -1
- package/build/dist/UI/Components/TelemetryViewer/components/TelemetryFacetSidebar.js +14 -4
- package/build/dist/UI/Components/TelemetryViewer/components/TelemetryFacetSidebar.js.map +1 -1
- package/build/dist/UI/Components/TextArea/TextArea.js +9 -3
- package/build/dist/UI/Components/TextArea/TextArea.js.map +1 -1
- package/build/dist/UI/Components/Workflow/ModelFieldPicker.js +1 -2
- package/build/dist/UI/Components/Workflow/ModelFieldPicker.js.map +1 -1
- package/build/dist/Utils/LabelRuleImportExport.js +2 -0
- package/build/dist/Utils/LabelRuleImportExport.js.map +1 -1
- package/build/dist/Utils/Markdown/UntrustedMarkdown.js +988 -0
- package/build/dist/Utils/Markdown/UntrustedMarkdown.js.map +1 -0
- package/build/dist/Utils/Monitor/IncomingEmailMonitorRequestUtil.js +34 -0
- package/build/dist/Utils/Monitor/IncomingEmailMonitorRequestUtil.js.map +1 -0
- package/build/dist/Utils/Monitor/MonitorLogSummaryUtil.js +148 -0
- package/build/dist/Utils/Monitor/MonitorLogSummaryUtil.js.map +1 -0
- package/build/dist/Utils/Telemetry/EntityKey.js +36 -0
- package/build/dist/Utils/Telemetry/EntityKey.js.map +1 -1
- package/package.json +1 -3
- package/Server/Utils/CommunityEditionSsoReport.ts +0 -361
- package/Tests/App/Accounts/LoginSsoEdition.test.tsx +0 -616
- package/Tests/App/AdminDashboard/AdminAuthenticationSsoEdition.test.tsx +0 -217
- package/Tests/App/AdminDashboard/GlobalSSOEnterpriseShells.test.tsx +0 -271
- package/Tests/App/Dashboard/CloudDocumentationMarkdown.test.ts +0 -215
- package/Tests/App/Dashboard/TelemetryResourceRetentionSettings.test.tsx +0 -784
- package/Tests/Server/Middleware/UserAuthorizationEditionEnforcement.test.ts +0 -518
- package/Tests/Server/Services/SsoRequirementReadMasking.test.ts +0 -419
- package/Tests/Server/Services/SsoRequirementWriteGuard.test.ts +0 -769
- package/Tests/UI/Components/CodeEditor.test.tsx +0 -638
- package/Tests/UI/Components/MonacoLoader.test.ts +0 -67
- package/Tests/UI/Components/MonacoRuntime.test.ts +0 -121
- package/Tests/UI/Components/Telemetry/TelemetryRetentionConfigForm.test.tsx +0 -329
- package/Tests/UI/Components/YamlEditor.test.tsx +0 -847
- package/UI/Components/CodeEditor/MonacoLoader.ts +0 -36
- package/UI/Components/Telemetry/TelemetryRetentionConfigForm.tsx +0 -319
- package/UI/Components/Telemetry/TelemetryRetentionConfigSummary.tsx +0 -223
- package/build/dist/Server/Utils/CommunityEditionSsoReport.js +0 -223
- package/build/dist/Server/Utils/CommunityEditionSsoReport.js.map +0 -1
- package/build/dist/UI/Components/CodeEditor/MonacoLoader.js +0 -34
- package/build/dist/UI/Components/CodeEditor/MonacoLoader.js.map +0 -1
- package/build/dist/UI/Components/Telemetry/TelemetryRetentionConfigForm.js +0 -171
- package/build/dist/UI/Components/Telemetry/TelemetryRetentionConfigForm.js.map +0 -1
- package/build/dist/UI/Components/Telemetry/TelemetryRetentionConfigSummary.js +0 -119
- package/build/dist/UI/Components/Telemetry/TelemetryRetentionConfigSummary.js.map +0 -1
|
@@ -0,0 +1,1318 @@
|
|
|
1
|
+
import { describe, expect, test } from "@jest/globals";
|
|
2
|
+
import fs from "fs";
|
|
3
|
+
import path from "path";
|
|
4
|
+
import yaml from "js-yaml";
|
|
5
|
+
import markdownSlugify from "../../../Server/Types/MarkdownSlugify";
|
|
6
|
+
import {
|
|
7
|
+
DEFAULT_PROXMOX_CONNECT_METHOD,
|
|
8
|
+
PROXMOX_AGENT_COLLECTOR_CONFIG,
|
|
9
|
+
PROXMOX_AGENT_CONTAINER,
|
|
10
|
+
PROXMOX_AGENT_INSTALL_DIR,
|
|
11
|
+
PROXMOX_AGENT_RAW_URL,
|
|
12
|
+
PROXMOX_AGENT_SOURCE_URL,
|
|
13
|
+
PROXMOX_AI_AGENT_CONTAINER,
|
|
14
|
+
PROXMOX_CONNECT_METHODS,
|
|
15
|
+
PROXMOX_EXAMPLE_CLUSTER_NAME,
|
|
16
|
+
PROXMOX_EXPORTER_CONTAINER,
|
|
17
|
+
PROXMOX_NATIVE_PUSH_PATH,
|
|
18
|
+
PROXMOX_PUSH_HOST_PLACEHOLDER,
|
|
19
|
+
PROXMOX_TOKEN_ID,
|
|
20
|
+
PROXMOX_TOKEN_USER,
|
|
21
|
+
ProxmoxConnectMethod,
|
|
22
|
+
ProxmoxPushTarget,
|
|
23
|
+
getProxmoxInstallScriptCommand,
|
|
24
|
+
getProxmoxPushTarget,
|
|
25
|
+
getProxmoxSetupGuide,
|
|
26
|
+
resolveProxmoxConnectMethod,
|
|
27
|
+
} from "../../../../App/FeatureSet/Dashboard/src/Pages/Proxmox/Utils/DocumentationMarkdown";
|
|
28
|
+
import {
|
|
29
|
+
SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
30
|
+
SETUP_GUIDE_URL_PLACEHOLDER,
|
|
31
|
+
SetupGuideContent,
|
|
32
|
+
SetupGuideOption,
|
|
33
|
+
SetupGuideStep,
|
|
34
|
+
SetupGuideStepVariant,
|
|
35
|
+
SetupGuideTopic,
|
|
36
|
+
codeBlock,
|
|
37
|
+
getSetupGuideCodeBlocks,
|
|
38
|
+
getSetupGuideMarkdown,
|
|
39
|
+
} from "../../../../App/FeatureSet/Dashboard/src/Components/SetupGuide/SetupGuide";
|
|
40
|
+
|
|
41
|
+
/*
|
|
42
|
+
* The Proxmox guide asks how to connect the cluster — the agent through the
|
|
43
|
+
* install script, the agent through Docker Compose, or Proxmox VE 9's own
|
|
44
|
+
* OpenTelemetry push — and shows only that path. These tests pin:
|
|
45
|
+
*
|
|
46
|
+
* - the reader's URL and key in every command, file and form field that
|
|
47
|
+
* needs them, and never a placeholder key in the install script's
|
|
48
|
+
* environment (the script would write it into .env as the key);
|
|
49
|
+
* - a read-only token that actually works: a privilege-separated token
|
|
50
|
+
* only gets what its user also has, so the role goes on both;
|
|
51
|
+
* - that the native push never mentions installing anything, and says
|
|
52
|
+
* what it cannot send;
|
|
53
|
+
* - that the collector config the guide shows IS the shipped file, and
|
|
54
|
+
* every variable, file, container and script it names exists in
|
|
55
|
+
* agents/ProxmoxAgent.
|
|
56
|
+
*/
|
|
57
|
+
|
|
58
|
+
const REPO_ROOT: string = path.resolve(__dirname, "../../../../..");
|
|
59
|
+
const AGENT_DIR: string = path.join(REPO_ROOT, "agents", "ProxmoxAgent");
|
|
60
|
+
const DOCS_DIR: string = path.join(
|
|
61
|
+
REPO_ROOT,
|
|
62
|
+
"packages",
|
|
63
|
+
"App",
|
|
64
|
+
"FeatureSet",
|
|
65
|
+
"Docs",
|
|
66
|
+
"Content",
|
|
67
|
+
"en",
|
|
68
|
+
);
|
|
69
|
+
|
|
70
|
+
const URL: string = "https://oneuptime.example.com";
|
|
71
|
+
const KEY: string = "tik_secret_123";
|
|
72
|
+
|
|
73
|
+
// What ObjectID.generate() mints: the E2E spec greps the page for one.
|
|
74
|
+
const UUID_KEY: string = "0f8fad5b-d9cb-469f-a165-70867728950e";
|
|
75
|
+
|
|
76
|
+
const METHOD_KEYS: Array<ProxmoxConnectMethod> = PROXMOX_CONNECT_METHODS.map(
|
|
77
|
+
(option: SetupGuideOption<ProxmoxConnectMethod>): ProxmoxConnectMethod => {
|
|
78
|
+
return option.key;
|
|
79
|
+
},
|
|
80
|
+
);
|
|
81
|
+
|
|
82
|
+
const AGENT_METHODS: Array<ProxmoxConnectMethod> = [
|
|
83
|
+
"install-script",
|
|
84
|
+
"docker-compose",
|
|
85
|
+
];
|
|
86
|
+
|
|
87
|
+
interface GuideOverrides {
|
|
88
|
+
oneuptimeUrl?: string;
|
|
89
|
+
apiKey?: string;
|
|
90
|
+
hasApiKey?: boolean;
|
|
91
|
+
clusterName?: string;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const guideFor: (
|
|
95
|
+
method: ProxmoxConnectMethod,
|
|
96
|
+
overrides?: GuideOverrides,
|
|
97
|
+
) => SetupGuideContent = (
|
|
98
|
+
method: ProxmoxConnectMethod,
|
|
99
|
+
overrides?: GuideOverrides,
|
|
100
|
+
): SetupGuideContent => {
|
|
101
|
+
const apiKey: string = overrides?.apiKey ?? KEY;
|
|
102
|
+
return getProxmoxSetupGuide({
|
|
103
|
+
oneuptimeUrl: overrides?.oneuptimeUrl ?? URL,
|
|
104
|
+
apiKey: apiKey,
|
|
105
|
+
hasApiKey:
|
|
106
|
+
overrides?.hasApiKey ?? apiKey !== SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
107
|
+
method: method,
|
|
108
|
+
clusterName: overrides?.clusterName,
|
|
109
|
+
});
|
|
110
|
+
};
|
|
111
|
+
|
|
112
|
+
const noKeyGuideFor: (method: ProxmoxConnectMethod) => SetupGuideContent = (
|
|
113
|
+
method: ProxmoxConnectMethod,
|
|
114
|
+
): SetupGuideContent => {
|
|
115
|
+
return guideFor(method, {
|
|
116
|
+
apiKey: SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
117
|
+
hasApiKey: false,
|
|
118
|
+
});
|
|
119
|
+
};
|
|
120
|
+
|
|
121
|
+
const stepTitled: (
|
|
122
|
+
guide: SetupGuideContent,
|
|
123
|
+
title: string,
|
|
124
|
+
) => SetupGuideStep = (
|
|
125
|
+
guide: SetupGuideContent,
|
|
126
|
+
title: string,
|
|
127
|
+
): SetupGuideStep => {
|
|
128
|
+
const step: SetupGuideStep | undefined = guide.steps.find(
|
|
129
|
+
(candidate: SetupGuideStep): boolean => {
|
|
130
|
+
return candidate.title === title;
|
|
131
|
+
},
|
|
132
|
+
);
|
|
133
|
+
if (!step) {
|
|
134
|
+
throw new Error(`No step titled "${title}"`);
|
|
135
|
+
}
|
|
136
|
+
return step;
|
|
137
|
+
};
|
|
138
|
+
|
|
139
|
+
const topicTitled: (
|
|
140
|
+
topics: Array<SetupGuideTopic> | undefined,
|
|
141
|
+
title: string,
|
|
142
|
+
) => SetupGuideTopic = (
|
|
143
|
+
topics: Array<SetupGuideTopic> | undefined,
|
|
144
|
+
title: string,
|
|
145
|
+
): SetupGuideTopic => {
|
|
146
|
+
const topic: SetupGuideTopic | undefined = (topics || []).find(
|
|
147
|
+
(candidate: SetupGuideTopic): boolean => {
|
|
148
|
+
return candidate.title === title;
|
|
149
|
+
},
|
|
150
|
+
);
|
|
151
|
+
if (!topic) {
|
|
152
|
+
throw new Error(`No topic titled "${title}"`);
|
|
153
|
+
}
|
|
154
|
+
return topic;
|
|
155
|
+
};
|
|
156
|
+
|
|
157
|
+
const topicTitles: (
|
|
158
|
+
topics: Array<SetupGuideTopic> | undefined,
|
|
159
|
+
) => Array<string> = (
|
|
160
|
+
topics: Array<SetupGuideTopic> | undefined,
|
|
161
|
+
): Array<string> => {
|
|
162
|
+
return (topics || []).map((topic: SetupGuideTopic): string => {
|
|
163
|
+
return topic.title;
|
|
164
|
+
});
|
|
165
|
+
};
|
|
166
|
+
|
|
167
|
+
// Everything a step shows: its description, its markdown and every tab.
|
|
168
|
+
const stepText: (step: SetupGuideStep) => string = (
|
|
169
|
+
step: SetupGuideStep,
|
|
170
|
+
): string => {
|
|
171
|
+
return [
|
|
172
|
+
step.description || "",
|
|
173
|
+
step.markdown || "",
|
|
174
|
+
...(step.variants || []).map((variant: SetupGuideStepVariant): string => {
|
|
175
|
+
return variant.markdown;
|
|
176
|
+
}),
|
|
177
|
+
].join("\n");
|
|
178
|
+
};
|
|
179
|
+
|
|
180
|
+
const stepsText: (guide: SetupGuideContent) => string = (
|
|
181
|
+
guide: SetupGuideContent,
|
|
182
|
+
): string => {
|
|
183
|
+
return guide.steps.map(stepText).join("\n");
|
|
184
|
+
};
|
|
185
|
+
|
|
186
|
+
const installStep: (guide: SetupGuideContent) => string = (
|
|
187
|
+
guide: SetupGuideContent,
|
|
188
|
+
): string => {
|
|
189
|
+
return stepTitled(guide, "Install the agent").markdown || "";
|
|
190
|
+
};
|
|
191
|
+
|
|
192
|
+
const variantTitled: (
|
|
193
|
+
step: SetupGuideStep,
|
|
194
|
+
label: string,
|
|
195
|
+
) => SetupGuideStepVariant = (
|
|
196
|
+
step: SetupGuideStep,
|
|
197
|
+
label: string,
|
|
198
|
+
): SetupGuideStepVariant => {
|
|
199
|
+
const variant: SetupGuideStepVariant | undefined = (step.variants || []).find(
|
|
200
|
+
(candidate: SetupGuideStepVariant): boolean => {
|
|
201
|
+
return candidate.label === label;
|
|
202
|
+
},
|
|
203
|
+
);
|
|
204
|
+
if (!variant) {
|
|
205
|
+
throw new Error(`No tab labelled "${label}"`);
|
|
206
|
+
}
|
|
207
|
+
return variant;
|
|
208
|
+
};
|
|
209
|
+
|
|
210
|
+
// The .env block of the Docker Compose install.
|
|
211
|
+
const envFileOf: (guide: SetupGuideContent) => string = (
|
|
212
|
+
guide: SetupGuideContent,
|
|
213
|
+
): string => {
|
|
214
|
+
const block: string | undefined = getSetupGuideCodeBlocks(guide).find(
|
|
215
|
+
(candidate: string): boolean => {
|
|
216
|
+
return candidate.startsWith("ONEUPTIME_URL=");
|
|
217
|
+
},
|
|
218
|
+
);
|
|
219
|
+
if (!block) {
|
|
220
|
+
throw new Error("The guide has no .env block");
|
|
221
|
+
}
|
|
222
|
+
return block.trimEnd();
|
|
223
|
+
};
|
|
224
|
+
|
|
225
|
+
const readAgentFile: (name: string) => string = (name: string): string => {
|
|
226
|
+
return fs.readFileSync(path.join(AGENT_DIR, name), "utf8");
|
|
227
|
+
};
|
|
228
|
+
|
|
229
|
+
const composeFile: () => Record<string, any> = (): Record<string, any> => {
|
|
230
|
+
return yaml.load(readAgentFile("docker-compose.yml")) as Record<string, any>;
|
|
231
|
+
};
|
|
232
|
+
|
|
233
|
+
// Variables a compose service reads from .env: `${NAME}` and `${NAME:-x}`.
|
|
234
|
+
const composeVariables: (serviceName: string) => Map<string, string | null> = (
|
|
235
|
+
serviceName: string,
|
|
236
|
+
): Map<string, string | null> => {
|
|
237
|
+
const environment: Array<string> =
|
|
238
|
+
composeFile()["services"][serviceName]["environment"];
|
|
239
|
+
const variables: Map<string, string | null> = new Map();
|
|
240
|
+
for (const entry of environment) {
|
|
241
|
+
for (const match of entry.matchAll(/\$\{([A-Z0-9_]+)(?::-([^}]*))?\}/g)) {
|
|
242
|
+
variables.set(match[1]!, match[2] ?? null);
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
return variables;
|
|
246
|
+
};
|
|
247
|
+
|
|
248
|
+
// The rows of the guide's environment variable table.
|
|
249
|
+
const envTableRows: (
|
|
250
|
+
guide: SetupGuideContent,
|
|
251
|
+
) => Map<string, { required: string; description: string }> = (
|
|
252
|
+
guide: SetupGuideContent,
|
|
253
|
+
): Map<string, { required: string; description: string }> => {
|
|
254
|
+
const markdown: string = topicTitled(
|
|
255
|
+
guide.advanced,
|
|
256
|
+
"Environment variables",
|
|
257
|
+
).markdown;
|
|
258
|
+
const rows: Map<string, { required: string; description: string }> =
|
|
259
|
+
new Map();
|
|
260
|
+
for (const match of markdown.matchAll(
|
|
261
|
+
/^\| `([A-Z0-9_]+)` \| ([^|]+) \| (.*) \|$/gm,
|
|
262
|
+
)) {
|
|
263
|
+
rows.set(match[1]!, {
|
|
264
|
+
required: match[2]!.trim(),
|
|
265
|
+
description: match[3]!,
|
|
266
|
+
});
|
|
267
|
+
}
|
|
268
|
+
return rows;
|
|
269
|
+
};
|
|
270
|
+
|
|
271
|
+
describe("the connect method picker", () => {
|
|
272
|
+
test("offers the install script, Docker Compose and the native push, in that order", () => {
|
|
273
|
+
expect(METHOD_KEYS).toEqual([
|
|
274
|
+
"install-script",
|
|
275
|
+
"docker-compose",
|
|
276
|
+
"native-push",
|
|
277
|
+
]);
|
|
278
|
+
expect(DEFAULT_PROXMOX_CONNECT_METHOD).toBe("install-script");
|
|
279
|
+
expect(
|
|
280
|
+
PROXMOX_CONNECT_METHODS.map(
|
|
281
|
+
(option: SetupGuideOption<ProxmoxConnectMethod>): string => {
|
|
282
|
+
return option.label;
|
|
283
|
+
},
|
|
284
|
+
),
|
|
285
|
+
).toEqual([
|
|
286
|
+
"Install script",
|
|
287
|
+
"Docker Compose",
|
|
288
|
+
"Native push (Proxmox VE 9+)",
|
|
289
|
+
]);
|
|
290
|
+
});
|
|
291
|
+
|
|
292
|
+
test("recommends only the install script", () => {
|
|
293
|
+
expect(
|
|
294
|
+
PROXMOX_CONNECT_METHODS.map(
|
|
295
|
+
(
|
|
296
|
+
option: SetupGuideOption<ProxmoxConnectMethod>,
|
|
297
|
+
): string | undefined => {
|
|
298
|
+
return option.badge;
|
|
299
|
+
},
|
|
300
|
+
),
|
|
301
|
+
).toEqual(["Recommended", undefined, undefined]);
|
|
302
|
+
});
|
|
303
|
+
|
|
304
|
+
test("every method has a one-line description", () => {
|
|
305
|
+
for (const option of PROXMOX_CONNECT_METHODS) {
|
|
306
|
+
expect((option.description || "").length).toBeGreaterThan(0);
|
|
307
|
+
expect(option.description).not.toContain("\n");
|
|
308
|
+
}
|
|
309
|
+
});
|
|
310
|
+
|
|
311
|
+
test("the native push says up front what it leaves out", () => {
|
|
312
|
+
const native: string = PROXMOX_CONNECT_METHODS[2]!.description || "";
|
|
313
|
+
expect(native).toContain("Nothing to install");
|
|
314
|
+
expect(native).toContain("HA");
|
|
315
|
+
expect(native).toContain("backup");
|
|
316
|
+
expect(native).toContain("replication");
|
|
317
|
+
});
|
|
318
|
+
|
|
319
|
+
test("only the Docker Compose option's name mentions Docker Compose", () => {
|
|
320
|
+
/*
|
|
321
|
+
* A radio's accessible name is its label plus its description, and the
|
|
322
|
+
* E2E specs pick this option by /^Docker Compose/.
|
|
323
|
+
*/
|
|
324
|
+
for (const option of [
|
|
325
|
+
PROXMOX_CONNECT_METHODS[0]!,
|
|
326
|
+
PROXMOX_CONNECT_METHODS[2]!,
|
|
327
|
+
]) {
|
|
328
|
+
expect(`${option.label} ${option.description}`).not.toContain(
|
|
329
|
+
"Docker Compose",
|
|
330
|
+
);
|
|
331
|
+
}
|
|
332
|
+
});
|
|
333
|
+
|
|
334
|
+
test("an unknown or missing method resolves to the install script", () => {
|
|
335
|
+
for (const value of [undefined, null, "", "helm", "NATIVE-PUSH"]) {
|
|
336
|
+
expect(resolveProxmoxConnectMethod(value)).toBe("install-script");
|
|
337
|
+
}
|
|
338
|
+
expect(resolveProxmoxConnectMethod("native-push")).toBe("native-push");
|
|
339
|
+
expect(resolveProxmoxConnectMethod("docker-compose")).toBe(
|
|
340
|
+
"docker-compose",
|
|
341
|
+
);
|
|
342
|
+
});
|
|
343
|
+
});
|
|
344
|
+
|
|
345
|
+
describe.each(METHOD_KEYS)("the %s guide", (method: ProxmoxConnectMethod) => {
|
|
346
|
+
const guide: SetupGuideContent = guideFor(method);
|
|
347
|
+
const markdown: string = getSetupGuideMarkdown(guide);
|
|
348
|
+
|
|
349
|
+
test("every step has a plain one-sentence description", () => {
|
|
350
|
+
for (const step of guide.steps) {
|
|
351
|
+
expect(step.description).toBeTruthy();
|
|
352
|
+
// Descriptions render as plain text, so no markdown.
|
|
353
|
+
expect(step.description).not.toMatch(/[`*[\]]/);
|
|
354
|
+
expect(step.description).not.toContain("\n");
|
|
355
|
+
}
|
|
356
|
+
});
|
|
357
|
+
|
|
358
|
+
test("has two to four prerequisites", () => {
|
|
359
|
+
expect(guide.prerequisites!.length).toBeGreaterThanOrEqual(2);
|
|
360
|
+
expect(guide.prerequisites!.length).toBeLessThanOrEqual(4);
|
|
361
|
+
});
|
|
362
|
+
|
|
363
|
+
test("every Advanced topic has a plain one-line summary", () => {
|
|
364
|
+
expect((guide.advanced || []).length).toBeGreaterThan(0);
|
|
365
|
+
for (const topic of guide.advanced || []) {
|
|
366
|
+
expect(topic.summary).toBeTruthy();
|
|
367
|
+
// Summaries render as plain text, so no markdown.
|
|
368
|
+
expect(topic.summary).not.toMatch(/[`*[\]]/);
|
|
369
|
+
expect(topic.summary).not.toContain("\n");
|
|
370
|
+
}
|
|
371
|
+
});
|
|
372
|
+
|
|
373
|
+
test("links to the Proxmox documentation", () => {
|
|
374
|
+
expect(guide.links).toEqual([
|
|
375
|
+
{ title: "Proxmox documentation", url: "/docs/telemetry/proxmox" },
|
|
376
|
+
{
|
|
377
|
+
title: "Proxmox monitors and alerts",
|
|
378
|
+
url: "/docs/monitor/proxmox-monitor",
|
|
379
|
+
},
|
|
380
|
+
]);
|
|
381
|
+
});
|
|
382
|
+
|
|
383
|
+
test("every documentation link points at a page, and anchor, that exists", () => {
|
|
384
|
+
const links: Array<string> = Array.from(
|
|
385
|
+
markdown.matchAll(/\]\((\/docs\/[^)\s]+)\)/g),
|
|
386
|
+
).map((match: RegExpMatchArray): string => {
|
|
387
|
+
return match[1]!;
|
|
388
|
+
});
|
|
389
|
+
expect(links.length).toBeGreaterThanOrEqual(2);
|
|
390
|
+
for (const link of links) {
|
|
391
|
+
const parts: Array<string> = link.replace(/^\/docs\//, "").split("#");
|
|
392
|
+
const anchor: string | undefined = parts[1];
|
|
393
|
+
const file: string = path.join(DOCS_DIR, `${parts[0]}.md`);
|
|
394
|
+
expect({ link, exists: fs.existsSync(file) }).toEqual({
|
|
395
|
+
link,
|
|
396
|
+
exists: true,
|
|
397
|
+
});
|
|
398
|
+
if (anchor) {
|
|
399
|
+
const headings: Array<string> = Array.from(
|
|
400
|
+
fs.readFileSync(file, "utf8").matchAll(/^#+ (.+)$/gm),
|
|
401
|
+
).map((match: RegExpMatchArray): string => {
|
|
402
|
+
return markdownSlugify(match[1]!);
|
|
403
|
+
});
|
|
404
|
+
expect(headings).toContain(anchor);
|
|
405
|
+
}
|
|
406
|
+
}
|
|
407
|
+
});
|
|
408
|
+
});
|
|
409
|
+
|
|
410
|
+
describe.each(AGENT_METHODS)(
|
|
411
|
+
"the agent guide, %s",
|
|
412
|
+
(method: ProxmoxConnectMethod) => {
|
|
413
|
+
const guide: SetupGuideContent = guideFor(method);
|
|
414
|
+
const markdown: string = getSetupGuideMarkdown(guide);
|
|
415
|
+
|
|
416
|
+
test("is three steps after the key: token, install, verify", () => {
|
|
417
|
+
expect(
|
|
418
|
+
guide.steps.map((step: SetupGuideStep): string => {
|
|
419
|
+
return step.title;
|
|
420
|
+
}),
|
|
421
|
+
).toEqual([
|
|
422
|
+
"Create a read-only API token",
|
|
423
|
+
"Install the agent",
|
|
424
|
+
"Verify the installation",
|
|
425
|
+
]);
|
|
426
|
+
});
|
|
427
|
+
|
|
428
|
+
test("keeps the default key step, which shows the OneUptime URL", () => {
|
|
429
|
+
expect(guide.keyStep).toBeUndefined();
|
|
430
|
+
expect(guide.intro).toBeUndefined();
|
|
431
|
+
});
|
|
432
|
+
|
|
433
|
+
test("lists what must be in place first", () => {
|
|
434
|
+
const prerequisites: string = (guide.prerequisites || []).join("\n");
|
|
435
|
+
expect(prerequisites).toContain("Docker Engine 20.10+");
|
|
436
|
+
expect(prerequisites).toContain("Docker Compose v2");
|
|
437
|
+
expect(prerequisites).toContain("port 8006");
|
|
438
|
+
expect(prerequisites).toContain("outside the cluster");
|
|
439
|
+
});
|
|
440
|
+
|
|
441
|
+
test("the token step offers the shell and the web UI as tabs", () => {
|
|
442
|
+
const token: SetupGuideStep = stepTitled(
|
|
443
|
+
guide,
|
|
444
|
+
"Create a read-only API token",
|
|
445
|
+
);
|
|
446
|
+
expect(
|
|
447
|
+
(token.variants || []).map((variant: SetupGuideStepVariant): string => {
|
|
448
|
+
return variant.label;
|
|
449
|
+
}),
|
|
450
|
+
).toEqual(["Shell", "Proxmox web UI"]);
|
|
451
|
+
});
|
|
452
|
+
|
|
453
|
+
test("the verify step lists the three containers and the ready line", () => {
|
|
454
|
+
const verify: string =
|
|
455
|
+
stepTitled(guide, "Verify the installation").markdown || "";
|
|
456
|
+
expect(verify).toContain("docker compose ps");
|
|
457
|
+
expect(verify).toContain(
|
|
458
|
+
`docker compose logs -f ${PROXMOX_AGENT_CONTAINER}`,
|
|
459
|
+
);
|
|
460
|
+
for (const container of [
|
|
461
|
+
PROXMOX_AGENT_CONTAINER,
|
|
462
|
+
PROXMOX_EXPORTER_CONTAINER,
|
|
463
|
+
PROXMOX_AI_AGENT_CONTAINER,
|
|
464
|
+
]) {
|
|
465
|
+
expect(verify).toContain(`\`${container}\``);
|
|
466
|
+
}
|
|
467
|
+
expect(verify).toContain(
|
|
468
|
+
"Everything is ready. Begin running and processing data.",
|
|
469
|
+
);
|
|
470
|
+
expect(verify.includes(`cd ${PROXMOX_AGENT_INSTALL_DIR}`)).toBe(
|
|
471
|
+
method === "install-script",
|
|
472
|
+
);
|
|
473
|
+
});
|
|
474
|
+
|
|
475
|
+
test("keeps configuration options out of the first-run steps", () => {
|
|
476
|
+
const steps: string = stepsText(guide);
|
|
477
|
+
for (const advanced of [
|
|
478
|
+
"journald",
|
|
479
|
+
"oneuptime.label.",
|
|
480
|
+
"PVE_EXPORTER_URL",
|
|
481
|
+
"docker compose pull",
|
|
482
|
+
"docker compose down",
|
|
483
|
+
"transform/pve-identity",
|
|
484
|
+
]) {
|
|
485
|
+
expect(steps).not.toContain(advanced);
|
|
486
|
+
}
|
|
487
|
+
});
|
|
488
|
+
|
|
489
|
+
test("has Advanced topics for settings, exporter, data, config, logs, labels, AI and upgrades", () => {
|
|
490
|
+
expect(topicTitles(guide.advanced)).toEqual([
|
|
491
|
+
"Environment variables",
|
|
492
|
+
"Use your own prometheus-pve-exporter",
|
|
493
|
+
"What the agent collects",
|
|
494
|
+
"The collector configuration",
|
|
495
|
+
"Ship Proxmox service logs",
|
|
496
|
+
"Tag the cluster with project labels",
|
|
497
|
+
"OneUptime AI agent",
|
|
498
|
+
"Upgrade or uninstall the agent",
|
|
499
|
+
]);
|
|
500
|
+
});
|
|
501
|
+
|
|
502
|
+
test("troubleshooting starts with the diagnostic script and covers the known problems", () => {
|
|
503
|
+
expect(topicTitles(guide.troubleshooting)).toEqual([
|
|
504
|
+
"Run the diagnostic script first",
|
|
505
|
+
'Cluster shows as "Disconnected"',
|
|
506
|
+
"No metrics appearing",
|
|
507
|
+
"The exporter returns 401 or 595 errors",
|
|
508
|
+
"Only node metrics, no guest metrics",
|
|
509
|
+
"Cluster appears under the wrong name",
|
|
510
|
+
]);
|
|
511
|
+
});
|
|
512
|
+
|
|
513
|
+
test("the diagnostic script is the agent's own, run against this install", () => {
|
|
514
|
+
const script: string = topicTitled(
|
|
515
|
+
guide.troubleshooting,
|
|
516
|
+
"Run the diagnostic script first",
|
|
517
|
+
).markdown;
|
|
518
|
+
expect(script).toContain(
|
|
519
|
+
`curl -sSL ${PROXMOX_AGENT_RAW_URL}/troubleshoot.sh -o troubleshoot.sh`,
|
|
520
|
+
);
|
|
521
|
+
if (method === "install-script") {
|
|
522
|
+
expect(script).toContain("\nbash troubleshoot.sh\n");
|
|
523
|
+
} else {
|
|
524
|
+
expect(script).toContain('bash troubleshoot.sh -d "$PWD"');
|
|
525
|
+
}
|
|
526
|
+
});
|
|
527
|
+
|
|
528
|
+
test("checks the bundled exporter from inside its network namespace", () => {
|
|
529
|
+
expect(
|
|
530
|
+
topicTitled(guide.troubleshooting, "No metrics appearing").markdown,
|
|
531
|
+
).toContain(
|
|
532
|
+
codeBlock(
|
|
533
|
+
"bash",
|
|
534
|
+
`docker run --rm --network container:${PROXMOX_EXPORTER_CONTAINER} curlimages/curl -s "http://localhost:9221/pve?target=<PVE_HOST>&cluster=1&node=1" | head`,
|
|
535
|
+
),
|
|
536
|
+
);
|
|
537
|
+
});
|
|
538
|
+
|
|
539
|
+
test("the environment table carries the reader's URL", () => {
|
|
540
|
+
expect(
|
|
541
|
+
topicTitled(guide.advanced, "Environment variables").markdown,
|
|
542
|
+
).toContain(`(e.g. \`${URL}\`)`);
|
|
543
|
+
});
|
|
544
|
+
|
|
545
|
+
test("shows the shipped collector config verbatim", () => {
|
|
546
|
+
expect(
|
|
547
|
+
topicTitled(guide.advanced, "The collector configuration").markdown,
|
|
548
|
+
).toContain(codeBlock("yaml", PROXMOX_AGENT_COLLECTOR_CONFIG));
|
|
549
|
+
});
|
|
550
|
+
|
|
551
|
+
test("commands in the agent's folder run where this method installs it", () => {
|
|
552
|
+
const composeCommand: RegExp = /^docker compose /m;
|
|
553
|
+
for (const block of getSetupGuideCodeBlocks({
|
|
554
|
+
steps: [],
|
|
555
|
+
advanced: guide.advanced,
|
|
556
|
+
})) {
|
|
557
|
+
if (composeCommand.test(block)) {
|
|
558
|
+
expect(block.startsWith(`cd ${PROXMOX_AGENT_INSTALL_DIR}\n`)).toBe(
|
|
559
|
+
method === "install-script",
|
|
560
|
+
);
|
|
561
|
+
}
|
|
562
|
+
}
|
|
563
|
+
if (method === "docker-compose") {
|
|
564
|
+
expect(markdown).not.toContain(PROXMOX_AGENT_INSTALL_DIR);
|
|
565
|
+
}
|
|
566
|
+
});
|
|
567
|
+
|
|
568
|
+
test("the AI agent topic reads with the collector's token and stays read-only", () => {
|
|
569
|
+
const ai: string = topicTitled(
|
|
570
|
+
guide.advanced,
|
|
571
|
+
"OneUptime AI agent",
|
|
572
|
+
).markdown;
|
|
573
|
+
expect(ai).toContain("`PVE_API_TOKEN_ID` / `PVE_API_TOKEN_SECRET`");
|
|
574
|
+
expect(ai).toContain("ONEUPTIME_AI_ALLOW_WRITES=true");
|
|
575
|
+
expect(ai).toContain("ONEUPTIME_AI_PROTECTED_TARGETS");
|
|
576
|
+
expect(ai).toContain(
|
|
577
|
+
`docker exec ${PROXMOX_AI_AGENT_CONTAINER} wget -qO- http://127.0.0.1:3877/status`,
|
|
578
|
+
);
|
|
579
|
+
expect(ai).toContain(
|
|
580
|
+
"(/docs/ai/infrastructure-ai-agents#proxmox-clusters)",
|
|
581
|
+
);
|
|
582
|
+
});
|
|
583
|
+
|
|
584
|
+
test("names the alert templates' identity processor", () => {
|
|
585
|
+
expect(
|
|
586
|
+
topicTitled(guide.advanced, "What the agent collects").markdown,
|
|
587
|
+
).toContain("`pve.scope`");
|
|
588
|
+
});
|
|
589
|
+
|
|
590
|
+
test("shows none of the native push instructions", () => {
|
|
591
|
+
expect(markdown).not.toContain("Metric Server");
|
|
592
|
+
expect(markdown).not.toContain(PROXMOX_NATIVE_PUSH_PATH);
|
|
593
|
+
expect(markdown).not.toContain(PROXMOX_PUSH_HOST_PLACEHOLDER);
|
|
594
|
+
});
|
|
595
|
+
},
|
|
596
|
+
);
|
|
597
|
+
|
|
598
|
+
describe("the read-only API token", () => {
|
|
599
|
+
const token: SetupGuideStep = stepTitled(
|
|
600
|
+
guideFor("install-script"),
|
|
601
|
+
"Create a read-only API token",
|
|
602
|
+
);
|
|
603
|
+
|
|
604
|
+
test("the shell tab creates the user and token and gives both PVEAuditor on /", () => {
|
|
605
|
+
expect(variantTitled(token, "Shell").markdown).toContain(
|
|
606
|
+
codeBlock(
|
|
607
|
+
"bash",
|
|
608
|
+
[
|
|
609
|
+
`pveum user add ${PROXMOX_TOKEN_USER}`,
|
|
610
|
+
`pveum acl modify / --roles PVEAuditor --users ${PROXMOX_TOKEN_USER}`,
|
|
611
|
+
`pveum user token add ${PROXMOX_TOKEN_USER} oneuptime --privsep 1`,
|
|
612
|
+
`pveum acl modify / --roles PVEAuditor --tokens '${PROXMOX_TOKEN_ID}'`,
|
|
613
|
+
].join("\n"),
|
|
614
|
+
),
|
|
615
|
+
);
|
|
616
|
+
expect(PROXMOX_TOKEN_ID).toBe("monitoring@pam!oneuptime");
|
|
617
|
+
});
|
|
618
|
+
|
|
619
|
+
test("both tabs explain why the user and the token need the role", () => {
|
|
620
|
+
for (const label of ["Shell", "Proxmox web UI"]) {
|
|
621
|
+
const text: string = variantTitled(token, label).markdown;
|
|
622
|
+
expect(text).toContain("only gets the permissions its user also has");
|
|
623
|
+
expect(text).toContain("`Permission check failed (/, Sys.Audit)`");
|
|
624
|
+
}
|
|
625
|
+
});
|
|
626
|
+
|
|
627
|
+
test("the web UI tab grants the role to the token and to its user", () => {
|
|
628
|
+
const ui: string = variantTitled(token, "Proxmox web UI").markdown;
|
|
629
|
+
expect(ui).toContain("*Datacenter → Permissions → API Tokens*");
|
|
630
|
+
expect(ui).toContain("make sure **Privilege Separation** is checked");
|
|
631
|
+
expect(ui).toContain("**API Token Permission** for the token");
|
|
632
|
+
expect(ui).toContain("**User Permission** for its user");
|
|
633
|
+
expect(ui).toContain("the secret is shown only once");
|
|
634
|
+
});
|
|
635
|
+
|
|
636
|
+
test("the Docker Compose .env uses the token this step creates", () => {
|
|
637
|
+
expect(envFileOf(guideFor("docker-compose"))).toContain(
|
|
638
|
+
`PVE_API_TOKEN_ID=${PROXMOX_TOKEN_ID}`,
|
|
639
|
+
);
|
|
640
|
+
});
|
|
641
|
+
});
|
|
642
|
+
|
|
643
|
+
describe("the install script", () => {
|
|
644
|
+
test("carries the reader's URL and key on the command line", () => {
|
|
645
|
+
expect(
|
|
646
|
+
getProxmoxInstallScriptCommand({
|
|
647
|
+
oneuptimeUrl: URL,
|
|
648
|
+
apiKey: KEY,
|
|
649
|
+
hasApiKey: true,
|
|
650
|
+
}),
|
|
651
|
+
).toBe(
|
|
652
|
+
[
|
|
653
|
+
"curl -sSL https://raw.githubusercontent.com/OneUptime/oneuptime/master/agents/ProxmoxAgent/install.sh -o install.sh",
|
|
654
|
+
`ONEUPTIME_URL=${URL} ONEUPTIME_TELEMETRY_INGESTION_KEY=${KEY} bash install.sh`,
|
|
655
|
+
].join("\n"),
|
|
656
|
+
);
|
|
657
|
+
expect(installStep(guideFor("install-script"))).toContain(
|
|
658
|
+
codeBlock(
|
|
659
|
+
"bash",
|
|
660
|
+
getProxmoxInstallScriptCommand({
|
|
661
|
+
oneuptimeUrl: URL,
|
|
662
|
+
apiKey: KEY,
|
|
663
|
+
hasApiKey: true,
|
|
664
|
+
}),
|
|
665
|
+
),
|
|
666
|
+
);
|
|
667
|
+
});
|
|
668
|
+
|
|
669
|
+
test("quotes values the shell would otherwise change", () => {
|
|
670
|
+
const command: string = getProxmoxInstallScriptCommand({
|
|
671
|
+
oneuptimeUrl: URL,
|
|
672
|
+
apiKey: "key with space",
|
|
673
|
+
hasApiKey: true,
|
|
674
|
+
});
|
|
675
|
+
expect(command).toContain(
|
|
676
|
+
"ONEUPTIME_TELEMETRY_INGESTION_KEY='key with space'",
|
|
677
|
+
);
|
|
678
|
+
});
|
|
679
|
+
|
|
680
|
+
test("never puts the placeholder key into the script's environment", () => {
|
|
681
|
+
for (const hasApiKey of [false, true]) {
|
|
682
|
+
const command: string = getProxmoxInstallScriptCommand({
|
|
683
|
+
oneuptimeUrl: URL,
|
|
684
|
+
apiKey: SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
685
|
+
hasApiKey: hasApiKey,
|
|
686
|
+
});
|
|
687
|
+
expect(command).not.toContain("ONEUPTIME_");
|
|
688
|
+
expect(command.split("\n")[1]).toBe("bash install.sh");
|
|
689
|
+
}
|
|
690
|
+
});
|
|
691
|
+
|
|
692
|
+
test("leaves the URL to the prompt while the dashboard does not know it", () => {
|
|
693
|
+
const command: string = getProxmoxInstallScriptCommand({
|
|
694
|
+
oneuptimeUrl: SETUP_GUIDE_URL_PLACEHOLDER,
|
|
695
|
+
apiKey: KEY,
|
|
696
|
+
hasApiKey: true,
|
|
697
|
+
});
|
|
698
|
+
expect(command).not.toContain("ONEUPTIME_URL");
|
|
699
|
+
expect(command).toContain(`ONEUPTIME_TELEMETRY_INGESTION_KEY=${KEY}`);
|
|
700
|
+
});
|
|
701
|
+
|
|
702
|
+
test("before a key is picked, says the script asks for the URL and key", () => {
|
|
703
|
+
const guide: SetupGuideContent = noKeyGuideFor("install-script");
|
|
704
|
+
expect(installStep(guide)).toContain(
|
|
705
|
+
"The script asks for your OneUptime URL and ingestion key, both shown in step 1",
|
|
706
|
+
);
|
|
707
|
+
expect(getSetupGuideMarkdown(guide)).not.toContain(
|
|
708
|
+
SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
709
|
+
);
|
|
710
|
+
});
|
|
711
|
+
|
|
712
|
+
test("says what the script asks for, where it installs, and how it runs", () => {
|
|
713
|
+
const install: string = installStep(guideFor("install-script"));
|
|
714
|
+
expect(install).toContain(
|
|
715
|
+
"The command already carries your OneUptime URL and ingestion key.",
|
|
716
|
+
);
|
|
717
|
+
for (const prompt of [
|
|
718
|
+
"**Cluster name**",
|
|
719
|
+
"**Proxmox VE API host**",
|
|
720
|
+
"**Bundled prometheus-pve-exporter**",
|
|
721
|
+
"**API token**",
|
|
722
|
+
"**OneUptime AI agent**",
|
|
723
|
+
]) {
|
|
724
|
+
expect(install).toContain(prompt);
|
|
725
|
+
}
|
|
726
|
+
expect(install).toContain(
|
|
727
|
+
`It installs to \`${PROXMOX_AGENT_INSTALL_DIR}\` and starts everything with Docker Compose.`,
|
|
728
|
+
);
|
|
729
|
+
});
|
|
730
|
+
|
|
731
|
+
test("uses your own exporter by answering the script's question", () => {
|
|
732
|
+
expect(
|
|
733
|
+
topicTitled(
|
|
734
|
+
guideFor("install-script").advanced,
|
|
735
|
+
"Use your own prometheus-pve-exporter",
|
|
736
|
+
).markdown,
|
|
737
|
+
).toContain("**Run the bundled prometheus-pve-exporter?**, answer **n**");
|
|
738
|
+
});
|
|
739
|
+
|
|
740
|
+
test("shows none of the Docker Compose instructions", () => {
|
|
741
|
+
const guide: SetupGuideContent = guideFor("install-script");
|
|
742
|
+
const markdown: string = getSetupGuideMarkdown(guide);
|
|
743
|
+
expect(markdown).not.toContain("curl -fsSLO");
|
|
744
|
+
expect(markdown).not.toContain("mkdir oneuptime-proxmox-agent");
|
|
745
|
+
expect(markdown).not.toContain("COMPOSE_PROFILES=pve-exporter\n");
|
|
746
|
+
expect(() => {
|
|
747
|
+
return envFileOf(guide);
|
|
748
|
+
}).toThrow("The guide has no .env block");
|
|
749
|
+
});
|
|
750
|
+
});
|
|
751
|
+
|
|
752
|
+
describe("the Docker Compose install", () => {
|
|
753
|
+
const guide: SetupGuideContent = guideFor("docker-compose");
|
|
754
|
+
const install: string = installStep(guide);
|
|
755
|
+
|
|
756
|
+
test("downloads the two files, writes .env, then starts the agent", () => {
|
|
757
|
+
const download: number = install.indexOf(
|
|
758
|
+
`curl -fsSLO ${PROXMOX_AGENT_RAW_URL}/docker-compose.yml`,
|
|
759
|
+
);
|
|
760
|
+
const config: number = install.indexOf(
|
|
761
|
+
`curl -fsSLO ${PROXMOX_AGENT_RAW_URL}/otel-collector-config.yaml`,
|
|
762
|
+
);
|
|
763
|
+
const env: number = install.indexOf("ONEUPTIME_URL=");
|
|
764
|
+
const start: number = install.indexOf("docker compose up -d");
|
|
765
|
+
expect(download).toBeGreaterThan(-1);
|
|
766
|
+
expect(config).toBeGreaterThan(download);
|
|
767
|
+
expect(env).toBeGreaterThan(config);
|
|
768
|
+
expect(start).toBeGreaterThan(env);
|
|
769
|
+
expect(install).toContain(
|
|
770
|
+
`[ProxmoxAgent directory](${PROXMOX_AGENT_SOURCE_URL})`,
|
|
771
|
+
);
|
|
772
|
+
expect(install).toContain("`chmod 600 .env`");
|
|
773
|
+
});
|
|
774
|
+
|
|
775
|
+
test("the .env file carries the reader's URL and key and starts the bundled exporter", () => {
|
|
776
|
+
expect(envFileOf(guide)).toBe(
|
|
777
|
+
[
|
|
778
|
+
`ONEUPTIME_URL=${URL}`,
|
|
779
|
+
`ONEUPTIME_TELEMETRY_INGESTION_KEY=${KEY}`,
|
|
780
|
+
`PROXMOX_CLUSTER_NAME=${PROXMOX_EXAMPLE_CLUSTER_NAME}`,
|
|
781
|
+
"PVE_HOST=192.168.1.10",
|
|
782
|
+
`PVE_API_TOKEN_ID=${PROXMOX_TOKEN_ID}`,
|
|
783
|
+
"PVE_API_TOKEN_SECRET=your-token-secret",
|
|
784
|
+
"COMPOSE_PROFILES=pve-exporter",
|
|
785
|
+
].join("\n"),
|
|
786
|
+
);
|
|
787
|
+
});
|
|
788
|
+
|
|
789
|
+
test("shows the placeholder, and where to pick a key, until one is picked", () => {
|
|
790
|
+
const noKey: SetupGuideContent = noKeyGuideFor("docker-compose");
|
|
791
|
+
expect(envFileOf(noKey)).toContain(
|
|
792
|
+
`ONEUPTIME_TELEMETRY_INGESTION_KEY=${SETUP_GUIDE_API_KEY_PLACEHOLDER}`,
|
|
793
|
+
);
|
|
794
|
+
expect(installStep(noKey)).toContain("Pick an ingestion key in step 1");
|
|
795
|
+
expect(install).not.toContain("Pick an ingestion key in step 1");
|
|
796
|
+
expect(getSetupGuideMarkdown(guide)).not.toContain(
|
|
797
|
+
SETUP_GUIDE_API_KEY_PLACEHOLDER,
|
|
798
|
+
);
|
|
799
|
+
});
|
|
800
|
+
|
|
801
|
+
test("points your own exporter at an address the container can reach", () => {
|
|
802
|
+
const own: string = topicTitled(
|
|
803
|
+
guide.advanced,
|
|
804
|
+
"Use your own prometheus-pve-exporter",
|
|
805
|
+
).markdown;
|
|
806
|
+
expect(own).toContain(
|
|
807
|
+
codeBlock("bash", "PVE_EXPORTER_URL=your-exporter-host:9221"),
|
|
808
|
+
);
|
|
809
|
+
expect(own).toContain(
|
|
810
|
+
"`localhost` inside the container is the container itself",
|
|
811
|
+
);
|
|
812
|
+
expect(own).toContain("Keep `PVE_API_TOKEN_ID` and `PVE_API_TOKEN_SECRET`");
|
|
813
|
+
});
|
|
814
|
+
|
|
815
|
+
test("shows none of the install script's instructions", () => {
|
|
816
|
+
const markdown: string = getSetupGuideMarkdown(guide);
|
|
817
|
+
expect(markdown).not.toContain("install.sh");
|
|
818
|
+
expect(markdown).not.toContain("install script");
|
|
819
|
+
expect(markdown).not.toContain(PROXMOX_AGENT_INSTALL_DIR);
|
|
820
|
+
});
|
|
821
|
+
|
|
822
|
+
test("renders what the skipped E2E spec reads off the page", () => {
|
|
823
|
+
/*
|
|
824
|
+
* ProxmoxProduct.spec.ts picks Docker Compose after creating a key, then
|
|
825
|
+
* reads the page for these; the install script (the default) must still
|
|
826
|
+
* carry the key for the spec that reads it back out.
|
|
827
|
+
*/
|
|
828
|
+
const withKey: string = getSetupGuideMarkdown(
|
|
829
|
+
guideFor("docker-compose", {
|
|
830
|
+
oneuptimeUrl: "http://localhost",
|
|
831
|
+
apiKey: UUID_KEY,
|
|
832
|
+
}),
|
|
833
|
+
);
|
|
834
|
+
expect(withKey).toMatch(/ONEUPTIME_URL=http/);
|
|
835
|
+
expect(withKey).toContain("PROXMOX_CLUSTER_NAME=my-proxmox-cluster");
|
|
836
|
+
expect(withKey).toContain("docker compose up -d");
|
|
837
|
+
expect(withKey).not.toContain("<YOUR_API_KEY>");
|
|
838
|
+
expect(
|
|
839
|
+
withKey.match(
|
|
840
|
+
/ONEUPTIME_TELEMETRY_INGESTION_KEY=([0-9a-fA-F-]{36})/,
|
|
841
|
+
)?.[1],
|
|
842
|
+
).toBe(UUID_KEY);
|
|
843
|
+
|
|
844
|
+
const byDefault: string = getSetupGuideMarkdown(
|
|
845
|
+
guideFor(DEFAULT_PROXMOX_CONNECT_METHOD, {
|
|
846
|
+
oneuptimeUrl: "http://localhost",
|
|
847
|
+
apiKey: UUID_KEY,
|
|
848
|
+
}),
|
|
849
|
+
);
|
|
850
|
+
expect(
|
|
851
|
+
byDefault.match(
|
|
852
|
+
/ONEUPTIME_TELEMETRY_INGESTION_KEY=([0-9a-fA-F-]{36})/,
|
|
853
|
+
)?.[1],
|
|
854
|
+
).toBe(UUID_KEY);
|
|
855
|
+
});
|
|
856
|
+
});
|
|
857
|
+
|
|
858
|
+
describe("the native push", () => {
|
|
859
|
+
const guide: SetupGuideContent = guideFor("native-push");
|
|
860
|
+
const markdown: string = getSetupGuideMarkdown(guide);
|
|
861
|
+
|
|
862
|
+
test("is two steps after the key: add the metric server, check the cluster", () => {
|
|
863
|
+
expect(
|
|
864
|
+
guide.steps.map((step: SetupGuideStep): string => {
|
|
865
|
+
return step.title;
|
|
866
|
+
}),
|
|
867
|
+
).toEqual([
|
|
868
|
+
"Add OneUptime as a metric server",
|
|
869
|
+
"Check that the cluster appears",
|
|
870
|
+
]);
|
|
871
|
+
});
|
|
872
|
+
|
|
873
|
+
test("never mentions installing anything", () => {
|
|
874
|
+
for (const install of [
|
|
875
|
+
"install.sh",
|
|
876
|
+
"docker compose",
|
|
877
|
+
"docker-compose",
|
|
878
|
+
"pveum",
|
|
879
|
+
"PVE_API_TOKEN",
|
|
880
|
+
"otel-collector-config",
|
|
881
|
+
"curl ",
|
|
882
|
+
]) {
|
|
883
|
+
expect(markdown).not.toContain(install);
|
|
884
|
+
}
|
|
885
|
+
});
|
|
886
|
+
|
|
887
|
+
test("says what it cannot send before the steps, and not to run both", () => {
|
|
888
|
+
expect(guide.intro).toContain("Proxmox VE 9.0 and later");
|
|
889
|
+
for (const missing of [
|
|
890
|
+
"HA state",
|
|
891
|
+
"start-on-boot",
|
|
892
|
+
"backup coverage",
|
|
893
|
+
"replication",
|
|
894
|
+
]) {
|
|
895
|
+
expect(guide.intro).toContain(missing);
|
|
896
|
+
}
|
|
897
|
+
expect(guide.intro).toContain("running both reports every resource twice");
|
|
898
|
+
});
|
|
899
|
+
|
|
900
|
+
test("the key step shows the OTLP metrics endpoint the push is sent to", () => {
|
|
901
|
+
expect(guide.keyStep).toEqual({
|
|
902
|
+
description:
|
|
903
|
+
"Proxmox VE sends its metrics with this key, in the x-oneuptime-token header. Pick an existing key or create a new one — the settings below update to use it.",
|
|
904
|
+
endpointLabel: "OTLP metrics endpoint",
|
|
905
|
+
endpointValue: `${URL}/otlp/v1/metrics`,
|
|
906
|
+
});
|
|
907
|
+
});
|
|
908
|
+
|
|
909
|
+
test("the metric server fields carry the reader's host and key", () => {
|
|
910
|
+
const step: string =
|
|
911
|
+
stepTitled(guide, "Add OneUptime as a metric server").markdown || "";
|
|
912
|
+
expect(step).toContain("| **Server** | `oneuptime.example.com` |");
|
|
913
|
+
expect(step).toContain("| **Port** | `443` |");
|
|
914
|
+
expect(step).toContain("| **Protocol** | `https` |");
|
|
915
|
+
expect(step).toContain("| **Path** | `/otlp/v1/metrics` |");
|
|
916
|
+
expect(step).toContain(
|
|
917
|
+
codeBlock("json", `{"x-oneuptime-token": "${KEY}"}`),
|
|
918
|
+
);
|
|
919
|
+
expect(
|
|
920
|
+
JSON.parse(
|
|
921
|
+
getSetupGuideCodeBlocks(guide).find((block: string): boolean => {
|
|
922
|
+
return block.includes("x-oneuptime-token");
|
|
923
|
+
})!,
|
|
924
|
+
),
|
|
925
|
+
).toEqual({ "x-oneuptime-token": KEY });
|
|
926
|
+
expect(
|
|
927
|
+
stepTitled(guide, "Add OneUptime as a metric server").description,
|
|
928
|
+
).toContain("Datacenter → Metric Server");
|
|
929
|
+
});
|
|
930
|
+
|
|
931
|
+
test("shows the placeholder, and where to pick a key, until one is picked", () => {
|
|
932
|
+
const step: string =
|
|
933
|
+
stepTitled(
|
|
934
|
+
noKeyGuideFor("native-push"),
|
|
935
|
+
"Add OneUptime as a metric server",
|
|
936
|
+
).markdown || "";
|
|
937
|
+
expect(step).toContain(
|
|
938
|
+
`{"x-oneuptime-token": "${SETUP_GUIDE_API_KEY_PLACEHOLDER}"}`,
|
|
939
|
+
);
|
|
940
|
+
expect(step).toContain("Pick an ingestion key in step 1");
|
|
941
|
+
});
|
|
942
|
+
|
|
943
|
+
test("follows a self-hosted URL's scheme, port and path", () => {
|
|
944
|
+
const step: string =
|
|
945
|
+
stepTitled(
|
|
946
|
+
guideFor("native-push", {
|
|
947
|
+
oneuptimeUrl: "http://oneuptime.local:8080",
|
|
948
|
+
}),
|
|
949
|
+
"Add OneUptime as a metric server",
|
|
950
|
+
).markdown || "";
|
|
951
|
+
expect(step).toContain("| **Server** | `oneuptime.local` |");
|
|
952
|
+
expect(step).toContain("| **Port** | `8080` |");
|
|
953
|
+
expect(step).toContain("| **Protocol** | `http` |");
|
|
954
|
+
});
|
|
955
|
+
|
|
956
|
+
test("has Advanced topics for silent nodes, the cluster name and what is sent", () => {
|
|
957
|
+
expect(topicTitles(guide.advanced)).toEqual([
|
|
958
|
+
"When a node stops reporting",
|
|
959
|
+
"Which name the cluster registers under",
|
|
960
|
+
"What the native push sends",
|
|
961
|
+
]);
|
|
962
|
+
const silent: string = topicTitled(
|
|
963
|
+
guide.advanced,
|
|
964
|
+
"When a node stops reporting",
|
|
965
|
+
).markdown;
|
|
966
|
+
expect(silent).toContain("about 2 minutes after its last report");
|
|
967
|
+
expect(silent).toContain("**Node Offline** fires after about 5 minutes");
|
|
968
|
+
expect(silent).toContain("7–9 minutes");
|
|
969
|
+
expect(silent).toContain("oneuptime.proxmox.inferred=not-reporting");
|
|
970
|
+
});
|
|
971
|
+
|
|
972
|
+
test("the templates it names as agent-only are real Proxmox templates", () => {
|
|
973
|
+
const templates: string = fs.readFileSync(
|
|
974
|
+
path.join(
|
|
975
|
+
REPO_ROOT,
|
|
976
|
+
"packages",
|
|
977
|
+
"Common",
|
|
978
|
+
"Types",
|
|
979
|
+
"Monitor",
|
|
980
|
+
"ProxmoxAlertTemplates.ts",
|
|
981
|
+
),
|
|
982
|
+
"utf8",
|
|
983
|
+
);
|
|
984
|
+
const named: Array<string> = Array.from(
|
|
985
|
+
markdown.matchAll(/\*\*([A-Z][A-Za-z ]+)\*\*/g),
|
|
986
|
+
)
|
|
987
|
+
.map((match: RegExpMatchArray): string => {
|
|
988
|
+
return match[1]!;
|
|
989
|
+
})
|
|
990
|
+
.filter((name: string): boolean => {
|
|
991
|
+
return [
|
|
992
|
+
"Guest Down",
|
|
993
|
+
"HA Resource in Error State",
|
|
994
|
+
"Guest Not Backed Up",
|
|
995
|
+
"Replication Failing",
|
|
996
|
+
"Node Offline",
|
|
997
|
+
"Cluster Quorum at Risk",
|
|
998
|
+
].includes(name);
|
|
999
|
+
});
|
|
1000
|
+
expect(new Set(named).size).toBe(6);
|
|
1001
|
+
for (const name of named) {
|
|
1002
|
+
expect(templates).toContain(`name: "${name}",`);
|
|
1003
|
+
}
|
|
1004
|
+
});
|
|
1005
|
+
|
|
1006
|
+
test("troubleshooting covers a silent cluster, an offline node and agent-only alerts", () => {
|
|
1007
|
+
expect(topicTitles(guide.troubleshooting)).toEqual([
|
|
1008
|
+
'No cluster appears, or it shows as "Disconnected"',
|
|
1009
|
+
'A node shows as "Offline"',
|
|
1010
|
+
"Guest Down, HA or backup alerts never fire",
|
|
1011
|
+
]);
|
|
1012
|
+
expect(
|
|
1013
|
+
topicTitled(guide.troubleshooting, 'A node shows as "Offline"').markdown,
|
|
1014
|
+
).toContain("**Remove Node**");
|
|
1015
|
+
});
|
|
1016
|
+
|
|
1017
|
+
test("a cluster's own tab says how to keep reporting into it", () => {
|
|
1018
|
+
const named: SetupGuideContent = guideFor("native-push", {
|
|
1019
|
+
clusterName: "pve-prod",
|
|
1020
|
+
});
|
|
1021
|
+
expect(
|
|
1022
|
+
topicTitled(named.advanced, "Which name the cluster registers under")
|
|
1023
|
+
.markdown,
|
|
1024
|
+
).toContain("set `proxmox.cluster.name` to `pve-prod`");
|
|
1025
|
+
expect(
|
|
1026
|
+
topicTitled(guide.advanced, "Which name the cluster registers under")
|
|
1027
|
+
.markdown,
|
|
1028
|
+
).not.toContain("This cluster is");
|
|
1029
|
+
});
|
|
1030
|
+
});
|
|
1031
|
+
|
|
1032
|
+
describe("the metric server target", () => {
|
|
1033
|
+
const target: (url: string) => ProxmoxPushTarget = (
|
|
1034
|
+
url: string,
|
|
1035
|
+
): ProxmoxPushTarget => {
|
|
1036
|
+
return getProxmoxPushTarget(url);
|
|
1037
|
+
};
|
|
1038
|
+
|
|
1039
|
+
test("https on the default port", () => {
|
|
1040
|
+
expect(target("https://oneuptime.com")).toEqual({
|
|
1041
|
+
server: "oneuptime.com",
|
|
1042
|
+
port: "443",
|
|
1043
|
+
protocol: "https",
|
|
1044
|
+
path: "/otlp/v1/metrics",
|
|
1045
|
+
});
|
|
1046
|
+
});
|
|
1047
|
+
|
|
1048
|
+
test("http on the default port", () => {
|
|
1049
|
+
expect(target("http://oneuptime.local")).toEqual({
|
|
1050
|
+
server: "oneuptime.local",
|
|
1051
|
+
port: "80",
|
|
1052
|
+
protocol: "http",
|
|
1053
|
+
path: "/otlp/v1/metrics",
|
|
1054
|
+
});
|
|
1055
|
+
});
|
|
1056
|
+
|
|
1057
|
+
test("an explicit port, a path prefix and a trailing slash", () => {
|
|
1058
|
+
expect(target("HTTPS://example.com:8443/oneuptime/")).toEqual({
|
|
1059
|
+
server: "example.com",
|
|
1060
|
+
port: "8443",
|
|
1061
|
+
protocol: "https",
|
|
1062
|
+
path: "/oneuptime/otlp/v1/metrics",
|
|
1063
|
+
});
|
|
1064
|
+
});
|
|
1065
|
+
|
|
1066
|
+
test("a URL the dashboard does not know yet", () => {
|
|
1067
|
+
expect(target(SETUP_GUIDE_URL_PLACEHOLDER)).toEqual({
|
|
1068
|
+
server: PROXMOX_PUSH_HOST_PLACEHOLDER,
|
|
1069
|
+
port: "443",
|
|
1070
|
+
protocol: "https",
|
|
1071
|
+
path: "/otlp/v1/metrics",
|
|
1072
|
+
});
|
|
1073
|
+
});
|
|
1074
|
+
});
|
|
1075
|
+
|
|
1076
|
+
describe("the cluster name", () => {
|
|
1077
|
+
test("a product page suggests a name and says to replace it", () => {
|
|
1078
|
+
expect(installStep(guideFor("docker-compose"))).toContain(
|
|
1079
|
+
`Replace \`${PROXMOX_EXAMPLE_CLUSTER_NAME}\` with a name for this cluster`,
|
|
1080
|
+
);
|
|
1081
|
+
});
|
|
1082
|
+
|
|
1083
|
+
test("a cluster's own tab writes its name into .env and says to keep it", () => {
|
|
1084
|
+
const guide: SetupGuideContent = guideFor("docker-compose", {
|
|
1085
|
+
clusterName: "pve-prod",
|
|
1086
|
+
});
|
|
1087
|
+
expect(envFileOf(guide)).toContain("PROXMOX_CLUSTER_NAME=pve-prod");
|
|
1088
|
+
expect(installStep(guide)).toContain(
|
|
1089
|
+
"This installs the agent for **`pve-prod`**",
|
|
1090
|
+
);
|
|
1091
|
+
expect(
|
|
1092
|
+
topicTitled(guide.troubleshooting, "Cluster appears under the wrong name")
|
|
1093
|
+
.markdown,
|
|
1094
|
+
).toContain("This cluster is **`pve-prod`**.");
|
|
1095
|
+
});
|
|
1096
|
+
|
|
1097
|
+
test("the install script is told to enter a known name exactly", () => {
|
|
1098
|
+
const install: string = installStep(
|
|
1099
|
+
guideFor("install-script", { clusterName: "pve-prod" }),
|
|
1100
|
+
);
|
|
1101
|
+
expect(install).toContain("enter **`pve-prod`** exactly");
|
|
1102
|
+
expect(install).not.toContain("PROXMOX_CLUSTER_NAME=");
|
|
1103
|
+
});
|
|
1104
|
+
|
|
1105
|
+
test("a blank name counts as unknown", () => {
|
|
1106
|
+
expect(
|
|
1107
|
+
envFileOf(guideFor("docker-compose", { clusterName: " " })),
|
|
1108
|
+
).toContain(`PROXMOX_CLUSTER_NAME=${PROXMOX_EXAMPLE_CLUSTER_NAME}`);
|
|
1109
|
+
});
|
|
1110
|
+
});
|
|
1111
|
+
|
|
1112
|
+
describe("drift guards against agents/ProxmoxAgent", () => {
|
|
1113
|
+
test("the collector config is the shipped file, byte for byte", () => {
|
|
1114
|
+
expect(PROXMOX_AGENT_COLLECTOR_CONFIG).toBe(
|
|
1115
|
+
readAgentFile("otel-collector-config.yaml"),
|
|
1116
|
+
);
|
|
1117
|
+
});
|
|
1118
|
+
|
|
1119
|
+
test("the scrape the guide describes is the config's", () => {
|
|
1120
|
+
const config: Record<string, any> = yaml.load(
|
|
1121
|
+
PROXMOX_AGENT_COLLECTOR_CONFIG,
|
|
1122
|
+
) as Record<string, any>;
|
|
1123
|
+
const job: Record<string, any> =
|
|
1124
|
+
config["receivers"]["prometheus"]["config"]["scrape_configs"][0];
|
|
1125
|
+
expect(job["metrics_path"]).toBe("/pve");
|
|
1126
|
+
expect(job["scrape_interval"]).toBe("30s");
|
|
1127
|
+
expect(job["params"]["cluster"]).toEqual(["1"]);
|
|
1128
|
+
expect(job["params"]["node"]).toEqual(["1"]);
|
|
1129
|
+
expect(config["service"]["pipelines"]["metrics"]["processors"]).toContain(
|
|
1130
|
+
"transform/pve-identity",
|
|
1131
|
+
);
|
|
1132
|
+
});
|
|
1133
|
+
|
|
1134
|
+
test("the environment table documents exactly what the collector and the bundled exporter read", () => {
|
|
1135
|
+
const expected: Set<string> = new Set([
|
|
1136
|
+
...Array.from(composeVariables(PROXMOX_AGENT_CONTAINER).keys()),
|
|
1137
|
+
...Array.from(composeVariables("pve-exporter").keys()),
|
|
1138
|
+
// Read by Docker Compose itself, to pick the bundled exporter.
|
|
1139
|
+
"COMPOSE_PROFILES",
|
|
1140
|
+
]);
|
|
1141
|
+
for (const method of AGENT_METHODS) {
|
|
1142
|
+
expect(Array.from(envTableRows(guideFor(method)).keys()).sort()).toEqual(
|
|
1143
|
+
Array.from(expected).sort(),
|
|
1144
|
+
);
|
|
1145
|
+
}
|
|
1146
|
+
});
|
|
1147
|
+
|
|
1148
|
+
test("the defaults the table gives are the compose file's", () => {
|
|
1149
|
+
const variables: Map<string, string | null> = new Map([
|
|
1150
|
+
...Array.from(composeVariables(PROXMOX_AGENT_CONTAINER)),
|
|
1151
|
+
...Array.from(composeVariables("pve-exporter")),
|
|
1152
|
+
]);
|
|
1153
|
+
const rows: Map<string, { required: string; description: string }> =
|
|
1154
|
+
envTableRows(guideFor("docker-compose"));
|
|
1155
|
+
let checked: number = 0;
|
|
1156
|
+
for (const [name, row] of rows) {
|
|
1157
|
+
const stated: RegExpMatchArray | null =
|
|
1158
|
+
row.description.match(/\(default: `([^`]+)`/) ||
|
|
1159
|
+
row.description.match(/Defaults to the bundled exporter \(`([^`]+)`\)/);
|
|
1160
|
+
if (stated) {
|
|
1161
|
+
expect({ name, default: variables.get(name) }).toEqual({
|
|
1162
|
+
name,
|
|
1163
|
+
default: stated[1],
|
|
1164
|
+
});
|
|
1165
|
+
checked++;
|
|
1166
|
+
}
|
|
1167
|
+
}
|
|
1168
|
+
expect(checked).toBe(3);
|
|
1169
|
+
});
|
|
1170
|
+
|
|
1171
|
+
test("the .env block sets only variables the agent reads", () => {
|
|
1172
|
+
const readable: Set<string> = new Set([
|
|
1173
|
+
...Array.from(composeVariables(PROXMOX_AGENT_CONTAINER).keys()),
|
|
1174
|
+
...Array.from(composeVariables("pve-exporter").keys()),
|
|
1175
|
+
"COMPOSE_PROFILES",
|
|
1176
|
+
]);
|
|
1177
|
+
const names: Array<string> = envFileOf(guideFor("docker-compose"))
|
|
1178
|
+
.split("\n")
|
|
1179
|
+
.map((line: string): string => {
|
|
1180
|
+
return line.split("=")[0]!;
|
|
1181
|
+
});
|
|
1182
|
+
expect(names.length).toBe(7);
|
|
1183
|
+
for (const name of names) {
|
|
1184
|
+
expect(readable.has(name)).toBe(true);
|
|
1185
|
+
}
|
|
1186
|
+
});
|
|
1187
|
+
|
|
1188
|
+
test("the bundled exporter is a compose profile and takes the token id as copied", () => {
|
|
1189
|
+
const compose: Record<string, any> = composeFile();
|
|
1190
|
+
expect(compose["services"]["pve-exporter"]["profiles"]).toEqual([
|
|
1191
|
+
"pve-exporter",
|
|
1192
|
+
]);
|
|
1193
|
+
expect(compose["services"]["pve-exporter"]["container_name"]).toBe(
|
|
1194
|
+
PROXMOX_EXPORTER_CONTAINER,
|
|
1195
|
+
);
|
|
1196
|
+
// It splits user@realm!tokenname itself, so .env holds the id whole.
|
|
1197
|
+
expect(readAgentFile("docker-compose.yml")).toContain(
|
|
1198
|
+
'PVE_USER="$${PVE_API_TOKEN_ID%%!*}" PVE_TOKEN_NAME="$${PVE_API_TOKEN_ID##*!}"',
|
|
1199
|
+
);
|
|
1200
|
+
});
|
|
1201
|
+
|
|
1202
|
+
test("the AI agent variables the guide names are the AI agent's", () => {
|
|
1203
|
+
const aiVariables: Map<string, string | null> = composeVariables(
|
|
1204
|
+
PROXMOX_AI_AGENT_CONTAINER,
|
|
1205
|
+
);
|
|
1206
|
+
const ai: string = topicTitled(
|
|
1207
|
+
guideFor("docker-compose").advanced,
|
|
1208
|
+
"OneUptime AI agent",
|
|
1209
|
+
).markdown;
|
|
1210
|
+
const named: Array<string> = Array.from(
|
|
1211
|
+
ai.matchAll(/`([A-Z][A-Z0-9_]+)(?:=[^`]*)?`/g),
|
|
1212
|
+
).map((match: RegExpMatchArray): string => {
|
|
1213
|
+
return match[1]!;
|
|
1214
|
+
});
|
|
1215
|
+
expect(named.length).toBeGreaterThan(4);
|
|
1216
|
+
for (const name of named) {
|
|
1217
|
+
expect({ name, read: aiVariables.has(name) }).toEqual({
|
|
1218
|
+
name,
|
|
1219
|
+
read: true,
|
|
1220
|
+
});
|
|
1221
|
+
}
|
|
1222
|
+
});
|
|
1223
|
+
|
|
1224
|
+
test("the install script writes every required variable to .env", () => {
|
|
1225
|
+
const script: string = readAgentFile("install.sh");
|
|
1226
|
+
const rows: Map<string, { required: string; description: string }> =
|
|
1227
|
+
envTableRows(guideFor("install-script"));
|
|
1228
|
+
for (const [name, row] of rows) {
|
|
1229
|
+
if (row.required === "Yes") {
|
|
1230
|
+
expect(script).toMatch(new RegExp(`^${name}=\\$${name}$`, "m"));
|
|
1231
|
+
}
|
|
1232
|
+
}
|
|
1233
|
+
});
|
|
1234
|
+
|
|
1235
|
+
test("the install script honours a preset URL and key, which prefilling relies on", () => {
|
|
1236
|
+
const script: string = readAgentFile("install.sh");
|
|
1237
|
+
for (const name of ["ONEUPTIME_URL", "ONEUPTIME_TELEMETRY_INGESTION_KEY"]) {
|
|
1238
|
+
expect(script).toMatch(
|
|
1239
|
+
new RegExp(`if \\[ -z "\\$${name}" \\]; then\\s*\\n\\s*read -rp`),
|
|
1240
|
+
);
|
|
1241
|
+
}
|
|
1242
|
+
});
|
|
1243
|
+
|
|
1244
|
+
test("the install script installs where the guide says and asks what it says", () => {
|
|
1245
|
+
const script: string = readAgentFile("install.sh");
|
|
1246
|
+
expect(script).toContain(
|
|
1247
|
+
`INSTALL_DIR="\${INSTALL_DIR:-${PROXMOX_AGENT_INSTALL_DIR}}"`,
|
|
1248
|
+
);
|
|
1249
|
+
expect(script).toContain(`REPO_BASE="${PROXMOX_AGENT_RAW_URL}"`);
|
|
1250
|
+
expect(script).toContain("Run the bundled prometheus-pve-exporter? [Y/n]");
|
|
1251
|
+
expect(script).toContain('PVE_EXPORTER_URL="pve-exporter:9221"');
|
|
1252
|
+
expect(script).toContain("Proxmox VE API host");
|
|
1253
|
+
expect(script).toContain("Also let it apply fixes");
|
|
1254
|
+
});
|
|
1255
|
+
|
|
1256
|
+
test("every file the guide downloads exists in the agent's directory", () => {
|
|
1257
|
+
const files: Set<string> = new Set();
|
|
1258
|
+
for (const method of METHOD_KEYS) {
|
|
1259
|
+
const markdown: string = getSetupGuideMarkdown(guideFor(method));
|
|
1260
|
+
for (const match of markdown.matchAll(
|
|
1261
|
+
/https:\/\/raw\.githubusercontent\.com\/OneUptime\/oneuptime\/master\/agents\/([A-Za-z]+)\/([A-Za-z0-9._-]+)/g,
|
|
1262
|
+
)) {
|
|
1263
|
+
expect(match[1]).toBe("ProxmoxAgent");
|
|
1264
|
+
files.add(match[2]!);
|
|
1265
|
+
}
|
|
1266
|
+
}
|
|
1267
|
+
expect(Array.from(files).sort()).toEqual([
|
|
1268
|
+
"docker-compose.yml",
|
|
1269
|
+
"install.sh",
|
|
1270
|
+
"otel-collector-config.yaml",
|
|
1271
|
+
"troubleshoot.sh",
|
|
1272
|
+
]);
|
|
1273
|
+
for (const file of files) {
|
|
1274
|
+
expect(fs.existsSync(path.join(AGENT_DIR, file))).toBe(true);
|
|
1275
|
+
}
|
|
1276
|
+
});
|
|
1277
|
+
|
|
1278
|
+
test("the containers the guide names are the compose file's", () => {
|
|
1279
|
+
const containers: Array<string> = Object.values(
|
|
1280
|
+
composeFile()["services"] as Record<string, Record<string, string>>,
|
|
1281
|
+
).map((service: Record<string, string>): string => {
|
|
1282
|
+
return service["container_name"]!;
|
|
1283
|
+
});
|
|
1284
|
+
expect(containers.sort()).toEqual(
|
|
1285
|
+
[
|
|
1286
|
+
PROXMOX_AGENT_CONTAINER,
|
|
1287
|
+
PROXMOX_EXPORTER_CONTAINER,
|
|
1288
|
+
PROXMOX_AI_AGENT_CONTAINER,
|
|
1289
|
+
].sort(),
|
|
1290
|
+
);
|
|
1291
|
+
});
|
|
1292
|
+
|
|
1293
|
+
test("the lines the service-logs topic uncomments are in the shipped files", () => {
|
|
1294
|
+
const compose: string = readAgentFile("docker-compose.yml");
|
|
1295
|
+
expect(compose).toContain("# - /var/log/journal:/var/log/journal:ro");
|
|
1296
|
+
expect(compose).toContain("# - /etc/machine-id:/etc/machine-id:ro");
|
|
1297
|
+
expect(PROXMOX_AGENT_COLLECTOR_CONFIG).toContain(" # journald:\n");
|
|
1298
|
+
expect(PROXMOX_AGENT_COLLECTOR_CONFIG).toContain(" # logs:\n");
|
|
1299
|
+
for (const unit of [
|
|
1300
|
+
"pveproxy",
|
|
1301
|
+
"pvedaemon",
|
|
1302
|
+
"pve-firewall",
|
|
1303
|
+
"pve-ha-crm",
|
|
1304
|
+
"pve-ha-lrm",
|
|
1305
|
+
"pvescheduler",
|
|
1306
|
+
"pvestatd",
|
|
1307
|
+
"qmeventd",
|
|
1308
|
+
]) {
|
|
1309
|
+
expect(PROXMOX_AGENT_COLLECTOR_CONFIG).toContain(` # - ${unit}\n`);
|
|
1310
|
+
}
|
|
1311
|
+
});
|
|
1312
|
+
|
|
1313
|
+
test("the diagnostic script takes -d and defaults to the install directory", () => {
|
|
1314
|
+
const script: string = readAgentFile("troubleshoot.sh");
|
|
1315
|
+
expect(script).toContain('-d|--dir) DIR="${2:-}"; shift 2 ;;');
|
|
1316
|
+
expect(script).toContain(`DIR="${PROXMOX_AGENT_INSTALL_DIR}"`);
|
|
1317
|
+
});
|
|
1318
|
+
});
|