Class: ActiveRecord::HyperBase
Constant Summary collapse
- BILLION =
1_000_000_000.0- ROW_KEY_OFFSET =
0- COLUMN_FAMILY_OFFSET =
1- COLUMN_QUALIFIER_OFFSET =
2- VALUE_OFFSET =
3- TIMESTAMP_OFFSET =
4
Class Attribute Summary collapse
-
.mutator ⇒ Object
Returns the value of attribute mutator.
-
.mutator_flags ⇒ Object
Returns the value of attribute mutator_flags.
-
.mutator_flush_interval ⇒ Object
Returns the value of attribute mutator_flush_interval.
-
.qualified_columns ⇒ Object
qualified_column :misc, :qualifiers => [:name, :url].
-
.row_key_attributes(*attrs) ⇒ Object
row_key_attributes :regex => /_(\d4-\d2-\d2_\d2:\d2)$/, :attribute_names => [:timestamp].
Class Method Summary collapse
- .abstract_class? ⇒ Boolean
-
.close_mutator(mutator, flush = 0) ⇒ Object
As of Hypertable 0.9.2.5, flush is automatically performed on a close_mutator call (so flush should default to 0).
- .close_scanner(scanner) ⇒ Object
- .column_families_without_row_key ⇒ Object
-
.columns ⇒ Object
Returns array of column objects for table associated with this class.
-
.convert_cells_to_hashes(cells, options = {}) ⇒ Object
Converts cells that come back from Hypertable into hashes.
- .convert_cells_to_instantiated_rows(cells, options = {}) ⇒ Object
- .delete(*ids) ⇒ Object
- .drop_table ⇒ Object
-
.each_cell(scanner, &block) ⇒ Object
Iterator methods.
- .each_cell_as_arrays(scanner, &block) ⇒ Object
- .each_row(scanner, &block) ⇒ Object
- .each_row_as_arrays(scanner, &block) ⇒ Object
- .exists?(id_or_conditions) ⇒ Boolean
- .find(*args) ⇒ Object
-
.find_by_hql(hql) ⇒ Object
(also: find_by_sql)
Return the records that match a specific HQL query.
-
.find_by_options(options) ⇒ Object
Return an array of records matching the finder options.
-
.find_each_row(*args) ⇒ Object
Returns each row matching the finder options as a HyperRecord object.
-
.find_each_row_as_arrays(*args) ⇒ Object
Returns each row matching the finder options as an array of cells in native array format.
-
.find_from_ids(ids, options) ⇒ Object
Return multiple records by row keys.
-
.find_initial(options) ⇒ Object
Return the first record that matches the finder options.
-
.find_one(id, options) ⇒ Object
Return a single record identified by a row key.
- .find_some(ids, options) ⇒ Object
-
.find_to_scan_spec(*args) ⇒ Object
Converts incoming finder options into a scan spec.
-
.find_with_scanner(*args, &block) ⇒ Object
Returns a scanner object that allows you to iterate over the result set using the lower-level Thrift client APIs methods that require a scanner object.
- .flush_mutator(mutator) ⇒ Object
- .mutator_options(*attrs) ⇒ Object
-
.open_mutator(flags = @mutator_flags.to_i, flush_interval = @mutator_flush_interval.to_i) ⇒ Object
Return an open mutator on this table.
-
.open_scanner(scan_spec) ⇒ Object
Scanner methods.
-
.primary_key ⇒ Object
Returns the primary key field for a table.
- .qualified?(column_name) ⇒ Boolean
- .qualified_column(*attrs) ⇒ Object
- .qualified_column_names_without_row_key ⇒ Object
- .quoted_column_names(attributes = attributes_with_quotes) ⇒ Object
-
.set_default_options(options) ⇒ Object
Each hypertable query requires some default options (e.g., table name) that are set here if not specified in the query.
- .table_exists?(name = table_name) ⇒ Boolean
- .with_scanner(scan_spec, &block) ⇒ Object
- .with_thrift_client(&block) ⇒ Object
Instance Method Summary collapse
-
#attributes_with_quotes(include_primary_key = true, include_readonly_attributes = true) ⇒ Object
Returns a copy of the attributes hash where all the values have been safely quoted for insertion.
- #create(mutator = self.class.mutator) ⇒ Object
- #create_or_update_with_mutator(mutator) ⇒ Object
- #decrement(attribute, by = 1) ⇒ Object
- #decrement!(attribute, by = 1) ⇒ Object
-
#delete_cells(cells, table = self.class.table_name) ⇒ Object
Delete an array of cells from Hypertable cells is an array of cell keys [[“row”, “column”], …].
-
#delete_rows(row_keys, table = self.class.table_name) ⇒ Object
Delete an array of rows from Hypertable rows is an array of row keys [“row1”, “row2”, …].
-
#destroy ⇒ Object
Destroy an object.
-
#increment(attribute, by = 1) ⇒ Object
Casts the attribute to an integer before performing the increment.
- #increment!(attribute, by = 1) ⇒ Object
-
#initialize(attrs = {}) ⇒ HyperBase
constructor
A new instance of HyperBase.
-
#quoted_attributes_to_cells(quoted_attrs, table = self.class.table_name) ⇒ Object
Translates the output of attributes_with_quotes into an array of cells suitable for writing into Hypertable (through the write_cells method).
-
#save_with_mutator(mutator) ⇒ Object
Allows the save operation to be performed with a specific mutator.
- #save_with_mutator!(mutator) ⇒ Object
-
#update(mutator = self.class.mutator) ⇒ Object
Instance Methods.
-
#write_cells(cells, table = self.class.table_name, mutator = self.class.mutator) ⇒ Object
Write an array of cells to Hypertable.
- #write_quoted_attributes(quoted_attrs, table = self.class.table_name, mutator = self.class.mutator) ⇒ Object
Methods inherited from Base
hypertable_connection, inherited, require_hypertable_thrift_client
Constructor Details
#initialize(attrs = {}) ⇒ HyperBase
Returns a new instance of HyperBase.
31 32 33 34 |
# File 'lib/hyper_record.rb', line 31 def initialize(attrs={}) super(attrs) self.ROW = attrs[:ROW] if attrs[:ROW] && attrs[:ROW] end |
Class Attribute Details
.mutator ⇒ Object
Returns the value of attribute mutator.
574 575 576 |
# File 'lib/hyper_record.rb', line 574 def mutator @mutator end |
.mutator_flags ⇒ Object
Returns the value of attribute mutator_flags.
574 575 576 |
# File 'lib/hyper_record.rb', line 574 def mutator_flags @mutator_flags end |
.mutator_flush_interval ⇒ Object
Returns the value of attribute mutator_flush_interval.
574 575 576 |
# File 'lib/hyper_record.rb', line 574 def mutator_flush_interval @mutator_flush_interval end |
.qualified_columns ⇒ Object
qualified_column :misc, :qualifiers => [:name, :url]
524 525 526 |
# File 'lib/hyper_record.rb', line 524 def qualified_columns @qualified_columns end |
.row_key_attributes(*attrs) ⇒ Object
row_key_attributes :regex => /_(\d4-\d2-\d2_\d2:\d2)$/, :attribute_names => [:timestamp]
538 539 540 |
# File 'lib/hyper_record.rb', line 538 def row_key_attributes @row_key_attributes end |
Class Method Details
.abstract_class? ⇒ Boolean
208 209 210 |
# File 'lib/hyper_record.rb', line 208 def abstract_class? self == ActiveRecord::HyperBase end |
.close_mutator(mutator, flush = 0) ⇒ Object
As of Hypertable 0.9.2.5, flush is automatically performed on a close_mutator call (so flush should default to 0).
593 594 595 |
# File 'lib/hyper_record.rb', line 593 def close_mutator(mutator, flush=0) self.connection.close_mutator(mutator, flush) end |
.close_scanner(scanner) ⇒ Object
606 607 608 |
# File 'lib/hyper_record.rb', line 606 def close_scanner(scanner) self.connection.close_scanner(scanner) end |
.column_families_without_row_key ⇒ Object
508 509 510 |
# File 'lib/hyper_record.rb', line 508 def column_families_without_row_key columns[1,columns.length] end |
.columns ⇒ Object
Returns array of column objects for table associated with this class.
481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 |
# File 'lib/hyper_record.rb', line 481 def columns unless @columns @columns = connection.columns(table_name, "#{name} Columns") @qualified_columns ||= [] @qualified_columns.each{|qc| # Remove the column family from the column list @columns = @columns.reject{|c| c.name == qc[:column_name].to_s} connection.remove_column_from_name_map(table_name, qc[:column_name].to_s) # Add the new qualified column family to the column list @columns << connection.add_qualified_column(table_name, qc[:column_name].to_s, qc[:qualifiers]) } @columns.each {|column| column.primary = column.name == primary_key} end @columns end |
.convert_cells_to_hashes(cells, options = {}) ⇒ Object
Converts cells that come back from Hypertable into hashes. Each hash represents a separate record (where each cell that has the same row key is considered one record).
366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 |
# File 'lib/hyper_record.rb', line 366 def convert_cells_to_hashes(cells, ={}) rows = [] current_row = {} # Cells are guaranteed to come back in row key order, so assemble # a row by iterating over each cell and checking to see if the row key # has changed. If it has, then the row is complete and needs to be # instantiated before processing the next cell. cells.each_with_index do |cell, i| current_row['ROW'] = cell[ROW_KEY_OFFSET] family = connection.rubify_column_name(cell[COLUMN_FAMILY_OFFSET]) if !cell[COLUMN_QUALIFIER_OFFSET].blank? current_row[family] ||= {} current_row[family][cell[COLUMN_QUALIFIER_OFFSET]] = cell[VALUE_OFFSET] else current_row[family] = cell[VALUE_OFFSET] end # Instantiate the row if we've processed all cells for the row next_index = i + 1 # Check to see if next cell has different row key or if we're at # the end of the cell stream. if (cells[next_index] and cells[next_index][ROW_KEY_OFFSET] != current_row['ROW']) or next_index >= cells.length # Make sure that the resulting object has attributes for all # columns - even ones that aren't in the response (due to limited # select) for col in column_families_without_row_key next if [:instantiate_only_requested_columns] && ![:select].include?(col.name) if !current_row.has_key?(col.name) if col.is_a?(ActiveRecord::ConnectionAdapters::QualifiedColumn) current_row[col.name] = {} else current_row[col.name] = nil end end end rows << current_row current_row = {} end end rows end |
.convert_cells_to_instantiated_rows(cells, options = {}) ⇒ Object
416 417 418 |
# File 'lib/hyper_record.rb', line 416 def convert_cells_to_instantiated_rows(cells, ={}) convert_cells_to_hashes(cells, ).map{|row| instantiate(row)} end |
.delete(*ids) ⇒ Object
223 224 225 |
# File 'lib/hyper_record.rb', line 223 def delete(*ids) self.connection.delete_rows(table_name, ids.flatten) end |
.drop_table ⇒ Object
469 470 471 |
# File 'lib/hyper_record.rb', line 469 def drop_table connection.drop_table(table_name) if table_exists? end |
.each_cell(scanner, &block) ⇒ Object
Iterator methods
615 616 617 |
# File 'lib/hyper_record.rb', line 615 def each_cell(scanner, &block) self.connection.each_cell(scanner, &block) end |
.each_cell_as_arrays(scanner, &block) ⇒ Object
619 620 621 |
# File 'lib/hyper_record.rb', line 619 def each_cell_as_arrays(scanner, &block) self.connection.each_cell_as_arrays(scanner, &block) end |
.each_row(scanner, &block) ⇒ Object
623 624 625 |
# File 'lib/hyper_record.rb', line 623 def each_row(scanner, &block) self.connection.each_row(scanner, &block) end |
.each_row_as_arrays(scanner, &block) ⇒ Object
627 628 629 |
# File 'lib/hyper_record.rb', line 627 def each_row_as_arrays(scanner, &block) self.connection.each_row_as_arrays(scanner, &block) end |
.exists?(id_or_conditions) ⇒ Boolean
212 213 214 215 216 217 218 219 220 221 |
# File 'lib/hyper_record.rb', line 212 def exists?(id_or_conditions) case id_or_conditions when Fixnum, String !find(:first, :row_keys => [id_or_conditions]).nil? when Hash !find(:first, :conditions => id_or_conditions).nil? else raise "only Fixnum, String and Hash arguments supported" end end |
.find(*args) ⇒ Object
227 228 229 230 231 232 233 234 235 |
# File 'lib/hyper_record.rb', line 227 def find(*args) = args. case args.first when :first then find_initial() when :all then () else find_from_ids(args, ) end end |
.find_by_hql(hql) ⇒ Object Also known as: find_by_sql
Return the records that match a specific HQL query.
421 422 423 424 425 426 427 |
# File 'lib/hyper_record.rb', line 421 def find_by_hql(hql) hql_result = connection.execute(hql) cells_in_native_array_format = hql_result.cells.map do |c| connection.cell_native_array(c.row_key, c.column_family, c.column_qualifier, c.value) end convert_cells_to_instantiated_rows(cells_in_native_array_format) end |
.find_by_options(options) ⇒ Object
Return an array of records matching the finder options.
332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 |
# File 'lib/hyper_record.rb', line 332 def () () # If requested, instead of retrieving the matching cells from # Hypertable, simply return a scan spec that matches the finder # options. if [:scan_spec] return connection.() end cells = connection.() if HyperBase.log_calls msg = [ "Select" ] for key in .keys case key when :columns msg << " columns\t#{[:columns].map{|c| c.name}.join(',')}" else msg << " #{key}\t#{[key]}" end end msg << "Returned #{cell_count} cells" RAILS_DEFAULT_LOGGER.info(msg) # puts msg end convert_cells_to_instantiated_rows(cells, ) end |
.find_each_row(*args) ⇒ Object
Returns each row matching the finder options as a HyperRecord object. Each object is yielded to the caller so that large queries can be processed one object at a time without pulling the entire result set into memory.
Page.find_each_row(:all) do |page|
...
end
272 273 274 275 276 |
# File 'lib/hyper_record.rb', line 272 def find_each_row(*args) find_each_row_as_arrays(*args) do |row| yield convert_cells_to_instantiated_rows(row).first end end |
.find_each_row_as_arrays(*args) ⇒ Object
Returns each row matching the finder options as an array of cells in native array format. Each row is yielded to the caller so that large queries can be processed one row at a time without pulling the entire result set into memory.
Page.find_each_row(:all) do |page_as_array_of_cells|
...
end
286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 |
# File 'lib/hyper_record.rb', line 286 def find_each_row_as_arrays(*args) scan_spec = find_to_scan_spec(*args) with_scanner(scan_spec) do |scanner| row = [] current_row_key = nil each_cell_as_arrays(scanner) do |cell| current_row_key ||= cell[ROW_KEY_OFFSET] if cell[ROW_KEY_OFFSET] == current_row_key row << cell else yield row row = [cell] current_row_key = cell[ROW_KEY_OFFSET] end end yield row unless row.empty? end end |
.find_from_ids(ids, options) ⇒ Object
Return multiple records by row keys.
431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 |
# File 'lib/hyper_record.rb', line 431 def find_from_ids(ids, ) expects_array = ids.first.kind_of?(Array) return ids.first if expects_array && ids.first.empty? ids = ids.flatten.compact.uniq case ids.size when 0 raise RecordNotFound, "Couldn't find #{name} without an ID" when 1 result = find_one(ids.first, ) expects_array ? [ result ] : result else find_some(ids, ) end end |
.find_initial(options) ⇒ Object
Return the first record that matches the finder options.
321 322 323 324 325 326 327 328 329 |
# File 'lib/hyper_record.rb', line 321 def find_initial() .update(:limit => 1) if [:scan_spec] () else ().first end end |
.find_one(id, options) ⇒ Object
Return a single record identified by a row key.
448 449 450 451 452 453 454 455 456 457 458 |
# File 'lib/hyper_record.rb', line 448 def find_one(id, ) return nil if id.blank? [:row_keys] = [id.to_s] if result = find_initial() result else raise ::ActiveRecord::RecordNotFound, "Couldn't find #{name} with ID=#{id}" end end |
.find_some(ids, options) ⇒ Object
460 461 462 463 |
# File 'lib/hyper_record.rb', line 460 def find_some(ids, ) [:row_keys] = [ids.map{|i| i.to_s}] () end |
.find_to_scan_spec(*args) ⇒ Object
Converts incoming finder options into a scan spec. A scan spec is an object used to describe query parameters (columns to retrieve, number of rows to retrieve, row key ranges) for Hypertable queries.
240 241 242 243 244 245 |
# File 'lib/hyper_record.rb', line 240 def find_to_scan_spec(*args) = args. [:scan_spec] = true args << find(*args) end |
.find_with_scanner(*args, &block) ⇒ Object
Returns a scanner object that allows you to iterate over the result set using the lower-level Thrift client APIs methods that require a scanner object. e.g.,
Page.find_with_scanner(:all, :limit => 1) do |scanner|
Page.each_cell_as_arrays(scanner) do |cell|
...
end
end
See the Thrift Client API documentation for more detail. hypertable.org/thrift-api-ref/index.html
259 260 261 262 |
# File 'lib/hyper_record.rb', line 259 def find_with_scanner(*args, &block) scan_spec = find_to_scan_spec(*args) with_scanner(scan_spec, &block) end |
.flush_mutator(mutator) ⇒ Object
597 598 599 |
# File 'lib/hyper_record.rb', line 597 def flush_mutator(mutator) self.connection.flush_mutator(mutator) end |
.mutator_options(*attrs) ⇒ Object
575 576 577 578 579 580 581 582 |
# File 'lib/hyper_record.rb', line 575 def (*attrs) symbolized_attrs = attrs.first.symbolize_keys @mutator_flags = symbolized_attrs[:flags].to_i @mutator_flush_interval = symbolized_attrs[:flush_interval].to_i if symbolized_attrs[:persistent] @mutator = self.open_mutator(@mutator_flags, @mutator_flush_interval) end end |
.open_mutator(flags = @mutator_flags.to_i, flush_interval = @mutator_flush_interval.to_i) ⇒ Object
Return an open mutator on this table.
587 588 589 |
# File 'lib/hyper_record.rb', line 587 def open_mutator(flags=@mutator_flags.to_i, flush_interval=@mutator_flush_interval.to_i) self.connection.open_mutator(table_name, flags, flush_interval) end |
.open_scanner(scan_spec) ⇒ Object
Scanner methods
602 603 604 |
# File 'lib/hyper_record.rb', line 602 def open_scanner(scan_spec) self.connection.open_scanner(self.table_name, scan_spec) end |
.primary_key ⇒ Object
Returns the primary key field for a table. In Hypertable, a single row key exists for each row. The row key is referred to as ROW in HQL, so we’ll refer to it the same way here.
476 477 478 |
# File 'lib/hyper_record.rb', line 476 def primary_key "ROW" end |
.qualified?(column_name) ⇒ Boolean
498 499 500 |
# File 'lib/hyper_record.rb', line 498 def qualified?(column_name) @qualified_columns.map{|c| c[:column_name]}.include?(column_name.to_sym) end |
.qualified_column(*attrs) ⇒ Object
525 526 527 528 529 530 531 532 533 534 535 |
# File 'lib/hyper_record.rb', line 525 def qualified_column(*attrs) @qualified_columns ||= [] name = attrs.shift qualifiers = attrs.shift qualifiers = qualifiers.symbolize_keys[:qualifiers] if qualifiers @qualified_columns << { :column_name => name, :qualifiers => qualifiers || [] } end |
.qualified_column_names_without_row_key ⇒ Object
512 513 514 515 516 517 518 519 520 521 |
# File 'lib/hyper_record.rb', line 512 def qualified_column_names_without_row_key cols = column_families_without_row_key.map{|c| c.name} for qc in @qualified_columns cols.delete(qc[:column_name].to_s) for qualifier in qc[:qualifiers] cols << "#{qc[:column_name]}:#{qualifier}" end end cols end |
.quoted_column_names(attributes = attributes_with_quotes) ⇒ Object
502 503 504 505 506 |
# File 'lib/hyper_record.rb', line 502 def quoted_column_names(attributes=attributes_with_quotes) attributes.keys.collect do |column_name| self.class.connection.quote_column_name_for_table(column_name, table_name) end end |
.set_default_options(options) ⇒ Object
Each hypertable query requires some default options (e.g., table name) that are set here if not specified in the query.
310 311 312 313 314 315 316 317 318 |
# File 'lib/hyper_record.rb', line 310 def () [:table_name] ||= table_name [:columns] ||= columns # Don't request the ROW key explicitly, it always comes back [:select] ||= qualified_column_names_without_row_key.map{|c| connection.hypertable_column_name(c, table_name) } end |
.table_exists?(name = table_name) ⇒ Boolean
465 466 467 |
# File 'lib/hyper_record.rb', line 465 def table_exists?(name=table_name) connection.tables.include?(name) end |
.with_scanner(scan_spec, &block) ⇒ Object
610 611 612 |
# File 'lib/hyper_record.rb', line 610 def with_scanner(scan_spec, &block) self.connection.with_scanner(self.table_name, scan_spec, &block) end |
.with_thrift_client(&block) ⇒ Object
631 632 633 |
# File 'lib/hyper_record.rb', line 631 def with_thrift_client(&block) self.connection.raw_thrift_client(&block) end |
Instance Method Details
#attributes_with_quotes(include_primary_key = true, include_readonly_attributes = true) ⇒ Object
Returns a copy of the attributes hash where all the values have been safely quoted for insertion. Translates qualified columns from a Hash value in Ruby to a flat list of attributes.
>
"ROW" => "page_1",
"name" => "name",
"url" => "http://www.icanhascheezburger.com"
"ROW" => "page_1",
"name" => "name",
"url" => "http://www.icanhascheezburger.com"
135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 |
# File 'lib/hyper_record.rb', line 135 def attributes_with_quotes(include_primary_key = true, include_readonly_attributes = true) quoted = attributes.inject({}) do |quoted, (name, value)| if column = column_for_attribute(name) if column.is_a?(ConnectionAdapters::QualifiedColumn) and value.is_a?(Hash) value.keys.each{|k| quoted[self.class.connection.qualified_column_name(column.name, k)] = quote_value(value[k], column) } else quoted[name] = quote_value(value, column) unless !include_primary_key && column.primary end end quoted end include_readonly_attributes ? quoted : remove_readonly_attributes(quoted) end |
#create(mutator = self.class.mutator) ⇒ Object
43 44 45 46 47 48 |
# File 'lib/hyper_record.rb', line 43 def create(mutator=self.class.mutator) write_quoted_attributes(attributes_with_quotes(false, false), self.class.table_name, mutator) @new_record = false self.attributes[self.class.primary_key] end |
#create_or_update_with_mutator(mutator) ⇒ Object
76 77 78 79 80 |
# File 'lib/hyper_record.rb', line 76 def create_or_update_with_mutator(mutator) raise ReadOnlyRecord if readonly? result = new_record? ? create(mutator) : update(mutator) result != false end |
#decrement(attribute, by = 1) ⇒ Object
118 119 120 |
# File 'lib/hyper_record.rb', line 118 def decrement(attribute, by=1) increment(attribute, -by) end |
#decrement!(attribute, by = 1) ⇒ Object
122 123 124 |
# File 'lib/hyper_record.rb', line 122 def decrement!(attribute, by=1) increment!(attribute, -by) end |
#delete_cells(cells, table = self.class.table_name) ⇒ Object
Delete an array of cells from Hypertable cells is an array of cell keys [[“row”, “column”], …]
187 188 189 190 191 192 193 194 195 196 197 198 |
# File 'lib/hyper_record.rb', line 187 def delete_cells(cells, table=self.class.table_name) if HyperBase.log_calls msg = [ "Deleting #{cells.length} cells from #{table} table", cells.map{|c| [ c[0], c[1] ].compact.join("\t")} ].join("\n") RAILS_DEFAULT_LOGGER.info(msg) # puts msg end connection.delete_cells(table, cells) end |
#delete_rows(row_keys, table = self.class.table_name) ⇒ Object
Delete an array of rows from Hypertable rows is an array of row keys [“row1”, “row2”, …]
202 203 204 |
# File 'lib/hyper_record.rb', line 202 def delete_rows(row_keys, table=self.class.table_name) connection.delete_rows(table, cells) end |
#destroy ⇒ Object
Destroy an object. Since Hypertable does not have foreign keys, association cells must be removed manually.
84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 |
# File 'lib/hyper_record.rb', line 84 def destroy # check for associations and delete association cells as necessary for reflection_key in self.class.reflections.keys case self.class.reflections[reflection_key].macro when :has_and_belongs_to_many # remove all the association cells from the associated objects cells_to_delete = [] for row_key in self.send(self.class.reflections[reflection_key].association_foreign_key).keys cells_to_delete << connection.cell_native_array(row_key, self.class.reflections[reflection_key].primary_key_name, self.ROW) end self.delete_cells(cells_to_delete, self.class.reflections[reflection_key].klass.table_name) end end self.class.connection.delete_rows(self.class.table_name, [self.ROW]) end |
#increment(attribute, by = 1) ⇒ Object
Casts the attribute to an integer before performing the increment. This is necessary because Hypertable only supports integer types at the moment. The cast has the effect of initializing nil values (and most string values) to zero.
107 108 109 110 111 |
# File 'lib/hyper_record.rb', line 107 def increment(attribute, by=1) self[attribute] = self[attribute].to_i self[attribute] += by self end |
#increment!(attribute, by = 1) ⇒ Object
113 114 115 116 |
# File 'lib/hyper_record.rb', line 113 def increment!(attribute, by=1) increment(attribute, by) self.save end |
#quoted_attributes_to_cells(quoted_attrs, table = self.class.table_name) ⇒ Object
Translates the output of attributes_with_quotes into an array of cells suitable for writing into Hypertable (through the write_cells method). Data format is native array format for cells. [
["row_key", "column_family", "column_qualifier", "value"],
]
157 158 159 160 161 162 163 164 165 |
# File 'lib/hyper_record.rb', line 157 def quoted_attributes_to_cells(quoted_attrs, table=self.class.table_name) cells = [] pk = self.attributes[self.class.primary_key] quoted_attrs.keys.each{|key| name, qualifier = connection.hypertable_column_name(key, table).split(':', 2) cells << connection.cell_native_array(pk, name, qualifier, quoted_attrs[key]) } cells end |
#save_with_mutator(mutator) ⇒ Object
Allows the save operation to be performed with a specific mutator. By default, a new mutator is opened, flushed and closed for each save operation. Write-heavy application may wish to manually manage mutator flushes (which happens when the mutator is closed) at the application-layer in order to increase write throughput.
m = Page.open_mutator
p1 = Page.new({:ROW => 'created_with_mutator_1', :url => 'url_1'})
p1.save_with_mutator!(m)
p2 = Page.new({:ROW => 'created_with_mutator_2', :url => 'url_2'})
p2.save_with_mutator!(m)
Page.close_mutator(m)
Future versions of hypertable will provide a mutator that automatically periodically flushes. This feature is expected by Summary 2009. At that time, manually managing the mutator at the
68 69 70 |
# File 'lib/hyper_record.rb', line 68 def save_with_mutator(mutator) create_or_update_with_mutator(mutator) end |
#save_with_mutator!(mutator) ⇒ Object
72 73 74 |
# File 'lib/hyper_record.rb', line 72 def save_with_mutator!(mutator) create_or_update_with_mutator(mutator) || raise(RecordNotSaved) end |
#update(mutator = self.class.mutator) ⇒ Object
Instance Methods
37 38 39 40 41 |
# File 'lib/hyper_record.rb', line 37 def update(mutator=self.class.mutator) write_quoted_attributes(attributes_with_quotes(false, false), self.class.table_name, mutator) true end |
#write_cells(cells, table = self.class.table_name, mutator = self.class.mutator) ⇒ Object
Write an array of cells to Hypertable
172 173 174 175 176 177 178 179 180 181 182 183 |
# File 'lib/hyper_record.rb', line 172 def write_cells(cells, table=self.class.table_name, mutator=self.class.mutator) if HyperBase.log_calls msg = [ "Writing #{cells.length} cells to #{table} table", cells.map{|c| [c[0], c[1], c[2], c[3].to_s.first(20)].compact.join("\t")} ].join("\n") RAILS_DEFAULT_LOGGER.info(msg) # puts msg end connection.write_cells(table, cells, mutator, self.class.mutator_flags, self.class.mutator_flush_interval) end |
#write_quoted_attributes(quoted_attrs, table = self.class.table_name, mutator = self.class.mutator) ⇒ Object
167 168 169 |
# File 'lib/hyper_record.rb', line 167 def write_quoted_attributes(quoted_attrs, table=self.class.table_name, mutator=self.class.mutator) write_cells(quoted_attributes_to_cells(quoted_attrs, table), table, mutator) end |