swarm_memory 2.1.1 → 2.1.3

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 (79) hide show
  1. checksums.yaml +4 -4
  2. data/lib/claude_swarm/cli.rb +9 -11
  3. data/lib/claude_swarm/commands/ps.rb +1 -2
  4. data/lib/claude_swarm/configuration.rb +30 -7
  5. data/lib/claude_swarm/mcp_generator.rb +4 -10
  6. data/lib/claude_swarm/orchestrator.rb +43 -44
  7. data/lib/claude_swarm/system_utils.rb +4 -4
  8. data/lib/claude_swarm/version.rb +1 -1
  9. data/lib/claude_swarm.rb +5 -9
  10. data/lib/swarm_cli/commands/mcp_serve.rb +2 -2
  11. data/lib/swarm_cli/commands/mcp_tools.rb +3 -3
  12. data/lib/swarm_cli/config_loader.rb +14 -13
  13. data/lib/swarm_cli/version.rb +1 -1
  14. data/lib/swarm_cli.rb +2 -0
  15. data/lib/swarm_memory/adapters/base.rb +4 -4
  16. data/lib/swarm_memory/adapters/filesystem_adapter.rb +0 -12
  17. data/lib/swarm_memory/core/storage.rb +66 -6
  18. data/lib/swarm_memory/core/storage_read_tracker.rb +51 -14
  19. data/lib/swarm_memory/integration/cli_registration.rb +3 -2
  20. data/lib/swarm_memory/integration/sdk_plugin.rb +24 -4
  21. data/lib/swarm_memory/optimization/defragmenter.rb +4 -0
  22. data/lib/swarm_memory/tools/memory_edit.rb +3 -2
  23. data/lib/swarm_memory/tools/memory_glob.rb +24 -1
  24. data/lib/swarm_memory/tools/memory_multi_edit.rb +2 -2
  25. data/lib/swarm_memory/tools/memory_read.rb +3 -3
  26. data/lib/swarm_memory/tools/memory_write.rb +2 -2
  27. data/lib/swarm_memory/version.rb +1 -1
  28. data/lib/swarm_memory.rb +7 -0
  29. data/lib/swarm_sdk/agent/builder.rb +33 -0
  30. data/lib/swarm_sdk/agent/chat/context_tracker.rb +33 -0
  31. data/lib/swarm_sdk/agent/chat/hook_integration.rb +41 -0
  32. data/lib/swarm_sdk/agent/chat/system_reminder_injector.rb +11 -27
  33. data/lib/swarm_sdk/agent/chat.rb +199 -52
  34. data/lib/swarm_sdk/agent/context.rb +6 -2
  35. data/lib/swarm_sdk/agent/context_manager.rb +6 -0
  36. data/lib/swarm_sdk/agent/definition.rb +32 -23
  37. data/lib/swarm_sdk/agent/llm_instrumentation_middleware.rb +180 -0
  38. data/lib/swarm_sdk/configuration.rb +420 -103
  39. data/lib/swarm_sdk/events_to_messages.rb +181 -0
  40. data/lib/swarm_sdk/log_collector.rb +31 -5
  41. data/lib/swarm_sdk/log_stream.rb +37 -8
  42. data/lib/swarm_sdk/model_aliases.json +4 -1
  43. data/lib/swarm_sdk/node/agent_config.rb +39 -9
  44. data/lib/swarm_sdk/node/builder.rb +158 -42
  45. data/lib/swarm_sdk/node_context.rb +75 -0
  46. data/lib/swarm_sdk/node_orchestrator.rb +492 -18
  47. data/lib/swarm_sdk/plugin.rb +73 -1
  48. data/lib/swarm_sdk/proc_helpers.rb +53 -0
  49. data/lib/swarm_sdk/prompts/base_system_prompt.md.erb +0 -126
  50. data/lib/swarm_sdk/providers/openai_with_responses.rb +22 -15
  51. data/lib/swarm_sdk/restore_result.rb +65 -0
  52. data/lib/swarm_sdk/result.rb +32 -6
  53. data/lib/swarm_sdk/snapshot.rb +156 -0
  54. data/lib/swarm_sdk/snapshot_from_events.rb +386 -0
  55. data/lib/swarm_sdk/state_restorer.rb +491 -0
  56. data/lib/swarm_sdk/state_snapshot.rb +369 -0
  57. data/lib/swarm_sdk/swarm/agent_initializer.rb +360 -55
  58. data/lib/swarm_sdk/swarm/all_agents_builder.rb +28 -1
  59. data/lib/swarm_sdk/swarm/builder.rb +208 -11
  60. data/lib/swarm_sdk/swarm/swarm_registry_builder.rb +67 -0
  61. data/lib/swarm_sdk/swarm/tool_configurator.rb +46 -11
  62. data/lib/swarm_sdk/swarm.rb +367 -90
  63. data/lib/swarm_sdk/swarm_loader.rb +145 -0
  64. data/lib/swarm_sdk/swarm_registry.rb +136 -0
  65. data/lib/swarm_sdk/tools/delegate.rb +94 -9
  66. data/lib/swarm_sdk/tools/read.rb +17 -5
  67. data/lib/swarm_sdk/tools/scratchpad/scratchpad_list.rb +23 -2
  68. data/lib/swarm_sdk/tools/scratchpad/scratchpad_read.rb +23 -2
  69. data/lib/swarm_sdk/tools/scratchpad/scratchpad_write.rb +21 -4
  70. data/lib/swarm_sdk/tools/stores/read_tracker.rb +47 -12
  71. data/lib/swarm_sdk/tools/stores/scratchpad_storage.rb +45 -0
  72. data/lib/swarm_sdk/tools/stores/storage.rb +4 -4
  73. data/lib/swarm_sdk/tools/think.rb +4 -1
  74. data/lib/swarm_sdk/tools/todo_write.rb +20 -8
  75. data/lib/swarm_sdk/utils.rb +18 -0
  76. data/lib/swarm_sdk/validation_result.rb +33 -0
  77. data/lib/swarm_sdk/version.rb +1 -1
  78. data/lib/swarm_sdk.rb +365 -28
  79. metadata +17 -5
