Skip to content

Commit

Permalink
Merge 7eabed2 into 6757a3c
Browse files Browse the repository at this point in the history
  • Loading branch information
knu committed Jun 22, 2023
2 parents 6757a3c + 7eabed2 commit 79b86f0
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 3 deletions.
11 changes: 9 additions & 2 deletions app/models/agents/key_value_store_agent.rb
Expand Up @@ -40,6 +40,7 @@ class KeyValueStoreAgent < Agent
- Keys are always stringified as mandated by the JSON format.
- Values are stringified by default. Use the `as_object` filter to store non-string values.
- If the key is evaluated to an empty string, the event is ignored.
- If the value is evaluated to either `null` or empty (`""`, `[]`, `{}`) the key gets deleted.
- In the `value` template, the existing value (if any) can be accessed via the variable `_value_`.
- In the `key` and `value` templates, the whole event payload can be accessed via the variable `_event_`.
Expand Down Expand Up @@ -99,13 +100,19 @@ def receive(incoming_events)
interpolation_context['_event_'] = event.payload

key = interpolate_options(options)['key'].to_s
next if key.empty?

storage = memory
interpolation_context['_value_'] = storage.delete(key)

storage[key] = interpolate_options(options)['value']
value = interpolate_options(options)['value']

storage.shift while storage.size > max_keys
if value.nil? || value.try(:empty?)
storage.delete(key)
else
storage[key] = value
storage.shift while storage.size > max_keys
end

update!(memory: storage)
end
Expand Down
@@ -0,0 +1,8 @@
class DeleteEmptyKeysAndValuesFromKeyValueStoreAgents < ActiveRecord::Migration[6.1]
def up
Agents::KeyValueStoreAgent.find_each do |agent|
agent.memory.delete_if { |key, value| key.empty? || value.nil? || value.try(:empty?) }
agent.save!
end
end
end
43 changes: 42 additions & 1 deletion spec/models/agents/key_value_store_agent_spec.rb
Expand Up @@ -21,7 +21,7 @@
end

def create_event(payload)
source_agent.events.create!(payload: payload)
source_agent.events.create!(payload:)
end

let(:events) do
Expand Down Expand Up @@ -112,6 +112,47 @@ def create_event(payload)
"4" => { id: 4, name: "quux" },
}
)

expect {
agent.receive([create_event({ name: "empty key" })])
}.not_to(change { agent.reload.memory })
end

describe "empty value" do
let(:value_template) { "{{ name | as_object }}" }

it "deletes the key" do
agent.receive(events[0..2])

expect(agent.reload.memory).to match(
{
"1" => "foo",
"2" => "bar",
"3" => "baz",
}
)

agent.receive([create_event({ id: 1, name: "" })])

expect(agent.reload.memory).to match(
{
"2" => "bar",
"3" => "baz",
}
)

agent.receive([create_event({ id: 2, name: [] })])

expect(agent.reload.memory).to match(
{
"3" => "baz",
}
)

agent.receive([create_event({ id: 3, name: {} })])

expect(agent.reload.memory).to eq({})
end
end

describe "using _value_" do
Expand Down

0 comments on commit 79b86f0

Please sign in to comment.