Active Model 錯誤
提供錯誤相關功能,您可以將其包含在物件中,以處理錯誤訊息和與 Action View 輔助程式互動。
最小的實作可以是
class Person
# Required dependency for ActiveModel::Errors
extend ActiveModel::Naming
def initialize
@errors = ActiveModel::Errors.new(self)
end
attr_accessor :name
attr_reader :errors
def validate!
errors.add(:name, :blank, message: "cannot be nil") if name.nil?
end
# The following methods are needed to be minimally implemented
def read_attribute_for_validation(attr)
send(attr)
end
def self.human_attribute_name(attr, options = {})
attr
end
def self.lookup_ancestors
[self]
end
end
物件中需要最後三個方法,才能讓 Errors
正確產生錯誤訊息,並處理多種語言。當然,如果您使用 ActiveModel::Translation
擴充物件,就不需要實作最後兩個方法。同樣地,使用 ActiveModel::Validations
會為您處理與驗證相關的方法。
上述內容讓您可以執行
person = Person.new
person.validate! # => ["cannot be nil"]
person.errors.full_messages # => ["name cannot be nil"]
# etc..
- #
- A
- C
- D
- E
- F
- G
- H
- I
- K
- M
- N
- O
- S
- T
- W
屬性
[R] | errors |
|
[R] | objects |
|
類別公開方法
new(base) 連結
傳入使用錯誤物件的物件實例。
class Person
def initialize
@errors = ActiveModel::Errors.new(self)
end
end
來源: 顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 117 def initialize(base) @base = base @errors = [] end
實例公開方法
[](attribute) 連結
傳入符號或方法名稱時,傳回方法的錯誤陣列。
person.errors[:name] # => ["cannot be nil"]
person.errors['name'] # => ["cannot be nil"]
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 229 def [](attribute) messages_for(attribute) end
add(屬性, 類型 = :invalid, **選項) 連結
在 屬性
上新增 類型
的新錯誤。可以新增多個錯誤至同一個 屬性
。如果未提供 類型
,則假設為 :invalid
。
person.errors.add(:name)
# Adds <#ActiveModel::Error attribute=name, type=invalid>
person.errors.add(:name, :not_implemented, message: "must be implemented")
# Adds <#ActiveModel::Error attribute=name, type=not_implemented,
options={:message=>"must be implemented"}>
person.errors.messages
# => {:name=>["is invalid", "must be implemented"]}
如果 類型
是字串,它將被用作錯誤訊息。
如果 類型
是符號,它將使用適當的範圍進行翻譯(請參閱 generate_message
)。
person.errors.add(:name, :blank)
person.errors.messages
# => {:name=>["can't be blank"]}
person.errors.add(:name, :too_long, count: 25)
person.errors.messages
# => ["is too long (maximum is 25 characters)"]
如果 類型
是程序,它將被呼叫,允許在錯誤中使用 Time.now
等內容。
如果 :strict
選項設為 true
,它將引發 ActiveModel::StrictValidationFailed
,而不是新增錯誤。:strict
選項也可以設為任何其他例外。
person.errors.add(:name, :invalid, strict: true)
# => ActiveModel::StrictValidationFailed: Name is invalid
person.errors.add(:name, :invalid, strict: NameIsInvalid)
# => NameIsInvalid: Name is invalid
person.errors.messages # => {}
如果錯誤未直接與單一屬性關聯,則應將 屬性
設為 :base
。
person.errors.add(:base, :name_or_email_blank,
message: "either name or email must be present")
person.errors.messages
# => {:base=>["either name or email must be present"]}
person.errors.details
# => {:base=>[{error: :name_or_email_blank}]}
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 342 def add(attribute, type = :invalid, **options) attribute, type, options = normalize_arguments(attribute, type, **options) error = Error.new(@base, attribute, type, **options) if exception = options[:strict] exception = ActiveModel::StrictValidationFailed if exception == true raise exception, error.full_message end @errors.append(error) error end
added?(屬性, 類型 = :invalid, 選項 = {}) 連結
如果錯誤符合提供的 屬性
和 類型
,則傳回 true
,否則傳回 false
。類型
的處理方式與 add
相同。
person.errors.add :name, :blank
person.errors.added? :name, :blank # => true
person.errors.added? :name, "can't be blank" # => true
如果錯誤需要選項,則傳回正確選項的 true
,或不正確或遺失選項的 false
。
person.errors.add :name, :too_long, count: 25
person.errors.added? :name, :too_long, count: 25 # => true
person.errors.added? :name, "is too long (maximum is 25 characters)" # => true
person.errors.added? :name, :too_long, count: 24 # => false
person.errors.added? :name, :too_long # => false
person.errors.added? :name, "is too long" # => false
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 372 def added?(attribute, type = :invalid, options = {}) attribute, type, options = normalize_arguments(attribute, type, **options) if type.is_a? Symbol @errors.any? { |error| error.strict_match?(attribute, type, **options) } else messages_for(attribute).include?(type) end end
as_json(選項 = nil) 連結
傳回一個 Hash
,可用作此物件的 JSON 表示。你可以傳遞 :full_messages
選項。這會決定 JSON 物件是否應包含完整訊息(預設為 false)。
person.errors.as_json # => {:name=>["cannot be nil"]}
person.errors.as_json(full_messages: true) # => {:name=>["name cannot be nil"]}
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 247 def as_json(options = nil) to_hash(options && options[:full_messages]) end
attribute_names() 連結
傳回所有錯誤屬性名稱
person.errors.messages # => {:name=>["cannot be nil", "must be specified"]}
person.errors.attribute_names # => [:name]
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 237 def attribute_names @errors.map(&:attribute).uniq.freeze end
clear 連結
清除所有錯誤。不過,清除錯誤並不會讓模型有效。下次執行驗證時(例如,透過 ActiveRecord::Validations#valid?
),如果任何驗證失敗,錯誤集合將會再次填滿。
來源:在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 80
delete(attribute, type = nil, **options) 連結
刪除 key
的訊息。傳回已刪除的訊息。
person.errors[:name] # => ["cannot be nil"]
person.errors.delete(:name) # => ["cannot be nil"]
person.errors[:name] # => []
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 215 def delete(attribute, type = nil, **options) attribute, type, options = normalize_arguments(attribute, type, **options) matches = where(attribute, type, **options) matches.each do |error| @errors.delete(error) end matches.map(&:message).presence end
details() 連結
傳回一個 Hash
,其中包含屬性及其錯誤詳細資料的陣列。
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 276 def details hash = group_by_attribute.transform_values do |errors| errors.map(&:details) end hash.default = EMPTY_ARRAY hash.freeze hash end
each(&block) 連結
逐一迭代每個錯誤物件。
person.errors.add(:name, :too_short, count: 2)
person.errors.each do |error|
# Will yield <#ActiveModel::Error attribute=name, type=too_short,
options={:count=>3}>
end
來源:在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 67
full_message(attribute, message) 連結
傳回給定屬性的完整訊息。
person.errors.full_message(:name, 'is invalid') # => "Name is invalid"
來源: 顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 451 def full_message(attribute, message) Error.full_message(attribute, message, @base) end
full_messages() 連結
傳回陣列中所有完整的錯誤訊息。
class Person
validates_presence_of :name, :address, :email
validates_length_of :name, in: 5..30
end
person = Person.create(address: '123 First St.')
person.errors.full_messages
# => ["Name is too short (minimum is 5 characters)", "Name can't be blank", "Email can't be blank"]
來源: 顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 415 def full_messages @errors.map(&:full_message) end
full_messages_for(attribute) 連結
傳回給定屬性在陣列中所有完整的錯誤訊息。
class Person
validates_presence_of :name, :email
validates_length_of :name, in: 5..30
end
person = Person.create()
person.errors.full_messages_for(:name)
# => ["Name is too short (minimum is 5 characters)", "Name can't be blank"]
來源: 顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 430 def full_messages_for(attribute) where(attribute).map(&:full_message).freeze end
generate_message(attribute, type = :invalid, options = {}) 連結
在預設範圍 (activemodel.errors.messages
) 中翻譯錯誤訊息。
Error
訊息會先在 activemodel.errors.models.MODEL.attributes.ATTRIBUTE.MESSAGE
中查詢,如果沒有找到,會在 activemodel.errors.models.MODEL.MESSAGE
中查詢,如果還是沒有找到,會傳回預設訊息的翻譯 (例如 activemodel.errors.messages.MESSAGE
)。已翻譯的模型名稱、已翻譯的屬性名稱和值可供內插。
在模型中使用繼承時,它也會檢查所有繼承的模型,但前提是模型本身尚未找到。假設您有 class Admin < User; end
且您想要 title
屬性的 :blank
錯誤訊息的翻譯,它會尋找以下翻譯
-
activemodel.errors.models.admin.attributes.title.blank
-
activemodel.errors.models.admin.blank
-
activemodel.errors.models.user.attributes.title.blank
-
activemodel.errors.models.user.blank
-
您透過
options
hash (在activemodel.errors
範圍中) 提供的任何預設值 -
activemodel.errors.messages.blank
-
errors.attributes.title.blank
-
errors.messages.blank
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 479 def generate_message(attribute, type = :invalid, options = {}) Error.generate_message(attribute, type, @base, options) end
group_by_attribute() 連結
傳回一個 Hash
,其中包含屬性及其 Error
物件陣列。
person.errors.group_by_attribute
# => {:name=>[<#ActiveModel::Error>, <#ActiveModel::Error>]}
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 289 def group_by_attribute @errors.group_by(&:attribute) end
import(error, override_options = {}) 連結
匯入一個錯誤。匯入的錯誤會包裝為 NestedError
,提供對原始錯誤物件的存取。如果需要覆寫屬性或類型,請使用 override_options
。
選項
-
:attribute
- 覆寫錯誤所屬的屬性。 -
:type
- 覆寫錯誤的類型。
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 154 def import(error, override_options = {}) [:attribute, :type].each do |key| if override_options.key?(key) override_options[key] = override_options[key].to_sym end end @errors.append(NestedError.new(@base, error, override_options)) end
include?(attribute) 連結
如果錯誤訊息包含給定金鑰 attribute
的錯誤,則傳回 true
,否則傳回 false
。
person.errors.messages # => {:name=>["cannot be nil"]}
person.errors.include?(:name) # => true
person.errors.include?(:age) # => false
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 202 def include?(attribute) @errors.any? { |error| error.match?(attribute.to_sym) } end
merge!(other) 連結
合併來自 other
的錯誤,每個 Error
都包裝為 NestedError
。
參數
-
other
-ActiveModel::Errors
執行個體。
範例
person.errors.merge!(other)
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 174 def merge!(other) return errors if equal?(other) other.errors.each { |error| import(error) } end
messages() 連結
傳回一個 Hash
,其中包含具有其錯誤訊息陣列的屬性。
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 268 def messages hash = to_hash hash.default = EMPTY_ARRAY hash.freeze hash end
messages_for(attribute) 連結
傳回給定屬性中所有錯誤訊息,並放入陣列中。
class Person
validates_presence_of :name, :email
validates_length_of :name, in: 5..30
end
person = Person.create()
person.errors.messages_for(:name)
# => ["is too short (minimum is 5 characters)", "can't be blank"]
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 444 def messages_for(attribute) where(attribute).map(&:message) end
of_kind?(attribute, type = :invalid) 連結
如果存在具有給定類型屬性的錯誤,則傳回 true
,否則傳回 false
。type
的處理方式與 add
相同。
person.errors.add :age
person.errors.add :name, :too_long, count: 25
person.errors.of_kind? :age # => true
person.errors.of_kind? :name # => false
person.errors.of_kind? :name, :too_long # => true
person.errors.of_kind? :name, "is too long (maximum is 25 characters)" # => true
person.errors.of_kind? :name, :not_too_long # => false
person.errors.of_kind? :name, "is too long" # => false
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 395 def of_kind?(attribute, type = :invalid) attribute, type = normalize_arguments(attribute, type) if type.is_a? Symbol !where(attribute, type).empty? else messages_for(attribute).include?(type) end end
size 連結
傳回錯誤數目。
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 103 def_delegators :@errors, :each, :clear, :empty?, :size, :uniq!
to_hash(full_messages = false) 連結
傳回一個 Hash
,其中包含具有其錯誤訊息的屬性。如果 full_messages
為 true
,它將包含完整訊息(請參閱 full_message
)。
person.errors.to_hash # => {:name=>["cannot be nil"]}
person.errors.to_hash(true) # => {:name=>["name cannot be nil"]}
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 256 def to_hash(full_messages = false) message_method = full_messages ? :full_message : :message group_by_attribute.transform_values do |errors| errors.map(&message_method) end end
where(attribute, type = nil, **options) 連結
搜尋符合屬性
、類型
或選項
的錯誤。
只會比對提供的參數。
person.errors.where(:name) # => all name errors.
person.errors.where(:name, :too_short) # => all name errors being too short
person.errors.where(:name, :too_short, minimum: 2) # => all name errors being too short and minimum is 2
來源:顯示 | 在 GitHub 上
# File activemodel/lib/active_model/errors.rb, line 189 def where(attribute, type = nil, **options) attribute, type, options = normalize_arguments(attribute, type, **options) @errors.select { |error| error.match?(attribute, type, **options) } end