data/lib/swarm_sdk.rb CHANGED
@@ -21,19 +21,17 @@ require_relative "swarm_sdk/version"
21
21
 
22
22
  require "zeitwerk"
23
23
  loader = Zeitwerk::Loader.new
24
+ loader.tag = File.basename(__FILE__, ".rb")
24
25
  loader.push_dir("#{__dir__}/swarm_sdk", namespace: SwarmSDK)
26
+ loader.inflector = Zeitwerk::GemInflector.new(__FILE__)
25
27
  loader.inflector.inflect(
26
28
  "cli" => "CLI",
29
+ "llm_instrumentation_middleware" => "LLMInstrumentationMiddleware",
30
+ "mcp" => "MCP",
31
+ "openai_with_responses" => "OpenAIWithResponses",
27
32
  )
28
33
  loader.setup
29
34
 
30
- # Load plugin system explicitly (core infrastructure)
31
- require_relative "swarm_sdk/plugin"
32
- require_relative "swarm_sdk/plugin_registry"
33
-
34
- # Load custom providers explicitly (Zeitwerk doesn't eager load by default)
35
- require_relative "swarm_sdk/providers/openai_with_responses"
36
-
37
35
  module SwarmSDK
38
36
  class Error < StandardError; end
39
37
  class ConfigurationError < Error; end
@@ -48,8 +46,176 @@ module SwarmSDK
48
46
  attr_accessor :settings
49
47
 
50
48
  # Main entry point for DSL
