django-cfg 1.3.5__py3-none-any.whl → 1.3.9__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.
Files changed (252) hide show
  1. django_cfg/__init__.py +1 -1
  2. django_cfg/apps/accounts/admin/__init__.py +24 -8
  3. django_cfg/apps/accounts/admin/activity_admin.py +146 -0
  4. django_cfg/apps/accounts/admin/filters.py +98 -22
  5. django_cfg/apps/accounts/admin/group_admin.py +86 -0
  6. django_cfg/apps/accounts/admin/inlines.py +42 -13
  7. django_cfg/apps/accounts/admin/otp_admin.py +115 -0
  8. django_cfg/apps/accounts/admin/registration_admin.py +173 -0
  9. django_cfg/apps/accounts/admin/resources.py +123 -19
  10. django_cfg/apps/accounts/admin/twilio_admin.py +327 -0
  11. django_cfg/apps/accounts/admin/user_admin.py +362 -0
  12. django_cfg/apps/agents/admin/__init__.py +17 -4
  13. django_cfg/apps/agents/admin/execution_admin.py +204 -183
  14. django_cfg/apps/agents/admin/registry_admin.py +230 -255
  15. django_cfg/apps/agents/admin/toolsets_admin.py +274 -321
  16. django_cfg/apps/agents/core/__init__.py +1 -1
  17. django_cfg/apps/agents/core/django_agent.py +221 -0
  18. django_cfg/apps/agents/core/exceptions.py +14 -0
  19. django_cfg/apps/agents/core/orchestrator.py +18 -3
  20. django_cfg/apps/knowbase/admin/__init__.py +1 -1
  21. django_cfg/apps/knowbase/admin/archive_admin.py +352 -640
  22. django_cfg/apps/knowbase/admin/chat_admin.py +258 -192
  23. django_cfg/apps/knowbase/admin/document_admin.py +269 -262
  24. django_cfg/apps/knowbase/admin/external_data_admin.py +271 -489
  25. django_cfg/apps/knowbase/config/settings.py +21 -4
  26. django_cfg/apps/knowbase/views/chat_views.py +3 -0
  27. django_cfg/apps/leads/admin/__init__.py +3 -1
  28. django_cfg/apps/leads/admin/leads_admin.py +235 -35
  29. django_cfg/apps/maintenance/admin/__init__.py +2 -2
  30. django_cfg/apps/maintenance/admin/api_key_admin.py +125 -63
  31. django_cfg/apps/maintenance/admin/log_admin.py +143 -61
  32. django_cfg/apps/maintenance/admin/scheduled_admin.py +212 -301
  33. django_cfg/apps/maintenance/admin/site_admin.py +213 -352
  34. django_cfg/apps/newsletter/admin/__init__.py +29 -2
  35. django_cfg/apps/newsletter/admin/newsletter_admin.py +531 -193
  36. django_cfg/apps/payments/admin/__init__.py +18 -27
  37. django_cfg/apps/payments/admin/api_keys_admin.py +179 -546
  38. django_cfg/apps/payments/admin/balance_admin.py +166 -632
  39. django_cfg/apps/payments/admin/currencies_admin.py +235 -607
  40. django_cfg/apps/payments/admin/endpoint_groups_admin.py +127 -0
  41. django_cfg/apps/payments/admin/filters.py +83 -3
  42. django_cfg/apps/payments/admin/networks_admin.py +258 -0
  43. django_cfg/apps/payments/admin/payments_admin.py +171 -461
  44. django_cfg/apps/payments/admin/subscriptions_admin.py +119 -636
  45. django_cfg/apps/payments/admin/tariffs_admin.py +248 -0
  46. django_cfg/apps/payments/admin_interface/serializers/payment_serializers.py +105 -34
  47. django_cfg/apps/payments/admin_interface/templates/payments/payment_form.html +12 -16
  48. django_cfg/apps/payments/admin_interface/views/__init__.py +2 -0
  49. django_cfg/apps/payments/admin_interface/views/api/webhook_admin.py +13 -18
  50. django_cfg/apps/payments/management/commands/manage_currencies.py +236 -274
  51. django_cfg/apps/payments/management/commands/manage_providers.py +4 -1
  52. django_cfg/apps/payments/middleware/api_access.py +32 -6
  53. django_cfg/apps/payments/migrations/0002_currency_usd_rate_currency_usd_rate_updated_at.py +26 -0
  54. django_cfg/apps/payments/migrations/0003_remove_provider_currency_fields.py +28 -0
  55. django_cfg/apps/payments/migrations/0004_add_reserved_usd_field.py +30 -0
  56. django_cfg/apps/payments/models/balance.py +12 -0
  57. django_cfg/apps/payments/models/currencies.py +106 -32
  58. django_cfg/apps/payments/models/managers/currency_managers.py +65 -0
  59. django_cfg/apps/payments/services/core/currency_service.py +35 -28
  60. django_cfg/apps/payments/services/core/payment_service.py +1 -1
  61. django_cfg/apps/payments/services/providers/__init__.py +3 -0
  62. django_cfg/apps/payments/services/providers/base.py +95 -39
  63. django_cfg/apps/payments/services/providers/models/__init__.py +40 -0
  64. django_cfg/apps/payments/services/providers/models/base.py +122 -0
  65. django_cfg/apps/payments/services/providers/models/providers.py +87 -0
  66. django_cfg/apps/payments/services/providers/models/universal.py +48 -0
  67. django_cfg/apps/payments/services/providers/nowpayments/__init__.py +31 -0
  68. django_cfg/apps/payments/services/providers/nowpayments/config.py +70 -0
  69. django_cfg/apps/payments/services/providers/nowpayments/models.py +150 -0
  70. django_cfg/apps/payments/services/providers/nowpayments/parsers.py +879 -0
  71. django_cfg/apps/payments/services/providers/{nowpayments.py → nowpayments/provider.py} +240 -209
  72. django_cfg/apps/payments/services/providers/nowpayments/sync.py +196 -0
  73. django_cfg/apps/payments/services/providers/registry.py +4 -32
  74. django_cfg/apps/payments/services/providers/sync_service.py +277 -0
  75. django_cfg/apps/payments/static/payments/js/api-client.js +23 -5
  76. django_cfg/apps/payments/static/payments/js/payment-form.js +65 -8
  77. django_cfg/apps/payments/tasks/__init__.py +39 -0
  78. django_cfg/apps/payments/tasks/types.py +73 -0
  79. django_cfg/apps/payments/tasks/usage_tracking.py +308 -0
  80. django_cfg/apps/payments/templates/admin/payments/_components/dashboard_header.html +23 -0
  81. django_cfg/apps/payments/templates/admin/payments/_components/stats_card.html +25 -0
  82. django_cfg/apps/payments/templates/admin/payments/_components/stats_grid.html +16 -0
  83. django_cfg/apps/payments/templates/admin/payments/apikey/change_list.html +39 -0
  84. django_cfg/apps/payments/templates/admin/payments/balance/change_list.html +50 -0
  85. django_cfg/apps/payments/templates/admin/payments/currency/change_list.html +40 -0
  86. django_cfg/apps/payments/templates/admin/payments/payment/change_list.html +48 -0
  87. django_cfg/apps/payments/templates/admin/payments/subscription/change_list.html +48 -0
  88. django_cfg/apps/payments/urls_admin.py +1 -1
  89. django_cfg/apps/payments/views/api/currencies.py +5 -5
  90. django_cfg/apps/payments/views/overview/services.py +2 -2
  91. django_cfg/apps/payments/views/serializers/currencies.py +4 -3
  92. django_cfg/apps/support/admin/__init__.py +10 -1
  93. django_cfg/apps/support/admin/support_admin.py +338 -141
  94. django_cfg/apps/tasks/admin/__init__.py +11 -0
  95. django_cfg/apps/tasks/admin/tasks_admin.py +430 -0
  96. django_cfg/apps/urls.py +1 -2
  97. django_cfg/config.py +1 -1
  98. django_cfg/core/config.py +10 -5
  99. django_cfg/core/generation.py +1 -1
  100. django_cfg/management/commands/__init__.py +13 -1
  101. django_cfg/management/commands/app_agent_diagnose.py +470 -0
  102. django_cfg/management/commands/app_agent_generate.py +342 -0
  103. django_cfg/management/commands/app_agent_info.py +308 -0
  104. django_cfg/management/commands/migrate_all.py +9 -3
  105. django_cfg/management/commands/migrator.py +11 -6
  106. django_cfg/management/commands/rundramatiq.py +3 -2
  107. django_cfg/middleware/__init__.py +0 -2
  108. django_cfg/models/api_keys.py +115 -0
  109. django_cfg/modules/django_admin/__init__.py +64 -0
  110. django_cfg/modules/django_admin/decorators/__init__.py +13 -0
  111. django_cfg/modules/django_admin/decorators/actions.py +106 -0
  112. django_cfg/modules/django_admin/decorators/display.py +106 -0
  113. django_cfg/modules/django_admin/mixins/__init__.py +14 -0
  114. django_cfg/modules/django_admin/mixins/display_mixin.py +81 -0
  115. django_cfg/modules/django_admin/mixins/optimization_mixin.py +41 -0
  116. django_cfg/modules/django_admin/mixins/standalone_actions_mixin.py +202 -0
  117. django_cfg/modules/django_admin/models/__init__.py +20 -0
  118. django_cfg/modules/django_admin/models/action_models.py +33 -0
  119. django_cfg/modules/django_admin/models/badge_models.py +20 -0
  120. django_cfg/modules/django_admin/models/base.py +26 -0
  121. django_cfg/modules/django_admin/models/display_models.py +31 -0
  122. django_cfg/modules/django_admin/utils/badges.py +159 -0
  123. django_cfg/modules/django_admin/utils/displays.py +247 -0
  124. django_cfg/modules/django_app_agent/__init__.py +87 -0
  125. django_cfg/modules/django_app_agent/agents/__init__.py +40 -0
  126. django_cfg/modules/django_app_agent/agents/base/__init__.py +24 -0
  127. django_cfg/modules/django_app_agent/agents/base/agent.py +354 -0
  128. django_cfg/modules/django_app_agent/agents/base/context.py +236 -0
  129. django_cfg/modules/django_app_agent/agents/base/executor.py +430 -0
  130. django_cfg/modules/django_app_agent/agents/generation/__init__.py +12 -0
  131. django_cfg/modules/django_app_agent/agents/generation/app_generator/__init__.py +15 -0
  132. django_cfg/modules/django_app_agent/agents/generation/app_generator/config_validator.py +147 -0
  133. django_cfg/modules/django_app_agent/agents/generation/app_generator/main.py +99 -0
  134. django_cfg/modules/django_app_agent/agents/generation/app_generator/models.py +32 -0
  135. django_cfg/modules/django_app_agent/agents/generation/app_generator/prompt_manager.py +290 -0
  136. django_cfg/modules/django_app_agent/agents/interfaces.py +376 -0
  137. django_cfg/modules/django_app_agent/core/__init__.py +33 -0
  138. django_cfg/modules/django_app_agent/core/config.py +300 -0
  139. django_cfg/modules/django_app_agent/core/exceptions.py +359 -0
  140. django_cfg/modules/django_app_agent/models/__init__.py +71 -0
  141. django_cfg/modules/django_app_agent/models/base.py +283 -0
  142. django_cfg/modules/django_app_agent/models/context.py +496 -0
  143. django_cfg/modules/django_app_agent/models/enums.py +481 -0
  144. django_cfg/modules/django_app_agent/models/requests.py +500 -0
  145. django_cfg/modules/django_app_agent/models/responses.py +585 -0
  146. django_cfg/modules/django_app_agent/pytest.ini +6 -0
  147. django_cfg/modules/django_app_agent/services/__init__.py +42 -0
  148. django_cfg/modules/django_app_agent/services/app_generator/__init__.py +30 -0
  149. django_cfg/modules/django_app_agent/services/app_generator/ai_integration.py +133 -0
  150. django_cfg/modules/django_app_agent/services/app_generator/context.py +40 -0
  151. django_cfg/modules/django_app_agent/services/app_generator/main.py +202 -0
  152. django_cfg/modules/django_app_agent/services/app_generator/structure.py +316 -0
  153. django_cfg/modules/django_app_agent/services/app_generator/validation.py +125 -0
  154. django_cfg/modules/django_app_agent/services/base.py +437 -0
  155. django_cfg/modules/django_app_agent/services/context_builder/__init__.py +34 -0
  156. django_cfg/modules/django_app_agent/services/context_builder/code_extractor.py +141 -0
  157. django_cfg/modules/django_app_agent/services/context_builder/context_generator.py +276 -0
  158. django_cfg/modules/django_app_agent/services/context_builder/main.py +272 -0
  159. django_cfg/modules/django_app_agent/services/context_builder/models.py +40 -0
  160. django_cfg/modules/django_app_agent/services/context_builder/pattern_analyzer.py +85 -0
  161. django_cfg/modules/django_app_agent/services/project_scanner/__init__.py +31 -0
  162. django_cfg/modules/django_app_agent/services/project_scanner/app_discovery.py +311 -0
  163. django_cfg/modules/django_app_agent/services/project_scanner/main.py +221 -0
  164. django_cfg/modules/django_app_agent/services/project_scanner/models.py +59 -0
  165. django_cfg/modules/django_app_agent/services/project_scanner/pattern_detection.py +94 -0
  166. django_cfg/modules/django_app_agent/services/questioning_service/__init__.py +28 -0
  167. django_cfg/modules/django_app_agent/services/questioning_service/main.py +273 -0
  168. django_cfg/modules/django_app_agent/services/questioning_service/models.py +111 -0
  169. django_cfg/modules/django_app_agent/services/questioning_service/question_generator.py +251 -0
  170. django_cfg/modules/django_app_agent/services/questioning_service/response_processor.py +347 -0
  171. django_cfg/modules/django_app_agent/services/questioning_service/session_manager.py +356 -0
  172. django_cfg/modules/django_app_agent/services/report_service.py +332 -0
  173. django_cfg/modules/django_app_agent/services/template_manager/__init__.py +18 -0
  174. django_cfg/modules/django_app_agent/services/template_manager/jinja_engine.py +236 -0
  175. django_cfg/modules/django_app_agent/services/template_manager/main.py +159 -0
  176. django_cfg/modules/django_app_agent/services/template_manager/models.py +36 -0
  177. django_cfg/modules/django_app_agent/services/template_manager/template_loader.py +100 -0
  178. django_cfg/modules/django_app_agent/services/template_manager/templates/admin.py.j2 +105 -0
  179. django_cfg/modules/django_app_agent/services/template_manager/templates/apps.py.j2 +31 -0
  180. django_cfg/modules/django_app_agent/services/template_manager/templates/cfg_config.py.j2 +44 -0
  181. django_cfg/modules/django_app_agent/services/template_manager/templates/cfg_module.py.j2 +81 -0
  182. django_cfg/modules/django_app_agent/services/template_manager/templates/forms.py.j2 +107 -0
  183. django_cfg/modules/django_app_agent/services/template_manager/templates/models.py.j2 +139 -0
  184. django_cfg/modules/django_app_agent/services/template_manager/templates/serializers.py.j2 +91 -0
  185. django_cfg/modules/django_app_agent/services/template_manager/templates/tests.py.j2 +195 -0
  186. django_cfg/modules/django_app_agent/services/template_manager/templates/urls.py.j2 +35 -0
  187. django_cfg/modules/django_app_agent/services/template_manager/templates/views.py.j2 +211 -0
  188. django_cfg/modules/django_app_agent/services/template_manager/variable_processor.py +200 -0
  189. django_cfg/modules/django_app_agent/services/validation_service/__init__.py +25 -0
  190. django_cfg/modules/django_app_agent/services/validation_service/django_validator.py +333 -0
  191. django_cfg/modules/django_app_agent/services/validation_service/main.py +242 -0
  192. django_cfg/modules/django_app_agent/services/validation_service/models.py +66 -0
  193. django_cfg/modules/django_app_agent/services/validation_service/quality_validator.py +352 -0
  194. django_cfg/modules/django_app_agent/services/validation_service/security_validator.py +272 -0
  195. django_cfg/modules/django_app_agent/services/validation_service/syntax_validator.py +203 -0
  196. django_cfg/modules/django_app_agent/ui/__init__.py +25 -0
  197. django_cfg/modules/django_app_agent/ui/cli.py +419 -0
  198. django_cfg/modules/django_app_agent/ui/rich_components.py +622 -0
  199. django_cfg/modules/django_app_agent/utils/__init__.py +38 -0
  200. django_cfg/modules/django_app_agent/utils/logging.py +360 -0
  201. django_cfg/modules/django_app_agent/utils/validation.py +417 -0
  202. django_cfg/modules/django_currency/__init__.py +2 -2
  203. django_cfg/modules/django_currency/clients/__init__.py +2 -2
  204. django_cfg/modules/django_currency/clients/hybrid_client.py +587 -0
  205. django_cfg/modules/django_currency/core/converter.py +12 -12
  206. django_cfg/modules/django_currency/database/__init__.py +2 -2
  207. django_cfg/modules/django_currency/database/database_loader.py +93 -42
  208. django_cfg/modules/django_llm/llm/client.py +10 -2
  209. django_cfg/modules/django_unfold/callbacks/actions.py +1 -1
  210. django_cfg/modules/django_unfold/callbacks/statistics.py +1 -1
  211. django_cfg/modules/django_unfold/dashboard.py +14 -13
  212. django_cfg/modules/django_unfold/models/config.py +1 -1
  213. django_cfg/registry/core.py +3 -0
  214. django_cfg/registry/third_party.py +2 -2
  215. django_cfg/template_archive/django_sample.zip +0 -0
  216. {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/METADATA +2 -1
  217. {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/RECORD +224 -118
  218. django_cfg/apps/accounts/admin/activity.py +0 -96
  219. django_cfg/apps/accounts/admin/group.py +0 -17
  220. django_cfg/apps/accounts/admin/otp.py +0 -59
  221. django_cfg/apps/accounts/admin/registration_source.py +0 -97
  222. django_cfg/apps/accounts/admin/twilio_response.py +0 -227
  223. django_cfg/apps/accounts/admin/user.py +0 -300
  224. django_cfg/apps/agents/core/agent.py +0 -281
  225. django_cfg/apps/payments/admin_interface/old/payments/base.html +0 -175
  226. django_cfg/apps/payments/admin_interface/old/payments/components/dev_tool_card.html +0 -125
  227. django_cfg/apps/payments/admin_interface/old/payments/components/loading_spinner.html +0 -16
  228. django_cfg/apps/payments/admin_interface/old/payments/components/ngrok_status_card.html +0 -113
  229. django_cfg/apps/payments/admin_interface/old/payments/components/notification.html +0 -27
  230. django_cfg/apps/payments/admin_interface/old/payments/components/provider_card.html +0 -86
  231. django_cfg/apps/payments/admin_interface/old/payments/components/status_card.html +0 -35
  232. django_cfg/apps/payments/admin_interface/old/payments/currency_converter.html +0 -382
  233. django_cfg/apps/payments/admin_interface/old/payments/payment_dashboard.html +0 -309
  234. django_cfg/apps/payments/admin_interface/old/payments/payment_form.html +0 -303
  235. django_cfg/apps/payments/admin_interface/old/payments/payment_list.html +0 -382
  236. django_cfg/apps/payments/admin_interface/old/payments/payment_status.html +0 -500
  237. django_cfg/apps/payments/admin_interface/old/payments/webhook_dashboard.html +0 -518
  238. django_cfg/apps/payments/admin_interface/old/static/payments/css/components.css +0 -619
  239. django_cfg/apps/payments/admin_interface/old/static/payments/css/dashboard.css +0 -188
  240. django_cfg/apps/payments/admin_interface/old/static/payments/js/components.js +0 -545
  241. django_cfg/apps/payments/admin_interface/old/static/payments/js/ngrok-status.js +0 -163
  242. django_cfg/apps/payments/admin_interface/old/static/payments/js/utils.js +0 -412
  243. django_cfg/apps/tasks/admin.py +0 -320
  244. django_cfg/middleware/static_nocache.py +0 -55
  245. django_cfg/modules/django_currency/clients/yahoo_client.py +0 -157
  246. /django_cfg/modules/{django_unfold → django_admin}/icons/README.md +0 -0
  247. /django_cfg/modules/{django_unfold → django_admin}/icons/__init__.py +0 -0
  248. /django_cfg/modules/{django_unfold → django_admin}/icons/constants.py +0 -0
  249. /django_cfg/modules/{django_unfold → django_admin}/icons/generate_icons.py +0 -0
  250. {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/WHEEL +0 -0
  251. {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/entry_points.txt +0 -0
  252. {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/licenses/LICENSE +0 -0
@@ -0,0 +1,360 @@
1
+ """
2
+ Structured logging utilities for Django App Agent Module.
3
+
4
+ This module provides comprehensive logging functionality with:
5
+ - Structured JSON logging
6
+ - Context-aware log entries
7
+ - Performance tracking
8
+ - Agent operation logging
9
+ - Integration with Django logging
10
+ """
11
+
12
+ import logging
13
+ import json
14
+ import time
15
+ import uuid
16
+ from typing import Any, Dict, Optional, Callable, TypeVar, ParamSpec
17
+ from functools import wraps
18
+ from pathlib import Path
19
+ from datetime import datetime, timezone
20
+ from contextlib import contextmanager
21
+ from contextvars import ContextVar
22
+
23
+ from pydantic import BaseModel, Field, ConfigDict
24
+
25
+ from ..core.config import LogLevel
26
+
27
+ # Type variables for decorators
28
+ P = ParamSpec('P')
29
+ T = TypeVar('T')
30
+
31
+ # Context variables for structured logging
32
+ correlation_id_var: ContextVar[Optional[str]] = ContextVar('correlation_id', default=None)
33
+ operation_context_var: ContextVar[Optional[str]] = ContextVar('operation_context', default=None)
34
+
35
+
36
+ class LogEntry(BaseModel):
37
+ """Structured log entry model."""
38
+
39
+ model_config = ConfigDict(
40
+ extra='forbid',
41
+ validate_assignment=True
42
+ )
43
+
44
+ timestamp: str = Field(description="ISO timestamp")
45
+ level: str = Field(description="Log level")
46
+ message: str = Field(description="Log message")
47
+ module: str = Field(description="Module name")
48
+ operation: Optional[str] = Field(default=None, description="Current operation")
49
+ correlation_id: Optional[str] = Field(default=None, description="Correlation ID")
50
+ component: str = Field(description="Component that generated the log")
51
+ metadata: Dict[str, Any] = Field(default_factory=dict, description="Additional metadata")
52
+
53
+ @classmethod
54
+ def create(
55
+ cls,
56
+ level: str,
57
+ message: str,
58
+ component: str,
59
+ *,
60
+ operation: Optional[str] = None,
61
+ correlation_id: Optional[str] = None,
62
+ **metadata: Any
63
+ ) -> "LogEntry":
64
+ """Create a structured log entry."""
65
+ return cls(
66
+ timestamp=datetime.now(timezone.utc).isoformat(),
67
+ level=level,
68
+ message=message,
69
+ module="django_app_agent",
70
+ operation=operation or operation_context_var.get(),
71
+ correlation_id=correlation_id or correlation_id_var.get(),
72
+ component=component,
73
+ metadata=metadata
74
+ )
75
+
76
+
77
+ class StructuredFormatter(logging.Formatter):
78
+ """Custom formatter for structured JSON logging."""
79
+
80
+ def format(self, record: logging.LogRecord) -> str:
81
+ """Format log record as structured JSON."""
82
+ # Extract structured data if present
83
+ if hasattr(record, 'structured_data'):
84
+ log_entry = record.structured_data
85
+ else:
86
+ # Create structured entry from standard log record
87
+ log_entry = LogEntry.create(
88
+ level=record.levelname,
89
+ message=record.getMessage(),
90
+ component=record.name,
91
+ filename=getattr(record, 'filename', ''),
92
+ lineno=getattr(record, 'lineno', 0),
93
+ funcName=getattr(record, 'funcName', '')
94
+ )
95
+
96
+ return json.dumps(log_entry.model_dump(), ensure_ascii=False)
97
+
98
+
99
+ class StructuredLogger:
100
+ """Structured logger for Django App Agent operations."""
101
+
102
+ def __init__(self, component: str, logger: Optional[logging.Logger] = None):
103
+ """Initialize structured logger.
104
+
105
+ Args:
106
+ component: Component name for logging context
107
+ logger: Optional logger instance (creates one if not provided)
108
+ """
109
+ self.component = component
110
+ self.logger = logger or logging.getLogger(f"django_app_agent.{component}")
111
+
112
+ def _log(
113
+ self,
114
+ level: str,
115
+ message: str,
116
+ *,
117
+ operation: Optional[str] = None,
118
+ correlation_id: Optional[str] = None,
119
+ **metadata: Any
120
+ ) -> None:
121
+ """Internal logging method."""
122
+ log_entry = LogEntry.create(
123
+ level=level,
124
+ message=message,
125
+ component=self.component,
126
+ operation=operation,
127
+ correlation_id=correlation_id,
128
+ **metadata
129
+ )
130
+
131
+ # Get numeric log level
132
+ numeric_level = getattr(logging, level)
133
+
134
+ # Create log record with structured data
135
+ record = self.logger.makeRecord(
136
+ name=self.logger.name,
137
+ level=numeric_level,
138
+ fn="",
139
+ lno=0,
140
+ msg=message,
141
+ args=(),
142
+ exc_info=None
143
+ )
144
+ record.structured_data = log_entry
145
+
146
+ self.logger.handle(record)
147
+
148
+ def debug(self, message: str, **metadata: Any) -> None:
149
+ """Log debug message."""
150
+ self._log("DEBUG", message, **metadata)
151
+
152
+ def info(self, message: str, **metadata: Any) -> None:
153
+ """Log info message."""
154
+ self._log("INFO", message, **metadata)
155
+
156
+ def warning(self, message: str, **metadata: Any) -> None:
157
+ """Log warning message."""
158
+ self._log("WARNING", message, **metadata)
159
+
160
+ def error(self, message: str, **metadata: Any) -> None:
161
+ """Log error message."""
162
+ self._log("ERROR", message, **metadata)
163
+
164
+ def critical(self, message: str, **metadata: Any) -> None:
165
+ """Log critical message."""
166
+ self._log("CRITICAL", message, **metadata)
167
+
168
+ @contextmanager
169
+ def operation_context(self, operation: str, correlation_id: Optional[str] = None):
170
+ """Context manager for operation logging."""
171
+ if correlation_id is None:
172
+ correlation_id = str(uuid.uuid4())
173
+
174
+ # Set context variables
175
+ correlation_token = correlation_id_var.set(correlation_id)
176
+ operation_token = operation_context_var.set(operation)
177
+
178
+ self.info(
179
+ f"Starting operation: {operation}",
180
+ operation=operation,
181
+ correlation_id=correlation_id
182
+ )
183
+
184
+ start_time = time.time()
185
+
186
+ try:
187
+ yield correlation_id
188
+ except Exception as e:
189
+ self.error(
190
+ f"Operation failed: {operation}",
191
+ operation=operation,
192
+ correlation_id=correlation_id,
193
+ error=str(e),
194
+ error_type=type(e).__name__
195
+ )
196
+ raise
197
+ finally:
198
+ execution_time = time.time() - start_time
199
+ self.info(
200
+ f"Completed operation: {operation}",
201
+ operation=operation,
202
+ correlation_id=correlation_id,
203
+ execution_time_seconds=execution_time
204
+ )
205
+
206
+ # Reset context variables
207
+ correlation_id_var.reset(correlation_token)
208
+ operation_context_var.reset(operation_token)
209
+
210
+
211
+ def setup_logging(
212
+ level: LogLevel = LogLevel.INFO,
213
+ log_file: Optional[Path] = None,
214
+ enable_structured: bool = True
215
+ ) -> None:
216
+ """Set up logging configuration for Django App Agent Module.
217
+
218
+ Args:
219
+ level: Logging level
220
+ log_file: Optional log file path
221
+ enable_structured: Whether to use structured JSON logging
222
+ """
223
+ # Get root logger for the module
224
+ logger = logging.getLogger("django_app_agent")
225
+ logger.setLevel(getattr(logging, level.value))
226
+
227
+ # Clear existing handlers
228
+ logger.handlers.clear()
229
+
230
+ # Console handler
231
+ console_handler = logging.StreamHandler()
232
+ console_handler.setLevel(getattr(logging, level.value))
233
+
234
+ if enable_structured:
235
+ console_handler.setFormatter(StructuredFormatter())
236
+ else:
237
+ console_handler.setFormatter(
238
+ logging.Formatter(
239
+ '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
240
+ )
241
+ )
242
+
243
+ logger.addHandler(console_handler)
244
+
245
+ # File handler if specified
246
+ if log_file:
247
+ log_file.parent.mkdir(parents=True, exist_ok=True)
248
+ file_handler = logging.FileHandler(log_file)
249
+ file_handler.setLevel(getattr(logging, level.value))
250
+ file_handler.setFormatter(StructuredFormatter())
251
+ logger.addHandler(file_handler)
252
+
253
+ # Prevent propagation to avoid duplicate logs
254
+ logger.propagate = False
255
+
256
+
257
+ def get_logger(component: str) -> StructuredLogger:
258
+ """Get a structured logger for a component.
259
+
260
+ Args:
261
+ component: Component name
262
+
263
+ Returns:
264
+ Structured logger instance
265
+ """
266
+ return StructuredLogger(component)
267
+
268
+
269
+ def log_execution_time(operation: str) -> Callable[[Callable[P, T]], Callable[P, T]]:
270
+ """Decorator to log execution time of functions.
271
+
272
+ Args:
273
+ operation: Operation name for logging
274
+
275
+ Returns:
276
+ Decorated function
277
+ """
278
+ def decorator(func: Callable[P, T]) -> Callable[P, T]:
279
+ @wraps(func)
280
+ def wrapper(*args: P.args, **kwargs: P.kwargs) -> T:
281
+ logger = get_logger(func.__module__ or "unknown")
282
+
283
+ with logger.operation_context(operation):
284
+ start_time = time.time()
285
+ try:
286
+ result = func(*args, **kwargs)
287
+ execution_time = time.time() - start_time
288
+ logger.info(
289
+ f"Function {func.__name__} completed",
290
+ function_name=func.__name__,
291
+ execution_time_seconds=execution_time
292
+ )
293
+ return result
294
+ except Exception as e:
295
+ execution_time = time.time() - start_time
296
+ logger.error(
297
+ f"Function {func.__name__} failed",
298
+ function_name=func.__name__,
299
+ execution_time_seconds=execution_time,
300
+ error=str(e),
301
+ error_type=type(e).__name__
302
+ )
303
+ raise
304
+
305
+ return wrapper
306
+ return decorator
307
+
308
+
309
+ def log_agent_operation(
310
+ agent_name: str,
311
+ operation: str
312
+ ) -> Callable[[Callable[P, T]], Callable[P, T]]:
313
+ """Decorator to log AI agent operations.
314
+
315
+ Args:
316
+ agent_name: Name of the AI agent
317
+ operation: Operation being performed
318
+
319
+ Returns:
320
+ Decorated function
321
+ """
322
+ def decorator(func: Callable[P, T]) -> Callable[P, T]:
323
+ @wraps(func)
324
+ def wrapper(*args: P.args, **kwargs: P.kwargs) -> T:
325
+ logger = get_logger(f"agents.{agent_name}")
326
+
327
+ with logger.operation_context(f"{agent_name}.{operation}"):
328
+ logger.info(
329
+ f"Agent {agent_name} starting {operation}",
330
+ agent_name=agent_name,
331
+ operation=operation
332
+ )
333
+
334
+ start_time = time.time()
335
+ try:
336
+ result = func(*args, **kwargs)
337
+ execution_time = time.time() - start_time
338
+ logger.info(
339
+ f"Agent {agent_name} completed {operation}",
340
+ agent_name=agent_name,
341
+ operation=operation,
342
+ execution_time_seconds=execution_time,
343
+ success=True
344
+ )
345
+ return result
346
+ except Exception as e:
347
+ execution_time = time.time() - start_time
348
+ logger.error(
349
+ f"Agent {agent_name} failed {operation}",
350
+ agent_name=agent_name,
351
+ operation=operation,
352
+ execution_time_seconds=execution_time,
353
+ success=False,
354
+ error=str(e),
355
+ error_type=type(e).__name__
356
+ )
357
+ raise
358
+
359
+ return wrapper
360
+ return decorator