module ActiveRecord::ConnectionAdapters::PostgreSQL::DatabaseStatements

Constants

IDLE_TRANSACTION_STATUSES

Public Instance Methods

build_explain_clause(options = []) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 96
def build_explain_clause(options = [])
  return "EXPLAIN" if options.empty?

  "EXPLAIN (#{options.join(", ").upcase})"
end
explain(arel, binds = [], options = []) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 7
def explain(arel, binds = [], options = [])
  sql    = build_explain_clause(options) + " " + to_sql(arel, binds)
  result = internal_exec_query(sql, "EXPLAIN", binds)
  PostgreSQL::ExplainPrettyPrinter.new.pp(result)
end
high_precision_current_timestamp() click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 92
def high_precision_current_timestamp
  HIGH_PRECISION_CURRENT_TIMESTAMP
end
set_constraints(deferred, *constraints) click to toggle source

Set when constraints will be checked for the current transaction.

Not passing any specific constraint names will set the value for all deferrable constraints.

deferred

Valid values are :deferred or :immediate.

See www.postgresql.org/docs/current/sql-set-constraints.html

# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 110
def set_constraints(deferred, *constraints)
  unless %i[deferred immediate].include?(deferred)
    raise ArgumentError, "deferred must be :deferred or :immediate"
  end

  constraints = if constraints.empty?
    "ALL"
  else
    constraints.map { |c| quote_table_name(c) }.join(", ")
  end
  execute("SET CONSTRAINTS #{constraints} #{deferred.to_s.upcase}")
end

Private Instance Methods

affected_rows(result) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 189
def affected_rows(result)
  affected_rows = result.cmd_tuples
  result.clear
  affected_rows
end
build_truncate_statements(table_names) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 199
def build_truncate_statements(table_names)
  ["TRUNCATE TABLE #{table_names.map(&method(:quote_table_name)).join(", ")}"]
end
cancel_any_running_query() click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 127
def cancel_any_running_query
  return if @raw_connection.nil? || IDLE_TRANSACTION_STATUSES.include?(@raw_connection.transaction_status)

  @raw_connection.cancel
  @raw_connection.block
rescue PG::Error
end
cast_result(result) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 171
def cast_result(result)
  if result.fields.empty?
    result.clear
    return ActiveRecord::Result.empty
  end

  types = {}
  fields = result.fields
  fields.each_with_index do |fname, i|
    ftype = result.ftype i
    fmod  = result.fmod i
    types[fname] = types[i] = get_oid_type(ftype, fmod, fname)
  end
  ar_result = ActiveRecord::Result.new(fields, result.values, types.freeze)
  result.clear
  ar_result
end
execute_batch(statements, name = nil, **kwargs) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 195
def execute_batch(statements, name = nil, **kwargs)
  raw_execute(combine_multi_statements(statements), name, batch: true, **kwargs)
end
handle_warnings(sql) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 216
def handle_warnings(sql)
  @notice_receiver_sql_warnings.each do |warning|
    next if warning_ignored?(warning)

    warning.sql = sql
    ActiveRecord.db_warnings_action.call(warning)
  end
end
last_insert_id_result(sequence_name) click to toggle source

Returns the current ID of a table’s sequence.

# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 204
def last_insert_id_result(sequence_name)
  internal_exec_query("SELECT currval(#{quote(sequence_name)})", "SQL")
end
perform_query(raw_connection, sql, binds, type_casted_binds, prepare:, notification_payload:, batch: false) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 135
def perform_query(raw_connection, sql, binds, type_casted_binds, prepare:, notification_payload:, batch: false)
  update_typemap_for_default_timezone
  result = if prepare
    begin
      stmt_key = prepare_statement(sql, binds, raw_connection)
      notification_payload[:statement_name] = stmt_key
      raw_connection.exec_prepared(stmt_key, type_casted_binds)
    rescue PG::FeatureNotSupported => error
      if is_cached_plan_failure?(error)
        # Nothing we can do if we are in a transaction because all commands
        # will raise InFailedSQLTransaction
        if in_transaction?
          raise PreparedStatementCacheExpired.new(error.message, connection_pool: @pool)
        else
          @lock.synchronize do
            # outside of transactions we can simply flush this query and retry
            @statements.delete sql_key(sql)
          end
          retry
        end
      end

      raise
    end
  elsif binds.nil? || binds.empty?
    raw_connection.async_exec(sql)
  else
    raw_connection.exec_params(sql, type_casted_binds)
  end

  verified!
  handle_warnings(result)
  notification_payload[:row_count] = result.count
  result
end
returning_column_values(result) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 208
def returning_column_values(result)
  result.rows.first
end
suppress_composite_primary_key(pk) click to toggle source
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 212
def suppress_composite_primary_key(pk)
  pk unless pk.is_a?(Array)
end
warning_ignored?(warning) click to toggle source
Calls superclass method
# File lib/active_record/connection_adapters/postgresql/database_statements.rb, line 225
def warning_ignored?(warning)
  ["WARNING", "ERROR", "FATAL", "PANIC"].exclude?(warning.level) || super
end