class Apartment::Adapters::PostgresqlSchemaAdapter

Separate Adapter for Postgresql when using schemas

Public Class Methods

new(config) click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 28
def initialize(config)
  super

  reset
end

Public Instance Methods

current() click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 43
def current
  @current || default_tenant
end
reset() click to toggle source

Reset schema search path to the default schema_search_path

@return {String} default schema search path

# File lib/apartment/adapters/postgresql_adapter.rb, line 38
def reset
  @current = default_tenant
  Apartment.connection.schema_search_path = full_search_path
end

Protected Instance Methods

connect_to_new(tenant = nil) click to toggle source

Set schema search path to new schema

# File lib/apartment/adapters/postgresql_adapter.rb, line 64
def connect_to_new(tenant = nil)
  return reset if tenant.nil?
  raise ActiveRecord::StatementInvalid.new("Could not find schema #{tenant}") unless Apartment.connection.schema_exists?(tenant.to_s)

  @current = tenant.to_s
  Apartment.connection.schema_search_path = full_search_path

  # When the PostgreSQL version is < 9.3,
  # there is a issue for prepared statement with changing search_path.
  # https://www.postgresql.org/docs/9.3/static/sql-prepare.html
  if postgresql_version < 90300
    Apartment.connection.clear_cache!
  end

rescue *rescuable_exceptions
  raise TenantNotFound, "One of the following schema(s) is invalid: \"#{tenant}\" #{full_search_path}"
end
drop_command(conn, tenant) click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 58
def drop_command(conn, tenant)
  conn.execute(%{DROP SCHEMA "#{tenant}" CASCADE})
end
process_excluded_model(excluded_model) click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 49
def process_excluded_model(excluded_model)
  excluded_model.constantize.tap do |klass|
    # Ensure that if a schema *was* set, we override
    table_name = klass.table_name.split('.', 2).last

    klass.table_name = "#{default_tenant}.#{table_name}"
  end
end

Private Instance Methods

create_tenant_command(conn, tenant) click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 84
def create_tenant_command(conn, tenant)
  conn.execute(%{CREATE SCHEMA "#{tenant}"})
end
full_search_path() click to toggle source

Generate the final search path to set including persistent_schemas

# File lib/apartment/adapters/postgresql_adapter.rb, line 90
def full_search_path
  persistent_schemas.map(&:inspect).join(", ")
end
persistent_schemas() click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 94
def persistent_schemas
  [@current, Apartment.persistent_schemas].flatten
end
postgresql_version() click to toggle source
# File lib/apartment/adapters/postgresql_adapter.rb, line 98
def postgresql_version
  # ActiveRecord::ConnectionAdapters::PostgreSQLAdapter#postgresql_version is
  # public from Rails 5.0.
  Apartment.connection.send(:postgresql_version)
end