kanoko 0.0.4 → 0.1.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/kanoko.gemspec +2 -0
- data/lib/kanoko.rb +5 -3
- data/lib/kanoko/application/convert.rb +67 -29
- data/lib/kanoko/application/convert/function.rb +38 -0
- data/lib/kanoko/version.rb +1 -1
- data/test/resize.jpg +0 -0
- data/test/resize_and_crop.jpg +0 -0
- data/test/src.jpg +0 -0
- data/test/test_application_convert.rb +63 -0
- data/test/test_kanoko.rb +8 -2
- metadata +39 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c507e252c2624f4482ad7e29ac990c0a698300f5
|
4
|
+
data.tar.gz: 416bc6b1987141e93dcb646e83e571434e6bea71
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fc89740eacc7b58c509b2cf8d84405945eb1fb1e3e2dc1eb6cd5a158c5f7f43d7b4719ab1d20de31cb231feb7c18a842f360fc6dad40159fa67c0c7215f92e18
|
7
|
+
data.tar.gz: 0f05b0052f0784639d6a42564bf04ee06b709860cbf6ace572fff11cb145cffaedd692b3eeca3c4096d1ca8a5d013454dec952b1db9a6c11c9a54c53b814dfcf
|
data/kanoko.gemspec
CHANGED
data/lib/kanoko.rb
CHANGED
@@ -1,5 +1,7 @@
|
|
1
1
|
require 'uri'
|
2
2
|
require 'kanoko/configure'
|
3
|
+
require 'kanoko/errors'
|
4
|
+
require 'kanoko/version'
|
3
5
|
|
4
6
|
module Kanoko
|
5
7
|
# example:
|
@@ -19,9 +21,9 @@ module Kanoko
|
|
19
21
|
@configure = value
|
20
22
|
end
|
21
23
|
|
22
|
-
def path_for(
|
23
|
-
hash = make_hash(
|
24
|
-
"/#{hash}/#{
|
24
|
+
def path_for(*function, src)
|
25
|
+
hash = make_hash(*function, src)
|
26
|
+
"/#{hash}/#{function.map{ |i| URI.encode_www_form_component(i) }.join('/')}/#{src}"
|
25
27
|
end
|
26
28
|
module_function :path_for
|
27
29
|
|
@@ -31,14 +31,22 @@ require 'kanoko'
|
|
31
31
|
module Kanoko
|
32
32
|
module Application
|
33
33
|
class Convert < Sinatra::Application
|
34
|
-
|
34
|
+
# /123abc456def=/resize/200x200/crop/100x100/path/to/src
|
35
|
+
get '/:hash/*' do
|
36
|
+
request_uri = URI.parse env["REQUEST_URI"]
|
35
37
|
hash = params[:hash]
|
36
|
-
|
37
|
-
|
38
|
-
|
38
|
+
unless params[:splat]
|
39
|
+
logger.error "invalid url #{request_uri}"
|
40
|
+
return 400
|
41
|
+
end
|
42
|
+
splat = params[:splat][0]
|
43
|
+
function = Function.new splat
|
44
|
+
hint_src = splat[function.to_path.length..-1]
|
45
|
+
hint_index = request_uri.to_s.index(hint_src)
|
46
|
+
src_path = request_uri.to_s[hint_index..-1]
|
39
47
|
|
40
|
-
unless hash == Kanoko.make_hash(
|
41
|
-
logger.error "hash check failed #{[
|
48
|
+
unless hash == Kanoko.make_hash(*(function.to_a.flatten), src_path)
|
49
|
+
logger.error "hash check failed #{[*(function.to_a.flatten), src_path]}"
|
42
50
|
return 400
|
43
51
|
end
|
44
52
|
|
@@ -51,36 +59,59 @@ module Kanoko
|
|
51
59
|
Tempfile.open("src") do |src_file|
|
52
60
|
src_file.write res.body
|
53
61
|
src_file.fdatasync
|
62
|
+
|
54
63
|
Tempfile.open("dst") do |dst_file|
|
55
64
|
default_env = {"OMP_NUM_THREADS" => "1"}
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
65
|
+
command = 'convert'
|
66
|
+
default_options = [
|
67
|
+
'-depth', '8'
|
68
|
+
]
|
69
|
+
options = []
|
70
|
+
|
71
|
+
function.each do |name, arg|
|
72
|
+
func_options = case name.to_sym
|
73
|
+
when :crop
|
74
|
+
[
|
75
|
+
'-crop', arg
|
76
|
+
]
|
77
|
+
|
78
|
+
when :fill
|
79
|
+
[
|
80
|
+
'-gravity', 'north',
|
81
|
+
'-extent', arg,
|
82
|
+
'-background', 'transparent',
|
83
|
+
]
|
84
|
+
|
85
|
+
when :resize
|
86
|
+
[
|
87
|
+
'-define', "jpeg:size=#{arg}",
|
88
|
+
'-thumbnail', arg,
|
89
|
+
]
|
90
|
+
|
91
|
+
else
|
92
|
+
logger.error "undefined func #{name}"
|
93
|
+
return 400
|
94
|
+
end
|
95
|
+
|
96
|
+
options.concat func_options
|
78
97
|
end
|
79
98
|
|
99
|
+
system_command = [
|
100
|
+
default_env,
|
101
|
+
command,
|
102
|
+
default_options,
|
103
|
+
options,
|
104
|
+
src_file.path,
|
105
|
+
dst_file.path
|
106
|
+
].flatten
|
107
|
+
|
108
|
+
result = system *system_command
|
109
|
+
|
80
110
|
unless result
|
81
111
|
logger.error "command fail $?=#{$?.inspect}"
|
82
112
|
return 500
|
83
113
|
end
|
114
|
+
|
84
115
|
dst_file.read
|
85
116
|
end
|
86
117
|
end
|
@@ -113,9 +144,16 @@ module Kanoko
|
|
113
144
|
|
114
145
|
def after_response(res)
|
115
146
|
res.each do |key, value|
|
116
|
-
|
147
|
+
case key.downcase
|
148
|
+
when "status"
|
149
|
+
next
|
150
|
+
else
|
151
|
+
headers[key] ||= value
|
152
|
+
end
|
117
153
|
end
|
118
154
|
end
|
119
155
|
end
|
120
156
|
end
|
121
157
|
end
|
158
|
+
|
159
|
+
require 'kanoko/application/convert/function'
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module Kanoko
|
2
|
+
module Application
|
3
|
+
class Convert
|
4
|
+
class Function
|
5
|
+
include Enumerable
|
6
|
+
extend Forwardable
|
7
|
+
def_delegators :@args, :each, :to_a, :to_h
|
8
|
+
|
9
|
+
def initialize(args)
|
10
|
+
@args = parse args
|
11
|
+
end
|
12
|
+
|
13
|
+
def to_path
|
14
|
+
paths = []
|
15
|
+
@args.each do |func, arg|
|
16
|
+
paths << "/#{func}/#{arg}"
|
17
|
+
end
|
18
|
+
paths.join
|
19
|
+
end
|
20
|
+
|
21
|
+
private
|
22
|
+
|
23
|
+
def parse(args)
|
24
|
+
hash = {}
|
25
|
+
items = args.split('/')
|
26
|
+
items.each_slice(2) do |funcname, arg|
|
27
|
+
if funcname.match(/\./)
|
28
|
+
break
|
29
|
+
else
|
30
|
+
hash[funcname.to_sym] = arg.to_s
|
31
|
+
end
|
32
|
+
end
|
33
|
+
hash
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/lib/kanoko/version.rb
CHANGED
data/test/resize.jpg
ADDED
Binary file
|
Binary file
|
data/test/src.jpg
ADDED
Binary file
|
@@ -0,0 +1,63 @@
|
|
1
|
+
require 'digest/sha1'
|
2
|
+
require 'stringio'
|
3
|
+
require 'minitest/autorun'
|
4
|
+
require "rack/test"
|
5
|
+
require "exifr"
|
6
|
+
require "kanoko/application/convert"
|
7
|
+
|
8
|
+
class TestKanokoApplicationConvert < Minitest::Test
|
9
|
+
include Rack::Test::Methods
|
10
|
+
|
11
|
+
class TestApp < Kanoko::Application::Convert
|
12
|
+
class ResponseMock < Struct.new(:body)
|
13
|
+
end
|
14
|
+
def http_get(uri)
|
15
|
+
ResponseMock.new(File.read "test/src.jpg")
|
16
|
+
end
|
17
|
+
def after_response(res)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def app
|
22
|
+
TestApp.new
|
23
|
+
end
|
24
|
+
|
25
|
+
def setup
|
26
|
+
ENV['RACK_ENV'] = 'test'
|
27
|
+
Kanoko.configure.digest_func = "sha1"
|
28
|
+
Kanoko.configure.secret_key = "test"
|
29
|
+
end
|
30
|
+
|
31
|
+
def assert_jpeg(expected, actual)
|
32
|
+
expected_exif = EXIFR::JPEG.new(StringIO.new(expected))
|
33
|
+
actual_exif = EXIFR::JPEG.new(StringIO.new(actual))
|
34
|
+
assert_equal expected_exif.to_hash, actual_exif.to_hash
|
35
|
+
end
|
36
|
+
|
37
|
+
def test_resize
|
38
|
+
url = Kanoko.path_for(:resize, "10x10", "src.jpg")
|
39
|
+
get url, {}, {"REQUEST_URI" => url}
|
40
|
+
assert last_response.ok?
|
41
|
+
assert 0 < last_response.body.length
|
42
|
+
assert_jpeg File.read("test/resize.jpg"), last_response.body
|
43
|
+
end
|
44
|
+
|
45
|
+
def test_resize_and_crop
|
46
|
+
url = Kanoko.path_for(:resize, "10x10", :crop, "5x5+1+1", "src.jpg")
|
47
|
+
get url, {}, {"REQUEST_URI" => url}
|
48
|
+
assert last_response.ok?
|
49
|
+
assert 0 < last_response.body.length
|
50
|
+
assert_jpeg File.read("test/resize_and_crop.jpg"), last_response.body
|
51
|
+
end
|
52
|
+
|
53
|
+
def test_not_found
|
54
|
+
get "/nothing"
|
55
|
+
assert_equal 404, last_response.status
|
56
|
+
|
57
|
+
post "/nothing"
|
58
|
+
assert_equal 404, last_response.status
|
59
|
+
|
60
|
+
delete "/nothing"
|
61
|
+
assert_equal 404, last_response.status
|
62
|
+
end
|
63
|
+
end
|
data/test/test_kanoko.rb
CHANGED
@@ -26,8 +26,14 @@ class TestKanoko < Minitest::Test
|
|
26
26
|
|
27
27
|
def test_path_for_with_default_hash_proc
|
28
28
|
change_hash_proc(proc{ "aaa" }) do
|
29
|
-
|
30
|
-
assert_equal "/aaa/test_func
|
29
|
+
path = Kanoko.path_for(:test_func, "test_args", "test_path")
|
30
|
+
assert_equal "/aaa/test_func/test_args/test_path", path
|
31
|
+
|
32
|
+
path = Kanoko.path_for(:test_func, "/?-_=!@#<>\\", "/?-_=!@#<>\\")
|
33
|
+
assert_equal "/aaa/test_func/%2F%3F-_%3D%21%40%23%3C%3E%5C//?-_=!@#<>\\", path
|
34
|
+
|
35
|
+
path = Kanoko.path_for(:test_func, "test_args", :test_func2, "test_args2", "test_path")
|
36
|
+
assert_equal "/aaa/test_func/test_args/test_func2/test_args2/test_path", path
|
31
37
|
end
|
32
38
|
end
|
33
39
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: kanoko
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- ksss
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-06-11 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: sinatra
|
@@ -66,6 +66,34 @@ dependencies:
|
|
66
66
|
- - ">="
|
67
67
|
- !ruby/object:Gem::Version
|
68
68
|
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: rack-test
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - ">="
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - ">="
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: exifr
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - ">="
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - ">="
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0'
|
69
97
|
description: kanoko is a active image generater library.
|
70
98
|
email:
|
71
99
|
- co000ri@gmail.com
|
@@ -82,9 +110,14 @@ files:
|
|
82
110
|
- kanoko.gemspec
|
83
111
|
- lib/kanoko.rb
|
84
112
|
- lib/kanoko/application/convert.rb
|
113
|
+
- lib/kanoko/application/convert/function.rb
|
85
114
|
- lib/kanoko/configure.rb
|
86
115
|
- lib/kanoko/errors.rb
|
87
116
|
- lib/kanoko/version.rb
|
117
|
+
- test/resize.jpg
|
118
|
+
- test/resize_and_crop.jpg
|
119
|
+
- test/src.jpg
|
120
|
+
- test/test_application_convert.rb
|
88
121
|
- test/test_configure.rb
|
89
122
|
- test/test_kanoko.rb
|
90
123
|
homepage: https://github.com/spice-life/kanoko
|
@@ -112,5 +145,9 @@ signing_key:
|
|
112
145
|
specification_version: 4
|
113
146
|
summary: kanoko is a active image generater library.
|
114
147
|
test_files:
|
148
|
+
- test/resize.jpg
|
149
|
+
- test/resize_and_crop.jpg
|
150
|
+
- test/src.jpg
|
151
|
+
- test/test_application_convert.rb
|
115
152
|
- test/test_configure.rb
|
116
153
|
- test/test_kanoko.rb
|