js-routes 0.3.1 → 0.4.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/Readme.md CHANGED
@@ -26,12 +26,22 @@ Available options:
26
26
  * `#{Rails.root}/app/assets/javascripts/routes.js` for Rails >= 3.1
27
27
  * `#{Rails.root}/public/javascripts/routes.js` for Rails < 3.1
28
28
  * `:default_format` - Format to append to urls. Default: blank
29
- * `:exclude` - Array of regexps to exclude form js routes. Default: []
29
+ * `:exclude` - Array of regexps to exclude from js routes. Default: []
30
+ * Note that regexp applied to **named route** not to *URL*
31
+ * `:include` - Array of regexps to include in js routes. Default: []
30
32
  * Note that regexp applied to **named route** not to *URL*
31
33
  * `:namespace` - global object used to access routes. Default: `Routes`
32
34
  * Possible variants: `MyProject.routes`, `MyProjectRoutes`
33
35
 
34
- In order to generate routes to string and manipulate them yourself:
36
+ Example options usage:
37
+
38
+ ``` ruby
39
+ JsRoutes.generate!(:file => "#{path}/app_routes.js", :namespace => "AppRoutes", :exclude => /^admin_/, :default_format => "json")
40
+ JsRoutes.generate!(:file => "#{path}/adm_routes.js", :namespace => "AdmRoutes", :include => /^admin_/, :default_format => "json")
41
+ ```
42
+
43
+ In order to generate routes to string and manipulate them yourself use `JsRoutes.generate`:
44
+ Like:
35
45
 
36
46
  ``` ruby
37
47
  JsRoutes.generate(options)
@@ -43,8 +53,11 @@ This will create a nice javascript file with `Routes` object that has all the ra
43
53
 
44
54
  ``` js
45
55
  Routes.users_path() // => "/users"
56
+ Routes.user_path(1) // => "/users/1"
46
57
  Routes.user_path(1, {format: 'json'}) // => "/users/1.json"
58
+ Routes.new_user_project_path(1, {format: 'json'}) // => "/users/1/projects/new.json"
47
59
  Routes.user_project_path(1,2, {q: 'hello', custom: true}) // => "/users/1/projects/2?q=hello&custom=true"