51
- def build(&block)
52
- Swarm::Builder.build(&block)
49
+ def build(allow_filesystem_tools: nil, &block)
50
+ Swarm::Builder.build(allow_filesystem_tools: allow_filesystem_tools, &block)
51
+ end
52
+
53
+ # Validate YAML configuration without creating a swarm
54
+ #
55
+ # Performs comprehensive validation of YAML configuration including:
56
+ # - YAML syntax
57
+ # - Required fields (version, swarm name, lead, agents)
58
+ # - Agent configurations (description, directory existence)
59
+ # - Circular dependencies
60
+ # - File references (agent_file paths)
61
+ # - Hook configurations
62
+ #
63
+ # @param yaml_content [String] YAML configuration content
64
+ # @param base_dir [String, Pathname] Base directory for resolving agent file paths (default: Dir.pwd)
65
+ # @return [Array<Hash>] Array of error hashes (empty if valid)
66
+ #
67
+ # @example Validate YAML string
68
+ # errors = SwarmSDK.validate(yaml_content)
69
+ # if errors.empty?
70
+ # puts "Configuration is valid!"
71
+ # else
72
+ # errors.each do |error|
73
+ # puts "#{error[:field]}: #{error[:message]}"
74
+ # end
75
+ # end
76
+ #
77
+ # @example Error hash structure
78
+ # {
79
+ # type: :missing_field, # Error type
80
+ # field: "swarm.agents.backend.description", # JSON-style path to field
81
+ # message: "Agent 'backend' missing required 'description' field",
82
+ # agent: "backend" # Optional, present if error is agent-specific
83
+ # }
84
+ def validate(yaml_content, base_dir: Dir.pwd)
85
+ errors = []
86
+
87
+ begin
88
+ config = Configuration.new(yaml_content, base_dir: base_dir)
89
+ config.load_and_validate
90
+
91
+ # Build swarm to trigger DSL validation
92
+ # This catches errors from Agent::Definition, Builder, etc.
93
+ config.to_swarm
94
+ rescue ConfigurationError, CircularDependencyError => e
95
+ errors << parse_configuration_error(e)
96
+ rescue StandardError => e
97
+ errors << {
98
+ type: :unknown_error,
99
+ field: nil,
100
+ message: e.message,
101
+ }
102
+ end
103
+
104
+ errors
105
+ end
106
+
107
+ # Validate YAML configuration file
108
+ #
109
+ # Convenience method that reads the file and validates the content.
110
+ #
111
+ # @param path [String, Pathname] Path to YAML configuration file
112
+ # @return [Array<Hash>] Array of error hashes (empty if valid)
113
+ #
114
+ # @example
115
+ # errors = SwarmSDK.validate_file("config.yml")
116
+ # if errors.empty?
117
+ # puts "Valid configuration!"
118
+ # swarm = SwarmSDK.load_file("config.yml")
119
+ # else
120
+ # errors.each { |e| puts "Error: #{e[:message]}" }
121
+ # end
122
+ def validate_file(path)
123
+ path = Pathname.new(path).expand_path
124
+
125
+ unless path.exist?
126
+ return [{
127
+ type: :file_not_found,
128
+ field: nil,
129
+ message: "Configuration file not found: #{path}",
130
+ }]
131
+ end
132
+
133
+ yaml_content = File.read(path)
134
+ base_dir = path.dirname
135
+
136
+ validate(yaml_content, base_dir: base_dir)
137
+ rescue StandardError => e
138
+ [{
139
+ type: :file_read_error,
140
+ field: nil,
141
+ message: "Error reading file: #{e.message}",
142
+ }]
143
+ end
144
+
145
+ # Load swarm from YAML string
146
+ #
147
+ # This is the primary programmatic API for loading YAML configurations.
148
+ # For file-based loading, use SwarmSDK.load_file for convenience.
149
+ #
150
+ # @param yaml_content [String] YAML configuration content
151
+ # @param base_dir [String, Pathname] Base directory for resolving agent file paths (default: Dir.pwd)
152
+ # @return [Swarm, NodeOrchestrator] Configured swarm or orchestrator instance
153
+ # @raise [ConfigurationError] If YAML is invalid or configuration is incorrect
154
+ #
155
+ # @example Load from YAML string
156
+ # yaml = <<~YAML
157
+ # version: 2
158
+ # swarm:
159
+ # name: "Dev Team"
160
+ # lead: backend
161
+ # agents:
162
+ # backend:
163
+ # description: "Backend developer"
164
+ # model: "gpt-4"
165
+ # agent_file: "agents/backend.md" # Resolved relative to base_dir
166
+ # YAML
167
+ #
168
+ # swarm = SwarmSDK.load(yaml, base_dir: "/path/to/project")
169
+ # result = swarm.execute("Build authentication")
170
+ #
171
+ # @example Load with default base_dir (Dir.pwd)
172
+ # yaml = File.read("config.yml")
173
+ # swarm = SwarmSDK.load(yaml) # base_dir defaults to Dir.pwd
174
+ def load(yaml_content, base_dir: Dir.pwd, allow_filesystem_tools: nil)
175
+ config = Configuration.new(yaml_content, base_dir: base_dir)
176
+ config.load_and_validate
177
+ swarm = config.to_swarm(allow_filesystem_tools: allow_filesystem_tools)
178
+
179
+ # Apply hooks if any are configured (YAML-only feature)
180
+ if hooks_configured?(config)
181
+ Hooks::Adapter.apply_hooks(swarm, config)
182
+ end
183
+
184
+ # Store config reference for agent hooks (applied during initialize_agents)
185
+ swarm.config_for_hooks = config
186
+
187
+ swarm
188
+ end
189
+
190
+ # Load swarm from YAML file (convenience method)
191
+ #
192
+ # Reads the YAML file and uses the file's directory as the base directory
193
+ # for resolving agent file paths. This is the recommended method for
194
+ # loading swarms from configuration files.
195
+ #
196
+ # @param path [String, Pathname] Path to YAML configuration file
197
+ # @return [Swarm, NodeOrchestrator] Configured swarm or orchestrator instance
198
+ # @raise [ConfigurationError] If file not found or configuration invalid
199
+ #
200
+ # @example
201
+ # swarm = SwarmSDK.load_file("config.yml")
202
+ # result = swarm.execute("Build authentication")
203
+ #
204
+ # @example With absolute path
205
+ # swarm = SwarmSDK.load_file("/absolute/path/config.yml")
206
+ def load_file(path, allow_filesystem_tools: nil)
207
+ config = Configuration.load_file(path)
208
+ swarm = config.to_swarm(allow_filesystem_tools: allow_filesystem_tools)
209
+
210
+ # Apply hooks if any are configured (YAML-only feature)
211
+ if hooks_configured?(config)
212
+ Hooks::Adapter.apply_hooks(swarm, config)
213
+ end
214
+
215
+ # Store config reference for agent hooks (applied during initialize_agents)
216
+ swarm.config_for_hooks = config
217
+
218
+ swarm
53
219
  end
