ruby_llm-agents 0.5.0 → 1.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.
Files changed (190) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +189 -31
  3. data/app/controllers/ruby_llm/agents/agents_controller.rb +136 -16
  4. data/app/controllers/ruby_llm/agents/dashboard_controller.rb +29 -9
  5. data/app/controllers/ruby_llm/agents/workflows_controller.rb +355 -0
  6. data/app/helpers/ruby_llm/agents/application_helper.rb +25 -0
  7. data/app/models/ruby_llm/agents/execution.rb +3 -0
  8. data/app/models/ruby_llm/agents/tenant_budget.rb +58 -15
  9. data/app/services/ruby_llm/agents/agent_registry.rb +51 -12
  10. data/app/views/layouts/ruby_llm/agents/application.html.erb +2 -29
  11. data/app/views/ruby_llm/agents/agents/_agent.html.erb +13 -1
  12. data/app/views/ruby_llm/agents/agents/_config_agent.html.erb +235 -0
  13. data/app/views/ruby_llm/agents/agents/_config_embedder.html.erb +70 -0
  14. data/app/views/ruby_llm/agents/agents/_config_image_generator.html.erb +152 -0
  15. data/app/views/ruby_llm/agents/agents/_config_moderator.html.erb +63 -0
  16. data/app/views/ruby_llm/agents/agents/_config_speaker.html.erb +108 -0
  17. data/app/views/ruby_llm/agents/agents/_config_transcriber.html.erb +91 -0
  18. data/app/views/ruby_llm/agents/agents/_workflow.html.erb +1 -1
  19. data/app/views/ruby_llm/agents/agents/index.html.erb +74 -9
  20. data/app/views/ruby_llm/agents/agents/show.html.erb +18 -378
  21. data/app/views/ruby_llm/agents/dashboard/_agent_comparison.html.erb +269 -15
  22. data/app/views/ruby_llm/agents/executions/show.html.erb +16 -0
  23. data/app/views/ruby_llm/agents/shared/_agent_type_badge.html.erb +93 -0
  24. data/app/views/ruby_llm/agents/workflows/_step_performance.html.erb +236 -0
  25. data/app/views/ruby_llm/agents/workflows/_structure_parallel.html.erb +76 -0
  26. data/app/views/ruby_llm/agents/workflows/_structure_pipeline.html.erb +74 -0
  27. data/app/views/ruby_llm/agents/workflows/_structure_router.html.erb +108 -0
  28. data/app/views/ruby_llm/agents/workflows/show.html.erb +442 -0
  29. data/config/routes.rb +1 -0
  30. data/lib/generators/ruby_llm_agents/agent_generator.rb +56 -7
  31. data/lib/generators/ruby_llm_agents/background_remover_generator.rb +110 -0
  32. data/lib/generators/ruby_llm_agents/embedder_generator.rb +107 -0
  33. data/lib/generators/ruby_llm_agents/image_analyzer_generator.rb +115 -0
  34. data/lib/generators/ruby_llm_agents/image_editor_generator.rb +108 -0
  35. data/lib/generators/ruby_llm_agents/image_generator_generator.rb +116 -0
  36. data/lib/generators/ruby_llm_agents/image_pipeline_generator.rb +178 -0
  37. data/lib/generators/ruby_llm_agents/image_transformer_generator.rb +109 -0
  38. data/lib/generators/ruby_llm_agents/image_upscaler_generator.rb +103 -0
  39. data/lib/generators/ruby_llm_agents/image_variator_generator.rb +102 -0
  40. data/lib/generators/ruby_llm_agents/install_generator.rb +76 -4
  41. data/lib/generators/ruby_llm_agents/restructure_generator.rb +292 -0
  42. data/lib/generators/ruby_llm_agents/speaker_generator.rb +121 -0
  43. data/lib/generators/ruby_llm_agents/templates/add_execution_type_migration.rb.tt +8 -0
  44. data/lib/generators/ruby_llm_agents/templates/agent.rb.tt +99 -84
  45. data/lib/generators/ruby_llm_agents/templates/application_agent.rb.tt +42 -40
  46. data/lib/generators/ruby_llm_agents/templates/application_background_remover.rb.tt +26 -0
  47. data/lib/generators/ruby_llm_agents/templates/application_embedder.rb.tt +50 -0
  48. data/lib/generators/ruby_llm_agents/templates/application_image_analyzer.rb.tt +26 -0
  49. data/lib/generators/ruby_llm_agents/templates/application_image_editor.rb.tt +20 -0
  50. data/lib/generators/ruby_llm_agents/templates/application_image_generator.rb.tt +38 -0
  51. data/lib/generators/ruby_llm_agents/templates/application_image_pipeline.rb.tt +139 -0
  52. data/lib/generators/ruby_llm_agents/templates/application_image_transformer.rb.tt +21 -0
  53. data/lib/generators/ruby_llm_agents/templates/application_image_upscaler.rb.tt +20 -0
  54. data/lib/generators/ruby_llm_agents/templates/application_image_variator.rb.tt +20 -0
  55. data/lib/generators/ruby_llm_agents/templates/application_speaker.rb.tt +49 -0
  56. data/lib/generators/ruby_llm_agents/templates/application_transcriber.rb.tt +53 -0
  57. data/lib/generators/ruby_llm_agents/templates/background_remover.rb.tt +44 -0
  58. data/lib/generators/ruby_llm_agents/templates/embedder.rb.tt +41 -0
  59. data/lib/generators/ruby_llm_agents/templates/image_analyzer.rb.tt +45 -0
  60. data/lib/generators/ruby_llm_agents/templates/image_editor.rb.tt +35 -0
  61. data/lib/generators/ruby_llm_agents/templates/image_generator.rb.tt +47 -0
  62. data/lib/generators/ruby_llm_agents/templates/image_pipeline.rb.tt +50 -0
  63. data/lib/generators/ruby_llm_agents/templates/image_transformer.rb.tt +44 -0
  64. data/lib/generators/ruby_llm_agents/templates/image_upscaler.rb.tt +38 -0
  65. data/lib/generators/ruby_llm_agents/templates/image_variator.rb.tt +33 -0
  66. data/lib/generators/ruby_llm_agents/templates/skills/AGENTS.md.tt +228 -0
  67. data/lib/generators/ruby_llm_agents/templates/skills/BACKGROUND_REMOVERS.md.tt +131 -0
  68. data/lib/generators/ruby_llm_agents/templates/skills/EMBEDDERS.md.tt +255 -0
  69. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_ANALYZERS.md.tt +120 -0
  70. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_EDITORS.md.tt +102 -0
  71. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_GENERATORS.md.tt +282 -0
  72. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_PIPELINES.md.tt +228 -0
  73. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_TRANSFORMERS.md.tt +120 -0
  74. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_UPSCALERS.md.tt +110 -0
  75. data/lib/generators/ruby_llm_agents/templates/skills/IMAGE_VARIATORS.md.tt +120 -0
  76. data/lib/generators/ruby_llm_agents/templates/skills/SPEAKERS.md.tt +212 -0
  77. data/lib/generators/ruby_llm_agents/templates/skills/TOOLS.md.tt +227 -0
  78. data/lib/generators/ruby_llm_agents/templates/skills/TRANSCRIBERS.md.tt +251 -0
  79. data/lib/generators/ruby_llm_agents/templates/skills/WORKFLOWS.md.tt +300 -0
  80. data/lib/generators/ruby_llm_agents/templates/speaker.rb.tt +56 -0
  81. data/lib/generators/ruby_llm_agents/templates/transcriber.rb.tt +51 -0
  82. data/lib/generators/ruby_llm_agents/transcriber_generator.rb +107 -0
  83. data/lib/generators/ruby_llm_agents/upgrade_generator.rb +152 -1
  84. data/lib/ruby_llm/agents/audio/speaker.rb +553 -0
  85. data/lib/ruby_llm/agents/audio/transcriber.rb +669 -0
  86. data/lib/ruby_llm/agents/base_agent.rb +675 -0
  87. data/lib/ruby_llm/agents/core/base/moderation_dsl.rb +181 -0
  88. data/lib/ruby_llm/agents/core/base/moderation_execution.rb +274 -0
  89. data/lib/ruby_llm/agents/core/base.rb +135 -0
  90. data/lib/ruby_llm/agents/core/configuration.rb +981 -0
  91. data/lib/ruby_llm/agents/core/errors.rb +150 -0
  92. data/lib/ruby_llm/agents/{instrumentation.rb → core/instrumentation.rb} +22 -1
  93. data/lib/ruby_llm/agents/core/llm_tenant.rb +358 -0
  94. data/lib/ruby_llm/agents/{version.rb → core/version.rb} +1 -1
  95. data/lib/ruby_llm/agents/dsl/base.rb +110 -0
  96. data/lib/ruby_llm/agents/dsl/caching.rb +142 -0
  97. data/lib/ruby_llm/agents/dsl/reliability.rb +307 -0
  98. data/lib/ruby_llm/agents/dsl.rb +41 -0
  99. data/lib/ruby_llm/agents/image/analyzer/dsl.rb +130 -0
  100. data/lib/ruby_llm/agents/image/analyzer/execution.rb +402 -0
  101. data/lib/ruby_llm/agents/image/analyzer.rb +90 -0
  102. data/lib/ruby_llm/agents/image/background_remover/dsl.rb +154 -0
  103. data/lib/ruby_llm/agents/image/background_remover/execution.rb +240 -0
  104. data/lib/ruby_llm/agents/image/background_remover.rb +89 -0
  105. data/lib/ruby_llm/agents/image/concerns/image_operation_dsl.rb +91 -0
  106. data/lib/ruby_llm/agents/image/concerns/image_operation_execution.rb +165 -0
  107. data/lib/ruby_llm/agents/image/editor/dsl.rb +56 -0
  108. data/lib/ruby_llm/agents/image/editor/execution.rb +207 -0
  109. data/lib/ruby_llm/agents/image/editor.rb +92 -0
  110. data/lib/ruby_llm/agents/image/generator/active_storage_support.rb +127 -0
  111. data/lib/ruby_llm/agents/image/generator/content_policy.rb +95 -0
  112. data/lib/ruby_llm/agents/image/generator/pricing.rb +353 -0
  113. data/lib/ruby_llm/agents/image/generator/templates.rb +124 -0
  114. data/lib/ruby_llm/agents/image/generator.rb +455 -0
  115. data/lib/ruby_llm/agents/image/pipeline/dsl.rb +213 -0
  116. data/lib/ruby_llm/agents/image/pipeline/execution.rb +382 -0
  117. data/lib/ruby_llm/agents/image/pipeline.rb +97 -0
  118. data/lib/ruby_llm/agents/image/transformer/dsl.rb +148 -0
  119. data/lib/ruby_llm/agents/image/transformer/execution.rb +223 -0
  120. data/lib/ruby_llm/agents/image/transformer.rb +95 -0
  121. data/lib/ruby_llm/agents/image/upscaler/dsl.rb +83 -0
  122. data/lib/ruby_llm/agents/image/upscaler/execution.rb +219 -0
  123. data/lib/ruby_llm/agents/image/upscaler.rb +81 -0
  124. data/lib/ruby_llm/agents/image/variator/dsl.rb +62 -0
  125. data/lib/ruby_llm/agents/image/variator/execution.rb +189 -0
  126. data/lib/ruby_llm/agents/image/variator.rb +80 -0
  127. data/lib/ruby_llm/agents/{alert_manager.rb → infrastructure/alert_manager.rb} +17 -22
  128. data/lib/ruby_llm/agents/infrastructure/budget/budget_query.rb +145 -0
  129. data/lib/ruby_llm/agents/infrastructure/budget/config_resolver.rb +149 -0
  130. data/lib/ruby_llm/agents/infrastructure/budget/forecaster.rb +68 -0
  131. data/lib/ruby_llm/agents/infrastructure/budget/spend_recorder.rb +279 -0
  132. data/lib/ruby_llm/agents/infrastructure/budget_tracker.rb +275 -0
  133. data/lib/ruby_llm/agents/{execution_logger_job.rb → infrastructure/execution_logger_job.rb} +17 -1
  134. data/lib/ruby_llm/agents/{reliability → infrastructure/reliability}/executor.rb +2 -1
  135. data/lib/ruby_llm/agents/{reliability → infrastructure/reliability}/retry_strategy.rb +9 -3
  136. data/lib/ruby_llm/agents/{reliability.rb → infrastructure/reliability.rb} +11 -21
  137. data/lib/ruby_llm/agents/pipeline/builder.rb +215 -0
  138. data/lib/ruby_llm/agents/pipeline/context.rb +255 -0
  139. data/lib/ruby_llm/agents/pipeline/executor.rb +86 -0
  140. data/lib/ruby_llm/agents/pipeline/middleware/base.rb +124 -0
  141. data/lib/ruby_llm/agents/pipeline/middleware/budget.rb +95 -0
  142. data/lib/ruby_llm/agents/pipeline/middleware/cache.rb +171 -0
  143. data/lib/ruby_llm/agents/pipeline/middleware/instrumentation.rb +415 -0
  144. data/lib/ruby_llm/agents/pipeline/middleware/reliability.rb +276 -0
  145. data/lib/ruby_llm/agents/pipeline/middleware/tenant.rb +196 -0
  146. data/lib/ruby_llm/agents/pipeline.rb +68 -0
  147. data/lib/ruby_llm/agents/{engine.rb → rails/engine.rb} +79 -11
  148. data/lib/ruby_llm/agents/results/background_removal_result.rb +286 -0
  149. data/lib/ruby_llm/agents/{result.rb → results/base.rb} +73 -1
  150. data/lib/ruby_llm/agents/results/embedding_result.rb +243 -0
  151. data/lib/ruby_llm/agents/results/image_analysis_result.rb +314 -0
  152. data/lib/ruby_llm/agents/results/image_edit_result.rb +250 -0
  153. data/lib/ruby_llm/agents/results/image_generation_result.rb +346 -0
  154. data/lib/ruby_llm/agents/results/image_pipeline_result.rb +399 -0
  155. data/lib/ruby_llm/agents/results/image_transform_result.rb +251 -0
  156. data/lib/ruby_llm/agents/results/image_upscale_result.rb +255 -0
  157. data/lib/ruby_llm/agents/results/image_variation_result.rb +237 -0
  158. data/lib/ruby_llm/agents/results/moderation_result.rb +158 -0
  159. data/lib/ruby_llm/agents/results/speech_result.rb +338 -0
  160. data/lib/ruby_llm/agents/results/transcription_result.rb +408 -0
  161. data/lib/ruby_llm/agents/text/embedder.rb +444 -0
  162. data/lib/ruby_llm/agents/text/moderator.rb +237 -0
  163. data/lib/ruby_llm/agents/workflow/async.rb +220 -0
  164. data/lib/ruby_llm/agents/workflow/async_executor.rb +156 -0
  165. data/lib/ruby_llm/agents/{workflow.rb → workflow/orchestrator.rb} +6 -5
  166. data/lib/ruby_llm/agents/workflow/parallel.rb +34 -17
  167. data/lib/ruby_llm/agents/workflow/thread_pool.rb +185 -0
  168. data/lib/ruby_llm/agents.rb +86 -20
  169. metadata +172 -34
  170. data/lib/ruby_llm/agents/base/caching.rb +0 -40
  171. data/lib/ruby_llm/agents/base/cost_calculation.rb +0 -105
  172. data/lib/ruby_llm/agents/base/dsl.rb +0 -324
  173. data/lib/ruby_llm/agents/base/execution.rb +0 -366
  174. data/lib/ruby_llm/agents/base/reliability_dsl.rb +0 -82
  175. data/lib/ruby_llm/agents/base/reliability_execution.rb +0 -136
  176. data/lib/ruby_llm/agents/base/response_building.rb +0 -86
  177. data/lib/ruby_llm/agents/base/tool_tracking.rb +0 -57
  178. data/lib/ruby_llm/agents/base.rb +0 -210
  179. data/lib/ruby_llm/agents/budget_tracker.rb +0 -733
  180. data/lib/ruby_llm/agents/configuration.rb +0 -394
  181. /data/lib/ruby_llm/agents/{deprecations.rb → core/deprecations.rb} +0 -0
  182. /data/lib/ruby_llm/agents/{inflections.rb → core/inflections.rb} +0 -0
  183. /data/lib/ruby_llm/agents/{resolved_config.rb → core/resolved_config.rb} +0 -0
  184. /data/lib/ruby_llm/agents/{attempt_tracker.rb → infrastructure/attempt_tracker.rb} +0 -0
  185. /data/lib/ruby_llm/agents/{cache_helper.rb → infrastructure/cache_helper.rb} +0 -0
  186. /data/lib/ruby_llm/agents/{circuit_breaker.rb → infrastructure/circuit_breaker.rb} +0 -0
  187. /data/lib/ruby_llm/agents/{redactor.rb → infrastructure/redactor.rb} +0 -0
  188. /data/lib/ruby_llm/agents/{reliability → infrastructure/reliability}/breaker_manager.rb +0 -0
  189. /data/lib/ruby_llm/agents/{reliability → infrastructure/reliability}/execution_constraints.rb +0 -0
  190. /data/lib/ruby_llm/agents/{reliability → infrastructure/reliability}/fallback_routing.rb +0 -0
