Add ImageValidator
This commit is contained in:
parent
25a06b1ce1
commit
da7d84ba51
7 changed files with 85 additions and 36 deletions
|
@ -6,14 +6,6 @@ class Account < ApplicationRecord
|
||||||
|
|
||||||
NICKNAME_RE = /\A[a-z][_a-z0-9]*[a-z0-9]\z/.freeze
|
NICKNAME_RE = /\A[a-z][_a-z0-9]*[a-z0-9]\z/.freeze
|
||||||
|
|
||||||
AVATAR_MAX_SIZE = 1.megabyte
|
|
||||||
|
|
||||||
AVATAR_CONTENT_TYPES = %w[
|
|
||||||
image/png
|
|
||||||
image/jpeg
|
|
||||||
image/gif
|
|
||||||
].freeze
|
|
||||||
|
|
||||||
self.role_cname = 'Role'
|
self.role_cname = 'Role'
|
||||||
self.role_table_name = 'roles'
|
self.role_table_name = 'roles'
|
||||||
self.strict_rolify = false
|
self.strict_rolify = false
|
||||||
|
@ -76,8 +68,7 @@ class Account < ApplicationRecord
|
||||||
|
|
||||||
validates :biography, allow_nil: true, length: { in: 3..10_000 }
|
validates :biography, allow_nil: true, length: { in: 3..10_000 }
|
||||||
|
|
||||||
validate :avatar_size_is_valid
|
validates :avatar, allow_nil: true, image: true
|
||||||
validate :avatar_content_type_is_valid
|
|
||||||
|
|
||||||
###########
|
###########
|
||||||
# Methods #
|
# Methods #
|
||||||
|
@ -137,18 +128,4 @@ private
|
||||||
self.public_name = public_name&.strip
|
self.public_name = public_name&.strip
|
||||||
self.biography = biography&.strip
|
self.biography = biography&.strip
|
||||||
end
|
end
|
||||||
|
|
||||||
def avatar_size_is_valid
|
|
||||||
return unless avatar.attached?
|
|
||||||
return if avatar.blob.byte_size <= AVATAR_MAX_SIZE
|
|
||||||
|
|
||||||
errors.add :avatar, :size
|
|
||||||
end
|
|
||||||
|
|
||||||
def avatar_content_type_is_valid
|
|
||||||
return unless avatar.attached?
|
|
||||||
return if avatar.blob.content_type.in? AVATAR_CONTENT_TYPES
|
|
||||||
|
|
||||||
errors.add :avatar, :format, content_type: avatar.blob.content_type
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
39
app/validators/application_each_validator.rb
Normal file
39
app/validators/application_each_validator.rb
Normal file
|
@ -0,0 +1,39 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
class ApplicationEachValidator < ActiveModel::EachValidator
|
||||||
|
def validate_each(record, attribute, value)
|
||||||
|
self.class::Validation.new(self, record, attribute, value).call
|
||||||
|
end
|
||||||
|
|
||||||
|
class Validation
|
||||||
|
attr_reader :value
|
||||||
|
|
||||||
|
delegate :options, to: :@validator
|
||||||
|
|
||||||
|
def initialize(validator, record, attribute, value)
|
||||||
|
@validator = validator
|
||||||
|
@record = record
|
||||||
|
@attribute = attribute
|
||||||
|
@value = value
|
||||||
|
end
|
||||||
|
|
||||||
|
def call
|
||||||
|
catch :stop_validating do
|
||||||
|
perform
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def perform
|
||||||
|
raise NotImplementedError, "#{self.class}#perform"
|
||||||
|
end
|
||||||
|
|
||||||
|
def error(*args)
|
||||||
|
@record.errors.add @attribute, *args
|
||||||
|
end
|
||||||
|
|
||||||
|
def error!(*args)
|
||||||
|
error(*args)
|
||||||
|
throw :stop_validating
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
27
app/validators/image_validator.rb
Normal file
27
app/validators/image_validator.rb
Normal file
|
@ -0,0 +1,27 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
class ImageValidator < ApplicationEachValidator
|
||||||
|
class Validation < Validation
|
||||||
|
MAX_SIZE = 1.megabyte
|
||||||
|
|
||||||
|
CONTENT_TYPES = %w[
|
||||||
|
image/png
|
||||||
|
image/jpeg
|
||||||
|
image/gif
|
||||||
|
].freeze
|
||||||
|
|
||||||
|
delegate :blob, to: :value
|
||||||
|
|
||||||
|
delegate :content_type, :byte_size, to: :blob
|
||||||
|
|
||||||
|
def perform
|
||||||
|
return unless value.attached?
|
||||||
|
|
||||||
|
unless content_type.in? CONTENT_TYPES
|
||||||
|
error :image_format, content_type: content_type
|
||||||
|
end
|
||||||
|
|
||||||
|
error :image_size unless byte_size <= MAX_SIZE
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
|
@ -41,6 +41,11 @@ module Partynest
|
||||||
# Fully qualified domain name.
|
# Fully qualified domain name.
|
||||||
config.site_domain = 'libertarian-party.com'
|
config.site_domain = 'libertarian-party.com'
|
||||||
|
|
||||||
|
# Custom directories with classes and modules you want to be autoloadable.
|
||||||
|
config.autoload_paths += [
|
||||||
|
config.root.join('app', 'validators'),
|
||||||
|
]
|
||||||
|
|
||||||
# Email which all mail is set from.
|
# Email which all mail is set from.
|
||||||
config.noreply_email_address = "no-reply@#{config.site_domain}"
|
config.noreply_email_address = "no-reply@#{config.site_domain}"
|
||||||
config.noreply_email_contact =
|
config.noreply_email_contact =
|
||||||
|
|
|
@ -108,9 +108,6 @@ en:
|
||||||
unlock_token: Unlock token
|
unlock_token: Unlock token
|
||||||
updated_at: Updated at
|
updated_at: Updated at
|
||||||
errors:
|
errors:
|
||||||
models:
|
messages:
|
||||||
account:
|
image_size: 'has too big size'
|
||||||
attributes:
|
image_format: 'has invalid format: %{content_type}'
|
||||||
avatar:
|
|
||||||
size: 'has too big size'
|
|
||||||
format: 'has invalid format: %{content_type}'
|
|
||||||
|
|
|
@ -108,9 +108,6 @@ ru:
|
||||||
unlock_token: Токен разблокировки
|
unlock_token: Токен разблокировки
|
||||||
updated_at: Дата обновления
|
updated_at: Дата обновления
|
||||||
errors:
|
errors:
|
||||||
models:
|
messages:
|
||||||
account:
|
image_size: 'имеет слишком большой размер'
|
||||||
attributes:
|
image_format: 'имеет неверный формат: %{content_type}'
|
||||||
avatar:
|
|
||||||
size: 'имеет слишком большой размер'
|
|
||||||
format: 'имеет неверный формат: %{content_type}'
|
|
||||||
|
|
7
spec/validators/image_validator_spec.rb
Normal file
7
spec/validators/image_validator_spec.rb
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
require 'rails_helper'
|
||||||
|
|
||||||
|
RSpec.describe ImageValidator do
|
||||||
|
pending "add some examples to (or delete) #{__FILE__}"
|
||||||
|
end
|
Reference in a new issue