Spec-Zone.ru › Ruby on Rails 6.1

класс ActiveRecord::Relation

Родитель:
Объект
Включенные модули:
Enumerable

Отношение Active Record

Константы

CLAUSE_METHODS
НЕДОПУСТИМЫЕ_МЕТОДЫ_ДЛЯ_DELETE_ALL
MULTI_VALUE_METHODS
SINGLE_VALUE_METHODS
VALUE_METHODS

Атрибуты

klass[R]
loaded[R]
loaded?[R]
model[R]
predicate_builder[R]
skip_preloading_value[RW]
table[R]

Открытые методы класса

new(klass, table: klass.arel_table, predicate_builder: klass.predicate_builder, values: {}) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 27
def initialize(klass, table: klass.arel_table, predicate_builder: klass.predicate_builder, values: {})
  @klass  = klass
  @table  = table
  @values = values
  @loaded = false
  @predicate_builder = predicate_builder
  @delegate_to_klass = false
end

Общедоступные методы экземпляров

==(other) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 708
def ==(other)
  case other
  when Associations::CollectionProxy, AssociationRelation
    self == other.records
  when Relation
    other.to_sql == to_sql
  when Array
    records == other
  end
end

Сравнивает два отношения на равенство.

any?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 276
def any?
  return super if block_given?
  !empty?
end

Возвращает true, если есть какие-либо записи.

Вызывается метод суперкласса
blank?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 724
def blank?
  records.blank?
end

Возвращает true, если отношение пустое.

build(attributes = nil, &block)
Псевдоним для: new
cache_key(timestamp_column = "updated_at") Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 310
def cache_key(timestamp_column = "updated_at")
  @cache_keys ||= {}
  @cache_keys[timestamp_column] ||= klass.collection_cache_key(self, timestamp_column)
end

Возвращает стабильный ключ кэша, который можно использовать для идентификации этого запроса. Ключ кэша создается с отпечатком SQL-запроса.

Product.where("name like ?", "%Cosmic Encounter%").cache_key
# => "products/query-1850ab3d302391b85b8693e941286659"

Если ActiveRecord::Base.collection_cache_versioning отключен, как это было в Rails 6.0 и ранее, ключ кэша также будет содержать версию.

ActiveRecord::Base.collection_cache_versioning = false
Product.where("name like ?", "%Cosmic Encounter%").cache_key
# => "products/query-1850ab3d302391b85b8693e941286659-1-20150714212553907087000"

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

Product.where("name like ?", "%Game%").cache_key(:last_reviewed_at)
cache_key_with_version() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 388
def cache_key_with_version
  if version = cache_version
    "#{cache_key}-#{version}"
  else
    cache_key
  end
end

Возвращает ключ кэша вместе с версией.

cache_version(timestamp_column = :updated_at) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 337
def cache_version(timestamp_column = :updated_at)
  if collection_cache_versioning
    @cache_versions ||= {}
    @cache_versions[timestamp_column] ||= compute_cache_version(timestamp_column)
  end
end

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

Если коллекция загружена, метод будет перебирать записи для генерации отметки времени, в противном случае он вызовет один SQL-запрос, например:

