brute 0.1.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 (37) hide show
  1. checksums.yaml +7 -0
  2. data/lib/brute/agent_stream.rb +49 -0
  3. data/lib/brute/compactor.rb +105 -0
  4. data/lib/brute/doom_loop.rb +84 -0
  5. data/lib/brute/file_mutation_queue.rb +99 -0
  6. data/lib/brute/hooks.rb +84 -0
  7. data/lib/brute/middleware/base.rb +27 -0
  8. data/lib/brute/middleware/compaction_check.rb +56 -0
  9. data/lib/brute/middleware/doom_loop_detection.rb +33 -0
  10. data/lib/brute/middleware/llm_call.rb +28 -0
  11. data/lib/brute/middleware/reasoning_normalizer.rb +98 -0
  12. data/lib/brute/middleware/retry.rb +45 -0
  13. data/lib/brute/middleware/session_persistence.rb +29 -0
  14. data/lib/brute/middleware/token_tracking.rb +46 -0
  15. data/lib/brute/middleware/tool_error_tracking.rb +46 -0
  16. data/lib/brute/middleware/tracing.rb +34 -0
  17. data/lib/brute/orchestrator.rb +297 -0
  18. data/lib/brute/patches/anthropic_tool_role.rb +35 -0
  19. data/lib/brute/patches/buffer_nil_guard.rb +21 -0
  20. data/lib/brute/pipeline.rb +81 -0
  21. data/lib/brute/session.rb +86 -0
  22. data/lib/brute/snapshot_store.rb +49 -0
  23. data/lib/brute/system_prompt.rb +88 -0
  24. data/lib/brute/todo_store.rb +27 -0
  25. data/lib/brute/tools/delegate.rb +35 -0
  26. data/lib/brute/tools/fs_patch.rb +37 -0
  27. data/lib/brute/tools/fs_read.rb +37 -0
  28. data/lib/brute/tools/fs_remove.rb +31 -0
  29. data/lib/brute/tools/fs_search.rb +38 -0
  30. data/lib/brute/tools/fs_undo.rb +29 -0
  31. data/lib/brute/tools/fs_write.rb +26 -0
  32. data/lib/brute/tools/net_fetch.rb +37 -0
  33. data/lib/brute/tools/shell.rb +38 -0
  34. data/lib/brute/tools/todo_read.rb +15 -0
  35. data/lib/brute/tools/todo_write.rb +32 -0
  36. data/lib/brute.rb +121 -0
  37. metadata +101 -0
