Spec-Zone.ru › Ruby on Rails 8.0

модуль ActiveRecord::ModelSchema::ClassMethods

Открытые методы экземпляров

column_defaults() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 472
def column_defaults
  load_schema
  @column_defaults ||= _default_attributes.deep_dup.to_hash.freeze
end

Возвращает хеш, где ключи — имена столбцов, а значения — значения по умолчанию при создании объекта Active Record для этой таблицы.

column_for_attribute(name) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 463
def column_for_attribute(name)
  name = name.to_s
  columns_hash.fetch(name) do
    ConnectionAdapters::NullColumn.new(name)
  end
end

Возвращает объект столбца для заданного атрибута. Возвращает ActiveRecord::ConnectionAdapters::NullColumn, если атрибут с указанным именем не существует.

class Person < ActiveRecord::Base
end

person = Person.new
person.column_for_attribute(:name) # the result depends on the ConnectionAdapter
# => #<ActiveRecord::ConnectionAdapters::Column:0x007ff4ab083980 @name="name", @sql_type="varchar(255)", @null=true, ...>

person.column_for_attribute(:nothing)
# => #<ActiveRecord::ConnectionAdapters::NullColumn:0xXXX @name=nil, @sql_type=nil, @cast_type=#<Type::Value>, ...>
column_names() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 478
def column_names
  @column_names ||= columns.map(&:name).freeze
end

Возвращает массив имён столбцов в виде строк.

columns() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 432
def columns
  @columns ||= columns_hash.values.freeze
end
content_columns() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 489
def content_columns
  @content_columns ||= columns.reject do |c|
    c.name == primary_key ||
    c.name == inheritance_column ||
    c.name.end_with?("_id", "_count")
  end.freeze
end

Возвращает массив объектов столбцов, из которого удалены первичный идентификатор, все столбцы, оканчивающиеся на «_id» или «_count», а также столбцы, используемые для наследования по одной таблице.

ignored_columns() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 331
def ignored_columns
  @ignored_columns || superclass.ignored_columns
end

Список имён столбцов, которые модель должна игнорировать. Для игнорируемых столбцов не будут определены аксессоры атрибутов, и они не будут использоваться в запросах SQL.

ignored_columns=(columns) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 366
def ignored_columns=(columns)
  reload_schema_from_cache
  @ignored_columns = columns.map(&:to_s).freeze
end

Устанавливает имена столбцов, которые модель должна игнорировать. Для игнорируемых столбцов не будут определены аксессоры атрибутов, и они не будут использоваться в запросах SQL.

Часто используется для того, чтобы убедиться, что все ссылки на атрибут удалены, прежде чем миграция для удаления столбца из базы данных будет применена. Такой двухступенчатый подход гарантирует отсутствие ошибок из-за кэшированной схемы в памяти во время выполнения миграции схемы.

Например, для удаления атрибута «category» сначала отметьте его как игнорируемый:

class Project < ActiveRecord::Base
  # schema:
  #   id         :bigint
  #   name       :string, limit: 255
  #   category   :string, limit: 255

  self.ignored_columns += [:category]
end

Схема все еще содержит «category», но теперь модель его пропускает, поэтому любой код или кэширование схемы на основе метаданных не будут пытаться использовать столбец:

Project.columns_hash["category"] => nil

При прямом обращении к этому атрибуту произойдет ошибка, поэтому убедитесь, что все использования столбца удалены (автоматические тесты помогут вам найти все его использования).

user = Project.create!(name: "First Project")
user.category # => raises NoMethodError
load_schema() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 534
def load_schema
  return if schema_loaded?
  @load_schema_monitor.synchronize do
    return if schema_loaded?

    load_schema!

    @schema_loaded = true
  rescue
    reload_schema_from_cache # If the schema loading failed half way through, we must reset the state.
    raise
  end
end

Загружает информацию о схеме модели либо из кэша схемы, либо непосредственно из базы данных.

next_sequence_value() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 411
def next_sequence_value
  with_connection { |c| c.next_sequence_value(sequence_name) }
end

Возвращает следующее значение, которое будет использоваться в качестве первичного ключа в операторе вставки.

prefetch_primary_key?() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 405
def prefetch_primary_key?
  with_connection { |c| c.prefetch_primary_key?(table_name) }
end

Определяет, должны ли значения первичного ключа выбираться из соответствующей последовательности перед оператором вставки.

protected_environments() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 312
def protected_environments
  if defined?(@protected_environments)
    @protected_environments
  else
    superclass.protected_environments
  end
end

Массив имён сред, в которых запрещены деструктивные действия. По умолчанию значение равно ["production"].

protected_environments=(environments) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 321
def protected_environments=(environments)
  @protected_environments = environments.map(&:to_s)
end

Устанавливает массив имён сред, в которых запрещены деструктивные действия.

quoted_table_name() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 285
def quoted_table_name
  adapter_class.quote_table_name(table_name)
end

Возвращает цитированную версию имени таблицы.

reset_column_information() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 523
def reset_column_information
  connection_pool.active_connection&.clear_cache!
  ([self] + descendants).each(&:undefine_attribute_methods)
  schema_cache.clear_data_source_cache!(table_name)

  reload_schema_from_cache
  initialize_find_by_cache
