httpimagestore 1.7.0 → 1.8.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.
data/Gemfile CHANGED
@@ -1,7 +1,7 @@
1
1
  source "http://rubygems.org"
2
2
  ruby "1.9.3"
3
3
 
4
- gem "unicorn-cuba-base", "~> 1.2.0"
4
+ gem "unicorn-cuba-base", "~> 1.2.2"
5
5
  #gem "unicorn-cuba-base", path: "../unicorn-cuba-base"
6
6
  gem "httpthumbnailer-client", "~> 1.2.0"
7
7
  #gem "httpthumbnailer-client", path: "../httpthumbnailer-client"
@@ -13,7 +13,7 @@ gem "msgpack", "~> 0.5"
13
13
  # Add dependencies to develop your gem here.
14
14
  # Include everything needed to run rake, tests, features, etc.
15
15
  group :development do
16
- gem "httpclient", ">= 2.3"
16
+ gem "faraday", ">= 0.8"
17
17
  gem "rspec", "~> 2.13"
18
18
  gem "cucumber", ">= 0"
19
19
  gem "jeweler", "~> 1.8.4"
data/Gemfile.lock CHANGED
@@ -8,7 +8,7 @@ GEM
8
8
  uuidtools (~> 2.1)
9
9
  builder (3.2.2)
10
10
  cli (1.3.1)
11
- cuba (3.1.1)
11
+ cuba (3.3.0)
12
12
  rack
13
13
  cucumber (1.3.8)
14
14
  builder (>= 2.1.2)
@@ -34,7 +34,7 @@ GEM
34
34
  hashie (2.0.5)
35
35
  highline (1.6.20)
36
36
  httpauth (0.2.0)
37
- httpclient (2.3.4.1)
37
+ httpclient (2.4.0)
38
38
  httpthumbnailer (1.2.0)
39
39
  rmagick (~> 2)
40
40
  unicorn-cuba-base
@@ -91,13 +91,13 @@ GEM
91
91
  rspec-expectations (2.14.2)
92
92
  diff-lcs (>= 1.1.3, < 2.0)
93
93
  rspec-mocks (2.14.3)
94
- ruby-ip (0.9.1)
94
+ ruby-ip (0.9.3)
95
95
  sdl4r (0.9.11)
96
- unicorn (4.8.2)
96
+ unicorn (4.8.3)
97
97
  kgio (~> 2.6)
98
98
  rack
99
99
  raindrops (~> 0.7)
100
- unicorn-cuba-base (1.2.0)
100
+ unicorn-cuba-base (1.2.2)
101
101
  cli (~> 1.3)
102
102
  cuba (~> 3.0)
103
103
  facter (~> 1.6.11)
@@ -113,7 +113,7 @@ DEPENDENCIES
113
113
  aws-sdk (~> 1.10)
114
114
  cucumber
115
115
  daemon (~> 1)
116
- httpclient (>= 2.3)
116
+ faraday (>= 0.8)
117
117
  httpthumbnailer (~> 1.2.0)
118
118
  httpthumbnailer-client (~> 1.2.0)
119
119
  jeweler (~> 1.8.4)
@@ -123,4 +123,4 @@ DEPENDENCIES
123
123
  rdoc (~> 3.9)
124
124
  rspec (~> 2.13)
125
125
  sdl4r (~> 0.9)