54
220
 
55
221
  # Configure SwarmSDK global settings
@@ -66,6 +232,180 @@ module SwarmSDK
66
232
  # Alias for backward compatibility
67
233
  alias_method :configuration, :settings
68
234
  alias_method :reset_configuration!, :reset_settings!
235
+
236
+ private
237
+
238
+ # Check if hooks are configured in the configuration
239
+ #
240
+ # @param config [Configuration] Configuration instance
241
+ # @return [Boolean] true if any hooks are configured
242
+ def hooks_configured?(config)
243
+ config.swarm_hooks.any? ||
244
+ config.all_agents_hooks.any? ||
245
+ config.agents.any? { |_, agent_config| agent_config[:hooks]&.any? }
246
+ end
247
+
248
+ # Parse configuration error and extract structured information
249
+ #
250
+ # Attempts to extract field path and agent name from error messages.
251
+ # Returns a structured error hash with type, field, message, and optional agent.
252
+ #
253
+ # @param error [StandardError] The caught error
254
+ # @return [Hash] Structured error hash
255
+ def parse_configuration_error(error)
256
+ message = error.message
257
+ error_hash = { message: message }
258
+
259
+ # Detect error type and extract field information
260
+ case message
261
+ # YAML syntax errors
262
+ when /Invalid YAML syntax/i
263
+ error_hash.merge!(
264
+ type: :syntax_error,
265
+ field: nil,
266
+ )
267
+
268
+ # Missing version field
269
+ when /Missing 'version' field/i
270
+ error_hash.merge!(
271
+ type: :missing_field,
272
+ field: "version",
273
+ )
274
+
275
+ # Invalid version
276
+ when /SwarmSDK requires version: (\d+)/i
277
+ error_hash.merge!(
278
+ type: :invalid_value,
279
+ field: "version",
280
+ )
281
+
282
+ # Missing swarm fields
283
+ when /Missing '(\w+)' field in swarm configuration/i
284
+ field_name = Regexp.last_match(1)
285
+ error_hash.merge!(
286
+ type: :missing_field,
287
+ field: "swarm.#{field_name}",
288
+ )
289
+
290
+ # Agent missing required field
291
+ when /Agent '([^']+)' missing required '([^']+)' field/i
292
+ agent_name = Regexp.last_match(1)
293
+ field_name = Regexp.last_match(2)
294
+ error_hash.merge!(
295
+ type: :missing_field,
296
+ field: "swarm.agents.#{agent_name}.#{field_name}",
297
+ agent: agent_name,
298
+ )
299
+
300
+ # Directory does not exist
301
+ when /Directory '([^']+)' for agent '([^']+)' does not exist/i
302
+ agent_name = Regexp.last_match(2)
303
+ error_hash.merge!(
304
+ type: :directory_not_found,
305
+ field: "swarm.agents.#{agent_name}.directory",
306
+ agent: agent_name,
307
+ )
308
+
309
+ # Error loading agent from file (must come before "Agent file not found")
310
+ when /Error loading agent '([^']+)' from file/i
311
+ agent_name = Regexp.last_match(1)
312
+ error_hash.merge!(
313
+ type: :file_load_error,
314
+ field: "swarm.agents.#{agent_name}.agent_file",
315
+ agent: agent_name,
316
+ )
317
+
318
+ # Agent file not found
319
+ when /Agent file not found: (.+)/i
320
+ # Try to extract agent name from the error context if available
321
+ error_hash.merge!(
322
+ type: :file_not_found,
323
+ field: nil, # We don't know which agent without more context
324
+ )
325
+
326
+ # Lead agent not found
327
+ when /Lead agent '([^']+)' not found in agents/i
328
+ error_hash.merge!(
329
+ type: :invalid_reference,
330
+ field: "swarm.lead",
331
+ )
332
+
333
+ # Unknown agent in connections (old format)
334
+ when /Agent '([^']+)' has connection to unknown agent '([^']+)'/i
335
+ agent_name = Regexp.last_match(1)
336
+ error_hash.merge!(
337
+ type: :invalid_reference,
338
+ field: "swarm.agents.#{agent_name}.delegates_to",
339
+ agent: agent_name,
340
+ )
341
+
342
+ # Unknown agent in connections (new format with composable swarms)
343
+ when /Agent '([^']+)' delegates to unknown target '([^']+)'/i
344
+ agent_name = Regexp.last_match(1)
345
+ error_hash.merge!(
346
+ type: :invalid_reference,
347
+ field: "swarm.agents.#{agent_name}.delegates_to",
348
+ agent: agent_name,
349
+ )
350
+
351
+ # Circular dependency
352
+ when /Circular dependency detected/i
353
+ error_hash.merge!(
354
+ type: :circular_dependency,
355
+ field: nil,
356
+ )
357
+
358
+ # Configuration file not found
359
+ when /Configuration file not found/i
360
+ error_hash.merge!(
361
+ type: :file_not_found,
362
+ field: nil,
363
+ )
364
+
365
+ # Invalid hook event
366
+ when /Invalid hook event '([^']+)' for agent '([^']+)'/i
367
+ agent_name = Regexp.last_match(2)
368
+ error_hash.merge!(
369
+ type: :invalid_value,
370
+ field: "swarm.agents.#{agent_name}.hooks",
371
+ agent: agent_name,
372
+ )
373
+
374
+ # api_version validation error
375
+ when /Agent '([^']+)' has api_version set, but provider is/i
376
+ agent_name = Regexp.last_match(1)
377
+ error_hash.merge!(
378
+ type: :invalid_value,
379
+ field: "swarm.agents.#{agent_name}.api_version",
380
+ agent: agent_name,
381
+ )
382
+
383
+ # api_version invalid value
384
+ when /Agent '([^']+)' has invalid api_version/i
385
+ agent_name = Regexp.last_match(1)
386
+ error_hash.merge!(
387
+ type: :invalid_value,
388
+ field: "swarm.agents.#{agent_name}.api_version",
389
+ agent: agent_name,
390
+ )
391
+
392
+ # No agents defined
393
+ when /No agents defined/i
394
+ error_hash.merge!(
395
+ type: :missing_field,
396
+ field: "swarm.agents",
397
+ )
398
+
399
+ # Default: unknown error
400
+ else
401
+ error_hash.merge!(
402
+ type: :validation_error,
403
+ field: nil,
404
+ )
405
+ end
406
+
407
+ error_hash.compact
408
+ end
69
409
  end
