django-cfg 1.4.21__py3-none-any.whl → 1.4.24__py3-none-any.whl
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.
- django_cfg/__init__.py +4 -4
- django_cfg/apps/accounts/__init__.py +1 -1
- django_cfg/apps/accounts/__models.py +30 -29
- django_cfg/apps/accounts/admin/__init__.py +14 -3
- django_cfg/apps/accounts/admin/activity_admin.py +19 -19
- django_cfg/apps/accounts/admin/filters.py +7 -6
- django_cfg/apps/accounts/admin/group_admin.py +10 -16
- django_cfg/apps/accounts/admin/inlines.py +21 -19
- django_cfg/apps/accounts/admin/otp_admin.py +12 -12
- django_cfg/apps/accounts/admin/registration_admin.py +24 -24
- django_cfg/apps/accounts/admin/resources.py +49 -48
- django_cfg/apps/accounts/admin/twilio_admin.py +37 -37
- django_cfg/apps/accounts/admin/user_admin.py +45 -41
- django_cfg/apps/accounts/management/commands/otp_test.py +11 -11
- django_cfg/apps/accounts/managers/__init__.py +1 -1
- django_cfg/apps/accounts/managers/user_manager.py +6 -7
- django_cfg/apps/accounts/migrations/0001_initial.py +3 -2
- django_cfg/apps/accounts/models/__init__.py +15 -16
- django_cfg/apps/accounts/models/activity.py +5 -5
- django_cfg/apps/accounts/models/integrations.py +15 -15
- django_cfg/apps/accounts/models/registration.py +3 -2
- django_cfg/apps/accounts/models/user.py +3 -2
- django_cfg/apps/accounts/serializers/__init__.py +10 -3
- django_cfg/apps/accounts/serializers/otp.py +5 -4
- django_cfg/apps/accounts/serializers/profile.py +4 -5
- django_cfg/apps/accounts/serializers/webhook.py +13 -13
- django_cfg/apps/accounts/services/activity_service.py +13 -12
- django_cfg/apps/accounts/services/otp_service.py +16 -14
- django_cfg/apps/accounts/signals.py +18 -16
- django_cfg/apps/accounts/urls.py +10 -5
- django_cfg/apps/accounts/utils/notifications.py +22 -22
- django_cfg/apps/accounts/views/__init__.py +1 -1
- django_cfg/apps/accounts/views/otp.py +15 -14
- django_cfg/apps/accounts/views/profile.py +14 -10
- django_cfg/apps/accounts/views/webhook.py +46 -48
- django_cfg/apps/agents/__init__.py +3 -3
- django_cfg/apps/agents/admin/__init__.py +1 -1
- django_cfg/apps/agents/admin/execution_admin.py +68 -72
- django_cfg/apps/agents/admin/registry_admin.py +50 -54
- django_cfg/apps/agents/admin/toolsets_admin.py +63 -67
- django_cfg/apps/agents/apps.py +3 -3
- django_cfg/apps/agents/core/__init__.py +4 -4
- django_cfg/apps/agents/core/dependencies.py +24 -23
- django_cfg/apps/agents/core/django_agent.py +41 -39
- django_cfg/apps/agents/core/exceptions.py +12 -12
- django_cfg/apps/agents/core/models.py +16 -15
- django_cfg/apps/agents/core/orchestrator.py +58 -58
- django_cfg/apps/agents/examples/simple_example.py +24 -19
- django_cfg/apps/agents/integration/__init__.py +1 -1
- django_cfg/apps/agents/integration/middleware.py +12 -11
- django_cfg/apps/agents/integration/registry.py +52 -49
- django_cfg/apps/agents/integration/signals.py +5 -5
- django_cfg/apps/agents/management/commands/create_agent.py +39 -38
- django_cfg/apps/agents/management/commands/orchestrator_status.py +40 -39
- django_cfg/apps/agents/managers/__init__.py +8 -3
- django_cfg/apps/agents/managers/execution.py +42 -41
- django_cfg/apps/agents/managers/registry.py +40 -39
- django_cfg/apps/agents/managers/toolsets.py +87 -86
- django_cfg/apps/agents/migrations/0001_initial.py +2 -1
- django_cfg/apps/agents/models/__init__.py +2 -2
- django_cfg/apps/agents/models/execution.py +43 -42
- django_cfg/apps/agents/models/registry.py +46 -45
- django_cfg/apps/agents/models/toolsets.py +63 -62
- django_cfg/apps/agents/patterns/__init__.py +5 -5
- django_cfg/apps/agents/patterns/content_agents.py +17 -16
- django_cfg/apps/agents/toolsets/__init__.py +3 -3
- django_cfg/apps/agents/toolsets/cache_toolset.py +56 -55
- django_cfg/apps/agents/toolsets/django_toolset.py +43 -42
- django_cfg/apps/agents/toolsets/file_toolset.py +64 -63
- django_cfg/apps/agents/toolsets/orm_toolset.py +75 -74
- django_cfg/apps/agents/urls.py +3 -2
- django_cfg/apps/api/commands/urls.py +1 -0
- django_cfg/apps/api/commands/views.py +23 -26
- django_cfg/apps/api/endpoints/checker.py +5 -4
- django_cfg/apps/api/endpoints/drf_views.py +2 -2
- django_cfg/apps/api/endpoints/tests.py +6 -5
- django_cfg/apps/api/endpoints/urls.py +2 -1
- django_cfg/apps/api/endpoints/views.py +1 -0
- django_cfg/apps/api/health/drf_views.py +6 -6
- django_cfg/apps/api/health/urls.py +2 -1
- django_cfg/apps/api/health/views.py +41 -41
- django_cfg/{modules/django_ipc_client → apps/ipc}/__init__.py +6 -6
- django_cfg/apps/ipc/apps.py +28 -0
- django_cfg/apps/ipc/serializers/__init__.py +19 -0
- django_cfg/apps/ipc/serializers/serializers.py +229 -0
- django_cfg/apps/ipc/services/__init__.py +7 -0
- django_cfg/apps/ipc/services/client/__init__.py +23 -0
- django_cfg/{modules/django_ipc_client → apps/ipc/services/client}/client.py +7 -6
- django_cfg/{modules/django_ipc_client → apps/ipc/services/client}/exceptions.py +1 -1
- django_cfg/{modules/django_ipc_client/dashboard → apps/ipc/services}/monitor.py +36 -7
- django_cfg/{modules/django_ipc_client/dashboard/static/django_ipc_dashboard/js/dashboard.js → apps/ipc/static/django_cfg_ipc/js/dashboard.mjs} +131 -63
- django_cfg/{modules/django_ipc_client/dashboard/templates/django_ipc_dashboard → apps/ipc/templates/django_cfg_ipc}/base.html +5 -10
- django_cfg/apps/ipc/templates/django_cfg_ipc/dashboard.html +202 -0
- django_cfg/apps/ipc/urls.py +21 -0
- django_cfg/apps/ipc/urls_admin.py +20 -0
- django_cfg/apps/ipc/views/__init__.py +8 -0
- django_cfg/apps/ipc/views/dashboard.py +15 -0
- django_cfg/apps/ipc/views/viewsets.py +245 -0
- django_cfg/apps/knowbase/admin/__init__.py +2 -2
- django_cfg/apps/knowbase/admin/actions/__init__.py +1 -1
- django_cfg/apps/knowbase/admin/actions/visibility_actions.py +2 -1
- django_cfg/apps/knowbase/admin/archive_admin.py +81 -84
- django_cfg/apps/knowbase/admin/chat_admin.py +70 -72
- django_cfg/apps/knowbase/admin/document_admin.py +10 -11
- django_cfg/apps/knowbase/admin/external_data_admin.py +69 -71
- django_cfg/apps/knowbase/admin/helpers/__init__.py +1 -1
- django_cfg/apps/knowbase/admin/helpers/configs.py +2 -2
- django_cfg/apps/knowbase/admin/helpers/statistics.py +1 -1
- django_cfg/apps/knowbase/apps.py +13 -13
- django_cfg/apps/knowbase/config/__init__.py +7 -6
- django_cfg/apps/knowbase/config/constance_fields.py +14 -12
- django_cfg/apps/knowbase/config/constance_settings.py +32 -31
- django_cfg/apps/knowbase/config/settings.py +28 -28
- django_cfg/apps/knowbase/examples/external_data_usage.py +35 -32
- django_cfg/apps/knowbase/management/commands/knowbase_stats.py +33 -32
- django_cfg/apps/knowbase/management/commands/setup_knowbase.py +11 -13
- django_cfg/apps/knowbase/managers/__init__.py +2 -2
- django_cfg/apps/knowbase/managers/archive.py +86 -85
- django_cfg/apps/knowbase/managers/base.py +5 -5
- django_cfg/apps/knowbase/managers/chat.py +29 -28
- django_cfg/apps/knowbase/managers/document.py +39 -39
- django_cfg/apps/knowbase/managers/external_data.py +74 -73
- django_cfg/apps/knowbase/migrations/0001_initial.py +2 -1
- django_cfg/apps/knowbase/migrations/0002_archiveitem_archiveitemchunk_documentarchive_and_more.py +2 -1
- django_cfg/apps/knowbase/mixins/__init__.py +4 -4
- django_cfg/apps/knowbase/mixins/config/__init__.py +1 -1
- django_cfg/apps/knowbase/mixins/config/meta_config.py +1 -1
- django_cfg/apps/knowbase/mixins/config.py +19 -18
- django_cfg/apps/knowbase/mixins/creator.py +7 -7
- django_cfg/apps/knowbase/mixins/examples/vehicle_model_example.py +29 -28
- django_cfg/apps/knowbase/mixins/external_data_mixin.py +6 -5
- django_cfg/apps/knowbase/mixins/generators/__init__.py +1 -1
- django_cfg/apps/knowbase/mixins/generators/content_generator.py +2 -2
- django_cfg/apps/knowbase/mixins/service.py +47 -45
- django_cfg/apps/knowbase/models/__init__.py +7 -7
- django_cfg/apps/knowbase/models/archive.py +72 -72
- django_cfg/apps/knowbase/models/base.py +12 -13
- django_cfg/apps/knowbase/models/chat.py +20 -19
- django_cfg/apps/knowbase/models/document.py +37 -35
- django_cfg/apps/knowbase/models/external_data.py +41 -42
- django_cfg/apps/knowbase/serializers/__init__.py +7 -7
- django_cfg/apps/knowbase/serializers/archive_serializers.py +50 -42
- django_cfg/apps/knowbase/serializers/chat_serializers.py +16 -15
- django_cfg/apps/knowbase/serializers/document_serializers.py +13 -12
- django_cfg/apps/knowbase/serializers/external_data_serializers.py +31 -31
- django_cfg/apps/knowbase/serializers/public_serializers.py +10 -9
- django_cfg/apps/knowbase/services/__init__.py +7 -7
- django_cfg/apps/knowbase/services/archive/__init__.py +7 -7
- django_cfg/apps/knowbase/services/archive/analyzers/__init__.py +1 -1
- django_cfg/apps/knowbase/services/archive/analyzers/tag_generator.py +1 -1
- django_cfg/apps/knowbase/services/archive/archive_service.py +109 -112
- django_cfg/apps/knowbase/services/archive/chunking/__init__.py +3 -3
- django_cfg/apps/knowbase/services/archive/chunking/base.py +1 -0
- django_cfg/apps/knowbase/services/archive/chunking/json_chunker.py +4 -3
- django_cfg/apps/knowbase/services/archive/chunking/markdown_chunker.py +5 -4
- django_cfg/apps/knowbase/services/archive/chunking/python_chunker.py +6 -5
- django_cfg/apps/knowbase/services/archive/chunking/text_chunker.py +4 -3
- django_cfg/apps/knowbase/services/archive/chunking_service.py +3 -7
- django_cfg/apps/knowbase/services/archive/context/__init__.py +1 -1
- django_cfg/apps/knowbase/services/archive/context/builders.py +2 -1
- django_cfg/apps/knowbase/services/archive/context/models.py +2 -1
- django_cfg/apps/knowbase/services/archive/exceptions.py +5 -5
- django_cfg/apps/knowbase/services/archive/extraction_service.py +111 -110
- django_cfg/apps/knowbase/services/archive/vectorization_service.py +80 -77
- django_cfg/apps/knowbase/services/base.py +11 -9
- django_cfg/apps/knowbase/services/chat_service.py +40 -39
- django_cfg/apps/knowbase/services/document_service.py +28 -27
- django_cfg/apps/knowbase/services/embedding/__init__.py +9 -9
- django_cfg/apps/knowbase/services/embedding/async_processor.py +38 -40
- django_cfg/apps/knowbase/services/embedding/batch_processor.py +45 -42
- django_cfg/apps/knowbase/services/embedding/batch_result.py +7 -6
- django_cfg/apps/knowbase/services/embedding/models.py +52 -51
- django_cfg/apps/knowbase/services/embedding/processors.py +24 -23
- django_cfg/apps/knowbase/services/embedding/utils.py +17 -17
- django_cfg/apps/knowbase/services/prompt_builder.py +24 -23
- django_cfg/apps/knowbase/services/search_service.py +52 -49
- django_cfg/apps/knowbase/signals/__init__.py +2 -5
- django_cfg/apps/knowbase/signals/archive_signals.py +35 -34
- django_cfg/apps/knowbase/signals/chat_signals.py +6 -5
- django_cfg/apps/knowbase/signals/document_signals.py +22 -22
- django_cfg/apps/knowbase/signals/external_data_signals.py +22 -22
- django_cfg/apps/knowbase/tasks/__init__.py +6 -7
- django_cfg/apps/knowbase/tasks/archive_tasks.py +41 -41
- django_cfg/apps/knowbase/tasks/document_processing.py +49 -44
- django_cfg/apps/knowbase/tasks/external_data_tasks.py +46 -44
- django_cfg/apps/knowbase/tasks/maintenance.py +26 -24
- django_cfg/apps/knowbase/urls.py +3 -2
- django_cfg/apps/knowbase/urls_admin.py +6 -3
- django_cfg/apps/knowbase/urls_system.py +4 -5
- django_cfg/apps/knowbase/utils/chunk_settings.py +22 -20
- django_cfg/apps/knowbase/utils/text_processing.py +76 -75
- django_cfg/apps/knowbase/utils/validation.py +9 -9
- django_cfg/apps/knowbase/views/__init__.py +5 -5
- django_cfg/apps/knowbase/views/archive_views.py +90 -87
- django_cfg/apps/knowbase/views/base.py +9 -12
- django_cfg/apps/knowbase/views/chat_views.py +32 -32
- django_cfg/apps/knowbase/views/document_views.py +27 -28
- django_cfg/apps/knowbase/views/public_views.py +19 -19
- django_cfg/apps/leads/admin/leads_admin.py +41 -45
- django_cfg/apps/leads/admin/resources.py +14 -14
- django_cfg/apps/leads/admin.py +7 -9
- django_cfg/apps/leads/apps.py +1 -1
- django_cfg/apps/leads/models.py +17 -17
- django_cfg/apps/leads/serializers.py +5 -4
- django_cfg/apps/leads/signals.py +7 -7
- django_cfg/apps/leads/tests.py +47 -47
- django_cfg/apps/leads/urls.py +2 -2
- django_cfg/apps/leads/views.py +11 -11
- django_cfg/apps/maintenance/__init__.py +3 -3
- django_cfg/apps/maintenance/admin/__init__.py +1 -1
- django_cfg/apps/maintenance/admin/api_key_admin.py +36 -36
- django_cfg/apps/maintenance/admin/log_admin.py +35 -37
- django_cfg/apps/maintenance/admin/scheduled_admin.py +47 -51
- django_cfg/apps/maintenance/admin/site_admin.py +49 -52
- django_cfg/apps/maintenance/apps.py +2 -2
- django_cfg/apps/maintenance/management/commands/maintenance.py +53 -52
- django_cfg/apps/maintenance/management/commands/process_scheduled_maintenance.py +44 -44
- django_cfg/apps/maintenance/management/commands/sync_cloudflare.py +32 -32
- django_cfg/apps/maintenance/managers/__init__.py +1 -1
- django_cfg/apps/maintenance/managers/cloudflare_site_manager.py +39 -38
- django_cfg/apps/maintenance/managers/maintenance_log_manager.py +32 -31
- django_cfg/apps/maintenance/migrations/0001_initial.py +1 -0
- django_cfg/apps/maintenance/models/__init__.py +2 -2
- django_cfg/apps/maintenance/models/cloudflare_api_key.py +15 -15
- django_cfg/apps/maintenance/models/cloudflare_site.py +24 -22
- django_cfg/apps/maintenance/models/maintenance_log.py +15 -14
- django_cfg/apps/maintenance/models/scheduled_maintenance.py +53 -52
- django_cfg/apps/maintenance/services/__init__.py +3 -3
- django_cfg/apps/maintenance/services/bulk_operations_service.py +68 -68
- django_cfg/apps/maintenance/services/maintenance_service.py +59 -58
- django_cfg/apps/maintenance/services/scheduled_maintenance_service.py +52 -52
- django_cfg/apps/maintenance/services/site_sync_service.py +64 -65
- django_cfg/apps/maintenance/utils/__init__.py +1 -1
- django_cfg/apps/maintenance/utils/retry_utils.py +17 -17
- django_cfg/apps/newsletter/admin/__init__.py +12 -16
- django_cfg/apps/newsletter/admin/newsletter_admin.py +90 -87
- django_cfg/apps/newsletter/admin/resources.py +29 -29
- django_cfg/apps/newsletter/admin.py +39 -32
- django_cfg/apps/newsletter/management/commands/test_newsletter.py +3 -3
- django_cfg/apps/newsletter/managers/__init__.py +1 -1
- django_cfg/apps/newsletter/migrations/0001_initial.py +2 -1
- django_cfg/apps/newsletter/models.py +34 -33
- django_cfg/apps/newsletter/serializers.py +13 -13
- django_cfg/apps/newsletter/services/email_service.py +42 -40
- django_cfg/apps/newsletter/signals.py +4 -3
- django_cfg/apps/newsletter/urls.py +7 -7
- django_cfg/apps/newsletter/views/__init__.py +14 -19
- django_cfg/apps/newsletter/views/campaigns.py +19 -19
- django_cfg/apps/newsletter/views/emails.py +20 -20
- django_cfg/apps/newsletter/views/newsletters.py +5 -5
- django_cfg/apps/newsletter/views/subscriptions.py +24 -24
- django_cfg/apps/newsletter/views/tracking.py +6 -5
- django_cfg/apps/payments/admin/__init__.py +6 -5
- django_cfg/apps/payments/admin/api_keys_admin.py +43 -45
- django_cfg/apps/payments/admin/balance_admin.py +41 -47
- django_cfg/apps/payments/admin/currencies_admin.py +60 -62
- django_cfg/apps/payments/admin/endpoint_groups_admin.py +14 -28
- django_cfg/apps/payments/admin/filters.py +59 -59
- django_cfg/apps/payments/admin/networks_admin.py +36 -50
- django_cfg/apps/payments/admin/payments_admin.py +47 -49
- django_cfg/apps/payments/admin/subscriptions_admin.py +30 -32
- django_cfg/apps/payments/admin/tariffs_admin.py +37 -42
- django_cfg/apps/payments/admin_interface/serializers/__init__.py +12 -13
- django_cfg/apps/payments/admin_interface/serializers/payment_serializers.py +28 -27
- django_cfg/apps/payments/admin_interface/serializers/webhook_serializers.py +4 -5
- django_cfg/apps/payments/admin_interface/templates/payments/base.html +407 -3
- django_cfg/apps/payments/admin_interface/templates/payments/components/ngrok_status.html +13 -13
- django_cfg/apps/payments/admin_interface/templates/payments/payment_dashboard.html +5 -1
- django_cfg/apps/payments/admin_interface/templates/payments/payment_detail.html +105 -49
- django_cfg/apps/payments/admin_interface/templates/payments/payment_form.html +4 -1
- django_cfg/apps/payments/admin_interface/templates/payments/payment_list.html +16 -8
- django_cfg/apps/payments/admin_interface/templates/payments/webhook_dashboard.html +16 -8
- django_cfg/apps/payments/admin_interface/views/__init__.py +8 -9
- django_cfg/apps/payments/admin_interface/views/api/__init__.py +3 -3
- django_cfg/apps/payments/admin_interface/views/api/payments.py +52 -54
- django_cfg/apps/payments/admin_interface/views/api/stats.py +33 -30
- django_cfg/apps/payments/admin_interface/views/api/users.py +10 -11
- django_cfg/apps/payments/admin_interface/views/api/webhook_admin.py +46 -51
- django_cfg/apps/payments/admin_interface/views/api/webhook_public.py +9 -9
- django_cfg/apps/payments/admin_interface/views/base.py +17 -19
- django_cfg/apps/payments/admin_interface/views/dashboard.py +10 -10
- django_cfg/apps/payments/admin_interface/views/forms.py +21 -20
- django_cfg/apps/payments/apps.py +7 -6
- django_cfg/apps/payments/config/__init__.py +4 -4
- django_cfg/apps/payments/config/django_cfg_integration.py +22 -21
- django_cfg/apps/payments/config/helpers.py +14 -12
- django_cfg/apps/payments/management/commands/cleanup_expired_data.py +85 -86
- django_cfg/apps/payments/management/commands/currency_stats.py +84 -87
- django_cfg/apps/payments/management/commands/manage_currencies.py +59 -58
- django_cfg/apps/payments/management/commands/manage_providers.py +103 -105
- django_cfg/apps/payments/management/commands/process_pending_payments.py +67 -70
- django_cfg/apps/payments/management/commands/test_providers.py +83 -84
- django_cfg/apps/payments/middleware/__init__.py +1 -1
- django_cfg/apps/payments/middleware/api_access.py +77 -78
- django_cfg/apps/payments/middleware/rate_limiting.py +72 -72
- django_cfg/apps/payments/middleware/usage_tracking.py +66 -64
- django_cfg/apps/payments/migrations/0001_initial.py +2 -1
- django_cfg/apps/payments/models/__init__.py +11 -12
- django_cfg/apps/payments/models/api_keys.py +29 -27
- django_cfg/apps/payments/models/balance.py +38 -38
- django_cfg/apps/payments/models/base.py +12 -11
- django_cfg/apps/payments/models/currencies.py +53 -52
- django_cfg/apps/payments/models/managers/__init__.py +13 -14
- django_cfg/apps/payments/models/managers/api_key_managers.py +55 -53
- django_cfg/apps/payments/models/managers/balance_managers.py +98 -97
- django_cfg/apps/payments/models/managers/currency_managers.py +70 -69
- django_cfg/apps/payments/models/managers/payment_managers.py +113 -111
- django_cfg/apps/payments/models/managers/subscription_managers.py +99 -97
- django_cfg/apps/payments/models/payments.py +167 -73
- django_cfg/apps/payments/models/subscriptions.py +56 -54
- django_cfg/apps/payments/models/tariffs.py +35 -34
- django_cfg/apps/payments/services/__init__.py +33 -36
- django_cfg/apps/payments/services/cache/__init__.py +7 -1
- django_cfg/apps/payments/services/cache_service/__init__.py +22 -20
- django_cfg/apps/payments/services/cache_service/api_key_cache.py +6 -5
- django_cfg/apps/payments/services/cache_service/interfaces.py +5 -5
- django_cfg/apps/payments/services/cache_service/keys.py +8 -8
- django_cfg/apps/payments/services/cache_service/rate_limit_cache.py +8 -7
- django_cfg/apps/payments/services/cache_service/simple_cache.py +17 -14
- django_cfg/apps/payments/services/core/__init__.py +3 -3
- django_cfg/apps/payments/services/core/balance_service.py +69 -65
- django_cfg/apps/payments/services/core/base.py +25 -22
- django_cfg/apps/payments/services/core/currency/__init__.py +1 -1
- django_cfg/apps/payments/services/core/currency/currency_converter.py +2 -0
- django_cfg/apps/payments/services/core/currency_service.py +68 -66
- django_cfg/apps/payments/services/core/operations/__init__.py +1 -1
- django_cfg/apps/payments/services/core/operations/payment_canceller.py +2 -1
- django_cfg/apps/payments/services/core/operations/payment_creator.py +2 -1
- django_cfg/apps/payments/services/core/operations/status_checker.py +2 -1
- django_cfg/apps/payments/services/core/payment_service.py +10 -7
- django_cfg/apps/payments/services/core/providers/provider_client.py +2 -2
- django_cfg/apps/payments/services/core/subscription_service.py +77 -74
- django_cfg/apps/payments/services/core/utils/data_converter.py +1 -0
- django_cfg/apps/payments/services/core/utils/statistics_calculator.py +1 -0
- django_cfg/apps/payments/services/core/webhook_service.py +67 -63
- django_cfg/apps/payments/services/integrations/__init__.py +3 -3
- django_cfg/apps/payments/services/integrations/ngrok_service.py +1 -0
- django_cfg/apps/payments/services/integrations/providers_config.py +3 -2
- django_cfg/apps/payments/services/providers/base.py +59 -57
- django_cfg/apps/payments/services/providers/models/__init__.py +7 -14
- django_cfg/apps/payments/services/providers/models/base.py +15 -15
- django_cfg/apps/payments/services/providers/models/providers.py +13 -12
- django_cfg/apps/payments/services/providers/models/universal.py +6 -5
- django_cfg/apps/payments/services/providers/nowpayments/__init__.py +4 -4
- django_cfg/apps/payments/services/providers/nowpayments/config.py +9 -8
- django_cfg/apps/payments/services/providers/nowpayments/models.py +15 -15
- django_cfg/apps/payments/services/providers/nowpayments/parsers/data/__init__.py +2 -2
- django_cfg/apps/payments/services/providers/nowpayments/parsers/data/patterns.py +26 -26
- django_cfg/apps/payments/services/providers/nowpayments/parsers/parser.py +3 -2
- django_cfg/apps/payments/services/providers/nowpayments/provider.py +95 -99
- django_cfg/apps/payments/services/providers/nowpayments/sync.py +41 -40
- django_cfg/apps/payments/services/providers/registry.py +65 -63
- django_cfg/apps/payments/services/providers/sync_service.py +50 -50
- django_cfg/apps/payments/services/types/__init__.py +21 -22
- django_cfg/apps/payments/services/types/data.py +14 -13
- django_cfg/apps/payments/services/types/requests.py +21 -22
- django_cfg/apps/payments/services/types/responses.py +16 -15
- django_cfg/apps/payments/services/types/webhooks.py +30 -30
- django_cfg/apps/payments/signals/__init__.py +4 -6
- django_cfg/apps/payments/signals/api_key_signals.py +33 -32
- django_cfg/apps/payments/signals/balance_signals.py +28 -26
- django_cfg/apps/payments/signals/payment_signals.py +29 -28
- django_cfg/apps/payments/signals/subscription_signals.py +39 -38
- django_cfg/apps/payments/static/payments/js/ngrok-status.js +12 -8
- django_cfg/apps/payments/static/payments/js/payment-detail.js +1 -1
- django_cfg/apps/payments/static/payments/js/payment-form.js +3 -3
- django_cfg/apps/payments/static/payments/js/payment-list.js +13 -6
- django_cfg/apps/payments/static/payments/js/webhook-dashboard-mjs.js +241 -0
- django_cfg/apps/payments/tasks/__init__.py +11 -12
- django_cfg/apps/payments/tasks/types.py +10 -9
- django_cfg/apps/payments/tasks/usage_tracking.py +44 -46
- django_cfg/apps/payments/templatetags/payment_tags.py +27 -27
- django_cfg/apps/payments/urls.py +31 -14
- django_cfg/apps/payments/urls_admin.py +10 -10
- django_cfg/apps/payments/views/api/__init__.py +32 -33
- django_cfg/apps/payments/views/api/api_keys.py +62 -62
- django_cfg/apps/payments/views/api/balances.py +63 -64
- django_cfg/apps/payments/views/api/base.py +52 -52
- django_cfg/apps/payments/views/api/currencies.py +75 -63
- django_cfg/apps/payments/views/api/payments.py +73 -74
- django_cfg/apps/payments/views/api/subscriptions.py +71 -72
- django_cfg/apps/payments/views/api/webhooks.py +85 -84
- django_cfg/apps/payments/views/overview/__init__.py +7 -7
- django_cfg/apps/payments/views/overview/serializers.py +13 -14
- django_cfg/apps/payments/views/overview/services.py +66 -67
- django_cfg/apps/payments/views/overview/urls.py +2 -1
- django_cfg/apps/payments/views/overview/views.py +31 -31
- django_cfg/apps/payments/views/serializers/__init__.py +35 -36
- django_cfg/apps/payments/views/serializers/api_keys.py +59 -57
- django_cfg/apps/payments/views/serializers/balances.py +34 -33
- django_cfg/apps/payments/views/serializers/currencies.py +36 -34
- django_cfg/apps/payments/views/serializers/payments.py +48 -47
- django_cfg/apps/payments/views/serializers/subscriptions.py +50 -45
- django_cfg/apps/payments/views/serializers/webhooks.py +17 -16
- django_cfg/apps/support/admin/__init__.py +3 -3
- django_cfg/apps/support/admin/resources.py +26 -26
- django_cfg/apps/support/admin/support_admin.py +44 -48
- django_cfg/apps/support/admin.py +16 -15
- django_cfg/apps/support/apps.py +1 -1
- django_cfg/apps/support/managers/message_manager.py +4 -4
- django_cfg/apps/support/managers/ticket_manager.py +13 -12
- django_cfg/apps/support/migrations/0001_initial.py +2 -1
- django_cfg/apps/support/models.py +3 -1
- django_cfg/apps/support/serializers.py +4 -2
- django_cfg/apps/support/signals.py +12 -10
- django_cfg/apps/support/urls.py +4 -3
- django_cfg/apps/support/utils/support_email_service.py +11 -9
- django_cfg/apps/support/views/__init__.py +3 -3
- django_cfg/apps/support/views/admin.py +9 -9
- django_cfg/apps/support/views/api.py +10 -9
- django_cfg/apps/support/views/chat.py +14 -14
- django_cfg/apps/tasks/admin/tasks_admin.py +65 -74
- django_cfg/apps/tasks/apps.py +2 -2
- django_cfg/apps/tasks/serializers.py +6 -6
- django_cfg/apps/tasks/static/tasks/js/dashboard/main.mjs +44 -20
- django_cfg/apps/tasks/static/tasks/js/dashboard/overview.mjs +7 -5
- django_cfg/apps/tasks/static/tasks/js/dashboard/queues.mjs +5 -3
- django_cfg/apps/tasks/static/tasks/js/dashboard/tasks.mjs +5 -3
- django_cfg/apps/tasks/static/tasks/js/dashboard/workers.mjs +5 -3
- django_cfg/apps/tasks/tasks/demo_tasks.py +12 -11
- django_cfg/apps/tasks/templates/tasks/components/tasks_mjs_integration.html +269 -0
- django_cfg/apps/tasks/templates/tasks/pages/dashboard-improved.html +168 -0
- django_cfg/apps/tasks/templates/tasks/pages/dashboard.html +21 -2
- django_cfg/apps/tasks/urls.py +3 -2
- django_cfg/apps/tasks/urls_admin.py +1 -0
- django_cfg/apps/tasks/utils/simulator.py +49 -52
- django_cfg/apps/tasks/views/api.py +75 -73
- django_cfg/apps/tasks/views/dashboard.py +5 -4
- django_cfg/apps/urls.py +20 -11
- django_cfg/apps.py +6 -5
- django_cfg/cli/commands/create_project.py +7 -6
- django_cfg/cli/commands/info.py +25 -25
- django_cfg/cli/utils.py +27 -27
- django_cfg/config.py +1 -1
- django_cfg/core/__init__.py +8 -8
- django_cfg/core/base/config_model.py +13 -12
- django_cfg/core/builders/apps_builder.py +2 -2
- django_cfg/core/builders/middleware_builder.py +1 -1
- django_cfg/core/builders/security_builder.py +1 -1
- django_cfg/core/config.py +2 -2
- django_cfg/core/environment/detector.py +27 -28
- django_cfg/core/exceptions.py +1 -1
- django_cfg/core/generation/core_generators/settings.py +1 -1
- django_cfg/core/generation/core_generators/static.py +11 -5
- django_cfg/core/generation/core_generators/templates.py +1 -1
- django_cfg/core/generation/data_generators/__init__.py +1 -1
- django_cfg/core/generation/data_generators/cache.py +1 -1
- django_cfg/core/generation/data_generators/database.py +1 -1
- django_cfg/core/generation/generation.py +1 -3
- django_cfg/core/generation/integration_generators/__init__.py +2 -2
- django_cfg/core/generation/integration_generators/api.py +12 -2
- django_cfg/core/generation/integration_generators/sessions.py +1 -1
- django_cfg/core/generation/integration_generators/tailwind.py +1 -1
- django_cfg/core/generation/integration_generators/tasks.py +1 -1
- django_cfg/core/generation/integration_generators/third_party.py +1 -1
- django_cfg/core/generation/orchestrator.py +1 -1
- django_cfg/core/generation/protocols.py +1 -1
- django_cfg/core/generation/utility_generators/__init__.py +1 -1
- django_cfg/core/generation/utility_generators/email.py +1 -1
- django_cfg/core/generation/utility_generators/i18n.py +1 -1
- django_cfg/core/generation/utility_generators/limits.py +1 -1
- django_cfg/core/generation/utility_generators/logging.py +1 -1
- django_cfg/core/generation/utility_generators/security.py +1 -1
- django_cfg/core/generation/utils/helpers.py +1 -1
- django_cfg/core/integration/__init__.py +5 -5
- django_cfg/core/integration/commands_collector.py +38 -39
- django_cfg/core/integration/display/__init__.py +2 -2
- django_cfg/core/integration/display/base.py +30 -30
- django_cfg/core/integration/display/ngrok.py +35 -36
- django_cfg/core/integration/display/startup.py +149 -139
- django_cfg/core/integration/url_integration.py +10 -10
- django_cfg/core/integration/version_checker.py +20 -19
- django_cfg/core/services/config_service.py +4 -4
- django_cfg/core/state/__init__.py +1 -1
- django_cfg/core/state/registry.py +1 -1
- django_cfg/core/types/__init__.py +8 -1
- django_cfg/core/validation.py +36 -39
- django_cfg/management/commands/check_endpoints.py +3 -1
- django_cfg/management/commands/check_settings.py +3 -1
- django_cfg/management/commands/clear_constance.py +3 -1
- django_cfg/management/commands/create_token.py +3 -1
- django_cfg/management/commands/generate_clients.py +3 -1
- django_cfg/management/commands/migrate_all.py +3 -1
- django_cfg/management/commands/rundramatiq.py +3 -1
- django_cfg/management/commands/rundramatiq_simulator.py +3 -1
- django_cfg/management/commands/runserver_ngrok.py +3 -1
- django_cfg/management/commands/show_config.py +3 -1
- django_cfg/management/commands/superuser.py +3 -1
- django_cfg/management/commands/task_clear.py +3 -1
- django_cfg/management/commands/task_status.py +3 -1
- django_cfg/management/commands/test_email.py +3 -1
- django_cfg/management/commands/test_telegram.py +3 -1
- django_cfg/management/commands/test_twilio.py +3 -1
- django_cfg/management/commands/validate_openapi.py +3 -1
- django_cfg/middleware/pagination.py +8 -8
- django_cfg/middleware/public_endpoints.py +24 -23
- django_cfg/middleware/user_activity.py +27 -25
- django_cfg/models/__init__.py +19 -20
- django_cfg/models/api/__init__.py +4 -4
- django_cfg/models/api/config.py +23 -21
- django_cfg/models/api/cors.py +17 -16
- django_cfg/models/api/drf/__init__.py +1 -1
- django_cfg/models/api/drf/config.py +2 -1
- django_cfg/models/api/drf/redoc.py +2 -1
- django_cfg/models/api/drf/spectacular.py +4 -2
- django_cfg/models/api/drf/swagger.py +2 -1
- django_cfg/models/api/jwt.py +37 -36
- django_cfg/models/api/keys.py +13 -12
- django_cfg/models/api/limits.py +31 -30
- django_cfg/models/base/config.py +40 -41
- django_cfg/models/base/module.py +8 -8
- django_cfg/models/django/__init__.py +1 -1
- django_cfg/models/django/constance.py +8 -7
- django_cfg/models/django/environment.py +5 -3
- django_cfg/models/django/openapi.py +6 -16
- django_cfg/models/django/revolution_legacy.py +17 -16
- django_cfg/models/infrastructure/__init__.py +1 -1
- django_cfg/models/infrastructure/cache.py +46 -45
- django_cfg/models/infrastructure/database/config.py +4 -6
- django_cfg/models/infrastructure/database/converters.py +1 -1
- django_cfg/models/infrastructure/database/parsers.py +1 -1
- django_cfg/models/infrastructure/database/validators.py +1 -1
- django_cfg/models/infrastructure/logging.py +59 -57
- django_cfg/models/infrastructure/security.py +26 -24
- django_cfg/models/ngrok/auth.py +2 -1
- django_cfg/models/ngrok/config.py +3 -2
- django_cfg/models/ngrok/tunnel.py +2 -1
- django_cfg/models/payments/__init__.py +1 -1
- django_cfg/models/payments/api_keys.py +3 -1
- django_cfg/models/payments/config.py +4 -1
- django_cfg/models/payments/providers/base.py +2 -1
- django_cfg/models/payments/providers/nowpayments.py +3 -1
- django_cfg/models/services/__init__.py +1 -1
- django_cfg/models/services/base.py +2 -1
- django_cfg/models/services/email.py +28 -26
- django_cfg/models/services/telegram.py +2 -1
- django_cfg/models/tasks/__init__.py +2 -2
- django_cfg/models/tasks/backends.py +4 -3
- django_cfg/models/tasks/config.py +6 -4
- django_cfg/models/tasks/utils.py +3 -3
- django_cfg/modules/base.py +18 -17
- django_cfg/modules/django_admin/__init__.py +14 -15
- django_cfg/modules/django_admin/decorators/__init__.py +1 -1
- django_cfg/modules/django_admin/decorators/actions.py +8 -7
- django_cfg/modules/django_admin/decorators/display.py +9 -7
- django_cfg/modules/django_admin/icons/__init__.py +1 -1
- django_cfg/modules/django_admin/icons/constants.py +27 -27
- django_cfg/modules/django_admin/icons/generate_icons.py +54 -54
- django_cfg/modules/django_admin/management/commands/check_endpoints.py +5 -3
- django_cfg/modules/django_admin/management/commands/check_settings.py +40 -44
- django_cfg/modules/django_admin/management/commands/clear_constance.py +29 -30
- django_cfg/modules/django_admin/management/commands/create_token.py +42 -42
- django_cfg/modules/django_admin/management/commands/list_urls.py +37 -38
- django_cfg/modules/django_admin/management/commands/migrate_all.py +13 -15
- django_cfg/modules/django_admin/management/commands/migrator.py +17 -17
- django_cfg/modules/django_admin/management/commands/script.py +58 -60
- django_cfg/modules/django_admin/management/commands/show_config.py +32 -30
- django_cfg/modules/django_admin/management/commands/show_urls.py +46 -44
- django_cfg/modules/django_admin/management/commands/superuser.py +47 -48
- django_cfg/modules/django_admin/management/commands/tree.py +50 -54
- django_cfg/modules/django_admin/mixins/display_mixin.py +16 -15
- django_cfg/modules/django_admin/mixins/optimization_mixin.py +9 -8
- django_cfg/modules/django_admin/mixins/standalone_actions_mixin.py +25 -24
- django_cfg/modules/django_admin/models/__init__.py +4 -4
- django_cfg/modules/django_admin/models/action_models.py +3 -1
- django_cfg/modules/django_admin/models/badge_models.py +4 -2
- django_cfg/modules/django_admin/models/base.py +3 -3
- django_cfg/modules/django_admin/models/display_models.py +1 -0
- django_cfg/modules/django_admin/utils/badges.py +27 -26
- django_cfg/modules/django_admin/utils/displays.py +49 -49
- django_cfg/modules/django_client/apps.py +21 -3
- django_cfg/modules/django_client/core/__init__.py +9 -10
- django_cfg/modules/django_client/core/archive/manager.py +2 -2
- django_cfg/modules/django_client/core/cli/main.py +1 -3
- django_cfg/modules/django_client/core/config/config.py +3 -1
- django_cfg/modules/django_client/core/config/group.py +1 -0
- django_cfg/modules/django_client/core/config/service.py +2 -1
- django_cfg/modules/django_client/core/generator/__init__.py +1 -1
- django_cfg/modules/django_client/core/generator/base.py +2 -2
- django_cfg/modules/django_client/core/generator/python/async_client_gen.py +1 -1
- django_cfg/modules/django_client/core/generator/python/files_generator.py +1 -1
- django_cfg/modules/django_client/core/generator/python/generator.py +4 -4
- django_cfg/modules/django_client/core/generator/python/models_generator.py +1 -1
- django_cfg/modules/django_client/core/generator/python/operations_generator.py +2 -2
- django_cfg/modules/django_client/core/generator/python/sync_client_gen.py +1 -1
- django_cfg/modules/django_client/core/generator/typescript/client_generator.py +3 -1
- django_cfg/modules/django_client/core/generator/typescript/fetchers_generator.py +14 -13
- django_cfg/modules/django_client/core/generator/typescript/files_generator.py +1 -0
- django_cfg/modules/django_client/core/generator/typescript/generator.py +6 -6
- django_cfg/modules/django_client/core/generator/typescript/hooks_generator.py +12 -10
- django_cfg/modules/django_client/core/generator/typescript/models_generator.py +2 -1
- django_cfg/modules/django_client/core/generator/typescript/naming.py +2 -3
- django_cfg/modules/django_client/core/generator/typescript/operations_generator.py +12 -10
- django_cfg/modules/django_client/core/generator/typescript/schemas_generator.py +3 -2
- django_cfg/modules/django_client/core/generator/typescript/templates/client/client.ts.jinja +14 -6
- django_cfg/modules/django_client/core/generator/typescript/templates/main_index.ts.jinja +4 -10
- django_cfg/modules/django_client/core/groups/__init__.py +1 -1
- django_cfg/modules/django_client/core/groups/detector.py +2 -1
- django_cfg/modules/django_client/core/groups/manager.py +2 -1
- django_cfg/modules/django_client/core/ir/schema.py +1 -1
- django_cfg/modules/django_client/core/parser/base.py +0 -2
- django_cfg/modules/django_client/core/parser/models/schema.py +1 -1
- django_cfg/modules/django_client/core/validation/__init__.py +1 -1
- django_cfg/modules/django_client/core/validation/fixer.py +1 -2
- django_cfg/modules/django_client/core/validation/reporter.py +2 -2
- django_cfg/modules/django_client/core/validation/safety.py +1 -1
- django_cfg/modules/django_client/management/commands/generate_client.py +14 -11
- django_cfg/modules/django_client/management/commands/validate_openapi.py +4 -6
- django_cfg/modules/django_client/spectacular/__init__.py +1 -1
- django_cfg/modules/django_client/spectacular/async_detection.py +3 -2
- django_cfg/modules/django_client/spectacular/enum_naming.py +1 -1
- django_cfg/modules/django_client/spectacular/schema.py +5 -5
- django_cfg/modules/django_client/system/__init__.py +24 -0
- django_cfg/modules/django_client/system/base_generator.py +123 -0
- django_cfg/modules/django_client/system/generate_mjs_clients.py +174 -0
- django_cfg/modules/django_client/system/mjs_generator.py +219 -0
- django_cfg/modules/django_client/system/schema_parser.py +195 -0
- django_cfg/modules/django_client/system/templates/api_client.js.j2 +87 -0
- django_cfg/modules/django_client/system/templates/app_index.js.j2 +13 -0
- django_cfg/modules/django_client/system/templates/base_client.js.j2 +166 -0
- django_cfg/modules/django_client/system/templates/main_index.js.j2 +80 -0
- django_cfg/modules/django_client/system/templates/types.js.j2 +24 -0
- django_cfg/modules/django_client/urls.py +3 -2
- django_cfg/modules/django_currency/__init__.py +17 -18
- django_cfg/modules/django_currency/clients/__init__.py +2 -2
- django_cfg/modules/django_currency/clients/coinpaprika_client.py +48 -48
- django_cfg/modules/django_currency/clients/hybrid_client.py +76 -75
- django_cfg/modules/django_currency/core/__init__.py +7 -13
- django_cfg/modules/django_currency/core/converter.py +25 -24
- django_cfg/modules/django_currency/core/models.py +9 -8
- django_cfg/modules/django_currency/database/__init__.py +4 -4
- django_cfg/modules/django_currency/database/database_loader.py +65 -66
- django_cfg/modules/django_currency/examples/example_database_usage.py +29 -28
- django_cfg/modules/django_currency/utils/cache.py +10 -11
- django_cfg/modules/django_dashboard/__init__.py +4 -5
- django_cfg/modules/django_dashboard/components.py +11 -7
- django_cfg/modules/django_dashboard/debug.py +1 -3
- django_cfg/modules/django_dashboard/management/commands/debug_dashboard.py +3 -3
- django_cfg/modules/django_dashboard/sections/base.py +2 -1
- django_cfg/modules/django_dashboard/sections/commands.py +3 -2
- django_cfg/modules/django_dashboard/sections/documentation.py +8 -6
- django_cfg/modules/django_dashboard/sections/overview.py +13 -9
- django_cfg/modules/django_dashboard/sections/stats.py +2 -2
- django_cfg/modules/django_dashboard/sections/system.py +2 -1
- django_cfg/modules/django_drf_theme/templatetags/tailwind_tags.py +12 -4
- django_cfg/modules/django_email/management/commands/test_email.py +8 -7
- django_cfg/modules/django_email/service.py +5 -4
- django_cfg/modules/django_health/service.py +46 -44
- django_cfg/modules/django_import_export/__init__.py +7 -3
- django_cfg/modules/django_llm/__init__.py +3 -2
- django_cfg/modules/django_llm/example.py +58 -56
- django_cfg/modules/django_llm/llm/__init__.py +1 -1
- django_cfg/modules/django_llm/llm/cache.py +21 -20
- django_cfg/modules/django_llm/llm/client.py +9 -9
- django_cfg/modules/django_llm/llm/costs.py +14 -14
- django_cfg/modules/django_llm/llm/embeddings/__init__.py +1 -1
- django_cfg/modules/django_llm/llm/embeddings/mock_embedder.py +1 -2
- django_cfg/modules/django_llm/llm/embeddings/openai_embedder.py +1 -2
- django_cfg/modules/django_llm/llm/extractor.py +8 -8
- django_cfg/modules/django_llm/llm/models.py +5 -5
- django_cfg/modules/django_llm/llm/models_api/models_query.py +2 -2
- django_cfg/modules/django_llm/llm/models_cache.py +91 -92
- django_cfg/modules/django_llm/llm/providers/config_builder.py +1 -1
- django_cfg/modules/django_llm/llm/providers/provider_manager.py +2 -1
- django_cfg/modules/django_llm/llm/requests/cache_manager.py +1 -1
- django_cfg/modules/django_llm/llm/requests/chat_handler.py +2 -2
- django_cfg/modules/django_llm/llm/requests/embedding_handler.py +1 -1
- django_cfg/modules/django_llm/llm/responses/response_builder.py +2 -2
- django_cfg/modules/django_llm/llm/stats/stats_manager.py +1 -1
- django_cfg/modules/django_llm/llm/tokenizer.py +10 -9
- django_cfg/modules/django_llm/translator/__init__.py +1 -1
- django_cfg/modules/django_llm/translator/cache.py +36 -35
- django_cfg/modules/django_llm/translator/detectors/__init__.py +1 -1
- django_cfg/modules/django_llm/translator/detectors/script_detector.py +0 -1
- django_cfg/modules/django_llm/translator/stats/stats_tracker.py +1 -1
- django_cfg/modules/django_llm/translator/translator.py +5 -4
- django_cfg/modules/django_llm/translator/translators/__init__.py +1 -1
- django_cfg/modules/django_llm/translator/translators/json_translator.py +1 -1
- django_cfg/modules/django_llm/translator/utils/__init__.py +1 -1
- django_cfg/modules/django_llm/translator/utils/prompt_builder.py +0 -1
- django_cfg/modules/django_logging/__init__.py +1 -1
- django_cfg/modules/django_logging/django_logger.py +33 -34
- django_cfg/modules/django_logging/logger.py +3 -7
- django_cfg/modules/django_ngrok/__init__.py +7 -7
- django_cfg/modules/django_ngrok/management/commands/runserver_ngrok.py +33 -30
- django_cfg/modules/django_ngrok/service.py +33 -32
- django_cfg/modules/django_tailwind/templates/django_tailwind/base.html +4 -36
- django_cfg/modules/django_tailwind/templates/django_tailwind/components/navbar.html +1 -1
- django_cfg/modules/django_tasks/__init__.py +5 -5
- django_cfg/modules/django_tasks/dramatiq_setup.py +1 -1
- django_cfg/modules/django_tasks/factory.py +1 -1
- django_cfg/modules/django_tasks/management/commands/rundramatiq.py +39 -40
- django_cfg/modules/django_tasks/management/commands/rundramatiq_simulator.py +79 -80
- django_cfg/modules/django_tasks/management/commands/task_clear.py +34 -34
- django_cfg/modules/django_tasks/management/commands/task_status.py +34 -34
- django_cfg/modules/django_tasks/service.py +4 -3
- django_cfg/modules/django_tasks/settings.py +1 -1
- django_cfg/modules/django_telegram/__init__.py +4 -4
- django_cfg/modules/django_telegram/management/commands/test_telegram.py +4 -5
- django_cfg/modules/django_telegram/service.py +4 -3
- django_cfg/modules/django_telegram/utils.py +1 -1
- django_cfg/modules/django_twilio/__init__.py +15 -16
- django_cfg/modules/django_twilio/_imports.py +1 -1
- django_cfg/modules/django_twilio/base.py +9 -5
- django_cfg/modules/django_twilio/email_otp.py +4 -3
- django_cfg/modules/django_twilio/exceptions.py +36 -36
- django_cfg/modules/django_twilio/management/commands/test_twilio.py +6 -7
- django_cfg/modules/django_twilio/models.py +54 -53
- django_cfg/modules/django_twilio/sendgrid_service.py +70 -72
- django_cfg/modules/django_twilio/simple_service.py +42 -41
- django_cfg/modules/django_twilio/sms.py +1 -0
- django_cfg/modules/django_twilio/twilio_service.py +79 -83
- django_cfg/modules/django_twilio/unified.py +6 -5
- django_cfg/modules/django_twilio/utils.py +2 -3
- django_cfg/modules/django_twilio/whatsapp.py +3 -2
- django_cfg/modules/django_unfold/__init__.py +7 -6
- django_cfg/modules/django_unfold/callbacks/actions.py +6 -5
- django_cfg/modules/django_unfold/callbacks/apizones.py +122 -0
- django_cfg/modules/django_unfold/callbacks/base.py +9 -8
- django_cfg/modules/django_unfold/callbacks/charts.py +36 -37
- django_cfg/modules/django_unfold/callbacks/commands.py +2 -2
- django_cfg/modules/django_unfold/callbacks/main.py +27 -27
- django_cfg/modules/django_unfold/callbacks/statistics.py +12 -12
- django_cfg/modules/django_unfold/callbacks/system.py +5 -5
- django_cfg/modules/django_unfold/callbacks/users.py +4 -4
- django_cfg/modules/django_unfold/dashboard.py +29 -29
- django_cfg/modules/django_unfold/models/__init__.py +23 -8
- django_cfg/modules/django_unfold/models/config.py +84 -81
- django_cfg/modules/django_unfold/models/dashboard.py +20 -19
- django_cfg/modules/django_unfold/models/dropdown.py +6 -4
- django_cfg/modules/django_unfold/models/navigation.py +6 -4
- django_cfg/modules/django_unfold/models/tabs.py +4 -3
- django_cfg/modules/django_unfold/models.py +2 -3
- django_cfg/modules/django_unfold/system_monitor.py +27 -25
- django_cfg/modules/django_unfold/tailwind.py +12 -14
- django_cfg/modules/django_unfold/utils.py +7 -6
- django_cfg/pyproject.toml +1 -1
- django_cfg/registry/__init__.py +3 -3
- django_cfg/registry/core.py +8 -8
- django_cfg/registry/modules.py +2 -2
- django_cfg/registry/services.py +2 -2
- django_cfg/registry/third_party.py +3 -3
- django_cfg/routing/__init__.py +3 -3
- django_cfg/routing/callbacks.py +27 -26
- django_cfg/routing/routers.py +2 -2
- django_cfg/static/js/api/accounts/client.mjs +69 -0
- django_cfg/static/js/api/accounts/index.mjs +13 -0
- django_cfg/static/js/api/base.mjs +166 -0
- django_cfg/static/js/api/index.mjs +100 -0
- django_cfg/static/js/api/ipc/client.mjs +74 -0
- django_cfg/static/js/api/ipc/index.mjs +13 -0
- django_cfg/static/js/api/leads/client.mjs +71 -0
- django_cfg/static/js/api/leads/index.mjs +13 -0
- django_cfg/static/js/api/newsletter/client.mjs +109 -0
- django_cfg/static/js/api/newsletter/index.mjs +13 -0
- django_cfg/static/js/api/payments/client.mjs +1264 -0
- django_cfg/static/js/api/payments/index.mjs +13 -0
- django_cfg/static/js/api/support/client.mjs +84 -0
- django_cfg/static/js/api/support/index.mjs +13 -0
- django_cfg/static/js/api/tasks/client.mjs +74 -0
- django_cfg/static/js/api/tasks/index.mjs +13 -0
- django_cfg/static/js/api/types.mjs +729 -0
- django_cfg/static/js/api-loader.mjs +169 -0
- django_cfg/templates/admin/snippets/zones/zones_table.html +4 -3
- django_cfg/templatetags/django_cfg.py +4 -4
- django_cfg/utils/path_resolution.py +49 -50
- django_cfg/utils/smart_defaults.py +27 -29
- django_cfg/utils/version_check.py +14 -14
- {django_cfg-1.4.21.dist-info → django_cfg-1.4.24.dist-info}/METADATA +1 -1
- django_cfg-1.4.24.dist-info/RECORD +1137 -0
- django_cfg/apps/payments/static/payments/js/api-client.js +0 -408
- django_cfg/modules/django_ipc_client/dashboard/README.md +0 -517
- django_cfg/modules/django_ipc_client/dashboard/UNFOLD_INTEGRATION.md +0 -439
- django_cfg/modules/django_ipc_client/dashboard/__init__.py +0 -11
- django_cfg/modules/django_ipc_client/dashboard/apps.py +0 -22
- django_cfg/modules/django_ipc_client/dashboard/templates/django_ipc_dashboard/dashboard.html +0 -200
- django_cfg/modules/django_ipc_client/dashboard/urls.py +0 -22
- django_cfg/modules/django_ipc_client/dashboard/urls_admin.py +0 -9
- django_cfg/modules/django_ipc_client/dashboard/views.py +0 -251
- django_cfg/modules/django_rpc_old/POETRY.md +0 -344
- django_cfg/modules/django_rpc_old/README.md +0 -397
- django_cfg/modules/django_rpc_old/TESTING.md +0 -358
- django_cfg/modules/django_rpc_old/__init__.py +0 -39
- django_cfg/modules/django_rpc_old/client.py +0 -531
- django_cfg/modules/django_rpc_old/config.py +0 -279
- django_cfg/modules/django_rpc_old/exceptions.py +0 -172
- django_cfg/modules/django_unfold/callbacks/revolution.py +0 -81
- django_cfg-1.4.21.dist-info/RECORD +0 -1111
- /django_cfg/{modules/django_ipc_client → apps/ipc}/README.md +0 -0
- /django_cfg/{modules/django_ipc_client → apps/ipc/services/client}/config.py +0 -0
- {django_cfg-1.4.21.dist-info → django_cfg-1.4.24.dist-info}/WHEEL +0 -0
- {django_cfg-1.4.21.dist-info → django_cfg-1.4.24.dist-info}/entry_points.txt +0 -0
- {django_cfg-1.4.21.dist-info → django_cfg-1.4.24.dist-info}/licenses/LICENSE +0 -0
@@ -2,27 +2,27 @@
|
|
2
2
|
Email views.
|
3
3
|
"""
|
4
4
|
|
5
|
+
from drf_spectacular.utils import extend_schema
|
5
6
|
from rest_framework import generics, status
|
6
|
-
from rest_framework.response import Response
|
7
7
|
from rest_framework.permissions import AllowAny, IsAuthenticated
|
8
|
-
from
|
8
|
+
from rest_framework.response import Response
|
9
9
|
|
10
10
|
from ..models import EmailLog
|
11
|
-
from ..services.email_service import NewsletterEmailService
|
12
11
|
from ..serializers import (
|
13
|
-
|
12
|
+
BulkEmailResponseSerializer,
|
14
13
|
BulkEmailSerializer,
|
15
14
|
EmailLogSerializer,
|
16
|
-
|
15
|
+
TestEmailSerializer,
|
17
16
|
)
|
17
|
+
from ..services.email_service import NewsletterEmailService
|
18
18
|
|
19
19
|
|
20
20
|
class TestEmailView(generics.CreateAPIView):
|
21
21
|
"""Test email sending functionality."""
|
22
|
-
|
22
|
+
|
23
23
|
serializer_class = TestEmailSerializer
|
24
24
|
permission_classes = [AllowAny]
|
25
|
-
|
25
|
+
|
26
26
|
@extend_schema(
|
27
27
|
summary="Test Email Sending",
|
28
28
|
description="Send a test email to verify mailer configuration.",
|
@@ -36,14 +36,14 @@ class TestEmailView(generics.CreateAPIView):
|
|
36
36
|
def post(self, request, *args, **kwargs):
|
37
37
|
serializer = self.get_serializer(data=request.data)
|
38
38
|
serializer.is_valid(raise_exception=True)
|
39
|
-
|
39
|
+
|
40
40
|
email = serializer.validated_data['email']
|
41
41
|
subject = serializer.validated_data['subject']
|
42
42
|
message = serializer.validated_data['message']
|
43
|
-
|
43
|
+
|
44
44
|
try:
|
45
45
|
email_service = NewsletterEmailService()
|
46
|
-
|
46
|
+
|
47
47
|
result = email_service.send_bulk_email(
|
48
48
|
recipients=[email],
|
49
49
|
subject=subject,
|
@@ -51,9 +51,9 @@ class TestEmailView(generics.CreateAPIView):
|
|
51
51
|
main_text=message,
|
52
52
|
main_html_content=f"<p>{message}</p><p>If you received this email, the mailer is working correctly!</p>"
|
53
53
|
)
|
54
|
-
|
54
|
+
|
55
55
|
return Response(result, status=status.HTTP_200_OK)
|
56
|
-
|
56
|
+
|
57
57
|
except Exception as e:
|
58
58
|
error_response = {
|
59
59
|
'success': False,
|
@@ -67,10 +67,10 @@ class TestEmailView(generics.CreateAPIView):
|
|
67
67
|
|
68
68
|
class BulkEmailView(generics.CreateAPIView):
|
69
69
|
"""Send bulk emails."""
|
70
|
-
|
70
|
+
|
71
71
|
serializer_class = BulkEmailSerializer
|
72
72
|
permission_classes = [IsAuthenticated]
|
73
|
-
|
73
|
+
|
74
74
|
@extend_schema(
|
75
75
|
summary="Send Bulk Email",
|
76
76
|
description="Send bulk emails to multiple recipients using base email template.",
|
@@ -84,10 +84,10 @@ class BulkEmailView(generics.CreateAPIView):
|
|
84
84
|
def post(self, request, *args, **kwargs):
|
85
85
|
serializer = self.get_serializer(data=request.data)
|
86
86
|
serializer.is_valid(raise_exception=True)
|
87
|
-
|
87
|
+
|
88
88
|
try:
|
89
89
|
email_service = NewsletterEmailService()
|
90
|
-
|
90
|
+
|
91
91
|
result = email_service.send_bulk_email(
|
92
92
|
recipients=serializer.validated_data['recipients'],
|
93
93
|
subject=serializer.validated_data['subject'],
|
@@ -98,9 +98,9 @@ class BulkEmailView(generics.CreateAPIView):
|
|
98
98
|
button_url=serializer.validated_data.get('button_url', ''),
|
99
99
|
secondary_text=serializer.validated_data.get('secondary_text', '')
|
100
100
|
)
|
101
|
-
|
101
|
+
|
102
102
|
return Response(result, status=status.HTTP_200_OK)
|
103
|
-
|
103
|
+
|
104
104
|
except Exception as e:
|
105
105
|
error_response = {
|
106
106
|
'success': False,
|
@@ -114,11 +114,11 @@ class BulkEmailView(generics.CreateAPIView):
|
|
114
114
|
|
115
115
|
class EmailLogListView(generics.ListAPIView):
|
116
116
|
"""List email logs."""
|
117
|
-
|
117
|
+
|
118
118
|
queryset = EmailLog.objects.all()
|
119
119
|
serializer_class = EmailLogSerializer
|
120
120
|
permission_classes = [IsAuthenticated]
|
121
|
-
|
121
|
+
|
122
122
|
@extend_schema(
|
123
123
|
summary="List Email Logs",
|
124
124
|
description="Get a list of email sending logs.",
|
@@ -2,9 +2,9 @@
|
|
2
2
|
Newsletter views.
|
3
3
|
"""
|
4
4
|
|
5
|
+
from drf_spectacular.utils import extend_schema
|
5
6
|
from rest_framework import generics
|
6
7
|
from rest_framework.permissions import AllowAny
|
7
|
-
from drf_spectacular.utils import extend_schema
|
8
8
|
|
9
9
|
from ..models import Newsletter
|
10
10
|
from ..serializers import NewsletterSerializer
|
@@ -12,11 +12,11 @@ from ..serializers import NewsletterSerializer
|
|
12
12
|
|
13
13
|
class NewsletterListView(generics.ListAPIView):
|
14
14
|
"""List all active newsletters."""
|
15
|
-
|
15
|
+
|
16
16
|
queryset = Newsletter.objects.filter(is_active=True)
|
17
17
|
serializer_class = NewsletterSerializer
|
18
18
|
permission_classes = [AllowAny]
|
19
|
-
|
19
|
+
|
20
20
|
@extend_schema(
|
21
21
|
summary="List Active Newsletters",
|
22
22
|
description="Get a list of all active newsletters available for subscription.",
|
@@ -29,11 +29,11 @@ class NewsletterListView(generics.ListAPIView):
|
|
29
29
|
|
30
30
|
class NewsletterDetailView(generics.RetrieveAPIView):
|
31
31
|
"""Retrieve a specific newsletter."""
|
32
|
-
|
32
|
+
|
33
33
|
queryset = Newsletter.objects.filter(is_active=True)
|
34
34
|
serializer_class = NewsletterSerializer
|
35
35
|
permission_classes = [AllowAny]
|
36
|
-
|
36
|
+
|
37
37
|
@extend_schema(
|
38
38
|
summary="Get Newsletter Details",
|
39
39
|
description="Retrieve details of a specific newsletter.",
|
@@ -2,28 +2,28 @@
|
|
2
2
|
Subscription views.
|
3
3
|
"""
|
4
4
|
|
5
|
+
from drf_spectacular.utils import extend_schema
|
5
6
|
from rest_framework import generics, status
|
6
|
-
from rest_framework.response import Response
|
7
7
|
from rest_framework.permissions import AllowAny, IsAuthenticated
|
8
|
-
from
|
8
|
+
from rest_framework.response import Response
|
9
9
|
|
10
10
|
from ..models import Newsletter, NewsletterSubscription
|
11
11
|
from ..serializers import (
|
12
|
+
ErrorResponseSerializer,
|
12
13
|
NewsletterSubscriptionSerializer,
|
13
|
-
SubscribeSerializer,
|
14
|
-
UnsubscribeSerializer,
|
15
14
|
SubscribeResponseSerializer,
|
15
|
+
SubscribeSerializer,
|
16
16
|
SuccessResponseSerializer,
|
17
|
-
|
17
|
+
UnsubscribeSerializer,
|
18
18
|
)
|
19
19
|
|
20
20
|
|
21
21
|
class SubscribeView(generics.CreateAPIView):
|
22
22
|
"""Handle newsletter subscriptions."""
|
23
|
-
|
23
|
+
|
24
24
|
serializer_class = SubscribeSerializer
|
25
25
|
permission_classes = [AllowAny]
|
26
|
-
|
26
|
+
|
27
27
|
@extend_schema(
|
28
28
|
summary="Subscribe to Newsletter",
|
29
29
|
description="Subscribe an email address to a newsletter.",
|
@@ -38,27 +38,27 @@ class SubscribeView(generics.CreateAPIView):
|
|
38
38
|
def post(self, request, *args, **kwargs):
|
39
39
|
serializer = self.get_serializer(data=request.data)
|
40
40
|
serializer.is_valid(raise_exception=True)
|
41
|
-
|
41
|
+
|
42
42
|
newsletter_id = serializer.validated_data['newsletter_id']
|
43
43
|
email = serializer.validated_data['email']
|
44
|
-
|
44
|
+
|
45
45
|
try:
|
46
46
|
newsletter = Newsletter.objects.get(id=newsletter_id, is_active=True)
|
47
|
-
|
47
|
+
|
48
48
|
# Create or reactivate subscription
|
49
49
|
subscription, created = NewsletterSubscription.objects.get_or_create(
|
50
50
|
newsletter=newsletter,
|
51
51
|
email=email,
|
52
52
|
defaults={'is_active': True}
|
53
53
|
)
|
54
|
-
|
54
|
+
|
55
55
|
if not created and not subscription.is_active:
|
56
56
|
# Reactivate subscription
|
57
57
|
subscription.is_active = True
|
58
58
|
subscription.unsubscribed_at = None
|
59
59
|
subscription.save()
|
60
60
|
created = True
|
61
|
-
|
61
|
+
|
62
62
|
if created:
|
63
63
|
response_data = {
|
64
64
|
'success': True,
|
@@ -72,7 +72,7 @@ class SubscribeView(generics.CreateAPIView):
|
|
72
72
|
'message': 'Already subscribed to this newsletter'
|
73
73
|
}
|
74
74
|
return Response(response_data, status=status.HTTP_400_BAD_REQUEST)
|
75
|
-
|
75
|
+
|
76
76
|
except Newsletter.DoesNotExist:
|
77
77
|
return Response(
|
78
78
|
{'success': False, 'message': 'Newsletter not found'},
|
@@ -82,10 +82,10 @@ class SubscribeView(generics.CreateAPIView):
|
|
82
82
|
|
83
83
|
class UnsubscribeView(generics.UpdateAPIView):
|
84
84
|
"""Handle newsletter unsubscriptions."""
|
85
|
-
|
85
|
+
|
86
86
|
serializer_class = UnsubscribeSerializer
|
87
87
|
permission_classes = [AllowAny]
|
88
|
-
|
88
|
+
|
89
89
|
@extend_schema(
|
90
90
|
summary="Unsubscribe from Newsletter",
|
91
91
|
description="Unsubscribe from a newsletter using subscription ID.",
|
@@ -99,24 +99,24 @@ class UnsubscribeView(generics.UpdateAPIView):
|
|
99
99
|
def post(self, request, *args, **kwargs):
|
100
100
|
serializer = self.get_serializer(data=request.data)
|
101
101
|
serializer.is_valid(raise_exception=True)
|
102
|
-
|
102
|
+
|
103
103
|
subscription_id = serializer.validated_data['subscription_id']
|
104
|
-
|
104
|
+
|
105
105
|
try:
|
106
106
|
subscription = NewsletterSubscription.objects.get(
|
107
|
-
id=subscription_id,
|
107
|
+
id=subscription_id,
|
108
108
|
is_active=True
|
109
109
|
)
|
110
|
-
|
110
|
+
|
111
111
|
newsletter_title = subscription.newsletter.title
|
112
112
|
subscription.unsubscribe()
|
113
|
-
|
113
|
+
|
114
114
|
response_data = {
|
115
115
|
'success': True,
|
116
116
|
'message': f'Successfully unsubscribed from {newsletter_title}'
|
117
117
|
}
|
118
118
|
return Response(response_data, status=status.HTTP_200_OK)
|
119
|
-
|
119
|
+
|
120
120
|
except NewsletterSubscription.DoesNotExist:
|
121
121
|
return Response(
|
122
122
|
{'success': False, 'message': 'Subscription not found'},
|
@@ -126,16 +126,16 @@ class UnsubscribeView(generics.UpdateAPIView):
|
|
126
126
|
|
127
127
|
class SubscriptionListView(generics.ListAPIView):
|
128
128
|
"""List user's subscriptions."""
|
129
|
-
|
129
|
+
|
130
130
|
serializer_class = NewsletterSubscriptionSerializer
|
131
131
|
permission_classes = [IsAuthenticated]
|
132
|
-
|
132
|
+
|
133
133
|
def get_queryset(self):
|
134
134
|
return NewsletterSubscription.objects.filter(
|
135
135
|
user=self.request.user,
|
136
136
|
is_active=True
|
137
137
|
)
|
138
|
-
|
138
|
+
|
139
139
|
@extend_schema(
|
140
140
|
summary="List User Subscriptions",
|
141
141
|
description="Get a list of current user's active newsletter subscriptions.",
|
@@ -3,11 +3,12 @@ Email tracking views.
|
|
3
3
|
"""
|
4
4
|
|
5
5
|
import uuid
|
6
|
+
|
6
7
|
from django.http import HttpResponse, HttpResponseRedirect
|
7
|
-
from django.views.decorators.cache import never_cache
|
8
|
-
from django.views.decorators.csrf import csrf_exempt
|
9
8
|
from django.utils.decorators import method_decorator
|
10
9
|
from django.views import View
|
10
|
+
from django.views.decorators.cache import never_cache
|
11
|
+
from django.views.decorators.csrf import csrf_exempt
|
11
12
|
|
12
13
|
from ..models import EmailLog
|
13
14
|
|
@@ -18,7 +19,7 @@ class TrackEmailOpenView(View):
|
|
18
19
|
"""
|
19
20
|
Track email opens using a 1x1 pixel image.
|
20
21
|
"""
|
21
|
-
|
22
|
+
|
22
23
|
def get(self, request, email_log_id):
|
23
24
|
"""Handle tracking pixel request."""
|
24
25
|
try:
|
@@ -37,7 +38,7 @@ class TrackEmailOpenView(View):
|
|
37
38
|
except (ValueError, TypeError):
|
38
39
|
# Silently fail for invalid UUID format
|
39
40
|
pass
|
40
|
-
|
41
|
+
|
41
42
|
# Return 1x1 transparent pixel
|
42
43
|
pixel_data = b'\x47\x49\x46\x38\x39\x61\x01\x00\x01\x00\x80\x00\x00\x00\x00\x00\x00\x00\x00\x21\xF9\x04\x01\x00\x00\x00\x00\x2C\x00\x00\x00\x00\x01\x00\x01\x00\x00\x02\x02\x04\x01\x00\x3B'
|
43
44
|
return HttpResponse(pixel_data, content_type='image/gif')
|
@@ -49,7 +50,7 @@ class TrackEmailClickView(View):
|
|
49
50
|
"""
|
50
51
|
Track email link clicks and redirect to target URL.
|
51
52
|
"""
|
52
|
-
|
53
|
+
|
53
54
|
def get(self, request, email_log_id):
|
54
55
|
"""Handle click tracking and redirect."""
|
55
56
|
redirect_url = request.GET.get('url', '/')
|
@@ -6,15 +6,16 @@ Modern, clean admin interfaces with Material Icons and no HTML duplication.
|
|
6
6
|
|
7
7
|
from django.contrib import admin
|
8
8
|
|
9
|
-
# Import all admin classes
|
10
|
-
from .balance_admin import UserBalanceAdmin, TransactionAdmin
|
11
|
-
from .payments_admin import UniversalPaymentAdmin
|
12
9
|
from .api_keys_admin import APIKeyAdmin
|
10
|
+
|
11
|
+
# Import all admin classes
|
12
|
+
from .balance_admin import TransactionAdmin, UserBalanceAdmin
|
13
13
|
from .currencies_admin import CurrencyAdmin # Use working version
|
14
|
+
from .endpoint_groups_admin import EndpointGroupAdmin
|
15
|
+
from .networks_admin import NetworkAdmin, ProviderCurrencyAdmin
|
16
|
+
from .payments_admin import UniversalPaymentAdmin
|
14
17
|
from .subscriptions_admin import SubscriptionAdmin
|
15
18
|
from .tariffs_admin import TariffAdmin, TariffEndpointGroupAdmin
|
16
|
-
from .networks_admin import NetworkAdmin, ProviderCurrencyAdmin
|
17
|
-
from .endpoint_groups_admin import EndpointGroupAdmin
|
18
19
|
|
19
20
|
# All models are registered in their respective admin files using @admin.register
|
20
21
|
# This provides:
|
@@ -4,23 +4,20 @@ API Keys Admin interface using Django Admin Utilities.
|
|
4
4
|
Clean API key management with security features.
|
5
5
|
"""
|
6
6
|
|
7
|
+
|
7
8
|
from django.contrib import admin
|
8
|
-
from django.db.models import Count, Q
|
9
9
|
from django.utils import timezone
|
10
|
-
from datetime import timedelta
|
11
|
-
|
12
10
|
from unfold.admin import ModelAdmin
|
13
11
|
|
14
12
|
from django_cfg.modules.django_admin import (
|
15
|
-
|
16
|
-
DisplayMixin,
|
17
|
-
UserDisplayConfig,
|
18
|
-
StatusBadgeConfig,
|
13
|
+
ActionVariant,
|
19
14
|
DateTimeDisplayConfig,
|
15
|
+
DisplayMixin,
|
20
16
|
Icons,
|
21
|
-
|
17
|
+
OptimizedModelAdmin,
|
18
|
+
StatusBadgeConfig,
|
22
19
|
action,
|
23
|
-
|
20
|
+
display,
|
24
21
|
)
|
25
22
|
from django_cfg.modules.django_admin.utils.badges import StatusBadge
|
26
23
|
from django_cfg.modules.django_logging import get_logger
|
@@ -41,13 +38,13 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
41
38
|
- Activity monitoring
|
42
39
|
- Clean utilities integration
|
43
40
|
"""
|
44
|
-
|
41
|
+
|
45
42
|
# Performance optimization
|
46
43
|
select_related_fields = ['user']
|
47
44
|
annotations = {}
|
48
45
|
# Note: Annotations disabled until proper usage tracking is implemented
|
49
46
|
# 'usage_count': Count('usage_logs') or similar
|
50
|
-
|
47
|
+
|
51
48
|
# List configuration
|
52
49
|
list_display = [
|
53
50
|
'key_display',
|
@@ -57,20 +54,20 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
57
54
|
'usage_display',
|
58
55
|
'created_display'
|
59
56
|
]
|
60
|
-
|
57
|
+
|
61
58
|
list_filter = [
|
62
59
|
'is_active',
|
63
60
|
'created_at',
|
64
61
|
'last_used_at'
|
65
62
|
]
|
66
|
-
|
63
|
+
|
67
64
|
search_fields = [
|
68
65
|
'name',
|
69
66
|
'user__username',
|
70
67
|
'user__email',
|
71
68
|
'key' # Be careful with this in production
|
72
69
|
]
|
73
|
-
|
70
|
+
|
74
71
|
readonly_fields = [
|
75
72
|
'key',
|
76
73
|
'created_at',
|
@@ -78,10 +75,10 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
78
75
|
'last_used_at',
|
79
76
|
'key_details_display'
|
80
77
|
]
|
81
|
-
|
78
|
+
|
82
79
|
# Register actions
|
83
80
|
actions = ['activate_selected_keys', 'deactivate_selected_keys', 'regenerate_selected_keys']
|
84
|
-
|
81
|
+
|
85
82
|
# Display methods using utilities
|
86
83
|
@display(description="API Key")
|
87
84
|
def key_display(self, obj):
|
@@ -89,33 +86,33 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
89
86
|
if not obj.key:
|
90
87
|
config = StatusBadgeConfig(show_icons=True, icon=Icons.KEY_OFF)
|
91
88
|
return StatusBadge.create(text="No Key", variant="secondary", config=config)
|
92
|
-
|
89
|
+
|
93
90
|
# Show first 8 and last 4 characters
|
94
91
|
masked_key = f"{obj.key[:8]}...{obj.key[-4:]}"
|
95
|
-
|
92
|
+
|
96
93
|
config = StatusBadgeConfig(show_icons=True, icon=Icons.KEY)
|
97
94
|
return StatusBadge.create(
|
98
95
|
text=masked_key,
|
99
96
|
variant="info",
|
100
97
|
config=config
|
101
98
|
)
|
102
|
-
|
99
|
+
|
103
100
|
@display(description="User", header=True)
|
104
101
|
def user_display(self, obj):
|
105
102
|
"""User display with avatar."""
|
106
103
|
return self.display_user_with_avatar(obj, 'user')
|
107
|
-
|
104
|
+
|
108
105
|
@display(description="Name")
|
109
106
|
def name_display(self, obj):
|
110
107
|
"""API key name display."""
|
111
108
|
if not obj.name:
|
112
109
|
return StatusBadge.create(text="Unnamed", variant="secondary")
|
113
|
-
|
110
|
+
|
114
111
|
return StatusBadge.create(
|
115
112
|
text=obj.name,
|
116
113
|
variant="primary"
|
117
114
|
)
|
118
|
-
|
115
|
+
|
119
116
|
@display(description="Status", label=True)
|
120
117
|
def status_display(self, obj):
|
121
118
|
"""Status display with activity level."""
|
@@ -125,14 +122,14 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
125
122
|
'status',
|
126
123
|
StatusBadgeConfig(custom_mappings={'Inactive': 'danger'})
|
127
124
|
)
|
128
|
-
|
125
|
+
|
129
126
|
# Determine activity level based on last usage
|
130
127
|
if not obj.last_used_at:
|
131
128
|
status = "Active (Unused)"
|
132
129
|
variant = "info"
|
133
130
|
else:
|
134
131
|
days_since_use = (timezone.now() - obj.last_used_at).days
|
135
|
-
|
132
|
+
|
136
133
|
if days_since_use <= 1:
|
137
134
|
status = "Active (Recent)"
|
138
135
|
variant = "success"
|
@@ -145,31 +142,31 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
145
142
|
else:
|
146
143
|
status = "Active (Idle)"
|
147
144
|
variant = "secondary"
|
148
|
-
|
145
|
+
|
149
146
|
config = StatusBadgeConfig(
|
150
147
|
custom_mappings={status: variant},
|
151
148
|
show_icons=True
|
152
149
|
)
|
153
|
-
|
150
|
+
|
154
151
|
return self.display_status_auto(
|
155
152
|
type('obj', (), {'status': status})(),
|
156
153
|
'status',
|
157
154
|
config
|
158
155
|
)
|
159
|
-
|
156
|
+
|
160
157
|
@display(description="Usage")
|
161
158
|
def usage_display(self, obj):
|
162
159
|
"""Usage count display."""
|
163
160
|
# This would need actual usage tracking implementation
|
164
161
|
usage_count = getattr(obj, 'usage_count', 0)
|
165
|
-
|
162
|
+
|
166
163
|
return self.display_count_simple(
|
167
164
|
type('obj', (), {'usage_count': usage_count})(),
|
168
165
|
'usage_count',
|
169
166
|
'requests',
|
170
167
|
CounterBadgeConfig(use_humanize=True)
|
171
168
|
)
|
172
|
-
|
169
|
+
|
173
170
|
@display(description="Created")
|
174
171
|
def created_display(self, obj):
|
175
172
|
"""Created time display."""
|
@@ -178,21 +175,22 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
178
175
|
'created_at',
|
179
176
|
DateTimeDisplayConfig(show_relative=True, show_seconds=False)
|
180
177
|
)
|
181
|
-
|
178
|
+
|
182
179
|
# Readonly field displays
|
183
180
|
def key_details_display(self, obj):
|
184
181
|
"""Detailed API key information for detail view."""
|
185
182
|
if not obj.pk:
|
186
183
|
return "Save to see details"
|
187
|
-
|
184
|
+
|
188
185
|
from django.utils.html import format_html
|
186
|
+
|
189
187
|
from django_cfg.modules.django_admin.utils.displays import DateTimeDisplay
|
190
|
-
|
188
|
+
|
191
189
|
details = []
|
192
|
-
|
190
|
+
|
193
191
|
# Full key (be careful in production!)
|
194
192
|
details.append(f"<strong>Full Key:</strong> <code>{obj.key}</code>")
|
195
|
-
|
193
|
+
|
196
194
|
# Usage statistics
|
197
195
|
if obj.last_used_at:
|
198
196
|
last_used_html = DateTimeDisplay.relative(
|
@@ -202,24 +200,24 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
202
200
|
details.append(f"<strong>Last Used:</strong> {last_used_html}")
|
203
201
|
else:
|
204
202
|
details.append("<strong>Last Used:</strong> Never")
|
205
|
-
|
203
|
+
|
206
204
|
# Age calculation
|
207
205
|
age = timezone.now() - obj.created_at
|
208
206
|
age_text = f"{age.days} days old"
|
209
207
|
details.append(f"<strong>Age:</strong> {age_text}")
|
210
|
-
|
208
|
+
|
211
209
|
# Security info
|
212
210
|
if obj.is_active:
|
213
211
|
security_status = '<span class="text-green-600">🔓 Active</span>'
|
214
212
|
else:
|
215
213
|
security_status = '<span class="text-red-600">🔒 Inactive</span>'
|
216
|
-
|
214
|
+
|
217
215
|
details.append(f"<strong>Security Status:</strong> {security_status}")
|
218
|
-
|
216
|
+
|
219
217
|
return format_html("<br>".join(details))
|
220
|
-
|
218
|
+
|
221
219
|
key_details_display.short_description = "Key Details"
|
222
|
-
|
220
|
+
|
223
221
|
# Actions
|
224
222
|
@action(description="Activate selected keys", variant=ActionVariant.SUCCESS)
|
225
223
|
def activate_keys(self, request, queryset):
|
@@ -230,7 +228,7 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
230
228
|
f"Successfully activated {updated} API key(s).",
|
231
229
|
level='SUCCESS'
|
232
230
|
)
|
233
|
-
|
231
|
+
|
234
232
|
@action(description="Deactivate selected keys", variant=ActionVariant.WARNING)
|
235
233
|
def deactivate_keys(self, request, queryset):
|
236
234
|
"""Deactivate selected API keys."""
|
@@ -240,23 +238,23 @@ class APIKeyAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin):
|
|
240
238
|
f"Successfully deactivated {updated} API key(s).",
|
241
239
|
level='WARNING'
|
242
240
|
)
|
243
|
-
|
241
|
+
|
244
242
|
@action(description="Regenerate selected keys", variant=ActionVariant.DANGER)
|
245
243
|
def regenerate_keys(self, request, queryset):
|
246
244
|
"""Regenerate selected API keys."""
|
247
245
|
import secrets
|
248
246
|
import string
|
249
|
-
|
247
|
+
|
250
248
|
updated_count = 0
|
251
249
|
for api_key in queryset:
|
252
250
|
# Generate new key
|
253
251
|
alphabet = string.ascii_letters + string.digits
|
254
252
|
new_key = ''.join(secrets.choice(alphabet) for _ in range(32))
|
255
|
-
|
253
|
+
|
256
254
|
api_key.key = new_key
|
257
255
|
api_key.save()
|
258
256
|
updated_count += 1
|
259
|
-
|
257
|
+
|
260
258
|
self.message_user(
|
261
259
|
request,
|
262
260
|
f"Successfully regenerated {updated_count} API key(s).",
|