126
- unicorn-cuba-base (~> 1.2.0)
126
+ unicorn-cuba-base (~> 1.2.2)
data/README.md CHANGED
@@ -17,6 +17,13 @@ It is using [HTTP Thumbnailer](https://github.com/jpastuszek/httpthumbnailer) as
17
17
 
18
18
  ## Changelog
19
19
 
20
+ ### 1.8.0
21
+ * `output_store_url` support additional arguments: `scheme`, `port` and `host`
22
+ * `output_store_uri` support added
23
+ * fixed `output_store_url` URL formatting for `file_store`
24
+ * fixed parsing of POST body when query string matches are used
25
+ * decoding UTF-8 characters encoded with JavaScript encode() (%uXXXX) to support legacy/broken clients
26
+
20
27
  ### 1.7.0
21
28
  * `output_data_uri_image` support
22
29
  * `source_failover` support
@@ -562,7 +569,7 @@ Putting image data to `/multi` URI will result with image `original` sourced fro
562
569
 
563
570
  #### output_store_url
564
571
 
565
- This is similar statement to `output_store_file` but it will output `file://` URL for file stored images and valid S3 access URL for S3 stored images.
572
+ This is similar statement to `output_store_file` but it will output `file:` URL for file stored images and valid S3 access URL for S3 stored images.
566
573
 
567
574
  For S3 stored image if `ssl` is set to `true` on the S3 client statement (`s3 ssl="true"`) the URL will start with `https://`. If `public` is set to `true` when storing image in S3 (`store_s3 public="true"`) then the URL will not contain query string options, otherwise authentication tokens and expiration token (set to expire in 20 years) will be include in the query string.
568
575
 
@@ -575,7 +582,10 @@ Arguments:
575
582
 
576
583
  Options:
577
584
 
578
- * `path` - name of predefined path that will be used to generate output URL path part; `#{path}` variable and all derivative will be replaced with given image storage path; if not specified the original URL will be provided
585
+ * `scheme` - rewrite URL scheme with provided one; variables can be used; `#{path}` variable and all derivative will be replaced with given image storage path; `#{url}` variable will contain full original URL
586
+ * `host` - add/rewrite provided host to the URL; variables can be used; `#{path}` variable and all derivative will be replaced with given image storage path; `#{url}` variable will contain full original URL
587
+ * `port` - add provided port to the URL; variables can be used; `#{path}` variable and all derivative will be replaced with given image storage path; `#{url}` variable will contain full original URL
588
+ * `path` - name of predefined path that will be used to generate output URL path part; `#{path}` variable and all derivative will be replaced with given image storage path; if not specified the original URL will be provided; `#{url}` variable will contain full original URL
579
589
 
580
590
  Example:
581
591
 
@@ -611,9 +621,54 @@ http://mybucket.s3.amazonaws.com/4006450256177f4a/small.jpg
611
621
  http://mybucket.s3.amazonaws.com/4006450256177f4a/tiny_png.png
612
622
  ```
613
623
 
614
- #### output_source_file and output_source_url
624
+ #### output_store_uri
625
+
626
+ This is similar statement to `output_store_url` but it will output only path component of the URL for stored images.
627
+
628
+ The `Content-Type` header of this response is `text/uri-list`.
629
+ Each output URL is `\r\n` ended.
630
+
631
+ Arguments:
632
+
633
+ 1. image names - names of images
634
+
635
+ Options:
615
636
 
616
- This statements are similar to their storage variants. The difference is that they will output path and URL of the source locations.
637
+ * `path` - name of predefined path that will be used to generate output URL path part; `#{path}` variable and all derivative will be replaced with given image storage path; if not specified the original URL will be provided; `#{url}` variable will contain full original URL
638
+
639
+ Example:
640
+
641
+ ```sdl
642
+ s3 key="AIAITCKMELYWQZPJP7HQ" secret="V37lCu0F48Tv9s7QVqIT/sLf/wwqhNSB4B0Em7Ei" ssl=false
643
+
644
+ path "hash" "#{input_digest}.#{image_mime_extension}"
645
+ path "hash-name" "#{input_digest}/#{image_name}.#{image_mime_extension}"
646
+
647
+ put "thumbnail" {
648
+ thumbnail "input" {
649
+ "small" operation="crop" width=128 height=128 format="jpeg"
650
+ "tiny_png" operation="crop" width=32 height=32 format="png"
651
+ }
652
+
653
+ store_s3 "input" bucket="mybucket" path="hash" public=true
654
+ store_s3 "small" bucket="mybucket" path="hash-name" public=true
655
+ store_s3 "tiny_png" bucket="mybucket" path="hash-name" public=true
656
+
657
+ output_store_uri {
658
+ "input"
659
+ "small"
660
+ "tiny_png"
661
+ }
662
+ }
663
+ ```
664
+
665
+ Putting image data will result in storage of that image and two thumbnails generated from it. The output will contain `\r\n` ended lines like:
666
+
667
+ ```
668
+ /4006450256177f4a.jpg
669
+ /4006450256177f4a/small.jpg
670
+ /4006450256177f4a/tiny_png.png
671
+ ```
617
672
 
618
673
  ### API endpoint meta options
619
674
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.7.0
1
+ 1.8.0
@@ -130,7 +130,7 @@ Feature: Image list based thumbnailing and S3 storage
130
130
  Given there is no test/图像/4006450256177f4a/测试.jpg file in S3 bucket
131
131
  And there is no test/图像/4006450256177f4a/测试-small.jpg file in S3 bucket
132
132
  Given test.jpg file content as request body
133
- When I do PUT request http://localhost:3000/thumbnail/small/test/图像/测试
133
+ When I do PUT request with encoded URL http://localhost:3000/thumbnail/small/test/图像/测试
134
134
  Then response status will be 200
135
135
  And response content type will be text/uri-list
136
136
  And response body will be CRLF ended lines
@@ -138,8 +138,8 @@ Feature: Image list based thumbnailing and S3 storage
138
138
  http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/%E5%9B%BE%E5%83%8F/4006450256177f4a/%E6%B5%8B%E8%AF%95.jpg
139
139
  http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/%E5%9B%BE%E5%83%8F/4006450256177f4a/%E6%B5%8B%E8%AF%95-small.jpg
140
140
  """
141
- And http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/图像/4006450256177f4a/测试.jpg will contain JPEG image of size 509x719
142
- And http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/图像/4006450256177f4a/测试-small.jpg will contain JPEG image of size 128x128
141
+ And Encoded URL http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/图像/4006450256177f4a/测试.jpg will contain JPEG image of size 509x719
142
+ And Encoded URL http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/test/图像/4006450256177f4a/测试-small.jpg will contain JPEG image of size 128x128
143
143
 
144
144
  @compatibility @forward @test
145
145
  Scenario: Getting thumbanils requested with compatibility API from flexi bucket
@@ -0,0 +1,35 @@
1
+ Feature: Encoded UTF-8 URI support
2
+ HTTP Image Store should be able to decode UTF-8 characters form URI using URI decode and also support JavaScript encode() format.
3
+
4
+ Background:
5
+ Given httpthumbnailer server is running at http://localhost:3100/health_check
6
+ Given httpimagestore server is running at http://localhost:3000/health_check with the following configuration
7
+ """
8
+ path "path" "#{path}"
9
+
10
+ post "encoding" "encoded" {
11
+ store_file "input" root="/tmp" path="path"
12
+ output_store_uri "input" path="path"
13
+ }
14
+
15
+ post "encoding" "decoded" {
16
+ store_file "input" root="/tmp" path="path"
17
+ output_store_path "input" path="path"
18
+ }
19
+ """
20
+
21
+ Scenario: JavaScript encode() + URL encoded variable decoding and URL encoding
22
+ Given test.png file content as request body
23
+ When I do POST request http://localhost:3000/encoding/encoded/triple%20kro%25u0301l.png
24
+ And response body will be CRLF ended lines
25
+ """
26
+ /triple%20kro%CC%81l.png
27
+ """
28
+
29
+ Scenario: URL encoded variable decoding
30
+ Given test.png file content as request body
31
+ When I do POST request http://localhost:3000/encoding/decoded/triple%20kr%C3%B3l.png
32
+ And response body will be CRLF ended lines
33
+ """
34
+ triple król.png
35
+ """
@@ -217,6 +217,17 @@ Feature: Error handling
217
217
  invalid UTF-8 encoding in URI: "hello\\xE9world"
218
218
  """
219
219
 
220
+ @error-reporting
221
+ Scenario: Bad URI encoding + JavaScript encode
222
+ Given test.jpg file content as request body
223
+ When I do POST request http://localhost:3000/filename/triple%20kro%25udfcfl.png
224
+ Then response status will be 400
225
+ And response content type will be text/plain
226
+ And response body will be CRLF ended lines like
227
+ """
228
+ invalid UTF-8 encoding in URI: "triple kro\\xED\\xBF\\x8Fl"
229
+ """
230
+
220
231
  @error-reporting
221
232
  Scenario: Zero body length
222
233
  Given test.empty file content as request body
@@ -0,0 +1,122 @@
1
+ Feature: Rewrite of the output path and URL
2
+ Output path or URL can be rewritten with variables to customise further the API output.
3
+
4
+ Background:
5
+ Given httpthumbnailer server is running at http://localhost:3100/health_check
6
+ Given httpimagestore server is running at http://localhost:3000/health_check with the following configuration
7
+ """
8
+ path "input_digest" "#{input_digest}"
9
+ path "rewritten" "hello/#{prefix}/#{input_sha256}.jpg"
10
+ path "rewritten-absolute" "/hello/#{prefix}/#{input_sha256}.jpg"
11
+ path "demo" "image/#{input_sha256}.jpg"
12
+
13
+ post "rewrite" "path" "&:prefix" {
14
+ store_file "input" root="/tmp" path="input_digest"
15
+ output_store_path "input" path="rewritten"
16
+ }
17
+
18
+ post "rewrite" "uri" "path" "&:prefix" {
19
+ store_file "input" root="/tmp" path="input_digest"
20
+ output_store_uri "input" path="rewritten"
21
+ }
22
+
23
+ post "rewrite" "uri" "path-absolute" "&:prefix" {
24
+ store_file "input" root="/tmp" path="input_digest"
25
+ output_store_uri "input" path="rewritten-absolute"
26
+ }
27
+
28
+ post "rewrite" "url" "path" "&:prefix" {
29
+ store_file "input" root="/tmp" path="input_digest"
30
+ output_store_url "input" path="rewritten"
31
+ }
32
+
33
+ post "rewrite" "url" "path-absolute" "&:prefix" {
34
+ store_file "input" root="/tmp" path="input_digest"
35
+ output_store_url "input" path="rewritten-absolute"
36
+ }
37
+
38
+ post "rewrite" "url" "scheme" "&:proto" {
39
+ store_file "input" root="/tmp" path="input_digest"
40
+ output_store_url "input" scheme="#{proto}"
41
+ }
42
+
43
+ post "rewrite" "url" "host" "&:target" {
44
+ store_file "input" root="/tmp" path="input_digest"
45
+ output_store_url "input" host="www.#{target}"
46
+ }
47
+
48
+ post "rewrite" "url" "port" "&:number" {
49
+ store_file "input" root="/tmp" path="input_digest"
50
+ output_store_url "input" port="#{number}"
51
+ }
52
+
53
+ post "rewrite" "demo" {
54
+ store_file "input" root="/tmp" path="input_digest"
55
+ output_store_url "input" scheme="ftp" host="example.com" port="21" path="demo"
56
+ }
57
+ """
58
+
59
+ Scenario: Store path rewriting
60
+ Given test.png file content as request body
61
+ When I do POST request http://localhost:3000/rewrite/path?prefix=world
62
+ And response body will be CRLF ended lines
63
+ """
64
+ hello/world/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
65
+ """
66
+
67
+ Scenario: Store URI path rewriting
68
+ Given test.png file content as request body
69
+ When I do POST request http://localhost:3000/rewrite/uri/path?prefix=world
70
+ And response body will be CRLF ended lines
71
+ """
72
+ /hello/world/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
73
+ """
74
+
75
+ Scenario: Store URI path rewriting - absolute path
76
+ Given test.png file content as request body
77
+ When I do POST request http://localhost:3000/rewrite/uri/path-absolute?prefix=world
78
+ And response body will be CRLF ended lines
79
+ """
80
+ /hello/world/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
81
+ """
82
+
83
+ Scenario: Store URL path rewriting
84
+ Given test.png file content as request body
85
+ When I do POST request http://localhost:3000/rewrite/url/path?prefix=world
86
+ And response body will be CRLF ended lines
87
+ """
88
+ file:/hello/world/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
89
+ """
90
+
91
+ Scenario: Store URL path rewriting - absolute path
92
+ Given test.png file content as request body
93
+ When I do POST request http://localhost:3000/rewrite/url/path-absolute?prefix=world
94
+ And response body will be CRLF ended lines
95
+ """
96
+ file:/hello/world/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
97
+ """
98
+
99
+ Scenario: Store URL scheme rewriting
100
+ Given test.png file content as request body
101
+ When I do POST request http://localhost:3000/rewrite/url/host?target=example.com
102
+ And response body will be CRLF ended lines
103
+ """
104
+ file://www.example.com/b0fe25319ba5909a
105
+ """
106
+
107
+ Scenario: Store URL port rewriting
108
+ Given test.png file content as request body
109
+ When I do POST request http://localhost:3000/rewrite/url/port?number=41
110
+ And response body will be CRLF ended lines
111
+ """
112
+ file::41/b0fe25319ba5909a
113
+ """
114
+
115
+ Scenario: Store URL rewriting demo
116
+ Given test.png file content as request body
117
+ When I do POST request http://localhost:3000/rewrite/demo
118
+ And response body will be CRLF ended lines
119
+ """
120
+ ftp://example.com:21/image/b0fe25319ba5909aa97fded546847a96d7fdf26e18715b0cfccfcbee52dce57e.jpg
121
+ """
122
+
@@ -16,7 +16,7 @@ Feature: Store limited original image in S3 and thumbnail based on request
16
16
  put "original" {
17
17
  thumbnail "input" "original" operation="limit" width=100 height=100 format="jpeg" quality=95
18
18
  store_s3 "original" bucket="@AWS_S3_TEST_BUCKET@" path="original-hash" cache-root="/tmp"
19
- output_store_path "original"
19
+ output_store_uri "original"
20
20
  }
21
21
 
22
22
  get "thumbnail" "v1" ":path" ":operation" ":width" ":height" ":options?" {
@@ -38,10 +38,10 @@ Feature: Store limited original image in S3 and thumbnail based on request
38
38
  Given test.jpg file content as request body
39
39
  When I do PUT request http://localhost:3000/original
40
40
  Then response status will be 200
41
- And response content type will be text/plain
41
+ And response content type will be text/uri-list
42
42
  And response body will be CRLF ended lines
43
43
  """
44
- 4006450256177f4a.jpg
44
+ /4006450256177f4a.jpg
45
45
  """
46
46
  Then S3 object 4006450256177f4a.jpg will contain JPEG image of size 71x100
47
47
  When I do GET request http://@AWS_S3_TEST_BUCKET@.s3.amazonaws.com/4006450256177f4a.jpg
@@ -79,4 +79,4 @@ Feature: Store limited original image in S3 and thumbnail based on request
79
79
  Then response status will be 200
80
80
  And response content type will be image/png
81
81
  Then response body will contain PNG image of size 50x50
82
- And that image pixel at 2x2 should be of color green
82
+ And that image pixel at 2x2 should be of color green
@@ -81,9 +81,14 @@ Then /S3 bucket will not contain (.*)/ do |key|
81
81
  @bucket.objects[key].exists?.should_not be_true
82
82
  end
83
83
 
84
- When /I do (.*) request (.*)/ do |method, uri|
84
+ When /I do (.*) request ([^ ]+)$/ do |method, uri|
85
85
  @request_body = nil if method == 'GET'
86
- @response = HTTPClient.new.request(method, uri.replace_s3_variables, nil, @request_body, (@request_headers or {}))
86
+
87
+ @response = request(method, uri, @request_body, (@request_headers or {}))
88
+ end
89
+
90
+ When /I do (.*) request with encoded URL (.*)/ do |method, uri|
91
+ step "I do #{method} request #{URI.encode(uri)}"
87
92
  end
88
93
 
89
94
  Then /response status will be (.*)/ do |status|
@@ -91,11 +96,11 @@ Then /response status will be (.*)/ do |status|
91
96
  end
92
97
 
93
98
  Then /response content type will be (.*)/ do |content_type|
94
- @response.header['Content-Type'].first.should == content_type
99
+ @response.headers['Content-Type'].should == content_type
95
100
  end
96
101
 
97
102
  Then /response Cache-Control will be (.*)/ do |content_type|
98
- @response.header['Cache-Control'].first.should == content_type
103
+ @response.headers['Cache-Control'].should == content_type
99
104
  end
100
105
 
101
106
  Then /response body will be CRLF ended lines like/ do |body|
@@ -110,7 +115,9 @@ Then /response body will be$/ do |body|
110
115
  end
111
116
 
112
117
  Then /response body will be CRLF ended lines$/ do |body|
113
- @response.body.should == body.replace_s3_variables.gsub("\n", "\r\n") + "\r\n"
118
+ res = @response.body.dup
119
+ res.force_encoding('UTF-8')
120
+ res.should == body.replace_s3_variables.gsub("\n", "\r\n") + "\r\n"
114
121
  end
115
122
 
116
123
  Then /(http.*) content type will be (.*)/ do |url, content_type|
@@ -125,7 +132,7 @@ Then /(http.*) ([^ ]+) header will not be set/ do |url, header|
125
132
  get_headers(url.replace_s3_variables)[header].should be_nil
126
133
  end
127
134
 
128
- Then /(http.*) will contain (.*) image of size (.*)x(.*)/ do |url, format, width, height|
135
+ Then /^(http[^ ]+) will contain (.*) image of size (.*)x(.*)/ do |url, format, width, height|
129
136
  data = get(url.replace_s3_variables)
130
137
 
131
138
  @image.destroy! if @image
@@ -136,6 +143,11 @@ Then /(http.*) will contain (.*) image of size (.*)x(.*)/ do |url, format, width
136
143
  @image.rows.should == height.to_i
137
144
  end
138
145
 
146
+
147
+ Then /Encoded URL (http.*) will contain (.*) image of size (.*)x(.*)/ do |url, format, width, height|
148
+ step "#{URI.encode(url)} will contain #{format} image of size #{width}x#{height}"
149
+ end
150
+
139
151
  Then /S3 object (.*) will contain (.*) image of size (.*)x(.*)/ do |key, format, width, height|
140
152
  data = @bucket.objects[key].read
141
153
 
@@ -12,7 +12,7 @@ require 'rspec/expectations'
12
12
 
13
13
  require 'daemon'
14
14
  require 'timeout'
15
- require 'httpclient'
15
+ require 'faraday'
16
16
  require "open3"
17
17
  require "thread"
18
18
  require 'tempfile'
@@ -48,24 +48,26 @@ def script(file)
48
48
  end
49
49
 
50
50
  def http_client
51
- client = HTTPClient.new
52
- #client.debug_dev = STDOUT
53
- client
51
+ @faraday ||= Faraday.new
52
+ end
53
+
54
+ def request(method, uri, body, headers)
55
+ http_client.run_request(method.downcase.to_sym, uri.replace_s3_variables, body, headers || {})
54
56
  end
55
57
 
56
58
  def get(url)
57
- http_client.get_content(URI.encode(url))
59
+ http_client.get(url).body
58
60
  end
59
61
 
60
62
  def get_headers(url)
61
- http_client.get(URI.encode(url)).headers
63
+ http_client.get(url).headers
62
64
  end
63
65
 
64
66
  @@running_cmd = {}
65
67
  def start_server(cmd, pid_file, log_file, test_url)
66
68
  if @@running_cmd[pid_file]
67
69
  return if @@running_cmd[pid_file] == cmd
68
- stop_server(pid_file)
70
+ stop_server(pid_file)
69
71
  end
70
72
 
71
73
  fork do
@@ -85,7 +87,7 @@ def start_server(cmd, pid_file, log_file, test_url)
85
87
  Timeout.timeout(10) do
86
88
  begin
87
89
  get test_url
88
- rescue Errno::ECONNREFUSED
90
+ rescue Faraday::Error::ConnectionFailed
89
91
  sleep 0.1
90
92
  retry
91
93
  end
@@ -96,7 +98,7 @@ def stop_server(pid_file)
96
98
  pid_file = Pathname.new(pid_file)
97
99
  return unless pid_file.exist?
98
100
 
99
- STDERR.puts http_client.get_content("http://localhost:3000/stats") if pid_file.to_s.include? 'httpimagestore'
101
+ #STDERR.puts http_client.get("http://localhost:3000/stats").body if pid_file.to_s.include? 'httpimagestore'
100
102
  pid = pid_file.read.strip.to_i
101
103
 
102
104
  Timeout.timeout(20) do
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = "httpimagestore"
8
- s.version = "1.7.0"
8
+ s.version = "1.8.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Jakub Pastuszek"]
12
- s.date = "2014-07-28"
12
+ s.date = "2014-08-22"
13
13
  s.description = "Thumbnails images using httpthumbnailer and stored data on HTTP server (S3)"
14
14
  s.email = "jpastuszek@gmail.com"
15
15
  s.executables = ["httpimagestore"]
@@ -30,10 +30,12 @@ Gem::Specification.new do |s|
30
30
  "features/cache-control.feature",
31
31
  "features/compatibility.feature",
32
32
  "features/data-uri.feature",
33
+ "features/encoding.feature",
33
34
  "features/error-reporting.feature",
34
35
  "features/flexi.feature",
35
36
  "features/health-check.feature",
36
37
  "features/request-matching.feature",
38
+ "features/rewrite.feature",
37
39
  "features/s3-store-and-thumbnail.feature",
38
40
  "features/source-failover.feature",
39
41
  "features/step_definitions/httpimagestore_steps.rb",
@@ -77,7 +79,8 @@ Gem::Specification.new do |s|
77
79
  "spec/spec_helper.rb",
78
80
  "spec/support/compute.jpg",
79
81
  "spec/support/cuba_response_env.rb",
80
- "spec/support/full.cfg"
82
+ "spec/support/full.cfg",
83
+ "spec/support/utf_string.txt"
81
84
  ]
