hazo_auth 1.4.2 → 1.6.1
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/README.md +65 -19
- package/SETUP_CHECKLIST.md +779 -0
- package/dist/app/api/hazo_auth/change_password/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/change_password/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/change_password/route.js +98 -0
- package/dist/app/api/hazo_auth/forgot_password/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/forgot_password/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/forgot_password/route.js +78 -0
- package/dist/app/api/hazo_auth/get_auth/route.d.ts +10 -0
- package/dist/app/api/hazo_auth/get_auth/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/get_auth/route.js +63 -0
- package/dist/app/api/hazo_auth/invalidate_cache/route.d.ts +14 -0
- package/dist/app/api/hazo_auth/invalidate_cache/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/invalidate_cache/route.js +96 -0
- package/dist/app/api/hazo_auth/library_photo/[category]/[filename]/route.d.ts +9 -0
- package/dist/app/api/hazo_auth/library_photo/[category]/[filename]/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/library_photo/[category]/[filename]/route.js +82 -0
- package/dist/app/api/hazo_auth/library_photos/route.d.ts +22 -0
- package/dist/app/api/hazo_auth/library_photos/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/library_photos/route.js +80 -0
- package/dist/app/api/hazo_auth/login/route.d.ts +12 -0
- package/dist/app/api/hazo_auth/login/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/login/route.js +140 -0
- package/dist/app/api/hazo_auth/logout/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/logout/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/logout/route.js +71 -0
- package/dist/app/api/hazo_auth/me/route.d.ts +3 -0
- package/dist/app/api/hazo_auth/me/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/me/route.js +34 -0
- package/dist/app/api/hazo_auth/profile_picture/[filename]/route.d.ts +7 -0
- package/dist/app/api/hazo_auth/profile_picture/[filename]/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/profile_picture/[filename]/route.js +43 -0
- package/dist/app/api/hazo_auth/register/route.d.ts +9 -0
- package/dist/app/api/hazo_auth/register/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/register/route.js +80 -0
- package/dist/app/api/hazo_auth/remove_profile_picture/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/remove_profile_picture/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/remove_profile_picture/route.js +64 -0
- package/dist/app/api/hazo_auth/resend_verification/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/resend_verification/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/resend_verification/route.js +79 -0
- package/dist/app/api/hazo_auth/reset_password/route.d.ts +8 -0
- package/dist/app/api/hazo_auth/reset_password/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/reset_password/route.js +76 -0
- package/dist/app/api/hazo_auth/update_user/route.d.ts +9 -0
- package/dist/app/api/hazo_auth/update_user/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/update_user/route.js +95 -0
- package/dist/app/api/hazo_auth/upload_profile_picture/route.d.ts +9 -0
- package/dist/app/api/hazo_auth/upload_profile_picture/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/upload_profile_picture/route.js +204 -0
- package/dist/app/api/hazo_auth/validate_reset_token/route.d.ts +6 -0
- package/dist/app/api/hazo_auth/validate_reset_token/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/validate_reset_token/route.js +58 -0
- package/dist/app/api/hazo_auth/verify_email/route.d.ts +11 -0
- package/dist/app/api/hazo_auth/verify_email/route.d.ts.map +1 -0
- package/dist/app/api/hazo_auth/verify_email/route.js +63 -0
- package/dist/cli/generate.d.ts +7 -0
- package/dist/cli/generate.d.ts.map +1 -0
- package/dist/cli/generate.js +184 -0
- package/dist/cli/index.d.ts +3 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +173 -0
- package/dist/cli/init.d.ts +2 -0
- package/dist/cli/init.d.ts.map +1 -0
- package/dist/cli/init.js +201 -0
- package/dist/cli/validate.d.ts +15 -0
- package/dist/cli/validate.d.ts.map +1 -0
- package/dist/cli/validate.js +509 -0
- package/dist/components/ui/card.d.ts +9 -0
- package/dist/components/ui/card.d.ts.map +1 -0
- package/dist/components/ui/card.js +45 -0
- package/dist/hooks/use-mobile.d.ts.map +1 -1
- package/dist/hooks/use-mobile.js +17 -3
- package/dist/lib/services/profile_picture_service.d.ts +34 -2
- package/dist/lib/services/profile_picture_service.d.ts.map +1 -1
- package/dist/lib/services/profile_picture_service.js +157 -15
- package/dist/page_components/forgot_password.d.ts +19 -0
- package/dist/page_components/forgot_password.d.ts.map +1 -0
- package/dist/page_components/forgot_password.js +36 -0
- package/dist/page_components/index.d.ts +7 -0
- package/dist/page_components/index.d.ts.map +1 -0
- package/dist/page_components/index.js +9 -0
- package/dist/page_components/login.d.ts +26 -0
- package/dist/page_components/login.d.ts.map +1 -0
- package/dist/page_components/login.js +40 -0
- package/dist/page_components/my_settings.d.ts +64 -0
- package/dist/page_components/my_settings.d.ts.map +1 -0
- package/dist/page_components/my_settings.js +67 -0
- package/dist/page_components/register.d.ts +25 -0
- package/dist/page_components/register.d.ts.map +1 -0
- package/dist/page_components/register.js +43 -0
- package/dist/page_components/reset_password.d.ts +25 -0
- package/dist/page_components/reset_password.d.ts.map +1 -0
- package/dist/page_components/reset_password.js +43 -0
- package/dist/page_components/verify_email.d.ts +21 -0
- package/dist/page_components/verify_email.d.ts.map +1 -0
- package/dist/page_components/verify_email.js +36 -0
- package/dist/server/routes/change_password.d.ts +2 -0
- package/dist/server/routes/change_password.d.ts.map +1 -0
- package/dist/server/routes/change_password.js +2 -0
- package/dist/server/routes/forgot_password.d.ts +2 -0
- package/dist/server/routes/forgot_password.d.ts.map +1 -0
- package/dist/server/routes/forgot_password.js +2 -0
- package/dist/server/routes/get_auth.d.ts +2 -0
- package/dist/server/routes/get_auth.d.ts.map +1 -0
- package/dist/server/routes/get_auth.js +2 -0
- package/dist/server/routes/index.d.ts +19 -0
- package/dist/server/routes/index.d.ts.map +1 -0
- package/dist/server/routes/index.js +25 -0
- package/dist/server/routes/invalidate_cache.d.ts +2 -0
- package/dist/server/routes/invalidate_cache.d.ts.map +1 -0
- package/dist/server/routes/invalidate_cache.js +2 -0
- package/dist/server/routes/library_photo.d.ts +2 -0
- package/dist/server/routes/library_photo.d.ts.map +1 -0
- package/dist/server/routes/library_photo.js +3 -0
- package/dist/server/routes/library_photos.d.ts +2 -0
- package/dist/server/routes/library_photos.d.ts.map +1 -0
- package/dist/server/routes/library_photos.js +2 -0
- package/dist/server/routes/login.d.ts +2 -0
- package/dist/server/routes/login.d.ts.map +1 -0
- package/dist/server/routes/login.js +2 -0
- package/dist/server/routes/logout.d.ts +2 -0
- package/dist/server/routes/logout.d.ts.map +1 -0
- package/dist/server/routes/logout.js +2 -0
- package/dist/server/routes/me.d.ts +2 -0
- package/dist/server/routes/me.d.ts.map +1 -0
- package/dist/server/routes/me.js +2 -0
- package/dist/server/routes/profile_picture_filename.d.ts +2 -0
- package/dist/server/routes/profile_picture_filename.d.ts.map +1 -0
- package/dist/server/routes/profile_picture_filename.js +3 -0
- package/dist/server/routes/register.d.ts +2 -0
- package/dist/server/routes/register.d.ts.map +1 -0
- package/dist/server/routes/register.js +2 -0
- package/dist/server/routes/remove_profile_picture.d.ts +2 -0
- package/dist/server/routes/remove_profile_picture.d.ts.map +1 -0
- package/dist/server/routes/remove_profile_picture.js +2 -0
- package/dist/server/routes/resend_verification.d.ts +2 -0
- package/dist/server/routes/resend_verification.d.ts.map +1 -0
- package/dist/server/routes/resend_verification.js +2 -0
- package/dist/server/routes/reset_password.d.ts +2 -0
- package/dist/server/routes/reset_password.d.ts.map +1 -0
- package/dist/server/routes/reset_password.js +2 -0
- package/dist/server/routes/update_user.d.ts +2 -0
- package/dist/server/routes/update_user.d.ts.map +1 -0
- package/dist/server/routes/update_user.js +2 -0
- package/dist/server/routes/upload_profile_picture.d.ts +2 -0
- package/dist/server/routes/upload_profile_picture.d.ts.map +1 -0
- package/dist/server/routes/upload_profile_picture.js +2 -0
- package/dist/server/routes/validate_reset_token.d.ts +2 -0
- package/dist/server/routes/validate_reset_token.d.ts.map +1 -0
- package/dist/server/routes/validate_reset_token.js +2 -0
- package/dist/server/routes/verify_email.d.ts +2 -0
- package/dist/server/routes/verify_email.d.ts.map +1 -0
- package/dist/server/routes/verify_email.js +2 -0
- package/package.json +40 -17
- package/components.json +0 -22
- package/instrumentation.ts +0 -32
- package/migrations/001_add_token_type_to_refresh_tokens.sql +0 -14
- package/migrations/002_add_name_to_hazo_users.sql +0 -7
- package/migrations/003_add_url_on_logon_to_hazo_users.sql +0 -8
- package/next.config.mjs +0 -67
- package/postcss.config.mjs +0 -8
- package/public/file.svg +0 -1
- package/public/globe.svg +0 -1
- package/public/next.svg +0 -1
- package/public/vercel.svg +0 -1
- package/public/window.svg +0 -1
- package/scripts/apply_migration.ts +0 -118
- package/scripts/init_users.ts +0 -378
- package/src/app/api/hazo_auth/auth/upload_profile_picture/route.ts +0 -268
- package/src/app/api/hazo_auth/change_password/route.ts +0 -132
- package/src/app/api/hazo_auth/forgot_password/route.ts +0 -107
- package/src/app/api/hazo_auth/get_auth/route.ts +0 -89
- package/src/app/api/hazo_auth/invalidate_cache/route.ts +0 -139
- package/src/app/api/hazo_auth/library_photos/route.ts +0 -73
- package/src/app/api/hazo_auth/login/route.ts +0 -181
- package/src/app/api/hazo_auth/logout/route.ts +0 -89
- package/src/app/api/hazo_auth/me/route.ts +0 -47
- package/src/app/api/hazo_auth/profile_picture/[filename]/route.ts +0 -67
- package/src/app/api/hazo_auth/register/route.ts +0 -109
- package/src/app/api/hazo_auth/remove_profile_picture/route.ts +0 -86
- package/src/app/api/hazo_auth/resend_verification/route.ts +0 -108
- package/src/app/api/hazo_auth/reset_password/route.ts +0 -107
- package/src/app/api/hazo_auth/update_user/route.ts +0 -126
- package/src/app/api/hazo_auth/upload_profile_picture/route.ts +0 -268
- package/src/app/api/hazo_auth/user_management/permissions/route.ts +0 -367
- package/src/app/api/hazo_auth/user_management/roles/route.ts +0 -442
- package/src/app/api/hazo_auth/user_management/users/roles/route.ts +0 -367
- package/src/app/api/hazo_auth/user_management/users/route.ts +0 -239
- package/src/app/api/hazo_auth/validate_reset_token/route.ts +0 -83
- package/src/app/api/hazo_auth/verify_email/route.ts +0 -88
- package/src/app/api/migrations/apply/route.ts +0 -91
- package/src/app/favicon.ico +0 -0
- package/src/app/fonts/GeistMonoVF.woff +0 -0
- package/src/app/fonts/GeistVF.woff +0 -0
- package/src/app/globals.css +0 -89
- package/src/app/hazo_auth/forgot_password/forgot_password_page_client.tsx +0 -60
- package/src/app/hazo_auth/forgot_password/page.tsx +0 -24
- package/src/app/hazo_auth/login/login_page_client.tsx +0 -86
- package/src/app/hazo_auth/login/page.tsx +0 -38
- package/src/app/hazo_auth/my_settings/my_settings_page_client.tsx +0 -120
- package/src/app/hazo_auth/my_settings/page.tsx +0 -40
- package/src/app/hazo_auth/register/page.tsx +0 -36
- package/src/app/hazo_auth/register/register_page_client.tsx +0 -81
- package/src/app/hazo_auth/reset_password/page.tsx +0 -29
- package/src/app/hazo_auth/reset_password/reset_password_page_client.tsx +0 -81
- package/src/app/hazo_auth/user_management/page.tsx +0 -14
- package/src/app/hazo_auth/user_management/user_management_page_client.tsx +0 -16
- package/src/app/hazo_auth/verify_email/page.tsx +0 -24
- package/src/app/hazo_auth/verify_email/verify_email_page_client.tsx +0 -60
- package/src/app/hazo_connect/api/sqlite/data/route.ts +0 -203
- package/src/app/hazo_connect/api/sqlite/schema/route.ts +0 -45
- package/src/app/hazo_connect/api/sqlite/tables/route.ts +0 -36
- package/src/app/hazo_connect/sqlite_admin/page.tsx +0 -51
- package/src/app/hazo_connect/sqlite_admin/sqlite-admin-client.tsx +0 -984
- package/src/app/layout.tsx +0 -43
- package/src/app/page.tsx +0 -170
- package/src/components/index.ts +0 -7
- package/src/components/layouts/email_verification/config/email_verification_field_config.ts +0 -86
- package/src/components/layouts/email_verification/hooks/use_email_verification.ts +0 -297
- package/src/components/layouts/email_verification/index.tsx +0 -297
- package/src/components/layouts/forgot_password/config/forgot_password_field_config.ts +0 -58
- package/src/components/layouts/forgot_password/hooks/use_forgot_password_form.ts +0 -179
- package/src/components/layouts/forgot_password/index.tsx +0 -168
- package/src/components/layouts/index.ts +0 -26
- package/src/components/layouts/login/config/login_field_config.ts +0 -67
- package/src/components/layouts/login/hooks/use_login_form.ts +0 -286
- package/src/components/layouts/login/index.tsx +0 -252
- package/src/components/layouts/my_settings/components/editable_field.tsx +0 -177
- package/src/components/layouts/my_settings/components/password_change_dialog.tsx +0 -301
- package/src/components/layouts/my_settings/components/profile_picture_dialog.tsx +0 -385
- package/src/components/layouts/my_settings/components/profile_picture_display.tsx +0 -66
- package/src/components/layouts/my_settings/components/profile_picture_gravatar_tab.tsx +0 -143
- package/src/components/layouts/my_settings/components/profile_picture_library_tab.tsx +0 -311
- package/src/components/layouts/my_settings/components/profile_picture_upload_tab.tsx +0 -341
- package/src/components/layouts/my_settings/config/my_settings_field_config.ts +0 -61
- package/src/components/layouts/my_settings/hooks/use_my_settings.ts +0 -458
- package/src/components/layouts/my_settings/index.tsx +0 -351
- package/src/components/layouts/register/config/register_field_config.ts +0 -101
- package/src/components/layouts/register/hooks/use_register_form.ts +0 -275
- package/src/components/layouts/register/index.tsx +0 -226
- package/src/components/layouts/reset_password/config/reset_password_field_config.ts +0 -86
- package/src/components/layouts/reset_password/hooks/use_reset_password_form.ts +0 -276
- package/src/components/layouts/reset_password/index.tsx +0 -294
- package/src/components/layouts/shared/components/already_logged_in_guard.tsx +0 -95
- package/src/components/layouts/shared/components/auth_page_shell.tsx +0 -36
- package/src/components/layouts/shared/components/field_error_message.tsx +0 -29
- package/src/components/layouts/shared/components/form_action_buttons.tsx +0 -64
- package/src/components/layouts/shared/components/form_field_wrapper.tsx +0 -44
- package/src/components/layouts/shared/components/form_header.tsx +0 -36
- package/src/components/layouts/shared/components/logout_button.tsx +0 -76
- package/src/components/layouts/shared/components/password_field.tsx +0 -72
- package/src/components/layouts/shared/components/profile_pic_menu.tsx +0 -321
- package/src/components/layouts/shared/components/profile_pic_menu_wrapper.tsx +0 -40
- package/src/components/layouts/shared/components/sidebar_layout_wrapper.tsx +0 -214
- package/src/components/layouts/shared/components/standalone_layout_wrapper.tsx +0 -53
- package/src/components/layouts/shared/components/two_column_auth_layout.tsx +0 -44
- package/src/components/layouts/shared/components/unauthorized_guard.tsx +0 -78
- package/src/components/layouts/shared/components/visual_panel.tsx +0 -41
- package/src/components/layouts/shared/config/layout_customization.ts +0 -95
- package/src/components/layouts/shared/data/layout_data_client.ts +0 -19
- package/src/components/layouts/shared/hooks/use_auth_status.ts +0 -103
- package/src/components/layouts/shared/hooks/use_hazo_auth.ts +0 -158
- package/src/components/layouts/shared/index.ts +0 -34
- package/src/components/layouts/shared/utils/ip_address.ts +0 -37
- package/src/components/layouts/shared/utils/validation.ts +0 -66
- package/src/components/layouts/user_management/components/roles_matrix.tsx +0 -607
- package/src/components/layouts/user_management/index.tsx +0 -1295
- package/src/components/ui/alert-dialog.tsx +0 -141
- package/src/components/ui/avatar.tsx +0 -50
- package/src/components/ui/button.tsx +0 -57
- package/src/components/ui/checkbox.tsx +0 -30
- package/src/components/ui/dialog.tsx +0 -122
- package/src/components/ui/dropdown-menu.tsx +0 -201
- package/src/components/ui/hazo_ui_tooltip.tsx +0 -67
- package/src/components/ui/index.ts +0 -22
- package/src/components/ui/input.tsx +0 -22
- package/src/components/ui/label.tsx +0 -26
- package/src/components/ui/separator.tsx +0 -31
- package/src/components/ui/sheet.tsx +0 -139
- package/src/components/ui/sidebar.tsx +0 -773
- package/src/components/ui/skeleton.tsx +0 -15
- package/src/components/ui/sonner.tsx +0 -31
- package/src/components/ui/switch.tsx +0 -29
- package/src/components/ui/table.tsx +0 -120
- package/src/components/ui/tabs.tsx +0 -55
- package/src/components/ui/tooltip.tsx +0 -32
- package/src/components/ui/vertical-tabs.tsx +0 -59
- package/src/hooks/use-mobile.tsx +0 -19
- package/src/index.ts +0 -7
- package/src/lib/already_logged_in_config.server.ts +0 -46
- package/src/lib/app_logger.ts +0 -24
- package/src/lib/auth/auth_cache.ts +0 -220
- package/src/lib/auth/auth_rate_limiter.ts +0 -121
- package/src/lib/auth/auth_types.ts +0 -65
- package/src/lib/auth/auth_utils.server.ts +0 -196
- package/src/lib/auth/hazo_get_auth.server.ts +0 -333
- package/src/lib/auth/index.ts +0 -23
- package/src/lib/auth/server_auth.ts +0 -88
- package/src/lib/auth_utility_config.server.ts +0 -136
- package/src/lib/config/config_loader.server.ts +0 -164
- package/src/lib/email_verification_config.server.ts +0 -32
- package/src/lib/file_types_config.server.ts +0 -25
- package/src/lib/forgot_password_config.server.ts +0 -32
- package/src/lib/hazo_connect_instance.server.ts +0 -101
- package/src/lib/hazo_connect_setup.server.ts +0 -194
- package/src/lib/hazo_connect_setup.ts +0 -54
- package/src/lib/index.ts +0 -44
- package/src/lib/login_config.server.ts +0 -71
- package/src/lib/messages_config.server.ts +0 -45
- package/src/lib/migrations/apply_migration.ts +0 -105
- package/src/lib/my_settings_config.server.ts +0 -135
- package/src/lib/password_requirements_config.server.ts +0 -39
- package/src/lib/profile_pic_menu_config.server.ts +0 -138
- package/src/lib/profile_picture_config.server.ts +0 -56
- package/src/lib/register_config.server.ts +0 -73
- package/src/lib/reset_password_config.server.ts +0 -75
- package/src/lib/services/email_service.ts +0 -581
- package/src/lib/services/email_verification_service.ts +0 -270
- package/src/lib/services/index.ts +0 -15
- package/src/lib/services/login_service.ts +0 -134
- package/src/lib/services/password_change_service.ts +0 -154
- package/src/lib/services/password_reset_service.ts +0 -405
- package/src/lib/services/profile_picture_remove_service.ts +0 -120
- package/src/lib/services/profile_picture_service.ts +0 -215
- package/src/lib/services/profile_picture_source_mapper.ts +0 -62
- package/src/lib/services/registration_service.ts +0 -184
- package/src/lib/services/token_service.ts +0 -240
- package/src/lib/services/user_profiles_service.ts +0 -143
- package/src/lib/services/user_update_service.ts +0 -141
- package/src/lib/ui_shell_config.server.ts +0 -73
- package/src/lib/ui_sizes_config.server.ts +0 -37
- package/src/lib/user_fields_config.server.ts +0 -31
- package/src/lib/user_management_config.server.ts +0 -39
- package/src/lib/utils/api_route_helpers.ts +0 -60
- package/src/lib/utils/error_sanitizer.ts +0 -75
- package/src/lib/utils.ts +0 -11
- package/src/middleware.ts +0 -94
- package/src/routes/index.ts +0 -34
- package/src/server/config/config_loader.ts +0 -496
- package/src/server/index.ts +0 -38
- package/src/server/logging/logger_service.ts +0 -56
- package/src/server/routes/root_router.ts +0 -16
- package/src/server/server.ts +0 -28
- package/src/server/types/app_types.ts +0 -74
- package/src/server/types/express.d.ts +0 -16
- package/src/stories/email_verification_layout.stories.tsx +0 -137
- package/src/stories/forgot_password_layout.stories.tsx +0 -85
- package/src/stories/login_layout.stories.tsx +0 -85
- package/src/stories/project_overview.stories.tsx +0 -33
- package/src/stories/register_layout.stories.tsx +0 -107
- package/tailwind.config.ts +0 -77
- package/tsconfig.build.json +0 -36
- package/tsconfig.json +0 -28
package/src/middleware.ts
DELETED
|
@@ -1,94 +0,0 @@
|
|
|
1
|
-
// file_description: Next.js middleware for protecting routes based on authentication
|
|
2
|
-
// Note: Middleware runs in Edge Runtime, so it cannot use Node.js APIs (like SQLite)
|
|
3
|
-
// This middleware only checks for cookies - actual database validation happens in API routes
|
|
4
|
-
// section: imports
|
|
5
|
-
import { NextResponse } from "next/server";
|
|
6
|
-
import type { NextRequest } from "next/server";
|
|
7
|
-
|
|
8
|
-
// section: helpers
|
|
9
|
-
/**
|
|
10
|
-
* Checks if authentication cookies exist (lightweight check for Edge Runtime)
|
|
11
|
-
* Does not validate against database - that happens in API routes
|
|
12
|
-
* @param request - NextRequest object
|
|
13
|
-
* @returns true if cookies exist, false otherwise
|
|
14
|
-
*/
|
|
15
|
-
function has_auth_cookies(request: NextRequest): boolean {
|
|
16
|
-
const user_id = request.cookies.get("hazo_auth_user_id")?.value;
|
|
17
|
-
const user_email = request.cookies.get("hazo_auth_user_email")?.value;
|
|
18
|
-
|
|
19
|
-
return !!(user_id && user_email);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
// section: middleware
|
|
23
|
-
/**
|
|
24
|
-
* Next.js middleware function that runs on every request
|
|
25
|
-
* Protects routes by checking for authentication cookies
|
|
26
|
-
*
|
|
27
|
-
* Note: This middleware runs in Edge Runtime and cannot access Node.js APIs (like SQLite)
|
|
28
|
-
* It only checks if cookies exist - actual database validation happens in API routes
|
|
29
|
-
*
|
|
30
|
-
* Public routes (login, register, etc.) are allowed without authentication
|
|
31
|
-
* Protected routes require authentication cookies and redirect to login if not present
|
|
32
|
-
*/
|
|
33
|
-
export async function middleware(request: NextRequest) {
|
|
34
|
-
const pathname = request.nextUrl.pathname;
|
|
35
|
-
|
|
36
|
-
// Public routes that don't require authentication
|
|
37
|
-
const public_routes = [
|
|
38
|
-
"/hazo_auth/login",
|
|
39
|
-
"/hazo_auth/register",
|
|
40
|
-
"/hazo_auth/forgot_password",
|
|
41
|
-
"/hazo_auth/reset_password",
|
|
42
|
-
"/hazo_auth/verify_email",
|
|
43
|
-
"/api/hazo_auth/login",
|
|
44
|
-
"/api/hazo_auth/register",
|
|
45
|
-
"/api/hazo_auth/forgot_password",
|
|
46
|
-
"/api/hazo_auth/reset_password",
|
|
47
|
-
"/api/hazo_auth/verify_email",
|
|
48
|
-
"/api/hazo_auth/validate_reset_token",
|
|
49
|
-
"/api/hazo_auth/resend_verification", // Allow resend verification email without auth
|
|
50
|
-
"/api/hazo_auth/me", // Allow /api/hazo_auth/me to be public (returns authenticated: false if not logged in)
|
|
51
|
-
"/hazo_connect/api/sqlite", // SQLite Admin API routes (admin tool, should be accessible)
|
|
52
|
-
"/hazo_connect/sqlite_admin", // SQLite Admin UI page
|
|
53
|
-
];
|
|
54
|
-
|
|
55
|
-
// Check if route is public
|
|
56
|
-
const is_public_route = public_routes.some((route) =>
|
|
57
|
-
pathname.startsWith(route)
|
|
58
|
-
);
|
|
59
|
-
|
|
60
|
-
// Allow public routes
|
|
61
|
-
if (is_public_route) {
|
|
62
|
-
return NextResponse.next();
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
// Check if authentication cookies exist (lightweight check)
|
|
66
|
-
// Note: This doesn't validate against database - API routes will do that
|
|
67
|
-
const has_cookies = has_auth_cookies(request);
|
|
68
|
-
|
|
69
|
-
if (!has_cookies) {
|
|
70
|
-
// Redirect to login if no cookies (not authenticated)
|
|
71
|
-
const login_url = new URL("/hazo_auth/login", request.url);
|
|
72
|
-
login_url.searchParams.set("redirect", pathname);
|
|
73
|
-
return NextResponse.redirect(login_url);
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
// Allow requests with cookies (actual validation happens in API routes)
|
|
77
|
-
return NextResponse.next();
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
// section: config
|
|
81
|
-
export const config = {
|
|
82
|
-
matcher: [
|
|
83
|
-
/*
|
|
84
|
-
* Match all request paths except for the ones starting with:
|
|
85
|
-
* - _next/static (static files)
|
|
86
|
-
* - _next/image (image optimization files)
|
|
87
|
-
* - favicon.ico (favicon file)
|
|
88
|
-
* - public (public files)
|
|
89
|
-
* - api/auth/me (public endpoint)
|
|
90
|
-
*/
|
|
91
|
-
"/((?!_next/static|_next/image|favicon.ico|public).*)",
|
|
92
|
-
],
|
|
93
|
-
};
|
|
94
|
-
|
package/src/routes/index.ts
DELETED
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
// file_description: barrel export for all re-exportable route handlers and page components
|
|
2
|
-
// section: page_exports
|
|
3
|
-
// These are the client-side page components that can be re-exported by consumers
|
|
4
|
-
export { LoginPageClient } from "hazo_auth/app/hazo_auth/login/login_page_client";
|
|
5
|
-
export { RegisterPageClient } from "hazo_auth/app/hazo_auth/register/register_page_client";
|
|
6
|
-
export { ForgotPasswordPageClient } from "hazo_auth/app/hazo_auth/forgot_password/forgot_password_page_client";
|
|
7
|
-
export { ResetPasswordPageClient } from "hazo_auth/app/hazo_auth/reset_password/reset_password_page_client";
|
|
8
|
-
export { VerifyEmailPageClient } from "hazo_auth/app/hazo_auth/verify_email/verify_email_page_client";
|
|
9
|
-
export { MySettingsPageClient } from "hazo_auth/app/hazo_auth/my_settings/my_settings_page_client";
|
|
10
|
-
export { UserManagementPageClient } from "hazo_auth/app/hazo_auth/user_management/user_management_page_client";
|
|
11
|
-
|
|
12
|
-
// section: api_handler_exports
|
|
13
|
-
// These are the API route handlers that can be re-exported by consumers
|
|
14
|
-
export { POST as loginPOST } from "hazo_auth/app/api/hazo_auth/login/route";
|
|
15
|
-
export { POST as registerPOST } from "hazo_auth/app/api/hazo_auth/register/route";
|
|
16
|
-
export { POST as forgotPasswordPOST } from "hazo_auth/app/api/hazo_auth/forgot_password/route";
|
|
17
|
-
export { POST as resetPasswordPOST } from "hazo_auth/app/api/hazo_auth/reset_password/route";
|
|
18
|
-
export { GET as verifyEmailGET } from "hazo_auth/app/api/hazo_auth/verify_email/route";
|
|
19
|
-
export { POST as resendVerificationPOST } from "hazo_auth/app/api/hazo_auth/resend_verification/route";
|
|
20
|
-
export { POST as logoutPOST } from "hazo_auth/app/api/hazo_auth/logout/route";
|
|
21
|
-
export { POST as getAuthPOST } from "hazo_auth/app/api/hazo_auth/get_auth/route";
|
|
22
|
-
export { GET as meGET } from "hazo_auth/app/api/hazo_auth/me/route";
|
|
23
|
-
export { POST as changePasswordPOST } from "hazo_auth/app/api/hazo_auth/change_password/route";
|
|
24
|
-
export { PATCH as updateUserPATCH } from "hazo_auth/app/api/hazo_auth/update_user/route";
|
|
25
|
-
export { POST as invalidateCachePOST } from "hazo_auth/app/api/hazo_auth/invalidate_cache/route";
|
|
26
|
-
export { GET as libraryPhotosGET } from "hazo_auth/app/api/hazo_auth/library_photos/route";
|
|
27
|
-
export { POST as uploadProfilePicturePOST } from "hazo_auth/app/api/hazo_auth/upload_profile_picture/route";
|
|
28
|
-
export { DELETE as removeProfilePictureDELETE } from "hazo_auth/app/api/hazo_auth/remove_profile_picture/route";
|
|
29
|
-
export { GET as validateResetTokenGET } from "hazo_auth/app/api/hazo_auth/validate_reset_token/route";
|
|
30
|
-
|
|
31
|
-
// section: shell_exports
|
|
32
|
-
// Shell component for wrapping pages
|
|
33
|
-
export { AuthPageShell } from "hazo_auth/components/layouts/shared/components/auth_page_shell";
|
|
34
|
-
|
|
@@ -1,496 +0,0 @@
|
|
|
1
|
-
// file_description: bootstrap configuration handling for the hazo_auth server
|
|
2
|
-
// section: imports
|
|
3
|
-
import fs from "fs";
|
|
4
|
-
import path from "path";
|
|
5
|
-
import axios from "axios";
|
|
6
|
-
import { HazoConfig } from "hazo_config/dist/lib";
|
|
7
|
-
import { create_logger_service } from "../logging/logger_service";
|
|
8
|
-
import type {
|
|
9
|
-
app_context,
|
|
10
|
-
captcha_settings,
|
|
11
|
-
logger_service,
|
|
12
|
-
password_policy,
|
|
13
|
-
rate_limit_settings,
|
|
14
|
-
runtime_configuration,
|
|
15
|
-
token_settings,
|
|
16
|
-
} from "../types/app_types";
|
|
17
|
-
|
|
18
|
-
// section: schema_definitions
|
|
19
|
-
type direct_configuration_input = {
|
|
20
|
-
permission_names?: string[];
|
|
21
|
-
templates?: Record<string, string>;
|
|
22
|
-
labels?: Record<string, string>;
|
|
23
|
-
styles?: Record<string, string>;
|
|
24
|
-
emailer?: resolved_emailer_options;
|
|
25
|
-
logger?: logger_service;
|
|
26
|
-
password_policy?: Partial<password_policy>;
|
|
27
|
-
token_settings?: Partial<token_settings>;
|
|
28
|
-
rate_limit?: Partial<rate_limit_settings>;
|
|
29
|
-
captcha?: captcha_settings;
|
|
30
|
-
};
|
|
31
|
-
|
|
32
|
-
export type configuration_options = {
|
|
33
|
-
config_file_path?: string;
|
|
34
|
-
direct_configuration?: direct_configuration_input;
|
|
35
|
-
};
|
|
36
|
-
const is_string_record = (value: unknown): value is Record<string, string> =>
|
|
37
|
-
!!value &&
|
|
38
|
-
typeof value === "object" &&
|
|
39
|
-
!Array.isArray(value) &&
|
|
40
|
-
Object.values(value).every((entry) => typeof entry === "string");
|
|
41
|
-
|
|
42
|
-
const sanitize_configuration_options = (
|
|
43
|
-
options: configuration_options | undefined,
|
|
44
|
-
logger: logger_service
|
|
45
|
-
): configuration_options => {
|
|
46
|
-
if (!options || typeof options !== "object") {
|
|
47
|
-
return {};
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
const sanitized: configuration_options = {};
|
|
51
|
-
|
|
52
|
-
if (typeof options.config_file_path === "string" && options.config_file_path.length > 0) {
|
|
53
|
-
sanitized.config_file_path = options.config_file_path;
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
if (options.direct_configuration && typeof options.direct_configuration === "object") {
|
|
57
|
-
const direct_config: direct_configuration_input = {};
|
|
58
|
-
const provided = options.direct_configuration;
|
|
59
|
-
|
|
60
|
-
if (Array.isArray(provided.permission_names)) {
|
|
61
|
-
direct_config.permission_names = provided.permission_names.filter(
|
|
62
|
-
(permission) => typeof permission === "string"
|
|
63
|
-
);
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
if (is_string_record(provided.templates)) {
|
|
67
|
-
direct_config.templates = provided.templates;
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
if (is_string_record(provided.labels)) {
|
|
71
|
-
direct_config.labels = provided.labels;
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
if (is_string_record(provided.styles)) {
|
|
75
|
-
direct_config.styles = provided.styles;
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
if (
|
|
79
|
-
provided.emailer &&
|
|
80
|
-
typeof provided.emailer === "object" &&
|
|
81
|
-
typeof provided.emailer.base_url === "string"
|
|
82
|
-
) {
|
|
83
|
-
direct_config.emailer = {
|
|
84
|
-
base_url: provided.emailer.base_url,
|
|
85
|
-
api_key:
|
|
86
|
-
typeof provided.emailer.api_key === "string" ? provided.emailer.api_key : undefined,
|
|
87
|
-
headers: is_string_record(provided.emailer.headers) ? provided.emailer.headers : undefined,
|
|
88
|
-
};
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
if (provided.logger) {
|
|
92
|
-
direct_config.logger = provided.logger;
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
if (provided.password_policy) {
|
|
96
|
-
direct_config.password_policy = {
|
|
97
|
-
min_length:
|
|
98
|
-
typeof provided.password_policy.min_length === "number"
|
|
99
|
-
? provided.password_policy.min_length
|
|
100
|
-
: undefined,
|
|
101
|
-
requires_lowercase: provided.password_policy.requires_lowercase,
|
|
102
|
-
requires_uppercase: provided.password_policy.requires_uppercase,
|
|
103
|
-
requires_number: provided.password_policy.requires_number,
|
|
104
|
-
requires_symbol: provided.password_policy.requires_symbol,
|
|
105
|
-
};
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
if (provided.token_settings) {
|
|
109
|
-
direct_config.token_settings = {
|
|
110
|
-
access_token_ttl_seconds: provided.token_settings.access_token_ttl_seconds,
|
|
111
|
-
refresh_token_ttl_seconds: provided.token_settings.refresh_token_ttl_seconds,
|
|
112
|
-
};
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
if (provided.rate_limit) {
|
|
116
|
-
direct_config.rate_limit = {
|
|
117
|
-
max_attempts: provided.rate_limit.max_attempts,
|
|
118
|
-
window_minutes: provided.rate_limit.window_minutes,
|
|
119
|
-
};
|
|
120
|
-
}
|
|
121
|
-
|
|
122
|
-
if (provided.captcha) {
|
|
123
|
-
direct_config.captcha = provided.captcha;
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
direct_config.logger?.info?.("config_direct_override_detected", { fields: Object.keys(direct_config) });
|
|
127
|
-
sanitized.direct_configuration = direct_config;
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
return sanitized;
|
|
131
|
-
};
|
|
132
|
-
|
|
133
|
-
type resolved_emailer_options = {
|
|
134
|
-
base_url: string;
|
|
135
|
-
api_key?: string;
|
|
136
|
-
headers?: Record<string, string>;
|
|
137
|
-
};
|
|
138
|
-
|
|
139
|
-
// section: defaults
|
|
140
|
-
const default_config_path = path.resolve(process.cwd(), "config.ini");
|
|
141
|
-
|
|
142
|
-
const default_password_policy: password_policy = {
|
|
143
|
-
min_length: 12,
|
|
144
|
-
requires_uppercase: true,
|
|
145
|
-
requires_lowercase: true,
|
|
146
|
-
requires_number: true,
|
|
147
|
-
requires_symbol: true,
|
|
148
|
-
};
|
|
149
|
-
|
|
150
|
-
const default_token_settings: token_settings = {
|
|
151
|
-
access_token_ttl_seconds: 15 * 60,
|
|
152
|
-
refresh_token_ttl_seconds: 60 * 60 * 24 * 30,
|
|
153
|
-
};
|
|
154
|
-
|
|
155
|
-
const default_rate_limit: rate_limit_settings = {
|
|
156
|
-
max_attempts: 5,
|
|
157
|
-
window_minutes: 5,
|
|
158
|
-
};
|
|
159
|
-
|
|
160
|
-
const read_ini_section = (
|
|
161
|
-
instance: HazoConfig | undefined,
|
|
162
|
-
section: string
|
|
163
|
-
): Record<string, string> => {
|
|
164
|
-
if (instance === undefined) {
|
|
165
|
-
return {};
|
|
166
|
-
}
|
|
167
|
-
return instance.getSection(section) ?? {};
|
|
168
|
-
};
|
|
169
|
-
|
|
170
|
-
// section: helper_functions
|
|
171
|
-
const resolve_permissions = (
|
|
172
|
-
direct_permissions: string[] | undefined,
|
|
173
|
-
permission_section: Record<string, string>,
|
|
174
|
-
logger: logger_service
|
|
175
|
-
): string[] => {
|
|
176
|
-
if (direct_permissions && direct_permissions.length > 0) {
|
|
177
|
-
logger.info("config_permissions_direct_override", { count: direct_permissions.length });
|
|
178
|
-
return direct_permissions;
|
|
179
|
-
}
|
|
180
|
-
|
|
181
|
-
const configured = permission_section.list
|
|
182
|
-
?.split(",")
|
|
183
|
-
.map((value) => value.trim())
|
|
184
|
-
.filter((value) => value.length > 0);
|
|
185
|
-
|
|
186
|
-
if (configured && configured.length > 0) {
|
|
187
|
-
logger.info("config_permissions_from_file", { count: configured.length });
|
|
188
|
-
return configured;
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
logger.warn("config_permissions_default", {});
|
|
192
|
-
return [];
|
|
193
|
-
};
|
|
194
|
-
|
|
195
|
-
const resolve_password_policy = (
|
|
196
|
-
direct_policy: Partial<password_policy> | undefined,
|
|
197
|
-
auth_section: Record<string, string>,
|
|
198
|
-
logger: logger_service
|
|
199
|
-
): password_policy => {
|
|
200
|
-
const resolved: password_policy = { ...default_password_policy };
|
|
201
|
-
|
|
202
|
-
const apply_value = <K extends keyof password_policy>(key: K, value: string | undefined) => {
|
|
203
|
-
if (value === undefined) {
|
|
204
|
-
return;
|
|
205
|
-
}
|
|
206
|
-
if (key === "min_length") {
|
|
207
|
-
const parsed = Number(value);
|
|
208
|
-
if (!Number.isNaN(parsed)) {
|
|
209
|
-
(resolved as any)[key] = parsed;
|
|
210
|
-
}
|
|
211
|
-
return;
|
|
212
|
-
}
|
|
213
|
-
(resolved as any)[key] = value === "true";
|
|
214
|
-
};
|
|
215
|
-
|
|
216
|
-
apply_value("min_length", auth_section.min_length);
|
|
217
|
-
apply_value("requires_uppercase", auth_section.requires_uppercase);
|
|
218
|
-
apply_value("requires_lowercase", auth_section.requires_lowercase);
|
|
219
|
-
apply_value("requires_number", auth_section.requires_number);
|
|
220
|
-
apply_value("requires_symbol", auth_section.requires_symbol);
|
|
221
|
-
|
|
222
|
-
if (direct_policy) {
|
|
223
|
-
Object.assign(resolved, direct_policy);
|
|
224
|
-
logger.info("config_password_policy_direct_override", resolved);
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
return resolved;
|
|
228
|
-
};
|
|
229
|
-
|
|
230
|
-
const resolve_token_settings = (
|
|
231
|
-
direct_tokens: Partial<token_settings> | undefined,
|
|
232
|
-
auth_section: Record<string, string>,
|
|
233
|
-
logger: logger_service
|
|
234
|
-
): token_settings => {
|
|
235
|
-
const resolved: token_settings = { ...default_token_settings };
|
|
236
|
-
|
|
237
|
-
const access_token_value = Number(auth_section.access_token_ttl_seconds);
|
|
238
|
-
if (!Number.isNaN(access_token_value) && access_token_value > 0) {
|
|
239
|
-
resolved.access_token_ttl_seconds = access_token_value;
|
|
240
|
-
}
|
|
241
|
-
|
|
242
|
-
const refresh_token_value = Number(auth_section.refresh_token_ttl_seconds);
|
|
243
|
-
if (!Number.isNaN(refresh_token_value) && refresh_token_value > 0) {
|
|
244
|
-
resolved.refresh_token_ttl_seconds = refresh_token_value;
|
|
245
|
-
}
|
|
246
|
-
|
|
247
|
-
if (direct_tokens) {
|
|
248
|
-
Object.assign(resolved, direct_tokens);
|
|
249
|
-
logger.info("config_token_settings_direct_override", resolved);
|
|
250
|
-
}
|
|
251
|
-
|
|
252
|
-
return resolved;
|
|
253
|
-
};
|
|
254
|
-
|
|
255
|
-
const resolve_rate_limit = (
|
|
256
|
-
direct_rate_limit: Partial<rate_limit_settings> | undefined,
|
|
257
|
-
rate_section: Record<string, string>,
|
|
258
|
-
logger: logger_service
|
|
259
|
-
): rate_limit_settings => {
|
|
260
|
-
const resolved: rate_limit_settings = { ...default_rate_limit };
|
|
261
|
-
|
|
262
|
-
const max_attempts = Number(rate_section.max_attempts);
|
|
263
|
-
if (!Number.isNaN(max_attempts) && max_attempts > 0) {
|
|
264
|
-
resolved.max_attempts = max_attempts;
|
|
265
|
-
}
|
|
266
|
-
|
|
267
|
-
const window_minutes = Number(rate_section.window_minutes);
|
|
268
|
-
if (!Number.isNaN(window_minutes) && window_minutes > 0) {
|
|
269
|
-
resolved.window_minutes = window_minutes;
|
|
270
|
-
}
|
|
271
|
-
|
|
272
|
-
if (direct_rate_limit) {
|
|
273
|
-
Object.assign(resolved, direct_rate_limit);
|
|
274
|
-
logger.info("config_rate_limit_direct_override", resolved);
|
|
275
|
-
}
|
|
276
|
-
|
|
277
|
-
return resolved;
|
|
278
|
-
};
|
|
279
|
-
|
|
280
|
-
const resolve_captcha = (
|
|
281
|
-
direct_captcha: captcha_settings | undefined,
|
|
282
|
-
captcha_section: Record<string, string>,
|
|
283
|
-
logger: logger_service
|
|
284
|
-
): captcha_settings => {
|
|
285
|
-
if (direct_captcha) {
|
|
286
|
-
logger.info("config_captcha_direct_override", { provider: direct_captcha.provider });
|
|
287
|
-
return direct_captcha;
|
|
288
|
-
}
|
|
289
|
-
|
|
290
|
-
if (captcha_section.provider && captcha_section.secret_key) {
|
|
291
|
-
logger.info("config_captcha_from_file", { provider: captcha_section.provider });
|
|
292
|
-
return {
|
|
293
|
-
provider: captcha_section.provider as "recaptcha_v2" | "recaptcha_v3" | "hcaptcha",
|
|
294
|
-
secret_key: captcha_section.secret_key,
|
|
295
|
-
};
|
|
296
|
-
}
|
|
297
|
-
|
|
298
|
-
logger.warn("config_captcha_missing", {});
|
|
299
|
-
return undefined;
|
|
300
|
-
};
|
|
301
|
-
|
|
302
|
-
const resolve_dictionary = (
|
|
303
|
-
direct_values: Record<string, string> | undefined,
|
|
304
|
-
section_values: Record<string, string>,
|
|
305
|
-
logger: logger_service,
|
|
306
|
-
metric_name: string
|
|
307
|
-
): Record<string, string> => {
|
|
308
|
-
if (direct_values && Object.keys(direct_values).length > 0) {
|
|
309
|
-
logger.info(`${metric_name}_direct_override`, { keys: Object.keys(direct_values) });
|
|
310
|
-
return direct_values;
|
|
311
|
-
}
|
|
312
|
-
|
|
313
|
-
if (Object.keys(section_values).length > 0) {
|
|
314
|
-
logger.info(`${metric_name}_from_file`, { keys: Object.keys(section_values) });
|
|
315
|
-
return section_values;
|
|
316
|
-
}
|
|
317
|
-
|
|
318
|
-
logger.warn(`${metric_name}_empty`, {});
|
|
319
|
-
return {};
|
|
320
|
-
};
|
|
321
|
-
|
|
322
|
-
const read_template_file = (file_path: string, logger: logger_service): string | undefined => {
|
|
323
|
-
const absolute_path = path.isAbsolute(file_path)
|
|
324
|
-
? file_path
|
|
325
|
-
: path.resolve(process.cwd(), file_path);
|
|
326
|
-
|
|
327
|
-
try {
|
|
328
|
-
const content = fs.readFileSync(absolute_path, "utf-8");
|
|
329
|
-
logger.info("config_template_loaded", { file_path: absolute_path });
|
|
330
|
-
return content;
|
|
331
|
-
} catch (error) {
|
|
332
|
-
logger.error("config_template_load_failed", {
|
|
333
|
-
file_path: absolute_path,
|
|
334
|
-
error: (error as Error).message,
|
|
335
|
-
});
|
|
336
|
-
return undefined;
|
|
337
|
-
}
|
|
338
|
-
};
|
|
339
|
-
|
|
340
|
-
const resolve_templates = (
|
|
341
|
-
direct_templates: Record<string, string> | undefined,
|
|
342
|
-
template_section: Record<string, string>,
|
|
343
|
-
logger: logger_service
|
|
344
|
-
): Record<string, string> => {
|
|
345
|
-
const resolved_templates: Record<string, string> = {};
|
|
346
|
-
|
|
347
|
-
Object.entries(template_section).forEach(([template_name, template_path]) => {
|
|
348
|
-
const template_content = read_template_file(template_path, logger);
|
|
349
|
-
if (template_content) {
|
|
350
|
-
resolved_templates[template_name] = template_content;
|
|
351
|
-
}
|
|
352
|
-
});
|
|
353
|
-
|
|
354
|
-
if (direct_templates) {
|
|
355
|
-
Object.entries(direct_templates).forEach(([template_name, template_body]) => {
|
|
356
|
-
resolved_templates[template_name] = template_body;
|
|
357
|
-
});
|
|
358
|
-
logger.info("config_templates_direct_override", { count: Object.keys(direct_templates).length });
|
|
359
|
-
}
|
|
360
|
-
|
|
361
|
-
return resolved_templates;
|
|
362
|
-
};
|
|
363
|
-
|
|
364
|
-
const create_emailer_client = (
|
|
365
|
-
emailer_options: resolved_emailer_options | undefined,
|
|
366
|
-
logger: logger_service
|
|
367
|
-
) => {
|
|
368
|
-
if (!emailer_options) {
|
|
369
|
-
return {
|
|
370
|
-
send_message: async () => {
|
|
371
|
-
logger.warn("emailer_placeholder_invoked", {});
|
|
372
|
-
return { success: true };
|
|
373
|
-
},
|
|
374
|
-
};
|
|
375
|
-
}
|
|
376
|
-
|
|
377
|
-
const client = axios.create({
|
|
378
|
-
baseURL: emailer_options.base_url,
|
|
379
|
-
headers: {
|
|
380
|
-
...(emailer_options.headers ?? {}),
|
|
381
|
-
...(emailer_options.api_key ? { Authorization: `Bearer ${emailer_options.api_key}` } : {}),
|
|
382
|
-
"Content-Type": "application/json",
|
|
383
|
-
},
|
|
384
|
-
});
|
|
385
|
-
|
|
386
|
-
return {
|
|
387
|
-
send_message: async (payload: Record<string, unknown>) => {
|
|
388
|
-
try {
|
|
389
|
-
logger.info("emailer_request_initiated", { payload });
|
|
390
|
-
await client.post("/send", payload);
|
|
391
|
-
logger.info("emailer_request_success", {});
|
|
392
|
-
return { success: true };
|
|
393
|
-
} catch (error) {
|
|
394
|
-
logger.error("emailer_request_failed", { error: (error as Error).message });
|
|
395
|
-
return { success: false };
|
|
396
|
-
}
|
|
397
|
-
},
|
|
398
|
-
};
|
|
399
|
-
};
|
|
400
|
-
|
|
401
|
-
// section: loader
|
|
402
|
-
export const load_runtime_configuration = (
|
|
403
|
-
options?: configuration_options
|
|
404
|
-
): runtime_configuration => {
|
|
405
|
-
const fallback_logger = create_logger_service("hazo_auth_config");
|
|
406
|
-
const parsed_options = sanitize_configuration_options(options, fallback_logger);
|
|
407
|
-
const direct_configuration = parsed_options.direct_configuration;
|
|
408
|
-
const logger = direct_configuration?.logger ?? fallback_logger;
|
|
409
|
-
|
|
410
|
-
let hazo_config: HazoConfig | undefined;
|
|
411
|
-
|
|
412
|
-
try {
|
|
413
|
-
const config_file_path = parsed_options?.config_file_path ?? default_config_path;
|
|
414
|
-
if (fs.existsSync(config_file_path)) {
|
|
415
|
-
hazo_config = new HazoConfig({
|
|
416
|
-
filePath: config_file_path,
|
|
417
|
-
logger,
|
|
418
|
-
});
|
|
419
|
-
logger.info("config_file_loaded", { config_file_path });
|
|
420
|
-
} else {
|
|
421
|
-
logger.warn("config_file_missing", { config_file_path });
|
|
422
|
-
}
|
|
423
|
-
} catch (error) {
|
|
424
|
-
logger.error("config_file_error", { error: (error as Error).message });
|
|
425
|
-
}
|
|
426
|
-
|
|
427
|
-
const permission_section = read_ini_section(hazo_config, "permissions");
|
|
428
|
-
const auth_section = read_ini_section(hazo_config, "auth");
|
|
429
|
-
const rate_section = read_ini_section(hazo_config, "rate_limit");
|
|
430
|
-
const label_section = read_ini_section(hazo_config, "labels");
|
|
431
|
-
const style_section = read_ini_section(hazo_config, "styles");
|
|
432
|
-
const template_section = read_ini_section(hazo_config, "templates");
|
|
433
|
-
const emailer_section = read_ini_section(hazo_config, "emailer");
|
|
434
|
-
const captcha_section = read_ini_section(hazo_config, "captcha");
|
|
435
|
-
|
|
436
|
-
const permission_names = resolve_permissions(
|
|
437
|
-
direct_configuration?.permission_names,
|
|
438
|
-
permission_section,
|
|
439
|
-
logger
|
|
440
|
-
);
|
|
441
|
-
|
|
442
|
-
const password_policy = resolve_password_policy(
|
|
443
|
-
direct_configuration?.password_policy,
|
|
444
|
-
auth_section,
|
|
445
|
-
logger
|
|
446
|
-
);
|
|
447
|
-
|
|
448
|
-
const token_settings = resolve_token_settings(
|
|
449
|
-
direct_configuration?.token_settings,
|
|
450
|
-
auth_section,
|
|
451
|
-
logger
|
|
452
|
-
);
|
|
453
|
-
|
|
454
|
-
const rate_limit = resolve_rate_limit(
|
|
455
|
-
direct_configuration?.rate_limit,
|
|
456
|
-
rate_section,
|
|
457
|
-
logger
|
|
458
|
-
);
|
|
459
|
-
|
|
460
|
-
const labels = resolve_dictionary(direct_configuration?.labels, label_section, logger, "config_labels");
|
|
461
|
-
const styles = resolve_dictionary(direct_configuration?.styles, style_section, logger, "config_styles");
|
|
462
|
-
const templates = resolve_templates(direct_configuration?.templates, template_section, logger);
|
|
463
|
-
|
|
464
|
-
const resolved_emailer_options =
|
|
465
|
-
direct_configuration?.emailer ??
|
|
466
|
-
(emailer_section.base_url
|
|
467
|
-
? {
|
|
468
|
-
base_url: emailer_section.base_url,
|
|
469
|
-
api_key: emailer_section.api_key,
|
|
470
|
-
headers: emailer_section.headers ? JSON.parse(emailer_section.headers) : undefined,
|
|
471
|
-
}
|
|
472
|
-
: undefined);
|
|
473
|
-
|
|
474
|
-
const emailer = create_emailer_client(resolved_emailer_options, logger);
|
|
475
|
-
|
|
476
|
-
const captcha = resolve_captcha(direct_configuration?.captcha, captcha_section, logger);
|
|
477
|
-
|
|
478
|
-
return {
|
|
479
|
-
permission_names,
|
|
480
|
-
logger,
|
|
481
|
-
emailer,
|
|
482
|
-
templates,
|
|
483
|
-
labels,
|
|
484
|
-
styles,
|
|
485
|
-
password_policy,
|
|
486
|
-
token_settings,
|
|
487
|
-
rate_limit,
|
|
488
|
-
captcha,
|
|
489
|
-
};
|
|
490
|
-
};
|
|
491
|
-
|
|
492
|
-
// section: context_factory
|
|
493
|
-
export const create_app_context = (options?: configuration_options): app_context => ({
|
|
494
|
-
config: load_runtime_configuration(options),
|
|
495
|
-
});
|
|
496
|
-
|
package/src/server/index.ts
DELETED
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
// file_description: bootstrap entry point for the hazo_auth express server
|
|
2
|
-
// section: imports
|
|
3
|
-
import http from "http";
|
|
4
|
-
import { create_server_app } from "./server";
|
|
5
|
-
import { create_logger_service } from "./logging/logger_service";
|
|
6
|
-
|
|
7
|
-
// section: constants
|
|
8
|
-
const default_port = Number(process.env.PORT ?? 4100);
|
|
9
|
-
const server_namespace = "hazo_auth_server";
|
|
10
|
-
|
|
11
|
-
// section: bootstrap_runner
|
|
12
|
-
export const start_server = async (): Promise<void> => {
|
|
13
|
-
const logger = create_logger_service(server_namespace);
|
|
14
|
-
const app = create_server_app();
|
|
15
|
-
const http_server = http.createServer(app);
|
|
16
|
-
|
|
17
|
-
return new Promise((resolve, reject) => {
|
|
18
|
-
http_server.listen(default_port, () => {
|
|
19
|
-
logger.info("server_started", { port: default_port });
|
|
20
|
-
resolve();
|
|
21
|
-
});
|
|
22
|
-
|
|
23
|
-
http_server.on("error", (error) => {
|
|
24
|
-
logger.error("server_start_failed", { error: (error as Error).message });
|
|
25
|
-
reject(error);
|
|
26
|
-
});
|
|
27
|
-
});
|
|
28
|
-
};
|
|
29
|
-
|
|
30
|
-
// section: direct_execution_guard
|
|
31
|
-
const resolved_module_path = new URL(import.meta.url).pathname;
|
|
32
|
-
const entry_module_path =
|
|
33
|
-
process.argv[1] !== undefined ? new URL(`file://${process.argv[1]}`).pathname : undefined;
|
|
34
|
-
const is_primary_module = entry_module_path !== undefined && entry_module_path === resolved_module_path;
|
|
35
|
-
if (is_primary_module) {
|
|
36
|
-
void start_server();
|
|
37
|
-
}
|
|
38
|
-
|