Class: Mxrb::Runtime::Native::Store
- Inherits:
-
Object
- Object
- Mxrb::Runtime::Native::Store
- Defined in:
- lib/mxrb/runtime/native.rb
Overview
Transactional in-memory persistence used by the Ruby model Runtime.
Constant Summary collapse
- LIFECYCLE_EVENTS =
%i[ before_create after_create before_update after_update before_commit after_commit before_delete after_delete ].freeze
Instance Method Summary collapse
- #close ⇒ Object
- #commit(value, events: true) ⇒ Object
- #count(entity, predicate = nil) ⇒ Object
- #create(entity, events: true) ⇒ Object
- #delete(value, events: true) ⇒ Object
- #find(entity, id) ⇒ Object
-
#initialize(defaults: {}, hooks: {}, transient_entities: []) ⇒ Store
constructor
A new instance of Store.
- #on(entity, event, &callback) ⇒ Object
- #restore(snapshot) ⇒ Object
- #retrieve(entity) ⇒ Object
- #retrieve_association(association, start) ⇒ Object
- #rollback(value) ⇒ Object
- #snapshot ⇒ Object
- #transaction ⇒ Object
Constructor Details
#initialize(defaults: {}, hooks: {}, transient_entities: []) ⇒ Store
Returns a new instance of Store.
26 27 28 29 30 31 32 |
# File 'lib/mxrb/runtime/native.rb', line 26 def initialize(defaults: {}, hooks: {}, transient_entities: []) @records = Hash.new { |records, entity| records[entity] = [] } @defaults = defaults @committed = {} @hooks = hooks @transient_entities = Array(transient_entities).map(&:to_s).to_h { [_1, true] }.freeze end |
Instance Method Details
#close ⇒ Object
127 |
# File 'lib/mxrb/runtime/native.rb', line 127 def close; end |
#commit(value, events: true) ⇒ Object
103 104 105 106 107 108 109 110 111 112 113 |
# File 'lib/mxrb/runtime/native.rb', line 103 def commit(value, events: true) Array(value).each do |object| creating = !@committed.key?(record_key(object)) run_hooks(creating ? :before_create : :before_update, object) if events run_hooks(:before_commit, object) if events @committed[record_key(object)] = object.members.dup run_hooks(:after_commit, object) if events run_hooks(creating ? :after_create : :after_update, object) if events end value end |
#count(entity, predicate = nil) ⇒ Object
75 76 77 78 |
# File 'lib/mxrb/runtime/native.rb', line 75 def count(entity, predicate = nil) values = retrieve(entity) predicate ? values.count { predicate.call(_1) } : values.size end |
#create(entity, events: true) ⇒ Object
44 45 46 47 48 49 50 51 |
# File 'lib/mxrb/runtime/native.rb', line 44 def create(entity, events: true) raise ArgumentError, 'events must be boolean' unless [true, false].include?(events) members = @defaults.fetch(entity, {}).dup ObjectValue.new(entity:, id: SecureRandom.uuid, members:).tap do |object| @records[entity] << object end end |
#delete(value, events: true) ⇒ Object
66 67 68 69 70 71 72 73 |
# File 'lib/mxrb/runtime/native.rb', line 66 def delete(value, events: true) Array(value).each do |object| run_hooks(:before_delete, object) if events @records[object.entity].delete(object) @committed.delete(record_key(object)) run_hooks(:after_delete, object) if events end end |
#find(entity, id) ⇒ Object
55 |
# File 'lib/mxrb/runtime/native.rb', line 55 def find(entity, id) = @records[entity].find { _1.id == id.to_s } |
#on(entity, event, &callback) ⇒ Object
34 35 36 37 38 39 40 41 42 |
# File 'lib/mxrb/runtime/native.rb', line 34 def on(entity, event, &callback) raise ArgumentError, "unknown lifecycle event #{event}" unless LIFECYCLE_EVENTS.include?(event.to_sym) raise ArgumentError, 'lifecycle callback is required' unless callback @hooks[entity.to_s] ||= {} @hooks[entity.to_s][event.to_sym] ||= [] @hooks[entity.to_s][event.to_sym] << callback self end |
#restore(snapshot) ⇒ Object
87 88 89 90 91 |
# File 'lib/mxrb/runtime/native.rb', line 87 def restore(snapshot) @records.clear snapshot.fetch(:records).each { |entity, values| @records[entity] = values } @committed = snapshot.fetch(:committed).transform_values(&:dup) end |
#retrieve(entity) ⇒ Object
53 |
# File 'lib/mxrb/runtime/native.rb', line 53 def retrieve(entity) = @records[entity].dup |
#retrieve_association(association, start) ⇒ Object
57 58 59 60 61 62 63 64 |
# File 'lib/mxrb/runtime/native.rb', line 57 def retrieve_association(association, start) member = association.to_s.split('.').last direct = Array(start&.members&.[](association) || start&.members&.[](member)) inverse = @records.values.flatten.select do |object| Array(object.members[association] || object.members[member]).include?(start) end (direct + inverse).uniq end |
#rollback(value) ⇒ Object
115 116 117 118 119 120 121 122 123 124 125 |
# File 'lib/mxrb/runtime/native.rb', line 115 def rollback(value) Array(value).each do |object| persisted = @committed[record_key(object)] if persisted object.members.replace(persisted.dup) else @records[object.entity].delete(object) end end value end |
#snapshot ⇒ Object
80 81 82 83 84 85 |
# File 'lib/mxrb/runtime/native.rb', line 80 def snapshot { records: copy_records(@records), committed: @committed.transform_values(&:dup) } end |
#transaction ⇒ Object
93 94 95 96 97 98 99 100 101 |
# File 'lib/mxrb/runtime/native.rb', line 93 def transaction state = snapshot result = yield discard_uncommitted result rescue StandardError restore(state) raise end |