data/lib/brute.rb ADDED
@@ -0,0 +1,121 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "llm"
4
+ require "timeout"
5
+ require "logger"
6
+
7
+ # Brute — a coding agent built on llm.rb
8
+ #
9
+ # Cross-cutting concerns are implemented as Rack-style middleware in a
10
+ # Pipeline that wraps every LLM call:
11
+ #
12
+ # Tracing → Retry → Session → Tokens → Compaction → ToolErrors → DoomLoop → Reasoning → [LLM Call]
13
+ #
14
+ module Brute
15
+ module Tools; end
16
+ module Hooks; end
17
+ module Middleware; end
18
+ end
19
+
20
+ # Infrastructure
21
+ require_relative "brute/snapshot_store"
22
+ require_relative "brute/todo_store"
23
+ require_relative "brute/file_mutation_queue"
24
+ require_relative "brute/doom_loop"
25
+ require_relative "brute/hooks"
26
+ require_relative "brute/compactor"
27
+ require_relative "brute/system_prompt"
28
+ require_relative "brute/session"
29
+ require_relative "brute/pipeline"
30
+ require_relative "brute/agent_stream"
31
+
32
+ # Provider patches
33
+ require_relative "brute/patches/anthropic_tool_role"
34
+ require_relative "brute/patches/buffer_nil_guard"
35
+
36
+ # Middleware (Rack-style)
37
+ require_relative "brute/middleware/base"
38
+ require_relative "brute/middleware/llm_call"
39
+ require_relative "brute/middleware/retry"
40
+ require_relative "brute/middleware/doom_loop_detection"
41
+ require_relative "brute/middleware/token_tracking"
42
+ require_relative "brute/middleware/compaction_check"
43
+ require_relative "brute/middleware/session_persistence"
44
+ require_relative "brute/middleware/tracing"
45
+ require_relative "brute/middleware/tool_error_tracking"
46
+ require_relative "brute/middleware/reasoning_normalizer"
47
+
48
+ # Tools
49
+ require_relative "brute/tools/fs_read"
50
+ require_relative "brute/tools/fs_write"
51
+ require_relative "brute/tools/fs_patch"
52
+ require_relative "brute/tools/fs_remove"
53
+ require_relative "brute/tools/fs_search"
54
+ require_relative "brute/tools/fs_undo"
55
+ require_relative "brute/tools/shell"
56
+ require_relative "brute/tools/net_fetch"
57
+ require_relative "brute/tools/todo_write"
58
+ require_relative "brute/tools/todo_read"
59
+ require_relative "brute/tools/delegate"
60
+
61
+ # Orchestrator (depends on tools, middleware, and infrastructure)
62
+ require_relative "brute/orchestrator"
63
+
64
+ module Brute
65
+ VERSION = "0.1.0"
66
+
67
+ # The complete set of tools available to the agent.
68
+ TOOLS = [
69
+ Tools::FSRead,
70
+ Tools::FSWrite,
71
+ Tools::FSPatch,
72
+ Tools::FSRemove,
73
+ Tools::FSSearch,
74
+ Tools::FSUndo,
75
+ Tools::Shell,
76
+ Tools::NetFetch,
77
+ Tools::TodoWrite,
78
+ Tools::TodoRead,
79
+ Tools::Delegate,
80
+ ].freeze
81
+
82
+ # Default provider, resolved from environment.
83
+ def self.provider
84
+ @provider ||= resolve_provider
85
+ end
86
+
87
+ def self.provider=(p)
88
+ @provider = p
89
+ end
90
+
91
+ # Create a new orchestrator with sensible defaults.
92
+ def self.agent(cwd: Dir.pwd, tools: TOOLS, session: nil, reasoning: {}, **callbacks)
93
+ Orchestrator.new(
94
+ provider: provider,
95
+ tools: tools,
96
+ cwd: cwd,
97
+ session: session,
98
+ reasoning: reasoning,
99
+ **callbacks
100
+ )
101
+ end
102
+
103
+ def self.resolve_provider
104
+ if ENV["ANTHROPIC_API_KEY"]
105
+ LLM.anthropic(key: ENV["ANTHROPIC_API_KEY"]).tap { Patches::AnthropicToolRole.apply! }
106
+ elsif ENV["OPENAI_API_KEY"]
107
+ LLM.openai(key: ENV["OPENAI_API_KEY"])
108
+ elsif ENV["GOOGLE_API_KEY"]
109
+ LLM.google(key: ENV["GOOGLE_API_KEY"])
110
+ else
111
+ raise <<~MSG
112
+ No API key found. Set one of:
113
+ ANTHROPIC_API_KEY
114
+ OPENAI_API_KEY
115
+ GOOGLE_API_KEY
116
+ MSG
117
+ end
118
+ end
119
+
120
+ private_class_method :resolve_provider
121
+ end
metadata ADDED
@@ -0,0 +1,101 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: brute
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Brute Contributors
8
+ bindir: bin
9
+ cert_chain: []
10
+ date: 1980-01-02 00:00:00.000000000 Z
11
+ dependencies:
12
+ - !ruby/object:Gem::Dependency
13
+ name: llm.rb
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - "~>"
17
+ - !ruby/object:Gem::Version
18
+ version: '4.11'
19
+ type: :runtime
20
+ prerelease: false
21
+ version_requirements: !ruby/object:Gem::Requirement
22
+ requirements:
23
+ - - "~>"
24
+ - !ruby/object:Gem::Version
25
+ version: '4.11'
26
+ - !ruby/object:Gem::Dependency
27
+ name: async
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - "~>"
31
+ - !ruby/object:Gem::Version
32
+ version: '2.0'
33
+ type: :runtime
34
+ prerelease: false
35
+ version_requirements: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - "~>"
38
+ - !ruby/object:Gem::Version
39
+ version: '2.0'
40
+ description: Production-grade coding agent with tool execution, middleware pipeline,
41
+ context compaction, session persistence, and multi-provider LLM support.
42
+ executables: []
43
+ extensions: []
44
+ extra_rdoc_files: []
45
+ files:
46
+ - lib/brute.rb
47
+ - lib/brute/agent_stream.rb
48
+ - lib/brute/compactor.rb
49
+ - lib/brute/doom_loop.rb
50
+ - lib/brute/file_mutation_queue.rb
51
+ - lib/brute/hooks.rb
52
+ - lib/brute/middleware/base.rb
53
+ - lib/brute/middleware/compaction_check.rb
54
+ - lib/brute/middleware/doom_loop_detection.rb
55
+ - lib/brute/middleware/llm_call.rb
56
+ - lib/brute/middleware/reasoning_normalizer.rb
57
+ - lib/brute/middleware/retry.rb
58
+ - lib/brute/middleware/session_persistence.rb
59
+ - lib/brute/middleware/token_tracking.rb
60
+ - lib/brute/middleware/tool_error_tracking.rb
61
+ - lib/brute/middleware/tracing.rb
62
+ - lib/brute/orchestrator.rb
63
+ - lib/brute/patches/anthropic_tool_role.rb
64
+ - lib/brute/patches/buffer_nil_guard.rb
65
+ - lib/brute/pipeline.rb
66
+ - lib/brute/session.rb
67
+ - lib/brute/snapshot_store.rb
68
+ - lib/brute/system_prompt.rb
69
+ - lib/brute/todo_store.rb
70
+ - lib/brute/tools/delegate.rb
71
+ - lib/brute/tools/fs_patch.rb
72
+ - lib/brute/tools/fs_read.rb
73
+ - lib/brute/tools/fs_remove.rb
74
+ - lib/brute/tools/fs_search.rb
75
+ - lib/brute/tools/fs_undo.rb
76
+ - lib/brute/tools/fs_write.rb
77
+ - lib/brute/tools/net_fetch.rb
78
+ - lib/brute/tools/shell.rb
79
+ - lib/brute/tools/todo_read.rb
80
+ - lib/brute/tools/todo_write.rb
81
+ licenses:
82
+ - MIT
83
+ metadata: {}
84
+ rdoc_options: []
85
+ require_paths:
86
+ - lib
87
+ required_ruby_version: !ruby/object:Gem::Requirement
88
+ requirements:
89
+ - - ">="
90
+ - !ruby/object:Gem::Version
91
+ version: '3.2'
92
+ required_rubygems_version: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ requirements: []
98
+ rubygems_version: 3.7.2
99
+ specification_version: 4
100
+ summary: A coding agent built on llm.rb
101
+ test_files: []