@oneuptime/common 8.0.5239 → 8.0.5285
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/Index.ts +4 -2
- package/Models/DatabaseModels/OnCallDutyPolicyUserOverride.ts +5 -3
- package/Models/DatabaseModels/Project.ts +4 -2
- package/Models/DatabaseModels/ProjectSmtpConfig.ts +4 -2
- package/Models/DatabaseModels/StatusPageDomain.ts +6 -4
- package/Models/DatabaseModels/User.ts +0 -46
- package/Models/DatabaseModels/{UserTwoFactorAuth.ts → UserTotpAuth.ts} +16 -16
- package/Models/DatabaseModels/UserWebAuthn.ts +244 -0
- package/Models/DatabaseModels/WorkspaceProjectAuthToken.ts +21 -0
- package/Server/API/BaseAPI.ts +4 -2
- package/Server/API/GlobalConfigAPI.ts +16 -12
- package/Server/API/MicrosoftTeamsAPI.ts +1240 -0
- package/Server/API/ProjectAPI.ts +4 -2
- package/Server/API/ResellerPlanAPI.ts +4 -2
- package/Server/API/SlackAPI.ts +54 -48
- package/Server/API/StatusPageAPI.ts +5 -3
- package/Server/API/UserOnCallLogTimelineAPI.ts +5 -3
- package/Server/API/{UserTwoFactorAuthAPI.ts → UserTotpAuthAPI.ts} +20 -20
- package/Server/API/UserWebAuthnAPI.ts +103 -0
- package/Server/EnvironmentConfig.ts +6 -0
- package/Server/Images/MicrosoftTeams/color.png +0 -0
- package/Server/Images/MicrosoftTeams/outline.png +0 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1753131488925-AddEnableCustomSubscriberEmailNotificationFooterText.ts +4 -2
- package/Server/Infrastructure/Postgres/SchemaMigrations/1759175457008-MigrationName.ts +27 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1759232954703-MigrationName.ts +25 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/1759234532998-MigrationName.ts +15 -0
- package/Server/Infrastructure/Postgres/SchemaMigrations/Index.ts +6 -0
- package/Server/Infrastructure/Queue.ts +4 -2
- package/Server/Infrastructure/SocketIO.ts +4 -2
- package/Server/Middleware/ProjectAuthorization.ts +5 -3
- package/Server/Middleware/SlackAuthorization.ts +2 -2
- package/Server/Middleware/TelemetryIngest.ts +12 -6
- package/Server/Services/AlertStateTimelineService.ts +34 -18
- package/Server/Services/BillingInvoiceService.ts +8 -4
- package/Server/Services/BillingService.ts +13 -9
- package/Server/Services/DatabaseService.ts +42 -30
- package/Server/Services/IncidentService.ts +5 -3
- package/Server/Services/IncidentStateTimelineService.ts +34 -18
- package/Server/Services/Index.ts +4 -2
- package/Server/Services/MonitorStatusTimelineService.ts +34 -18
- package/Server/Services/OnCallDutyPolicyScheduleService.ts +4 -2
- package/Server/Services/ProjectService.ts +6 -4
- package/Server/Services/ScheduledMaintenanceStateTimelineService.ts +26 -14
- package/Server/Services/StatusPageService.ts +4 -2
- package/Server/Services/UserService.ts +21 -5
- package/Server/Services/{UserTwoFactorAuthService.ts → UserTotpAuthService.ts} +26 -7
- package/Server/Services/UserWebAuthnService.ts +419 -0
- package/Server/Services/WorkspaceNotificationRuleService.ts +257 -77
- package/Server/Services/WorkspaceProjectAuthTokenService.ts +2 -2
- package/Server/Types/AnalyticsDatabase/ModelPermission.ts +9 -5
- package/Server/Types/Database/Permissions/BasePermission.ts +4 -2
- package/Server/Types/Database/Permissions/TenantPermission.ts +5 -3
- package/Server/Types/Database/QueryHelper.ts +4 -2
- package/Server/Types/Markdown.ts +6 -4
- package/Server/Types/Workflow/ComponentCode.ts +4 -2
- package/Server/Types/Workflow/Components/Conditions/IfElse.ts +5 -3
- package/Server/Types/Workflow/Components/JavaScript.ts +5 -3
- package/Server/Types/Workflow/TriggerCode.ts +4 -2
- package/Server/Utils/AnalyticsDatabase/Statement.ts +4 -2
- package/Server/Utils/AnalyticsDatabase/StatementGenerator.ts +21 -11
- package/Server/Utils/Browser.ts +6 -4
- package/Server/Utils/CodeRepository/GitHub/GitHub.ts +4 -2
- package/Server/Utils/LocalFile.ts +14 -0
- package/Server/Utils/Monitor/MonitorResource.ts +17 -9
- package/Server/Utils/Realtime.ts +4 -2
- package/Server/Utils/StartServer.ts +1 -1
- package/Server/Utils/Telemetry.ts +15 -9
- package/Server/Utils/{TwoFactorAuth.ts → TotpAuth.ts} +2 -2
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/ActionTypes.ts +75 -16
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/Alert.ts +649 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/Auth.ts +237 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.ts +1321 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/Monitor.ts +155 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/OnCallDutyPolicy.ts +119 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Actions/ScheduledMaintenance.ts +959 -0
- package/Server/Utils/Workspace/MicrosoftTeams/Messages/Alert.ts +16 -14
- package/Server/Utils/Workspace/MicrosoftTeams/Messages/Incident.ts +17 -14
- package/Server/Utils/Workspace/MicrosoftTeams/Messages/ScheduledMaintenance.ts +18 -13
- package/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.ts +2547 -14
- package/Server/Utils/Workspace/Slack/Actions/Alert.ts +4 -2
- package/Server/Utils/Workspace/Slack/Actions/Auth.ts +4 -2
- package/Server/Utils/Workspace/Slack/Actions/Incident.ts +14 -10
- package/Server/Utils/Workspace/Slack/Actions/Monitor.ts +4 -2
- package/Server/Utils/Workspace/Slack/Actions/OnCallDutyPolicy.ts +4 -2
- package/Server/Utils/Workspace/Slack/Actions/ScheduledMaintenance.ts +14 -10
- package/Server/Utils/Workspace/Slack/Messages/Alert.ts +9 -7
- package/Server/Utils/Workspace/Slack/Messages/Incident.ts +9 -7
- package/Server/Utils/Workspace/Slack/Messages/Monitor.ts +9 -7
- package/Server/Utils/Workspace/Slack/Messages/ScheduledMaintenance.ts +9 -7
- package/Server/Utils/Workspace/Slack/Slack.ts +6 -0
- package/Server/Utils/Workspace/Workspace.ts +13 -10
- package/Server/Utils/Workspace/WorkspaceBase.ts +9 -0
- package/Tests/Server/API/BaseAPI.test.ts +64 -52
- package/Tests/Server/Services/BillingService.test.ts +4 -4
- package/Tests/Server/Services/TeamMemberService.test.ts +20 -12
- package/Tests/Server/TestingUtils/Services/BillingServiceHelper.ts +2 -2
- package/Tests/Types/OnCallDutyPolicy/LayerUtil.test.ts +8 -4
- package/Tests/UI/Components/DictionaryOfStrings.test.tsx +4 -2
- package/Tests/UI/Components/FilePicker.test.tsx +2 -2
- package/Tests/Utils/API.test.ts +9 -8
- package/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.ts +5 -3
- package/Types/Html.ts +5 -3
- package/Types/JSONFunctions.ts +5 -5
- package/Types/Metrics/MetricsQuery.ts +6 -4
- package/Types/Monitor/MonitorType.ts +8 -6
- package/Types/OnCallDutyPolicy/Layer.ts +29 -17
- package/Types/Phone.ts +5 -3
- package/Types/Workspace/NotificationRules/BaseNotificationRule.ts +1 -0
- package/Types/Workspace/NotificationRules/CreateChannelNotificationRule.ts +5 -2
- package/Types/Workspace/WorkspaceMessagePayload.ts +1 -0
- package/Types/Workspace/WorkspaceType.ts +13 -0
- package/UI/Components/Charts/Utils/DataPoint.ts +8 -6
- package/UI/Components/Detail/Detail.tsx +4 -1
- package/UI/Components/FilePicker/FilePicker.tsx +1 -1
- package/UI/Components/Forms/Types/Field.ts +4 -2
- package/UI/Components/Image/Image.tsx +1 -1
- package/UI/Components/JSONTable/JSONTable.tsx +4 -2
- package/UI/Components/ModelTable/BaseModelTable.tsx +5 -3
- package/UI/Components/SideMenu/SideMenu.tsx +4 -2
- package/UI/Components/SideMenu/SideMenuItem.tsx +69 -45
- package/UI/Config.ts +3 -0
- package/UI/Utils/API/API.ts +5 -3
- package/UI/Utils/Countries.ts +5 -3
- package/UI/Utils/Login.ts +6 -1
- package/Utils/Base64.ts +13 -0
- package/Utils/Schema/ModelSchema.ts +4 -2
- package/build/dist/Models/DatabaseModels/Index.js +4 -2
- package/build/dist/Models/DatabaseModels/Index.js.map +1 -1
- package/build/dist/Models/DatabaseModels/OnCallDutyPolicyUserOverride.js +5 -3
- package/build/dist/Models/DatabaseModels/OnCallDutyPolicyUserOverride.js.map +1 -1
- package/build/dist/Models/DatabaseModels/Project.js +4 -2
- package/build/dist/Models/DatabaseModels/Project.js.map +1 -1
- package/build/dist/Models/DatabaseModels/ProjectSmtpConfig.js +4 -2
- package/build/dist/Models/DatabaseModels/ProjectSmtpConfig.js.map +1 -1
- package/build/dist/Models/DatabaseModels/StatusPageDomain.js +6 -4
- package/build/dist/Models/DatabaseModels/StatusPageDomain.js.map +1 -1
- package/build/dist/Models/DatabaseModels/User.js +0 -49
- package/build/dist/Models/DatabaseModels/User.js.map +1 -1
- package/build/dist/Models/DatabaseModels/{UserTwoFactorAuth.js → UserTotpAuth.js} +27 -27
- package/build/dist/Models/DatabaseModels/UserTotpAuth.js.map +1 -0
- package/build/dist/Models/DatabaseModels/UserWebAuthn.js +270 -0
- package/build/dist/Models/DatabaseModels/UserWebAuthn.js.map +1 -0
- package/build/dist/Models/DatabaseModels/WorkspaceProjectAuthToken.js.map +1 -1
- package/build/dist/Server/API/BaseAPI.js +4 -2
- package/build/dist/Server/API/BaseAPI.js.map +1 -1
- package/build/dist/Server/API/GlobalConfigAPI.js +16 -12
- package/build/dist/Server/API/GlobalConfigAPI.js.map +1 -1
- package/build/dist/Server/API/MicrosoftTeamsAPI.js +771 -0
- package/build/dist/Server/API/MicrosoftTeamsAPI.js.map +1 -0
- package/build/dist/Server/API/ProjectAPI.js +4 -2
- package/build/dist/Server/API/ProjectAPI.js.map +1 -1
- package/build/dist/Server/API/ResellerPlanAPI.js +4 -2
- package/build/dist/Server/API/ResellerPlanAPI.js.map +1 -1
- package/build/dist/Server/API/SlackAPI.js +53 -47
- package/build/dist/Server/API/SlackAPI.js.map +1 -1
- package/build/dist/Server/API/StatusPageAPI.js +5 -3
- package/build/dist/Server/API/StatusPageAPI.js.map +1 -1
- package/build/dist/Server/API/UserOnCallLogTimelineAPI.js +5 -3
- package/build/dist/Server/API/UserOnCallLogTimelineAPI.js.map +1 -1
- package/build/dist/Server/API/{UserTwoFactorAuthAPI.js → UserTotpAuthAPI.js} +16 -16
- package/build/dist/Server/API/UserTotpAuthAPI.js.map +1 -0
- package/build/dist/Server/API/UserWebAuthnAPI.js +65 -0
- package/build/dist/Server/API/UserWebAuthnAPI.js.map +1 -0
- package/build/dist/Server/EnvironmentConfig.js +3 -0
- package/build/dist/Server/EnvironmentConfig.js.map +1 -1
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1753131488925-AddEnableCustomSubscriberEmailNotificationFooterText.js +4 -2
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1753131488925-AddEnableCustomSubscriberEmailNotificationFooterText.js.map +1 -1
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759175457008-MigrationName.js +16 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759175457008-MigrationName.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759232954703-MigrationName.js +16 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759232954703-MigrationName.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759234532998-MigrationName.js +12 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/1759234532998-MigrationName.js.map +1 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js +6 -0
- package/build/dist/Server/Infrastructure/Postgres/SchemaMigrations/Index.js.map +1 -1
- package/build/dist/Server/Infrastructure/Queue.js +4 -2
- package/build/dist/Server/Infrastructure/Queue.js.map +1 -1
- package/build/dist/Server/Infrastructure/SocketIO.js +4 -2
- package/build/dist/Server/Infrastructure/SocketIO.js.map +1 -1
- package/build/dist/Server/Middleware/ProjectAuthorization.js +5 -3
- package/build/dist/Server/Middleware/ProjectAuthorization.js.map +1 -1
- package/build/dist/Server/Middleware/SlackAuthorization.js.map +1 -1
- package/build/dist/Server/Middleware/TelemetryIngest.js +12 -6
- package/build/dist/Server/Middleware/TelemetryIngest.js.map +1 -1
- package/build/dist/Server/Services/AlertStateTimelineService.js +34 -18
- package/build/dist/Server/Services/AlertStateTimelineService.js.map +1 -1
- package/build/dist/Server/Services/BillingInvoiceService.js +8 -4
- package/build/dist/Server/Services/BillingInvoiceService.js.map +1 -1
- package/build/dist/Server/Services/BillingService.js +13 -9
- package/build/dist/Server/Services/BillingService.js.map +1 -1
- package/build/dist/Server/Services/DatabaseService.js +40 -28
- package/build/dist/Server/Services/DatabaseService.js.map +1 -1
- package/build/dist/Server/Services/IncidentService.js +5 -3
- package/build/dist/Server/Services/IncidentService.js.map +1 -1
- package/build/dist/Server/Services/IncidentStateTimelineService.js +34 -18
- package/build/dist/Server/Services/IncidentStateTimelineService.js.map +1 -1
- package/build/dist/Server/Services/Index.js +4 -2
- package/build/dist/Server/Services/Index.js.map +1 -1
- package/build/dist/Server/Services/MonitorStatusTimelineService.js +34 -18
- package/build/dist/Server/Services/MonitorStatusTimelineService.js.map +1 -1
- package/build/dist/Server/Services/OnCallDutyPolicyScheduleService.js +4 -2
- package/build/dist/Server/Services/OnCallDutyPolicyScheduleService.js.map +1 -1
- package/build/dist/Server/Services/ProjectService.js +6 -4
- package/build/dist/Server/Services/ProjectService.js.map +1 -1
- package/build/dist/Server/Services/ScheduledMaintenanceStateTimelineService.js +26 -14
- package/build/dist/Server/Services/ScheduledMaintenanceStateTimelineService.js.map +1 -1
- package/build/dist/Server/Services/StatusPageService.js +4 -2
- package/build/dist/Server/Services/StatusPageService.js.map +1 -1
- package/build/dist/Server/Services/UserService.js +16 -3
- package/build/dist/Server/Services/UserService.js.map +1 -1
- package/build/dist/Server/Services/{UserTwoFactorAuthService.js → UserTotpAuthService.js} +22 -8
- package/build/dist/Server/Services/UserTotpAuthService.js.map +1 -0
- package/build/dist/Server/Services/UserWebAuthnService.js +365 -0
- package/build/dist/Server/Services/UserWebAuthnService.js.map +1 -0
- package/build/dist/Server/Services/WorkspaceNotificationRuleService.js +142 -51
- package/build/dist/Server/Services/WorkspaceNotificationRuleService.js.map +1 -1
- package/build/dist/Server/Types/AnalyticsDatabase/ModelPermission.js +9 -5
- package/build/dist/Server/Types/AnalyticsDatabase/ModelPermission.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/BasePermission.js +4 -2
- package/build/dist/Server/Types/Database/Permissions/BasePermission.js.map +1 -1
- package/build/dist/Server/Types/Database/Permissions/TenantPermission.js +5 -3
- package/build/dist/Server/Types/Database/Permissions/TenantPermission.js.map +1 -1
- package/build/dist/Server/Types/Database/QueryHelper.js +4 -2
- package/build/dist/Server/Types/Database/QueryHelper.js.map +1 -1
- package/build/dist/Server/Types/Markdown.js +6 -4
- package/build/dist/Server/Types/Markdown.js.map +1 -1
- package/build/dist/Server/Types/Workflow/ComponentCode.js +4 -2
- package/build/dist/Server/Types/Workflow/ComponentCode.js.map +1 -1
- package/build/dist/Server/Types/Workflow/Components/Conditions/IfElse.js +5 -3
- package/build/dist/Server/Types/Workflow/Components/Conditions/IfElse.js.map +1 -1
- package/build/dist/Server/Types/Workflow/Components/JavaScript.js +5 -3
- package/build/dist/Server/Types/Workflow/Components/JavaScript.js.map +1 -1
- package/build/dist/Server/Types/Workflow/TriggerCode.js.map +1 -1
- package/build/dist/Server/Utils/AnalyticsDatabase/Statement.js +4 -2
- package/build/dist/Server/Utils/AnalyticsDatabase/Statement.js.map +1 -1
- package/build/dist/Server/Utils/AnalyticsDatabase/StatementGenerator.js +21 -11
- package/build/dist/Server/Utils/AnalyticsDatabase/StatementGenerator.js.map +1 -1
- package/build/dist/Server/Utils/Browser.js +6 -4
- package/build/dist/Server/Utils/Browser.js.map +1 -1
- package/build/dist/Server/Utils/CodeRepository/GitHub/GitHub.js +4 -2
- package/build/dist/Server/Utils/CodeRepository/GitHub/GitHub.js.map +1 -1
- package/build/dist/Server/Utils/LocalFile.js +16 -0
- package/build/dist/Server/Utils/LocalFile.js.map +1 -1
- package/build/dist/Server/Utils/Monitor/MonitorResource.js +17 -9
- package/build/dist/Server/Utils/Monitor/MonitorResource.js.map +1 -1
- package/build/dist/Server/Utils/Realtime.js +4 -2
- package/build/dist/Server/Utils/Realtime.js.map +1 -1
- package/build/dist/Server/Utils/StartServer.js.map +1 -1
- package/build/dist/Server/Utils/Telemetry.js +6 -4
- package/build/dist/Server/Utils/Telemetry.js.map +1 -1
- package/build/dist/Server/Utils/{TwoFactorAuth.js → TotpAuth.js} +8 -8
- package/build/dist/Server/Utils/TotpAuth.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/ActionTypes.js +86 -36
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/ActionTypes.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Alert.js +531 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Alert.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Auth.js +206 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Auth.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.js +1102 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Incident.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Monitor.js +136 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/Monitor.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/OnCallDutyPolicy.js +107 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/OnCallDutyPolicy.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/ScheduledMaintenance.js +795 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Actions/ScheduledMaintenance.js.map +1 -0
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/Alert.js +16 -14
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/Alert.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/Incident.js +16 -14
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/Incident.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/ScheduledMaintenance.js +15 -13
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/Messages/ScheduledMaintenance.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.js +1982 -13
- package/build/dist/Server/Utils/Workspace/MicrosoftTeams/MicrosoftTeams.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Alert.js +4 -2
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Alert.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Auth.js +4 -2
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Auth.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Incident.js +14 -10
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Incident.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Monitor.js +4 -2
- package/build/dist/Server/Utils/Workspace/Slack/Actions/Monitor.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/OnCallDutyPolicy.js +4 -2
- package/build/dist/Server/Utils/Workspace/Slack/Actions/OnCallDutyPolicy.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Actions/ScheduledMaintenance.js +14 -10
- package/build/dist/Server/Utils/Workspace/Slack/Actions/ScheduledMaintenance.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Alert.js +9 -7
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Alert.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Incident.js +9 -7
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Incident.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Monitor.js +9 -7
- package/build/dist/Server/Utils/Workspace/Slack/Messages/Monitor.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Messages/ScheduledMaintenance.js +9 -7
- package/build/dist/Server/Utils/Workspace/Slack/Messages/ScheduledMaintenance.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Slack/Slack.js +5 -0
- package/build/dist/Server/Utils/Workspace/Slack/Slack.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/Workspace.js +12 -10
- package/build/dist/Server/Utils/Workspace/Workspace.js.map +1 -1
- package/build/dist/Server/Utils/Workspace/WorkspaceBase.js.map +1 -1
- package/build/dist/Tests/Server/API/BaseAPI.test.js +59 -47
- package/build/dist/Tests/Server/API/BaseAPI.test.js.map +1 -1
- package/build/dist/Tests/Server/Services/BillingService.test.js +4 -4
- package/build/dist/Tests/Server/Services/BillingService.test.js.map +1 -1
- package/build/dist/Tests/Server/Services/TeamMemberService.test.js +20 -12
- package/build/dist/Tests/Server/Services/TeamMemberService.test.js.map +1 -1
- package/build/dist/Tests/Server/TestingUtils/Services/BillingServiceHelper.js +2 -2
- package/build/dist/Tests/Server/TestingUtils/Services/BillingServiceHelper.js.map +1 -1
- package/build/dist/Tests/Types/OnCallDutyPolicy/LayerUtil.test.js +8 -4
- package/build/dist/Tests/Types/OnCallDutyPolicy/LayerUtil.test.js.map +1 -1
- package/build/dist/Tests/UI/Components/DictionaryOfStrings.test.js +4 -2
- package/build/dist/Tests/UI/Components/DictionaryOfStrings.test.js.map +1 -1
- package/build/dist/Tests/UI/Components/FilePicker.test.js +2 -2
- package/build/dist/Tests/UI/Components/FilePicker.test.js.map +1 -1
- package/build/dist/Tests/Utils/API.test.js +8 -7
- package/build/dist/Tests/Utils/API.test.js.map +1 -1
- package/build/dist/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.js +5 -3
- package/build/dist/Types/BaseDatabase/DatabaseCommonInteractionPropsUtil.js.map +1 -1
- package/build/dist/Types/Html.js +5 -3
- package/build/dist/Types/Html.js.map +1 -1
- package/build/dist/Types/JSONFunctions.js +5 -5
- package/build/dist/Types/JSONFunctions.js.map +1 -1
- package/build/dist/Types/Monitor/MonitorType.js +8 -6
- package/build/dist/Types/Monitor/MonitorType.js.map +1 -1
- package/build/dist/Types/OnCallDutyPolicy/Layer.js +29 -17
- package/build/dist/Types/OnCallDutyPolicy/Layer.js.map +1 -1
- package/build/dist/Types/Phone.js +5 -3
- package/build/dist/Types/Phone.js.map +1 -1
- package/build/dist/Types/Workspace/WorkspaceType.js +9 -0
- package/build/dist/Types/Workspace/WorkspaceType.js.map +1 -1
- package/build/dist/UI/Components/Charts/Utils/DataPoint.js +8 -6
- package/build/dist/UI/Components/Charts/Utils/DataPoint.js.map +1 -1
- package/build/dist/UI/Components/Detail/Detail.js +4 -1
- package/build/dist/UI/Components/Detail/Detail.js.map +1 -1
- package/build/dist/UI/Components/FilePicker/FilePicker.js +1 -1
- package/build/dist/UI/Components/FilePicker/FilePicker.js.map +1 -1
- package/build/dist/UI/Components/Image/Image.js +1 -1
- package/build/dist/UI/Components/Image/Image.js.map +1 -1
- package/build/dist/UI/Components/JSONTable/JSONTable.js.map +1 -1
- package/build/dist/UI/Components/ModelTable/BaseModelTable.js.map +1 -1
- package/build/dist/UI/Components/SideMenu/SideMenu.js +4 -2
- package/build/dist/UI/Components/SideMenu/SideMenu.js.map +1 -1
- package/build/dist/UI/Components/SideMenu/SideMenuItem.js +62 -38
- package/build/dist/UI/Components/SideMenu/SideMenuItem.js.map +1 -1
- package/build/dist/UI/Config.js +1 -0
- package/build/dist/UI/Config.js.map +1 -1
- package/build/dist/UI/Utils/API/API.js +5 -3
- package/build/dist/UI/Utils/API/API.js.map +1 -1
- package/build/dist/UI/Utils/Countries.js.map +1 -1
- package/build/dist/UI/Utils/Login.js +6 -1
- package/build/dist/UI/Utils/Login.js.map +1 -1
- package/build/dist/Utils/Base64.js +12 -0
- package/build/dist/Utils/Base64.js.map +1 -0
- package/build/dist/Utils/Schema/ModelSchema.js +4 -2
- package/build/dist/Utils/Schema/ModelSchema.js.map +1 -1
- package/package.json +5 -1
- package/build/dist/Models/DatabaseModels/UserTwoFactorAuth.js.map +0 -1
- package/build/dist/Server/API/UserTwoFactorAuthAPI.js.map +0 -1
- package/build/dist/Server/Services/UserTwoFactorAuthService.js.map +0 -1
- package/build/dist/Server/Utils/TwoFactorAuth.js.map +0 -1
|
@@ -29,8 +29,10 @@ import EmailVerificationToken from "../../Models/DatabaseModels/EmailVerificatio
|
|
|
29
29
|
import TeamMember from "../../Models/DatabaseModels/TeamMember";
|
|
30
30
|
import Model from "../../Models/DatabaseModels/User";
|
|
31
31
|
import SlackUtil from "../Utils/Workspace/Slack/Slack";
|
|
32
|
-
import
|
|
33
|
-
import
|
|
32
|
+
import UserTotpAuth from "../../Models/DatabaseModels/UserTotpAuth";
|
|
33
|
+
import UserTotpAuthService from "./UserTotpAuthService";
|
|
34
|
+
import UserWebAuthn from "../../Models/DatabaseModels/UserWebAuthn";
|
|
35
|
+
import UserWebAuthnService from "./UserWebAuthnService";
|
|
34
36
|
import BadDataException from "../../Types/Exception/BadDataException";
|
|
35
37
|
import Name from "../../Types/Name";
|
|
36
38
|
import CaptureSpan from "../Utils/Telemetry/CaptureSpan";
|
|
@@ -157,8 +159,8 @@ export class Service extends DatabaseService<Model> {
|
|
|
157
159
|
});
|
|
158
160
|
|
|
159
161
|
for (const user of users) {
|
|
160
|
-
const
|
|
161
|
-
await
|
|
162
|
+
const totpAuth: UserTotpAuth | null =
|
|
163
|
+
await UserTotpAuthService.findOneBy({
|
|
162
164
|
query: {
|
|
163
165
|
userId: user.id!,
|
|
164
166
|
isVerified: true,
|
|
@@ -171,7 +173,21 @@ export class Service extends DatabaseService<Model> {
|
|
|
171
173
|
},
|
|
172
174
|
});
|
|
173
175
|
|
|
174
|
-
|
|
176
|
+
const webAuthn: UserWebAuthn | null =
|
|
177
|
+
await UserWebAuthnService.findOneBy({
|
|
178
|
+
query: {
|
|
179
|
+
userId: user.id!,
|
|
180
|
+
isVerified: true,
|
|
181
|
+
},
|
|
182
|
+
select: {
|
|
183
|
+
_id: true,
|
|
184
|
+
},
|
|
185
|
+
props: {
|
|
186
|
+
isRoot: true,
|
|
187
|
+
},
|
|
188
|
+
});
|
|
189
|
+
|
|
190
|
+
if (!totpAuth && !webAuthn) {
|
|
175
191
|
throw new BadDataException(
|
|
176
192
|
"Please verify two factor authentication method before you enable two factor authentication.",
|
|
177
193
|
);
|
|
@@ -1,14 +1,16 @@
|
|
|
1
1
|
import CreateBy from "../Types/Database/CreateBy";
|
|
2
2
|
import { OnCreate, OnDelete } from "../Types/Database/Hooks";
|
|
3
3
|
import DatabaseService from "./DatabaseService";
|
|
4
|
-
import Model from "../../Models/DatabaseModels/
|
|
5
|
-
import
|
|
4
|
+
import Model from "../../Models/DatabaseModels/UserTotpAuth";
|
|
5
|
+
import TotpAuth from "../Utils/TotpAuth";
|
|
6
6
|
import UserService from "./UserService";
|
|
7
7
|
import BadDataException from "../../Types/Exception/BadDataException";
|
|
8
8
|
import User from "../../Models/DatabaseModels/User";
|
|
9
9
|
import DeleteBy from "../Types/Database/DeleteBy";
|
|
10
10
|
import LIMIT_MAX from "../../Types/Database/LimitMax";
|
|
11
11
|
import CaptureSpan from "../Utils/Telemetry/CaptureSpan";
|
|
12
|
+
import UserWebAuthn from "../../Models/DatabaseModels/UserWebAuthn";
|
|
13
|
+
import UserWebAuthnService from "./UserWebAuthnService";
|
|
12
14
|
|
|
13
15
|
export class Service extends DatabaseService<Model> {
|
|
14
16
|
public constructor() {
|
|
@@ -43,8 +45,8 @@ export class Service extends DatabaseService<Model> {
|
|
|
43
45
|
throw new BadDataException("User email is required");
|
|
44
46
|
}
|
|
45
47
|
|
|
46
|
-
createBy.data.twoFactorSecret =
|
|
47
|
-
createBy.data.twoFactorOtpUrl =
|
|
48
|
+
createBy.data.twoFactorSecret = TotpAuth.generateSecret();
|
|
49
|
+
createBy.data.twoFactorOtpUrl = TotpAuth.generateUri({
|
|
48
50
|
secret: createBy.data.twoFactorSecret,
|
|
49
51
|
userEmail: user.email,
|
|
50
52
|
});
|
|
@@ -91,9 +93,9 @@ export class Service extends DatabaseService<Model> {
|
|
|
91
93
|
}
|
|
92
94
|
|
|
93
95
|
if (user.enableTwoFactorAuth) {
|
|
94
|
-
// if enabled then check if this is the only verified
|
|
96
|
+
// if enabled then check if this is the only verified 2FA method for this user.
|
|
95
97
|
|
|
96
|
-
const
|
|
98
|
+
const verifiedTotpItems: Array<Model> = await this.findBy({
|
|
97
99
|
query: {
|
|
98
100
|
userId: item.userId!,
|
|
99
101
|
isVerified: true,
|
|
@@ -106,7 +108,24 @@ export class Service extends DatabaseService<Model> {
|
|
|
106
108
|
props: deleteBy.props,
|
|
107
109
|
});
|
|
108
110
|
|
|
109
|
-
|
|
111
|
+
const verifiedWebAuthnItems: Array<UserWebAuthn> =
|
|
112
|
+
await UserWebAuthnService.findBy({
|
|
113
|
+
query: {
|
|
114
|
+
userId: item.userId!,
|
|
115
|
+
isVerified: true,
|
|
116
|
+
},
|
|
117
|
+
select: {
|
|
118
|
+
_id: true,
|
|
119
|
+
},
|
|
120
|
+
limit: LIMIT_MAX,
|
|
121
|
+
skip: 0,
|
|
122
|
+
props: deleteBy.props,
|
|
123
|
+
});
|
|
124
|
+
|
|
125
|
+
const totalVerified2FA: number =
|
|
126
|
+
verifiedTotpItems.length + verifiedWebAuthnItems.length;
|
|
127
|
+
|
|
128
|
+
if (totalVerified2FA === 1) {
|
|
110
129
|
throw new BadDataException(
|
|
111
130
|
"You must have atleast one verified two factor auth. Please disable two factor auth before deleting this item.",
|
|
112
131
|
);
|
|
@@ -0,0 +1,419 @@
|
|
|
1
|
+
import CreateBy from "../Types/Database/CreateBy";
|
|
2
|
+
import { OnCreate, OnDelete } from "../Types/Database/Hooks";
|
|
3
|
+
import DatabaseService from "./DatabaseService";
|
|
4
|
+
import Model from "../../Models/DatabaseModels/UserWebAuthn";
|
|
5
|
+
import UserService from "./UserService";
|
|
6
|
+
import BadDataException from "../../Types/Exception/BadDataException";
|
|
7
|
+
import User from "../../Models/DatabaseModels/User";
|
|
8
|
+
import DeleteBy from "../Types/Database/DeleteBy";
|
|
9
|
+
import LIMIT_MAX, { LIMIT_PER_PROJECT } from "../../Types/Database/LimitMax";
|
|
10
|
+
import CaptureSpan from "../Utils/Telemetry/CaptureSpan";
|
|
11
|
+
import {
|
|
12
|
+
generateRegistrationOptions,
|
|
13
|
+
verifyRegistrationResponse,
|
|
14
|
+
generateAuthenticationOptions,
|
|
15
|
+
verifyAuthenticationResponse,
|
|
16
|
+
} from "@simplewebauthn/server";
|
|
17
|
+
import { Host, HttpProtocol } from "../EnvironmentConfig";
|
|
18
|
+
import ObjectID from "../../Types/ObjectID";
|
|
19
|
+
import DatabaseCommonInteractionProps from "../../Types/BaseDatabase/DatabaseCommonInteractionProps";
|
|
20
|
+
import UserTotpAuth from "../../Models/DatabaseModels/UserTotpAuth";
|
|
21
|
+
import UserTotpAuthService from "./UserTotpAuthService";
|
|
22
|
+
|
|
23
|
+
export class Service extends DatabaseService<Model> {
|
|
24
|
+
public constructor() {
|
|
25
|
+
super(Model);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
@CaptureSpan()
|
|
29
|
+
public async generateRegistrationOptions(data: {
|
|
30
|
+
userId: ObjectID;
|
|
31
|
+
}): Promise<{ options: any; challenge: string }> {
|
|
32
|
+
const user: User | null = await UserService.findOneById({
|
|
33
|
+
id: data.userId,
|
|
34
|
+
select: {
|
|
35
|
+
email: true,
|
|
36
|
+
name: true,
|
|
37
|
+
},
|
|
38
|
+
props: {
|
|
39
|
+
isRoot: true,
|
|
40
|
+
},
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
if (!user) {
|
|
44
|
+
throw new BadDataException("User not found");
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
if (!user.email) {
|
|
48
|
+
throw new BadDataException("User email not found");
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
// Get existing credentials for this user
|
|
52
|
+
const existingCredentials: Array<Model> = await this.findBy({
|
|
53
|
+
query: {
|
|
54
|
+
userId: data.userId,
|
|
55
|
+
},
|
|
56
|
+
select: {
|
|
57
|
+
credentialId: true,
|
|
58
|
+
},
|
|
59
|
+
limit: LIMIT_PER_PROJECT,
|
|
60
|
+
skip: 0,
|
|
61
|
+
props: {
|
|
62
|
+
isRoot: true,
|
|
63
|
+
},
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
const options: any = await generateRegistrationOptions({
|
|
67
|
+
rpName: "OneUptime",
|
|
68
|
+
rpID: Host.toString(),
|
|
69
|
+
userID: new Uint8Array(Buffer.from(data.userId.toString())),
|
|
70
|
+
userName: user.email.toString(),
|
|
71
|
+
userDisplayName: user.name ? user.name.toString() : user.email.toString(),
|
|
72
|
+
attestationType: "none",
|
|
73
|
+
excludeCredentials: existingCredentials
|
|
74
|
+
.filter((cred: Model) => {
|
|
75
|
+
return cred.credentialId;
|
|
76
|
+
})
|
|
77
|
+
.map((cred: Model) => {
|
|
78
|
+
return {
|
|
79
|
+
id: cred.credentialId!,
|
|
80
|
+
type: "public-key",
|
|
81
|
+
};
|
|
82
|
+
}),
|
|
83
|
+
authenticatorSelection: {
|
|
84
|
+
residentKey: "discouraged",
|
|
85
|
+
userVerification: "preferred",
|
|
86
|
+
},
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
// Convert to JSON serializable format
|
|
90
|
+
options.challenge = Buffer.from(options.challenge).toString("base64url");
|
|
91
|
+
if (options.excludeCredentials) {
|
|
92
|
+
options.excludeCredentials = options.excludeCredentials.map(
|
|
93
|
+
(cred: any) => {
|
|
94
|
+
return {
|
|
95
|
+
...cred,
|
|
96
|
+
id:
|
|
97
|
+
typeof cred.id === "string"
|
|
98
|
+
? cred.id
|
|
99
|
+
: Buffer.from(cred.id).toString("base64url"),
|
|
100
|
+
};
|
|
101
|
+
},
|
|
102
|
+
);
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
return {
|
|
106
|
+
options: options as any,
|
|
107
|
+
challenge: options.challenge,
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
@CaptureSpan()
|
|
112
|
+
public async verifyRegistration(data: {
|
|
113
|
+
challenge: string;
|
|
114
|
+
credential: any;
|
|
115
|
+
name: string;
|
|
116
|
+
props: DatabaseCommonInteractionProps;
|
|
117
|
+
}): Promise<void> {
|
|
118
|
+
const expectedOrigin: string = `${HttpProtocol}${Host.toString()}`;
|
|
119
|
+
|
|
120
|
+
const verification: any = await verifyRegistrationResponse({
|
|
121
|
+
response: data.credential,
|
|
122
|
+
expectedChallenge: data.challenge,
|
|
123
|
+
expectedOrigin: expectedOrigin,
|
|
124
|
+
expectedRPID: Host.toString(),
|
|
125
|
+
});
|
|
126
|
+
|
|
127
|
+
if (!verification.verified) {
|
|
128
|
+
throw new BadDataException("Registration verification failed");
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
const { registrationInfo } = verification;
|
|
132
|
+
|
|
133
|
+
if (!registrationInfo) {
|
|
134
|
+
throw new BadDataException("Registration info not found");
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
if (!data.props.userId) {
|
|
138
|
+
throw new BadDataException("User ID not found in request");
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
// Save the credential
|
|
142
|
+
const userWebAuthn: Model = Model.fromJSON(
|
|
143
|
+
{
|
|
144
|
+
name: data.name,
|
|
145
|
+
credentialId: registrationInfo.credential.id,
|
|
146
|
+
publicKey: Buffer.from(registrationInfo.credential.publicKey).toString(
|
|
147
|
+
"base64",
|
|
148
|
+
),
|
|
149
|
+
counter: "0",
|
|
150
|
+
transports: JSON.stringify([]),
|
|
151
|
+
isVerified: true,
|
|
152
|
+
userId: data.props.userId,
|
|
153
|
+
},
|
|
154
|
+
Model,
|
|
155
|
+
) as Model;
|
|
156
|
+
|
|
157
|
+
await this.create({
|
|
158
|
+
data: userWebAuthn,
|
|
159
|
+
props: data.props,
|
|
160
|
+
});
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
@CaptureSpan()
|
|
164
|
+
public async generateAuthenticationOptions(data: {
|
|
165
|
+
email: string;
|
|
166
|
+
}): Promise<{ options: any; challenge: string; userId: string }> {
|
|
167
|
+
const user: User | null = await UserService.findOneBy({
|
|
168
|
+
query: { email: data.email },
|
|
169
|
+
select: {
|
|
170
|
+
_id: true,
|
|
171
|
+
},
|
|
172
|
+
props: {
|
|
173
|
+
isRoot: true,
|
|
174
|
+
},
|
|
175
|
+
});
|
|
176
|
+
|
|
177
|
+
if (!user) {
|
|
178
|
+
throw new BadDataException("User not found");
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
// Get user's WebAuthn credentials
|
|
182
|
+
const credentials: Array<Model> = await this.findBy({
|
|
183
|
+
query: {
|
|
184
|
+
userId: user.id!,
|
|
185
|
+
isVerified: true,
|
|
186
|
+
},
|
|
187
|
+
select: {
|
|
188
|
+
credentialId: true,
|
|
189
|
+
},
|
|
190
|
+
limit: LIMIT_PER_PROJECT,
|
|
191
|
+
skip: 0,
|
|
192
|
+
props: {
|
|
193
|
+
isRoot: true,
|
|
194
|
+
},
|
|
195
|
+
});
|
|
196
|
+
|
|
197
|
+
if (credentials.length === 0) {
|
|
198
|
+
throw new BadDataException("No WebAuthn credentials found for this user");
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
const options: any = await generateAuthenticationOptions({
|
|
202
|
+
rpID: Host.toString(),
|
|
203
|
+
allowCredentials: credentials.map((cred: Model) => {
|
|
204
|
+
return {
|
|
205
|
+
id: cred.credentialId!,
|
|
206
|
+
type: "public-key",
|
|
207
|
+
};
|
|
208
|
+
}),
|
|
209
|
+
userVerification: "preferred",
|
|
210
|
+
});
|
|
211
|
+
|
|
212
|
+
// Convert to JSON serializable format
|
|
213
|
+
options.challenge = Buffer.from(options.challenge).toString("base64url");
|
|
214
|
+
// allowCredentials id is already base64url string
|
|
215
|
+
|
|
216
|
+
return {
|
|
217
|
+
options: options as any,
|
|
218
|
+
challenge: options.challenge,
|
|
219
|
+
userId: user.id!.toString(),
|
|
220
|
+
};
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
@CaptureSpan()
|
|
224
|
+
public async verifyAuthentication(data: {
|
|
225
|
+
userId: string;
|
|
226
|
+
challenge: string;
|
|
227
|
+
credential: any;
|
|
228
|
+
}): Promise<User> {
|
|
229
|
+
const user: User | null = await UserService.findOneById({
|
|
230
|
+
id: new ObjectID(data.userId),
|
|
231
|
+
select: {
|
|
232
|
+
_id: true,
|
|
233
|
+
email: true,
|
|
234
|
+
},
|
|
235
|
+
props: {
|
|
236
|
+
isRoot: true,
|
|
237
|
+
},
|
|
238
|
+
});
|
|
239
|
+
|
|
240
|
+
if (!user) {
|
|
241
|
+
throw new BadDataException("User not found");
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
// Get the credential from database
|
|
245
|
+
const dbCredential: Model | null = await this.findOneBy({
|
|
246
|
+
query: {
|
|
247
|
+
credentialId: data.credential.id,
|
|
248
|
+
userId: new ObjectID(data.userId),
|
|
249
|
+
isVerified: true,
|
|
250
|
+
},
|
|
251
|
+
select: {
|
|
252
|
+
credentialId: true,
|
|
253
|
+
publicKey: true,
|
|
254
|
+
counter: true,
|
|
255
|
+
_id: true,
|
|
256
|
+
},
|
|
257
|
+
props: {
|
|
258
|
+
isRoot: true,
|
|
259
|
+
},
|
|
260
|
+
});
|
|
261
|
+
|
|
262
|
+
if (!dbCredential) {
|
|
263
|
+
throw new BadDataException("Credential not found");
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
const expectedOrigin: string = `${HttpProtocol}${Host.toString()}`;
|
|
267
|
+
|
|
268
|
+
const verification: any = await verifyAuthenticationResponse({
|
|
269
|
+
response: data.credential,
|
|
270
|
+
expectedChallenge: data.challenge,
|
|
271
|
+
expectedOrigin: expectedOrigin,
|
|
272
|
+
expectedRPID: Host.toString(),
|
|
273
|
+
credential: {
|
|
274
|
+
id: dbCredential.credentialId!,
|
|
275
|
+
publicKey: Buffer.from(dbCredential.publicKey!, "base64"),
|
|
276
|
+
counter: parseInt(dbCredential.counter!),
|
|
277
|
+
} as any,
|
|
278
|
+
});
|
|
279
|
+
|
|
280
|
+
if (!verification.verified) {
|
|
281
|
+
throw new BadDataException("Authentication verification failed");
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
// Update counter
|
|
285
|
+
await this.updateOneById({
|
|
286
|
+
id: dbCredential.id!,
|
|
287
|
+
data: {
|
|
288
|
+
counter: verification.authenticationInfo.newCounter.toString(),
|
|
289
|
+
},
|
|
290
|
+
props: {
|
|
291
|
+
isRoot: true,
|
|
292
|
+
},
|
|
293
|
+
});
|
|
294
|
+
|
|
295
|
+
return user;
|
|
296
|
+
}
|
|
297
|
+
|
|
298
|
+
@CaptureSpan()
|
|
299
|
+
protected override async onBeforeCreate(
|
|
300
|
+
createBy: CreateBy<Model>,
|
|
301
|
+
): Promise<OnCreate<Model>> {
|
|
302
|
+
if (!createBy.props.userId) {
|
|
303
|
+
throw new BadDataException("User id is required");
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
createBy.data.userId = createBy.props.userId;
|
|
307
|
+
|
|
308
|
+
const user: User | null = await UserService.findOneById({
|
|
309
|
+
id: createBy.data.userId,
|
|
310
|
+
props: {
|
|
311
|
+
isRoot: true,
|
|
312
|
+
},
|
|
313
|
+
select: {
|
|
314
|
+
email: true,
|
|
315
|
+
},
|
|
316
|
+
});
|
|
317
|
+
|
|
318
|
+
if (!user) {
|
|
319
|
+
throw new BadDataException("User not found");
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
if (!user.email) {
|
|
323
|
+
throw new BadDataException("User email is required");
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
// by default secuirty keys are always verified. You can't add an unverified security key.
|
|
327
|
+
|
|
328
|
+
createBy.data.isVerified = true;
|
|
329
|
+
|
|
330
|
+
return {
|
|
331
|
+
createBy: createBy,
|
|
332
|
+
carryForward: {},
|
|
333
|
+
};
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
@CaptureSpan()
|
|
337
|
+
protected override async onBeforeDelete(
|
|
338
|
+
deleteBy: DeleteBy<Model>,
|
|
339
|
+
): Promise<OnDelete<Model>> {
|
|
340
|
+
const itemsToBeDeleted: Array<Model> = await this.findBy({
|
|
341
|
+
query: deleteBy.query,
|
|
342
|
+
select: {
|
|
343
|
+
userId: true,
|
|
344
|
+
_id: true,
|
|
345
|
+
isVerified: true,
|
|
346
|
+
},
|
|
347
|
+
limit: LIMIT_MAX,
|
|
348
|
+
skip: 0,
|
|
349
|
+
props: deleteBy.props,
|
|
350
|
+
});
|
|
351
|
+
|
|
352
|
+
for (const item of itemsToBeDeleted) {
|
|
353
|
+
if (item.isVerified) {
|
|
354
|
+
// check if user two auth is enabled.
|
|
355
|
+
|
|
356
|
+
const user: User | null = await UserService.findOneById({
|
|
357
|
+
id: item.userId!,
|
|
358
|
+
props: {
|
|
359
|
+
isRoot: true,
|
|
360
|
+
},
|
|
361
|
+
select: {
|
|
362
|
+
enableTwoFactorAuth: true,
|
|
363
|
+
},
|
|
364
|
+
});
|
|
365
|
+
|
|
366
|
+
if (!user) {
|
|
367
|
+
throw new BadDataException("User not found");
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
if (user.enableTwoFactorAuth) {
|
|
371
|
+
// if enabled then check if this is the only verified 2FA method for this user.
|
|
372
|
+
|
|
373
|
+
const verifiedWebAuthnItems: Array<Model> = await this.findBy({
|
|
374
|
+
query: {
|
|
375
|
+
userId: item.userId!,
|
|
376
|
+
isVerified: true,
|
|
377
|
+
},
|
|
378
|
+
select: {
|
|
379
|
+
_id: true,
|
|
380
|
+
},
|
|
381
|
+
limit: LIMIT_MAX,
|
|
382
|
+
skip: 0,
|
|
383
|
+
props: deleteBy.props,
|
|
384
|
+
});
|
|
385
|
+
|
|
386
|
+
const verifiedTotpItems: Array<UserTotpAuth> =
|
|
387
|
+
await UserTotpAuthService.findBy({
|
|
388
|
+
query: {
|
|
389
|
+
userId: item.userId!,
|
|
390
|
+
isVerified: true,
|
|
391
|
+
},
|
|
392
|
+
select: {
|
|
393
|
+
_id: true,
|
|
394
|
+
},
|
|
395
|
+
limit: LIMIT_MAX,
|
|
396
|
+
skip: 0,
|
|
397
|
+
props: deleteBy.props,
|
|
398
|
+
});
|
|
399
|
+
|
|
400
|
+
const totalVerified2FA: number =
|
|
401
|
+
verifiedWebAuthnItems.length + verifiedTotpItems.length;
|
|
402
|
+
|
|
403
|
+
if (totalVerified2FA === 1) {
|
|
404
|
+
throw new BadDataException(
|
|
405
|
+
"You must have atleast one verified two factor auth. Please disable two factor auth before deleting this item.",
|
|
406
|
+
);
|
|
407
|
+
}
|
|
408
|
+
}
|
|
409
|
+
}
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
return {
|
|
413
|
+
deleteBy: deleteBy,
|
|
414
|
+
carryForward: {},
|
|
415
|
+
};
|
|
416
|
+
}
|
|
417
|
+
}
|
|
418
|
+
|
|
419
|
+
export default new Service();
|