70
410
 
71
411
  # Settings class for SwarmSDK global settings (not to be confused with Configuration for YAML loading)
@@ -73,17 +413,33 @@ module SwarmSDK
73
413
  # WebFetch tool LLM processing configuration
74
414
  attr_accessor :webfetch_provider, :webfetch_model, :webfetch_base_url, :webfetch_max_tokens
75
415
 
416
+ # Filesystem tools control
417
+ attr_accessor :allow_filesystem_tools
418
+
76
419
  def initialize
77
420
  @webfetch_provider = nil
78
421
  @webfetch_model = nil
79
422
  @webfetch_base_url = nil
80
423
  @webfetch_max_tokens = 4096
424
+ @allow_filesystem_tools = parse_env_bool("SWARM_SDK_ALLOW_FILESYSTEM_TOOLS", default: true)
81
425
  end
82
426
 
83
427
  # Check if WebFetch LLM processing is enabled
84
428
  def webfetch_llm_enabled?
85
429
  !@webfetch_provider.nil? && !@webfetch_model.nil?
86
430
  end
431
+
432
+ private
433
+
434
+ def parse_env_bool(key, default:)
435
+ return default unless ENV.key?(key)
436
+
437
+ value = ENV[key].to_s.downcase
438
+ return true if ["true", "yes", "1", "on", "enabled"].include?(value)
439
+ return false if ["false", "no", "0", "off", "disabled"].include?(value)
440
+
441
+ default
442
+ end
87
443
  end
