soka-rails 0.0.1.beta4

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.
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 jiunjiun
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,420 @@
1
+ # Soka Rails
2
+
3
+ <p align="center">
4
+ <strong>Rails Integration for Soka AI Agent Framework</strong>
5
+ </p>
6
+
7
+ <p align="center">
8
+ <a href="#features">Features</a> •
9
+ <a href="#installation">Installation</a> •
10
+ <a href="#quick-start">Quick Start</a> •
11
+ <a href="#usage">Usage</a> •
12
+ <a href="#generators">Generators</a> •
13
+ <a href="#testing">Testing</a> •
14
+ <a href="#contributing">Contributing</a>
15
+ </p>
16
+
17
+ Soka Rails is a Rails integration package for the Soka AI Agent Framework, providing seamless integration with the Rails ecosystem. It follows Rails conventions and best practices, making it easy for developers to use AI Agents in their Rails applications.
18
+
19
+ ## Features
20
+
21
+ - 🚂 **Native Rails Integration**: Following Rails conventions and best practices
22
+ - 📁 **Auto-loading Support**: Automatically loads the `app/soka` directory
23
+ - 🛠️ **Generator Support**: Quickly generate Agent and Tool templates
24
+ - ⚙️ **Rails Configuration Integration**: Uses Rails' configuration system
25
+ - 🧪 **Rails Testing Integration**: Seamless integration with RSpec
26
+ - 🔄 **Rails Lifecycle Hooks**: Integrates with Rails logging and error tracking
27
+ - 💾 **Session Memory Support**: Store conversation history in Rails sessions
28
+ - 🔐 **Authentication Integration**: Works with Rails authentication systems
29
+
30
+ ## Installation
31
+
32
+ Add the following to your Gemfile:
33
+
34
+ ```ruby
35
+ gem 'soka-rails'
36
+ ```
37
+
38
+ Then execute:
39
+
40
+ ```bash
41
+ bundle install
42
+ ```
43
+
44
+ Run the installation generator:
45
+
46
+ ```bash
47
+ rails generate soka:install
48
+ ```
49
+
50
+ This will generate:
51
+ - `config/initializers/soka.rb` - Main configuration file
52
+ - `app/soka/agents/application_agent.rb` - Base Agent class
53
+ - `app/soka/tools/application_tool.rb` - Base Tool class
54
+
55
+ ## Quick Start
56
+
57
+ ### 1. Configure API Keys
58
+
59
+ ```ruby
60
+ # config/initializers/soka.rb
61
+ Soka::Rails.configure do |config|
62
+ config.ai do |ai|
63
+ ai.provider = ENV.fetch('SOKA_PROVIDER', :gemini)
64
+ ai.model = ENV.fetch('SOKA_MODEL', 'gemini-2.5-flash-lite')
65
+ ai.api_key = ENV['SOKA_API_KEY']
66
+ end
67
+ end
68
+ ```
69
+
70
+ ### 2. Create an Agent
71
+
72
+ ```bash
73
+ rails generate soka:agent customer_support
74
+ ```
75
+
76
+ ```ruby
77
+ # app/soka/agents/customer_support_agent.rb
78
+ class CustomerSupportAgent < ApplicationAgent
79
+ tool OrderLookupTool
80
+ tool UserInfoTool
81
+ end
82
+ ```
83
+
84
+ ### 3. Use in Controller
85
+
86
+ ```ruby
87
+ class ConversationsController < ApplicationController
88
+ def create
89
+ agent = CustomerSupportAgent.new
90
+ result = agent.run(params[:message])
91
+
92
+ render json: {
93
+ answer: result.final_answer,
94
+ confidence: result.confidence_score
95
+ }
96
+ end
97
+ end
98
+ ```
99
+
100
+ ## Usage
101
+
102
+ ### Directory Structure
103
+
104
+ ```
105
+ rails-app/
106
+ ├── app/
107
+ │ └── soka/
108
+ │ ├── agents/ # Agent definitions
109
+ │ │ ├── application_agent.rb
110
+ │ │ └── customer_support_agent.rb
111
+ │ └── tools/ # Tool definitions
112
+ │ ├── application_tool.rb
113
+ │ └── order_lookup_tool.rb
114
+ └── config/
115
+ └── initializers/
116
+ └── soka.rb # Global configuration
117
+ ```
118
+
119
+ ### Creating Agents
120
+
121
+ ```ruby
122
+ class WeatherAgent < ApplicationAgent
123
+ # Configure AI settings
124
+ provider :gemini
125
+ model 'gemini-2.5-flash-lite'
126
+ max_iterations 10
127
+ timeout 30.seconds
128
+
129
+ # Register tools
130
+ tool WeatherApiTool
131
+ tool LocationTool
132
+
133
+ # Rails integration hooks
134
+ before_action :log_request
135
+ on_error :notify_error_service
136
+
137
+ private
138
+
139
+ def log_request(input)
140
+ Rails.logger.info "[WeatherAgent] Processing: #{input}"
141
+ end
142
+
143
+ def notify_error_service(error, context)
144
+ Rails.error.report(error, context: context)
145
+ :continue
146
+ end
147
+ end
148
+ ```
149
+
150
+ ### Creating Tools
151
+
152
+ ```ruby
153
+ class OrderLookupTool < ApplicationTool
154
+ desc "Look up order information"
155
+
156
+ params do
157
+ requires :order_id, String, desc: "Order ID"
158
+ optional :include_items, :boolean, desc: "Include order items", default: false
159
+ end
160
+
161
+ def call(order_id:, include_items: false)
162
+ order = Order.find_by(id: order_id)
163
+ return { error: "Order not found" } unless order
164
+
165
+ data = {
166
+ id: order.id,
167
+ status: order.status,
168
+ total: order.total,
169
+ created_at: order.created_at
170
+ }
171
+
172
+ data[:items] = order.items if include_items
173
+ data
174
+ end
175
+ end
176
+ ```
177
+
178
+ ### Session Memory
179
+
180
+ ```ruby
181
+ class ConversationsController < ApplicationController
182
+ def create
183
+ # Load memory from session
184
+ memory = session[:conversation_memory] || []
185
+
186
+ agent = CustomerSupportAgent.new(memory: memory)
187
+ result = agent.run(params[:message])
188
+
189
+ # Update session memory
190
+ session[:conversation_memory] = agent.memory.to_a
191
+
192
+ render json: { answer: result.final_answer }
193
+ end
194
+ end
195
+ ```
196
+
197
+ ### Event Streaming
198
+
199
+ ```ruby
200
+ class ConversationsController < ApplicationController
201
+ include ActionController::Live
202
+
203
+ def stream
204
+ response.headers['Content-Type'] = 'text/event-stream'
205
+ agent = CustomerSupportAgent.new
206
+
207
+ agent.run(params[:message]) do |event|
208
+ response.stream.write("event: #{event.type}\n")
209
+ response.stream.write("data: #{event.content.to_json}\n\n")
210
+ end
211
+ ensure
212
+ response.stream.close
213
+ end
214
+ end
215
+ ```
216
+
217
+ ## Generators
218
+
219
+ ### Install Generator
220
+
221
+ ```bash
222
+ rails generate soka:install
223
+ ```
224
+
225
+ ### Agent Generator
226
+
227
+ ```bash
228
+ # Basic usage
229
+ rails generate soka:agent weather
230
+
231
+ # With tools - automatically registers tools in the agent
232
+ rails generate soka:agent weather forecast temperature humidity
233
+ ```
234
+
235
+ Creates `app/soka/agents/weather_agent.rb` with a template structure.
236
+
237
+ When tools are specified, the generated agent will include them:
238
+
239
+ ```ruby
240
+ class WeatherAgent < ApplicationAgent
241
+ # Tool registration
242
+ tool ForecastTool
243
+ tool TemperatureTool
244
+ tool HumidityTool
245
+
246
+ # Configuration
247
+ # max_iterations 10
248
+ # timeout 30
249
+ end
250
+ ```
251
+
252
+ ### Tool Generator
253
+
254
+ ```bash
255
+ # Basic usage
256
+ rails generate soka:tool weather_api
257
+
258
+ # With parameters - automatically generates parameter definitions
259
+ rails generate soka:tool weather_api location:string units:string timeout:integer
260
+ ```
261
+
262
+ Creates `app/soka/tools/weather_api_tool.rb` with parameter definitions.
263
+
264
+ When parameters are specified, the generated tool will include them:
265
+
266
+ ```ruby
267
+ class WeatherApiTool < ApplicationTool
268
+ desc 'Description of your tool'
269
+
270
+ params do
271
+ requires :location, String, desc: 'Location'
272
+ requires :units, String, desc: 'Units'
273
+ requires :timeout, Integer, desc: 'Timeout'
274
+ end
275
+
276
+ def call(**params)
277
+ # Implement your tool logic here
278
+ end
279
+ end
280
+ ```
281
+
282
+ ## Testing
283
+
284
+ ### RSpec Configuration
285
+
286
+ ```ruby
287
+ # spec/rails_helper.rb
288
+ require 'soka/rails/rspec'
289
+
290
+ RSpec.configure do |config|
291
+ config.include Soka::Rails::TestHelpers, type: :agent
292
+ config.include Soka::Rails::TestHelpers, type: :tool
293
+ end
294
+ ```
295
+
296
+ ### Testing Agents
297
+
298
+ ```ruby
299
+ RSpec.describe WeatherAgent, type: :agent do
300
+ let(:agent) { described_class.new }
301
+
302
+ before do
303
+ mock_ai_response(
304
+ final_answer: "Today in Tokyo it's sunny with 28°C"
305
+ )
306
+ end
307
+
308
+ it "responds to weather queries" do
309
+ result = agent.run("What's the weather in Tokyo?")
310
+
311
+ expect(result).to be_successful
312
+ expect(result.final_answer).to include("28°C")
313
+ end
314
+ end
315
+ ```
316
+
317
+ ### Testing Tools
318
+
319
+ ```ruby
320
+ RSpec.describe OrderLookupTool, type: :tool do
321
+ let(:tool) { described_class.new }
322
+ let(:order) { create(:order, id: "123", status: "delivered") }
323
+
324
+ it "finds existing orders" do
325
+ result = tool.call(order_id: order.id)
326
+
327
+ expect(result[:status]).to eq("delivered")
328
+ expect(result[:id]).to eq("123")
329
+ end
330
+
331
+ it "handles missing orders" do
332
+ result = tool.call(order_id: "nonexistent")
333
+
334
+ expect(result[:error]).to include("not found")
335
+ end
336
+ end
337
+ ```
338
+
339
+ ## Rails-Specific Tools
340
+
341
+ ### RailsInfoTool
342
+
343
+ A built-in tool for accessing Rails application information:
344
+
345
+ ```ruby
346
+ class RailsInfoTool < ApplicationTool
347
+ desc "Get Rails application information"
348
+
349
+ params do
350
+ requires :info_type, String, desc: "Type of information",
351
+ validates: { inclusion: { in: %w[routes version environment config] } }
352
+ end
353
+
354
+ def call(info_type:)
355
+ case info_type
356
+ when 'routes'
357
+ # Returns application routes
358
+ when 'version'
359
+ # Returns Rails and Ruby versions
360
+ when 'environment'
361
+ # Returns environment information
362
+ when 'config'
363
+ # Returns safe configuration values
364
+ end
365
+ end
366
+ end
367
+ ```
368
+
369
+ ## Configuration
370
+
371
+ ### Environment-based Configuration
372
+
373
+ ```ruby
374
+ Soka::Rails.configure do |config|
375
+ config.ai do |ai|
376
+ ai.provider = ENV.fetch('SOKA_PROVIDER', :gemini)
377
+ ai.model = ENV.fetch('SOKA_MODEL', 'gemini-2.5-flash-lite')
378
+ ai.api_key = ENV['SOKA_API_KEY']
379
+ end
380
+
381
+ config.performance do |perf|
382
+ perf.max_iterations = Rails.env.production? ? 10 : 5
383
+ perf.timeout = 30.seconds
384
+ end
385
+ end
386
+ ```
387
+
388
+ ## Compatibility
389
+
390
+ - Ruby: >= 3.4
391
+ - Rails: >= 7.0
392
+ - Soka: >= 1.0
393
+
394
+ ## Contributing
395
+
396
+ We welcome all forms of contributions!
397
+
398
+ 1. Fork the project
399
+ 2. Create your feature branch (`git checkout -b feature/amazing-feature`)
400
+ 3. Commit your changes (`git commit -m 'Add amazing feature'`)
401
+ 4. Push to the branch (`git push origin feature/amazing-feature`)
402
+ 5. Open a Pull Request
403
+
404
+ Please ensure:
405
+ - Add appropriate tests
406
+ - Update relevant documentation
407
+ - Follow Rails coding conventions
408
+ - Pass Rubocop checks
409
+
410
+ ## License
411
+
412
+ This project is licensed under the MIT License. See the [LICENSE](LICENSE) file for details.
413
+
414
+ ---
415
+
416
+ <p align="center">
417
+ Made with ❤️ for the Rails Community<br>
418
+ Built on top of <a href="https://github.com/jiunjiun/soka">Soka AI Agent Framework</a><br>
419
+ Created by <a href="https://claude.ai/code">Claude Code</a>
420
+ </p>