critical-path-css-rails 2.10.1 → 3.0.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
2
  SHA1:
3
- metadata.gz: fa63ebb4981fc4894ceadac1a422a7cc328ca769
4
- data.tar.gz: db00b262c891af99be925bdb0ccd93bf43c2f246
3
+ metadata.gz: 9e125cf7a784d74a2cb6d73d750126b9770a54ed
4
+ data.tar.gz: b414e4fa457d7ee3f8e57f4cd81912489da64a24
5
5
  SHA512:
6
- metadata.gz: f171e796311df1c45f618a8cebf33098d2ffa078a8fce996706e48770b0c4c22443aa80b9d69abd256d99ed9d3fd25bf715e9e940e0e221f05d3351c0ff8ef0c
7
- data.tar.gz: '08796cc6cc00255a01d0caa90af1f7626ea49d9459d4687cc716a68c1661c55a7c791e95c6bd6f2428fa554479245afcab8e23eea84599f21dd0512c4d406a0e'
6
+ metadata.gz: 47d951d41f4f6b30cd2c757461a371f7f2ca408efaba7d7d7d6ae4e1a747b40ad6a37c17ec137d489ac7fdb44fda4a0756318171c6f5da2d464d6217805a7128
7
+ data.tar.gz: 3d93c0c5f7b0fcabb32b2ea8e42d8a974abb06c713bcd9339ea86a3dc9179a2b0cdf67b7a5ffcdd89ddf33ce038dd9284f18eb3bcd98ead391f76766b030f90c
data/README.md CHANGED
@@ -27,7 +27,7 @@ However, more packages may need to be installed depending on your OS distributio
27
27
  After reviewing the dependency requirements, add `critical-path-css-rails` to your Gemfile:
28
28
 
29
29
  ```
30
- gem 'critical-path-css-rails', '~> 2.10.0'
30
+ gem 'critical-path-css-rails', '~> 3.0.0'
31
31
  ```
32
32
 
33
33
  Download and install by running:
@@ -54,6 +54,7 @@ First, you'll need to configue a few things in the YAML file: `config/critical_p
54
54
 
55
55
  * `manifest_name`: If you're using the asset pipeline, add the manifest name.
56
56
  * `css_path`: If you're not using the asset pipeline, you'll need to define the path to the application's main CSS. The gem assumes your CSS lives in `RAILS_ROOT/public`. If your main CSS file is in `RAILS_ROOT/public/assets/main.css`, you would set the variable to `/assets/main.css`.
57
+ * `css_paths`: If you have the need to specify multiple CSS source files, you can do so with `css_paths`. Note that `css_path` and `css_paths` are **mutually exclusive**; if using `css_path`, configuration for `css_paths` should be omitted, and vice versa. When using this option, a separate CSS path must be specified for each route, and they will be matched based on the order specified (the first CSS path will be applied to the first route, the second CSS path to the second route, etc).
57
58
  * `routes`: List the routes that you would like to generate the critical CSS for. (i.e. /resources, /resources/show/1, etc.)
58
59
  * `base_url`: Add your application's URL for the necessary environments.
59
60
 
@@ -87,7 +88,7 @@ A simple example using [loadcss-rails](https://github.com/michael-misshore/loadc
87
88
  <script>
88
89
  loadCSS("<%= stylesheet_path('application') %>");
89
90
  </script>
90
- <link rel="preload" href="<%= stylesheet_path('application') %>" as="style" onload="this.rel='stylesheet'">
91
+ <link rel="preload" href="<%= stylesheet_path('application') %>" as="style" onload="this.onload=null;this.rel='stylesheet'">
91
92
  <noscript>
92
93
  <link rel="stylesheet" href="<%= stylesheet_path('application') %>">
93
94
  </noscript>
@@ -146,6 +147,12 @@ This gem is to be tested inside of docker/docker-compose. [Combustion](https://g
146
147
 
147
148
  Once shell'd in, run `bundle exec rspec spec` to run the test. The test rails app lives in `spec/internal`, and it can be viewed locally at `http://localhost:9292/`
148
149
 
150
+ If you encounter Chromium errors trying to run the tests, installing [Puppeteer](https://github.com/GoogleChrome/puppeteer) might help.
151
+
152
+ ```Bash
153
+ npm install puppeteer
154
+ ```
155
+
149
156
 
150
157
  ## Versions
151
158
 
@@ -7,10 +7,11 @@ RUN apt-get update && apt-get install -y build-essential libpq-dev nodejs npm
7
7
  # Install Penthouse JS Dependencies
8
8
  RUN apt-get install -y libpangocairo-1.0-0 libx11-xcb1 libxcomposite1 libxcursor1 libxdamage1 libxi6 libxtst6 libnss3 libcups2 libxss1 libxrandr2 libgconf2-4 libasound2 libatk1.0-0 libgtk-3-0
9
9
 
10
+ # Configure Node/NPM
10
11
  RUN npm cache clean -f
11
12
  RUN npm install -g n
12
- RUN n 8.9.3
13
- RUN ln -sf /usr/local/n/versions/node/8.9.3/bin/node /usr/bin/nodejs
13
+ RUN n 10.15.1
14
+ RUN ln -sf /usr/local/n/versions/node/10.15.1/bin/node /usr/bin/nodejs
14
15
 
15
16
  ENV BUNDLE_PATH /gems
16
17
 
@@ -3,6 +3,9 @@ defaults: &defaults
3
3
  manifest_name: application
4
4
  # Else provide the relative path of your CSS file from the /public directory
5
5
  # css_path: /path/to/css/from/public/main.css
6
+ # Or provide a separate path for each route
7
+ # css_paths:
8
+ # - /path/to/css/from/public/main.css
6
9
  routes:
7
10
  - /
8
11
 
@@ -6,16 +6,11 @@ module CriticalPathCss
6
6
  CACHE_NAMESPACE = 'critical-path-css'.freeze
7
7
 
8
8
  def self.generate(route)
9
- ::Rails.cache.write(
10
- route,
11
- CssFetcher.new(config).fetch_route(route),
12
- namespace: CACHE_NAMESPACE,
13
- expires_in: nil
14
- )
9
+ ::Rails.cache.write(route, fetcher.fetch_route(route), namespace: CACHE_NAMESPACE, expires_in: nil)
15
10
  end
16
11
 
17
12
  def self.generate_all
18
- CssFetcher.new(config).fetch.each do |route, css|
13
+ fetcher.fetch.each do |route, css|
19
14
  ::Rails.cache.write(route, css, namespace: CACHE_NAMESPACE, expires_in: nil)
20
15
  end
21
16
  end
@@ -32,7 +27,11 @@ module CriticalPathCss
32
27
  ::Rails.cache.read(route, namespace: CACHE_NAMESPACE) || ''
33
28
  end
34
29
 
35
- def self.config
36
- @config ||= Configuration.new(CriticalPathCss::Rails::ConfigLoader.new.load)
30
+ def self.fetcher
31
+ @fetcher ||= CssFetcher.new(Configuration.new(config_loader.config))
32
+ end
33
+
34
+ def self.config_loader
35
+ @config_loader ||= CriticalPathCss::Rails::ConfigLoader.new
37
36
  end
38
37
  end
@@ -13,6 +13,10 @@ module CriticalPathCss
13
13
  @config['css_path']
14
14
  end
15
15
 
16
+ def css_paths
17
+ @config['css_paths']
18
+ end
19
+
16
20
  def manifest_name
17
21
  @config['manifest_name']
18
22
  end
@@ -10,30 +10,21 @@ module CriticalPathCss
10
10
  end
11
11
 
12
12
  def fetch
13
- @config.routes.map { |route| [route, css_for_route(route)] }.to_h
13
+ @config.routes.map { |route| [route, fetch_route(route)] }.to_h
14
14
  end
15
15
 
16
16
  def fetch_route(route)
17
- css_for_route route
18
- end
19
-
20
- protected
21
-
22
- def css_for_route(route)
23
17
  options = {
24
18
  'url' => @config.base_url + route,
25
- 'css' => @config.css_path,
26
- ## optional params
27
- # viewport dimensions
19
+ 'css' => fetch_css_path_for_route(route),
28
20
  'width' => 1300,
29
21
  'height' => 900,
22
+ 'timeout' => 30_000,
30
23
  # CSS selectors to always include, e.g.:
31
24
  'forceInclude' => [
32
25
  # '.keepMeEvenIfNotSeenInDom',
33
26
  # '^\.regexWorksToo'
34
27
  ],
35
- # ms; abort critical CSS generation after this timeout
36
- 'timeout' => 30_000,
37
28
  # set to true to throw on CSS errors (will run faster if no errors)
38
29
  'strict' => false,
39
30
  # characters; strip out inline base64 encoded resources larger than this
@@ -60,5 +51,17 @@ module CriticalPathCss
60
51
  end
61
52
  out
62
53
  end
54
+
55
+ private
56
+
57
+ def fetch_css_path_for_route(route)
58
+ index_for_route = @config.routes.index(route)
59
+
60
+ if index_for_route && @config.css_paths[index_for_route]
61
+ @config.css_paths[index_for_route]
62
+ else
63
+ @config.css_path
64
+ end
65
+ end
63
66
  end
64
67
  end
@@ -3,15 +3,13 @@ module CriticalPathCss
3
3
  class ConfigLoader
4
4
  CONFIGURATION_FILENAME = 'critical_path_css.yml'.freeze
5
5
 
6
- def load
7
- config = YAML.safe_load(ERB.new(File.read(configuration_file_path)).result, [], [], true)[::Rails.env]
8
- config['css_path'] = "#{::Rails.root}/public" + (
9
- config['css_path'] ||
10
- ActionController::Base.helpers.stylesheet_path(
11
- config['manifest_name'], host: ''
12
- )
13
- )
14
- config
6
+ def initialize
7
+ validate_css_paths
8
+ format_css_paths
9
+ end
10
+
11
+ def config
12
+ @config ||= YAML.safe_load(ERB.new(File.read(configuration_file_path)).result, [], [], true)[::Rails.env]
15
13
  end
16
14
 
17
15
  private
@@ -19,6 +17,28 @@ module CriticalPathCss
19
17
  def configuration_file_path
20
18
  @configuration_file_path ||= ::Rails.root.join('config', CONFIGURATION_FILENAME)
21
19
  end
20
+
21
+ def format_css_paths
22
+ if config['css_path']
23
+ config['css_path'] = format_path(config['css_path'])
24
+ config['css_paths'] = []
25
+ else
26
+ config['css_path'] = ''
27
+ config['css_paths'] = config['css_paths'].collect { |path| format_path(path) }
28
+ end
29
+ end
30
+
31
+ def format_path(path)
32
+ "#{::Rails.root}/public#{path}"
33
+ end
34
+
35
+ def validate_css_paths
36
+ if config['css_path'] && config['css_paths']
37
+ raise LoadError, 'Cannot specify both css_path and css_paths'
38
+ elsif config['css_paths'] && config['css_paths'].length != config['routes'].length
39
+ raise LoadError, 'Must specify css_paths for each route'
40
+ end
41
+ end
22
42
  end
23
43
  end
24
44
  end
@@ -1,5 +1,5 @@
1
1
  module CriticalPathCSS
2
2
  module Rails
3
- VERSION = '2.10.1'.freeze
3
+ VERSION = '3.0.0'.freeze
4
4
  end
5
5
  end
@@ -9,7 +9,7 @@
9
9
  "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.2.1.tgz",
10
10
  "integrity": "sha512-JVwXMr9nHYTUXsBFKUqhJwvlcYU/blreOEUkhNR2eXZIvwd+c+o5V4MgDPKWnMS/56awN3TRzIP+KoPn+roQtg==",
11
11
  "requires": {
12
- "es6-promisify": "5.0.0"
12
+ "es6-promisify": "^5.0.0"
13
13
  }
14
14
  },
15
15
  "async-limiter": {
@@ -27,7 +27,7 @@
27
27
  "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
28
28
  "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
29
29
  "requires": {
30
- "balanced-match": "1.0.0",
30
+ "balanced-match": "^1.0.0",
31
31
  "concat-map": "0.0.1"
32
32
  }
33
33
  },
@@ -46,10 +46,10 @@
46
46
  "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz",
47
47
  "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==",
48
48
  "requires": {
49
- "buffer-from": "1.1.1",
50
- "inherits": "2.0.3",
51
- "readable-stream": "2.3.6",
52
- "typedarray": "0.0.6"
49
+ "buffer-from": "^1.0.0",
50
+ "inherits": "^2.0.3",
51
+ "readable-stream": "^2.2.2",
52
+ "typedarray": "^0.0.6"
53
53
  }
54
54
  },
55
55
  "core-util-is": {
@@ -67,8 +67,8 @@
67
67
  "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.0.0-alpha.28.tgz",
68
68
  "integrity": "sha512-joNNW1gCp3qFFzj4St6zk+Wh/NBv0vM5YbEreZk0SD4S23S+1xBKb6cLDg2uj4P4k/GUMlIm6cKIDqIG+vdt0w==",
69
69
  "requires": {
70
- "mdn-data": "1.1.4",
71
- "source-map": "0.5.7"
70
+ "mdn-data": "~1.1.0",
71
+ "source-map": "^0.5.3"
72
72
  }
73
73
  },
74
74
  "debug": {
@@ -76,7 +76,7 @@
76
76
  "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.0.tgz",
77
77
  "integrity": "sha512-heNPJUJIqC+xB6ayLAMHaIrmN9HKa7aQO8MGqKpvCA+uJYVcvR6l5kgdrhRuwPFHU7P5/A1w0BjByPHwpfTDKg==",
78
78
  "requires": {
79
- "ms": "2.1.1"
79
+ "ms": "^2.1.1"
80
80
  }
81
81
  },
82
82
  "es6-promise": {
@@ -86,10 +86,10 @@
86
86
  },
87
87
  "es6-promisify": {
88
88
  "version": "5.0.0",
89
- "resolved": "http://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz",
89
+ "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz",
90
90
  "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=",
91
91
  "requires": {
92
- "es6-promise": "4.2.5"
92
+ "es6-promise": "^4.0.3"
93
93
  }
94
94
  },
95
95
  "extract-zip": {
@@ -123,7 +123,7 @@
123
123
  "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz",
124
124
  "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=",
125
125
  "requires": {
126
- "pend": "1.2.0"
126
+ "pend": "~1.2.0"
127
127
  }
128
128
  },
129
129
  "fs.realpath": {
@@ -136,12 +136,12 @@
136
136
  "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz",
137
137
  "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==",
138
138
  "requires": {
139
- "fs.realpath": "1.0.0",
140
- "inflight": "1.0.6",
141
- "inherits": "2.0.3",
142
- "minimatch": "3.0.4",
143
- "once": "1.4.0",
144
- "path-is-absolute": "1.0.1"
139
+ "fs.realpath": "^1.0.0",
140
+ "inflight": "^1.0.4",
141
+ "inherits": "2",
142
+ "minimatch": "^3.0.4",
143
+ "once": "^1.3.0",
144
+ "path-is-absolute": "^1.0.0"
145
145
  }
146
146
  },
147
147
  "https-proxy-agent": {
@@ -149,8 +149,8 @@
149
149
  "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.1.tgz",
150
150
  "integrity": "sha512-HPCTS1LW51bcyMYbxUIOO4HEOlQ1/1qRaFWcyxvwaqUS9TY88aoEuHUY33kuAh1YhVVaDQhLZsnPd+XNARWZlQ==",
151
151
  "requires": {
152
- "agent-base": "4.2.1",
153
- "debug": "3.2.6"
152
+ "agent-base": "^4.1.0",
153
+ "debug": "^3.1.0"
154
154
  },
155
155
  "dependencies": {
156
156
  "debug": {
@@ -158,7 +158,7 @@
158
158
  "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz",
159
159
  "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==",
160
160
  "requires": {
161
- "ms": "2.1.1"
161
+ "ms": "^2.1.1"
162
162
  }
163
163
  }
164
164
  }
@@ -168,8 +168,8 @@
168
168
  "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
169
169
  "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=",
170
170
  "requires": {
171
- "once": "1.4.0",
172
- "wrappy": "1.0.2"
171
+ "once": "^1.3.0",
172
+ "wrappy": "1"
173
173
  }
174
174
  },
175
175
  "inherits": {
@@ -202,17 +202,17 @@
202
202
  "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
203
203
  "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
204
204
  "requires": {
205
- "brace-expansion": "1.1.11"
205
+ "brace-expansion": "^1.1.7"
206
206
  }
207
207
  },
208
208
  "minimist": {
209
209
  "version": "0.0.8",
210
- "resolved": "http://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz",
210
+ "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz",
211
211
  "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0="
212
212
  },
213
213
  "mkdirp": {
214
214
  "version": "0.5.1",
215
- "resolved": "http://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz",
215
+ "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz",
216
216
  "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=",
217
217
  "requires": {
218
218
  "minimist": "0.0.8"
@@ -228,7 +228,7 @@
228
228
  "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
229
229
  "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
230
230
  "requires": {
231
- "wrappy": "1.0.2"
231
+ "wrappy": "1"
232
232
  }
233
233
  },
234
234
  "path-is-absolute": {
@@ -246,10 +246,10 @@
246
246
  "resolved": "https://registry.npmjs.org/penthouse/-/penthouse-1.10.1.tgz",
247
247
  "integrity": "sha512-D0fUazt6EvtoJvbKJ4u6yVIwfrWoSW1+2clr5JZaKag5pzgwLJKYcN8NgmAoBmWOwsMk+3ZAkV5Cv09LzQtqAw==",
248
248
  "requires": {
249
- "css-mediaquery": "0.1.2",
249
+ "css-mediaquery": "^0.1.2",
250
250
  "css-tree": "1.0.0-alpha.28",
251
- "debug": "4.1.0",
252
- "jsesc": "2.5.1",
251
+ "debug": "^4.1.0",
252
+ "jsesc": "^2.5.1",
253
253
  "puppeteer": "1.9.0"
254
254
  }
255
255
  },
@@ -273,14 +273,14 @@
273
273
  "resolved": "https://registry.npmjs.org/puppeteer/-/puppeteer-1.9.0.tgz",
274
274
  "integrity": "sha512-GH4PmhJf9wBRAPvtJkEJLAvdNNOofZortmBZSj8cGWYni98GUFqsf66blOEfJbo5B8l0KG5HR2d/W2MejnUrzg==",
275
275
  "requires": {
276
- "debug": "3.2.6",
277
- "extract-zip": "1.6.7",
278
- "https-proxy-agent": "2.2.1",
279
- "mime": "2.3.1",
280
- "progress": "2.0.1",
281
- "proxy-from-env": "1.0.0",
282
- "rimraf": "2.6.2",
283
- "ws": "5.2.2"
276
+ "debug": "^3.1.0",
277
+ "extract-zip": "^1.6.6",
278
+ "https-proxy-agent": "^2.2.1",
279
+ "mime": "^2.0.3",
280
+ "progress": "^2.0.0",
281
+ "proxy-from-env": "^1.0.0",
282
+ "rimraf": "^2.6.1",
283
+ "ws": "^5.1.1"
284
284
  },
285
285
  "dependencies": {
286
286
  "debug": {
@@ -288,23 +288,23 @@
288
288
  "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz",
289
289
  "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==",
290
290
  "requires": {
291
- "ms": "2.1.1"
291
+ "ms": "^2.1.1"
292
292
  }
293
293
  }
294
294
  }
295
295
  },
296
296
  "readable-stream": {
297
297
  "version": "2.3.6",
298
- "resolved": "http://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz",
298
+ "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz",
299
299
  "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==",
300
300
  "requires": {
301
- "core-util-is": "1.0.2",
302
- "inherits": "2.0.3",
303
- "isarray": "1.0.0",
304
- "process-nextick-args": "2.0.0",
305
- "safe-buffer": "5.1.2",
306
- "string_decoder": "1.1.1",
307
- "util-deprecate": "1.0.2"
301
+ "core-util-is": "~1.0.0",
302
+ "inherits": "~2.0.3",
303
+ "isarray": "~1.0.0",
304
+ "process-nextick-args": "~2.0.0",
305
+ "safe-buffer": "~5.1.1",
306
+ "string_decoder": "~1.1.1",
307
+ "util-deprecate": "~1.0.1"
308
308
  }
309
309
  },
310
310
  "rimraf": {
@@ -312,7 +312,7 @@
312
312
  "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz",
313
313
  "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==",
314
314
  "requires": {
315
- "glob": "7.1.3"
315
+ "glob": "^7.0.5"
316
316
  }
317
317
  },
318
318
  "safe-buffer": {
@@ -330,7 +330,7 @@
330
330
  "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz",
331
331
  "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==",
332
332
  "requires": {
333
- "safe-buffer": "5.1.2"
333
+ "safe-buffer": "~5.1.0"
334
334
  }
335
335
  },
336
336
  "typedarray": {
@@ -353,7 +353,7 @@
353
353
  "resolved": "https://registry.npmjs.org/ws/-/ws-5.2.2.tgz",
354
354
  "integrity": "sha512-jaHFD6PFv6UgoIVda6qZllptQsMlDEJkTQcybzzXDYM1XO9Y8em691FGMPmM46WGyLU4z9KMgQN+qrux/nhlHA==",
355
355
  "requires": {
356
- "async-limiter": "1.0.0"
356
+ "async-limiter": "~1.0.0"
357
357
  }
358
358
  },
359
359
  "yauzl": {
@@ -361,7 +361,7 @@
361
361
  "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.4.1.tgz",
362
362
  "integrity": "sha1-lSj0QtqxsihOWLQ3m7GU4i4MQAU=",
363
363
  "requires": {
364
- "fd-slicer": "1.0.1"
364
+ "fd-slicer": "~1.0.1"
365
365
  }
366
366
  }
367
367
  }
@@ -1 +1,2 @@
1
+ <h1>Critical Path CSS Rails Test App</h1>
1
2
  <p><%= CriticalPathCss.fetch(request.path) %></p>
@@ -0,0 +1,77 @@
1
+ require 'spec_helper'
2
+
3
+ RSpec.describe 'CssFetcher' do
4
+ let(:subject) { CriticalPathCss::CssFetcher.new(config) }
5
+ let(:response) { ['foo','', OpenStruct.new(exitstatus: 0)] }
6
+ let(:routes) { ['/', '/new_route'] }
7
+ let(:config) do
8
+ OpenStruct.new(
9
+ base_url: 'http://0.0.0.0:9292',
10
+ css_path: css_path,
11
+ css_paths: css_paths,
12
+ penthouse_options: {},
13
+ routes: routes
14
+ )
15
+ end
16
+
17
+ describe '#fetch_route' do
18
+ context 'when a single css_path is configured' do
19
+ let(:css_path) { '/test.css' }
20
+ let(:css_paths) { [] }
21
+
22
+ it 'generates css for the single route' do
23
+ expect(Open3).to receive(:capture3) do |arg1, arg2, arg3|
24
+ options = JSON.parse(arg3)
25
+ expect(options['css']).to eq '/test.css'
26
+ end.once.and_return(response)
27
+
28
+ subject.fetch_route(routes.first)
29
+ end
30
+ end
31
+ end
32
+
33
+ describe '#fetch' do
34
+ context 'when a single css_path is configured' do
35
+ let(:css_path) { '/test.css' }
36
+ let(:css_paths) { [] }
37
+
38
+ it 'generates css for each route from the same file' do
39
+ expect(Open3).to receive(:capture3) do |arg1, arg2, arg3|
40
+ options = JSON.parse(arg3)
41
+ expect(options['css']).to eq '/test.css'
42
+ end.twice.and_return(response)
43
+ subject.fetch
44
+ end
45
+ end
46
+
47
+ context 'when multiple css_paths are configured' do
48
+ let(:css_path) { '' }
49
+ let(:css_paths) { ['/test.css', '/test2.css'] }
50
+
51
+ it 'generates css for each route from the respective file' do
52
+ expect(Open3).to receive(:capture3) do |arg1, arg2, arg3|
53
+ options = JSON.parse(arg3)
54
+ expect(options['css']).to eq '/test.css' if options['url'] == 'http://0.0.0.0:9292/'
55
+ expect(options['css']).to eq '/test2.css' if options['url'] == 'http://0.0.0.0:9292/new_route'
56
+ end.twice.and_return(response)
57
+ subject.fetch
58
+ end
59
+ end
60
+
61
+ context 'when same css file applies to multiple routes' do
62
+ let(:css_path) { '' }
63
+ let(:css_paths) { ['/test.css', '/test2.css', '/test.css'] }
64
+ let(:routes) { ['/', '/new_route', '/newer_route'] }
65
+
66
+ it 'generates css for each route from the respective file' do
67
+ expect(Open3).to receive(:capture3) do |arg1, arg2, arg3|
68
+ options = JSON.parse(arg3)
69
+ expect(options['css']).to eq '/test.css' if options['url'] == 'http://0.0.0.0:9292/'
70
+ expect(options['css']).to eq '/test2.css' if options['url'] == 'http://0.0.0.0:9292/new_route'
71
+ expect(options['css']).to eq '/test.css' if options['url'] == 'http://0.0.0.0:9292/newer_route'
72
+ end.thrice.and_return(response)
73
+ subject.fetch
74
+ end
75
+ end
76
+ end
77
+ end
@@ -0,0 +1,118 @@
1
+ require 'spec_helper'
2
+
3
+ RSpec.describe 'ConfigLoader' do
4
+ let(:subject) { CriticalPathCss::Rails::ConfigLoader.new }
5
+
6
+ describe '#load' do
7
+ before do
8
+ allow(File).to receive(:read).and_return(config_file)
9
+ end
10
+
11
+ context 'when single css_path is specified' do
12
+ let(:config_file) {
13
+ <<~CONFIG
14
+ defaults: &defaults
15
+ base_url: http://0.0.0.0:9292
16
+ css_path: /test.css
17
+ routes:
18
+ - /
19
+
20
+ development:
21
+ <<: *defaults
22
+
23
+ test:
24
+ <<: *defaults
25
+ CONFIG
26
+ }
27
+
28
+ it 'sets css_path with the path' do
29
+ expect(subject.config['css_path']).to eq '/app/spec/internal/public/test.css'
30
+ end
31
+
32
+ it 'leaves css_paths empty' do
33
+ expect(subject.config['css_paths']).to eq []
34
+ end
35
+ end
36
+
37
+ context 'when multiple css_paths are specified' do
38
+ let(:config_file) {
39
+ <<~CONFIG
40
+ defaults: &defaults
41
+ base_url: http://0.0.0.0:9292
42
+ css_paths:
43
+ - /test.css
44
+ - /test2.css
45
+ routes:
46
+ - /
47
+ - /new_route
48
+
49
+ development:
50
+ <<: *defaults
51
+
52
+ test:
53
+ <<: *defaults
54
+ CONFIG
55
+ }
56
+
57
+ it 'sets css_path to empty string' do
58
+ expect(subject.config['css_path']).to eq ''
59
+ end
60
+
61
+ it 'leaves css_paths to an array of paths' do
62
+ expect(subject.config['css_paths']).to eq ['/app/spec/internal/public/test.css','/app/spec/internal/public/test2.css']
63
+ end
64
+ end
65
+
66
+ context 'when single css_path and multiple css_paths are both specified' do
67
+ let(:config_file) {
68
+ <<~CONFIG
69
+ defaults: &defaults
70
+ base_url: http://0.0.0.0:9292
71
+ css_path: /test.css
72
+ css_paths:
73
+ - /test.css
74
+ - /test2.css
75
+ routes:
76
+ - /
77
+ - /new_route
78
+
79
+ development:
80
+ <<: *defaults
81
+
82
+ test:
83
+ <<: *defaults
84
+ CONFIG
85
+ }
86
+
87
+ it 'raises an error' do
88
+ expect { subject }.to raise_error LoadError, 'Cannot specify both css_path and css_paths'
89
+ end
90
+ end
91
+
92
+ context 'when css_paths and routes are not the same length' do
93
+ let(:config_file) {
94
+ <<~CONFIG
95
+ defaults: &defaults
96
+ base_url: http://0.0.0.0:9292
97
+ css_paths:
98
+ - /test.css
99
+ - /test2.css
100
+ routes:
101
+ - /
102
+ - /new_route
103
+ - /newer_route
104
+
105
+ development:
106
+ <<: *defaults
107
+
108
+ test:
109
+ <<: *defaults
110
+ CONFIG
111
+ }
112
+
113
+ it 'raises an error' do
114
+ expect { subject }.to raise_error LoadError, 'Must specify css_paths for each route'
115
+ end
116
+ end
117
+ end
118
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: critical-path-css-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.10.1
4
+ version: 3.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Michael Misshore
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-11-01 00:00:00.000000000 Z
11
+ date: 2019-02-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: combustion
@@ -72,6 +72,8 @@ files:
72
72
  - spec/internal/log/.gitignore
73
73
  - spec/internal/public/favicon.ico
74
74
  - spec/internal/public/test.css
75
+ - spec/lib/critical_path_css/css_fetcher_spec.rb
76
+ - spec/lib/critical_path_css/rails/config_loader_spec.rb
75
77
  - spec/spec_helper.rb
76
78
  homepage:
77
79
  licenses: