ruby_llm-agents 1.3.3 → 2.0.0
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.
- checksums.yaml +4 -4
- data/README.md +101 -334
- data/app/controllers/concerns/ruby_llm/agents/sortable.rb +0 -1
- data/app/controllers/ruby_llm/agents/agents_controller.rb +5 -56
- data/app/controllers/ruby_llm/agents/dashboard_controller.rb +22 -106
- data/app/controllers/ruby_llm/agents/executions_controller.rb +4 -114
- data/app/controllers/ruby_llm/agents/tenants_controller.rb +30 -2
- data/app/helpers/ruby_llm/agents/application_helper.rb +19 -53
- data/app/models/ruby_llm/agents/execution/analytics.rb +13 -54
- data/app/models/ruby_llm/agents/execution/scopes.rb +61 -14
- data/app/models/ruby_llm/agents/execution.rb +46 -10
- data/app/models/ruby_llm/agents/execution_detail.rb +18 -0
- data/app/models/ruby_llm/agents/tenant/budgetable.rb +132 -24
- data/app/models/ruby_llm/agents/tenant/incrementable.rb +117 -0
- data/app/models/ruby_llm/agents/tenant/resettable.rb +128 -0
- data/app/models/ruby_llm/agents/tenant/trackable.rb +46 -12
- data/app/models/ruby_llm/agents/tenant.rb +2 -3
- data/app/models/ruby_llm/agents/tenant_budget.rb +6 -3
- data/app/services/ruby_llm/agents/agent_registry.rb +6 -112
- data/app/views/layouts/ruby_llm/agents/application.html.erb +87 -252
- data/app/views/ruby_llm/agents/agents/_config_agent.html.erb +71 -218
- data/app/views/ruby_llm/agents/agents/_config_embedder.html.erb +20 -63
- data/app/views/ruby_llm/agents/agents/_config_image_generator.html.erb +44 -131
- data/app/views/ruby_llm/agents/agents/_config_moderator.html.erb +16 -57
- data/app/views/ruby_llm/agents/agents/_config_speaker.html.erb +39 -104
- data/app/views/ruby_llm/agents/agents/_config_transcriber.html.erb +29 -82
- data/app/views/ruby_llm/agents/agents/_empty_state.html.erb +4 -14
- data/app/views/ruby_llm/agents/agents/index.html.erb +105 -274
- data/app/views/ruby_llm/agents/agents/show.html.erb +248 -378
- data/app/views/ruby_llm/agents/dashboard/_action_center.html.erb +29 -52
- data/app/views/ruby_llm/agents/dashboard/_tenant_budget.html.erb +73 -99
- data/app/views/ruby_llm/agents/dashboard/index.html.erb +228 -433
- data/app/views/ruby_llm/agents/executions/_execution.html.erb +1 -1
- data/app/views/ruby_llm/agents/executions/_filters.html.erb +4 -25
- data/app/views/ruby_llm/agents/executions/_list.html.erb +111 -152
- data/app/views/ruby_llm/agents/executions/index.html.erb +5 -7
- data/app/views/ruby_llm/agents/executions/show.html.erb +528 -989
- data/app/views/ruby_llm/agents/shared/_agent_type_badge.html.erb +5 -21
- data/app/views/ruby_llm/agents/shared/_executions_table.html.erb +70 -191
- data/app/views/ruby_llm/agents/shared/_filter_dropdown.html.erb +16 -44
- data/app/views/ruby_llm/agents/shared/_select_dropdown.html.erb +12 -41
- data/app/views/ruby_llm/agents/shared/_status_badge.html.erb +11 -65
- data/app/views/ruby_llm/agents/shared/_tenant_filter.html.erb +6 -5
- data/app/views/ruby_llm/agents/system_config/show.html.erb +240 -351
- data/app/views/ruby_llm/agents/tenants/_form.html.erb +67 -77
- data/app/views/ruby_llm/agents/tenants/edit.html.erb +7 -9
- data/app/views/ruby_llm/agents/tenants/index.html.erb +100 -122
- data/app/views/ruby_llm/agents/tenants/show.html.erb +146 -336
- data/config/routes.rb +0 -13
- data/lib/generators/ruby_llm_agents/install_generator.rb +9 -14
- data/lib/generators/ruby_llm_agents/migrate_structure_generator.rb +2 -12
- data/lib/generators/ruby_llm_agents/restructure_generator.rb +0 -2
- data/lib/generators/ruby_llm_agents/templates/add_usage_counters_to_tenants_migration.rb.tt +37 -0
- data/lib/generators/ruby_llm_agents/templates/agent.rb.tt +1 -2
- data/lib/generators/ruby_llm_agents/templates/application_agent.rb.tt +1 -1
- data/lib/generators/ruby_llm_agents/templates/application_image_pipeline.rb.tt +0 -1
- data/lib/generators/ruby_llm_agents/templates/create_execution_details_migration.rb.tt +27 -0
- data/lib/generators/ruby_llm_agents/templates/create_tenants_migration.rb.tt +25 -0
- data/lib/generators/ruby_llm_agents/templates/image_pipeline.rb.tt +0 -1
- data/lib/generators/ruby_llm_agents/templates/initializer.rb.tt +9 -12
- data/lib/generators/ruby_llm_agents/templates/migration.rb.tt +40 -71
- data/lib/generators/ruby_llm_agents/templates/remove_agent_version_migration.rb.tt +13 -0
- data/lib/generators/ruby_llm_agents/templates/remove_workflow_columns_migration.rb.tt +19 -0
- data/lib/generators/ruby_llm_agents/templates/skills/AGENTS.md.tt +2 -4
- data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_PIPELINES.md.tt +0 -1
- data/lib/generators/ruby_llm_agents/templates/split_execution_details_migration.rb.tt +232 -0
- data/lib/generators/ruby_llm_agents/upgrade_generator.rb +58 -262
- data/lib/ruby_llm/agents/audio/speaker.rb +0 -1
- data/lib/ruby_llm/agents/audio/transcriber.rb +0 -1
- data/lib/ruby_llm/agents/base_agent.rb +52 -6
- data/lib/ruby_llm/agents/core/base/callbacks.rb +142 -0
- data/lib/ruby_llm/agents/core/base.rb +23 -55
- data/lib/ruby_llm/agents/core/configuration.rb +58 -117
- data/lib/ruby_llm/agents/core/errors.rb +0 -58
- data/lib/ruby_llm/agents/core/instrumentation.rb +157 -110
- data/lib/ruby_llm/agents/core/llm_tenant.rb +8 -7
- data/lib/ruby_llm/agents/core/version.rb +1 -1
- data/lib/ruby_llm/agents/dsl/base.rb +157 -17
- data/lib/ruby_llm/agents/dsl/caching.rb +33 -2
- data/lib/ruby_llm/agents/dsl/reliability.rb +148 -0
- data/lib/ruby_llm/agents/dsl.rb +1 -2
- data/lib/ruby_llm/agents/image/analyzer/execution.rb +1 -2
- data/lib/ruby_llm/agents/image/background_remover/execution.rb +1 -2
- data/lib/ruby_llm/agents/image/concerns/image_operation_dsl.rb +1 -13
- data/lib/ruby_llm/agents/image/concerns/image_operation_execution.rb +2 -2
- data/lib/ruby_llm/agents/image/editor/dsl.rb +0 -14
- data/lib/ruby_llm/agents/image/editor/execution.rb +1 -10
- data/lib/ruby_llm/agents/image/editor.rb +0 -1
- data/lib/ruby_llm/agents/image/generator.rb +0 -21
- data/lib/ruby_llm/agents/image/pipeline/dsl.rb +0 -13
- data/lib/ruby_llm/agents/image/pipeline/execution.rb +0 -1
- data/lib/ruby_llm/agents/image/transformer/dsl.rb +0 -13
- data/lib/ruby_llm/agents/image/transformer/execution.rb +1 -10
- data/lib/ruby_llm/agents/image/transformer.rb +0 -1
- data/lib/ruby_llm/agents/image/upscaler/execution.rb +1 -2
- data/lib/ruby_llm/agents/image/variator/execution.rb +1 -2
- data/lib/ruby_llm/agents/infrastructure/alert_manager.rb +78 -173
- data/lib/ruby_llm/agents/infrastructure/attempt_tracker.rb +1 -0
- data/lib/ruby_llm/agents/infrastructure/budget/budget_query.rb +66 -2
- data/lib/ruby_llm/agents/infrastructure/budget/spend_recorder.rb +0 -12
- data/lib/ruby_llm/agents/infrastructure/circuit_breaker.rb +10 -13
- data/lib/ruby_llm/agents/infrastructure/reliability.rb +37 -2
- data/lib/ruby_llm/agents/pipeline/context.rb +0 -1
- data/lib/ruby_llm/agents/pipeline/middleware/budget.rb +28 -4
- data/lib/ruby_llm/agents/pipeline/middleware/cache.rb +3 -10
- data/lib/ruby_llm/agents/pipeline/middleware/instrumentation.rb +88 -55
- data/lib/ruby_llm/agents/pipeline/middleware/tenant.rb +5 -41
- data/lib/ruby_llm/agents/rails/engine.rb +6 -6
- data/lib/ruby_llm/agents/results/base.rb +1 -49
- data/lib/ruby_llm/agents/text/embedder.rb +0 -1
- data/lib/ruby_llm/agents.rb +1 -9
- data/lib/tasks/ruby_llm_agents.rake +34 -0
- metadata +12 -81
- data/app/controllers/ruby_llm/agents/api_configurations_controller.rb +0 -214
- data/app/controllers/ruby_llm/agents/workflows_controller.rb +0 -544
- data/app/mailers/ruby_llm/agents/alert_mailer.rb +0 -84
- data/app/mailers/ruby_llm/agents/application_mailer.rb +0 -28
- data/app/models/ruby_llm/agents/api_configuration.rb +0 -386
- data/app/models/ruby_llm/agents/execution/workflow.rb +0 -170
- data/app/models/ruby_llm/agents/tenant/configurable.rb +0 -135
- data/app/views/ruby_llm/agents/agents/_agent.html.erb +0 -98
- data/app/views/ruby_llm/agents/agents/_version_comparison.html.erb +0 -186
- data/app/views/ruby_llm/agents/agents/_workflow.html.erb +0 -126
- data/app/views/ruby_llm/agents/alert_mailer/alert_notification.html.erb +0 -107
- data/app/views/ruby_llm/agents/alert_mailer/alert_notification.text.erb +0 -18
- data/app/views/ruby_llm/agents/api_configurations/_api_key_field.html.erb +0 -34
- data/app/views/ruby_llm/agents/api_configurations/_form.html.erb +0 -288
- data/app/views/ruby_llm/agents/api_configurations/edit.html.erb +0 -95
- data/app/views/ruby_llm/agents/api_configurations/edit_tenant.html.erb +0 -97
- data/app/views/ruby_llm/agents/api_configurations/show.html.erb +0 -214
- data/app/views/ruby_llm/agents/api_configurations/tenant.html.erb +0 -179
- data/app/views/ruby_llm/agents/dashboard/_agent_comparison.html.erb +0 -73
- data/app/views/ruby_llm/agents/dashboard/_alerts_feed.html.erb +0 -62
- data/app/views/ruby_llm/agents/dashboard/_breaker_strip.html.erb +0 -47
- data/app/views/ruby_llm/agents/dashboard/_budgets_bar.html.erb +0 -75
- data/app/views/ruby_llm/agents/dashboard/_model_comparison.html.erb +0 -56
- data/app/views/ruby_llm/agents/dashboard/_model_cost_breakdown.html.erb +0 -115
- data/app/views/ruby_llm/agents/dashboard/_now_strip.html.erb +0 -59
- data/app/views/ruby_llm/agents/dashboard/_top_errors.html.erb +0 -60
- data/app/views/ruby_llm/agents/executions/_workflow_summary.html.erb +0 -86
- data/app/views/ruby_llm/agents/executions/dry_run.html.erb +0 -149
- data/app/views/ruby_llm/agents/shared/_breadcrumbs.html.erb +0 -48
- data/app/views/ruby_llm/agents/shared/_nav_link.html.erb +0 -27
- data/app/views/ruby_llm/agents/shared/_stat_card.html.erb +0 -14
- data/app/views/ruby_llm/agents/shared/_workflow_type_badge.html.erb +0 -35
- data/app/views/ruby_llm/agents/workflows/_empty_state.html.erb +0 -22
- data/app/views/ruby_llm/agents/workflows/_step_performance.html.erb +0 -228
- data/app/views/ruby_llm/agents/workflows/_structure_dsl.html.erb +0 -539
- data/app/views/ruby_llm/agents/workflows/_structure_parallel.html.erb +0 -76
- data/app/views/ruby_llm/agents/workflows/_structure_pipeline.html.erb +0 -74
- data/app/views/ruby_llm/agents/workflows/_structure_router.html.erb +0 -108
- data/app/views/ruby_llm/agents/workflows/_workflow_diagram.html.erb +0 -920
- data/app/views/ruby_llm/agents/workflows/index.html.erb +0 -179
- data/app/views/ruby_llm/agents/workflows/show.html.erb +0 -467
- data/lib/generators/ruby_llm_agents/api_configuration_generator.rb +0 -100
- data/lib/generators/ruby_llm_agents/templates/add_workflow_migration.rb.tt +0 -38
- data/lib/generators/ruby_llm_agents/templates/application_workflow.rb.tt +0 -48
- data/lib/generators/ruby_llm_agents/templates/create_api_configurations_migration.rb.tt +0 -90
- data/lib/generators/ruby_llm_agents/templates/skills/WORKFLOWS.md.tt +0 -551
- data/lib/ruby_llm/agents/core/base/moderation_dsl.rb +0 -181
- data/lib/ruby_llm/agents/core/base/moderation_execution.rb +0 -274
- data/lib/ruby_llm/agents/core/resolved_config.rb +0 -348
- data/lib/ruby_llm/agents/image/generator/content_policy.rb +0 -95
- data/lib/ruby_llm/agents/infrastructure/redactor.rb +0 -130
- data/lib/ruby_llm/agents/results/moderation_result.rb +0 -158
- data/lib/ruby_llm/agents/text/moderator.rb +0 -237
- data/lib/ruby_llm/agents/workflow/approval.rb +0 -205
- data/lib/ruby_llm/agents/workflow/approval_store.rb +0 -179
- data/lib/ruby_llm/agents/workflow/async.rb +0 -220
- data/lib/ruby_llm/agents/workflow/async_executor.rb +0 -156
- data/lib/ruby_llm/agents/workflow/dsl/executor.rb +0 -467
- data/lib/ruby_llm/agents/workflow/dsl/input_schema.rb +0 -244
- data/lib/ruby_llm/agents/workflow/dsl/iteration_executor.rb +0 -289
- data/lib/ruby_llm/agents/workflow/dsl/parallel_group.rb +0 -107
- data/lib/ruby_llm/agents/workflow/dsl/route_builder.rb +0 -150
- data/lib/ruby_llm/agents/workflow/dsl/schedule_helpers.rb +0 -187
- data/lib/ruby_llm/agents/workflow/dsl/step_config.rb +0 -352
- data/lib/ruby_llm/agents/workflow/dsl/step_executor.rb +0 -415
- data/lib/ruby_llm/agents/workflow/dsl/wait_config.rb +0 -257
- data/lib/ruby_llm/agents/workflow/dsl/wait_executor.rb +0 -317
- data/lib/ruby_llm/agents/workflow/dsl.rb +0 -576
- data/lib/ruby_llm/agents/workflow/instrumentation.rb +0 -249
- data/lib/ruby_llm/agents/workflow/notifiers/base.rb +0 -117
- data/lib/ruby_llm/agents/workflow/notifiers/email.rb +0 -117
- data/lib/ruby_llm/agents/workflow/notifiers/slack.rb +0 -180
- data/lib/ruby_llm/agents/workflow/notifiers/webhook.rb +0 -121
- data/lib/ruby_llm/agents/workflow/notifiers.rb +0 -70
- data/lib/ruby_llm/agents/workflow/orchestrator.rb +0 -416
- data/lib/ruby_llm/agents/workflow/result.rb +0 -592
- data/lib/ruby_llm/agents/workflow/thread_pool.rb +0 -185
- data/lib/ruby_llm/agents/workflow/throttle_manager.rb +0 -206
- data/lib/ruby_llm/agents/workflow/wait_result.rb +0 -213
|
@@ -37,26 +37,26 @@
|
|
|
37
37
|
credits: { enabled: false },
|
|
38
38
|
chart: {
|
|
39
39
|
backgroundColor: 'transparent',
|
|
40
|
-
style: { fontFamily: '
|
|
40
|
+
style: { fontFamily: 'ui-monospace, monospace' }
|
|
41
41
|
},
|
|
42
42
|
title: { text: null },
|
|
43
43
|
xAxis: {
|
|
44
|
-
labels: { style: { color: '#
|
|
45
|
-
lineColor: 'rgba(
|
|
46
|
-
tickColor: 'rgba(
|
|
44
|
+
labels: { style: { color: '#6B7280' } },
|
|
45
|
+
lineColor: 'rgba(107, 114, 128, 0.1)',
|
|
46
|
+
tickColor: 'rgba(107, 114, 128, 0.1)'
|
|
47
47
|
},
|
|
48
48
|
yAxis: {
|
|
49
|
-
labels: { style: { color: '#
|
|
50
|
-
gridLineColor: 'rgba(
|
|
49
|
+
labels: { style: { color: '#6B7280' } },
|
|
50
|
+
gridLineColor: 'rgba(107, 114, 128, 0.1)'
|
|
51
51
|
},
|
|
52
52
|
legend: {
|
|
53
|
-
itemStyle: { color: '#
|
|
54
|
-
itemHoverStyle: { color: '#
|
|
53
|
+
itemStyle: { color: '#6B7280' },
|
|
54
|
+
itemHoverStyle: { color: '#9CA3AF' }
|
|
55
55
|
},
|
|
56
56
|
tooltip: {
|
|
57
|
-
backgroundColor: 'rgba(
|
|
58
|
-
borderColor: '
|
|
59
|
-
style: { color: '#
|
|
57
|
+
backgroundColor: 'rgba(0, 0, 0, 0.85)',
|
|
58
|
+
borderColor: 'transparent',
|
|
59
|
+
style: { color: '#E5E7EB', fontFamily: 'ui-monospace, monospace' }
|
|
60
60
|
}
|
|
61
61
|
});
|
|
62
62
|
</script>
|
|
@@ -71,12 +71,9 @@
|
|
|
71
71
|
|
|
72
72
|
<!-- Clickable rows -->
|
|
73
73
|
<script type="module">
|
|
74
|
-
// Initialize on page load
|
|
75
74
|
document.addEventListener('DOMContentLoaded', function() {
|
|
76
|
-
// Handle data-href clickable rows (semantic alternative to onclick)
|
|
77
75
|
document.querySelectorAll('[data-href]').forEach(function(element) {
|
|
78
76
|
element.addEventListener('click', function(e) {
|
|
79
|
-
// Don't navigate if clicking on a link or button inside the row
|
|
80
77
|
if (e.target.closest('a, button')) return;
|
|
81
78
|
window.location = element.dataset.href;
|
|
82
79
|
});
|
|
@@ -109,291 +106,129 @@
|
|
|
109
106
|
}
|
|
110
107
|
</script>
|
|
111
108
|
|
|
112
|
-
<style>
|
|
113
|
-
/* Custom styles for the dashboard */
|
|
114
|
-
|
|
115
|
-
/* Standard card components */
|
|
116
|
-
.card {
|
|
117
|
-
@apply bg-white dark:bg-gray-800 border border-gray-200 dark:border-gray-700 rounded-xl p-6 mb-6;
|
|
118
|
-
}
|
|
119
|
-
.card-compact {
|
|
120
|
-
@apply bg-white dark:bg-gray-800 border border-gray-200 dark:border-gray-700 rounded-xl p-4 mb-4;
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
.stat-card {
|
|
124
|
-
@apply bg-white dark:bg-gray-800 rounded-xl shadow-sm border border-gray-100 dark:border-gray-700 p-4 transition-shadow;
|
|
125
|
-
}
|
|
126
|
-
.stat-card:hover {
|
|
127
|
-
@apply shadow-md;
|
|
128
|
-
}
|
|
129
|
-
.stat-value {
|
|
130
|
-
@apply text-2xl font-bold text-gray-900 dark:text-gray-100 mt-2;
|
|
131
|
-
}
|
|
132
|
-
@media (min-width: 1024px) {
|
|
133
|
-
.stat-value {
|
|
134
|
-
font-size: 1.5rem;
|
|
135
|
-
}
|
|
136
|
-
}
|
|
137
|
-
.stat-label {
|
|
138
|
-
@apply text-xs text-gray-500 dark:text-gray-400 uppercase tracking-wide font-medium;
|
|
139
|
-
}
|
|
140
|
-
.chart-card {
|
|
141
|
-
@apply bg-white dark:bg-gray-800 rounded-xl shadow-sm border border-gray-100 dark:border-gray-700 p-6;
|
|
142
|
-
}
|
|
143
|
-
.nav-link {
|
|
144
|
-
@apply px-4 py-2 text-gray-600 dark:text-gray-300 hover:text-gray-900 dark:hover:text-gray-100 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-md transition-colors;
|
|
145
|
-
}
|
|
146
|
-
.nav-link.active {
|
|
147
|
-
@apply bg-blue-50 dark:bg-blue-900 text-blue-700 dark:text-blue-300;
|
|
148
|
-
}
|
|
109
|
+
<style type="text/tailwindcss">
|
|
149
110
|
.badge {
|
|
150
111
|
@apply inline-flex items-center px-2.5 py-0.5 rounded-full text-xs font-medium;
|
|
151
112
|
}
|
|
152
113
|
.badge-running {
|
|
153
|
-
@apply bg-blue-100 dark:bg-blue-
|
|
114
|
+
@apply bg-blue-100 dark:bg-blue-500/20 text-blue-700 dark:text-blue-300;
|
|
154
115
|
}
|
|
155
116
|
.badge-success {
|
|
156
|
-
@apply bg-green-100 dark:bg-green-
|
|
117
|
+
@apply bg-green-100 dark:bg-green-500/20 text-green-700 dark:text-green-300;
|
|
157
118
|
}
|
|
158
119
|
.badge-error {
|
|
159
|
-
@apply bg-red-100 dark:bg-red-
|
|
120
|
+
@apply bg-red-100 dark:bg-red-500/20 text-red-700 dark:text-red-300;
|
|
160
121
|
}
|
|
161
122
|
.badge-timeout {
|
|
162
|
-
@apply bg-yellow-100 dark:bg-yellow-
|
|
123
|
+
@apply bg-yellow-100 dark:bg-yellow-500/20 text-yellow-700 dark:text-yellow-300;
|
|
163
124
|
}
|
|
164
125
|
.badge-cyan {
|
|
165
|
-
@apply bg-cyan-100 dark:bg-cyan-
|
|
126
|
+
@apply bg-cyan-100 dark:bg-cyan-500/20 text-cyan-700 dark:text-cyan-300;
|
|
166
127
|
}
|
|
167
128
|
.badge-purple {
|
|
168
|
-
@apply bg-purple-100 dark:bg-purple-
|
|
129
|
+
@apply bg-purple-100 dark:bg-purple-500/20 text-purple-700 dark:text-purple-300;
|
|
169
130
|
}
|
|
170
131
|
.badge-orange {
|
|
171
|
-
@apply bg-orange-100 dark:bg-orange-
|
|
132
|
+
@apply bg-orange-100 dark:bg-orange-500/20 text-orange-700 dark:text-orange-300;
|
|
172
133
|
}
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
.badge-pipeline {
|
|
176
|
-
@apply bg-indigo-100 dark:bg-indigo-900/50 text-indigo-700 dark:text-indigo-300;
|
|
177
|
-
}
|
|
178
|
-
.badge-parallel {
|
|
179
|
-
@apply bg-cyan-100 dark:bg-cyan-900/50 text-cyan-700 dark:text-cyan-300;
|
|
180
|
-
}
|
|
181
|
-
.badge-router {
|
|
182
|
-
@apply bg-amber-100 dark:bg-amber-900/50 text-amber-700 dark:text-amber-300;
|
|
183
|
-
}
|
|
184
|
-
|
|
185
|
-
/* Alpine.js utilities */
|
|
186
|
-
[x-cloak] {
|
|
187
|
-
display: none !important;
|
|
134
|
+
.badge-sm {
|
|
135
|
+
@apply inline-flex items-center px-1.5 py-px rounded-full text-[10px] font-medium;
|
|
188
136
|
}
|
|
189
|
-
|
|
190
|
-
</style>
|
|
137
|
+
</style>
|
|
191
138
|
</head>
|
|
192
139
|
|
|
193
|
-
<body class="bg-gray-50 dark:bg-gray-
|
|
140
|
+
<body class="bg-gray-50 dark:bg-gray-950 min-h-screen flex flex-col font-sans">
|
|
194
141
|
<!-- Header -->
|
|
195
|
-
<header
|
|
196
|
-
class="
|
|
197
|
-
|
|
198
|
-
dark:
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
<
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
142
|
+
<header class="border-b border-gray-200 dark:border-gray-800" x-data="{ mobileMenuOpen: false }">
|
|
143
|
+
<div class="max-w-7xl w-full mx-auto px-4 sm:px-6 lg:px-8 h-12 flex items-center">
|
|
144
|
+
<!-- Brand -->
|
|
145
|
+
<%= link_to ruby_llm_agents.root_path, class: "font-mono text-sm font-medium text-gray-900 dark:text-gray-100 hover:text-gray-600 dark:hover:text-gray-400 transition-colors" do %>
|
|
146
|
+
ruby_llm<span class="text-gray-400 dark:text-gray-600">::</span>agents
|
|
147
|
+
<% end %>
|
|
148
|
+
|
|
149
|
+
<!-- Desktop Navigation -->
|
|
150
|
+
<nav class="hidden md:flex items-center ml-8 gap-0.5 font-mono text-xs">
|
|
151
|
+
<% [
|
|
152
|
+
[ruby_llm_agents.root_path, "dashboard"],
|
|
153
|
+
[ruby_llm_agents.agents_path, "agents"],
|
|
154
|
+
[ruby_llm_agents.executions_path, "executions"],
|
|
155
|
+
[ruby_llm_agents.tenants_path, "tenants"]
|
|
156
|
+
].each do |path, label| %>
|
|
157
|
+
<% active = current_page?(path) %>
|
|
158
|
+
<%= link_to label, path, class: "px-2.5 py-1 rounded transition-colors #{active ? 'text-gray-900 dark:text-gray-100 bg-gray-100 dark:bg-gray-800' : 'text-gray-400 dark:text-gray-500 hover:text-gray-700 dark:hover:text-gray-300'}" %>
|
|
159
|
+
<% end %>
|
|
160
|
+
</nav>
|
|
212
161
|
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
]
|
|
222
|
-
%>
|
|
223
|
-
<nav class="hidden md:flex items-center space-x-1">
|
|
224
|
-
<% nav_items.each do |item| %>
|
|
225
|
-
<%= render "ruby_llm/agents/shared/nav_link", path: item[:path], label: item[:label], icon: item[:icon], mobile: false %>
|
|
226
|
-
<% end %>
|
|
227
|
-
</nav>
|
|
228
|
-
</div>
|
|
162
|
+
<!-- Right Side -->
|
|
163
|
+
<div class="ml-auto flex items-center gap-1">
|
|
164
|
+
<%= link_to ruby_llm_agents.system_config_path, class: "hidden md:flex p-1.5 text-gray-400 dark:text-gray-600 hover:text-gray-700 dark:hover:text-gray-300 rounded transition-colors", title: "Config" do %>
|
|
165
|
+
<svg class="w-3.5 h-3.5" fill="none" stroke="currentColor" stroke-width="2" viewBox="0 0 24 24">
|
|
166
|
+
<path stroke-linecap="round" stroke-linejoin="round" d="M10.325 4.317c.426-1.756 2.924-1.756 3.35 0a1.724 1.724 0 002.573 1.066c1.543-.94 3.31.826 2.37 2.37a1.724 1.724 0 001.065 2.572c1.756.426 1.756 2.924 0 3.35a1.724 1.724 0 00-1.066 2.573c.94 1.543-.826 3.31-2.37 2.37a1.724 1.724 0 00-2.572 1.065c-.426 1.756-2.924 1.756-3.35 0a1.724 1.724 0 00-2.573-1.066c-1.543.94-3.31-.826-2.37-2.37a1.724 1.724 0 00-1.065-2.572c-1.756-.426-1.756-2.924 0-3.35a1.724 1.724 0 001.066-2.573c-.94-1.543.826-3.31 2.37-2.37.996.608 2.296.07 2.572-1.065z"/>
|
|
167
|
+
<path stroke-linecap="round" stroke-linejoin="round" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/>
|
|
168
|
+
</svg>
|
|
169
|
+
<% end %>
|
|
229
170
|
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
"
|
|
171
|
+
<!-- Mobile menu button -->
|
|
172
|
+
<button
|
|
173
|
+
type="button"
|
|
174
|
+
@click="mobileMenuOpen = !mobileMenuOpen"
|
|
175
|
+
:aria-expanded="mobileMenuOpen"
|
|
176
|
+
class="md:hidden p-1.5 text-gray-400 dark:text-gray-500 hover:text-gray-700 dark:hover:text-gray-300 rounded transition-colors"
|
|
235
177
|
>
|
|
236
|
-
|
|
237
|
-
<
|
|
238
|
-
<
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
type="button"
|
|
242
|
-
class="p-2 rounded-md text-gray-500 hover:text-gray-700 hover:bg-gray-100 dark:text-gray-400 dark:hover:text-gray-200 dark:hover:bg-gray-700 transition-colors"
|
|
243
|
-
aria-label="Settings"
|
|
244
|
-
>
|
|
245
|
-
<svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
246
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M10.325 4.317c.426-1.756 2.924-1.756 3.35 0a1.724 1.724 0 002.573 1.066c1.543-.94 3.31.826 2.37 2.37a1.724 1.724 0 001.065 2.572c1.756.426 1.756 2.924 0 3.35a1.724 1.724 0 00-1.066 2.573c.94 1.543-.826 3.31-2.37 2.37a1.724 1.724 0 00-2.572 1.065c-.426 1.756-2.924 1.756-3.35 0a1.724 1.724 0 00-2.573-1.066c-1.543.94-3.31-.826-2.37-2.37a1.724 1.724 0 00-1.065-2.572c-1.756-.426-1.756-2.924 0-3.35a1.724 1.724 0 001.066-2.573c-.94-1.543.826-3.31 2.37-2.37.996.608 2.296.07 2.572-1.065z"/>
|
|
247
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/>
|
|
248
|
-
</svg>
|
|
249
|
-
</button>
|
|
250
|
-
|
|
251
|
-
<div
|
|
252
|
-
x-show="settingsOpen"
|
|
253
|
-
x-cloak
|
|
254
|
-
x-transition:enter="transition ease-out duration-100"
|
|
255
|
-
x-transition:enter-start="opacity-0 scale-95"
|
|
256
|
-
x-transition:enter-end="opacity-100 scale-100"
|
|
257
|
-
x-transition:leave="transition ease-in duration-75"
|
|
258
|
-
x-transition:leave-start="opacity-100 scale-100"
|
|
259
|
-
x-transition:leave-end="opacity-0 scale-95"
|
|
260
|
-
class="absolute right-0 mt-2 w-48 bg-white dark:bg-gray-800 border border-gray-200 dark:border-gray-700 rounded-lg shadow-lg z-50 py-1"
|
|
261
|
-
>
|
|
262
|
-
<a href="<%= ruby_llm_agents.system_config_path %>"
|
|
263
|
-
class="flex items-center gap-2 px-4 py-2 text-sm text-gray-700 dark:text-gray-200 hover:bg-gray-100 dark:hover:bg-gray-700 <%= 'bg-gray-100 dark:bg-gray-700' if request.path == ruby_llm_agents.system_config_path %>">
|
|
264
|
-
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
265
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 6V4m0 2a2 2 0 100 4m0-4a2 2 0 110 4m-6 8a2 2 0 100-4m0 4a2 2 0 110-4m0 4v2m0-6V4m6 6v10m6-2a2 2 0 100-4m0 4a2 2 0 110-4m0 4v2m0-6V4"/>
|
|
266
|
-
</svg>
|
|
267
|
-
System Config
|
|
268
|
-
</a>
|
|
269
|
-
<a href="<%= ruby_llm_agents.api_configuration_path %>"
|
|
270
|
-
class="flex items-center gap-2 px-4 py-2 text-sm text-gray-700 dark:text-gray-200 hover:bg-gray-100 dark:hover:bg-gray-700 <%= 'bg-gray-100 dark:bg-gray-700' if request.path == ruby_llm_agents.api_configuration_path %>">
|
|
271
|
-
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
272
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 7a2 2 0 012 2m4 0a6 6 0 01-7.743 5.743L11 17H9v2H7v2H4a1 1 0 01-1-1v-2.586a1 1 0 01.293-.707l5.964-5.964A6 6 0 1121 9z"/>
|
|
273
|
-
</svg>
|
|
274
|
-
API Keys
|
|
275
|
-
</a>
|
|
276
|
-
<div class="border-t border-gray-100 dark:border-gray-700 my-1"></div>
|
|
277
|
-
<a href="#" class="flex items-center gap-2 px-4 py-2 text-sm text-gray-700 dark:text-gray-200 hover:bg-gray-100 dark:hover:bg-gray-700">
|
|
278
|
-
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
279
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M17 16l4-4m0 0l-4-4m4 4H7m6 4v1a3 3 0 01-3 3H6a3 3 0 01-3-3V7a3 3 0 013-3h4a3 3 0 013 3v1"/>
|
|
280
|
-
</svg>
|
|
281
|
-
Logout
|
|
282
|
-
</a>
|
|
283
|
-
</div>
|
|
284
|
-
</div>
|
|
285
|
-
|
|
286
|
-
<!-- Mobile menu button -->
|
|
287
|
-
<button
|
|
288
|
-
type="button"
|
|
289
|
-
@click="mobileMenuOpen = !mobileMenuOpen"
|
|
290
|
-
:aria-expanded="mobileMenuOpen"
|
|
291
|
-
aria-controls="mobile-menu"
|
|
292
|
-
class="
|
|
293
|
-
md:hidden inline-flex items-center justify-center p-2
|
|
294
|
-
rounded-md text-gray-500 dark:text-gray-400
|
|
295
|
-
hover:text-gray-900 dark:hover:text-gray-100
|
|
296
|
-
hover:bg-gray-100 dark:hover:bg-gray-700 focus:outline-none
|
|
297
|
-
focus:ring-2 focus:ring-inset focus:ring-blue-500
|
|
298
|
-
"
|
|
299
|
-
>
|
|
300
|
-
<span class="sr-only">Open main menu</span>
|
|
301
|
-
|
|
302
|
-
<svg
|
|
303
|
-
class="w-5 h-5"
|
|
304
|
-
fill="none"
|
|
305
|
-
stroke="currentColor"
|
|
306
|
-
viewBox="0 0 24 24"
|
|
307
|
-
>
|
|
308
|
-
<path
|
|
309
|
-
stroke-linecap="round"
|
|
310
|
-
stroke-linejoin="round"
|
|
311
|
-
stroke-width="2"
|
|
312
|
-
d="M4 6h16M4 12h16M4 18h16"
|
|
313
|
-
/>
|
|
314
|
-
</svg>
|
|
315
|
-
</button>
|
|
316
|
-
</div>
|
|
178
|
+
<span class="sr-only">Open main menu</span>
|
|
179
|
+
<svg class="w-4 h-4" fill="none" stroke="currentColor" stroke-width="2" viewBox="0 0 24 24">
|
|
180
|
+
<path stroke-linecap="round" stroke-linejoin="round" d="M4 6h16M4 12h16M4 18h16"/>
|
|
181
|
+
</svg>
|
|
182
|
+
</button>
|
|
317
183
|
</div>
|
|
318
184
|
</div>
|
|
319
185
|
|
|
320
|
-
<!-- Mobile Navigation
|
|
186
|
+
<!-- Mobile Navigation -->
|
|
321
187
|
<div
|
|
322
|
-
id="mobile-menu"
|
|
323
188
|
x-show="mobileMenuOpen"
|
|
324
189
|
x-cloak
|
|
325
|
-
x-transition:enter="transition ease-out duration-
|
|
190
|
+
x-transition:enter="transition ease-out duration-150"
|
|
326
191
|
x-transition:enter-start="opacity-0 -translate-y-1"
|
|
327
192
|
x-transition:enter-end="opacity-100 translate-y-0"
|
|
328
|
-
x-transition:leave="transition ease-in duration-
|
|
193
|
+
x-transition:leave="transition ease-in duration-100"
|
|
329
194
|
x-transition:leave-start="opacity-100 translate-y-0"
|
|
330
195
|
x-transition:leave-end="opacity-0 -translate-y-1"
|
|
331
196
|
@click.outside="mobileMenuOpen = false"
|
|
332
|
-
class="
|
|
333
|
-
md:hidden border-t border-gray-200 dark:border-gray-700 bg-white
|
|
334
|
-
dark:bg-gray-800
|
|
335
|
-
"
|
|
197
|
+
class="md:hidden border-t border-gray-200 dark:border-gray-800"
|
|
336
198
|
>
|
|
337
|
-
<nav class="max-w-7xl mx-auto px-4 py-
|
|
338
|
-
<%
|
|
339
|
-
|
|
199
|
+
<nav class="max-w-7xl mx-auto px-4 py-2 font-mono text-xs space-y-0.5">
|
|
200
|
+
<% [
|
|
201
|
+
[ruby_llm_agents.root_path, "dashboard"],
|
|
202
|
+
[ruby_llm_agents.agents_path, "agents"],
|
|
203
|
+
[ruby_llm_agents.executions_path, "executions"],
|
|
204
|
+
[ruby_llm_agents.tenants_path, "tenants"]
|
|
205
|
+
].each do |path, label| %>
|
|
206
|
+
<% active = current_page?(path) %>
|
|
207
|
+
<%= link_to label, path, class: "block px-3 py-2 rounded transition-colors #{active ? 'text-gray-900 dark:text-gray-100 bg-gray-100 dark:bg-gray-800' : 'text-gray-400 dark:text-gray-500 hover:text-gray-700 dark:hover:text-gray-300'}" %>
|
|
340
208
|
<% end %>
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
<div class="border-t border-gray-200 dark:border-gray-700 my-2 pt-2">
|
|
344
|
-
<span class="px-3 text-xs font-semibold text-gray-400 dark:text-gray-500 uppercase tracking-wider">Settings</span>
|
|
345
|
-
</div>
|
|
346
|
-
|
|
347
|
-
<%= render "ruby_llm/agents/shared/nav_link",
|
|
348
|
-
path: ruby_llm_agents.system_config_path,
|
|
349
|
-
label: "System Config",
|
|
350
|
-
icon: '<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 6V4m0 2a2 2 0 100 4m0-4a2 2 0 110 4m-6 8a2 2 0 100-4m0 4a2 2 0 110-4m0 4v2m0-6V4m6 6v10m6-2a2 2 0 100-4m0 4a2 2 0 110-4m0 4v2m0-6V4"/>',
|
|
351
|
-
mobile: true %>
|
|
352
|
-
|
|
353
|
-
<%= render "ruby_llm/agents/shared/nav_link",
|
|
354
|
-
path: ruby_llm_agents.api_configuration_path,
|
|
355
|
-
label: "API Keys",
|
|
356
|
-
icon: '<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 7a2 2 0 012 2m4 0a6 6 0 01-7.743 5.743L11 17H9v2H7v2H4a1 1 0 01-1-1v-2.586a1 1 0 01.293-.707l5.964-5.964A6 6 0 1121 9z"/>',
|
|
357
|
-
mobile: true %>
|
|
358
|
-
|
|
359
|
-
<a href="#" class="flex items-center px-3 py-2 text-sm font-medium text-gray-600 dark:text-gray-300 hover:text-gray-900 dark:hover:text-gray-100 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-md">
|
|
360
|
-
<svg class="w-5 h-5 mr-3 text-gray-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
|
361
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M17 16l4-4m0 0l-4-4m4 4H7m6 4v1a3 3 0 01-3 3H6a3 3 0 01-3-3V7a3 3 0 013-3h4a3 3 0 013 3v1"/>
|
|
362
|
-
</svg>
|
|
363
|
-
Logout
|
|
364
|
-
</a>
|
|
209
|
+
<div class="border-t border-gray-200 dark:border-gray-800 my-1.5"></div>
|
|
210
|
+
<%= link_to "config", ruby_llm_agents.system_config_path, class: "block px-3 py-2 rounded text-gray-400 dark:text-gray-500 hover:text-gray-700 dark:hover:text-gray-300 transition-colors" %>
|
|
365
211
|
</nav>
|
|
366
212
|
</div>
|
|
367
213
|
</header>
|
|
368
214
|
|
|
369
215
|
<!-- Main content -->
|
|
370
|
-
<main class="max-w-7xl w-full mx-auto px-4 sm:px-6 lg:px-8 py-
|
|
216
|
+
<main class="max-w-7xl w-full mx-auto px-4 sm:px-6 lg:px-8 py-6 flex-1">
|
|
371
217
|
<%= yield %>
|
|
372
218
|
</main>
|
|
373
219
|
|
|
374
220
|
<!-- Footer -->
|
|
375
|
-
<footer
|
|
376
|
-
class="
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
<
|
|
383
|
-
<
|
|
384
|
-
id="theme-select"
|
|
385
|
-
x-model="preference"
|
|
386
|
-
@change="setTheme($event.target.value)"
|
|
387
|
-
class="text-sm border border-gray-300 dark:border-gray-600 dark:bg-gray-700 dark:text-gray-200 rounded-md shadow-sm focus:ring-blue-500 focus:border-blue-500 py-1 px-2"
|
|
388
|
-
>
|
|
389
|
-
<option value="light">Light</option>
|
|
390
|
-
<option value="dark">Dark</option>
|
|
391
|
-
<option value="auto">Auto</option>
|
|
392
|
-
</select>
|
|
221
|
+
<footer class="border-t border-gray-200 dark:border-gray-800 mt-auto" x-data="themeManager()">
|
|
222
|
+
<div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-3">
|
|
223
|
+
<div class="flex items-center justify-between font-mono text-[10px] text-gray-400 dark:text-gray-600 uppercase tracking-widest">
|
|
224
|
+
<div class="flex items-center gap-1">
|
|
225
|
+
<button @click="setTheme('light')" :class="preference === 'light' && 'text-gray-700 dark:text-gray-300'" class="px-1.5 py-0.5 rounded hover:text-gray-600 dark:hover:text-gray-400 transition-colors">light</button>
|
|
226
|
+
<span class="text-gray-300 dark:text-gray-700">·</span>
|
|
227
|
+
<button @click="setTheme('dark')" :class="preference === 'dark' && 'text-gray-700 dark:text-gray-300'" class="px-1.5 py-0.5 rounded hover:text-gray-600 dark:hover:text-gray-400 transition-colors">dark</button>
|
|
228
|
+
<span class="text-gray-300 dark:text-gray-700">·</span>
|
|
229
|
+
<button @click="setTheme('auto')" :class="preference === 'auto' && 'text-gray-700 dark:text-gray-300'" class="px-1.5 py-0.5 rounded hover:text-gray-600 dark:hover:text-gray-400 transition-colors">auto</button>
|
|
393
230
|
</div>
|
|
394
|
-
<
|
|
395
|
-
Powered by <a href="https://github.com/adham90/ruby_llm-agents" class="text-blue-600 dark:text-blue-400 hover:underline">ruby_llm-agents</a>
|
|
396
|
-
</p>
|
|
231
|
+
<a href="https://github.com/adham90/ruby_llm-agents" class="hover:text-gray-600 dark:hover:text-gray-400 transition-colors normal-case tracking-normal">ruby_llm-agents</a>
|
|
397
232
|
</div>
|
|
398
233
|
</div>
|
|
399
234
|
</footer>
|