88
444
 
89
445
  # Initialize default settings
@@ -136,22 +492,3 @@ RubyLLM.configure do |config|
136
492
  config.gpustack_api_base ||= ENV["GPUSTACK_API_BASE"]
137
493
  config.gpustack_api_key ||= ENV["GPUSTACK_API_KEY"]
138
494
  end
139
-
140
- # monkey patches
141
- # ruby_llm/mcp
142
- # - add `id` when sending "notifications/initialized" message: https://github.com/patvice/ruby_llm-mcp/issues/65
143
- # - remove `to_sym` on MCP parameter type: https://github.com/patvice/ruby_llm-mcp/issues/62#issuecomment-3421488406
144
- require "ruby_llm/mcp/notifications/initialize"
145
- require "ruby_llm/mcp/parameter"
146
-
147
- module RubyLLM
148
- module MCP
149
- module Notifications
150
- class Initialize
151
- def call
152
- @coordinator.request(notification_body, add_id: true, wait_for_response: false)
153
- end
154
- end
155
- end
156
- end
157
- end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: swarm_memory
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.1
4
+ version: 2.1.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Paulo Arruda
@@ -57,28 +57,28 @@ dependencies:
57
57
  requirements:
58
58
  - - "~>"
59
59
  - !ruby/object:Gem::Version
60
- version: '1.8'
60
+ version: '1.9'
61
61
  type: :runtime
62
62
  prerelease: false
63
63
  version_requirements: !ruby/object:Gem::Requirement
64
64
  requirements:
