django-cfg 1.1.81__py3-none-any.whl → 1.2.0__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 +20 -448
- django_cfg/apps/accounts/README.md +3 -3
- django_cfg/apps/accounts/admin/__init__.py +0 -2
- django_cfg/apps/accounts/admin/activity.py +2 -9
- django_cfg/apps/accounts/admin/filters.py +0 -42
- django_cfg/apps/accounts/admin/inlines.py +8 -8
- django_cfg/apps/accounts/admin/otp.py +5 -5
- django_cfg/apps/accounts/admin/registration_source.py +1 -8
- django_cfg/apps/accounts/admin/user.py +12 -20
- django_cfg/apps/accounts/managers/user_manager.py +2 -129
- django_cfg/apps/accounts/migrations/0006_remove_twilioresponse_otp_secret_and_more.py +46 -0
- django_cfg/apps/accounts/models.py +3 -123
- django_cfg/apps/accounts/serializers/otp.py +40 -44
- django_cfg/apps/accounts/serializers/profile.py +0 -2
- django_cfg/apps/accounts/services/otp_service.py +98 -186
- django_cfg/apps/accounts/signals.py +25 -15
- django_cfg/apps/accounts/utils/auth_email_service.py +84 -0
- django_cfg/apps/accounts/views/otp.py +35 -36
- django_cfg/apps/agents/README.md +129 -0
- django_cfg/apps/agents/__init__.py +68 -0
- django_cfg/apps/agents/admin/__init__.py +17 -0
- django_cfg/apps/agents/admin/execution_admin.py +460 -0
- django_cfg/apps/agents/admin/registry_admin.py +360 -0
- django_cfg/apps/agents/admin/toolsets_admin.py +482 -0
- django_cfg/apps/agents/apps.py +29 -0
- django_cfg/apps/agents/core/__init__.py +20 -0
- django_cfg/apps/agents/core/agent.py +281 -0
- django_cfg/apps/agents/core/dependencies.py +154 -0
- django_cfg/apps/agents/core/exceptions.py +66 -0
- django_cfg/apps/agents/core/models.py +106 -0
- django_cfg/apps/agents/core/orchestrator.py +391 -0
- django_cfg/apps/agents/examples/__init__.py +3 -0
- django_cfg/apps/agents/examples/simple_example.py +161 -0
- django_cfg/apps/agents/integration/__init__.py +14 -0
- django_cfg/apps/agents/integration/middleware.py +80 -0
- django_cfg/apps/agents/integration/registry.py +345 -0
- django_cfg/apps/agents/integration/signals.py +50 -0
- django_cfg/apps/agents/management/__init__.py +3 -0
- django_cfg/apps/agents/management/commands/__init__.py +3 -0
- django_cfg/apps/agents/management/commands/create_agent.py +365 -0
- django_cfg/apps/agents/management/commands/orchestrator_status.py +191 -0
- django_cfg/apps/agents/managers/__init__.py +23 -0
- django_cfg/apps/agents/managers/execution.py +236 -0
- django_cfg/apps/agents/managers/registry.py +254 -0
- django_cfg/apps/agents/managers/toolsets.py +496 -0
- django_cfg/apps/agents/migrations/0001_initial.py +286 -0
- django_cfg/apps/agents/migrations/__init__.py +5 -0
- django_cfg/apps/agents/models/__init__.py +15 -0
- django_cfg/apps/agents/models/execution.py +215 -0
- django_cfg/apps/agents/models/registry.py +220 -0
- django_cfg/apps/agents/models/toolsets.py +305 -0
- django_cfg/apps/agents/patterns/__init__.py +24 -0
- django_cfg/apps/agents/patterns/content_agents.py +234 -0
- django_cfg/apps/agents/toolsets/__init__.py +15 -0
- django_cfg/apps/agents/toolsets/cache_toolset.py +285 -0
- django_cfg/apps/agents/toolsets/django_toolset.py +220 -0
- django_cfg/apps/agents/toolsets/file_toolset.py +324 -0
- django_cfg/apps/agents/toolsets/orm_toolset.py +319 -0
- django_cfg/apps/agents/urls.py +46 -0
- django_cfg/apps/knowbase/README.md +150 -0
- django_cfg/apps/knowbase/__init__.py +27 -0
- django_cfg/apps/knowbase/admin/__init__.py +23 -0
- django_cfg/apps/knowbase/admin/archive_admin.py +857 -0
- django_cfg/apps/knowbase/admin/chat_admin.py +386 -0
- django_cfg/apps/knowbase/admin/document_admin.py +650 -0
- django_cfg/apps/knowbase/admin/external_data_admin.py +685 -0
- django_cfg/apps/knowbase/apps.py +81 -0
- django_cfg/apps/knowbase/config/README.md +176 -0
- django_cfg/apps/knowbase/config/__init__.py +51 -0
- django_cfg/apps/knowbase/config/constance_fields.py +186 -0
- django_cfg/apps/knowbase/config/constance_settings.py +200 -0
- django_cfg/apps/knowbase/config/settings.py +444 -0
- django_cfg/apps/knowbase/examples/__init__.py +3 -0
- django_cfg/apps/knowbase/examples/external_data_usage.py +191 -0
- django_cfg/apps/knowbase/management/__init__.py +0 -0
- django_cfg/apps/knowbase/management/commands/__init__.py +0 -0
- django_cfg/apps/knowbase/management/commands/knowbase_stats.py +158 -0
- django_cfg/apps/knowbase/management/commands/setup_knowbase.py +59 -0
- django_cfg/apps/knowbase/managers/__init__.py +22 -0
- django_cfg/apps/knowbase/managers/archive.py +426 -0
- django_cfg/apps/knowbase/managers/base.py +32 -0
- django_cfg/apps/knowbase/managers/chat.py +141 -0
- django_cfg/apps/knowbase/managers/document.py +203 -0
- django_cfg/apps/knowbase/managers/external_data.py +471 -0
- django_cfg/apps/knowbase/migrations/0001_initial.py +427 -0
- django_cfg/apps/knowbase/migrations/0002_archiveitem_archiveitemchunk_documentarchive_and_more.py +434 -0
- django_cfg/apps/knowbase/migrations/__init__.py +5 -0
- django_cfg/apps/knowbase/mixins/__init__.py +15 -0
- django_cfg/apps/knowbase/mixins/config.py +108 -0
- django_cfg/apps/knowbase/mixins/creator.py +81 -0
- django_cfg/apps/knowbase/mixins/examples/vehicle_model_example.py +199 -0
- django_cfg/apps/knowbase/mixins/external_data_mixin.py +813 -0
- django_cfg/apps/knowbase/mixins/service.py +362 -0
- django_cfg/apps/knowbase/models/__init__.py +41 -0
- django_cfg/apps/knowbase/models/archive.py +599 -0
- django_cfg/apps/knowbase/models/base.py +58 -0
- django_cfg/apps/knowbase/models/chat.py +157 -0
- django_cfg/apps/knowbase/models/document.py +267 -0
- django_cfg/apps/knowbase/models/external_data.py +376 -0
- django_cfg/apps/knowbase/serializers/__init__.py +68 -0
- django_cfg/apps/knowbase/serializers/archive_serializers.py +386 -0
- django_cfg/apps/knowbase/serializers/chat_serializers.py +137 -0
- django_cfg/apps/knowbase/serializers/document_serializers.py +94 -0
- django_cfg/apps/knowbase/serializers/external_data_serializers.py +256 -0
- django_cfg/apps/knowbase/serializers/public_serializers.py +74 -0
- django_cfg/apps/knowbase/services/__init__.py +40 -0
- django_cfg/apps/knowbase/services/archive/__init__.py +42 -0
- django_cfg/apps/knowbase/services/archive/archive_service.py +541 -0
- django_cfg/apps/knowbase/services/archive/chunking_service.py +791 -0
- django_cfg/apps/knowbase/services/archive/exceptions.py +52 -0
- django_cfg/apps/knowbase/services/archive/extraction_service.py +508 -0
- django_cfg/apps/knowbase/services/archive/vectorization_service.py +362 -0
- django_cfg/apps/knowbase/services/base.py +53 -0
- django_cfg/apps/knowbase/services/chat_service.py +239 -0
- django_cfg/apps/knowbase/services/document_service.py +144 -0
- django_cfg/apps/knowbase/services/embedding/__init__.py +43 -0
- django_cfg/apps/knowbase/services/embedding/async_processor.py +244 -0
- django_cfg/apps/knowbase/services/embedding/batch_processor.py +250 -0
- django_cfg/apps/knowbase/services/embedding/batch_result.py +61 -0
- django_cfg/apps/knowbase/services/embedding/models.py +229 -0
- django_cfg/apps/knowbase/services/embedding/processors.py +148 -0
- django_cfg/apps/knowbase/services/embedding/utils.py +176 -0
- django_cfg/apps/knowbase/services/prompt_builder.py +191 -0
- django_cfg/apps/knowbase/services/search_service.py +293 -0
- django_cfg/apps/knowbase/signals/__init__.py +21 -0
- django_cfg/apps/knowbase/signals/archive_signals.py +211 -0
- django_cfg/apps/knowbase/signals/chat_signals.py +37 -0
- django_cfg/apps/knowbase/signals/document_signals.py +143 -0
- django_cfg/apps/knowbase/signals/external_data_signals.py +157 -0
- django_cfg/apps/knowbase/tasks/__init__.py +39 -0
- django_cfg/apps/knowbase/tasks/archive_tasks.py +316 -0
- django_cfg/apps/knowbase/tasks/document_processing.py +341 -0
- django_cfg/apps/knowbase/tasks/external_data_tasks.py +341 -0
- django_cfg/apps/knowbase/tasks/maintenance.py +195 -0
- django_cfg/apps/knowbase/urls.py +43 -0
- django_cfg/apps/knowbase/utils/__init__.py +12 -0
- django_cfg/apps/knowbase/utils/chunk_settings.py +261 -0
- django_cfg/apps/knowbase/utils/text_processing.py +375 -0
- django_cfg/apps/knowbase/utils/validation.py +99 -0
- django_cfg/apps/knowbase/views/__init__.py +28 -0
- django_cfg/apps/knowbase/views/archive_views.py +469 -0
- django_cfg/apps/knowbase/views/base.py +49 -0
- django_cfg/apps/knowbase/views/chat_views.py +181 -0
- django_cfg/apps/knowbase/views/document_views.py +183 -0
- django_cfg/apps/knowbase/views/public_views.py +129 -0
- django_cfg/apps/leads/admin.py +70 -0
- django_cfg/apps/newsletter/admin.py +234 -0
- django_cfg/apps/newsletter/admin_filters.py +124 -0
- django_cfg/apps/support/admin.py +196 -0
- django_cfg/apps/support/admin_filters.py +71 -0
- django_cfg/apps/support/templates/support/chat/ticket_chat.html +1 -1
- django_cfg/apps/urls.py +5 -4
- django_cfg/cli/README.md +1 -1
- django_cfg/cli/commands/create_project.py +2 -2
- django_cfg/cli/commands/info.py +1 -1
- django_cfg/config.py +44 -0
- django_cfg/core/config.py +29 -82
- django_cfg/core/environment.py +1 -1
- django_cfg/core/generation.py +19 -107
- django_cfg/{integration.py → core/integration.py} +18 -16
- django_cfg/core/validation.py +1 -1
- django_cfg/management/__init__.py +1 -1
- django_cfg/management/commands/__init__.py +1 -1
- django_cfg/management/commands/auto_generate.py +482 -0
- django_cfg/management/commands/migrator.py +19 -101
- django_cfg/management/commands/test_email.py +1 -1
- django_cfg/middleware/README.md +0 -158
- django_cfg/middleware/__init__.py +0 -2
- django_cfg/middleware/user_activity.py +3 -3
- django_cfg/models/api.py +145 -0
- django_cfg/models/base.py +287 -0
- django_cfg/models/cache.py +4 -4
- django_cfg/models/constance.py +25 -88
- django_cfg/models/database.py +9 -9
- django_cfg/models/drf.py +3 -36
- django_cfg/models/email.py +163 -0
- django_cfg/models/environment.py +276 -0
- django_cfg/models/limits.py +1 -1
- django_cfg/models/logging.py +366 -0
- django_cfg/models/revolution.py +41 -2
- django_cfg/models/security.py +125 -0
- django_cfg/models/services.py +1 -1
- django_cfg/modules/__init__.py +2 -56
- django_cfg/modules/base.py +78 -52
- django_cfg/modules/django_currency/service.py +2 -2
- django_cfg/modules/django_email.py +2 -2
- django_cfg/modules/django_health.py +267 -0
- django_cfg/modules/django_llm/llm/client.py +79 -17
- django_cfg/modules/django_llm/translator/translator.py +2 -2
- django_cfg/modules/django_logger.py +2 -2
- django_cfg/modules/django_ngrok.py +2 -2
- django_cfg/modules/django_tasks.py +68 -3
- django_cfg/modules/django_telegram.py +3 -3
- django_cfg/modules/django_twilio/sendgrid_service.py +2 -2
- django_cfg/modules/django_twilio/service.py +2 -2
- django_cfg/modules/django_twilio/simple_service.py +2 -2
- django_cfg/modules/django_twilio/templates/guide.md +266 -0
- django_cfg/modules/django_twilio/twilio_service.py +2 -2
- django_cfg/modules/django_unfold/__init__.py +69 -0
- django_cfg/modules/{unfold → django_unfold}/callbacks.py +23 -22
- django_cfg/modules/django_unfold/dashboard.py +278 -0
- django_cfg/modules/django_unfold/icons/README.md +145 -0
- django_cfg/modules/django_unfold/icons/__init__.py +12 -0
- django_cfg/modules/django_unfold/icons/constants.py +2851 -0
- django_cfg/modules/django_unfold/icons/generate_icons.py +486 -0
- django_cfg/modules/django_unfold/models/__init__.py +42 -0
- django_cfg/modules/django_unfold/models/config.py +601 -0
- django_cfg/modules/django_unfold/models/dashboard.py +206 -0
- django_cfg/modules/django_unfold/models/dropdown.py +40 -0
- django_cfg/modules/django_unfold/models/navigation.py +73 -0
- django_cfg/modules/django_unfold/models/tabs.py +25 -0
- django_cfg/modules/{unfold → django_unfold}/system_monitor.py +2 -2
- django_cfg/modules/django_unfold/utils.py +140 -0
- django_cfg/registry/__init__.py +23 -0
- django_cfg/registry/core.py +61 -0
- django_cfg/registry/exceptions.py +11 -0
- django_cfg/registry/modules.py +12 -0
- django_cfg/registry/services.py +26 -0
- django_cfg/registry/third_party.py +52 -0
- django_cfg/routing/__init__.py +19 -0
- django_cfg/routing/callbacks.py +198 -0
- django_cfg/routing/routers.py +48 -0
- django_cfg/templates/admin/layouts/dashboard_with_tabs.html +8 -9
- django_cfg/templatetags/__init__.py +0 -0
- django_cfg/templatetags/django_cfg.py +33 -0
- django_cfg/urls.py +33 -0
- django_cfg/utils/path_resolution.py +1 -1
- django_cfg/utils/smart_defaults.py +7 -61
- django_cfg/utils/toolkit.py +663 -0
- {django_cfg-1.1.81.dist-info → django_cfg-1.2.0.dist-info}/METADATA +83 -86
- django_cfg-1.2.0.dist-info/RECORD +441 -0
- django_cfg/apps/tasks/@docs/README.md +0 -195
- django_cfg/archive/django_sample.zip +0 -0
- django_cfg/models/unfold.py +0 -271
- django_cfg/modules/unfold/__init__.py +0 -29
- django_cfg/modules/unfold/dashboard.py +0 -318
- django_cfg/pyproject.toml +0 -370
- django_cfg/routers.py +0 -83
- django_cfg-1.1.81.dist-info/RECORD +0 -278
- /django_cfg/{exceptions.py → core/exceptions.py} +0 -0
- /django_cfg/modules/{unfold → django_unfold}/models.py +0 -0
- /django_cfg/modules/{unfold → django_unfold}/tailwind.py +0 -0
- /django_cfg/{version_check.py → utils/version_check.py} +0 -0
- {django_cfg-1.1.81.dist-info → django_cfg-1.2.0.dist-info}/WHEEL +0 -0
- {django_cfg-1.1.81.dist-info → django_cfg-1.2.0.dist-info}/entry_points.txt +0 -0
- {django_cfg-1.1.81.dist-info → django_cfg-1.2.0.dist-info}/licenses/LICENSE +0 -0
django_cfg/models/revolution.py
CHANGED
@@ -83,13 +83,16 @@ class ExtendedRevolutionConfig(BaseDjangoRevolutionConfig):
|
|
83
83
|
|
84
84
|
# Add default django-cfg zones if enabled
|
85
85
|
try:
|
86
|
-
from django_cfg.modules.base import
|
87
|
-
base_module =
|
86
|
+
from django_cfg.modules.base import BaseCfgModule
|
87
|
+
base_module = BaseCfgModule()
|
88
88
|
|
89
89
|
support_enabled = base_module.is_support_enabled()
|
90
90
|
accounts_enabled = base_module.is_accounts_enabled()
|
91
91
|
newsletter_enabled = base_module.is_newsletter_enabled()
|
92
92
|
leads_enabled = base_module.is_leads_enabled()
|
93
|
+
knowbase_enabled = base_module.is_knowbase_enabled()
|
94
|
+
agents_enabled = base_module.is_agents_enabled()
|
95
|
+
tasks_enabled = base_module.is_tasks_enabled()
|
93
96
|
|
94
97
|
# Add Support zone if enabled
|
95
98
|
default_support_zone = 'cfg_support'
|
@@ -138,6 +141,42 @@ class ExtendedRevolutionConfig(BaseDjangoRevolutionConfig):
|
|
138
141
|
auth_required=False,
|
139
142
|
version="v1",
|
140
143
|
)
|
144
|
+
|
145
|
+
# Add Knowbase zone if enabled
|
146
|
+
default_knowbase_zone = 'cfg_knowbase'
|
147
|
+
if knowbase_enabled and default_knowbase_zone not in zones:
|
148
|
+
zones[default_knowbase_zone] = ZoneConfig(
|
149
|
+
apps=["django_cfg.apps.knowbase"],
|
150
|
+
title="Knowbase API",
|
151
|
+
description="Knowledge base, AI chat, embeddings, and search API",
|
152
|
+
public=False,
|
153
|
+
auth_required=True,
|
154
|
+
version="v1",
|
155
|
+
)
|
156
|
+
|
157
|
+
# Add Agents zone if enabled
|
158
|
+
default_agents_zone = 'cfg_agents'
|
159
|
+
if agents_enabled and default_agents_zone not in zones:
|
160
|
+
zones[default_agents_zone] = ZoneConfig(
|
161
|
+
apps=["django_cfg.apps.agents"],
|
162
|
+
title="Agents API",
|
163
|
+
description="Agent definitions, executions, workflows, and tools API",
|
164
|
+
public=False,
|
165
|
+
auth_required=True,
|
166
|
+
version="v1",
|
167
|
+
)
|
168
|
+
|
169
|
+
# Add Tasks zone if enabled
|
170
|
+
default_tasks_zone = 'cfg_tasks'
|
171
|
+
if tasks_enabled and default_tasks_zone not in zones:
|
172
|
+
zones[default_tasks_zone] = ZoneConfig(
|
173
|
+
apps=["django_cfg.apps.tasks"],
|
174
|
+
title="Tasks API",
|
175
|
+
description="Tasks, workflows, and automation API",
|
176
|
+
public=False,
|
177
|
+
auth_required=True,
|
178
|
+
version="v1",
|
179
|
+
)
|
141
180
|
except Exception:
|
142
181
|
pass
|
143
182
|
|
@@ -0,0 +1,125 @@
|
|
1
|
+
"""
|
2
|
+
Security Configuration Model
|
3
|
+
|
4
|
+
Django security settings with Pydantic 2.
|
5
|
+
"""
|
6
|
+
|
7
|
+
from typing import List, Dict, Any
|
8
|
+
from pydantic import Field, field_validator
|
9
|
+
from .base import BaseConfig
|
10
|
+
|
11
|
+
|
12
|
+
class SecurityConfig(BaseConfig):
|
13
|
+
"""
|
14
|
+
🔒 Security Configuration - Django security settings
|
15
|
+
|
16
|
+
Handles CORS, CSRF, SSL, sessions, and other security configurations
|
17
|
+
with environment-aware defaults.
|
18
|
+
"""
|
19
|
+
|
20
|
+
# CORS settings
|
21
|
+
cors_enabled: bool = Field(default=True, description="Enable CORS support")
|
22
|
+
cors_allow_all_origins: bool = Field(default=False, description="Allow all origins (dev only)")
|
23
|
+
cors_allowed_origins: List[str] = Field(default_factory=list, description="Allowed CORS origins")
|
24
|
+
cors_allow_credentials: bool = Field(default=True, description="Allow CORS credentials")
|
25
|
+
|
26
|
+
# CSRF settings
|
27
|
+
csrf_enabled: bool = Field(default=True, description="Enable CSRF protection")
|
28
|
+
csrf_trusted_origins: List[str] = Field(default_factory=list, description="CSRF trusted origins")
|
29
|
+
csrf_cookie_secure: bool = Field(default=False, description="Secure CSRF cookies")
|
30
|
+
|
31
|
+
# SSL/HTTPS settings
|
32
|
+
ssl_redirect: bool = Field(default=False, description="Redirect HTTP to HTTPS")
|
33
|
+
hsts_enabled: bool = Field(default=False, description="Enable HTTP Strict Transport Security")
|
34
|
+
hsts_max_age: int = Field(default=31536000, description="HSTS max age in seconds")
|
35
|
+
|
36
|
+
# Session settings
|
37
|
+
session_cookie_secure: bool = Field(default=False, description="Secure session cookies")
|
38
|
+
session_cookie_age: int = Field(default=86400, description="Session cookie age in seconds")
|
39
|
+
|
40
|
+
# Production domains for auto-configuration
|
41
|
+
production_domains: List[str] = Field(
|
42
|
+
default_factory=lambda: [
|
43
|
+
"https://carapis.com",
|
44
|
+
"https://api2.carapis.com",
|
45
|
+
"https://djangocfg.com",
|
46
|
+
],
|
47
|
+
description="Production domains for security configuration"
|
48
|
+
)
|
49
|
+
|
50
|
+
@field_validator('hsts_max_age')
|
51
|
+
@classmethod
|
52
|
+
def validate_hsts_max_age(cls, v: int) -> int:
|
53
|
+
"""Validate HSTS max age."""
|
54
|
+
if v < 0:
|
55
|
+
raise ValueError("HSTS max age must be non-negative")
|
56
|
+
return v
|
57
|
+
|
58
|
+
def configure_for_production(self) -> None:
|
59
|
+
"""Configure security settings for production."""
|
60
|
+
self.cors_allow_all_origins = False
|
61
|
+
self.cors_allowed_origins = self.production_domains
|
62
|
+
self.csrf_cookie_secure = True
|
63
|
+
self.csrf_trusted_origins = self.production_domains
|
64
|
+
self.ssl_redirect = True
|
65
|
+
self.hsts_enabled = True
|
66
|
+
self.session_cookie_secure = True
|
67
|
+
|
68
|
+
def configure_for_development(self) -> None:
|
69
|
+
"""Configure security settings for development."""
|
70
|
+
self.cors_allow_all_origins = True
|
71
|
+
self.cors_allowed_origins = []
|
72
|
+
self.csrf_cookie_secure = False
|
73
|
+
self.csrf_trusted_origins = []
|
74
|
+
self.ssl_redirect = False
|
75
|
+
self.hsts_enabled = False
|
76
|
+
self.session_cookie_secure = False
|
77
|
+
|
78
|
+
def to_django_settings(self) -> Dict[str, Any]:
|
79
|
+
"""Convert to Django security settings."""
|
80
|
+
settings = {}
|
81
|
+
|
82
|
+
# CORS settings
|
83
|
+
if self.cors_enabled:
|
84
|
+
settings.update({
|
85
|
+
'CORS_ALLOW_ALL_ORIGINS': self.cors_allow_all_origins,
|
86
|
+
'CORS_ALLOWED_ORIGINS': self.cors_allowed_origins,
|
87
|
+
'CORS_ALLOW_CREDENTIALS': self.cors_allow_credentials,
|
88
|
+
})
|
89
|
+
|
90
|
+
# Add corsheaders to middleware if not present
|
91
|
+
# This will be handled by the main ConfigToolkit
|
92
|
+
|
93
|
+
# CSRF settings
|
94
|
+
settings.update({
|
95
|
+
'CSRF_TRUSTED_ORIGINS': self.csrf_trusted_origins,
|
96
|
+
'CSRF_COOKIE_SECURE': self.csrf_cookie_secure,
|
97
|
+
})
|
98
|
+
|
99
|
+
# SSL/HTTPS settings
|
100
|
+
if self.ssl_redirect:
|
101
|
+
settings['SECURE_SSL_REDIRECT'] = True
|
102
|
+
|
103
|
+
if self.hsts_enabled:
|
104
|
+
settings.update({
|
105
|
+
'SECURE_HSTS_SECONDS': self.hsts_max_age,
|
106
|
+
'SECURE_HSTS_INCLUDE_SUBDOMAINS': True,
|
107
|
+
'SECURE_HSTS_PRELOAD': True,
|
108
|
+
})
|
109
|
+
|
110
|
+
# Session settings
|
111
|
+
settings.update({
|
112
|
+
'SESSION_COOKIE_SECURE': self.session_cookie_secure,
|
113
|
+
'SESSION_COOKIE_AGE': self.session_cookie_age,
|
114
|
+
'SESSION_COOKIE_HTTPONLY': True,
|
115
|
+
'SESSION_COOKIE_SAMESITE': 'Lax',
|
116
|
+
})
|
117
|
+
|
118
|
+
# Additional security headers
|
119
|
+
settings.update({
|
120
|
+
'SECURE_CONTENT_TYPE_NOSNIFF': True,
|
121
|
+
'SECURE_BROWSER_XSS_FILTER': True,
|
122
|
+
'X_FRAME_OPTIONS': 'DENY',
|
123
|
+
})
|
124
|
+
|
125
|
+
return settings
|
django_cfg/models/services.py
CHANGED
@@ -12,7 +12,7 @@ from typing import Dict, Optional, Any, Literal, List
|
|
12
12
|
from pydantic import BaseModel, Field, field_validator, model_validator, EmailStr
|
13
13
|
from pathlib import Path
|
14
14
|
|
15
|
-
from django_cfg.exceptions import ConfigurationError, ValidationError
|
15
|
+
from django_cfg.core.exceptions import ConfigurationError, ValidationError
|
16
16
|
|
17
17
|
|
18
18
|
class EmailConfig(BaseModel):
|
django_cfg/modules/__init__.py
CHANGED
@@ -6,61 +6,7 @@ All modules automatically receive configuration from the DjangoConfig instance
|
|
6
6
|
without requiring manual parameter passing.
|
7
7
|
"""
|
8
8
|
|
9
|
-
from
|
10
|
-
import importlib
|
11
|
-
import os
|
12
|
-
|
13
|
-
if TYPE_CHECKING:
|
14
|
-
from django_cfg.core.config import DjangoConfig
|
15
|
-
|
16
|
-
|
17
|
-
class BaseModule:
|
18
|
-
"""
|
19
|
-
Base class for auto-configuring django_cfg modules.
|
20
|
-
|
21
|
-
All modules inherit from this to automatically receive
|
22
|
-
configuration from the DjangoConfig instance.
|
23
|
-
"""
|
24
|
-
|
25
|
-
_config_instance: Optional["DjangoConfig"] = None
|
26
|
-
|
27
|
-
@classmethod
|
28
|
-
def get_config(cls) -> "DjangoConfig":
|
29
|
-
"""Get the DjangoConfig instance automatically."""
|
30
|
-
if cls._config_instance is None:
|
31
|
-
cls._config_instance = cls._discover_config()
|
32
|
-
return cls._config_instance
|
33
|
-
|
34
|
-
@classmethod
|
35
|
-
def _discover_config(cls) -> "DjangoConfig":
|
36
|
-
"""Discover the DjangoConfig instance from Django settings."""
|
37
|
-
try:
|
38
|
-
# Try to get config from Django settings module
|
39
|
-
settings_module = os.environ.get("DJANGO_SETTINGS_MODULE")
|
40
|
-
if settings_module:
|
41
|
-
settings_mod = importlib.import_module(settings_module)
|
42
|
-
if hasattr(settings_mod, "config"):
|
43
|
-
return settings_mod.config
|
44
|
-
|
45
|
-
# Fallback: try to create minimal config from Django settings
|
46
|
-
from django.conf import settings
|
47
|
-
from django_cfg import DjangoConfig
|
48
|
-
|
49
|
-
return DjangoConfig(
|
50
|
-
project_name=getattr(settings, "PROJECT_NAME", "Django Project"),
|
51
|
-
secret_key=settings.SECRET_KEY,
|
52
|
-
debug=settings.DEBUG,
|
53
|
-
allowed_hosts=settings.ALLOWED_HOSTS,
|
54
|
-
)
|
55
|
-
|
56
|
-
except Exception as e:
|
57
|
-
raise RuntimeError(f"Could not discover DjangoConfig instance: {e}")
|
58
|
-
|
59
|
-
@classmethod
|
60
|
-
def reset_config(cls):
|
61
|
-
"""Reset the cached config instance (useful for testing)."""
|
62
|
-
cls._config_instance = None
|
63
|
-
|
9
|
+
from .base import BaseCfgModule
|
64
10
|
|
65
11
|
# Export the base module
|
66
|
-
__all__ = ["
|
12
|
+
__all__ = ["BaseCfgModule"]
|
django_cfg/modules/base.py
CHANGED
@@ -4,56 +4,69 @@ Base Module for Django CFG
|
|
4
4
|
Provides base functionality for all auto-configuring modules.
|
5
5
|
"""
|
6
6
|
|
7
|
-
from typing import Any, Optional
|
7
|
+
from typing import Any, Optional, TYPE_CHECKING
|
8
8
|
from abc import ABC
|
9
|
+
import importlib
|
10
|
+
import os
|
9
11
|
|
12
|
+
if TYPE_CHECKING:
|
13
|
+
from django_cfg.core.config import DjangoConfig
|
10
14
|
|
11
|
-
|
15
|
+
|
16
|
+
class BaseCfgModule(ABC):
|
12
17
|
"""
|
13
18
|
Base class for all django_cfg modules.
|
14
19
|
|
15
20
|
Provides common functionality and configuration access.
|
21
|
+
Auto-discovers configuration from Django settings.
|
16
22
|
"""
|
17
23
|
|
24
|
+
_config_instance: Optional["DjangoConfig"] = None
|
25
|
+
|
18
26
|
def __init__(self):
|
19
27
|
"""Initialize the base module."""
|
20
28
|
self._config = None
|
21
29
|
|
22
|
-
|
23
|
-
|
24
|
-
Get the
|
25
|
-
|
26
|
-
Returns:
|
27
|
-
The current DjangoConfig instance or None
|
28
|
-
"""
|
29
|
-
if self._config is None:
|
30
|
+
@classmethod
|
31
|
+
def get_config(cls) -> Optional["DjangoConfig"]:
|
32
|
+
"""Get the DjangoConfig instance automatically."""
|
33
|
+
if cls._config_instance is None:
|
30
34
|
try:
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
35
|
+
cls._config_instance = cls._discover_config()
|
36
|
+
except Exception:
|
37
|
+
# Return None if config discovery fails (e.g., during Django startup)
|
38
|
+
return None
|
39
|
+
return cls._config_instance
|
40
|
+
|
41
|
+
@classmethod
|
42
|
+
def _discover_config(cls) -> "DjangoConfig":
|
43
|
+
"""Discover the DjangoConfig instance from Django settings."""
|
44
|
+
try:
|
45
|
+
# Try to get config from Django settings module
|
46
|
+
settings_module = os.environ.get("DJANGO_SETTINGS_MODULE")
|
47
|
+
if settings_module:
|
48
|
+
settings_mod = importlib.import_module(settings_module)
|
49
|
+
if hasattr(settings_mod, "config"):
|
50
|
+
return settings_mod.config
|
51
|
+
|
52
|
+
# Fallback: try to create minimal config from Django settings
|
53
|
+
from django.conf import settings
|
54
|
+
from django_cfg.core.config import DjangoConfig
|
55
|
+
|
56
|
+
return DjangoConfig(
|
57
|
+
project_name=getattr(settings, "PROJECT_NAME", "Django Project"),
|
58
|
+
secret_key=settings.SECRET_KEY,
|
59
|
+
debug=settings.DEBUG,
|
60
|
+
allowed_hosts=settings.ALLOWED_HOSTS,
|
61
|
+
)
|
62
|
+
|
63
|
+
except Exception as e:
|
64
|
+
raise RuntimeError(f"Could not discover DjangoConfig instance: {e}")
|
65
|
+
|
66
|
+
@classmethod
|
67
|
+
def reset_config(cls):
|
68
|
+
"""Reset the cached config instance (useful for testing)."""
|
69
|
+
cls._config_instance = None
|
57
70
|
|
58
71
|
def set_config(self, config: Any) -> None:
|
59
72
|
"""
|
@@ -73,13 +86,12 @@ class BaseModule(ABC):
|
|
73
86
|
default: The default value to return if the key is not found
|
74
87
|
"""
|
75
88
|
try:
|
76
|
-
#
|
77
|
-
|
78
|
-
self._config = self.get_config()
|
89
|
+
# Get config using class method
|
90
|
+
config = self.get_config()
|
79
91
|
|
80
92
|
# If config is available, get the key
|
81
|
-
if
|
82
|
-
result = getattr(
|
93
|
+
if config is not None:
|
94
|
+
result = getattr(config, key, default)
|
83
95
|
return bool(result)
|
84
96
|
|
85
97
|
# Fallback to default if no config available
|
@@ -125,25 +137,39 @@ class BaseModule(ABC):
|
|
125
137
|
"""
|
126
138
|
return self._get_config_key('enable_leads', False)
|
127
139
|
|
140
|
+
def is_agents_enabled(self) -> bool:
|
141
|
+
"""
|
142
|
+
Check if django-cfg Agents is enabled.
|
143
|
+
|
144
|
+
Returns:
|
145
|
+
True if Agents is enabled, False otherwise
|
146
|
+
"""
|
147
|
+
return self._get_config_key('enable_agents', False)
|
148
|
+
|
149
|
+
def is_knowbase_enabled(self) -> bool:
|
150
|
+
"""
|
151
|
+
Check if django-cfg Knowbase is enabled.
|
152
|
+
|
153
|
+
Returns:
|
154
|
+
True if Knowbase is enabled, False otherwise
|
155
|
+
"""
|
156
|
+
return self._get_config_key('enable_knowbase', False)
|
157
|
+
|
128
158
|
def is_tasks_enabled(self) -> bool:
|
129
159
|
"""
|
130
|
-
Check if django-cfg Tasks
|
160
|
+
Check if django-cfg Tasks is enabled.
|
161
|
+
Auto-enables if knowbase or agents are enabled.
|
131
162
|
|
132
163
|
Returns:
|
133
164
|
True if Tasks is enabled, False otherwise
|
134
165
|
"""
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
if tasks_config is not None:
|
140
|
-
return getattr(tasks_config, 'enabled', False)
|
141
|
-
return False
|
142
|
-
except Exception:
|
143
|
-
return False
|
166
|
+
# Auto-enable if knowbase or agents are enabled
|
167
|
+
if self.is_knowbase_enabled() or self.is_agents_enabled():
|
168
|
+
return True
|
169
|
+
return self._get_config_key('enable_tasks', False)
|
144
170
|
|
145
171
|
|
146
172
|
# Export the base class
|
147
173
|
__all__ = [
|
148
|
-
"
|
174
|
+
"BaseCfgModule",
|
149
175
|
]
|
@@ -9,7 +9,7 @@ from typing import Optional, Dict, Any, Union, List
|
|
9
9
|
from datetime import datetime, date
|
10
10
|
from pathlib import Path
|
11
11
|
|
12
|
-
from django_cfg.modules import
|
12
|
+
from django_cfg.modules import BaseCfgModule
|
13
13
|
from .converter import CurrencyConverter
|
14
14
|
from .cache import CurrencyCache
|
15
15
|
|
@@ -31,7 +31,7 @@ class CurrencyConversionError(CurrencyError):
|
|
31
31
|
pass
|
32
32
|
|
33
33
|
|
34
|
-
class DjangoCurrency(
|
34
|
+
class DjangoCurrency(BaseCfgModule):
|
35
35
|
"""
|
36
36
|
Currency Service for django_cfg, configured via DjangoConfig.
|
37
37
|
|
@@ -11,10 +11,10 @@ from django.template.loader import render_to_string
|
|
11
11
|
from django.utils.html import strip_tags
|
12
12
|
from django.conf import settings
|
13
13
|
|
14
|
-
from . import
|
14
|
+
from . import BaseCfgModule
|
15
15
|
|
16
16
|
|
17
|
-
class DjangoEmailService(
|
17
|
+
class DjangoEmailService(BaseCfgModule):
|
18
18
|
"""
|
19
19
|
Auto-configuring email service that gets settings from DjangoConfig.
|
20
20
|
|