82
85
  s.homepage = "http://github.com/jpastuszek/httpimagestore"
83
86
  s.licenses = ["MIT"]
@@ -89,13 +92,13 @@ Gem::Specification.new do |s|
89
92
  s.specification_version = 3
90
93
 
91
94
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
92
- s.add_runtime_dependency(%q<unicorn-cuba-base>, ["~> 1.2.0"])
95
+ s.add_runtime_dependency(%q<unicorn-cuba-base>, ["~> 1.2.2"])
93
96
  s.add_runtime_dependency(%q<httpthumbnailer-client>, ["~> 1.2.0"])
94
97
  s.add_runtime_dependency(%q<aws-sdk>, ["~> 1.10"])
95
98
  s.add_runtime_dependency(%q<mime-types>, ["~> 1.17"])
96
99
  s.add_runtime_dependency(%q<sdl4r>, ["~> 0.9"])
97
100
  s.add_runtime_dependency(%q<msgpack>, ["~> 0.5"])
98
- s.add_development_dependency(%q<httpclient>, [">= 2.3"])
101
+ s.add_development_dependency(%q<faraday>, [">= 0.8"])
99
102
  s.add_development_dependency(%q<rspec>, ["~> 2.13"])
100
103
  s.add_development_dependency(%q<cucumber>, [">= 0"])
101
104
  s.add_development_dependency(%q<jeweler>, ["~> 1.8.4"])
@@ -104,13 +107,13 @@ Gem::Specification.new do |s|
104
107
  s.add_development_dependency(%q<prawn>, ["= 0.8.4"])
105
108
  s.add_development_dependency(%q<httpthumbnailer>, ["~> 1.2.0"])
106
109
  else
107
- s.add_dependency(%q<unicorn-cuba-base>, ["~> 1.2.0"])
110
+ s.add_dependency(%q<unicorn-cuba-base>, ["~> 1.2.2"])
108
111
  s.add_dependency(%q<httpthumbnailer-client>, ["~> 1.2.0"])
109
112
  s.add_dependency(%q<aws-sdk>, ["~> 1.10"])
110
113
  s.add_dependency(%q<mime-types>, ["~> 1.17"])
111
114
  s.add_dependency(%q<sdl4r>, ["~> 0.9"])
112
115
  s.add_dependency(%q<msgpack>, ["~> 0.5"])
113
- s.add_dependency(%q<httpclient>, [">= 2.3"])
116
+ s.add_dependency(%q<faraday>, [">= 0.8"])
114
117
  s.add_dependency(%q<rspec>, ["~> 2.13"])
115
118
  s.add_dependency(%q<cucumber>, [">= 0"])
