Module: PgPower::CreateIndexConcurrently::Migration

Defined in:
lib/pg_power/create_index_concurrently.rb

Overview

Provides ability to postpone index creation queries in migrations.

Overrides ‘add_index` and `add_foreign_key` methods for migration to be able to prevent indexes creation inside scope of transaction if they have to be created concurrently. Allows to run creation of postponed indexes.

This module included into ActiveRecord::Migration class to extend it with new features.

All postponed index creation queries are stored inside migration instance.

Instance Method Summary collapse

Instance Method Details

#add_foreign_key(from_table, to_table, options = {}, &block) ⇒ Object

Add a foreign key.

Options:

  • :column

  • :primary_key

  • :dependent

  • :exclude_index [Boolean]

  • :concurrent_index [Boolean]

Parameters:

  • from_table (String, Symbol)
  • to_table (String, Symbol)
  • options (Hash) (defaults to: {})

Options Hash (options):

  • :column (String, Symbol)
  • :primary_key (String, Symbol)
  • :dependent (Hash)
  • :exclude_index (Boolean)
  • :concurrent_index (Boolean)

Raises:

  • (ArgumentError)

    in case of conflicted option were set

See Also:



110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
# File 'lib/pg_power/create_index_concurrently.rb', line 110

def add_foreign_key(from_table, to_table, options = {}, &block)
  from_table = ::ActiveRecord::Migrator.proper_table_name(from_table)
  if options[:concurrent_index]
    if options[:exclude_index]
      raise ArgumentError, 'Conflicted options(exclude_index, concurrent_index) was found, both are set to true.'
    end

    options[:column] ||= connection.id_column_name_from_table_name(to_table)
    options = options.merge(:concurrently => options[:concurrent_index])

    index_options = { :concurrently => true }
    enque(from_table, options[:column], index_options)
  end

  # GOTCHA:
  #   proceed foreign key creation, but giving :concurrent_index => true
  #   prevent normal index creation in PgPower's `add_foreign_key`.
  #   So, postponed creation could be done after transaction.
  #   -- zekefast 2012-09-12
  connection.add_foreign_key(from_table, to_table, options, &block)
end

#add_index(table_name, column_name, options = {}, &block) ⇒ nil

Add a new index to the table. column_name can be a single Symbol, or an Array of Symbols.

Parameters:

  • table_name (Symbol, String)
  • column_name (Symbol, String, Array<Symbol, String>)
  • options (optional, Hash) (defaults to: {})

Options Hash (options):

  • :unique (Boolean)
  • :concurrently (Boolean)
  • :where (String)

Returns:

  • (nil)

See Also:

  • in pg_power gem


72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
# File 'lib/pg_power/create_index_concurrently.rb', line 72

def add_index(table_name, column_name, options = {}, &block)
  table_name = ::ActiveRecord::Migrator.proper_table_name(table_name)
  # GOTCHA:
  #   checks if index should be created concurretnly then put it into
  #   the queue to wait till queue processing will be called (should be
  #   happended after closing transaction).
  #   Otherwise just delegate call to PgPower's `add_index`.
  #   Block is given for future compatibility.
  #   -- zekefast 2012-09-12
  unless options[:concurrently]
    return connection.add_index(table_name, column_name, options, &block)
  end

  enque(table_name, column_name, options, &block)
  nil
end

#process_postponed_queries::PgPower::CreateIndexConcurrently::Migration

Execute all postponed index creation.



135
136
137
138
139
140
141
142
143
# File 'lib/pg_power/create_index_concurrently.rb', line 135

def process_postponed_queries
  Array(@postponed_queries).each do |arguments, block|
    connection.add_index(*arguments, &block)
  end

  clear_queue

  self
end