Class: Insika::ToolStore
- Inherits:
-
Object
- Object
- Insika::ToolStore
- Defined in:
- lib/insika/tool_store.rb
Overview
DATA-DEFINED tools authored at runtime. One record per tool in the ConfigStore
(scope "tools"), keyed by name. It stores the whole ToolDefinition, versions it
(like SkillStore/AgentFileStore) and MASKS the credential headers (just as
McpStore masks the env): headers whose name is in secret_headers never
leave in plaintext to the UI — they become the sentinel __OCULTO__. Only get_raw/
all_raw (consumed by DataDefinedTool/overlay, never the screen) return the
real values. Phase 5, Step A.
Record in the ConfigStore:
{ "definition" => { ...ToolDefinition#to_h... },
"updated_at" => iso8601,
"history" => [ { "definition" =>, "at" => }, ... ] }
Constant Summary collapse
- SCOPE =
"tools"- HISTORY_MAX =
20
Instance Method Summary collapse
-
#all ⇒ Object
-> [Hash] MASKED definitions (for the UI).
-
#all_raw ⇒ Object
-> [Hash] definitions with REAL headers (for the overlay/registry).
-
#delete(name) ⇒ Object
-> bool (did it exist?).
-
#get(name) ⇒ Object
-> MASKED ToolDefinition Hash (secret headers with sentinel) | nil.
-
#get_raw(name) ⇒ Object
-> ToolDefinition Hash with REAL headers | nil.
-
#initialize(config_store:) ⇒ ToolStore
constructor
A new instance of ToolStore.
-
#names ⇒ Object
-> [String] names, lexicographic order.
-
#restore(name, index) ⇒ Object
Restores version
indexas the current definition (new write, versions the current). -
#versions(name) ⇒ Object
-> [ { "definition" => MASKED, "at" => } ] most recent first.
-
#write(attrs, create_only: false) ⇒ Object
Writes (upsert).
Constructor Details
#initialize(config_store:) ⇒ ToolStore
Returns a new instance of ToolStore.
22 23 24 |
# File 'lib/insika/tool_store.rb', line 22 def initialize(config_store:) @cs = config_store end |
Instance Method Details
#all ⇒ Object
-> [Hash] MASKED definitions (for the UI).
39 40 41 |
# File 'lib/insika/tool_store.rb', line 39 def all names.filter_map { |n| get(n) } end |
#all_raw ⇒ Object
-> [Hash] definitions with REAL headers (for the overlay/registry). Never to the screen.
44 45 46 |
# File 'lib/insika/tool_store.rb', line 44 def all_raw names.filter_map { |n| raw_definition(n) } end |
#delete(name) ⇒ Object
-> bool (did it exist?).
69 |
# File 'lib/insika/tool_store.rb', line 69 def delete(name) = @cs.delete(SCOPE, name.to_s) |
#get(name) ⇒ Object
-> MASKED ToolDefinition Hash (secret headers with sentinel) | nil.
27 28 29 30 |
# File 'lib/insika/tool_store.rb', line 27 def get(name) d = raw_definition(name) d && mask_definition(d) end |
#get_raw(name) ⇒ Object
-> ToolDefinition Hash with REAL headers | nil. Internal use (tool/overlay).
33 |
# File 'lib/insika/tool_store.rb', line 33 def get_raw(name) = raw_definition(name) |
#names ⇒ Object
-> [String] names, lexicographic order.
36 |
# File 'lib/insika/tool_store.rb', line 36 def names = @cs.keys(SCOPE) |
#restore(name, index) ⇒ Object
Restores version index as the current definition (new write, versions the current).
-> MASKED definition Hash.
80 81 82 83 84 85 86 87 88 89 90 91 |
# File 'lib/insika/tool_store.rb', line 80 def restore(name, index) rec = record(name) raise Insika::NotFoundError, "tool '#{name}' not found" unless rec hist = rec.fetch("history", []) i = Integer(index) raise Insika::ValidationError, "version #{index} does not exist" if i.negative? || i >= hist.length # The historical version stores REAL headers -> rewrite directly (bypasses the # input masking; write only re-validates the structure). write(hist[i]["definition"]) end |
#versions(name) ⇒ Object
-> [ { "definition" => MASKED, "at" => } ] most recent first.
72 73 74 75 76 |
# File 'lib/insika/tool_store.rb', line 72 def versions(name) (record(name)&.fetch("history", []) || []).map do |h| { "definition" => mask_definition(h["definition"]), "at" => h["at"] } end end |
#write(attrs, create_only: false) ⇒ Object
Writes (upsert). attrs is a ToolDefinition Hash (the UI may send secret
headers as sentinel: preserves what was stored). create_only refuses to overwrite.
Validates via ToolDefinition.from_h. -> MASKED definition Hash.
51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 |
# File 'lib/insika/tool_store.rb', line 51 def write(attrs, create_only: false) definition = Insika::ToolDefinition.from_h(attrs) # validates (raises ValidationError) name = definition.name existing = @cs.get(SCOPE, name) raise Insika::ValidationError, "tool '#{name}' already exists" if create_only && existing final = definition.to_h final["request"]["headers"] = reconcile_secret_headers( final["request"]["headers"], definition.secret_headers, existing&.dig("definition", "request", "headers") ) rec = build_record(final, existing) @cs.put(SCOPE, name, rec) mask_definition(final) end |