116
119
  s.add_dependency(%q<jeweler>, ["~> 1.8.4"])
@@ -120,13 +123,13 @@ Gem::Specification.new do |s|
120
123
  s.add_dependency(%q<httpthumbnailer>, ["~> 1.2.0"])
121
124
  end
122
125
  else
123
- s.add_dependency(%q<unicorn-cuba-base>, ["~> 1.2.0"])
126
+ s.add_dependency(%q<unicorn-cuba-base>, ["~> 1.2.2"])
124
127
  s.add_dependency(%q<httpthumbnailer-client>, ["~> 1.2.0"])
125
128
  s.add_dependency(%q<aws-sdk>, ["~> 1.10"])
126
129
  s.add_dependency(%q<mime-types>, ["~> 1.17"])
127
130
  s.add_dependency(%q<sdl4r>, ["~> 0.9"])
128
131
  s.add_dependency(%q<msgpack>, ["~> 0.5"])
129
- s.add_dependency(%q<httpclient>, [">= 2.3"])
132
+ s.add_dependency(%q<faraday>, [">= 0.8"])
130
133
  s.add_dependency(%q<rspec>, ["~> 2.13"])
131
134
  s.add_dependency(%q<cucumber>, [">= 0"])
132
135
  s.add_dependency(%q<jeweler>, ["~> 1.8.4"])
@@ -86,7 +86,7 @@ module Configuration
86
86
  FileSourceStoreBase.stats.incr_total_file_source_bytes(data.bytesize)
87
87
 
88
88
  image = Image.new(data)
89
- image.source_url = "file://#{URI.encode(rendered_path.to_s)}"
89
+ image.source_url = URI::Generic.new('file', nil, nil, nil, nil, "/#{URI.encode(rendered_path.to_s)}", nil, nil, nil, URI::DEFAULT_PARSER, true)
90
90
  image
91
91
  rescue Errno::ENOENT
92
92
  raise NoSuchFileError.new(image_name, rendered_path)
@@ -112,7 +112,7 @@ module Configuration
112
112
  get_named_image_for_storage(request_state) do |image_name, image, rendered_path|
113
113
  storage_path = storage_path(rendered_path)
114
114
 
115
- image.store_url = "file://#{URI.encode(rendered_path.to_s)}"
115
+ image.store_url = URI::Generic.new('file', nil, nil, nil, nil, "/#{URI.encode(rendered_path.to_s)}", nil, nil, nil, URI::DEFAULT_PARSER, true)
116
116
 
117
117
  log.info "storing '#{image_name}' in file '#{storage_path}' (#{image.data.length} bytes)"
118
118
  storage_path.open('wb'){|io| io.write image.data}