60
+
48
61
  ```
49
62
 
50
63
  In order to make routes helpers available globally:
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.3.1
1
+ 0.4.0
data/js-routes.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{js-routes}
8
- s.version = "0.3.1"
8
+ s.version = "0.4.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Bogdan Gusiev"]
12
- s.date = %q{2011-08-07}
12
+ s.date = %q{2011-08-18}
13
13
  s.description = %q{Generates javascript file that defines all Rails named routes as javascript helpers}
14
14
  s.email = %q{agresso@gmail.com}
15
15
  s.extra_rdoc_files = [
data/lib/js_routes.rb CHANGED
@@ -25,64 +25,53 @@ module JsRoutes
25
25
  def js_routes(options = {})
26
26
 
27
27
  options[:default_format] ||= ""
28
- exclude = Array(options[:exclude])
28
+ excludes = options[:exclude] || []
29
+ includes = options[:include] || //
29
30
 
30
31
  Rails.application.reload_routes!
31
- Rails.application.routes.named_routes.routes.map do |_, route|
32
- if exclude.find {|e| route.name =~ e}
32
+ js_routes = Rails.application.routes.named_routes.routes.map do |_, route|
33
+ if any_match?(route, excludes) || !any_match?(route, includes)
33
34
  nil
34
35
  else
35
36
  build_js(route, options)
36
37
  end
37
- end.compact.join(",\n")
38
+ end.compact
39
+
40
+ "{\n" + js_routes.join(",\n") + "}\n"
41
+ end
42
+
43
+ def any_match?(route, matchers)
44
+ matchers = Array(matchers)
45
+ matchers.any? {|regex| route.name =~ regex}
38
46
  end
39
47
 
40
48
  def build_js(route, options)
41
49
  _ = <<-JS.strip!
42
50
  // #{route.name} => #{route.path}
43
51
  #{route.name}_path: function(#{build_params route}) {
44
- var opts = options || {};
45
- var format = Utils.extract_format(opts);
46
- #{build_default_params route};
47
- return Utils.check_path('#{build_path route}' + format) + Utils.serialize(opts);
52
+ return Utils.build_path(#{path_parts(route).inspect}, arguments)
48
53
  }
49
54
  JS
50
55
  end
51
56
 
52
57
 
53
58
  def build_params route
54
- route.conditions[:path_info].captures.map do |cap|
55
- if cap.is_a?(Rack::Mount::GeneratableRegexp::DynamicSegment) && !(cap.name.to_s == "format")
56
- cap.name.to_s.gsub(':', '')
59
+ route.conditions[:path_info].named_captures.map do |cap|
60
+ name = cap.first
61
+ if !(name.to_s == "format")
62
+ # prepending each parameter name with underscore
63
+ # to prevent conflict with JS reserved words
64
+ "_" + name.to_s.gsub(/^:/, '')
57
65
  end
58
66
  end.compact.<<("options").join(', ')
59
67
  end
60
68
 
61
- def build_default_params route
62
- route.conditions[:path_info].captures.map do |cap|
63
- if cap.is_a?(Rack::Mount::GeneratableRegexp::DynamicSegment)
64
- segg = cap.name.to_s.gsub(':', '')
65
- "#{segg} = Utils.check_parameter(#{segg});"
66
- end
67
- end.join("\n")
68
- end
69
-
70
- def build_path route
71
- s = route.path.gsub(/\(\.:format\)$/, ".")
72
-
73
- route.conditions[:path_info].captures.each do |cap|
74
- unless cap.name.to_s == "format"
75
- if route.conditions[:path_info].required_params.include?(cap.name)
76
- s.gsub!(/:#{cap.name.to_s}/){ "' + #{cap.name.to_s.gsub(':','')} + '" }
77
- else
78
- s.gsub!(/\((\.)?:#{cap.name.to_s}\)/){ "#{$1}' + #{cap.name.to_s.gsub(':','')} + '" }
79
- end
80
- end
81
- end
82
- s
83
69
 
70
+ def path_parts route
71
+ route.path.gsub(/\(\.:format\)$/, "").split(/:[a-z\-_]+/)
84
72
  end
85
73
 
74
+
86
75
  def default_file
87
76
  if Rails.version >= "3.1"
88
77
  "#{Rails.root}/app/assets/javascripts/routes.js"
data/lib/routes.js CHANGED
@@ -5,37 +5,45 @@
5
5
  default_format: 'DEFAULT_FORMAT',
6
6
 
7
7
  serialize: function(obj){
8
- if (obj == null) {return '';}
8
+ if (obj === null) {return '';}
9
9
  var s = [];
10
10
  for (prop in obj){
11
11
  s.push(prop + "=" + obj[prop]);
12
12
  }
13
- if (s.length == 0) {
13
+ if (s.length === 0) {
14
14
  return '';
15
15
  }
16
16
  return "?" + s.join('&');
17
17
  },
18
18
 
19
-
20
- check_parameter: function(param) {
21
- if (param === undefined) {
22
- param = '';
23
- }
24
- return param;
25
- },
26
-
27
- check_path: function(path) {
28
- return path.replace(/\.$/m, '');
19
+ clean_path: function(path) {
20
+ return path.replace(/\.$/m, '').replace(/\/$/m, '');
29
21
  },
30
22
 
31
23
  extract_format: function(options) {
32
24
  var format = options.hasOwnProperty("format") ? options.format : Utils.default_format;
33
25
  delete options.format;
34
- return format || "";
26
+ return format ? "." + format : "";
27
+ },
28
+
29
+ extract_options: function(args) {
30
+ return typeof(args[args.length-1]) == "object" ? args.pop() : {};
31
+ },
32
+
33
+ build_path: function(parts, args) {
34
+ args = Array.prototype.slice.call(args);
35
+ result = "";
36
+ var opts = Utils.extract_options(args);
37
+ for (var i=0; i < parts.length; i++) {
38
+ part = parts[i];
39
+ result += part;
40
+ result += args.shift() || "";
41
+ }
42
+ var format = Utils.extract_format(opts);
43
+ return Utils.clean_path(result + format) + Utils.serialize(opts);
35
44
  }
36
45
  };
37
46
 
38
- window.NAMESPACE = {
39
- ROUTES
40
- };
47
+ window.NAMESPACE = ROUTES;
48
+
41
49
  })();
@@ -21,6 +21,10 @@ describe JsRoutes do
21
21
  evaljs("Routes.inbox_path(1)").should == "/inboxes/1"
22
22
  end
23
23
 
24
+ it "should generate nested routing with one parameter" do
25
+ evaljs("Routes.inbox_message_path(1)").should == "/inboxes/1/messages"
26
+ end
27
+
24
28
  it "should generate nested routing" do
25
29
  evaljs("Routes.inbox_message_path(1,2)").should == "/inboxes/1/messages/2"
26
30
  end
@@ -33,6 +37,13 @@ describe JsRoutes do
33
37
  evaljs("Routes.inbox_path(1, {format: 'json', q: 'hello', lang: 'ua'})").should == "/inboxes/1.json?q=hello&lang=ua"
34
38
  end
35
39
 
40
+ it "should support routes with reserved javascript words as parameters" do
41
+ #TODO: this doesn't actually test what it should test
42
+ #because the parameter name is return_id
43
+ #need to find the real way to test
44
+ evaljs("Routes.return_path(1)").should == "/returns/1"
45
+ end
46
+
36
47
  context "when exclude is specified" do
37
48
 
38
49
  let(:_options) { {:exclude => /^admin_/} }
@@ -45,6 +56,18 @@ describe JsRoutes do
45
56
  evaljs("Routes.inboxes_path()").should_not be_nil
46
57
  end
47
58
  end
59
+ context "when include is specified" do
60
+
61
+ let(:_options) { {:include => /^admin_/} }
62
+
63
+ it "should exclude specified routes from file" do
64
+ evaljs("Routes.admin_users_path()").should_not be_nil
65
+ end
66
+
67
+ it "should not exclude routes not under specified pattern" do
68
+ evaljs("Routes.inboxes_path").should be_nil
69
+ end
70
+ end
48
71
 
49
72
  context "when default_format is specified" do
50
73
  let(:_options) { {:default_format => "json"} }
@@ -80,6 +103,13 @@ describe JsRoutes do
80
103
 
81
104
  end
82
105
 
106
+ describe "generated js" do
107
+ subject { JsRoutes.generate }
108
+ it "should have correct function signature" do
109
+ subject.should include("inbox_message_path: function(_inbox_id, _id, options)")
110
+ end
111
+ end
112
+
83
113
  describe ".generate!" do
84
114
  let(:name) { "#{File.dirname(__FILE__)}/../routes.js" }
85
115
  it "should generate routes file" do
data/spec/spec_helper.rb CHANGED
@@ -21,6 +21,8 @@ class App < Rails::Application
21
21
  namespace :admin do
22
22
  resources :users
23
23
  end
24
+
25
+ resources :returns
24
26
  end
25
27
  end
26
28
 
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: js-routes
3
3
  version: !ruby/object:Gem::Version
4
- hash: 17
4
+ hash: 15
5
5
  prerelease: false
6
6
  segments:
7
7
  - 0
8
- - 3
9
- - 1
10
- version: 0.3.1
8
+ - 4
9
+ - 0
10
+ version: 0.4.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - Bogdan Gusiev
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-08-07 00:00:00 +03:00
18
+ date: 2011-08-18 00:00:00 +03:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency