imgproxy 2.0.1 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.yardopts +8 -0
- data/CHANGELOG.md +74 -0
- data/README.md +176 -133
- data/UPGRADE.md +136 -0
- data/docs/info_options.md +223 -0
- data/docs/processing_options.md +724 -0
- data/docs/yard/fix_pictures.rb +25 -0
- data/docs/yard/github_alerts.rb +16 -0
- data/docs/yard/relative_markdown_links.rb +31 -0
- data/lib/imgproxy/config.rb +96 -41
- data/lib/imgproxy/extensions/active_storage.rb +6 -4
- data/lib/imgproxy/extensions/shrine.rb +6 -4
- data/lib/imgproxy/option_aliases/info.rb +33 -0
- data/lib/imgproxy/option_aliases/processing.rb +74 -0
- data/lib/imgproxy/options_builders/base.rb +54 -0
- data/lib/imgproxy/options_builders/info.rb +52 -0
- data/lib/imgproxy/options_builders/processing.rb +150 -0
- data/lib/imgproxy/options_casters/adjust.rb +3 -1
- data/lib/imgproxy/options_casters/alpha.rb +27 -0
- data/lib/imgproxy/options_casters/array.rb +3 -1
- data/lib/imgproxy/options_casters/autoquality.rb +28 -0
- data/lib/imgproxy/options_casters/average.rb +27 -0
- data/lib/imgproxy/options_casters/background.rb +27 -0
- data/lib/imgproxy/options_casters/base64.rb +2 -0
- data/lib/imgproxy/options_casters/blur_detections.rb +28 -0
- data/lib/imgproxy/options_casters/blurhash.rb +21 -0
- data/lib/imgproxy/options_casters/bool.rb +3 -1
- data/lib/imgproxy/options_casters/crop.rb +3 -1
- data/lib/imgproxy/options_casters/dominant_colors.rb +27 -0
- data/lib/imgproxy/options_casters/draw_detections.rb +28 -0
- data/lib/imgproxy/options_casters/extend.rb +3 -1
- data/lib/imgproxy/options_casters/filename.rb +31 -0
- data/lib/imgproxy/options_casters/float.rb +4 -2
- data/lib/imgproxy/options_casters/format_quality.rb +19 -0
- data/lib/imgproxy/options_casters/gradient.rb +31 -0
- data/lib/imgproxy/options_casters/gravity.rb +20 -6
- data/lib/imgproxy/options_casters/group.rb +2 -0
- data/lib/imgproxy/options_casters/hashsum.rb +24 -0
- data/lib/imgproxy/options_casters/integer.rb +2 -0
- data/lib/imgproxy/options_casters/jpeg_options.rb +3 -1
- data/lib/imgproxy/options_casters/padding.rb +41 -0
- data/lib/imgproxy/options_casters/png_options.rb +3 -1
- data/lib/imgproxy/options_casters/resize.rb +3 -1
- data/lib/imgproxy/options_casters/size.rb +3 -1
- data/lib/imgproxy/options_casters/string.rb +2 -0
- data/lib/imgproxy/options_casters/trim.rb +3 -1
- data/lib/imgproxy/options_casters/unsharp_masking.rb +25 -0
- data/lib/imgproxy/options_casters/video_thumbnail_tile.rb +34 -0
- data/lib/imgproxy/options_casters/watermark.rb +5 -4
- data/lib/imgproxy/options_casters/watermark_size.rb +21 -0
- data/lib/imgproxy/options_casters/{gif_options.rb → webp_options.rb} +6 -5
- data/lib/imgproxy/options_casters/zoom.rb +27 -0
- data/lib/imgproxy/service_config.rb +111 -0
- data/lib/imgproxy/trim_array.rb +2 -0
- data/lib/imgproxy/url_adapters/active_storage.rb +15 -3
- data/lib/imgproxy/url_adapters/shrine.rb +9 -3
- data/lib/imgproxy/url_adapters.rb +3 -0
- data/lib/imgproxy/url_builders/base.rb +184 -0
- data/lib/imgproxy/url_builders/info.rb +44 -0
- data/lib/imgproxy/url_builders/processing.rb +59 -0
- data/lib/imgproxy/version.rb +3 -1
- data/lib/imgproxy.rb +19 -55
- data/logo/logo-dark.svg +22 -0
- data/logo/logo-light.svg +31 -0
- metadata +74 -35
- data/lib/imgproxy/builder.rb +0 -140
- data/lib/imgproxy/options.rb +0 -115
- data/lib/imgproxy/options_aliases.rb +0 -43
@@ -0,0 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "imgproxy/options_casters/integer"
|
4
|
+
require "imgproxy/options_casters/bool"
|
5
|
+
require "imgproxy/options_casters/extend"
|
6
|
+
|
7
|
+
module Imgproxy
|
8
|
+
module OptionsCasters
|
9
|
+
# Casts `watermark_size` processing option
|
10
|
+
module WatermarkSize
|
11
|
+
def self.cast(raw)
|
12
|
+
return raw unless raw.is_a?(Hash)
|
13
|
+
|
14
|
+
[
|
15
|
+
Imgproxy::OptionsCasters::Integer.cast(raw[:width]) || 0,
|
16
|
+
Imgproxy::OptionsCasters::Integer.cast(raw[:height]) || 0,
|
17
|
+
]
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -1,13 +1,14 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "imgproxy/options_casters/group"
|
2
|
-
require "imgproxy/options_casters/
|
4
|
+
require "imgproxy/options_casters/string"
|
3
5
|
|
4
6
|
module Imgproxy
|
5
7
|
module OptionsCasters
|
6
|
-
# Casts
|
7
|
-
module
|
8
|
+
# Casts `webp_options` processing option
|
9
|
+
module WebpOptions
|
8
10
|
CASTER = Imgproxy::OptionsCasters::Group.new(
|
9
|
-
|
10
|
-
optimize_transparency: Imgproxy::OptionsCasters::Bool,
|
11
|
+
compression: Imgproxy::OptionsCasters::String,
|
11
12
|
).freeze
|
12
13
|
|
13
14
|
def self.cast(raw)
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "imgproxy/trim_array"
|
4
|
+
require "imgproxy/options_casters/float"
|
5
|
+
|
6
|
+
module Imgproxy
|
7
|
+
module OptionsCasters
|
8
|
+
# Casts `zoom` info option
|
9
|
+
module Zoom
|
10
|
+
using TrimArray
|
11
|
+
|
12
|
+
def self.cast(raw)
|
13
|
+
# Allow zoom to be just a float
|
14
|
+
return Imgproxy::OptionsCasters::Float.cast(raw) if raw.is_a?(Numeric)
|
15
|
+
|
16
|
+
return raw unless raw.is_a?(Hash)
|
17
|
+
|
18
|
+
return Imgproxy::OptionsCasters::Float.cast(raw[:zoom_x_y]) if raw.key?(:zoom_x_y)
|
19
|
+
|
20
|
+
[
|
21
|
+
Imgproxy::OptionsCasters::Float.cast(raw[:zoom_x]) || 1,
|
22
|
+
Imgproxy::OptionsCasters::Float.cast(raw[:zoom_y]) || 1,
|
23
|
+
].trim!
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,111 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "anyway_config"
|
4
|
+
|
5
|
+
module Imgproxy
|
6
|
+
# Imgproxy custom config for services
|
7
|
+
#
|
8
|
+
# @!attribute endpoint
|
9
|
+
# imgproxy endpoint
|
10
|
+
# @return [String]
|
11
|
+
# @!attribute key
|
12
|
+
# imgproxy hex-encoded signature key
|
13
|
+
# @return [String]
|
14
|
+
# @!attribute salt
|
15
|
+
# imgproxy hex-encoded signature salt
|
16
|
+
# @return [String]
|
17
|
+
# @!attribute raw_key
|
18
|
+
# Decoded signature key
|
19
|
+
# @return [String]
|
20
|
+
# @!attribute raw_salt
|
21
|
+
# Decoded signature salt
|
22
|
+
# @return [String]
|
23
|
+
# @!attribute signature_size
|
24
|
+
# imgproxy signature size. Defaults to 32
|
25
|
+
# @return [String]
|
26
|
+
# @!attribute source_url_encryption_key
|
27
|
+
# imgproxy hex-encoded source URL encryption key
|
28
|
+
# @return [String]
|
29
|
+
# @!attribute raw_source_url_encryption_key
|
30
|
+
# Decoded source URL encryption key
|
31
|
+
# @return [String]
|
32
|
+
# @!attribute always_encrypt_source_urls
|
33
|
+
# Always encrypt source URLs. Defaults to false
|
34
|
+
# @return [String]
|
35
|
+
#
|
36
|
+
# @see Imgproxy::Config
|
37
|
+
class ServiceConfig < Anyway::Config
|
38
|
+
# Inherit global config values
|
39
|
+
config_name :imgproxy
|
40
|
+
|
41
|
+
attr_config(
|
42
|
+
:endpoint,
|
43
|
+
:key,
|
44
|
+
:salt,
|
45
|
+
:raw_key,
|
46
|
+
:raw_salt,
|
47
|
+
:source_url_encryption_key,
|
48
|
+
:raw_source_url_encryption_key,
|
49
|
+
signature_size: 32,
|
50
|
+
always_encrypt_source_urls: false,
|
51
|
+
)
|
52
|
+
|
53
|
+
coerce_types(
|
54
|
+
endpoint: :string,
|
55
|
+
key: :string,
|
56
|
+
salt: :string,
|
57
|
+
raw_key: :string,
|
58
|
+
raw_salt: :string,
|
59
|
+
signature_size: :integer,
|
60
|
+
source_url_encryption_key: :string,
|
61
|
+
raw_source_url_encryption_key: :string,
|
62
|
+
always_encrypt_source_urls: :boolean,
|
63
|
+
)
|
64
|
+
|
65
|
+
alias_method :set_key, :key=
|
66
|
+
alias_method :set_raw_key, :raw_key=
|
67
|
+
alias_method :set_salt, :salt=
|
68
|
+
alias_method :set_raw_salt, :raw_salt=
|
69
|
+
alias_method :set_source_url_encryption_key, :source_url_encryption_key=
|
70
|
+
alias_method :set_raw_source_url_encryption_key, :raw_source_url_encryption_key=
|
71
|
+
|
72
|
+
private :set_key, :set_raw_key, :set_salt, :set_raw_salt,
|
73
|
+
:set_source_url_encryption_key, :set_raw_source_url_encryption_key
|
74
|
+
|
75
|
+
def key=(value)
|
76
|
+
value = value&.to_s
|
77
|
+
super(value)
|
78
|
+
set_raw_key(value && [value].pack("H*"))
|
79
|
+
end
|
80
|
+
|
81
|
+
def raw_key=(value)
|
82
|
+
value = value&.to_s
|
83
|
+
super(value)
|
84
|
+
set_key(value&.unpack!("H*"))
|
85
|
+
end
|
86
|
+
|
87
|
+
def salt=(value)
|
88
|
+
value = value&.to_s
|
89
|
+
super(value)
|
90
|
+
set_raw_salt(value && [value].pack("H*"))
|
91
|
+
end
|
92
|
+
|
93
|
+
def raw_salt=(value)
|
94
|
+
value = value&.to_s
|
95
|
+
super(value)
|
96
|
+
set_salt(value&.unpack1("H*"))
|
97
|
+
end
|
98
|
+
|
99
|
+
def source_url_encryption_key=(value)
|
100
|
+
value = value&.to_s
|
101
|
+
super(value)
|
102
|
+
set_raw_source_url_encryption_key(value && [value].pack("H*"))
|
103
|
+
end
|
104
|
+
|
105
|
+
def raw_source_url_encryption_key=(value)
|
106
|
+
value = value&.to_s
|
107
|
+
super(value)
|
108
|
+
set_source_url_encryption_key(value&.unpack1("H*"))
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|
data/lib/imgproxy/trim_array.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Imgproxy
|
2
4
|
class UrlAdapters
|
3
5
|
# Adapter for ActiveStorage
|
@@ -24,11 +26,11 @@ module Imgproxy
|
|
24
26
|
private
|
25
27
|
|
26
28
|
def s3_url(image)
|
27
|
-
"s3://#{image.
|
29
|
+
"s3://#{service(image).bucket.name}/#{image.key}"
|
28
30
|
end
|
29
31
|
|
30
32
|
def use_s3_url(image)
|
31
|
-
config.use_s3_urls && image.
|
33
|
+
config.use_s3_urls && service(image).is_a?(::ActiveStorage::Service::S3Service)
|
32
34
|
end
|
33
35
|
|
34
36
|
def gcs_url(image)
|
@@ -36,7 +38,17 @@ module Imgproxy
|
|
36
38
|
end
|
37
39
|
|
38
40
|
def use_gcs_url(image)
|
39
|
-
config.use_gcs_urls && image.
|
41
|
+
config.use_gcs_urls && service(image).is_a?(::ActiveStorage::Service::GCSService)
|
42
|
+
end
|
43
|
+
|
44
|
+
def service(image)
|
45
|
+
unwrap_service(image.service)
|
46
|
+
end
|
47
|
+
|
48
|
+
def unwrap_service(service)
|
49
|
+
return service unless defined?(::ActiveStorage::Service::MirrorService)
|
50
|
+
return service unless service.is_a?(::ActiveStorage::Service::MirrorService)
|
51
|
+
unwrap_service(service.primary)
|
40
52
|
end
|
41
53
|
|
42
54
|
def config
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Imgproxy
|
2
4
|
class UrlAdapters
|
3
5
|
# Adapter for Shrine
|
@@ -16,8 +18,8 @@ module Imgproxy
|
|
16
18
|
return s3_url(image) if use_s3_url(image)
|
17
19
|
|
18
20
|
opts = {}
|
19
|
-
opts[:host] =
|
20
|
-
image.url(opts)
|
21
|
+
opts[:host] = config.shrine_host if config.shrine_host
|
22
|
+
image.url(**opts)
|
21
23
|
end
|
22
24
|
|
23
25
|
private
|
@@ -28,9 +30,13 @@ module Imgproxy
|
|
28
30
|
end
|
29
31
|
|
30
32
|
def use_s3_url(image)
|
31
|
-
|
33
|
+
config.use_s3_urls &&
|
32
34
|
image.storage.is_a?(::Shrine::Storage::S3)
|
33
35
|
end
|
36
|
+
|
37
|
+
def config
|
38
|
+
Imgproxy.config
|
39
|
+
end
|
34
40
|
end
|
35
41
|
end
|
36
42
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "imgproxy/url_adapters/active_storage"
|
2
4
|
require "imgproxy/url_adapters/shrine"
|
3
5
|
|
@@ -11,6 +13,7 @@ module Imgproxy
|
|
11
13
|
# Imgproxy.url_for(user.avatar)
|
12
14
|
class UrlAdapters
|
13
15
|
class NotFound < StandardError; end
|
16
|
+
|
14
17
|
class NotConfigured < StandardError; end
|
15
18
|
|
16
19
|
# @return [Array] Currently added adapters
|
@@ -0,0 +1,184 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "openssl"
|
4
|
+
require "base64"
|
5
|
+
require "erb"
|
6
|
+
|
7
|
+
require "imgproxy/options_builders/base"
|
8
|
+
|
9
|
+
module Imgproxy
|
10
|
+
module UrlBuilders
|
11
|
+
class UnknownServiceError < StandardError; end
|
12
|
+
|
13
|
+
class InvalidEncryptionKeyError < StandardError; end
|
14
|
+
|
15
|
+
# Builds imgproxy URL
|
16
|
+
#
|
17
|
+
# builder = Imgproxy::UrlBuilders::Base.new(
|
18
|
+
# width: 500,
|
19
|
+
# height: 400,
|
20
|
+
# resizing_type: :fill,
|
21
|
+
# sharpen: 0.5
|
22
|
+
# )
|
23
|
+
#
|
24
|
+
# builder.url_for("http://images.example.com/images/image1.jpg")
|
25
|
+
# builder.url_for("http://images.example.com/images/image2.jpg")
|
26
|
+
class Base
|
27
|
+
OPTIONS_BUILDER = OptionsBuilders::Base
|
28
|
+
OPTION_ALIASES = {}.freeze
|
29
|
+
|
30
|
+
# @param [Hash] options imgproxy URL options
|
31
|
+
# @see Imgproxy.url_for
|
32
|
+
# @see Imgproxy.info_url_for
|
33
|
+
def initialize(options = {})
|
34
|
+
options = options.dup
|
35
|
+
|
36
|
+
extract_builder_options(options)
|
37
|
+
|
38
|
+
@options = self.class::OPTIONS_BUILDER.new(options)
|
39
|
+
end
|
40
|
+
|
41
|
+
# Genrates imgproxy URL
|
42
|
+
#
|
43
|
+
# @return [String] imgproxy URL
|
44
|
+
# @param [String,URI, Object] _image Source image URL or object applicable for
|
45
|
+
# the configured URL adapters
|
46
|
+
# @see Imgproxy.url_for
|
47
|
+
# @see Imgproxy.info_url_for
|
48
|
+
def url_for(_image)
|
49
|
+
raise NotImplementedError
|
50
|
+
end
|
51
|
+
|
52
|
+
private
|
53
|
+
|
54
|
+
attr_reader :service
|
55
|
+
|
56
|
+
NEED_ESCAPE_RE = /[@?% ]|[^\p{Ascii}]/.freeze
|
57
|
+
AES_SIZES = {32 => 256, 24 => 196, 16 => 128}.freeze
|
58
|
+
|
59
|
+
def extract_builder_options(options)
|
60
|
+
@service = options.delete(:service)&.to_sym || :default
|
61
|
+
|
62
|
+
@use_short_options =
|
63
|
+
not_nil_or(options.delete(:use_short_options), config.use_short_options)
|
64
|
+
@base64_encode_url =
|
65
|
+
not_nil_or(options.delete(:base64_encode_url), config.base64_encode_urls)
|
66
|
+
@escape_plain_url =
|
67
|
+
not_nil_or(options.delete(:escape_plain_url), config.always_escape_plain_urls)
|
68
|
+
@encrypt_source_url =
|
69
|
+
not_nil_or(options.delete(:encrypt_source_url), service_config.always_encrypt_source_urls)
|
70
|
+
@source_url_encryption_iv = options.delete(:source_url_encryption_iv)
|
71
|
+
end
|
72
|
+
|
73
|
+
def option_strings
|
74
|
+
@option_strings ||= @options.map do |key, value|
|
75
|
+
[option_alias(key), value].join(":")
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
def sourcce_url(image, ext: nil)
|
80
|
+
url = config.url_adapters.url_of(image)
|
81
|
+
|
82
|
+
return encrypted_sourcce_url_for(url, ext: ext) if @encrypt_source_url
|
83
|
+
return base64_sourcce_url_for(url, ext: ext) if @base64_encode_url
|
84
|
+
plain_url_for(url, ext: ext)
|
85
|
+
end
|
86
|
+
|
87
|
+
def plain_url_for(url, ext: nil)
|
88
|
+
escaped_url = need_escape_url?(url) ? ERB::Util.url_encode(url) : url
|
89
|
+
|
90
|
+
ext ? "plain/#{escaped_url}@#{ext}" : "plain/#{escaped_url}"
|
91
|
+
end
|
92
|
+
|
93
|
+
def base64_sourcce_url_for(url, ext: nil)
|
94
|
+
encoded_url = Base64.urlsafe_encode64(url).tr("=", "").scan(/.{1,16}/).join("/")
|
95
|
+
|
96
|
+
ext ? "#{encoded_url}.#{ext}" : encoded_url
|
97
|
+
end
|
98
|
+
|
99
|
+
def encrypted_sourcce_url_for(url, ext: nil)
|
100
|
+
cipher = build_cipher
|
101
|
+
|
102
|
+
iv = @source_url_encryption_iv || cipher.random_iv
|
103
|
+
cipher.iv = iv
|
104
|
+
|
105
|
+
"enc/#{base64_sourcce_url_for(iv + cipher.update(url) + cipher.final, ext: ext)}"
|
106
|
+
end
|
107
|
+
|
108
|
+
def need_escape_url?(url)
|
109
|
+
@escape_plain_url || url.match?(NEED_ESCAPE_RE)
|
110
|
+
end
|
111
|
+
|
112
|
+
def build_cipher
|
113
|
+
key = encryption_key.to_s
|
114
|
+
|
115
|
+
aes_size = AES_SIZES.fetch(key.length) do
|
116
|
+
raise Imgproxy::UrlBuilders::InvalidEncryptionKeyError,
|
117
|
+
"Encryption key should be 16/24/32 bytes long, now - #{key.length}"
|
118
|
+
end
|
119
|
+
|
120
|
+
OpenSSL::Cipher::AES.new(aes_size, :CBC).tap do |cipher|
|
121
|
+
cipher.encrypt
|
122
|
+
cipher.key = key
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
def option_alias(name)
|
127
|
+
return name unless @use_short_options
|
128
|
+
|
129
|
+
self.class::OPTION_ALIASES.fetch(name, name)
|
130
|
+
end
|
131
|
+
|
132
|
+
def sign_path(path)
|
133
|
+
return "unsafe" unless ready_to_sign?
|
134
|
+
|
135
|
+
digest = OpenSSL::HMAC.digest(
|
136
|
+
OpenSSL::Digest.new("sha256"),
|
137
|
+
signature_key,
|
138
|
+
"#{signature_salt}/#{path}",
|
139
|
+
)[0, signature_size]
|
140
|
+
|
141
|
+
Base64.urlsafe_encode64(digest).tr("=", "")
|
142
|
+
end
|
143
|
+
|
144
|
+
def ready_to_sign?
|
145
|
+
!(signature_key.nil? || signature_salt.nil? ||
|
146
|
+
signature_key.empty? || signature_salt.empty?)
|
147
|
+
end
|
148
|
+
|
149
|
+
def signature_key
|
150
|
+
service_config.raw_key
|
151
|
+
end
|
152
|
+
|
153
|
+
def signature_salt
|
154
|
+
service_config.raw_salt
|
155
|
+
end
|
156
|
+
|
157
|
+
def signature_size
|
158
|
+
service_config.signature_size
|
159
|
+
end
|
160
|
+
|
161
|
+
def encryption_key
|
162
|
+
service_config.raw_source_url_encryption_key
|
163
|
+
end
|
164
|
+
|
165
|
+
def not_nil_or(value, fallback)
|
166
|
+
value.nil? ? fallback : value
|
167
|
+
end
|
168
|
+
|
169
|
+
def endpoint
|
170
|
+
service_config.endpoint
|
171
|
+
end
|
172
|
+
|
173
|
+
def service_config
|
174
|
+
@service_config ||= config.services[service].tap do |c|
|
175
|
+
raise Imgproxy::UrlBuilders::UnknownServiceError, service unless c
|
176
|
+
end
|
177
|
+
end
|
178
|
+
|
179
|
+
def config
|
180
|
+
Imgproxy.config
|
181
|
+
end
|
182
|
+
end
|
183
|
+
end
|
184
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "imgproxy/option_aliases/info"
|
4
|
+
require "imgproxy/options_builders/info"
|
5
|
+
require "imgproxy/url_builders/base"
|
6
|
+
|
7
|
+
module Imgproxy
|
8
|
+
module UrlBuilders
|
9
|
+
# Builds imgproxy info URL
|
10
|
+
#
|
11
|
+
# builder = Imgproxy::UrlBuilders::Info.new(
|
12
|
+
# width: 500,
|
13
|
+
# height: 400,
|
14
|
+
# resizing_type: :fill,
|
15
|
+
# sharpen: 0.5
|
16
|
+
# )
|
17
|
+
#
|
18
|
+
# builder.url_for("http://images.example.com/images/image1.jpg")
|
19
|
+
# builder.url_for("http://images.example.com/images/image2.jpg")
|
20
|
+
class Info < Base
|
21
|
+
OPTIONS_BUILDER = OptionsBuilders::Info
|
22
|
+
OPTION_ALIASES = Imgproxy::OptionAliases::INFO
|
23
|
+
|
24
|
+
# @param [Hash] options Info options
|
25
|
+
# @see Imgproxy.info_url_for
|
26
|
+
def initialize(options = {})
|
27
|
+
super
|
28
|
+
end
|
29
|
+
|
30
|
+
# Genrates imgproxy info URL
|
31
|
+
#
|
32
|
+
# @return [String] imgproxy info URL
|
33
|
+
# @param [String,URI, Object] image Source image URL or object applicable for
|
34
|
+
# the configured URL adapters
|
35
|
+
# @see Imgproxy.info_url_for
|
36
|
+
def url_for(image)
|
37
|
+
path = [*option_strings, sourcce_url(image)].join("/")
|
38
|
+
signature = sign_path(path)
|
39
|
+
|
40
|
+
File.join(endpoint.to_s, "info", signature, path)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,59 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "imgproxy/option_aliases/processing"
|
4
|
+
require "imgproxy/options_builders/processing"
|
5
|
+
require "imgproxy/url_builders/base"
|
6
|
+
|
7
|
+
module Imgproxy
|
8
|
+
module UrlBuilders
|
9
|
+
# Builds imgproxy URL
|
10
|
+
#
|
11
|
+
# builder = Imgproxy::UrlBuilders::Processing.new(
|
12
|
+
# width: 500,
|
13
|
+
# height: 400,
|
14
|
+
# resizing_type: :fill,
|
15
|
+
# sharpen: 0.5
|
16
|
+
# )
|
17
|
+
#
|
18
|
+
# builder.url_for("http://images.example.com/images/image1.jpg")
|
19
|
+
# builder.url_for("http://images.example.com/images/image2.jpg")
|
20
|
+
class Processing < Base
|
21
|
+
OPTIONS_BUILDER = OptionsBuilders::Processing
|
22
|
+
OPTION_ALIASES = Imgproxy::OptionAliases::PROCESSING
|
23
|
+
|
24
|
+
# @param [Hash] options Processing options
|
25
|
+
# @see Imgproxy.url_for
|
26
|
+
def initialize(options = {})
|
27
|
+
super(options)
|
28
|
+
|
29
|
+
@format = @options.delete(:format)
|
30
|
+
end
|
31
|
+
|
32
|
+
# Genrates imgproxy URL
|
33
|
+
#
|
34
|
+
# @return [String] imgproxy URL
|
35
|
+
# @param [String,URI, Object] image Source image URL or object applicable for
|
36
|
+
# the configured URL adapters
|
37
|
+
# @see Imgproxy.url_for
|
38
|
+
def url_for(image)
|
39
|
+
path = [*option_strings, sourcce_url(image, ext: @format)].join("/")
|
40
|
+
signature = sign_path(path)
|
41
|
+
|
42
|
+
File.join(endpoint.to_s, signature, path)
|
43
|
+
end
|
44
|
+
|
45
|
+
# # Genrates imgproxy info URL
|
46
|
+
# #
|
47
|
+
# # @return [String] imgproxy info URL
|
48
|
+
# # @param [String,URI, Object] image Source image URL or object applicable for
|
49
|
+
# # the configured URL adapters
|
50
|
+
# # @see Imgproxy.info_url_for
|
51
|
+
# def info_url_for(image)
|
52
|
+
# path = url(image)
|
53
|
+
# signature = sign_path(path)
|
54
|
+
|
55
|
+
# File.join(endpoint.to_s, "info", signature, path)
|
56
|
+
# end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
data/lib/imgproxy/version.rb
CHANGED
data/lib/imgproxy.rb
CHANGED
@@ -1,6 +1,9 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "imgproxy/version"
|
2
4
|
require "imgproxy/config"
|
3
|
-
require "imgproxy/
|
5
|
+
require "imgproxy/url_builders/processing"
|
6
|
+
require "imgproxy/url_builders/info"
|
4
7
|
|
5
8
|
require "imgproxy/extensions/active_storage"
|
6
9
|
require "imgproxy/extensions/shrine"
|
@@ -58,69 +61,30 @@ module Imgproxy
|
|
58
61
|
# @return [String] imgproxy URL
|
59
62
|
# @param [String,URI, Object] image Source image URL or object applicable for
|
60
63
|
# the configured URL adapters
|
61
|
-
# @param [Hash] options Processing options
|
62
|
-
#
|
63
|
-
# @option options [Hash|Array|String] :size
|
64
|
-
# @option options [String] :resizing_type
|
65
|
-
# @option options [String] :resizing_algorithm supported only by imgproxy pro
|
66
|
-
# @option options [Integer] :width
|
67
|
-
# @option options [Integer] :height
|
68
|
-
# @option options [Float] :dpr
|
69
|
-
# @option options [Boolean] :enlarge
|
70
|
-
# @option options [Hash|Array|Boolean|String] :extend
|
71
|
-
# @option options [Hash|Array|String] :gravity
|
72
|
-
# @option options [Hash|Array|String] :crop
|
73
|
-
# @option options [Array] :padding
|
74
|
-
# @option options [Hash|Array|String] :trim
|
75
|
-
# @option options [Integer] :rotate
|
76
|
-
# @option options [Integer] :quality
|
77
|
-
# @option options [Integer] :max_bytes
|
78
|
-
# @option options [Array|String] :background
|
79
|
-
# @option options [Float] :background_alpha supported only by imgproxy pro
|
80
|
-
# @option options [Hash|Array|String] :adjust
|
81
|
-
# @option options [Integer] :brightness supported only by imgproxy pro
|
82
|
-
# @option options [Float] :contrast supported only by imgproxy pro
|
83
|
-
# @option options [Float] :saturation supported only by imgproxy pro
|
84
|
-
# @option options [Float] :blur
|
85
|
-
# @option options [Float] :sharpen
|
86
|
-
# @option options [Integer] :pixelate supported only by imgproxy pro
|
87
|
-
# @option options [String] :unsharpening supported only by imgproxy pro
|
88
|
-
# @option options [Hash|Array|Float|String] :watermark
|
89
|
-
# @option options [String] :watermark_url supported only by imgproxy pro
|
90
|
-
# @option options [String] :style supported only by imgproxy pro
|
91
|
-
# @option options [Hash|Array|String] :jpeg_options supported only by imgproxy pro
|
92
|
-
# @option options [Hash|Array|String] :png_options supported only by imgproxy pro
|
93
|
-
# @option options [Hash|Array|String] :gif_options supported only by imgproxy pro
|
94
|
-
# @option options [Integer] :page supported only by imgproxy pro
|
95
|
-
# @option options [Integer] :video_thumbnail_second supported only by imgproxy pro
|
96
|
-
# @option options [Array] :preset
|
97
|
-
# @option options [String] :cachebuster
|
98
|
-
# @option options [Boolean] :strip_metadata
|
99
|
-
# @option options [Boolean] :strip_color_profile
|
100
|
-
# @option options [Boolean] :auto_rotate
|
101
|
-
# @option options [String] :filename
|
102
|
-
# @option options [String] :format
|
103
|
-
# @option options [Boolean] :use_short_options
|
104
|
-
# @option options [Boolean] :base64_encode_urls
|
105
|
-
# @option options [Boolean] :escape_plain_url
|
106
|
-
# @see https://docs.imgproxy.net/#/generating_the_url_advanced?id=processing-options
|
107
|
-
# Available imgproxy URL processing options and their arguments
|
64
|
+
# @param [Hash] options Processing options.
|
65
|
+
# See: {file:docs/processing_options.md Supported processing options}
|
108
66
|
def url_for(image, options = {})
|
109
|
-
Imgproxy::
|
67
|
+
Imgproxy::UrlBuilders::Processing.new(options).url_for(image)
|
110
68
|
end
|
111
69
|
|
112
|
-
# Genrates imgproxy info URL. Supported only by imgproxy
|
70
|
+
# Genrates imgproxy info URL. Supported only by imgproxy Pro
|
113
71
|
#
|
114
|
-
# Imgproxy.info_url_for(
|
72
|
+
# Imgproxy.info_url_for(
|
73
|
+
# "http://images.example.com/images/image.jpg",
|
74
|
+
# alpha: {
|
75
|
+
# alpha: true,
|
76
|
+
# check_transparency: true
|
77
|
+
# },
|
78
|
+
# palette: 128,
|
79
|
+
# )
|
115
80
|
#
|
116
81
|
# @return [String] imgproxy info URL
|
117
82
|
# @param [String,URI, Object] image Source image URL or object applicable for
|
118
83
|
# the configured URL adapters
|
119
|
-
# @param [Hash] options
|
120
|
-
#
|
121
|
-
# @option options [Boolean] :escape_plain_url
|
84
|
+
# @param [Hash] options Info options.
|
85
|
+
# See: {file:docs/info_options.md Supported info options}
|
122
86
|
def info_url_for(image, options = {})
|
123
|
-
Imgproxy::
|
87
|
+
Imgproxy::UrlBuilders::Info.new(options).url_for(image)
|
124
88
|
end
|
125
89
|
|
126
90
|
# Extends +ActiveStorage::Blob+ with {Imgproxy::Extensions::ActiveStorage.imgproxy_url} method
|