end

Сбрасывает всю кэшированную информацию о столбцах, что приведет к их перезагрузке при следующем запросе.

Наиболее распространённое использование этого метода, вероятно, в миграции, когда сразу после создания таблицы вы хотите заполнить её некоторыми значениями по умолчанию, например:

class CreateJobLevels < ActiveRecord::Migration[8.0]
  def up
    create_table :job_levels do |t|
      t.integer :id
      t.string :name

      t.timestamps
    end

    JobLevel.reset_column_information
    %w{assistant executive manager director}.each do |type|
      JobLevel.create(name: type)
    end
  end

  def down
    drop_table :job_levels
  end
end
sequence_name() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 371
def sequence_name
  if base_class?
    @sequence_name ||= reset_sequence_name
  else
    (@sequence_name ||= nil) || base_class.sequence_name
  end
end
sequence_name=(value) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 398
def sequence_name=(value)
  @sequence_name          = value.to_s
  @explicit_sequence_name = true
end

Устанавливает имя последовательности для генерации идентификаторов заданному значению, или (если значение равно nil или false) значению, возвращаемому заданным блоком. Это необходимо для Oracle и полезно для любой базы данных, которая использует последовательности для генерации первичных ключей.

Если имя последовательности не установлено явно при использовании Oracle, оно будет по умолчанию равно: #{table_name}_seq

Если имя последовательности не установлено явно при использовании PostgreSQL, оно будет обнаружено для вашего первичного ключа.

class Project < ActiveRecord::Base
  self.sequence_name = "projectseq"   # default would have been "project_seq"
end
table_exists?() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 416
def table_exists?
  schema_cache.data_source_exists?(table_name)
end

Указывает, существует ли таблица, связанная с этим классом.

table_name() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 260
def table_name
  reset_table_name unless defined?(@table_name)
  @table_name
end

Определяет имя таблицы (в принудительно нижнем регистре) на основе имени класса в иерархии наследования, непосредственно унаследованной от ActiveRecord::Base. Таким образом, если иерархия выглядит как: Reply < Message < ActiveRecord::Base, то Message используется для определения имени таблицы даже при вызове из Reply. Правила определения имени таблицы обрабатываются классом Inflector в Active Support, который знает практически все распространённые английские склонения. Вы можете добавить новые склонения в файл config/initializers/inflections.rb.

Вложенным классам присваиваются имена таблиц, начинающиеся с единственного числа имени родительской таблицы. Вложенные модули не рассматриваются.

Примеры

class Invoice < ActiveRecord::Base
end

file                  class               table_name
invoice.rb            Invoice             invoices

class Invoice < ActiveRecord::Base
  class Lineitem < ActiveRecord::Base
  end
end

file                  class               table_name
invoice.rb            Invoice::Lineitem   invoice_lineitems

module Invoice
  class Lineitem < ActiveRecord::Base
  end
end

file                  class               table_name
invoice/lineitem.rb   Invoice::Lineitem   lineitems

Кроме того, к имени класса добавляется префикс уровня класса table_name_prefix и суффикс table_name_suffix. Таким образом, если у вас есть префикс «myapp_», то предполагаемое имя таблицы для класса Invoice становится «myapp_invoices». Invoice::Lineitem станет «myapp_invoice_lineitems».

Базовое имя, используемое для определения имени таблицы, — это model_name из Active Model Naming. В случае определения пользовательского имени Active Model Name, оно также будет использоваться для имени таблицы:

class PostRecord < ActiveRecord::Base
  class << self
    def model_name
      ActiveModel::Name.new(self, nil, "Post")
    end
  end
end

PostRecord.table_name
# => "posts"

Также вы можете явно задать имя таблицы:

class Mouse < ActiveRecord::Base
  self.table_name = "mice"
end
table_name=(value) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 270
def table_name=(value)
  value = value && value.to_s

  if defined?(@table_name)
    return if value == @table_name
    reset_column_information if connected?
  end

  @table_name        = value
  @arel_table        = nil
  @sequence_name     = nil unless @explicit_sequence_name
  @predicate_builder = nil
end

Явно устанавливает имя таблицы. Пример:

class Project < ActiveRecord::Base
  self.table_name = "project"
end

Защищённые методы экземпляра

initialize_load_schema_monitor() Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 549
def initialize_load_schema_monitor
  @load_schema_monitor = Monitor.new
end
reload_schema_from_cache(recursive = true) Показать исходный код
# File activerecord/lib/active_record/model_schema.rb, line 553
def reload_schema_from_cache(recursive = true)
  @_returning_columns_for_insert = nil
  @arel_table = nil
  @column_names = nil
  @symbol_column_to_string_name_hash = nil
  @content_columns = nil
  @column_defaults = nil
  @attributes_builder = nil
  @columns = nil
  @columns_hash = nil
  @schema_loaded = false
  @attribute_names = nil
  @yaml_encoder = nil
  if recursive
    subclasses.each do |descendant|
      descendant.send(:reload_schema_from_cache)
    end
  end
end

© 2004–2021 David Heinemeier Hansson
Licensed under the MIT License.

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API