rack-proxy 0.6.5 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 7613a66b731bfac2c3f24a961757f359894ebdce
4
- data.tar.gz: f69050ff757d137cebc48c7afcf385661e703d33
2
+ SHA256:
3
+ metadata.gz: 228f3bf6e52dcd2bdcebf9c52bf1db47dfdc7179ed52cd3664e14cfd8df80db9
4
+ data.tar.gz: 6613d7f13087046d9ad6ee22e5afa56db6910145df427e42101f5aa491d3fe26
5
5
  SHA512:
6
- metadata.gz: 9085c724256f803ecd1d232c41ef1811c560b4600759af715e44bbd06ab343f239a5c4db7c3da6c2ede58f8089bfdd00f76cda3f509f7e65ba99e5f6d4450c68
7
- data.tar.gz: e158ad03e8ff6f415d39f12759659f0148d2463d85f9734b73000401ac20b395ab7226f2cc49a5db0c69e8175f807823a9d1502a151b1aeddaaf970049190ba4
6
+ metadata.gz: 151b04e286d1305d116cf743f00c6b811ed10fad0f24cf806b685a4e038a4dcf5c3b8f7e0dd0cf1e8aa95dd8c46763b0f8b114d36c668fdaabda541d48d5722a
7
+ data.tar.gz: 234ec48678c973b203cf00f256039c6e88f63c67c5e279e6f0ec17fc51de07022f7a3099dfe0efdaacf46808a0512cd9e16444823b6d616fdee08ae5572efbb2
data/Gemfile CHANGED
@@ -1,4 +1,4 @@
1
- source "http://rubygems.org"
1
+ source "https://rubygems.org"
2
2
 
3
3
  gem 'rake'
4
4
 
data/Gemfile.lock CHANGED
@@ -1,17 +1,17 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- rack-proxy (0.6.5)
4
+ rack-proxy (0.7.0)
5
5
  rack
6
6
 
7
7
  GEM
8
- remote: http://rubygems.org/
8
+ remote: https://rubygems.org/
9
9
  specs:
10
10
  power_assert (0.2.6)
11
11
  rack (2.0.3)
12
12
  rack-test (0.5.6)
13
13
  rack (>= 1.0)
14
- rake (0.9.2.2)
14
+ rake (13.0.1)
15
15
  test-unit (3.1.5)
16
16
  power_assert
17
17
 
@@ -25,4 +25,4 @@ DEPENDENCIES
25
25
  test-unit
26
26
 
27
27
  BUNDLED WITH
28
- 1.16.0
28
+ 1.17.2
data/README.md CHANGED
@@ -6,7 +6,7 @@ Installation
6
6
  Add the following to your `Gemfile`:
7
7
 
8
8
  ```
9
- gem 'rack-proxy', '~> 0.6.4'
9
+ gem 'rack-proxy', '~> 0.7.0'
10
10
  ```
11
11
 
12
12
  Or install:
@@ -17,7 +17,8 @@ gem install rack-proxy
17
17
 
18
18
  Use Cases
19
19
  ----
20
- Below are some examples of real world use cases for Rack-Proxy, done something interesting add the list below and send a PR.
20
+
21
+ Below are some examples of real world use cases for Rack-Proxy. If you have done something interesting, add it to the list below and send a PR.
21
22
 
22
23
  * Allowing one app to act as central trust authority
23
24
  * handle accepting self-sign certificates for internal apps
@@ -25,7 +26,7 @@ Below are some examples of real world use cases for Rack-Proxy, done something i
25
26
  * avoiding CORs complications by proxying from same domain to another backend
26
27
  * subdomain based pass-through to multiple apps
27
28
  * Complex redirect rules
28
- * redirect pages with different extensions (ex: `.php`) to another app
29
+ * redirect pages with different extensions (ex: `.php`) to another app
29
30
  * useful for handling awkward redirection rules for moved pages
