Class: OMF::OML::OmlTable
- Inherits:
-
Base::LObject
- Object
- Base::LObject
- OMF::OML::OmlTable
- Includes:
- MonitorMixin
- Defined in:
- lib/omf_oml/table.rb
Overview
This class represents a database like table holding a sequence of OML measurements (rows) according a common schema.
Direct Known Subclasses
Instance Attribute Summary collapse
-
#max_size ⇒ Object
Returns the value of attribute max_size.
-
#name ⇒ Object
readonly
Returns the value of attribute name.
-
#offset ⇒ Object
readonly
Returns the value of attribute offset.
-
#schema ⇒ Object
readonly
Returns the value of attribute schema.
Class Method Summary collapse
Instance Method Summary collapse
- #<<(row) ⇒ Object
-
#add_row(row, needs_casting = false) ⇒ Object
NOTE:
on_row_added
callbacks are done within the monitor. -
#add_rows(rows, needs_casting = false) ⇒ Object
Add an array of rows to this table.
-
#clear ⇒ Object
Remove all rows from table.
-
#create_sliced_table(col_name, col_value, table_opts = {}) ⇒ Object
Return a new table which only contains the rows of this table whose value in column ‘col_name’ is equal to ‘col_value’.
- #data_sources ⇒ Object
- #describe ⇒ Object
-
#indexed_by(col_name) ⇒ Object
Return a new table which shadows this table but only contains rows with unique values in the column ‘col_name’ and of these the latest added rows to this table.
-
#initialize(tname, schema, opts = {}, &on_before_row_added) ⇒ OmlTable
constructor
tname - Name of table schema - OmlSchema or Array containing [name, type*] for every column in table Table adds a ‘__id__’ column at the beginning which keeps track of the rows unique id unless option ‘supress_index’ is set.
-
#on_before_row_added(&callback) ⇒ Object
Register
callback
to be called to process any newly offered row before it being added to internal storage. -
#on_content_changed(key = nil, offset = -1,, &proc) ⇒ Object
Register callback for when the content of the table is changes.
- #on_row_added(key, &block) ⇒ Object
- #rows ⇒ Object
-
#to_a ⇒ Object
Return table as an array of rows.
Constructor Details
#initialize(tname, schema, opts = {}, &on_before_row_added) ⇒ OmlTable
tname - Name of table schema - OmlSchema or Array containing [name, type*] for every column in table
Table adds a '__id__' column at the beginning which keeps track of the rows unique id unless
option 'supress_index' is set.
opts -
:max_size - keep table to that size by dropping older rows
:supress_index - don't pex, even if schema doesn't start with '__id__'
49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 |
# File 'lib/omf_oml/table.rb', line 49 def initialize(tname, schema, opts = {}, &on_before_row_added) super tname #@endpoint = endpoint @name = tname @schema = OmlSchema.create(schema) @add_index = false unless opts[:supress_index] unless @schema.name_at(0) == :__id__ @add_index = true @schema.insert_column_at(0, [:__id__, 'int']) end end @col_count = @schema.columns.length @opts = opts if (index = opts[:index]) throw "No longer supported, use IndexedTable instead" # @indexed_rows = {} # @index_col = @schema.index_for_col(index) end @on_before_row_added = on_before_row_added @offset = 0 # number of rows skipped before the first one recorded here @rows = [] @row_id = 0 # Each new row is assigned an id @max_size = opts[:max_size] @on_content_changed = {} end |
Instance Attribute Details
#max_size ⇒ Object
Returns the value of attribute max_size.
36 37 38 |
# File 'lib/omf_oml/table.rb', line 36 def max_size @max_size end |
#name ⇒ Object (readonly)
Returns the value of attribute name.
35 36 37 |
# File 'lib/omf_oml/table.rb', line 35 def name @name end |
#offset ⇒ Object (readonly)
Returns the value of attribute offset.
38 39 40 |
# File 'lib/omf_oml/table.rb', line 38 def offset @offset end |
#schema ⇒ Object (readonly)
Returns the value of attribute schema.
37 38 39 |
# File 'lib/omf_oml/table.rb', line 37 def schema @schema end |
Class Method Details
.create(tname, schema, opts = {}, &on_before_row_added) ⇒ Object
25 26 27 28 29 30 31 32 |
# File 'lib/omf_oml/table.rb', line 25 def self.create(tname, schema, opts = {}, &on_before_row_added) if (index = opts.delete(:index)) require 'omf_oml/indexed_table' OmlIndexedTable.new(tname, index, schema, &on_before_row_added) else OmlTable.new(tname, schema, opts, &on_before_row_added) end end |
Instance Method Details
#<<(row) ⇒ Object
149 150 151 |
# File 'lib/omf_oml/table.rb', line 149 def <<(row) add_row(row) end |
#add_row(row, needs_casting = false) ⇒ Object
NOTE: on_row_added
callbacks are done within the monitor.
126 127 128 129 130 131 132 |
# File 'lib/omf_oml/table.rb', line 126 def add_row(row, needs_casting = false) synchronize do if row = _add_row(row, needs_casting) _notify_content_changed(:added, [row]) end end end |
#add_rows(rows, needs_casting = false) ⇒ Object
Add an array of rows to this table
166 167 168 169 170 171 172 173 174 |
# File 'lib/omf_oml/table.rb', line 166 def add_rows(rows, needs_casting = false) synchronize do added = rows.map { |row| _add_row(row, needs_casting) } added = added.compact unless added.empty? _notify_content_changed(:added, added) end end end |
#clear ⇒ Object
Remove all rows from table.
NOTE: on_row_removed
callbacks are done within the monitor.
138 139 140 141 142 143 144 145 146 |
# File 'lib/omf_oml/table.rb', line 138 def clear() synchronize do return if @rows.empty? old = @rows @rows = [] #@row_id = 0 # Should we rest that as well?? _notify_content_changed(:removed, old) end end |
#create_sliced_table(col_name, col_value, table_opts = {}) ⇒ Object
Return a new table which only contains the rows of this table whose value in column ‘col_name’ is equal to ‘col_value’
179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 |
# File 'lib/omf_oml/table.rb', line 179 def create_sliced_table(col_name, col_value, table_opts = {}) sname = "#{@name}_slice_#{Kernel.rand}" st = self.class.new(name, @schema, @opts.merge(table_opts)) st.instance_variable_set(:@sname, sname) st.instance_variable_set(:@master_ds, self) st.instance_variable_set(:@add_index, true) def st.release @master_ds.on_content_changed(@sname) # release callback end index = @schema.index_for_col(col_name) on_content_changed(sname, 0) do |action, rows| if action == :removed warn "No support for removing rows from sliced table '#{sname}'." next end first_row = true rows.each do |row| if row[index] == col_value row = row[1 .. -1] # remove the row_id debug "Add first row '#{row.inspect}'" if first_row st.add_row(row) first_row = false end end end debug "Created sliced table from '#{@name}' (rows: #{st.rows.length}-#{@rows.length})" st end |
#data_sources ⇒ Object
220 221 222 |
# File 'lib/omf_oml/table.rb', line 220 def data_sources self end |
#describe ⇒ Object
216 217 218 |
# File 'lib/omf_oml/table.rb', line 216 def describe() rows end |
#indexed_by(col_name) ⇒ Object
Return a new table which shadows this table but only contains rows with unique values in the column ‘col_name’ and of these the latest added rows to this table.
col_name - Name of column to use for indexing
159 160 161 162 |
# File 'lib/omf_oml/table.rb', line 159 def indexed_by(col_name) require 'omf_oml/indexed_table' OmlIndexedTable.shadow(self, col_name) end |
#on_before_row_added(&callback) ⇒ Object
Register callback
to be called to process any newly offered row before it being added to internal storage. The callback’s argument is the new row (TODO: in what form) and should return what is being added instead of the original row. If the callback
returns nil, nothing is being added.
87 88 89 |
# File 'lib/omf_oml/table.rb', line 87 def on_before_row_added(&callback) @on_before_row_added = callback end |
#on_content_changed(key = nil, offset = -1,, &proc) ⇒ Object
Register callback for when the content of the table is changes. The key allows for the callback to be removed by calling this method without a block. . If the optional ‘offset’ value is set to zero or a positive value, then the currently stored values starting at this index are being immediately sent to ‘proc’. The ‘proc’ is expected to receive two parameters, an ‘action’ and the content changed. The ‘action’ is either ‘:added’, or ‘:removed’ and the content is an array of rows.
100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 |
# File 'lib/omf_oml/table.rb', line 100 def on_content_changed(key = nil, offset = -1, &proc) #puts ">>>>>>> #{offset}" if proc @on_content_changed[key || proc] = proc if offset >= 0 #with_offset = proc.arity == 2 proc.call(:added, @rows[offset .. -1]) #.each_with_index do |r, i| # with_offset ? proc.call(r, offset + i) : proc.call(r) # end end else @on_content_changed.delete key end end |
#on_row_added(key, &block) ⇒ Object
116 117 118 119 120 121 122 |
# File 'lib/omf_oml/table.rb', line 116 def on_row_added(key, &block) on_content_changed(key) do |action, rows| if action == :added rows.each {|r| block.call(r)} end end end |
#rows ⇒ Object
76 77 78 79 |
# File 'lib/omf_oml/table.rb', line 76 def rows #@indexed_rows ? @indexed_rows.values : @rows @rows end |
#to_a ⇒ Object
Return table as an array of rows
212 213 214 |
# File 'lib/omf_oml/table.rb', line 212 def to_a @rows.dup end |