@@ -0,0 +1,282 @@
1
+ # <%= @root_namespace %>::Image Generators
2
+
3
+ This directory contains image generation services. All generators inherit from `ApplicationImageGenerator`.
4
+
5
+ ## Creating a New Generator
6
+
7
+ Use the generator:
8
+ ```bash
9
+ rails generate ruby_llm_agents:image_generator GeneratorName
10
+ rails generate ruby_llm_agents:image_generator Logo --model gpt-image-1 --size 1024x1024
11
+ rails generate ruby_llm_agents:image_generator Product --quality hd --style vivid
12
+ ```
13
+
14
+ Or create manually:
15
+ ```ruby
16
+ module <%= @root_namespace %>
17
+ module Image
18
+ class LogoGenerator < ApplicationImageGenerator
19
+ model "gpt-image-1"
20
+ size "1024x1024"
21
+ quality "hd"
22
+ style "vivid"
23
+ content_policy :standard
24
+ end
25
+ end
26
+ end
27
+ ```
28
+
29
+ ## DSL Reference
30
+
31
+ ### Model Configuration
32
+
33
+ | Method | Description | Example |
34
+ |--------|-------------|---------|
35
+ | `model` | Image generation model | `model "gpt-image-1"` |
36
+ | `size` | Output image size | `size "1024x1024"` |
37
+ | `quality` | Image quality | `quality "hd"` |
38
+ | `style` | Generation style | `style "vivid"` |
39
+ | `content_policy` | Content filtering level | `content_policy :strict` |
40
+
41
+ ### Available Sizes
42
+
43
+ - `1024x1024` - Square (default)
44
+ - `1792x1024` - Landscape
45
+ - `1024x1792` - Portrait
46
+ - `512x512` - Small square
47
+ - `256x256` - Thumbnail
48
+
49
+ ### Quality Options
50
+
51
+ - `standard` - Faster generation, good quality
52
+ - `hd` - Higher detail, slower generation
53
+
54
+ ### Style Options
55
+
56
+ - `vivid` - Hyper-real, dramatic (default)
57
+ - `natural` - More natural, less extreme
58
+
59
+ ### Content Policy Levels
60
+
61
+ - `:none` - No filtering
62
+ - `:standard` - Default content filtering
63
+ - `:moderate` - Stricter filtering
64
+ - `:strict` - Maximum filtering
65
+
66
+ ### Caching
67
+
68
+ ```ruby
69
+ cache_for 1.day # Cache generated images
70
+ cache_for 1.week # Long-term caching
71
+ ```
72
+
73
+ ## Optional Methods & DSL
74
+
75
+ ### `template`
76
+ Define a prompt template:
77
+
78
+ ```ruby
79
+ template "Professional {prompt}, minimalist design, vector art style"
80
+ ```
81
+
82
+ ### `negative_prompt`
83
+ Specify what to avoid (for supported models):
84
+
85
+ ```ruby
86
+ negative_prompt "blurry, low quality, distorted, watermark"
87
+ ```
88
+
89
+ ### `preprocess_prompt(prompt)`
90
+ Transform prompt before generation:
91
+
92
+ ```ruby
93
+ def preprocess_prompt(prompt)
94
+ "#{prompt}, professional quality, 8k resolution"
95
+ end
96
+ ```
97
+
98
+ ## Using Generators
99
+
100
+ ### Basic Generation
101
+
102
+ ```ruby
103
+ result = <%= @root_namespace %>::Image::LogoGenerator.call(prompt: "Tech startup logo")
104
+
105
+ result.url # Temporary URL to generated image
106
+ result.image_data # Binary image data
107
+ result.size # "1024x1024"
108
+ result.total_cost # Cost in USD
109
+ ```
110
+
111
+ ### Save to File
112
+
113
+ ```ruby
114
+ result = <%= @root_namespace %>::Image::LogoGenerator.call(prompt: "Company logo")
115
+ result.save("logo.png")
116
+ ```
117
+
118
+ ### Generate Multiple Images
119
+
120
+ ```ruby
121
+ result = <%= @root_namespace %>::Image::LogoGenerator.call(
122
+ prompt: "Product photography",
123
+ count: 4
124
+ )
125
+
126
+ result.urls # Array of image URLs
127
+ result.images # Array of image data
128
+ ```
129
+
130
+ ### Override Settings at Runtime
131
+
132
+ ```ruby
133
+ result = <%= @root_namespace %>::Image::LogoGenerator.call(
134
+ prompt: "High quality portrait",
135
+ quality: "hd",
136
+ size: "1792x1024",
137
+ style: "natural"
138
+ )
139
+ ```
140
+
141
+ ### With ActiveStorage
142
+
143
+ If ActiveStorage is available:
144
+
145
+ ```ruby
146
+ result = <%= @root_namespace %>::Image::ProductGenerator.call(prompt: "Product shot")
147
+
148
+ # Attach to a model
149
+ product.images.attach(
150
+ io: StringIO.new(result.image_data),
151
+ filename: "product_image.png",
152
+ content_type: "image/png"
153
+ )
154
+ ```
155
+
156
+ ## Use Cases
157
+
158
+ ### Product Photography
159
+
160
+ ```ruby
161
+ module <%= @root_namespace %>
162
+ module Image
163
+ class ProductGenerator < ApplicationImageGenerator
164
+ model "gpt-image-1"
165
+ size "1024x1024"
166
+ quality "hd"
167
+ style "natural"
168
+
169
+ template "Professional product photography of {prompt}, " \
170
+ "white background, studio lighting, e-commerce style"
171
+
172
+ negative_prompt "text, watermark, blurry, low quality"
173
+ end
174
+ end
175
+ end
176
+ ```
177
+
178
+ ### Marketing Banners
179
+
180
+ ```ruby
181
+ module <%= @root_namespace %>
182
+ module Image
183
+ class BannerGenerator < ApplicationImageGenerator
184
+ model "gpt-image-1"
185
+ size "1792x1024" # Landscape
186
+ quality "hd"
187
+ style "vivid"
188
+
189
+ template "Marketing banner for {prompt}, bold colors, " \
190
+ "eye-catching design, professional"
191
+ end
192
+ end
193
+ end
194
+ ```
195
+
196
+ ### Avatar Generation
197
+
198
+ ```ruby
199
+ module <%= @root_namespace %>
200
+ module Image
201
+ class AvatarGenerator < ApplicationImageGenerator
202
+ model "gpt-image-1"
203
+ size "512x512"
204
+ quality "standard"
205
+ style "vivid"
206
+ content_policy :strict
207
+
208
+ template "Friendly cartoon avatar of {prompt}, " \
209
+ "professional, approachable, colorful"
210
+ end
211
+ end
212
+ end
213
+ ```
214
+
215
+ ### Social Media Graphics
216
+
217
+ ```ruby
218
+ module <%= @root_namespace %>
219
+ module Image
220
+ class SocialGenerator < ApplicationImageGenerator
221
+ model "gpt-image-1"
222
+ quality "standard"
223
+
224
+ def preprocess_prompt(prompt)
225
+ "#{prompt}, social media post, engaging, modern design"
226
+ end
227
+ end
228
+ end
229
+ end
230
+
231
+ # Usage with different sizes
232
+ <%= @root_namespace %>::Image::SocialGenerator.call(
233
+ prompt: "Tech announcement",
234
+ size: "1024x1024" # Instagram
235
+ )
236
+
237
+ <%= @root_namespace %>::Image::SocialGenerator.call(
238
+ prompt: "Tech announcement",
239
+ size: "1792x1024" # Twitter/LinkedIn
240
+ )
241
+ ```
242
+
243
+ ## Testing Generators
244
+
245
+ ```ruby
246
+ RSpec.describe <%= @root_namespace %>::Image::LogoGenerator do
247
+ describe ".call" do
248
+ it "generates an image" do
249
+ result = described_class.call(prompt: "Test logo")
250
+
251
+ expect(result.url).to be_present
252
+ expect(result.size).to eq("1024x1024")
253
+ end
254
+
255
+ it "respects quality setting" do
256
+ result = described_class.call(prompt: "Test", quality: "hd")
257
+
258
+ expect(result.quality).to eq("hd")
259
+ end
260
+ end
261
+
262
+ describe "#preprocess_prompt" do
263
+ it "enhances the prompt" do
264
+ generator = described_class.new(prompt: "simple logo")
265
+
266
+ result = generator.preprocess_prompt("simple logo")
267
+
268
+ expect(result).to include("simple logo")
269
+ end
270
+ end
271
+ end
272
+ ```
273
+
274
+ ## Best Practices
275
+
276
+ 1. **Use templates** - Ensure consistent style across generations
277
+ 2. **Set appropriate quality** - HD for final assets, standard for drafts
278
+ 3. **Use caching** - Same prompt produces same image
279
+ 4. **Add negative prompts** - Exclude unwanted elements
280
+ 5. **Match size to use case** - Don't generate larger than needed
281
+ 6. **Consider content policy** - Use strict for user-facing content
282
+ 7. **Handle errors gracefully** - Content policy rejections, rate limits
@@ -0,0 +1,228 @@
1
+ # <%= @root_namespace %>::Image Pipelines
2
+
3
+ This directory contains multi-step image processing pipelines. All pipelines inherit from `ApplicationImagePipeline`.
4
+
5
+ ## Creating a New Pipeline
6
+
7
+ Use the generator:
8
+ ```bash
9
+ rails generate ruby_llm_agents:image_pipeline PipelineName
10
+ rails generate ruby_llm_agents:image_pipeline Product --steps generate,upscale,remove_background
11
+ ```
12
+
13
+ Or create manually:
14
+ ```ruby
15
+ module <%= @root_namespace %>
16
+ module Image
17
+ class ProductPipeline < ApplicationImagePipeline
18
+ step :generate, generator: ProductGenerator
19
+ step :upscale, upscaler: PhotoUpscaler, scale: 2
20
+ step :remove_bg, remover: BackgroundRemover
21
+ end
22
+ end
23
+ end
24
+ ```
25
+
26
+ ## DSL Reference
27
+
28
+ ### Step Definition
29
+
30
+ ```ruby
31
+ step :name, generator: MyGenerator # Text-to-image generation
32
+ step :name, upscaler: MyUpscaler # Resolution enhancement
33
+ step :name, transformer: MyTransformer # Style transfer / img2img
34
+ step :name, editor: MyEditor # Inpainting / editing
35
+ step :name, variator: MyVariator # Generate variations
36
+ step :name, analyzer: MyAnalyzer # Image analysis
37
+ step :name, remover: MyRemover # Background removal
38
+ ```
39
+
40
+ ### Conditional Steps
41
+
42
+ ```ruby
43
+ step :upscale, upscaler: Upscaler, if: ->(ctx) { ctx[:high_quality] }
44
+ step :remove_bg, remover: Remover, unless: ->(ctx) { ctx[:keep_background] }
45
+ ```
46
+
47
+ ### Step Options
48
+
49
+ ```ruby
50
+ step :upscale, upscaler: PhotoUpscaler, scale: 4
51
+ step :transform, transformer: StyleTransformer, strength: 0.8
52
+ ```
53
+
54
+ ### Callbacks
55
+
56
+ ```ruby
57
+ before_pipeline :validate_inputs
58
+ after_pipeline :add_watermark
59
+ after_pipeline { |result| notify_completion(result) }
60
+ ```
61
+
62
+ ### Error Handling
63
+
64
+ ```ruby
65
+ stop_on_error true # Stop pipeline on first error (default)
66
+ stop_on_error false # Continue even if a step fails
67
+ ```
68
+
69
+ ### Caching
70
+
71
+ ```ruby
72
+ cache_for 1.hour # Cache pipeline results
73
+ ```
74
+
75
+ ## Using Pipelines
76
+
77
+ ### Basic Execution
78
+
79
+ ```ruby
80
+ result = <%= @root_namespace %>::Image::ProductPipeline.call(prompt: "Laptop on desk")
81
+
82
+ result.success? # All steps succeeded
83
+ result.final_image # Final processed image
84
+ result.url # Final image URL
85
+ result.total_cost # Combined cost of all steps
86
+ result.duration_ms # Total pipeline duration
87
+ ```
88
+
89
+ ### Access Individual Steps
90
+
91
+ ```ruby
92
+ result = <%= @root_namespace %>::Image::ProductPipeline.call(prompt: "Product photo")
93
+
94
+ result.step(:generate) # Generation step result
95
+ result.step(:upscale) # Upscale step result
96
+ result.steps # Array of all step results
97
+ result.step_count # Total number of steps
98
+ ```
99
+
100
+ ### Save Result
101
+
102
+ ```ruby
103
+ result = <%= @root_namespace %>::Image::ProductPipeline.call(prompt: "...")
104
+ result.save("final_output.png")
105
+ ```
106
+
107
+ ### Conditional Execution
108
+
109
+ ```ruby
110
+ module <%= @root_namespace %>
111
+ module Image
112
+ class SmartPipeline < ApplicationImagePipeline
113
+ step :generate, generator: ProductGenerator
114
+ step :upscale, upscaler: PhotoUpscaler, if: ->(ctx) { ctx[:hd] }
115
+ step :remove_bg, remover: BackgroundRemover, if: ->(ctx) { ctx[:transparent] }
116
+ end
117
+ end
118
+ end
119
+
120
+ # Call with options
121
+ result = <%= @root_namespace %>::Image::SmartPipeline.call(
122
+ prompt: "Product photo",
123
+ hd: true,
124
+ transparent: false
125
+ )
126
+ ```
127
+
128
+ ## Use Cases
129
+
130
+ ### E-commerce Product Pipeline
131
+
132
+ ```ruby
133
+ module <%= @root_namespace %>
134
+ module Image
135
+ class EcommercePipeline < ApplicationImagePipeline
136
+ description "Generate and process product images"
137
+ version "1.0"
138
+
139
+ step :generate, generator: ProductGenerator
140
+ step :upscale, upscaler: PhotoUpscaler, scale: 2
141
+ step :remove_bg, remover: BackgroundRemover
142
+ step :analyze, analyzer: ProductAnalyzer
143
+
144
+ cache_for 1.day
145
+
146
+ after_pipeline :log_completion
147
+
148
+ private
149
+
150
+ def log_completion(result)
151
+ Rails.logger.info("Pipeline completed: cost=#{result.total_cost}")
152
+ end
153
+ end
154
+ end
155
+ end
156
+ ```
157
+
158
+ ### Marketing Asset Pipeline
159
+
160
+ ```ruby
161
+ module <%= @root_namespace %>
162
+ module Image
163
+ class MarketingPipeline < ApplicationImagePipeline
164
+ step :generate, generator: MarketingGenerator, quality: "hd"
165
+ step :transform, transformer: BrandStyleTransformer, strength: 0.3
166
+ step :variations, variator: DesignVariator, count: 4
167
+
168
+ stop_on_error false # Continue even if transform fails
169
+ end
170
+ end
171
+ end
172
+
173
+ result = <%= @root_namespace %>::Image::MarketingPipeline.call(prompt: "Sale banner")
174
+ result.step(:variations).images # Get all variations
175
+ ```
176
+
177
+ ### Photo Enhancement Pipeline
178
+
179
+ ```ruby
180
+ module <%= @root_namespace %>
181
+ module Image
182
+ class EnhancementPipeline < ApplicationImagePipeline
183
+ step :upscale, upscaler: PhotoUpscaler, scale: 2
184
+ step :enhance, transformer: EnhancementTransformer, strength: 0.2
185
+ step :analyze, analyzer: QualityAnalyzer
186
+
187
+ before_pipeline :validate_image_format
188
+
189
+ private
190
+
191
+ def validate_image_format
192
+ raise ArgumentError, "Image required" unless context[:image]
193
+ end
194
+ end
195
+ end
196
+ end
197
+
198
+ # Process existing image
199
+ result = <%= @root_namespace %>::Image::EnhancementPipeline.call(image: "photo.jpg")
200
+ ```
201
+
202
+ ## Result Methods
203
+
204
+ ```ruby
205
+ result.success? # All steps succeeded
206
+ result.partial? # Some steps succeeded
207
+ result.error? # Pipeline failed
208
+
209
+ result.final_image # Final processed image
210
+ result.url # Final image URL
211
+ result.to_blob # Binary data
212
+ result.save("output.png") # Save to file
213
+
214
+ result.total_cost # Combined cost
215
+ result.duration_ms # Total duration
216
+ result.steps # All step results
217
+ result.step(:name) # Specific step result
218
+ ```
219
+
220
+ ## Best Practices
221
+
222
+ 1. **Order steps logically** - Generate before transform, upscale before final
223
+ 2. **Use conditional steps** - Skip unnecessary processing
224
+ 3. **Enable caching** - Especially for expensive pipelines
225
+ 4. **Add callbacks for monitoring** - Log completions, costs
226
+ 5. **Set appropriate stop_on_error** - Usually true for production
227
+ 6. **Version your pipelines** - Invalidate cache when steps change
228
+ 7. **Use analysis steps** - For quality assurance
@@ -0,0 +1,120 @@
1
+ # <%= @root_namespace %>::Image Transformers
2
+
3
+ This directory contains image transformation services (style transfer, img2img). All transformers inherit from `ApplicationImageTransformer`.
4
+
5
+ ## Creating a New Transformer
6
+
7
+ Use the generator:
8
+ ```bash
9
+ rails generate ruby_llm_agents:image_transformer TransformerName
10
+ rails generate ruby_llm_agents:image_transformer Style --strength 0.8
11
+ ```
12
+
13
+ Or create manually:
14
+ ```ruby
15
+ module <%= @root_namespace %>
16
+ module Image
17
+ class StyleTransformer < ApplicationImageTransformer
18
+ model "gpt-image-1"
19
+ strength 0.7
20
+ size "1024x1024"
21
+ end
22
+ end
23
+ end
24
+ ```
25
+
26
+ ## DSL Reference
27
+
28
+ | Method | Description | Example |
29
+ |--------|-------------|---------|
30
+ | `model` | Transformation model | `model "gpt-image-1"` |
31
+ | `strength` | Transformation intensity (0.0-1.0) | `strength 0.7` |
32
+ | `size` | Output size | `size "1024x1024"` |
33
+
34
+ ### Strength Values
35
+ - `0.1-0.3` - Subtle changes, preserve original
36
+ - `0.4-0.6` - Moderate transformation
37
+ - `0.7-0.9` - Strong style transfer
38
+ - `1.0` - Maximum transformation
39
+
40
+ ## Using Transformers
41
+
42
+ ```ruby
43
+ result = <%= @root_namespace %>::Image::StyleTransformer.call(
44
+ image: "photo.jpg",
45
+ prompt: "Oil painting style, impressionist"
46
+ )
47
+
48
+ result.url # Transformed image URL
49
+ result.image_data # Binary data
50
+ result.save("transformed.png")
51
+ ```
52
+
53
+ ### Override Strength
54
+
55
+ ```ruby
56
+ result = <%= @root_namespace %>::Image::StyleTransformer.call(
57
+ image: "photo.jpg",
58
+ prompt: "Watercolor painting",
59
+ strength: 0.5 # More subtle
60
+ )
61
+ ```
62
+
63
+ ## Use Cases
64
+
65
+ ### Artistic Style Transfer
66
+
67
+ ```ruby
68
+ module <%= @root_namespace %>
69
+ module Image
70
+ class ArtisticTransformer < ApplicationImageTransformer
71
+ strength 0.8
72
+
73
+ template "{prompt} style, artistic rendering, high quality"
74
+ end
75
+ end
76
+ end
77
+
78
+ # Usage
79
+ <%= @root_namespace %>::Image::ArtisticTransformer.call(
80
+ image: "photo.jpg",
81
+ prompt: "Van Gogh starry night"
82
+ )
83
+ ```
84
+
85
+ ### Photo Enhancement
86
+
87
+ ```ruby
88
+ module <%= @root_namespace %>
89
+ module Image
90
+ class EnhancementTransformer < ApplicationImageTransformer
91
+ strength 0.3 # Subtle enhancement
92
+
93
+ def default_prompt
94
+ "Enhanced lighting, improved colors, professional photography"
95
+ end
96
+ end
97
+ end
98
+ end
99
+ ```
100
+
101
+ ### Sketch to Photo
102
+
103
+ ```ruby
104
+ module <%= @root_namespace %>
105
+ module Image
106
+ class SketchToPhotoTransformer < ApplicationImageTransformer
107
+ strength 0.9
108
+
109
+ template "Photorealistic version of this sketch: {prompt}"
110
+ end
111
+ end
112
+ end
113
+ ```
114
+
115
+ ## Best Practices
116
+
117
+ 1. **Adjust strength carefully** - Start low, increase as needed
118
+ 2. **Match styles to content** - Some styles work better with certain images
119
+ 3. **Use descriptive prompts** - Specify the desired artistic style
120
+ 4. **Consider original quality** - Higher quality inputs produce better results