30
31
  * fan Parallel Requests: turning a single API request to [multiple concurrent backend requests](https://github.com/typhoeus/typhoeus#making-parallel-requests) & merging results.
31
32
  * inserting or stripping headers required or problematic for certain clients
@@ -76,7 +77,7 @@ class ForwardHost < Rack::Proxy
76
77
 
77
78
  # example of inserting an additional header
78
79
  headers["X-Foo"] = "Bar"
79
-
80
+
80
81
  # if you rewrite env, it appears that content-length isn't calculated correctly
81
82
  # resulting in only partial responses being sent to users
82
83
  # you can remove it or recalculate it here
@@ -98,14 +99,14 @@ class TrustingProxy < Rack::Proxy
98
99
  def rewrite_env(env)
99
100
  env["HTTP_HOST"] = "self-signed.badssl.com"
100
101
 
101
- # We are going to trust the self-signed SSL
102
+ # We are going to trust the self-signed SSL
102
103
  env["rack.ssl_verify_none"] = true
103
104
  env
104
105
  end
105
106
 
106
107
  def rewrite_response(triplet)
107
108
  status, headers, body = triplet
108
-
109
+
109
110
  # if you rewrite env, it appears that content-length isn't calculated correctly
110
111
  # resulting in only partial responses being sent to users
111
112
  # you can remove it or recalculate it here
@@ -130,12 +131,12 @@ Test with `require 'rack_proxy_examples/example_service_proxy'`
130
131
  ```ruby
131
132
  ###
132
133
  # This is an example of how to use Rack-Proxy in a Rails application.
133
- #
134
+ #
134
135
  # Setup:
135
- # 1. rails new test_app
136
+ # 1. rails new test_app
136
137
  # 2. cd test_app
137
138
  # 3. install Rack-Proxy in `Gemfile`
138
- # a. `gem 'rack-proxy', '~> 0.6.3'`
139
+ # a. `gem 'rack-proxy', '~> 0.7.0'`
139
140
  # 4. install gem: `bundle install`
140
141
  # 5. create `config/initializers/proxy.rb` adding this line `require 'rack_proxy_examples/example_service_proxy'`
141
142
  # 6. run: `SERVICE_URL=http://guides.rubyonrails.org rails server`
@@ -157,7 +158,7 @@ class ExampleServiceProxy < Rack::Proxy
157
158
 
158
159
  # This is the only path that needs to be set currently on Rails 5 & greater
159
160
  env['PATH_INFO'] = ENV['SERVICE_PATH'] || '/configuring.html'
160
-
161
+
161
162
  # don't send your sites cookies to target service, unless it is a trusted internal service that can parse all your cookies
162
163
  env['HTTP_COOKIE'] = ''
163
164
  super(env)
@@ -185,14 +186,14 @@ class RackPhpProxy < Rack::Proxy
185
186
  if request.path =~ %r{\.php}
186
187
  env["HTTP_HOST"] = ENV["HTTP_HOST"] ? URI(ENV["HTTP_HOST"]).host : "localhost"
187
188
  ENV["PHP_PATH"] ||= '/manual/en/tutorial.firstpage.php'
188
-
189
+
189
190
  # Rails 3 & 4
190
191
  env["REQUEST_PATH"] = ENV["PHP_PATH"] || "/php/#{request.fullpath}"
191
192
  # Rails 5 and above
192
193
  env['PATH_INFO'] = ENV["PHP_PATH"] || "/php/#{request.fullpath}"
193
194
 
194
195
  env['content-length'] = nil
195
-
196
+
196
197
  super(env)
197
198
  else
198
199
  @app.call(env)
@@ -201,7 +202,7 @@ class RackPhpProxy < Rack::Proxy
201
202
 
202
203
  def rewrite_response(triplet)
203
204
  status, headers, body = triplet
204
-
205
+
205
206
  # if you proxy depending on the backend, it appears that content-length isn't calculated correctly
206
207
  # resulting in only partial responses being sent to users
207
208
  # you can remove it or recalculate it here
@@ -232,6 +233,71 @@ This will allow to run the other requests through the application and only proxy
232
233
 
233
234
  See tests for more examples.
234
235
 
236
+ ### SSL proxy for SpringBoot applications debugging
237
+
238
+ Whenever you need to debug communication with external services with HTTPS protocol (like OAuth based) you have to be able to access to your local web app through HTTPS protocol too. Typical way is to use nginx or Apache httpd as a reverse proxy but it might be inconvinuent for development environment. Simple proxy server is a better way in this case. The only what we need is to unpack incoming SSL queries and proxy them to a backend. We can prepare minimal set of files to create autonomous proxy server.
239
+
240
+ Create `config.ru` file:
241
+ ```ruby
242
+ #
243
+ # config.ru
244
+ #
245
+ require 'rack'
246
+ require 'rack-proxy'
247
+
248
+ class ForwardHost < Rack::Proxy
249
+ def rewrite_env(env)
250
+ env['HTTP_X_FORWARDED_HOST'] = env['SERVER_NAME']
251
+ env['HTTP_X_FORWARDED_PROTO'] = env['rack.url_scheme']
252
+ env
253
+ end
254
+ end
255
+
256
+ run ForwardHost.new(backend: 'http://localhost:8080')
257
+ ```
258
+
259
+ Create `Gemfile` file:
260
+ ```ruby
261
+ source "https://rubygems.org"
262
+
263
+ gem 'thin'
264
+ gem 'rake'
265
+ gem 'rack-proxy'
266
+ ```
267
+
268
+ Create `config.yml` file with configuration of web server `thin`:
269
+ ```yml
270
+ ---
271
+ ssl: true
272
+ ssl-key-file: keys/domain.key
273
+ ssl-cert-file: keys/domain.crt
274
+ ssl-disable-verify: false
275
+ ```
276
+
277
+ Create 'keys' directory and generate SSL key and certificates files `domain.key` and `domain.crt`
278
+
279
+ Run `bundle exec thin start` for running it with `thin`'s default port.
280
+
281
+ Or use `sudo -E thin start -C config.yml -p 443` for running with default for `https://` port.
282
+
283
+ Don't forget to enable processing of `X-Forwarded-...` headers on your application side. Just add following strings to your `resources/application.yml` file.
284
+ ```yml
285
+ ---
286
+ server:
287
+ tomcat:
288
+ remote-ip-header: x-forwarded-for
289
+ protocol-header: x-forwarded-proto
290
+ use-forward-headers: true
291
+ ```
292
+
293
+ Add some domain name like `debug.your_app.com` into your local `/etc/hosts` file like
294
+ ```
295
+ 127.0.0.1 debug.your_app.com
296
+ ```
297
+
298
+ Next start the proxy and your app. And now you can access to your Spring application through SSL connection via `https://debug.your_app.com` URI in a browser.
299
+
300
+
235
301
  WARNING
236
302
  ----
237
303
 
@@ -242,4 +308,4 @@ Todos
242
308
 
243
309
  * Make the docs up to date with the current use case for this code: everything except streaming which involved a rather ugly monkey patch and only worked in 1.8, but does not work now.
244
310
  * Improve and validate requirements for Host and Path rewrite rules
245
- * Ability to inject logger and set log level
311
+ * Ability to inject logger and set log level
@@ -4,7 +4,7 @@
4
4
  #
5
5
  # [status, headers, streamable_body]
6
6
  #
7
- # See http://github.com/aniero/rack-streaming-proxy
7
+ # See http://github.com/zerowidth/rack-streaming-proxy
8
8
  # for alternative that uses additional process.
9
9
  #
10
10
  # BTW I don't like monkey patching either
data/lib/rack/proxy.rb CHANGED
@@ -5,12 +5,12 @@ module Rack
5
5
 
6
6
  # Subclass and bring your own #rewrite_request and #rewrite_response
7
7
  class Proxy
8
- VERSION = "0.6.5"
8
+ VERSION = "0.7.0"
9
9
 
10
10
  class << self
11
11
  def extract_http_request_headers(env)
12
12
  headers = env.reject do |k, v|
13
- !(/^HTTP_[A-Z0-9_]+$/ === k) || v.nil?
13
+ !(/^HTTP_[A-Z0-9_\.]+$/ === k) || v.nil?
14
14
  end.map do |k, v|
15
15
  [reconstruct_header_name(k), v]
16
16
  end.inject(Utils::HeaderHash.new) do |hash, k_v|
@@ -46,11 +46,17 @@ module Rack
46
46
  else
47
47
  @app = app
48
48
  end
49
+
49
50
  @streaming = opts.fetch(:streaming, true)
50
51
  @ssl_verify_none = opts.fetch(:ssl_verify_none, false)
51
52
  @backend = URI(opts[:backend]) if opts[:backend]
52
53
  @read_timeout = opts.fetch(:read_timeout, 60)
53
54
  @ssl_version = opts[:ssl_version] if opts[:ssl_version]
55
+
56
+ @username = opts[:username] if opts[:username]
57
+ @password = opts[:password] if opts[:password]
58
+
59
+ @opts = opts
54
60
  end
55
61
 
56
62
  def call(env)
@@ -92,6 +98,9 @@ module Rack
92
98
  target_request.body_stream.rewind
93
99
  end
94
100
 
101
+ # Use basic auth if we have to
102
+ target_request.basic_auth(@username, @password) if @username && @password
103
+
95
104
  backend = env.delete('rack.backend') || @backend || source_request
96
105
  use_ssl = backend.scheme == "https"
97
106
  ssl_verify_none = (env.delete('rack.ssl_verify_none') || @ssl_verify_none) == true
@@ -1,11 +1,11 @@
1
1
  ###
2
2
  # This is an example of how to use Rack-Proxy in a Rails application.
3
- #
3
+ #
4
4
  # Setup:
5
- # 1. rails new test_app
5
+ # 1. rails new test_app
6
6
  # 2. cd test_app
7
7
  # 3. install Rack-Proxy in `Gemfile`
8
- # a. `gem 'rack-proxy', '~> 0.6.3'`
8
+ # a. `gem 'rack-proxy', '~> 0.7.0'`
9
9
  # 4. install gem: `bundle install`
10
10
  # 5. create `config/initializers/proxy.rb` adding this line `require 'rack_proxy_examples/example_service_proxy'`
11
11
  # 6. run: `SERVICE_URL=http://guides.rubyonrails.org rails server`
@@ -27,7 +27,7 @@ class ExampleServiceProxy < Rack::Proxy
27
27
 
28
28
  # This is the only path that needs to be set currently on Rails 5 & greater
29
29
  env['PATH_INFO'] = ENV['SERVICE_PATH'] || '/configuring.html'
30
-
30
+
31
31
  # don't send your sites cookies to target service, unless it is a trusted internal service that can parse all your cookies
32
32
  env['HTTP_COOKIE'] = ''
33
33
  super(env)
data/rack-proxy.gemspec CHANGED
@@ -6,14 +6,13 @@ Gem::Specification.new do |s|
6
6
  s.name = "rack-proxy"
7
7
  s.version = Rack::Proxy::VERSION
8
8
  s.platform = Gem::Platform::RUBY
9
+ s.license = 'MIT'
9
10
  s.authors = ["Jacek Becela"]
10
11
  s.email = ["jacek.becela@gmail.com"]
11
12
  s.homepage = "https://github.com/ncr/rack-proxy"
12
13
  s.summary = %q{A request/response rewriting HTTP proxy. A Rack app.}
13
14
  s.description = %q{A Rack app that provides request/response rewriting proxy capabilities with streaming.}
14
15
 
15
- s.rubyforge_project = "rack-proxy"
16
-
17
16
  s.files = `git ls-files`.split("\n")
18
17
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
19
18
  s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
@@ -6,7 +6,7 @@ class RackProxyTest < Test::Unit::TestCase
6
6
  attr_accessor :host
7
7
 
8
8
  def rewrite_env(env)
9
- env["HTTP_HOST"] = self.host || 'www.trix.pl'
9
+ env["HTTP_HOST"] = self.host || 'example.com'
10
10
  env
11
11
  end
12
12
  end
@@ -18,14 +18,15 @@ class RackProxyTest < Test::Unit::TestCase
18
18
  def test_http_streaming
19
19
  get "/"
20
20
  assert last_response.ok?
21
- assert_match(/Jacek Becela/, last_response.body)
21
+
22
+ assert_match(/Example Domain/, last_response.body)
22
23
  end
23
24
 
24
25
  def test_http_full_request
25
26
  app(:streaming => false)
26
27
  get "/"
27
28
  assert last_response.ok?
28
- assert_match(/Jacek Becela/, last_response.body)
29
+ assert_match(/Example Domain/, last_response.body)
29
30
  end
30
31
 
31
32
  def test_http_full_request_headers
@@ -89,12 +90,14 @@ class RackProxyTest < Test::Unit::TestCase
89
90
  'NOT-HTTP-HEADER' => 'test-value',
90
91
  'HTTP_ACCEPT' => 'text/html',
91
92
  'HTTP_CONNECTION' => nil,
92
- 'HTTP_CONTENT_MD5' => 'deadbeef'
93
+ 'HTTP_CONTENT_MD5' => 'deadbeef',
94
+ 'HTTP_HEADER.WITH.PERIODS' => 'stillmooing'
93
95
  }