SELECT COUNT(*), MAX("products"."updated_at") FROM "products" WHERE (name like '%Cosmic Encounter%')
create(attributes = nil, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 94
def create(attributes = nil, &block)
  if attributes.is_a?(Array)
    attributes.collect { |attr| create(attr, &block) }
  else
    block = current_scope_restoring_block(&block)
    scoping { _create(attributes, &block) }
  end
end

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

Ожидает аргументов в том же формате, что и ActiveRecord::Base.create.

Примеры

users = User.where(name: 'Oscar')
users.create # => #<User id: 3, name: "Oscar", ...>

users.create(name: 'fxn')
users.create # => #<User id: 4, name: "fxn", ...>

users.create { |user| user.name = 'tenderlove' }
# => #<User id: 5, name: "tenderlove", ...>

users.create(name: nil) # validation on name
# => #<User id: nil, name: nil, ...>
create!(attributes = nil, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 109
def create!(attributes = nil, &block)
  if attributes.is_a?(Array)
    attributes.collect { |attr| create!(attr, &block) }
  else
    block = current_scope_restoring_block(&block)
    scoping { _create!(attributes, &block) }
  end
end

Аналогично create, но вызывает create! для базового класса. Вызывает исключение, если возникает ошибка проверки.

Ожидает аргументов в том же формате, что и ActiveRecord::Base.create!.

create_or_find_by(attributes, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 208
def create_or_find_by(attributes, &block)
  transaction(requires_new: true) { create(attributes, &block) }
rescue ActiveRecord::RecordNotUnique
  find_by!(attributes)
end

Попытка создания записи с заданными атрибутами в таблице, имеющей уникальное ограничение на один или несколько столбцов. Если строка уже существует с одним или несколькими из этих уникальных ограничений, исключение, которое обычно возникает при такой вставке, перехватывается, и существующая запись с этими атрибутами находится с помощью find_by!.

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

Однако существуют несколько недостатков create_or_find_by:

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

  • Нарушение уникального ограничения может быть вызвано только одним или по крайней мере менее чем всеми заданными атрибутами. Это означает, что последующий find_by! может не найти соответствующую запись, которая затем вызовет исключение ActiveRecord::RecordNotFound , а не запись с заданными атрибутами.

  • Хотя мы избегаем гонки условий между SELECT -> INSERT из find_or_create_by, у нас фактически есть еще одна гонка условий между INSERT -> SELECT, которая может быть вызвана, если другой клиент выполнит DELETE между этими двумя операторами. Но для большинства приложений это значительно менее вероятно.

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

  • Первичный ключ может автоматически инкрементироваться при каждом создании, даже если он не удается. Это может ускорить проблему исчерпания целых чисел, если базовая таблица все еще использует первичный ключ типа int (прим.: все приложения Rails с версии 5.1+ по умолчанию используют bigint, который не подвержен этой проблеме).

Этот метод вернет запись, если все заданные атрибуты покрываются уникальными ограничениями (если не вызвана гонка условий INSERT -> DELETE -> SELECT), но если попытка создания не удалась из-за ошибок проверки, она не будет сохранена, вы получите то, что возвращает create в такой ситуации.

create_or_find_by!(attributes, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 217
def create_or_find_by!(attributes, &block)
  transaction(requires_new: true) { create!(attributes, &block) }
rescue ActiveRecord::RecordNotUnique
  find_by!(attributes)
end

Подобно create_or_find_by, но вызывает create!, поэтому при возникновении ошибки проверки созданной записи будет вызвано исключение.

delete_all() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 576
def delete_all
  invalid_methods = INVALID_METHODS_FOR_DELETE_ALL.select do |method|
    value = @values[method]
    method == :distinct ? value : value&.any?
  end
  if invalid_methods.any?
    raise ActiveRecordError.new("delete_all doesn't support #{invalid_methods.join(', ')}")
  end

  if eager_loading?
    relation = apply_join_dependency
    return relation.delete_all
  end

  stmt = Arel::DeleteManager.new
  stmt.from(arel.join_sources.empty? ? table : arel.source)
  stmt.key = table[primary_key]
  stmt.take(arel.limit)
  stmt.offset(arel.offset)
  stmt.order(*arel.orders)
  stmt.wheres = arel.constraints

  affected = @klass.connection.delete(stmt, "#{@klass} Destroy")

  reset
  affected
end

Удаляет записи, не инициализируя их сначала, и, следовательно, не вызывая метод #destroy и не вызывая обратные вызовы. Это единственное SQL-утверждение DELETE, которое идет напрямую в базу данных, значительно эффективнее, чем destroy_all. Будьте осторожны с отношениями, в частности, правила :dependent , определенные в ассоциациях, не учитываются. Возвращает количество затронутых строк.

Post.where(person_id: 5).where(category: ['Something', 'Else']).delete_all

Оба вызова удаляют затронутые записи одновременно с помощью одного утверждения DELETE. Если вам нужно уничтожить зависимые ассоциации или вызвать ваши before_* или after_destroy обратные вызовы, используйте метод destroy_all вместо этого.

Если предоставлен неверный метод, delete_all выдает ActiveRecordError:

Post.distinct.delete_all
# => ActiveRecord::ActiveRecordError: delete_all doesn't support distinct
delete_by(*args) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 626
def delete_by(*args)
  where(*args).delete_all
end

Находит и удаляет все записи, соответствующие указанным условиям. Это сокращенная запись для relation.where(condition).delete_all. Возвращает количество затронутых строк.

Если запись не найдена, возвращает 0 , так как затронутых строк не было.

Person.delete_by(id: 13)
Person.delete_by(name: 'Spartacus', rating: 4)
Person.delete_by("published_at < ?", 2.weeks.ago)
destroy_all() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 554
def destroy_all
  records.each(&:destroy).tap { reset }
end

Уничтожает записи, инициализируя каждую запись и вызывая для неё метод #destroy. Выполняются обратные вызовы каждого объекта (включая :dependent параметры ассоциации). Возвращает коллекцию объектов, которые были уничтожены; каждый будет заморожен, чтобы отразить, что никаких изменений не должно быть внесено (поскольку они не могут быть сохранены).

Примечание: Инициализация, выполнение обратных вызовов и удаление каждой записи может быть длительным при удалении сразу многих записей. Это генерирует по крайней мере один SQL DELETE запрос на запись (или, возможно, больше, чтобы применить ваши обратные вызовы). Если вы хотите быстро удалить много строк, не беспокоясь об их ассоциациях или обратных вызовах, используйте delete_all вместо этого.

Примеры

Person.where(age: 0..18).destroy_all
destroy_by(*args) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 613
def destroy_by(*args)
  where(*args).destroy_all
end

Находит и уничтожает все записи, соответствующие указанным условиям. Это сокращение для relation.where(condition).destroy_all. Возвращает коллекцию уничтоженных объектов.

Если запись не найдена, возвращается пустой массив.

Person.destroy_by(id: 13)
Person.destroy_by(name: 'Spartacus', rating: 4)
Person.destroy_by("published_at < ?", 2.weeks.ago)
eager_loading?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 693
def eager_loading?
  @should_eager_load ||=
    eager_load_values.any? ||
    includes_values.any? && (joined_includes_values.any? || references_eager_loaded_tables?)
end

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

empty?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 264
def empty?
  return @records.empty? if loaded?
  !exists?
end

Возвращает true, если записей нет.

encode_with(coder) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 254
def encode_with(coder)
  coder.represent_seq(nil, records)
end

Сериализует объекты связи Array.

explain() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 238
def explain
  exec_explain(collecting_queries_for_explain { exec_queries })
end

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

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

Дополнительные сведения см. в руководстве по интерфейсу запросов Active Record.

find_or_create_by(attributes, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 167
def find_or_create_by(attributes, &block)
  find_by(attributes) || create(attributes, &block)
end

Находит первую запись с заданными атрибутами или создает запись с этими атрибутами, если запись не найдена:

# Find the first user named "Penélope" or create a new one.
User.find_or_create_by(first_name: 'Penélope')
# => #<User id: 1, first_name: "Penélope", last_name: nil>

# Find the first user named "Penélope" or create a new one.
# We already have one so the existing record will be returned.
User.find_or_create_by(first_name: 'Penélope')
# => #<User id: 1, first_name: "Penélope", last_name: nil>

# Find the first user named "Scarlett" or create a new one with
# a particular last name.
User.create_with(last_name: 'Johansson').find_or_create_by(first_name: 'Scarlett')
# => #<User id: 2, first_name: "Scarlett", last_name: "Johansson">

Этот метод принимает блок, который передается в create. Последний пример выше можно альтернативно написать следующим образом:

# Find the first user named "Scarlett" or create a new one with a
# different last name.
User.find_or_create_by(first_name: 'Scarlett') do |user|
  user.last_name = 'Johansson'
end
# => #<User id: 2, first_name: "Scarlett", last_name: "Johansson">

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

Обратите внимание, что этот метод не является атомарным, он сначала выполняет SELECT, а если результатов нет, пытается выполнить INSERT. Если есть другие потоки или процессы, существует условие гонки между двумя вызовами, и может оказаться так, что вы получите две похожие записи.

Если это может быть проблемой для вашего приложения, см. create_or_find_by.

find_or_create_by!(attributes, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 174
def find_or_create_by!(attributes, &block)
  find_by(attributes) || create!(attributes, &block)
end

Как find_or_create_by, но вызывает create!, поэтому исключение возникает, если созданная запись недействительна.

find_or_initialize_by(attributes, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 225
def find_or_initialize_by(attributes, &block)
  find_by(attributes) || new(attributes, &block)
end

Как find_or_create_by, но вызывает new вместо create.

initialize_copy(other) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 36
def initialize_copy(other)
  @values = @values.dup
  reset
end
inspect() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 732
def inspect
  subject = loaded? ? records : annotate("loading for inspect")
  entries = subject.take([limit_value, 11].compact.min).map!(&:inspect)

  entries[10] = "..." if entries.size == 11

  "#<#{self.class.name} [#{entries.join(', ')}]>"
end
joined_includes_values() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 703
def joined_includes_values
  includes_values & joins_values
end

Объединения, которые также помечены для предварительной загрузки. В этом случае мы должны просто нетерпеливо загрузить их. Обратите внимание, что это наивная реализация, потому что у нас могут быть строки и символы, которые представляют одну и ту же ассоциацию, но которые не соответствуют этому. Кроме того, у нас могут быть вложенные хеши, которые частично совпадают, например { a: :b } & { a: [:b, :c] }

load(&block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 636
def load(&block)
  unless loaded?
    @records = exec_queries(&block)
    @loaded = true
  end

  self
end

Заставляет записи загружаться из базы данных, если они еще не были загружены. Вы можете использовать это, если по какой-либо причине вам нужно явно загрузить некоторые записи перед их фактическим использованием. Возвращаемое значение — сама связь, а не записи.

Post.where(published: true).load # => #<ActiveRecord::Relation>
many?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 288
def many?
  return super if block_given?
  limit_value ? records.many? : size > 1
end

Возвращает true, если записей больше одной.

Вызывает метод суперкласса Enumerable#many?
new(attributes = nil, &block) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 69
def new(attributes = nil, &block)
  block = current_scope_restoring_block(&block)
  scoping { _new(attributes, &block) }
end

Инициализирует новую запись из связи, сохраняя текущую область видимости.

Ожидает аргументы в том же формате, что и ActiveRecord::Base.new.

users = User.where(name: 'DHH')
user = users.new # => #<User id: nil, name: "DHH", created_at: nil, updated_at: nil>

Вы также можете передать блок в new с новой записью в качестве аргумента:

user = users.new { |user| user.name = 'Oscar' }
user.name # => Oscar
Также имеет псевдоним: build
none?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 270
def none?
  return super if block_given?
  empty?
end

Возвращает true, если записей нет.

Вызывает метод суперкласса
one?() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 282
def one?
  return super if block_given?
  limit_value ? records.one? : size == 1
end

Возвращает true, если есть ровно одна запись.

Вызывает метод суперкласса
pretty_print(q) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 719
def pretty_print(q)
  q.pp(records)
end
reload() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 646
def reload
  reset
  load
end

Принудительно перезагружает связь.

reset() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 651
def reset
  @delegate_to_klass = false
  @to_sql = @arel = @loaded = @should_eager_load = nil
  @offsets = @take = nil
  @records = [].freeze
  self
end
scope_for_create() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 685
def scope_for_create
  hash = where_values_hash
  hash.delete(klass.inheritance_column) if klass.finder_needs_type_condition?
  create_with_value.each { |k, v| hash[k.to_s] = v } unless create_with_value.empty?
  hash
end
scoping() { |: _scoping(self) { yield }| ... } Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 405
def scoping
  already_in_scope? ? yield : _scoping(self) { yield }
end

Применяет область видимости ко всем запросам в текущей области видимости.

Comment.where(post_id: 1).scoping do
  Comment.first
end
# => SELECT "comments".* FROM "comments" WHERE "comments"."post_id" = 1 ORDER BY "comments"."id" ASC LIMIT 1

Проверьте unscoped, если вы хотите удалить все предыдущие области видимости (включая default_scope) во время выполнения блока.

size() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 259
def size
  loaded? ? @records.length : count(:all)
end

Возвращает размер набора записей.

to_a()
Псевдоним для: to_ary
to_ary() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 243
def to_ary
  records.dup
end

Преобразует объекты отношения в Array.

Также используется как псевдоним: to_a
to_sql() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 663
def to_sql
  @to_sql ||= begin
    if eager_loading?
      apply_join_dependency do |relation, join_dependency|
        relation = join_dependency.apply_column_aliases(relation)
        relation.to_sql
      end
    else
      conn = klass.connection
      conn.unprepared_statement { conn.to_sql(arel) }
    end
  end
end

Возвращает SQL-запрос для отношения.

User.where(name: 'Oscar').to_sql
# => SELECT "users".* FROM "users"  WHERE "users"."name" = 'Oscar'
touch_all(*names, time: nil) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 534
def touch_all(*names, time: nil)
  update_all klass.touch_attributes_with_time(*names, time: time)
end

Обновляет все записи в текущем отношении, устанавливая атрибуты updated_at/updated_on на текущее время или указанное время. Не создает вовлеченные модели и не запускает обратные вызовы или проверки Active Record. Этот метод может принимать имена атрибутов и необязательный аргумент времени. Если переданы имена атрибутов, они обновляются вместе с атрибутами updated_at/updated_on. Если аргумент времени не передан, используется текущее время по умолчанию.

Примеры

# Touch all records
Person.all.touch_all
# => "UPDATE \"people\" SET \"updated_at\" = '2018-01-04 22:55:23.132670'"

# Touch multiple records with a custom attribute
Person.all.touch_all(:created_at)
# => "UPDATE \"people\" SET \"updated_at\" = '2018-01-04 22:55:23.132670', \"created_at\" = '2018-01-04 22:55:23.132670'"

# Touch multiple records with a specified time
Person.all.touch_all(time: Time.new(2020, 5, 16, 0, 0, 0))
# => "UPDATE \"people\" SET \"updated_at\" = '2020-05-16 00:00:00'"

# Touch records with scope
Person.where(name: 'David').touch_all
# => "UPDATE \"people\" SET \"updated_at\" = '2018-01-04 22:55:23.132670' WHERE \"people\".\"name\" = 'David'"
update_all(updates) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 440
def update_all(updates)
  raise ArgumentError, "Empty list of attributes to change" if updates.blank?

  if eager_loading?
    relation = apply_join_dependency
    return relation.update_all(updates)
  end

  stmt = Arel::UpdateManager.new
  stmt.table(arel.join_sources.empty? ? table : arel.source)
  stmt.key = table[primary_key]
  stmt.take(arel.limit)
  stmt.offset(arel.offset)
  stmt.order(*arel.orders)
  stmt.wheres = arel.constraints

  if updates.is_a?(Hash)
    if klass.locking_enabled? &&
        !updates.key?(klass.locking_column) &&
        !updates.key?(klass.locking_column.to_sym)
      attr = table[klass.locking_column]
      updates[attr.name] = _increment_attribute(attr)
    end
    stmt.set _substitute_values(updates)
  else
    stmt.set Arel.sql(klass.sanitize_sql_for_assignment(updates, table.name))
  end

  @klass.connection.update stmt, "#{@klass} Update All"
end

Обновляет все записи в текущем отношении с указанными данными. Этот метод создает один SQL-запрос UPDATE и отправляет его напрямую в базу данных. Не создает вовлеченные модели и не запускает обратные вызовы или проверки Active Record. Однако значения, переданные в update_all, всё ещё будут проходить обычное приведение типов и сериализацию Active Record. Возвращает количество изменённых строк.

Примечание: Поскольку обратные вызовы Active Record не вызываются, этот метод не будет автоматически обновлять столбцы updated_at/updated_on.

Параметры

  • updates - Строка, массив или хеш, представляющий часть SET SQL-запроса.

Примеры

# Update all customers with the given attributes
Customer.update_all wants_email: true

# Update all books with 'Rails' in their title
Book.where('title LIKE ?', '%Rails%').update_all(author: 'David')

# Update all books that match conditions, but limit it to 5 ordered by date
Book.where('title LIKE ?', '%Rails%').order(:created_at).limit(5).update_all(author: 'David')

# Update all invoices and set the number column to its id value.
Invoice.update_all('number = id')
update_counters(counters) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 491
def update_counters(counters)
  touch = counters.delete(:touch)

  updates = {}
  counters.each do |counter_name, value|
    attr = table[counter_name]
    updates[attr.name] = _increment_attribute(attr, value)
  end

  if touch
    names = touch if touch != true
    names = Array.wrap(names)
    options = names.extract_options!
    touch_updates = klass.touch_attributes_with_time(*names, **options)
    updates.merge!(touch_updates) unless touch_updates.empty?
  end

  update_all updates
end

Обновляет счётчики записей в текущем отношении.

Параметры

  • counter - Hash содержащий имена полей для обновления в качестве ключей и количество для обновления в качестве значений.

  • :touch опция - Обновить временные метки при обновлении.

  • Если имена атрибутов переданы, они обновляются вместе с атрибутами update_at/on.

Примеры

# For Posts by a given author increment the comment_count by 1.
Post.where(author_id: author.id).update_counters(comment_count: 1)
values() Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 728
def values
  @values.dup
end
where_values_hash(relation_table_name = klass.table_name) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 681
def where_values_hash(relation_table_name = klass.table_name)
  where_clause.to_h(relation_table_name)
end

Возвращает хеш с условиями where.

User.where(name: 'Oscar').where_values_hash
# => {name: "Oscar"}

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

load_records(records) Показать исходный код
# File activerecord/lib/active_record/relation.rb, line 775
def load_records(records)
  @records = records.freeze
  @loaded = true
end

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

Spec-Zone.ru

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