Interpolations improvements from upstream

This commit is contained in:
Max Melentiev
2018-10-09 15:43:44 +03:00
parent dd37f2eea5
commit 5f3d81c15c
4 changed files with 81 additions and 11 deletions

View File

@@ -35,6 +35,7 @@ require 'paperclip/processor'
require 'paperclip/thumbnail'
require 'paperclip/recursive_thumbnail'
require 'paperclip/storage'
require 'paperclip/interpolations/plural_cache'
require 'paperclip/interpolations'
require 'paperclip/attachment'
require 'paperclip/optimizer'

View File

@@ -1,3 +1,5 @@
# frozen_string_literal: true
module Paperclip
# This module contains all the methods that are available for interpolation
# in paths and urls. To add your own (or override an existing one), you
@@ -6,13 +8,14 @@ module Paperclip
module Interpolations
extend self
# Hash assignment of interpolations. Included only for compatability,
# Hash assignment of interpolations. Included only for compatibility,
# and is not intended for normal use.
def self.[]= name, block
define_method(name, &block)
@interpolators_cache = nil
end
# Hash access of interpolations. Included only for compatability,
# Hash access of interpolations. Included only for compatibility,
# and is not intended for normal use.
def self.[] name
method(name)
@@ -20,17 +23,28 @@ module Paperclip
# Returns a sorted list of all interpolations.
def self.all
self.instance_methods(false).sort
self.instance_methods(false).sort!
end
# Perform the actual interpolation. Takes the pattern to interpolate
# and the arguments to pass, which are the attachment and style name.
# You can pass a method name on your record as a symbol, which should turn
# an interpolation pattern for Paperclip to use.
def self.interpolate pattern, *args
all.reverse.inject( pattern.dup ) do |result, tag|
result.gsub(/:#{tag}/) do |match|
send( tag, *args )
end
pattern = args.first.instance.send(pattern) if pattern.kind_of? Symbol
result = pattern.dup
interpolators_cache.each do |method, token|
result.gsub!(token) { send(method, *args) } if result.include?(token)
end
result
end
def self.interpolators_cache
@interpolators_cache ||= all.reverse!.map! { |method| [method, ":#{method}"] }
end
def self.plural_cache
@plural_cache ||= PluralCache.new
end
# Returns the filename, the same way as ":basename.:extension" would.
@@ -63,13 +77,16 @@ module Paperclip
# Returns the underscored, pluralized version of the class name.
# e.g. "users" for the User class.
def class attachment, style_name
attachment.instance.class.to_s.underscore.pluralize
# NOTE: The arguments need to be optional, because some tools fetch
# all class names. Calling #class will return the expected class.
def class attachment = nil, style_name = nil
return super() if attachment.nil? && style_name.nil?
plural_cache.underscore_and_pluralize_class(attachment.instance.class)
end
# Returns the basename of the file. e.g. "file" for "file.jpg"
def basename attachment, style_name
attachment.original_filename.gsub(/#{File.extname(attachment.original_filename)}$/, "")
File.basename(attachment.original_filename, ".*")
end
# Returns the extension of the file. e.g. "jpg" for "file.jpg"
@@ -94,7 +111,7 @@ module Paperclip
# Returns the pluralized form of the attachment name. e.g.
# "avatars" for an attachment of :avatar
def attachment attachment, style_name
attachment.name.to_s.downcase.pluralize
plural_cache.pluralize_symbol(attachment.name)
end
# Returns the style, or the default style if nil is supplied.

View File

@@ -0,0 +1,18 @@
module Paperclip
module Interpolations
class PluralCache
def initialize
@symbol_cache = {}.compare_by_identity
@klass_cache = {}.compare_by_identity
end
def pluralize_symbol(symbol)
@symbol_cache[symbol] ||= symbol.to_s.downcase.pluralize
end
def underscore_and_pluralize_class(klass)
@klass_cache[klass] ||= klass.name.underscore.pluralize
end
end
end
end

34
test/plural_cache_test.rb Normal file
View File

@@ -0,0 +1,34 @@
require 'test_helper'
class PluralCacheTest < Test::Unit::TestCase
should 'cache pluralizations' do
cache = Paperclip::Interpolations::PluralCache.new
symbol = :box
first = cache.pluralize_symbol(symbol)
second = cache.pluralize_symbol(symbol)
assert_equal first, second
end
should 'cache pluralizations and underscores' do
class BigBox ; end
cache = Paperclip::Interpolations::PluralCache.new
klass = BigBox
first = cache.underscore_and_pluralize_class(klass)
second = cache.underscore_and_pluralize_class(klass)
assert_equal first, second
end
should 'pluralize words' do
cache = Paperclip::Interpolations::PluralCache.new
assert_equal 'boxes', cache.pluralize_symbol(:box)
end
should 'pluralize and underscore words' do
class BigBox ; end
cache = Paperclip::Interpolations::PluralCache.new
klass = BigBox
assert_equal 'plural_cache_test/big_boxes', cache.underscore_and_pluralize_class(klass)
end
end