94
96
 
95
97
  headers = proxy_class.extract_http_request_headers(env)
96
98
  assert headers.key?('ACCEPT')
97
99
  assert headers.key?('CONTENT-MD5')
100
+ assert headers.key?('HEADER.WITH.PERIODS')
98
101
  assert !headers.key?('CONNECTION')
99
102
  assert !headers.key?('NOT-HTTP-HEADER')
100
103
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rack-proxy
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.5
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jacek Becela
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-09-17 00:00:00.000000000 Z
11
+ date: 2021-05-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rack
@@ -81,9 +81,10 @@ files:
81
81
  - test/rack_proxy_test.rb
82
82
  - test/test_helper.rb
83
83
  homepage: https://github.com/ncr/rack-proxy
84
- licenses: []
84
+ licenses:
85
+ - MIT
85
86
  metadata: {}
86
- post_install_message:
87
+ post_install_message:
87
88
  rdoc_options: []
88
89
  require_paths:
89
90
  - lib
@@ -98,9 +99,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
98
99
  - !ruby/object:Gem::Version
99
100
  version: '0'
100
101
  requirements: []
101
- rubyforge_project: rack-proxy
102
- rubygems_version: 2.6.13
103
- signing_key:
102
+ rubygems_version: 3.0.3
103
+ signing_key:
104
104
  specification_version: 4
105
105
  summary: A request/response rewriting HTTP proxy. A Rack app.
106
106
  test_files: