sitehub 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +6 -0
- data/.rspec +1 -0
- data/Gemfile +6 -0
- data/Gemfile.lock +114 -0
- data/LICENSE +28 -0
- data/README.md +198 -0
- data/Rakefile +11 -0
- data/lib/sitehub.rb +9 -0
- data/lib/sitehub/builder.rb +82 -0
- data/lib/sitehub/collection.rb +35 -0
- data/lib/sitehub/collection/route_collection.rb +28 -0
- data/lib/sitehub/collection/split_route_collection.rb +50 -0
- data/lib/sitehub/collection/split_route_collection/split.rb +18 -0
- data/lib/sitehub/constants.rb +23 -0
- data/lib/sitehub/constants/http_header_keys.rb +25 -0
- data/lib/sitehub/constants/rack_http_header_keys.rb +17 -0
- data/lib/sitehub/cookie.rb +54 -0
- data/lib/sitehub/cookie/attribute.rb +22 -0
- data/lib/sitehub/cookie/flag.rb +22 -0
- data/lib/sitehub/cookie_rewriting.rb +35 -0
- data/lib/sitehub/forward_proxies.rb +50 -0
- data/lib/sitehub/forward_proxy.rb +67 -0
- data/lib/sitehub/forward_proxy_builder.rb +99 -0
- data/lib/sitehub/http_headers.rb +60 -0
- data/lib/sitehub/logging.rb +5 -0
- data/lib/sitehub/logging/access_logger.rb +74 -0
- data/lib/sitehub/logging/error_logger.rb +36 -0
- data/lib/sitehub/logging/log_entry.rb +14 -0
- data/lib/sitehub/logging/log_stash.rb +10 -0
- data/lib/sitehub/logging/log_wrapper.rb +23 -0
- data/lib/sitehub/middleware.rb +21 -0
- data/lib/sitehub/path_directive.rb +32 -0
- data/lib/sitehub/path_directives.rb +21 -0
- data/lib/sitehub/request_mapping.rb +43 -0
- data/lib/sitehub/resolver.rb +11 -0
- data/lib/sitehub/reverse_proxy.rb +53 -0
- data/lib/sitehub/rules.rb +13 -0
- data/lib/sitehub/string_sanitiser.rb +7 -0
- data/lib/sitehub/transaction_id.rb +16 -0
- data/lib/sitehub/version.rb +3 -0
- data/mem_usage.txt +1584 -0
- data/sitehub.gemspec +43 -0
- data/spec/basket_spec.rb +30 -0
- data/spec/sitehub/builder_spec.rb +203 -0
- data/spec/sitehub/collection/route_collection_spec.rb +91 -0
- data/spec/sitehub/collection/split_route_collection_spec.rb +111 -0
- data/spec/sitehub/collection_spec.rb +40 -0
- data/spec/sitehub/cookie/attribute_spec.rb +37 -0
- data/spec/sitehub/cookie/flag_spec.rb +27 -0
- data/spec/sitehub/cookie_rewriting_spec.rb +67 -0
- data/spec/sitehub/cookie_spec.rb +61 -0
- data/spec/sitehub/error_handling_spec.rb +21 -0
- data/spec/sitehub/forward_proxies_spec.rb +99 -0
- data/spec/sitehub/forward_proxy_builder_spec.rb +295 -0
- data/spec/sitehub/forward_proxy_spec.rb +138 -0
- data/spec/sitehub/http_headers_spec.rb +71 -0
- data/spec/sitehub/integration_spec.rb +21 -0
- data/spec/sitehub/logging/access_logger_spec.rb +127 -0
- data/spec/sitehub/logging/error_logger_spec.rb +80 -0
- data/spec/sitehub/logging/log_entry_spec.rb +34 -0
- data/spec/sitehub/logging/log_stash_spec.rb +21 -0
- data/spec/sitehub/logging/log_wrapper_spec.rb +33 -0
- data/spec/sitehub/middleware_spec.rb +69 -0
- data/spec/sitehub/path_directive_spec.rb +50 -0
- data/spec/sitehub/path_directives_spec.rb +45 -0
- data/spec/sitehub/request_mapping_spec.rb +71 -0
- data/spec/sitehub/resolver_spec.rb +15 -0
- data/spec/sitehub/reverse_proxy_spec.rb +105 -0
- data/spec/sitehub/transaction_id_spec.rb +28 -0
- data/spec/sitehub_spec.rb +19 -0
- data/spec/spec_helper.rb +26 -0
- data/spec/support/patch/rack/response.rb +25 -0
- data/spec/support/shared_contexts/async_context.rb +69 -0
- data/spec/support/shared_contexts/middleware_context.rb +51 -0
- data/spec/support/shared_contexts/rack_test_context.rb +12 -0
- data/spec/support/shared_contexts/sitehub_context.rb +25 -0
- data/spec/support/silent_warnings.rb +5 -0
- metadata +359 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 8eab93145788748ecc28ef5f14aea92b7595f846
|
4
|
+
data.tar.gz: 69f240e1d1d707424bf2e6a07e4791b767441427
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: a4d317b035c62e2513261872065ef428ae0342fc8a40c5807b8b597908d53b9f288b6aa310cda0ece34b57e6d1d77068040af6ce27c96fc5e22aaf762e0a1f24
|
7
|
+
data.tar.gz: 4fbf75725640bbc3dcf06e742bb7b549c444048fb8e4f00d0a64888198d62acd1d0b541a4f225b91928107da2e2bc8b70104144ff8697c8035d03c01aef1a266
|
data/.gitignore
ADDED
data/.rspec
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
--require spec_helper
|
data/Gemfile
ADDED
data/Gemfile.lock
ADDED
@@ -0,0 +1,114 @@
|
|
1
|
+
PATH
|
2
|
+
remote: .
|
3
|
+
specs:
|
4
|
+
sitehub (0.4.1)
|
5
|
+
em-http-request
|
6
|
+
em-synchrony
|
7
|
+
faraday
|
8
|
+
rack
|
9
|
+
rack-fiber_pool
|
10
|
+
rack-ssl-enforcer
|
11
|
+
thin
|
12
|
+
uuid
|
13
|
+
|
14
|
+
GEM
|
15
|
+
remote: https://rubygems.org/
|
16
|
+
specs:
|
17
|
+
addressable (2.3.8)
|
18
|
+
builder (3.2.2)
|
19
|
+
cookiejar (0.3.0)
|
20
|
+
crack (0.4.3)
|
21
|
+
safe_yaml (~> 1.0.0)
|
22
|
+
daemons (1.2.3)
|
23
|
+
diff-lcs (1.2.5)
|
24
|
+
docile (1.1.5)
|
25
|
+
em-http-request (1.1.3)
|
26
|
+
addressable (>= 2.3.4)
|
27
|
+
cookiejar (<= 0.3.0)
|
28
|
+
em-socksify (>= 0.3)
|
29
|
+
eventmachine (>= 1.0.3)
|
30
|
+
http_parser.rb (>= 0.6.0)
|
31
|
+
em-socksify (0.3.1)
|
32
|
+
eventmachine (>= 1.0.0.beta.4)
|
33
|
+
em-synchrony (1.0.4)
|
34
|
+
eventmachine (>= 1.0.0.beta.1)
|
35
|
+
eventmachine (1.0.8)
|
36
|
+
faraday (0.9.2)
|
37
|
+
multipart-post (>= 1.2, < 3)
|
38
|
+
geminabox (0.12.4)
|
39
|
+
builder
|
40
|
+
faraday
|
41
|
+
httpclient (>= 2.2.7)
|
42
|
+
nesty
|
43
|
+
sinatra (>= 1.2.7)
|
44
|
+
hashdiff (0.2.3)
|
45
|
+
http_parser.rb (0.6.0)
|
46
|
+
httpclient (2.7.1)
|
47
|
+
json (1.8.3)
|
48
|
+
macaddr (1.7.1)
|
49
|
+
systemu (~> 2.6.2)
|
50
|
+
memory_profiler (0.9.6)
|
51
|
+
multipart-post (2.0.0)
|
52
|
+
nesty (1.0.2)
|
53
|
+
rack (1.6.4)
|
54
|
+
rack-fiber_pool (0.9.3)
|
55
|
+
rack-protection (1.5.3)
|
56
|
+
rack
|
57
|
+
rack-ssl-enforcer (0.2.9)
|
58
|
+
rack-test (0.6.3)
|
59
|
+
rack (>= 1.0)
|
60
|
+
rake (10.4.2)
|
61
|
+
rspec (3.2.0)
|
62
|
+
rspec-core (~> 3.2.0)
|
63
|
+
rspec-expectations (~> 3.2.0)
|
64
|
+
rspec-mocks (~> 3.2.0)
|
65
|
+
rspec-core (3.2.3)
|
66
|
+
rspec-support (~> 3.2.0)
|
67
|
+
rspec-expectations (3.2.1)
|
68
|
+
diff-lcs (>= 1.2.0, < 2.0)
|
69
|
+
rspec-support (~> 3.2.0)
|
70
|
+
rspec-mocks (3.2.1)
|
71
|
+
diff-lcs (>= 1.2.0, < 2.0)
|
72
|
+
rspec-support (~> 3.2.0)
|
73
|
+
rspec-support (3.2.2)
|
74
|
+
ruby-prof (0.15.9)
|
75
|
+
safe_yaml (1.0.4)
|
76
|
+
simplecov (0.11.1)
|
77
|
+
docile (~> 1.1.0)
|
78
|
+
json (~> 1.8)
|
79
|
+
simplecov-html (~> 0.10.0)
|
80
|
+
simplecov-html (0.10.0)
|
81
|
+
sinatra (1.4.6)
|
82
|
+
rack (~> 1.4)
|
83
|
+
rack-protection (~> 1.4)
|
84
|
+
tilt (>= 1.3, < 3)
|
85
|
+
systemu (2.6.5)
|
86
|
+
thin (1.6.4)
|
87
|
+
daemons (~> 1.0, >= 1.0.9)
|
88
|
+
eventmachine (~> 1.0, >= 1.0.4)
|
89
|
+
rack (~> 1.0)
|
90
|
+
tilt (2.0.2)
|
91
|
+
uuid (2.3.8)
|
92
|
+
macaddr (~> 1.0)
|
93
|
+
webmock (1.22.5)
|
94
|
+
addressable (< 2.4.0)
|
95
|
+
crack (>= 0.3.2)
|
96
|
+
hashdiff
|
97
|
+
|
98
|
+
PLATFORMS
|
99
|
+
ruby
|
100
|
+
|
101
|
+
DEPENDENCIES
|
102
|
+
bundler (~> 1.5)
|
103
|
+
geminabox
|
104
|
+
memory_profiler
|
105
|
+
rack-test
|
106
|
+
rake
|
107
|
+
rspec (~> 3.2.0)
|
108
|
+
ruby-prof
|
109
|
+
simplecov
|
110
|
+
sitehub!
|
111
|
+
webmock
|
112
|
+
|
113
|
+
BUNDLED WITH
|
114
|
+
1.11.2
|
data/LICENSE
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
Copyright (c) 2015, Ladtech Ltd
|
2
|
+
All rights reserved.
|
3
|
+
|
4
|
+
Redistribution and use in source and binary forms, with or without
|
5
|
+
modification, are permitted provided that the following conditions are met:
|
6
|
+
|
7
|
+
* Redistributions of source code must retain the above copyright notice, this
|
8
|
+
list of conditions and the following disclaimer.
|
9
|
+
|
10
|
+
* Redistributions in binary form must reproduce the above copyright notice,
|
11
|
+
this list of conditions and the following disclaimer in the documentation
|
12
|
+
and/or other materials provided with the distribution.
|
13
|
+
|
14
|
+
* Neither the name of sitehub nor the names of its
|
15
|
+
contributors may be used to endorse or promote products derived from
|
16
|
+
this software without specific prior written permission.
|
17
|
+
|
18
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
19
|
+
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
20
|
+
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
21
|
+
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
22
|
+
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
23
|
+
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
24
|
+
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
25
|
+
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
26
|
+
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
27
|
+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
28
|
+
|
data/README.md
ADDED
@@ -0,0 +1,198 @@
|
|
1
|
+
# SiteHub
|
2
|
+
SiteHub is a HTTP proxy written in Ruby with support for A|B testing baked in. SiteHub sits in front of your web application(s) routing all HTTP traffics between it and your users.
|
3
|
+
|
4
|
+
Wouldn't it be cool to write something like:
|
5
|
+
```ruby
|
6
|
+
sitehub = SiteHub.build do
|
7
|
+
proxy %r{/catalogue/(.*)} do
|
8
|
+
split percentage: 50, url: 'http://version1.com/$1', label: :prototype_1
|
9
|
+
split percentage: 50, url: 'http://version2.com/$1', label: :prototype_2
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
run sitehub
|
14
|
+
```
|
15
|
+
or
|
16
|
+
```ruby
|
17
|
+
user_eligible = proc{} #perform check and return boolean
|
18
|
+
|
19
|
+
sitehub = SiteHub.build do
|
20
|
+
proxy %r{/catalogue/(.*)} do
|
21
|
+
route url: 'http://new_catalogue.com/catalogue/$1', label: :new_version, rule: user_eligbile
|
22
|
+
|
23
|
+
default url: 'http://current_catalogue.com/$1'
|
24
|
+
end
|
25
|
+
# other proxy definitions ...
|
26
|
+
end
|
27
|
+
|
28
|
+
run sitehub
|
29
|
+
```
|
30
|
+
|
31
|
+
With SiteHub you can:
|
32
|
+
- A|B testing new features
|
33
|
+
- Silently release new features - SiteHub can be used to put a new version of you application live but inaccessible to users. This new version can still be accessed by teams to peform final checks before opening up the new version to the public.
|
34
|
+
- Modular Web Applications - SiteHub can be used to front discrete applications and present a unified root.
|
35
|
+
|
36
|
+
## Installation
|
37
|
+
`gem install sitehub`
|
38
|
+
|
39
|
+
## Definning a SiteHub
|
40
|
+
A SiteHub is a rack application so needs to be passed to the `run` method in your rackup file
|
41
|
+
|
42
|
+
example config.ru
|
43
|
+
```ruby
|
44
|
+
require 'sitehub'
|
45
|
+
sitehub = SiteHub.build do
|
46
|
+
proxy '/' => 'http://downstream.url.com'
|
47
|
+
end
|
48
|
+
run sitehub
|
49
|
+
```
|
50
|
+
|
51
|
+
## Defining proxies
|
52
|
+
Proxies can have either routes or splits defined within them but not both at the same time.
|
53
|
+
- Splits - define the percentage chance that a downstream url will be used to proxy a user request.
|
54
|
+
- Routes - routes are defined with a rule that determines whether or not a user request can be sent to its downstream url
|
55
|
+
|
56
|
+
### Version affinity
|
57
|
+
Once a downstream route has been chosen for a given route it is sticky. Meaning that users will stay with a version and not flip flop between them.
|
58
|
+
|
59
|
+
Sitehub does this by dropping a cookie that holds the route version that a request is sent to.
|
60
|
+
|
61
|
+
By default the cookie will be given the name `sitehub.recorded_route` and will have the path of the request.
|
62
|
+
|
63
|
+
#### Overiding the name
|
64
|
+
This is done at the top level of your sitehub definition. The name you supply will be used for all sitehub cookies dropped by all proxies.
|
65
|
+
```ruby
|
66
|
+
sitehub = SiteHub.build do
|
67
|
+
sitehub_cookie_name :your_custom_name
|
68
|
+
end
|
69
|
+
```
|
70
|
+
|
71
|
+
#### Overiding the path
|
72
|
+
This is done a proxy by proxy basis
|
73
|
+
```ruby
|
74
|
+
sitehub = SiteHub.build do
|
75
|
+
proxy '/' do
|
76
|
+
sitehub_cookie_path '/your/path'
|
77
|
+
#splits/routes defined here
|
78
|
+
end
|
79
|
+
end
|
80
|
+
```
|
81
|
+
**Caution:**
|
82
|
+
By default sitehub is going to use the path of the request. If you have used a regular expression to define a proxy, this will be different for each unique request that is made.
|
83
|
+
|
84
|
+
e.g. for the following example, calls to /path1, and /path2 would each be given a cookie meaning that users could flip between different version for the same proxy definition. In this case you are definately going to want to set the `sitehub_cookie_path` to keep things consistent.
|
85
|
+
|
86
|
+
```ruby
|
87
|
+
sitehub = SiteHub.build do
|
88
|
+
proxy %r{/*} do
|
89
|
+
#splits/routes defined here
|
90
|
+
end
|
91
|
+
end
|
92
|
+
```
|
93
|
+
|
94
|
+
### Routes with Rules
|
95
|
+
Define a route inside a proxy defintion as follows
|
96
|
+
```ruby
|
97
|
+
sitehub = SiteHub.build do
|
98
|
+
proxy '/catalogue' do
|
99
|
+
route url: 'http://new_catalogue.com/catalogue', label: :new_version, rule: user_eligbile
|
100
|
+
# ...
|
101
|
+
end
|
102
|
+
end
|
103
|
+
```
|
104
|
+
Rules must be an object that responds to call with a single parameter that returns a boolean. True means that the rule applies and false means that it does not.
|
105
|
+
|
106
|
+
The parameter passed to call is the request environment hash. This lets you write things like:
|
107
|
+
```ruby
|
108
|
+
has_special_parameter = proc do |env|
|
109
|
+
Rack::Request.new(env).params.include?(:special_param)
|
110
|
+
end
|
111
|
+
```
|
112
|
+
|
113
|
+
### Splits
|
114
|
+
Splits are defined as follows
|
115
|
+
```ruby
|
116
|
+
sitehub = SiteHub.build do
|
117
|
+
proxy '/catalogue' do
|
118
|
+
split percentage: 50, url: 'http://version1.com', label: :prototype_1
|
119
|
+
split percentage: 50, url: 'http://version2.com', label: :prototype_2
|
120
|
+
end
|
121
|
+
end
|
122
|
+
```
|
123
|
+
Split percentages must add up to 100% unless a default is defined.
|
124
|
+
|
125
|
+
### Default routes
|
126
|
+
When defining either Splits or Routes a default can be defined. Defaults are used as a fallback if a route with a rule that applies can't be found or a split can't be chosen on the first time of trying (This can happen when the splits don't add up to 100%).
|
127
|
+
```ruby
|
128
|
+
sitehub = SiteHub.build do
|
129
|
+
proxy '/catalogue' do
|
130
|
+
route url: 'http://new_catalogue.com/catalogue', label: :new_version, rule: a_rule
|
131
|
+
default url: 'http://current_catalogue.com'
|
132
|
+
end
|
133
|
+
end
|
134
|
+
```
|
135
|
+
### Labels
|
136
|
+
Splits and Routes must be defined with a label. Within a proxy defintion, this label must be unique. This is the value that SiteHub will use to identify the version of a downstream url that a user should stick to once it has been selected.
|
137
|
+
|
138
|
+
### Matching
|
139
|
+
Proxy can be defined to capture specific paths using a literal string or be defined to have a broader appeal using regexs
|
140
|
+
```ruby
|
141
|
+
sitehub = SiteHub.build do
|
142
|
+
proxy '/catalogue' => 'http://downstream.catalogue.com'
|
143
|
+
proxy %r{/orders/*} => 'http://downstream.orders.com'
|
144
|
+
end
|
145
|
+
```
|
146
|
+
|
147
|
+
### Substitution
|
148
|
+
Portions of the request path can be captured and passed downstream by specifying capture groups your path regular expression.
|
149
|
+
```ruby
|
150
|
+
sitehub = SiteHub.build do
|
151
|
+
proxy %r{'/orders/(.*)} => 'http://downstream.orders.com/$1'
|
152
|
+
end
|
153
|
+
```
|
154
|
+
|
155
|
+
## Using middleware
|
156
|
+
You can `use` middleware in conjunction with a particular proxy definition or the SiteHub as a whole.
|
157
|
+
### Proxy specifc middleware
|
158
|
+
```ruby
|
159
|
+
sitehub = SiteHub.build do
|
160
|
+
proxy '/catalogue/(.*)' do
|
161
|
+
use AuthenticationMiddlware
|
162
|
+
end
|
163
|
+
end
|
164
|
+
```
|
165
|
+
In this example, only requests received by the proxy definition will be made to go through the AuthenticationMiddleware
|
166
|
+
|
167
|
+
### SiteHub wide middlware
|
168
|
+
```ruby
|
169
|
+
sitehub = SiteHub.build do
|
170
|
+
use AuthenticationMiddleware
|
171
|
+
proxy '/catalogue' => 'http://downstream.catalogue.com'
|
172
|
+
proxy '/orders' => 'http://downstream.orders.com'
|
173
|
+
end
|
174
|
+
```
|
175
|
+
In this example, all requests handled by the SiteHub will go through the AuthenticationMiddleware
|
176
|
+
### Reverse Proxying
|
177
|
+
In order to ensure that you applications stay firmly behind your SiteHub, you are going need to ensure that any responses that they return have are rewritten to remove references to your downstream URLs. SiteHub does this for the `Location` header (set for redirects) and will soon do it for the [Content-Location](https://github.com/bskyb-commerce/sitehub/issues/8) header also.
|
178
|
+
```ruby
|
179
|
+
sitehub = SiteHub.build do
|
180
|
+
proxy %r{/orders/(.*)} => 'http://downstream.orders.com/$1'
|
181
|
+
reverse_proxy %r{http://downstream.orders.com/(.*)} => '/orders/$1'
|
182
|
+
end
|
183
|
+
```
|
184
|
+
*Note* The above example also performs substitution from the downstream URL in to the upstream mapping. This is not mandatory
|
185
|
+
|
186
|
+
## SiteHub Transaction ID
|
187
|
+
SiteHub introduces a custom header to downstream requests called `sitehub_transaction_id` that is unique to every request. The idea is that if a request is made from the downstream system to another then this header should be passed on also. If access/errors in each system are logged along with this id, then tracing things in distributed systems will become easier.
|
188
|
+
|
189
|
+
The transaction id, if passed on through out, could also be used for request scoped caching.
|
190
|
+
|
191
|
+
## Logging
|
192
|
+
By default SiteHub will log requests and errors to STDOUT and STDERR respectively. You can overide this with your own logging devices. For example you may want to send requests and errors to syslog. Just make sure that your logger object responds to `<<` or `write` and SiteHub will do the rest.
|
193
|
+
```ruby
|
194
|
+
sitehub = SiteHub.build do
|
195
|
+
access_logger YourLogger.new
|
196
|
+
error_logger YourLogger.new
|
197
|
+
end
|
198
|
+
```
|
data/Rakefile
ADDED
data/lib/sitehub.rb
ADDED
@@ -0,0 +1,82 @@
|
|
1
|
+
require 'sitehub/forward_proxies'
|
2
|
+
require 'sitehub/transaction_id'
|
3
|
+
require 'sitehub/middleware'
|
4
|
+
require 'sitehub/forward_proxy_builder'
|
5
|
+
require 'sitehub/reverse_proxy'
|
6
|
+
require 'rack/ssl-enforcer'
|
7
|
+
require 'sitehub/logging'
|
8
|
+
require 'rack/fiber_pool'
|
9
|
+
require 'logger'
|
10
|
+
|
11
|
+
|
12
|
+
class SiteHub
|
13
|
+
|
14
|
+
class InvalidProxyDefinitionException < Exception;
|
15
|
+
end
|
16
|
+
class Builder
|
17
|
+
|
18
|
+
attr_reader :sitehub, :forward_proxies, :reverse_proxies
|
19
|
+
|
20
|
+
include Middleware
|
21
|
+
|
22
|
+
def force_ssl except: []
|
23
|
+
@force_ssl = true
|
24
|
+
@ssl_exclusions = except
|
25
|
+
end
|
26
|
+
|
27
|
+
def initialize(&block)
|
28
|
+
@forward_proxies = ForwardProxies.new
|
29
|
+
@reverse_proxies = {}
|
30
|
+
instance_eval &block if block
|
31
|
+
end
|
32
|
+
|
33
|
+
def access_logger logger=nil
|
34
|
+
return @access_logger unless logger
|
35
|
+
@access_logger = logger
|
36
|
+
end
|
37
|
+
|
38
|
+
def error_logger logger=nil
|
39
|
+
return @error_logger unless logger
|
40
|
+
@error_logger = logger
|
41
|
+
end
|
42
|
+
|
43
|
+
def sitehub_cookie_name name=nil
|
44
|
+
@sitehub_cookie_name ||= RECORDED_ROUTES_COOKIE
|
45
|
+
|
46
|
+
return @sitehub_cookie_name unless name
|
47
|
+
@sitehub_cookie_name = name
|
48
|
+
end
|
49
|
+
|
50
|
+
def build
|
51
|
+
forward_proxies.init
|
52
|
+
use ReverseProxy, reverse_proxies
|
53
|
+
use TransactionId
|
54
|
+
use Logging::AccessLogger, access_logger || ::Logger.new(STDOUT)
|
55
|
+
use Logging::ErrorLogger, error_logger || ::Logger.new(STDERR)
|
56
|
+
use Rack::FiberPool
|
57
|
+
use Rack::SslEnforcer, except: @ssl_exclusions if @force_ssl
|
58
|
+
middlewares.reverse!
|
59
|
+
|
60
|
+
apply_middleware(forward_proxies)
|
61
|
+
end
|
62
|
+
|
63
|
+
def proxy opts={}, &block
|
64
|
+
args = {sitehub_cookie_name: sitehub_cookie_name}
|
65
|
+
|
66
|
+
if opts.is_a?(Hash)
|
67
|
+
mapped_path = opts.keys.first
|
68
|
+
url = opts.values.first
|
69
|
+
args.merge!(url: url, mapped_path: mapped_path)
|
70
|
+
else
|
71
|
+
args.merge!(mapped_path: opts)
|
72
|
+
end
|
73
|
+
|
74
|
+
forward_proxies << ForwardProxyBuilder.new(args, &block)
|
75
|
+
end
|
76
|
+
|
77
|
+
def reverse_proxy hash
|
78
|
+
reverse_proxies.merge!(hash)
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
end
|