js-routes 2.2.7 → 2.2.8

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cc558c858345b705d2ca048eaab529acf4d4ffe20299e152f1c23fcbeb31388e
4
- data.tar.gz: 70dc5ab9c6f629d3236d45a5cf202c6bb8f00893041857f137b9569a3467d48c
3
+ metadata.gz: 6dfe30c594c24cf044d0f19342e17cd6b23857da7ec68a0bf68d8f8be9f33def
4
+ data.tar.gz: 3aefa8fc04221f07996ada7c57f35b22d2ae519575a6df0e20c6d860fe6203ed
5
5
  SHA512:
6
- metadata.gz: 0536cff5b25734ae0c0399cba8d65fb48503e7038c6e5f7396acb69497505ab8849b109e3348bc2c7a010b073cb3cd4aebed1798c538e8bd0e0270f8949dd53c
7
- data.tar.gz: 99e9d0487c9062cf3789a8018beba7bcc0b9f985251921cb6f042c20c571d74fab8a4c79f82ad0a6530dde42ee8a678fb5dbfae184dd64e8756ef47d06805b0b
6
+ metadata.gz: 652fa60215a5c812e3a0cb0284870bfa63c6eeb1d249940388ade48a3f90a7209559d7cf66750e697ffc317bfcd1bec87e57fed44cad375795ead64fb1bcd254
7
+ data.tar.gz: a68bdb295fb704a5ed753d0576e700668aecfe30d5ec6d425ed458d029eb084de66ff26e0789c808e655574146973db02226a1a48f2cd81fa6ebda3379b7bc8c
data/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  ## master
2
2
 
3
+ ## v2.2.8
4
+
5
+ * Leave emoji symbols intact when encoding URI fragment [#312](https://github.com/railsware/js-routes/issues/312)
6
+ * Use webpacker config variable instead of hardcode [#309](https://github.com/railsware/js-routes/issues/309)
7
+ * Use `File.exist?` to be compatible with all versions of ruby [#310](https://github.com/railsware/js-routes/issues/310)
8
+
3
9
  ## v2.2.7
4
10
 
5
11
  * Fix ESM Tree Shaking [#306](https://github.com/railsware/js-routes/issues/306)
data/Readme.md CHANGED
@@ -16,16 +16,17 @@ gem "js-routes"
16
16
 
17
17
  There are several possible ways to setup JsRoutes:
18
18
 
19
- * [Quick and easy](#quick-start)
19
+ * [Quick and easy](#quick-start) - Recommended
20
20
  * Uses Rack Middleware to automatically update routes locally
21
21
  * Automatically generates routes files on javascript build
22
22
  * Works great for a simple Rails application
23
- * [Webpacker ERB Loader](#webpacker)
24
- * Requires ESM module system (the default)
25
- * Doesn't support typescript definitions
26
23
  * [Advanced Setup](#advanced-setup)
27
24
  * Allows very custom setups
28
- * [Sprockets](#sprockets) legacy
25
+ * Automatic updates need to be customized
26
+ * [Webpacker ERB Loader](#webpacker) - Legacy
27
+ * Requires ESM module system (the default)
28
+ * Doesn't support typescript definitions
29
+ * [Sprockets](#sprockets) - Legacy
29
30
  * Deprecated and not recommended for modern apps
30
31
 
31
32
  <div id='quick-start'></div>
@@ -80,7 +81,7 @@ Add js-routes files to `.gitignore`:
80
81
 
81
82
  ### Webpacker ERB loader
82
83
 
83
- **IMPORTANT**: this setup doesn't support IDE autocompletion with [Typescript](https://www.typescriptlang.org/docs/handbook/declaration-files/templates/module-d-ts.html)
84
+ **IMPORTANT**: the setup doesn't support IDE autocompletion with [Typescript](https://www.typescriptlang.org/docs/handbook/declaration-files/templates/module-d-ts.html)
84
85
 
85
86
 
86
87
  #### Use a Generator
@@ -75,7 +75,7 @@ module JsRoutes
75
75
  end
76
76
 
77
77
  def output_file
78
- webpacker_dir = pathname('app', 'javascript')
78
+ webpacker_dir = defined?(Webpacker) ? Webpacker.config.source_path : pathname('app', 'javascript')
79
79
  sprockets_dir = pathname('app','assets','javascripts')
80
80
  file_name = file || default_file_name
81
81
  sprockets_file = sprockets_dir.join(file_name)
@@ -10,7 +10,7 @@ class JsRoutes::Generators::Base < Rails::Generators::Base
10
10
  "app/javascript/packs/application.js",
11
11
  "app/javascript/controllers/application.js",
12
12
  ].find do |path|
13
- File.exists?(Rails.root.join(path))
13
+ File.exist?(Rails.root.join(path))
14
14
  end
15
15
  end
16
16
  end
@@ -7,7 +7,7 @@ class JsRoutes::Generators::Webpacker < Rails::Generators::Base
7
7
  def create_webpack
8
8
  copy_file "initializer.rb", "config/initializers/js_routes.rb"
9
9
  copy_file "erb.js", "config/webpack/loaders/erb.js"
10
- copy_file "routes.js.erb", "app/javascript/routes.js.erb"
10
+ copy_file "routes.js.erb", "#{Webpacker.config.source_path}/routes.js.erb"
11
11
  inject_into_file "config/webpack/environment.js", loader_content
12
12
  if path = application_js_path
13
13
  inject_into_file path, pack_content
@@ -1,3 +1,3 @@
1
1
  module JsRoutes
2
- VERSION = "2.2.7"
2
+ VERSION = "2.2.8"
3
3
  end
data/lib/routes.js CHANGED
@@ -19,6 +19,14 @@ RubyVariables.WRAPPER(
19
19
  NodeTypes[NodeTypes["DOT"] = 8] = "DOT";
20
20
  })(NodeTypes || (NodeTypes = {}));
21
21
  const isBrowser = typeof window !== "undefined";
22
+ const UnescapedSpecials = "-._~!$&'()*+,;=:@"
23
+ .split("")
24
+ .map((s) => s.charCodeAt(0));
25
+ const UnescapedRanges = [
26
+ ["a", "z"],
27
+ ["A", "Z"],
28
+ ["0", "9"],
29
+ ].map((range) => range.map((s) => s.charCodeAt(0)));
22
30
  const ModuleReferences = {
23
31
  CJS: {
24
32
  define(routes) {
@@ -97,7 +105,6 @@ RubyVariables.WRAPPER(
97
105
  this.name = ParametersMissing.name;
98
106
  }
99
107
  }
100
- const UriEncoderSegmentRegex = /[^a-zA-Z0-9\-._~!$&'()*+,;=:@]/g;
101
108
  const ReservedOptions = [
102
109
  "anchor",
103
110
  "trailing_slash",
@@ -349,7 +356,22 @@ RubyVariables.WRAPPER(
349
356
  }
350
357
  }
351
358
  encode_segment(segment) {
352
- return segment.replace(UriEncoderSegmentRegex, (str) => encodeURIComponent(str));
359
+ if (segment.match(/^[a-zA-Z0-9-]$/)) {
360
+ // Performance optimization for 99% of cases
361
+ return segment;
362
+ }
363
+ return (segment.match(/./gu) || [])
364
+ .map((ch) => {
365
+ const code = ch.charCodeAt(0);
366
+ if (UnescapedRanges.find((range) => code >= range[0] && code <= range[1]) ||
367
+ UnescapedSpecials.includes(code)) {
368
+ return ch;
369
+ }
370
+ else {
371
+ return encodeURIComponent(ch);
372
+ }
373
+ })
374
+ .join("");
353
375
  }
354
376
  is_optional_node(node) {
355
377
  return [NodeTypes.STAR, NodeTypes.SYMBOL, NodeTypes.CAT].includes(node);
@@ -358,7 +380,7 @@ RubyVariables.WRAPPER(
358
380
  let key;
359
381
  switch (route[0]) {
360
382
  case NodeTypes.GROUP:
361
- return "(" + this.build_path_spec(route[1]) + ")";
383
+ return `(${this.build_path_spec(route[1])})`;
362
384
  case NodeTypes.CAT:
363
385
  return (this.build_path_spec(route[1]) + this.build_path_spec(route[2]));
364
386
  case NodeTypes.STAR:
data/lib/routes.ts CHANGED
@@ -100,7 +100,7 @@ declare const module: { exports: any } | undefined;
100
100
  RubyVariables.WRAPPER(
101
101
  // eslint-disable-next-line
102
102
  (): RouterExposedMethods => {
103
- const hasProp = (value: unknown, key: string) =>
103
+ const hasProp = (value: unknown, key: string): boolean =>
104
104
  Object.prototype.hasOwnProperty.call(value, key);
105
105
  enum NodeTypes {
106
106
  GROUP = 1,
@@ -135,6 +135,16 @@ RubyVariables.WRAPPER(
135
135
  define: (routes: RouterExposedMethods) => void;
136
136
  isSupported: () => boolean;
137
137
  };
138
+
139
+ const UnescapedSpecials = "-._~!$&'()*+,;=:@"
140
+ .split("")
141
+ .map((s) => s.charCodeAt(0));
142
+ const UnescapedRanges = [
143
+ ["a", "z"],
144
+ ["A", "Z"],
145
+ ["0", "9"],
146
+ ].map((range) => range.map((s) => s.charCodeAt(0)));
147
+
138
148
  const ModuleReferences: Record<ModuleType, ModuleDefinition> = {
139
149
  CJS: {
140
150
  define(routes) {
@@ -215,8 +225,6 @@ RubyVariables.WRAPPER(
215
225
  }
216
226
  }
217
227
 
218
- const UriEncoderSegmentRegex = /[^a-zA-Z0-9\-._~!$&'()*+,;=:@]/g;
219
-
220
228
  const ReservedOptions = [
221
229
  "anchor",
222
230
  "trailing_slash",
@@ -525,9 +533,25 @@ RubyVariables.WRAPPER(
525
533
  }
526
534
 
527
535
  encode_segment(segment: string): string {
528
- return segment.replace(UriEncoderSegmentRegex, (str) =>
529
- encodeURIComponent(str)
530
- );
536
+ if (segment.match(/^[a-zA-Z0-9-]$/)) {
537
+ // Performance optimization for 99% of cases
538
+ return segment;
539
+ }
540
+ return (segment.match(/./gu) || [])
541
+ .map((ch) => {
542
+ const code = ch.charCodeAt(0);
543
+ if (
544
+ UnescapedRanges.find(
545
+ (range) => code >= range[0] && code <= range[1]
546
+ ) ||
547
+ UnescapedSpecials.includes(code)
548
+ ) {
549
+ return ch;
550
+ } else {
551
+ return encodeURIComponent(ch);
552
+ }
553
+ })
554
+ .join("");
531
555
  }
532
556
 
533
557
  is_optional_node(node: NodeTypes): boolean {
@@ -3,7 +3,7 @@ require "spec_helper"
3
3
  describe JsRoutes, "#serialize" do
4
4
 
5
5
  before(:each) do
6
- evaljs(JsRoutes.generate(module_type: nil, namespace: 'Routes'))
6
+ evallib(module_type: nil, namespace: 'Routes')
7
7
  end
8
8
 
9
9
  it "should provide this method" do
@@ -79,7 +79,7 @@ DOC
79
79
  end
80
80
 
81
81
  it "should not generate file before initialization" do
82
- expect(File.exists?(name)).to be_falsey
82
+ expect(File.exist?(name)).to be_falsey
83
83
  end
84
84
  end
85
85
  end
@@ -2,11 +2,8 @@ require "spec_helper"
2
2
 
3
3
  describe JsRoutes, "compatibility with Rails" do
4
4
 
5
- let(:generated_js) do
6
- JsRoutes.generate(module_type: nil, namespace: 'Routes')
7
- end
8
5
  before(:each) do
9
- evaljs(generated_js)
6
+ evallib(module_type: nil, namespace: 'Routes')
10
7
  end
11
8
 
12
9
  it "should generate collection routing" do
@@ -87,14 +84,22 @@ describe JsRoutes, "compatibility with Rails" do
87
84
  expectjs("Routes.budgie_descendents_path(1)").to eq(test_routes.budgie_descendents_path(1))
88
85
  end
89
86
 
90
- it "should support route with parameters containing symbols that need URI-encoding", :aggregate_failures do
91
- expectjs("Routes.inbox_path('#hello')").to eq(test_routes.inbox_path('#hello'))
92
- expectjs("Routes.inbox_path('some param')").to eq(test_routes.inbox_path('some param'))
93
- expectjs("Routes.inbox_path('some param with more & more encode symbols')").to eq(test_routes.inbox_path('some param with more & more encode symbols'))
94
- end
95
- it "should support route with parameters containing symbols not need URI-encoding", :aggregate_failures do
96
- expectjs("Routes.inbox_path(':some_id')").to eq(test_routes.inbox_path(':some_id'))
97
- expectjs("Routes.inbox_path('.+')").to eq(test_routes.inbox_path('.+'))
87
+ describe "url parameters encoding" do
88
+
89
+ it "should support route with parameters containing symbols that need URI-encoding", :aggregate_failures do
90
+ expectjs("Routes.inbox_path('#hello')").to eq(test_routes.inbox_path('#hello'))
91
+ expectjs("Routes.inbox_path('some param')").to eq(test_routes.inbox_path('some param'))
92
+ expectjs("Routes.inbox_path('some param with more & more encode symbols')").to eq(test_routes.inbox_path('some param with more & more encode symbols'))
93
+ end
94
+
95
+ it "should support route with parameters containing symbols not need URI-encoding", :aggregate_failures do
96
+ expectjs("Routes.inbox_path(':some_id')").to eq(test_routes.inbox_path(':some_id'))
97
+ expectjs("Routes.inbox_path('.+')").to eq(test_routes.inbox_path('.+'))
98
+ end
99
+
100
+ it "supports emoji characters", :aggregate_failures do
101
+ expectjs("Routes.inbox_path('💗')").to eq(test_routes.inbox_path('💗'))
102
+ end
98
103
  end
99
104
 
100
105
  describe "when route has defaults" do
@@ -3,11 +3,8 @@ require "spec_helper"
3
3
 
4
4
  describe JsRoutes, "compatibility with Rails" do
5
5
 
6
- let(:generated_js) do
7
- JsRoutes.generate(module_type: nil, namespace: 'Routes')
8
- end
9
6
  before(:each) do
10
- evaljs(generated_js)
7
+ evallib(module_type: nil, namespace: 'Routes')
11
8
  end
12
9
 
13
10
  context "when specs" do
@@ -47,7 +47,7 @@ describe "after Rails initialization", :slow do
47
47
  end
48
48
 
49
49
  it "should generate routes file" do
50
- expect(File.exists?(NAME)).to be_truthy
50
+ expect(File.exist?(NAME)).to be_truthy
51
51
  end
52
52
 
53
53
  it "should not rewrite routes file if nothing changed" do
data/spec/spec_helper.rb CHANGED
@@ -54,6 +54,10 @@ rescue MiniRacer::RuntimeError => e
54
54
  raise e
55
55
  end
56
56
 
57
+ def evallib(**options)
58
+ evaljs(JsRoutes.generate(**options), filename: 'lib/routes.js')
59
+ end
60
+
57
61
  def test_routes
58
62
  ::App.routes.url_helpers
59
63
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: js-routes
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.2.7
4
+ version: 2.2.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Bogdan Gusiev
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-07-26 00:00:00.000000000 Z
11
+ date: 2023-11-16 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: railties
@@ -197,7 +197,7 @@ files:
197
197
  - spec/js_routes/options_spec.rb
198
198
  - spec/js_routes/rails_routes_compatibility_spec.rb
199
199
  - spec/js_routes/route_specification_spec.rb
200
- - spec/js_routes/zzz_last_post_rails_init_spec.rb
200
+ - spec/js_routes/zzz_sprockets_spec.rb
201
201
  - spec/spec_helper.rb
202
202
  - spec/support/routes.rb
203
203
  - spec/tsconfig.json