@@ -98,6 +98,10 @@ module Configuration
98
98
  @output_callback or fail 'no output callback'
99
99
  end
100
100
 
101
+ def render_template(template)
102
+ RubyStringTemplate.new(template).render(self)
103
+ end
104
+
101
105
  def fetch_base_variable(name, base_name)
102
106
  fetch(base_name, nil) or generate_meta_variable(base_name) or raise NoVariableToGenerateMetaVariableError.new(base_name, name)
103
107
  end
@@ -346,18 +350,18 @@ module Configuration
346
350
  name = $1.to_sym
347
351
  value = $2
348
352
  Matcher.new([name], 'QueryKeyValue', "#{name}=#{value}") do
349
- ->{req[name] && req[name] == value && captures.push(req[name])}
353
+ ->{req.GET[name.to_s] && req.GET[name.to_s] == value && captures.push(req.GET[name.to_s])}
350
354
  end
351
355
  when /^\&:(.+)\?(.*)$/# &:foo?bar
352
356
  name = $1.to_sym
353
357
  default = $2
354
358
  Matcher.new([name], 'QueryKeyDefault', "#{name}=<key>|#{default}") do
355
- ->{captures.push(req[name] || default)}
359
+ ->{captures.push(req.GET[name.to_s] || default)}
356
360
  end
357
361
  when /^\&:(.+)$/# &:foo
358
362
  name = $1.to_sym
359
363
  Matcher.new([name], 'QueryKey', "#{name}=<key>") do
360
- ->{req[name] && captures.push(req[name])}
364
+ ->{req.GET[name.to_s] && captures.push(req.GET[name.to_s])}
361
365
  end
362
366
  # Literal URI segment matcher
363
367
  else # foobar