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.
- django_cfg/__init__.py +1 -1
- django_cfg/apps/accounts/admin/__init__.py +24 -8
- django_cfg/apps/accounts/admin/activity_admin.py +146 -0
- django_cfg/apps/accounts/admin/filters.py +98 -22
- django_cfg/apps/accounts/admin/group_admin.py +86 -0
- django_cfg/apps/accounts/admin/inlines.py +42 -13
- django_cfg/apps/accounts/admin/otp_admin.py +115 -0
- django_cfg/apps/accounts/admin/registration_admin.py +173 -0
- django_cfg/apps/accounts/admin/resources.py +123 -19
- django_cfg/apps/accounts/admin/twilio_admin.py +327 -0
- django_cfg/apps/accounts/admin/user_admin.py +362 -0
- django_cfg/apps/agents/admin/__init__.py +17 -4
- django_cfg/apps/agents/admin/execution_admin.py +204 -183
- django_cfg/apps/agents/admin/registry_admin.py +230 -255
- django_cfg/apps/agents/admin/toolsets_admin.py +274 -321
- django_cfg/apps/agents/core/__init__.py +1 -1
- django_cfg/apps/agents/core/django_agent.py +221 -0
- django_cfg/apps/agents/core/exceptions.py +14 -0
- django_cfg/apps/agents/core/orchestrator.py +18 -3
- django_cfg/apps/knowbase/admin/__init__.py +1 -1
- django_cfg/apps/knowbase/admin/archive_admin.py +352 -640
- django_cfg/apps/knowbase/admin/chat_admin.py +258 -192
- django_cfg/apps/knowbase/admin/document_admin.py +269 -262
- django_cfg/apps/knowbase/admin/external_data_admin.py +271 -489
- django_cfg/apps/knowbase/config/settings.py +21 -4
- django_cfg/apps/knowbase/views/chat_views.py +3 -0
- django_cfg/apps/leads/admin/__init__.py +3 -1
- django_cfg/apps/leads/admin/leads_admin.py +235 -35
- django_cfg/apps/maintenance/admin/__init__.py +2 -2
- django_cfg/apps/maintenance/admin/api_key_admin.py +125 -63
- django_cfg/apps/maintenance/admin/log_admin.py +143 -61
- django_cfg/apps/maintenance/admin/scheduled_admin.py +212 -301
- django_cfg/apps/maintenance/admin/site_admin.py +213 -352
- django_cfg/apps/newsletter/admin/__init__.py +29 -2
- django_cfg/apps/newsletter/admin/newsletter_admin.py +531 -193
- django_cfg/apps/payments/admin/__init__.py +18 -27
- django_cfg/apps/payments/admin/api_keys_admin.py +179 -546
- django_cfg/apps/payments/admin/balance_admin.py +166 -632
- django_cfg/apps/payments/admin/currencies_admin.py +235 -607
- django_cfg/apps/payments/admin/endpoint_groups_admin.py +127 -0
- django_cfg/apps/payments/admin/filters.py +83 -3
- django_cfg/apps/payments/admin/networks_admin.py +258 -0
- django_cfg/apps/payments/admin/payments_admin.py +171 -461
- django_cfg/apps/payments/admin/subscriptions_admin.py +119 -636
- django_cfg/apps/payments/admin/tariffs_admin.py +248 -0
- django_cfg/apps/payments/admin_interface/serializers/payment_serializers.py +105 -34
- django_cfg/apps/payments/admin_interface/templates/payments/payment_form.html +12 -16
- django_cfg/apps/payments/admin_interface/views/__init__.py +2 -0
- django_cfg/apps/payments/admin_interface/views/api/webhook_admin.py +13 -18
- django_cfg/apps/payments/management/commands/manage_currencies.py +236 -274
- django_cfg/apps/payments/management/commands/manage_providers.py +4 -1
- django_cfg/apps/payments/middleware/api_access.py +32 -6
- django_cfg/apps/payments/migrations/0002_currency_usd_rate_currency_usd_rate_updated_at.py +26 -0
- django_cfg/apps/payments/migrations/0003_remove_provider_currency_fields.py +28 -0
- django_cfg/apps/payments/migrations/0004_add_reserved_usd_field.py +30 -0
- django_cfg/apps/payments/models/balance.py +12 -0
- django_cfg/apps/payments/models/currencies.py +106 -32
- django_cfg/apps/payments/models/managers/currency_managers.py +65 -0
- django_cfg/apps/payments/services/core/currency_service.py +35 -28
- django_cfg/apps/payments/services/core/payment_service.py +1 -1
- django_cfg/apps/payments/services/providers/__init__.py +3 -0
- django_cfg/apps/payments/services/providers/base.py +95 -39
- django_cfg/apps/payments/services/providers/models/__init__.py +40 -0
- django_cfg/apps/payments/services/providers/models/base.py +122 -0
- django_cfg/apps/payments/services/providers/models/providers.py +87 -0
- django_cfg/apps/payments/services/providers/models/universal.py +48 -0
- django_cfg/apps/payments/services/providers/nowpayments/__init__.py +31 -0
- django_cfg/apps/payments/services/providers/nowpayments/config.py +70 -0
- django_cfg/apps/payments/services/providers/nowpayments/models.py +150 -0
- django_cfg/apps/payments/services/providers/nowpayments/parsers.py +879 -0
- django_cfg/apps/payments/services/providers/{nowpayments.py → nowpayments/provider.py} +240 -209
- django_cfg/apps/payments/services/providers/nowpayments/sync.py +196 -0
- django_cfg/apps/payments/services/providers/registry.py +4 -32
- django_cfg/apps/payments/services/providers/sync_service.py +277 -0
- django_cfg/apps/payments/static/payments/js/api-client.js +23 -5
- django_cfg/apps/payments/static/payments/js/payment-form.js +65 -8
- django_cfg/apps/payments/tasks/__init__.py +39 -0
- django_cfg/apps/payments/tasks/types.py +73 -0
- django_cfg/apps/payments/tasks/usage_tracking.py +308 -0
- django_cfg/apps/payments/templates/admin/payments/_components/dashboard_header.html +23 -0
- django_cfg/apps/payments/templates/admin/payments/_components/stats_card.html +25 -0
- django_cfg/apps/payments/templates/admin/payments/_components/stats_grid.html +16 -0
- django_cfg/apps/payments/templates/admin/payments/apikey/change_list.html +39 -0
- django_cfg/apps/payments/templates/admin/payments/balance/change_list.html +50 -0
- django_cfg/apps/payments/templates/admin/payments/currency/change_list.html +40 -0
- django_cfg/apps/payments/templates/admin/payments/payment/change_list.html +48 -0
- django_cfg/apps/payments/templates/admin/payments/subscription/change_list.html +48 -0
- django_cfg/apps/payments/urls_admin.py +1 -1
- django_cfg/apps/payments/views/api/currencies.py +5 -5
- django_cfg/apps/payments/views/overview/services.py +2 -2
- django_cfg/apps/payments/views/serializers/currencies.py +4 -3
- django_cfg/apps/support/admin/__init__.py +10 -1
- django_cfg/apps/support/admin/support_admin.py +338 -141
- django_cfg/apps/tasks/admin/__init__.py +11 -0
- django_cfg/apps/tasks/admin/tasks_admin.py +430 -0
- django_cfg/apps/urls.py +1 -2
- django_cfg/config.py +1 -1
- django_cfg/core/config.py +10 -5
- django_cfg/core/generation.py +1 -1
- django_cfg/management/commands/__init__.py +13 -1
- django_cfg/management/commands/app_agent_diagnose.py +470 -0
- django_cfg/management/commands/app_agent_generate.py +342 -0
- django_cfg/management/commands/app_agent_info.py +308 -0
- django_cfg/management/commands/migrate_all.py +9 -3
- django_cfg/management/commands/migrator.py +11 -6
- django_cfg/management/commands/rundramatiq.py +3 -2
- django_cfg/middleware/__init__.py +0 -2
- django_cfg/models/api_keys.py +115 -0
- django_cfg/modules/django_admin/__init__.py +64 -0
- django_cfg/modules/django_admin/decorators/__init__.py +13 -0
- django_cfg/modules/django_admin/decorators/actions.py +106 -0
- django_cfg/modules/django_admin/decorators/display.py +106 -0
- django_cfg/modules/django_admin/mixins/__init__.py +14 -0
- django_cfg/modules/django_admin/mixins/display_mixin.py +81 -0
- django_cfg/modules/django_admin/mixins/optimization_mixin.py +41 -0
- django_cfg/modules/django_admin/mixins/standalone_actions_mixin.py +202 -0
- django_cfg/modules/django_admin/models/__init__.py +20 -0
- django_cfg/modules/django_admin/models/action_models.py +33 -0
- django_cfg/modules/django_admin/models/badge_models.py +20 -0
- django_cfg/modules/django_admin/models/base.py +26 -0
- django_cfg/modules/django_admin/models/display_models.py +31 -0
- django_cfg/modules/django_admin/utils/badges.py +159 -0
- django_cfg/modules/django_admin/utils/displays.py +247 -0
- django_cfg/modules/django_app_agent/__init__.py +87 -0
- django_cfg/modules/django_app_agent/agents/__init__.py +40 -0
- django_cfg/modules/django_app_agent/agents/base/__init__.py +24 -0
- django_cfg/modules/django_app_agent/agents/base/agent.py +354 -0
- django_cfg/modules/django_app_agent/agents/base/context.py +236 -0
- django_cfg/modules/django_app_agent/agents/base/executor.py +430 -0
- django_cfg/modules/django_app_agent/agents/generation/__init__.py +12 -0
- django_cfg/modules/django_app_agent/agents/generation/app_generator/__init__.py +15 -0
- django_cfg/modules/django_app_agent/agents/generation/app_generator/config_validator.py +147 -0
- django_cfg/modules/django_app_agent/agents/generation/app_generator/main.py +99 -0
- django_cfg/modules/django_app_agent/agents/generation/app_generator/models.py +32 -0
- django_cfg/modules/django_app_agent/agents/generation/app_generator/prompt_manager.py +290 -0
- django_cfg/modules/django_app_agent/agents/interfaces.py +376 -0
- django_cfg/modules/django_app_agent/core/__init__.py +33 -0
- django_cfg/modules/django_app_agent/core/config.py +300 -0
- django_cfg/modules/django_app_agent/core/exceptions.py +359 -0
- django_cfg/modules/django_app_agent/models/__init__.py +71 -0
- django_cfg/modules/django_app_agent/models/base.py +283 -0
- django_cfg/modules/django_app_agent/models/context.py +496 -0
- django_cfg/modules/django_app_agent/models/enums.py +481 -0
- django_cfg/modules/django_app_agent/models/requests.py +500 -0
- django_cfg/modules/django_app_agent/models/responses.py +585 -0
- django_cfg/modules/django_app_agent/pytest.ini +6 -0
- django_cfg/modules/django_app_agent/services/__init__.py +42 -0
- django_cfg/modules/django_app_agent/services/app_generator/__init__.py +30 -0
- django_cfg/modules/django_app_agent/services/app_generator/ai_integration.py +133 -0
- django_cfg/modules/django_app_agent/services/app_generator/context.py +40 -0
- django_cfg/modules/django_app_agent/services/app_generator/main.py +202 -0
- django_cfg/modules/django_app_agent/services/app_generator/structure.py +316 -0
- django_cfg/modules/django_app_agent/services/app_generator/validation.py +125 -0
- django_cfg/modules/django_app_agent/services/base.py +437 -0
- django_cfg/modules/django_app_agent/services/context_builder/__init__.py +34 -0
- django_cfg/modules/django_app_agent/services/context_builder/code_extractor.py +141 -0
- django_cfg/modules/django_app_agent/services/context_builder/context_generator.py +276 -0
- django_cfg/modules/django_app_agent/services/context_builder/main.py +272 -0
- django_cfg/modules/django_app_agent/services/context_builder/models.py +40 -0
- django_cfg/modules/django_app_agent/services/context_builder/pattern_analyzer.py +85 -0
- django_cfg/modules/django_app_agent/services/project_scanner/__init__.py +31 -0
- django_cfg/modules/django_app_agent/services/project_scanner/app_discovery.py +311 -0
- django_cfg/modules/django_app_agent/services/project_scanner/main.py +221 -0
- django_cfg/modules/django_app_agent/services/project_scanner/models.py +59 -0
- django_cfg/modules/django_app_agent/services/project_scanner/pattern_detection.py +94 -0
- django_cfg/modules/django_app_agent/services/questioning_service/__init__.py +28 -0
- django_cfg/modules/django_app_agent/services/questioning_service/main.py +273 -0
- django_cfg/modules/django_app_agent/services/questioning_service/models.py +111 -0
- django_cfg/modules/django_app_agent/services/questioning_service/question_generator.py +251 -0
- django_cfg/modules/django_app_agent/services/questioning_service/response_processor.py +347 -0
- django_cfg/modules/django_app_agent/services/questioning_service/session_manager.py +356 -0
- django_cfg/modules/django_app_agent/services/report_service.py +332 -0
- django_cfg/modules/django_app_agent/services/template_manager/__init__.py +18 -0
- django_cfg/modules/django_app_agent/services/template_manager/jinja_engine.py +236 -0
- django_cfg/modules/django_app_agent/services/template_manager/main.py +159 -0
- django_cfg/modules/django_app_agent/services/template_manager/models.py +36 -0
- django_cfg/modules/django_app_agent/services/template_manager/template_loader.py +100 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/admin.py.j2 +105 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/apps.py.j2 +31 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/cfg_config.py.j2 +44 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/cfg_module.py.j2 +81 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/forms.py.j2 +107 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/models.py.j2 +139 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/serializers.py.j2 +91 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/tests.py.j2 +195 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/urls.py.j2 +35 -0
- django_cfg/modules/django_app_agent/services/template_manager/templates/views.py.j2 +211 -0
- django_cfg/modules/django_app_agent/services/template_manager/variable_processor.py +200 -0
- django_cfg/modules/django_app_agent/services/validation_service/__init__.py +25 -0
- django_cfg/modules/django_app_agent/services/validation_service/django_validator.py +333 -0
- django_cfg/modules/django_app_agent/services/validation_service/main.py +242 -0
- django_cfg/modules/django_app_agent/services/validation_service/models.py +66 -0
- django_cfg/modules/django_app_agent/services/validation_service/quality_validator.py +352 -0
- django_cfg/modules/django_app_agent/services/validation_service/security_validator.py +272 -0
- django_cfg/modules/django_app_agent/services/validation_service/syntax_validator.py +203 -0
- django_cfg/modules/django_app_agent/ui/__init__.py +25 -0
- django_cfg/modules/django_app_agent/ui/cli.py +419 -0
- django_cfg/modules/django_app_agent/ui/rich_components.py +622 -0
- django_cfg/modules/django_app_agent/utils/__init__.py +38 -0
- django_cfg/modules/django_app_agent/utils/logging.py +360 -0
- django_cfg/modules/django_app_agent/utils/validation.py +417 -0
- django_cfg/modules/django_currency/__init__.py +2 -2
- django_cfg/modules/django_currency/clients/__init__.py +2 -2
- django_cfg/modules/django_currency/clients/hybrid_client.py +587 -0
- django_cfg/modules/django_currency/core/converter.py +12 -12
- django_cfg/modules/django_currency/database/__init__.py +2 -2
- django_cfg/modules/django_currency/database/database_loader.py +93 -42
- django_cfg/modules/django_llm/llm/client.py +10 -2
- django_cfg/modules/django_unfold/callbacks/actions.py +1 -1
- django_cfg/modules/django_unfold/callbacks/statistics.py +1 -1
- django_cfg/modules/django_unfold/dashboard.py +14 -13
- django_cfg/modules/django_unfold/models/config.py +1 -1
- django_cfg/registry/core.py +3 -0
- django_cfg/registry/third_party.py +2 -2
- django_cfg/template_archive/django_sample.zip +0 -0
- {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/METADATA +2 -1
- {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/RECORD +224 -118
- django_cfg/apps/accounts/admin/activity.py +0 -96
- django_cfg/apps/accounts/admin/group.py +0 -17
- django_cfg/apps/accounts/admin/otp.py +0 -59
- django_cfg/apps/accounts/admin/registration_source.py +0 -97
- django_cfg/apps/accounts/admin/twilio_response.py +0 -227
- django_cfg/apps/accounts/admin/user.py +0 -300
- django_cfg/apps/agents/core/agent.py +0 -281
- django_cfg/apps/payments/admin_interface/old/payments/base.html +0 -175
- django_cfg/apps/payments/admin_interface/old/payments/components/dev_tool_card.html +0 -125
- django_cfg/apps/payments/admin_interface/old/payments/components/loading_spinner.html +0 -16
- django_cfg/apps/payments/admin_interface/old/payments/components/ngrok_status_card.html +0 -113
- django_cfg/apps/payments/admin_interface/old/payments/components/notification.html +0 -27
- django_cfg/apps/payments/admin_interface/old/payments/components/provider_card.html +0 -86
- django_cfg/apps/payments/admin_interface/old/payments/components/status_card.html +0 -35
- django_cfg/apps/payments/admin_interface/old/payments/currency_converter.html +0 -382
- django_cfg/apps/payments/admin_interface/old/payments/payment_dashboard.html +0 -309
- django_cfg/apps/payments/admin_interface/old/payments/payment_form.html +0 -303
- django_cfg/apps/payments/admin_interface/old/payments/payment_list.html +0 -382
- django_cfg/apps/payments/admin_interface/old/payments/payment_status.html +0 -500
- django_cfg/apps/payments/admin_interface/old/payments/webhook_dashboard.html +0 -518
- django_cfg/apps/payments/admin_interface/old/static/payments/css/components.css +0 -619
- django_cfg/apps/payments/admin_interface/old/static/payments/css/dashboard.css +0 -188
- django_cfg/apps/payments/admin_interface/old/static/payments/js/components.js +0 -545
- django_cfg/apps/payments/admin_interface/old/static/payments/js/ngrok-status.js +0 -163
- django_cfg/apps/payments/admin_interface/old/static/payments/js/utils.js +0 -412
- django_cfg/apps/tasks/admin.py +0 -320
- django_cfg/middleware/static_nocache.py +0 -55
- django_cfg/modules/django_currency/clients/yahoo_client.py +0 -157
- /django_cfg/modules/{django_unfold → django_admin}/icons/README.md +0 -0
- /django_cfg/modules/{django_unfold → django_admin}/icons/__init__.py +0 -0
- /django_cfg/modules/{django_unfold → django_admin}/icons/constants.py +0 -0
- /django_cfg/modules/{django_unfold → django_admin}/icons/generate_icons.py +0 -0
- {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/WHEEL +0 -0
- {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/entry_points.txt +0 -0
- {django_cfg-1.3.5.dist-info → django_cfg-1.3.9.dist-info}/licenses/LICENSE +0 -0
@@ -1,16 +1,29 @@
|
|
1
1
|
"""
|
2
|
-
|
2
|
+
Agents admin interfaces using Django Admin Utilities.
|
3
|
+
|
4
|
+
Modern, clean admin interfaces with Material Icons and consistent styling.
|
3
5
|
"""
|
4
6
|
|
5
|
-
from .
|
7
|
+
from django.contrib import admin
|
8
|
+
|
9
|
+
# Import all admin classes
|
6
10
|
from .execution_admin import AgentExecutionAdmin, WorkflowExecutionAdmin
|
11
|
+
from .registry_admin import AgentDefinitionAdmin, AgentTemplateAdmin
|
7
12
|
from .toolsets_admin import ToolExecutionAdmin, ApprovalLogAdmin, ToolsetConfigurationAdmin
|
8
13
|
|
14
|
+
# All models are registered in their respective admin files using @admin.register
|
15
|
+
# This provides:
|
16
|
+
# - Clean separation of concerns
|
17
|
+
# - Material Icons integration
|
18
|
+
# - Type-safe configurations
|
19
|
+
# - Performance optimizations
|
20
|
+
# - Consistent styling with django_admin module
|
21
|
+
|
9
22
|
__all__ = [
|
10
|
-
'AgentDefinitionAdmin',
|
11
|
-
'AgentTemplateAdmin',
|
12
23
|
'AgentExecutionAdmin',
|
13
24
|
'WorkflowExecutionAdmin',
|
25
|
+
'AgentDefinitionAdmin',
|
26
|
+
'AgentTemplateAdmin',
|
14
27
|
'ToolExecutionAdmin',
|
15
28
|
'ApprovalLogAdmin',
|
16
29
|
'ToolsetConfigurationAdmin',
|
@@ -1,9 +1,10 @@
|
|
1
1
|
"""
|
2
|
-
Execution admin interfaces
|
2
|
+
Execution admin interfaces using Django Admin Utilities.
|
3
|
+
|
4
|
+
Enhanced execution management with Material Icons and optimized queries.
|
3
5
|
"""
|
4
6
|
|
5
7
|
from django.contrib import admin, messages
|
6
|
-
from django.utils.html import format_html
|
7
8
|
from django.urls import reverse
|
8
9
|
from django.utils.safestring import mark_safe
|
9
10
|
from django.db import models
|
@@ -13,21 +14,32 @@ from django.db.models.fields.json import JSONField
|
|
13
14
|
from datetime import timedelta
|
14
15
|
from django_json_widget.widgets import JSONEditorWidget
|
15
16
|
from unfold.admin import ModelAdmin, TabularInline
|
16
|
-
from unfold.decorators import display, action
|
17
|
-
from unfold.enums import ActionVariant
|
18
17
|
from unfold.contrib.filters.admin import AutocompleteSelectFilter, AutocompleteSelectMultipleFilter
|
19
18
|
from unfold.contrib.forms.widgets import WysiwygWidget
|
20
19
|
from django_cfg import ExportMixin, ExportForm
|
21
20
|
|
21
|
+
from django_cfg.modules.django_admin import (
|
22
|
+
OptimizedModelAdmin,
|
23
|
+
DisplayMixin,
|
24
|
+
MoneyDisplayConfig,
|
25
|
+
StatusBadgeConfig,
|
26
|
+
DateTimeDisplayConfig,
|
27
|
+
Icons,
|
28
|
+
ActionVariant,
|
29
|
+
display,
|
30
|
+
action
|
31
|
+
)
|
32
|
+
from django_cfg.modules.django_admin.utils.badges import StatusBadge
|
33
|
+
|
22
34
|
from ..models.execution import AgentExecution, WorkflowExecution
|
23
35
|
|
24
36
|
|
25
37
|
class AgentExecutionInlineForWorkflow(TabularInline):
|
26
|
-
"""
|
38
|
+
"""Enhanced inline for agent executions within workflow."""
|
27
39
|
|
28
40
|
model = AgentExecution
|
29
41
|
verbose_name = "Agent Execution"
|
30
|
-
verbose_name_plural = "🔗 Workflow Steps
|
42
|
+
verbose_name_plural = "🔗 Workflow Steps"
|
31
43
|
extra = 0
|
32
44
|
max_num = 0
|
33
45
|
can_delete = False
|
@@ -58,32 +70,33 @@ class AgentExecutionInlineForWorkflow(TabularInline):
|
|
58
70
|
@display(description="Status")
|
59
71
|
def status_badge_inline(self, obj):
|
60
72
|
"""Status badge for inline display."""
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
color_class, obj.get_status_display()
|
73
|
+
status_config = StatusBadgeConfig(
|
74
|
+
custom_mappings={
|
75
|
+
'pending': 'warning',
|
76
|
+
'running': 'info',
|
77
|
+
'completed': 'success',
|
78
|
+
'failed': 'danger',
|
79
|
+
'cancelled': 'secondary'
|
80
|
+
},
|
81
|
+
show_icons=True,
|
82
|
+
icon=Icons.PLAY_ARROW
|
72
83
|
)
|
84
|
+
return self.display_status_auto(obj, 'status', status_config)
|
73
85
|
|
74
86
|
@display(description="Execution Time")
|
75
87
|
def execution_time_display(self, obj):
|
76
88
|
"""Execution time display for inline."""
|
77
89
|
if obj.execution_time:
|
78
90
|
return f"{obj.execution_time:.2f}s"
|
79
|
-
return "
|
91
|
+
return "—"
|
80
92
|
|
81
93
|
@display(description="Cost")
|
82
94
|
def cost_display_inline(self, obj):
|
83
95
|
"""Cost display for inline."""
|
84
96
|
if obj.cost:
|
85
|
-
|
86
|
-
|
97
|
+
config = MoneyDisplayConfig(currency="USD", show_sign=False)
|
98
|
+
return self.display_money_amount(obj, 'cost', config)
|
99
|
+
return "—"
|
87
100
|
|
88
101
|
def get_queryset(self, request):
|
89
102
|
"""Optimize queryset for inline display."""
|
@@ -91,29 +104,33 @@ class AgentExecutionInlineForWorkflow(TabularInline):
|
|
91
104
|
|
92
105
|
|
93
106
|
@admin.register(AgentExecution)
|
94
|
-
class AgentExecutionAdmin(ModelAdmin, ExportMixin):
|
95
|
-
"""
|
107
|
+
class AgentExecutionAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin, ExportMixin):
|
108
|
+
"""Enhanced admin for AgentExecution model using Django Admin Utilities."""
|
109
|
+
|
110
|
+
# Performance optimization
|
111
|
+
select_related_fields = ['user', 'workflow_execution', 'agent_definition']
|
96
112
|
|
97
113
|
# Export-only configuration
|
98
114
|
export_form_class = ExportForm
|
99
115
|
|
100
116
|
list_display = [
|
101
|
-
'id_display', 'agent_name_display', '
|
102
|
-
'
|
117
|
+
'id_display', 'agent_name_display', 'status_display', 'user_display',
|
118
|
+
'execution_time_display', 'tokens_display', 'cost_display', 'cached_display', 'created_at_display'
|
103
119
|
]
|
104
|
-
|
120
|
+
list_display_links = ['id_display', 'agent_name_display']
|
105
121
|
list_filter = [
|
106
122
|
'status', 'cached', 'agent_name', 'created_at',
|
107
123
|
('user', AutocompleteSelectFilter),
|
108
124
|
('workflow_execution', AutocompleteSelectFilter)
|
109
125
|
]
|
110
126
|
search_fields = ['agent_name', 'user__username', 'input_prompt', 'output_data']
|
111
|
-
autocomplete_fields = ['user', 'workflow_execution']
|
127
|
+
autocomplete_fields = ['user', 'workflow_execution', 'agent_definition']
|
112
128
|
readonly_fields = [
|
113
129
|
'id', 'execution_time', 'tokens_used', 'cost', 'cached',
|
114
130
|
'created_at', 'started_at', 'completed_at', 'duration_display',
|
115
131
|
'input_preview', 'output_preview', 'error_preview'
|
116
132
|
]
|
133
|
+
ordering = ['-created_at']
|
117
134
|
|
118
135
|
# Unfold form field overrides
|
119
136
|
formfield_overrides = {
|
@@ -123,7 +140,7 @@ class AgentExecutionAdmin(ModelAdmin, ExportMixin):
|
|
123
140
|
|
124
141
|
fieldsets = (
|
125
142
|
("🚀 Execution Info", {
|
126
|
-
'fields': ('id', 'agent_name', 'user', 'status'),
|
143
|
+
'fields': ('id', 'agent_name', 'agent_definition', 'user', 'status'),
|
127
144
|
'classes': ('tab',)
|
128
145
|
}),
|
129
146
|
("📝 Input/Output", {
|
@@ -149,134 +166,139 @@ class AgentExecutionAdmin(ModelAdmin, ExportMixin):
|
|
149
166
|
@display(description="ID")
|
150
167
|
def id_display(self, obj):
|
151
168
|
"""Enhanced ID display."""
|
152
|
-
|
153
|
-
|
154
|
-
str(obj.id)[:8]
|
169
|
+
config = StatusBadgeConfig(show_icons=True, icon=Icons.TAG)
|
170
|
+
return StatusBadge.create(
|
171
|
+
text=f"#{str(obj.id)[:8]}",
|
172
|
+
variant="secondary",
|
173
|
+
config=config
|
155
174
|
)
|
156
175
|
|
157
176
|
@display(description="Agent")
|
158
177
|
def agent_name_display(self, obj):
|
159
178
|
"""Enhanced agent name display."""
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
|
179
|
+
config = StatusBadgeConfig(show_icons=True, icon=Icons.SMART_TOY)
|
180
|
+
return StatusBadge.create(
|
181
|
+
text=obj.agent_name,
|
182
|
+
variant="primary",
|
183
|
+
config=config
|
165
184
|
)
|
166
185
|
|
167
186
|
@display(description="Status")
|
168
|
-
def
|
169
|
-
"""Status
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
'
|
180
|
-
color_class, obj.get_status_display()
|
187
|
+
def status_display(self, obj):
|
188
|
+
"""Status display with appropriate icons."""
|
189
|
+
status_config = StatusBadgeConfig(
|
190
|
+
custom_mappings={
|
191
|
+
'pending': 'warning',
|
192
|
+
'running': 'info',
|
193
|
+
'completed': 'success',
|
194
|
+
'failed': 'danger',
|
195
|
+
'cancelled': 'secondary'
|
196
|
+
},
|
197
|
+
show_icons=True,
|
198
|
+
icon=Icons.PLAY_ARROW if obj.status == 'running' else Icons.CHECK_CIRCLE if obj.status == 'completed' else Icons.ERROR if obj.status == 'failed' else Icons.SCHEDULE
|
181
199
|
)
|
200
|
+
return self.display_status_auto(obj, 'status', status_config)
|
182
201
|
|
183
|
-
@display(description="
|
184
|
-
def
|
185
|
-
"""
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
193
|
-
|
202
|
+
@display(description="User")
|
203
|
+
def user_display(self, obj):
|
204
|
+
"""User display with avatar."""
|
205
|
+
if not obj.user:
|
206
|
+
return "—"
|
207
|
+
return self.display_user_simple(obj.user)
|
208
|
+
|
209
|
+
@display(description="Time")
|
210
|
+
def execution_time_display(self, obj):
|
211
|
+
"""Execution time display."""
|
212
|
+
if obj.execution_time:
|
213
|
+
return f"{obj.execution_time:.2f}s"
|
214
|
+
return "—"
|
215
|
+
|
216
|
+
@display(description="Tokens")
|
217
|
+
def tokens_display(self, obj):
|
218
|
+
"""Tokens display."""
|
219
|
+
if obj.tokens_used:
|
220
|
+
return f"{obj.tokens_used:,}"
|
221
|
+
return "—"
|
194
222
|
|
195
223
|
@display(description="Cost")
|
196
224
|
def cost_display(self, obj):
|
197
225
|
"""Cost display with formatting."""
|
198
226
|
if obj.cost:
|
199
|
-
|
200
|
-
|
201
|
-
|
227
|
+
config = MoneyDisplayConfig(
|
228
|
+
currency="USD",
|
229
|
+
show_sign=False,
|
230
|
+
smart_decimal_places=True
|
202
231
|
)
|
203
|
-
|
232
|
+
return self.display_money_amount(obj, 'cost', config)
|
233
|
+
return "—"
|
204
234
|
|
205
235
|
@display(description="Cached", boolean=True)
|
206
|
-
def
|
207
|
-
"""Cached status
|
236
|
+
def cached_display(self, obj):
|
237
|
+
"""Cached status display."""
|
208
238
|
return obj.cached
|
209
239
|
|
240
|
+
@display(description="Created")
|
241
|
+
def created_at_display(self, obj):
|
242
|
+
"""Created time with relative display."""
|
243
|
+
config = DateTimeDisplayConfig(show_relative=True)
|
244
|
+
return self.display_datetime_relative(obj, 'created_at', config)
|
245
|
+
|
210
246
|
@display(description="Duration")
|
211
247
|
def duration_display(self, obj):
|
212
248
|
"""Display execution duration."""
|
213
249
|
if obj.duration:
|
214
250
|
return f"{obj.duration:.2f}s"
|
215
|
-
return "
|
251
|
+
return "—"
|
216
252
|
|
217
253
|
@display(description="Input Preview")
|
218
254
|
def input_preview(self, obj):
|
219
255
|
"""Preview of input prompt."""
|
220
256
|
if not obj.input_prompt:
|
221
|
-
return "
|
222
|
-
|
223
|
-
return format_html(
|
224
|
-
'<div class="text-sm text-gray-600 max-w-md">{}</div>',
|
225
|
-
preview
|
226
|
-
)
|
257
|
+
return "—"
|
258
|
+
return obj.input_prompt[:200] + "..." if len(obj.input_prompt) > 200 else obj.input_prompt
|
227
259
|
|
228
260
|
@display(description="Output Preview")
|
229
261
|
def output_preview(self, obj):
|
230
262
|
"""Preview of output data."""
|
231
263
|
if not obj.output_data:
|
232
|
-
return "
|
233
|
-
|
234
|
-
return format_html(
|
235
|
-
'<div class="text-sm text-gray-600 max-w-md">{}</div>',
|
236
|
-
preview
|
237
|
-
)
|
264
|
+
return "—"
|
265
|
+
return str(obj.output_data)[:200] + "..." if len(str(obj.output_data)) > 200 else str(obj.output_data)
|
238
266
|
|
239
267
|
@display(description="Error Preview")
|
240
268
|
def error_preview(self, obj):
|
241
269
|
"""Preview of error message."""
|
242
270
|
if not obj.error_message:
|
243
|
-
return "
|
244
|
-
|
245
|
-
return format_html(
|
246
|
-
'<div class="text-sm text-red-600 max-w-md">{}</div>',
|
247
|
-
preview
|
248
|
-
)
|
271
|
+
return "—"
|
272
|
+
return obj.error_message[:200] + "..." if len(obj.error_message) > 200 else obj.error_message
|
249
273
|
|
250
|
-
@action(description="Retry failed executions",
|
274
|
+
@action(description="Retry failed executions", variant=ActionVariant.WARNING)
|
251
275
|
def retry_failed_executions(self, request, queryset):
|
252
276
|
"""Retry failed executions."""
|
253
277
|
failed_count = queryset.filter(status='failed').count()
|
254
278
|
messages.warning(request, f"Retry functionality not implemented yet. {failed_count} failed executions selected.")
|
255
279
|
|
256
|
-
@action(description="Clear cache",
|
280
|
+
@action(description="Clear cache", variant=ActionVariant.INFO)
|
257
281
|
def clear_cache(self, request, queryset):
|
258
282
|
"""Clear cache for selected executions."""
|
259
283
|
cached_count = queryset.filter(cached=True).count()
|
260
284
|
messages.info(request, f"Cache clearing not implemented yet. {cached_count} cached executions selected.")
|
261
|
-
|
262
|
-
def get_queryset(self, request):
|
263
|
-
"""Optimize queryset."""
|
264
|
-
return super().get_queryset(request).select_related('user', 'workflow_execution')
|
265
285
|
|
266
286
|
|
267
287
|
@admin.register(WorkflowExecution)
|
268
|
-
class WorkflowExecutionAdmin(ModelAdmin, ExportMixin):
|
269
|
-
"""
|
288
|
+
class WorkflowExecutionAdmin(OptimizedModelAdmin, DisplayMixin, ModelAdmin, ExportMixin):
|
289
|
+
"""Enhanced admin for WorkflowExecution model using Django Admin Utilities."""
|
290
|
+
|
291
|
+
# Performance optimization
|
292
|
+
select_related_fields = ['user']
|
270
293
|
|
271
294
|
# Export-only configuration
|
272
295
|
export_form_class = ExportForm
|
273
296
|
|
274
297
|
list_display = [
|
275
|
-
'id_display', 'name_display', '
|
276
|
-
'progress_display', '
|
298
|
+
'id_display', 'name_display', 'pattern_display', 'status_display', 'user_display',
|
299
|
+
'progress_display', 'total_time_display', 'total_tokens_display', 'cost_display', 'created_at_display'
|
277
300
|
]
|
278
|
-
|
279
|
-
inlines = [AgentExecutionInlineForWorkflow]
|
301
|
+
list_display_links = ['id_display', 'name_display']
|
280
302
|
list_filter = [
|
281
303
|
'status', 'pattern', 'created_at',
|
282
304
|
('user', AutocompleteSelectFilter)
|
@@ -288,6 +310,8 @@ class WorkflowExecutionAdmin(ModelAdmin, ExportMixin):
|
|
288
310
|
'created_at', 'started_at', 'completed_at', 'duration_display',
|
289
311
|
'progress_percentage', 'input_preview', 'output_preview', 'error_preview'
|
290
312
|
]
|
313
|
+
ordering = ['-created_at']
|
314
|
+
inlines = [AgentExecutionInlineForWorkflow]
|
291
315
|
|
292
316
|
# Unfold form field overrides
|
293
317
|
formfield_overrides = {
|
@@ -327,141 +351,138 @@ class WorkflowExecutionAdmin(ModelAdmin, ExportMixin):
|
|
327
351
|
@display(description="ID")
|
328
352
|
def id_display(self, obj):
|
329
353
|
"""Enhanced ID display."""
|
330
|
-
|
331
|
-
|
332
|
-
str(obj.id)[:8]
|
354
|
+
config = StatusBadgeConfig(show_icons=True, icon=Icons.TAG)
|
355
|
+
return StatusBadge.create(
|
356
|
+
text=f"#{str(obj.id)[:8]}",
|
357
|
+
variant="secondary",
|
358
|
+
config=config
|
333
359
|
)
|
334
360
|
|
335
361
|
@display(description="Workflow")
|
336
362
|
def name_display(self, obj):
|
337
363
|
"""Enhanced workflow name display."""
|
338
|
-
|
339
|
-
|
340
|
-
|
341
|
-
|
342
|
-
|
364
|
+
config = StatusBadgeConfig(show_icons=True, icon=Icons.ACCOUNT_TREE)
|
365
|
+
return StatusBadge.create(
|
366
|
+
text=obj.name,
|
367
|
+
variant="primary",
|
368
|
+
config=config
|
343
369
|
)
|
344
370
|
|
345
371
|
@display(description="Pattern")
|
346
|
-
def
|
347
|
-
"""Pattern
|
348
|
-
|
349
|
-
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
|
355
|
-
|
356
|
-
'
|
357
|
-
|
372
|
+
def pattern_display(self, obj):
|
373
|
+
"""Pattern display with appropriate icons."""
|
374
|
+
pattern_config = StatusBadgeConfig(
|
375
|
+
custom_mappings={
|
376
|
+
'sequential': 'info',
|
377
|
+
'parallel': 'success',
|
378
|
+
'conditional': 'warning',
|
379
|
+
'loop': 'secondary'
|
380
|
+
},
|
381
|
+
show_icons=True,
|
382
|
+
icon=Icons.LINEAR_SCALE if obj.pattern == 'sequential' else Icons.CALL_SPLIT if obj.pattern == 'parallel' else Icons.DEVICE_HUB if obj.pattern == 'conditional' else Icons.LOOP
|
383
|
+
)
|
384
|
+
return self.display_status_auto(
|
385
|
+
type('obj', (), {'pattern': obj.pattern.title() if obj.pattern else 'Unknown'})(),
|
386
|
+
'pattern',
|
387
|
+
pattern_config
|
358
388
|
)
|
359
389
|
|
360
390
|
@display(description="Status")
|
361
|
-
def
|
362
|
-
"""Status
|
363
|
-
|
364
|
-
|
365
|
-
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
|
371
|
-
|
372
|
-
'
|
373
|
-
color_class, obj.get_status_display()
|
391
|
+
def status_display(self, obj):
|
392
|
+
"""Status display with appropriate icons."""
|
393
|
+
status_config = StatusBadgeConfig(
|
394
|
+
custom_mappings={
|
395
|
+
'pending': 'warning',
|
396
|
+
'running': 'info',
|
397
|
+
'completed': 'success',
|
398
|
+
'failed': 'danger',
|
399
|
+
'cancelled': 'secondary'
|
400
|
+
},
|
401
|
+
show_icons=True,
|
402
|
+
icon=Icons.PLAY_ARROW if obj.status == 'running' else Icons.CHECK_CIRCLE if obj.status == 'completed' else Icons.ERROR if obj.status == 'failed' else Icons.SCHEDULE
|
374
403
|
)
|
404
|
+
return self.display_status_auto(obj, 'status', status_config)
|
405
|
+
|
406
|
+
@display(description="User")
|
407
|
+
def user_display(self, obj):
|
408
|
+
"""User display with avatar."""
|
409
|
+
if not obj.user:
|
410
|
+
return "—"
|
411
|
+
return self.display_user_simple(obj.user)
|
375
412
|
|
376
413
|
@display(description="Progress")
|
377
414
|
def progress_display(self, obj):
|
378
|
-
"""Display progress
|
379
|
-
|
380
|
-
|
381
|
-
|
382
|
-
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
|
389
|
-
|
390
|
-
|
391
|
-
|
392
|
-
|
393
|
-
|
394
|
-
return format_html(
|
395
|
-
'<div class="text-sm space-y-1">'
|
396
|
-
'<div><span class="font-medium">Time:</span> {}</div>'
|
397
|
-
'<div><span class="font-medium">Tokens:</span> {}</div>'
|
398
|
-
'</div>',
|
399
|
-
f"{obj.total_execution_time:.2f}s" if obj.total_execution_time else "-",
|
400
|
-
f"{obj.total_tokens_used:,}" if obj.total_tokens_used else "-"
|
401
|
-
)
|
415
|
+
"""Display progress percentage."""
|
416
|
+
return f"{int(obj.progress_percentage)}%"
|
417
|
+
|
418
|
+
@display(description="Time")
|
419
|
+
def total_time_display(self, obj):
|
420
|
+
"""Total execution time display."""
|
421
|
+
if obj.total_execution_time:
|
422
|
+
return f"{obj.total_execution_time:.2f}s"
|
423
|
+
return "—"
|
424
|
+
|
425
|
+
@display(description="Tokens")
|
426
|
+
def total_tokens_display(self, obj):
|
427
|
+
"""Total tokens display."""
|
428
|
+
if obj.total_tokens_used:
|
429
|
+
return f"{obj.total_tokens_used:,}"
|
430
|
+
return "—"
|
402
431
|
|
403
432
|
@display(description="Cost")
|
404
433
|
def cost_display(self, obj):
|
405
434
|
"""Cost display with formatting."""
|
406
435
|
if obj.total_cost:
|
407
|
-
|
408
|
-
|
409
|
-
|
436
|
+
config = MoneyDisplayConfig(
|
437
|
+
currency="USD",
|
438
|
+
show_sign=False,
|
439
|
+
smart_decimal_places=True
|
410
440
|
)
|
411
|
-
|
441
|
+
return self.display_money_amount(obj, 'total_cost', config)
|
442
|
+
return "—"
|
443
|
+
|
444
|
+
@display(description="Created")
|
445
|
+
def created_at_display(self, obj):
|
446
|
+
"""Created time with relative display."""
|
447
|
+
config = DateTimeDisplayConfig(show_relative=True)
|
448
|
+
return self.display_datetime_relative(obj, 'created_at', config)
|
412
449
|
|
413
450
|
@display(description="Duration")
|
414
451
|
def duration_display(self, obj):
|
415
452
|
"""Display workflow duration."""
|
416
453
|
if obj.duration:
|
417
454
|
return f"{obj.duration:.2f}s"
|
418
|
-
return "
|
455
|
+
return "—"
|
419
456
|
|
420
457
|
@display(description="Input Preview")
|
421
458
|
def input_preview(self, obj):
|
422
459
|
"""Preview of input prompt."""
|
423
460
|
if not obj.input_prompt:
|
424
|
-
return "
|
425
|
-
|
426
|
-
return format_html(
|
427
|
-
'<div class="text-sm text-gray-600 max-w-md">{}</div>',
|
428
|
-
preview
|
429
|
-
)
|
461
|
+
return "—"
|
462
|
+
return obj.input_prompt[:200] + "..." if len(obj.input_prompt) > 200 else obj.input_prompt
|
430
463
|
|
431
464
|
@display(description="Output Preview")
|
432
465
|
def output_preview(self, obj):
|
433
466
|
"""Preview of final output."""
|
434
467
|
if not obj.final_output:
|
435
|
-
return "
|
436
|
-
|
437
|
-
return format_html(
|
438
|
-
'<div class="text-sm text-gray-600 max-w-md">{}</div>',
|
439
|
-
preview
|
440
|
-
)
|
468
|
+
return "—"
|
469
|
+
return str(obj.final_output)[:200] + "..." if len(str(obj.final_output)) > 200 else str(obj.final_output)
|
441
470
|
|
442
471
|
@display(description="Error Preview")
|
443
472
|
def error_preview(self, obj):
|
444
473
|
"""Preview of error message."""
|
445
474
|
if not obj.error_message:
|
446
|
-
return "
|
447
|
-
|
448
|
-
return format_html(
|
449
|
-
'<div class="text-sm text-red-600 max-w-md">{}</div>',
|
450
|
-
preview
|
451
|
-
)
|
475
|
+
return "—"
|
476
|
+
return obj.error_message[:200] + "..." if len(obj.error_message) > 200 else obj.error_message
|
452
477
|
|
453
|
-
@action(description="Cancel running workflows",
|
478
|
+
@action(description="Cancel running workflows", variant=ActionVariant.DANGER)
|
454
479
|
def cancel_running_workflows(self, request, queryset):
|
455
480
|
"""Cancel running workflows."""
|
456
481
|
running_count = queryset.filter(status='running').count()
|
457
482
|
messages.warning(request, f"Cancel functionality not implemented yet. {running_count} running workflows selected.")
|
458
483
|
|
459
|
-
@action(description="Retry failed workflows",
|
484
|
+
@action(description="Retry failed workflows", variant=ActionVariant.WARNING)
|
460
485
|
def retry_failed_workflows(self, request, queryset):
|
461
486
|
"""Retry failed workflows."""
|
462
487
|
failed_count = queryset.filter(status='failed').count()
|
463
|
-
messages.warning(request, f"Retry functionality not implemented yet. {failed_count} failed workflows selected.")
|
464
|
-
|
465
|
-
def get_queryset(self, request):
|
466
|
-
"""Optimize queryset."""
|
467
|
-
return super().get_queryset(request).select_related('user')
|
488
|
+
messages.warning(request, f"Retry functionality not implemented yet. {failed_count} failed workflows selected.")
|