Class: ActiveRecord::Materialized::TableSwap Private
- Inherits:
-
Object
- Object
- ActiveRecord::Materialized::TableSwap
- Defined in:
- lib/activerecord/materialized/table_swap.rb
Overview
This class is part of a private API. You should avoid using this class if possible, as it may be removed or be changed in the future.
Swaps a view's cache table for a freshly-built temp table, atomically per the engine's DDL semantics: a transaction on SQLite/Postgres (transactional DDL), or a single multi-table RENAME TABLE on MySQL — whose DDL auto-commits, so a transaction could not make two separate renames atomic. Extracted from RelationCacheWriter, which builds the temp table and delegates the swap here.
Instance Method Summary collapse
-
#initialize(view_class) ⇒ TableSwap
constructor
private
A new instance of TableSwap.
-
#swap!(temp_table, old_table) ⇒ Object
private
Replace the view table with temp_table; the displaced view table becomes old_table and is dropped.
Constructor Details
#initialize(view_class) ⇒ TableSwap
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Returns a new instance of TableSwap.
13 14 15 |
# File 'lib/activerecord/materialized/table_swap.rb', line 13 def initialize(view_class) @view_class = view_class end |
Instance Method Details
#swap!(temp_table, old_table) ⇒ Object
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Replace the view table with temp_table; the displaced view table becomes old_table and is dropped. Indexes on the displaced table are preserved: the freshly built temp table only carries the schema-default index, so any index a user added to the cache table (or the default one, on a table built before it existed) would otherwise be lost with the dropped old table — unlike PostgreSQL's REFRESH MATERIALIZED VIEW, which keeps them.
22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
# File 'lib/activerecord/materialized/table_swap.rb', line 22 def swap!(temp_table, old_table) preserved = current_indexes if connection.supports_ddl_transactions? # SQLite/Postgres: rename + index restore commit together, so readers only ever see the old # table or the fully-indexed new one. connection.transaction do rename_in_place!(temp_table, old_table) restore_missing_indexes!(preserved) end else # MySQL/MariaDB: RENAME TABLE auto-commits (a transaction can't make it atomic with the # index rebuild), so the restore runs after. A crash in this window leaves the new table live # but missing the preserved indexes until the next rebuild! — degraded read/maintenance # performance, never data loss or an empty table (the rename itself is atomic). atomic_rename!(temp_table, old_table) restore_missing_indexes!(preserved) end end |