pwn 0.5.749 → 0.5.751
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/Gemfile +2 -2
- data/documentation/Blockchain.md +107 -9
- data/documentation/pwn-ai-Agent.md +310 -4
- data/documentation/pwn_silent_help_learn_demo.gif +0 -0
- data/etc/default_skills/pwn/banner/SKILL.md +7 -3
- data/etc/default_skills/pwn/blockchain/btc/SKILL.md +8 -5
- data/etc/default_skills/pwn/blockchain/eth/SKILL.md +12 -3
- data/etc/default_skills/pwn/blockchain/eth/references/urls.md +1 -1
- data/etc/default_skills/pwn/plugins/repl/SKILL.md +5 -0
- data/etc/default_skills/pwn/plugins/repl/ai/SKILL.md +4 -0
- data/etc/default_skills/pwn/plugins/repl/ai/references/urls.md +5 -0
- data/etc/default_skills/pwn/plugins/repl/ai_console/SKILL.md +48 -0
- data/etc/default_skills/pwn/plugins/repl/ai_console_commands/SKILL.md +47 -0
- data/etc/default_skills/pwn/plugins/repl/ai_console_usage/SKILL.md +48 -0
- data/etc/default_skills/pwn/plugins/repl/ai_swarm/SKILL.md +46 -0
- data/lib/pwn/ai/agent/loop.rb +287 -18
- data/lib/pwn/ai/agent/swarm.rb +28 -4
- data/lib/pwn/ai/open_ai.rb +4 -2
- data/lib/pwn/banner.rb +743 -2
- data/lib/pwn/blockchain/btc.rb +494 -196
- data/lib/pwn/blockchain/eth.rb +440 -81
- data/lib/pwn/blockchain.rb +6 -0
- data/lib/pwn/config.rb +22 -0
- data/lib/pwn/migrate.rb +9 -1
- data/lib/pwn/plugins/repl/ai.rb +182 -17
- data/lib/pwn/plugins/repl/ai_console.rb +1581 -0
- data/lib/pwn/plugins/repl/ai_console_commands.rb +282 -0
- data/lib/pwn/plugins/repl/ai_console_usage.rb +144 -0
- data/lib/pwn/plugins/repl/ai_swarm.rb +375 -0
- data/lib/pwn/plugins/repl.rb +25 -3
- data/lib/pwn/version.rb +1 -1
- data/spec/lib/pwn/ai/agent/loop_spec.rb +258 -1
- data/spec/lib/pwn/ai/agent/turn_finalizer_spec.rb +3 -2
- data/spec/lib/pwn/ai/open_ai_spec.rb +5 -0
- data/spec/lib/pwn/banner_spec.rb +643 -0
- data/spec/lib/pwn/blockchain/btc_spec.rb +372 -1
- data/spec/lib/pwn/blockchain/eth_spec.rb +205 -0
- data/spec/lib/pwn/blockchain_spec.rb +6 -0
- data/spec/lib/pwn/config_spec.rb +10 -0
- data/spec/lib/pwn/migrate_spec.rb +40 -3
- data/spec/lib/pwn/plugins/repl/ai_console_commands_spec.rb +65 -0
- data/spec/lib/pwn/plugins/repl/ai_console_spec.rb +1434 -0
- data/spec/lib/pwn/plugins/repl/ai_console_usage_spec.rb +29 -0
- data/spec/lib/pwn/plugins/repl/ai_swarm_spec.rb +127 -0
- data/spec/lib/pwn/plugins/repl_pwn_vault_spec.rb +5 -3
- data/spec/lib/pwn/plugins/repl_spec.rb +167 -1
- data/third_party/pwn_rdoc.jsonl +229 -10
- metadata +18 -6
- data/etc/default_skills/pwn/blockchain/btc/references/urls.md +0 -3
data/lib/pwn/ai/agent/swarm.rb
CHANGED
|
@@ -111,14 +111,27 @@ module PWN
|
|
|
111
111
|
end
|
|
112
112
|
|
|
113
113
|
# Supported Method Parameters::
|
|
114
|
-
# PWN::AI::Agent::Swarm.retire(
|
|
114
|
+
# PWN::AI::Agent::Swarm.retire(
|
|
115
|
+
# name: 'required - persona name',
|
|
116
|
+
# swarm_id: 'optional - swarm directory when local is true',
|
|
117
|
+
# local: 'optional - true retires only that swarm registry'
|
|
118
|
+
# )
|
|
115
119
|
|
|
116
120
|
public_class_method def self.retire(opts = {})
|
|
117
121
|
name = opts[:name].to_s
|
|
122
|
+
sid = opts[:swarm_id].to_s
|
|
123
|
+
if opts[:local] == true && !sid.empty?
|
|
124
|
+
path = File.join(SWARM_ROOT, sid, 'agents.yml')
|
|
125
|
+
all = load_personas_file(path: path)
|
|
126
|
+
gone = all.delete(name.to_sym)
|
|
127
|
+
File.write(path, YAML.dump(deep_stringify(hash: all))) if gone
|
|
128
|
+
return { name: name, removed: !gone.nil?, scope: :swarm }
|
|
129
|
+
end
|
|
130
|
+
|
|
118
131
|
all = personas
|
|
119
132
|
gone = all.delete(name.to_sym)
|
|
120
133
|
File.write(AGENTS_FILE, YAML.dump(deep_stringify(hash: all))) if gone
|
|
121
|
-
{ name: name, removed: !gone.nil
|
|
134
|
+
{ name: name, removed: !gone.nil?, scope: :global }
|
|
122
135
|
end
|
|
123
136
|
|
|
124
137
|
# ------------------------------------------------------------------
|
|
@@ -212,7 +225,9 @@ module PWN
|
|
|
212
225
|
# request: 'required - what to ask/instruct the persona',
|
|
213
226
|
# swarm_id: 'optional - join an existing swarm (created if omitted)',
|
|
214
227
|
# to: 'optional - addressee recorded on the bus (default :all)',
|
|
215
|
-
# on_tool: 'optional - ->(name, args, result) live-UI callback'
|
|
228
|
+
# on_tool: 'optional - ->(name, args, result) live-UI callback',
|
|
229
|
+
# steering: 'optional - Loop::Steering for this persona turn',
|
|
230
|
+
# usage_observer: 'optional - callable receiving provider usage'
|
|
216
231
|
# )
|
|
217
232
|
|
|
218
233
|
public_class_method def self.ask(opts = {})
|
|
@@ -246,6 +261,8 @@ module PWN
|
|
|
246
261
|
Thread.current[:pwn_swarm_depth] = depth + 1
|
|
247
262
|
Thread.current[:pwn_swarm_id] = sid
|
|
248
263
|
reply = with_persona_env(persona: persona) do
|
|
264
|
+
prior_observer = Thread.current[:pwn_usage_observer]
|
|
265
|
+
Thread.current[:pwn_usage_observer] = opts[:usage_observer] if opts[:usage_observer]
|
|
249
266
|
Loop.run(
|
|
250
267
|
request: opts[:request].to_s,
|
|
251
268
|
session_id: session_id,
|
|
@@ -253,8 +270,11 @@ module PWN
|
|
|
253
270
|
core_only: empty_tools ? false : true,
|
|
254
271
|
system_role_content: sys,
|
|
255
272
|
on_tool: opts[:on_tool],
|
|
273
|
+
steering: opts[:steering],
|
|
256
274
|
nested: true
|
|
257
275
|
)
|
|
276
|
+
ensure
|
|
277
|
+
Thread.current[:pwn_usage_observer] = prior_observer
|
|
258
278
|
end
|
|
259
279
|
|
|
260
280
|
bus_append(swarm_id: sid, from: name, to: opts[:to] || :all, content: reply)
|
|
@@ -698,7 +718,9 @@ module PWN
|
|
|
698
718
|
|
|
699
719
|
# Run retire and return its result
|
|
700
720
|
#{self}.retire(
|
|
701
|
-
name: '
|
|
721
|
+
name: 'required - persona name',
|
|
722
|
+
swarm_id: 'optional - swarm directory when local is true',
|
|
723
|
+
local: 'optional - true retires only that swarm registry'
|
|
702
724
|
)
|
|
703
725
|
|
|
704
726
|
# Swarm lifecycle & bus
|
|
@@ -730,6 +752,8 @@ module PWN
|
|
|
730
752
|
swarm_id: 'optional - join an existing swarm (created if omitted)',
|
|
731
753
|
to: 'optional - addressee recorded on the bus (default :all)',
|
|
732
754
|
on_tool: 'optional - ->(name, args, result) live-UI callback',
|
|
755
|
+
steering: 'optional - Loop::Steering for this persona turn',
|
|
756
|
+
usage_observer: 'optional - callable receiving provider usage',
|
|
733
757
|
from: 'optional - sender account or address to bind as operator (defaults to caller_label)',
|
|
734
758
|
text_only: 'required - text only value consumed by #ask',
|
|
735
759
|
unit: 'optional - claim key (host+phase) before the child runs',
|
data/lib/pwn/ai/open_ai.rb
CHANGED
|
@@ -676,6 +676,8 @@ module PWN
|
|
|
676
676
|
http_body[:tool_choice] = opts[:tool_choice] if opts[:tool_choice]
|
|
677
677
|
|
|
678
678
|
endpoint = api_endpoint(model: model, tools: opts[:tools])
|
|
679
|
+
effort = opts[:reasoning_effort] || engine[:reasoning_effort]
|
|
680
|
+
http_body[:reasoning_effort] = effort if reasoning && !effort.to_s.empty?
|
|
679
681
|
if endpoint == 'responses'
|
|
680
682
|
http_body = responses_http_body(
|
|
681
683
|
model: model,
|
|
@@ -683,7 +685,7 @@ module PWN
|
|
|
683
685
|
tools: opts[:tools],
|
|
684
686
|
tool_choice: opts[:tool_choice],
|
|
685
687
|
max_tokens: max_tokens,
|
|
686
|
-
reasoning_effort:
|
|
688
|
+
reasoning_effort: effort
|
|
687
689
|
)
|
|
688
690
|
end
|
|
689
691
|
|
|
@@ -791,7 +793,7 @@ module PWN
|
|
|
791
793
|
body[:tool_choice] = tc
|
|
792
794
|
end
|
|
793
795
|
effort = opts[:reasoning_effort].to_s
|
|
794
|
-
body[:reasoning] = { effort: effort, summary: 'auto' }
|
|
796
|
+
body[:reasoning] = { effort: effort, summary: 'auto' } unless effort.empty? || (effort == 'none' && model.to_s.start_with?('gpt-6-astra'))
|
|
795
797
|
body
|
|
796
798
|
end
|
|
797
799
|
|