65
65
  - - "~>"
66
66
  - !ruby/object:Gem::Version
67
- version: '1.8'
67
+ version: '1.9'
68
68
  - !ruby/object:Gem::Dependency
69
69
  name: swarm_sdk
70
70
  requirement: !ruby/object:Gem::Requirement
71
71
  requirements:
72
72
  - - "~>"
73
73
  - !ruby/object:Gem::Version
74
- version: '2.1'
74
+ version: '2.2'
75
75
  type: :runtime
76
76
  prerelease: false
77
77
  version_requirements: !ruby/object:Gem::Requirement
78
78
  requirements:
79
79
  - - "~>"
80
80
  - !ruby/object:Gem::Version
81
- version: '2.1'
81
+ version: '2.2'
82
82
  - !ruby/object:Gem::Dependency
83
83
  name: zeitwerk
84
84
  requirement: !ruby/object:Gem::Requirement
@@ -214,11 +214,13 @@ files:
214
214
  - lib/swarm_sdk/agent/context.rb
215
215
  - lib/swarm_sdk/agent/context_manager.rb
216
216
  - lib/swarm_sdk/agent/definition.rb
217
+ - lib/swarm_sdk/agent/llm_instrumentation_middleware.rb
217
218
  - lib/swarm_sdk/claude_code_agent_adapter.rb
218
219
  - lib/swarm_sdk/configuration.rb
219
220
  - lib/swarm_sdk/context_compactor.rb
220
221
  - lib/swarm_sdk/context_compactor/metrics.rb
221
222
  - lib/swarm_sdk/context_compactor/token_counter.rb
223
+ - lib/swarm_sdk/events_to_messages.rb
222
224
  - lib/swarm_sdk/hooks/adapter.rb
223
225
  - lib/swarm_sdk/hooks/context.rb
224
226
  - lib/swarm_sdk/hooks/definition.rb
@@ -247,15 +249,24 @@ files:
247
249
  - lib/swarm_sdk/permissions_builder.rb
248
250
  - lib/swarm_sdk/plugin.rb
249
251
  - lib/swarm_sdk/plugin_registry.rb
252
+ - lib/swarm_sdk/proc_helpers.rb
250
253
  - lib/swarm_sdk/prompts/base_system_prompt.md.erb
251
254
  - lib/swarm_sdk/providers/openai_with_responses.rb
255
+ - lib/swarm_sdk/restore_result.rb
252
256
  - lib/swarm_sdk/result.rb
257
+ - lib/swarm_sdk/snapshot.rb
258
+ - lib/swarm_sdk/snapshot_from_events.rb
259
+ - lib/swarm_sdk/state_restorer.rb
260
+ - lib/swarm_sdk/state_snapshot.rb
253
261
  - lib/swarm_sdk/swarm.rb
254
262
  - lib/swarm_sdk/swarm/agent_initializer.rb
255
263
  - lib/swarm_sdk/swarm/all_agents_builder.rb
256
264
  - lib/swarm_sdk/swarm/builder.rb
257
265
  - lib/swarm_sdk/swarm/mcp_configurator.rb
266
+ - lib/swarm_sdk/swarm/swarm_registry_builder.rb
258
267
  - lib/swarm_sdk/swarm/tool_configurator.rb
268
+ - lib/swarm_sdk/swarm_loader.rb
269
+ - lib/swarm_sdk/swarm_registry.rb
259
270
  - lib/swarm_sdk/tools/bash.rb
260
271
  - lib/swarm_sdk/tools/clock.rb
261
272
  - lib/swarm_sdk/tools/delegate.rb
@@ -286,6 +297,7 @@ files:
286
297
  - lib/swarm_sdk/tools/web_fetch.rb
287
298
  - lib/swarm_sdk/tools/write.rb
288
299
  - lib/swarm_sdk/utils.rb
300
+ - lib/swarm_sdk/validation_result.rb
289
301
  - lib/swarm_sdk/version.rb
290
302
  homepage: https://github.com/parruda/claude-swarm
291
303
  licenses: