described_routes 0.1.4 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/History.txt +9 -1
- data/Manifest.txt +1 -0
- data/README.rdoc +16 -12
- data/lib/described_routes.rb +1 -87
- data/lib/described_routes/rails_controller.rb +24 -5
- data/lib/described_routes/rails_routes.rb +23 -9
- data/lib/described_routes/resource_template.rb +103 -1
- data/lib/tasks/described_routes.rb +27 -7
- data/test/fixtures/described_routes_test.json +1 -0
- data/test/test_resource_template.rb +43 -0
- metadata +3 -2
data/History.txt
CHANGED
data/Manifest.txt
CHANGED
data/README.rdoc
CHANGED
@@ -6,7 +6,7 @@ Outputs hierarchical, framework-neutral descriptions of Rails routes in JSON, YA
|
|
6
6
|
|
7
7
|
== SYNOPSIS:
|
8
8
|
|
9
|
-
=== Build
|
9
|
+
=== Build time
|
10
10
|
|
11
11
|
In your Rakefile:
|
12
12
|
|
@@ -16,7 +16,6 @@ Then:
|
|
16
16
|
|
17
17
|
$ rake --tasks described_routes
|
18
18
|
rake described_routes:json # Describe resource structure in JSON format
|
19
|
-
rake described_routes:ruby # Describe resource structure as a Ruby literal
|
20
19
|
rake described_routes:xml # Describe resource structure in XML format
|
21
20
|
rake described_routes:yaml # Describe resource structure in YAML format
|
22
21
|
rake described_routes:yaml_short # Describe resource structure in YAML format (basic structure only)
|
@@ -62,20 +61,27 @@ Add the following route in config/routes.rb:
|
|
62
61
|
|
63
62
|
map.resources :described_routes, :controller => "described_routes/rails"
|
64
63
|
|
65
|
-
You (or your client application) can now browse to any of the following:
|
64
|
+
You (or your client application) can now browse to any of the following top level addresses:
|
66
65
|
|
67
66
|
* .../described_routes.json
|
68
67
|
* .../described_routes.xml
|
69
68
|
* .../described_routes.yaml
|
70
69
|
* .../described_routes.yaml?short=true
|
71
70
|
|
72
|
-
|
71
|
+
and for the named route "users" (say):
|
72
|
+
|
73
|
+
* .../described_routes/users.json
|
74
|
+
* .../described_routes/users.xml
|
75
|
+
* .../described_routes/users.yaml
|
76
|
+
* .../described_routes/users.yaml?short=true
|
77
|
+
|
78
|
+
If the application has a route named "root", run-time-generated data will include uri_template attributes based on root_url in addition to the path_template attributes supported at build time.
|
73
79
|
|
74
80
|
== DATA STRUCTURES and FORMATS
|
75
81
|
|
76
82
|
=== Natural structure
|
77
83
|
|
78
|
-
The YAML
|
84
|
+
The YAML and JSON representations appear as simple array and hash structures (which is what they're generated from internally). Each resource is represented by a hash of attributes (one of which may be a list of child resources); the top level structure is an array of the resources that don't have parents.
|
79
85
|
|
80
86
|
Attributes:
|
81
87
|
|
@@ -95,23 +101,21 @@ Note that only named routes are considered. Pre-Rails 2.3 "formatted routes" ar
|
|
95
101
|
|
96
102
|
This follows the natural structure but with the following modifications:
|
97
103
|
|
98
|
-
* A +
|
99
|
-
* A +
|
104
|
+
* A +ResourceTemplate+ element for each resource template
|
105
|
+
* A +ResourceTemplates+ element for each list of resources (top level or subresources)
|
100
106
|
* +Params+ and +OptionalParams+ elements for +params+ and +optional_params+, each containing +param+ elements
|
101
107
|
* A single +options+ element contains the applicable HTTP methods as a comma-separated list
|
102
108
|
|
109
|
+
Calls to parse_xml will at present result in NoMethodError exceptions being raised.
|
110
|
+
|
103
111
|
== REQUIREMENTS:
|
104
112
|
|
105
|
-
Rails.
|
113
|
+
Rails, for the Rake tasks and Rails controller. The ResourceTemplate class and its formats are however Rails-independent.
|
106
114
|
|
107
115
|
== INSTALL:
|
108
116
|
|
109
117
|
sudo gem install described_routes
|
110
118
|
|
111
|
-
Then add the following to your Rakefile:
|
112
|
-
|
113
|
-
require "tasks/described_routes"
|
114
|
-
|
115
119
|
== Author
|
116
120
|
|
117
121
|
Mike Burrows (asplake), email mailto:mjb@asplake.co.uk, website positiveincline.com[http://positiveincline.com] (see articles tagged described_routes[http://positiveincline.com/?tag=described_routes])
|
data/lib/described_routes.rb
CHANGED
@@ -2,91 +2,5 @@ require 'described_routes/resource_template'
|
|
2
2
|
|
3
3
|
module DescribedRoutes
|
4
4
|
# rubygem version
|
5
|
-
VERSION = "0.
|
6
|
-
|
7
|
-
# Convert an array of ResourceTemplate objects to array of hashes equivalent to their JSON or YAML representations
|
8
|
-
def self.to_parsed(resource_templates)
|
9
|
-
resource_templates.map{|resource_template| resource_template.to_hash}
|
10
|
-
end
|
11
|
-
|
12
|
-
# Convert an array of ResourceTemplate objects to JSON
|
13
|
-
def self.to_json(resource_templates)
|
14
|
-
self.to_parsed(resource_templates).to_json
|
15
|
-
end
|
16
|
-
|
17
|
-
# Convert an array of ResourceTemplate objects to YAML
|
18
|
-
def self.to_yaml(resource_templates)
|
19
|
-
self.to_parsed(resource_templates).to_yaml
|
20
|
-
end
|
21
|
-
|
22
|
-
# Create an array of ResourceTemplate objects from a JSON string
|
23
|
-
def self.parse_json(json)
|
24
|
-
self.from_parsed(JSON.parse(json))
|
25
|
-
end
|
26
|
-
|
27
|
-
# Create an array of ResourceTemplate objects from a JSON string
|
28
|
-
def self.parse_yaml(yaml)
|
29
|
-
self.from_parsed(YAML::load(yaml))
|
30
|
-
end
|
31
|
-
|
32
|
-
# Create an array of ResourceTemplate objects from an array of hashes
|
33
|
-
def self.from_parsed(parsed)
|
34
|
-
raise ArgumentError.new("not an array") unless parsed.kind_of?(Array)
|
35
|
-
|
36
|
-
parsed.map do |hash|
|
37
|
-
ResourceTemplate.from_hash(hash)
|
38
|
-
end
|
39
|
-
end
|
40
|
-
|
41
|
-
#
|
42
|
-
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
43
|
-
#
|
44
|
-
def self.to_xml(xm, resource_templates)
|
45
|
-
xm.ResourceTemplates do |xm|
|
46
|
-
resource_templates.each do |resource_template|
|
47
|
-
xm.ResourceTemplate do |xm|
|
48
|
-
value_tag(xm, resource_template, "rel")
|
49
|
-
value_tag(xm, resource_template, "name")
|
50
|
-
value_tag(xm, resource_template, "path_template")
|
51
|
-
value_tag(xm, resource_template, "uri_template")
|
52
|
-
|
53
|
-
list_tag(xm, resource_template["params"], "Params", "param")
|
54
|
-
list_tag(xm, resource_template["optional_params"], "OptionalParams", "param")
|
55
|
-
|
56
|
-
# could use a list of elements here, but let's follow HTTP's lead and reduce the verbosity
|
57
|
-
options = resource_template["options"] || []
|
58
|
-
xm.options(options.join(", ")) unless options.empty?
|
59
|
-
|
60
|
-
resource_templates = resource_template["resource_templates"] || []
|
61
|
-
to_xml(xm, resource_templates) unless resource_templates.empty?
|
62
|
-
end
|
63
|
-
end
|
64
|
-
end
|
65
|
-
xm
|
66
|
-
end
|
67
|
-
|
68
|
-
def self.value_tag(xm, h, tag) #:nodoc:
|
69
|
-
value = h[tag]
|
70
|
-
xm.tag!(tag, value) unless value.blank?
|
71
|
-
end
|
72
|
-
|
73
|
-
def self.list_tag(xm, collection, collection_tag, member_tag) #:nodoc:
|
74
|
-
unless collection.nil? or collection.empty?
|
75
|
-
xm.tag!(collection_tag) do |xm|
|
76
|
-
collection.each do |value|
|
77
|
-
xm.tag!(member_tag, value)
|
78
|
-
end
|
79
|
-
end
|
80
|
-
end
|
81
|
-
end
|
82
|
-
|
83
|
-
# Get a hash of all named ResourceTemplate objects contained in the supplied collection, keyed by name
|
84
|
-
def self.all_by_name(resource_templates, h = {})
|
85
|
-
resource_templates.inject(h) do |hash, resource_template|
|
86
|
-
hash[resource_template.name] = resource_template if resource_template.name
|
87
|
-
all_by_name(resource_template.resource_templates, hash)
|
88
|
-
hash
|
89
|
-
end
|
90
|
-
h
|
91
|
-
end
|
5
|
+
VERSION = "0.2.0"
|
92
6
|
end
|
@@ -5,20 +5,39 @@ module DescribedRoutes
|
|
5
5
|
class RailsController < ActionController::Base
|
6
6
|
def index
|
7
7
|
base_url = root_url rescue nil
|
8
|
-
|
8
|
+
resource_templates = RailsRoutes.get_resource_templates(base_url)
|
9
9
|
|
10
10
|
respond_to do |format|
|
11
11
|
format.html # index.html.erb
|
12
|
-
format.json { render :json =>
|
12
|
+
format.json { render :json => ResourceTemplate.to_json(resource_templates) }
|
13
13
|
format.yaml do
|
14
|
-
yaml =
|
14
|
+
yaml = resource_templates.to_yaml(resource_templates)
|
15
15
|
yaml = yaml.grep(/(name|rel|path_template|uri_template|resources):|^---/).to_s if ['true', '1'].member?(params["short"])
|
16
16
|
render :text => yaml
|
17
17
|
end
|
18
18
|
format.xml do
|
19
|
-
render :xml =>
|
19
|
+
render :xml => ResourceTemplate::to_xml(
|
20
20
|
Builder::XmlMarkup.new(:indent => 2),
|
21
|
-
|
21
|
+
resource_templates).target!
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def show
|
27
|
+
base_url = root_url rescue nil
|
28
|
+
resources = RailsRoutes.get_resource_templates(base_url)
|
29
|
+
resource_template = ResourceTemplate.all_by_name(resources)[params[:id]]
|
30
|
+
|
31
|
+
respond_to do |format|
|
32
|
+
format.html # show.html.erb
|
33
|
+
format.json { render :json => resource_template.to_json }
|
34
|
+
format.yaml do
|
35
|
+
yaml = resource_template.to_yaml
|
36
|
+
yaml = yaml.grep(/(name|rel|path_template|uri_template|resources):|^---/).to_s if ['true', '1'].member?(params["short"])
|
37
|
+
render :text => yaml
|
38
|
+
end
|
39
|
+
format.xml do
|
40
|
+
render :xml => resource_template.to_xml(Builder::XmlMarkup.new(:indent => 2)).target!
|
22
41
|
end
|
23
42
|
end
|
24
43
|
end
|
@@ -1,12 +1,19 @@
|
|
1
|
-
require 'described_routes'
|
1
|
+
require 'described_routes/resource_template'
|
2
2
|
|
3
3
|
module DescribedRoutes
|
4
4
|
module RailsRoutes
|
5
|
+
#
|
6
|
+
# Process Rails routes and return an array of DescribedRoutes::ResourceTemplate objects
|
7
|
+
#
|
8
|
+
def self.get_resource_templates(base_url = nil)
|
9
|
+
DescribedRoutes::ResourceTemplate.from_parsed(get_parsed_rails_resources(base_url))
|
10
|
+
end
|
11
|
+
|
5
12
|
#
|
6
13
|
# Based on the implementation of "rake routes". Returns a hash of Rails path specifications (slightly normalized)
|
7
14
|
# mapped to hashes of the attributes we need.
|
8
15
|
#
|
9
|
-
def self.get_rails_resources
|
16
|
+
def self.get_rails_resources #:nodoc:
|
10
17
|
ActionController::Routing::Routes.routes.inject({}) do |resources, route|
|
11
18
|
name = ActionController::Routing::Routes.named_routes.routes.index(route).to_s
|
12
19
|
controller = route.parameter_shell[:controller]
|
@@ -19,7 +26,11 @@ module DescribedRoutes
|
|
19
26
|
# TODO - probably a better way to do this, just need a pattern that matches :id and not :id[a-zA-Z0-9_]+
|
20
27
|
segs.gsub!(/:[a-zA-Z0-9_]+/) do |match|
|
21
28
|
if match == ":id" && controller
|
22
|
-
|
29
|
+
if controller == "described_routes/rails"
|
30
|
+
"{route_name}"
|
31
|
+
else
|
32
|
+
":#{controller.singularize.sub(/.*\//, "")}_id"
|
33
|
+
end
|
23
34
|
else
|
24
35
|
match
|
25
36
|
end
|
@@ -79,9 +90,10 @@ module DescribedRoutes
|
|
79
90
|
end
|
80
91
|
|
81
92
|
#
|
82
|
-
# Takes the routes from Rails and produces the required tree structure.
|
93
|
+
# Takes the routes from Rails and produces the required tree structure. Returns the "parsed" format - i.e. a representation
|
94
|
+
# in Ruby Array and Hash objects
|
83
95
|
#
|
84
|
-
def self.
|
96
|
+
def self.get_parsed_rails_resources(base_url = nil) #:nodoc:
|
85
97
|
base_url = base_url.sub(/\/$/, '') if base_url
|
86
98
|
resources = get_rails_resources
|
87
99
|
resources.delete_if{|k, v| v["name"].blank? or v["name"] =~ /^formatted/}
|
@@ -99,8 +111,8 @@ module DescribedRoutes
|
|
99
111
|
# compare parent and child names, and populate "rel" with either
|
100
112
|
# 1) a prefix (probably an action name)
|
101
113
|
# 2) a suffix (probably a nested resource)
|
102
|
-
#
|
103
|
-
#
|
114
|
+
# 3) the child's name if the parent and child's params are identical
|
115
|
+
# If none of the above applies, the child must be identifable by parameter
|
104
116
|
name = resource["name"]
|
105
117
|
prefix = /^(.*)_#{name}$/
|
106
118
|
suffix = /^#{name}_(.*)$/
|
@@ -110,13 +122,15 @@ module DescribedRoutes
|
|
110
122
|
child["rel"] = $1
|
111
123
|
elsif child_name =~ suffix
|
112
124
|
child["rel"] = $1
|
113
|
-
|
125
|
+
elsif child["params"] == resource["params"]
|
126
|
+
child["rel"] = child["name"]
|
127
|
+
end
|
114
128
|
end
|
115
129
|
|
116
130
|
resource
|
117
131
|
end
|
118
132
|
end
|
119
|
-
|
133
|
+
|
120
134
|
#
|
121
135
|
# Depth-first tree traversal
|
122
136
|
#
|
@@ -60,11 +60,113 @@ module DescribedRoutes
|
|
60
60
|
|
61
61
|
hash["options"] = options if options && !options.empty?
|
62
62
|
|
63
|
-
hashes = DescribedRoutes.to_parsed(resource_templates)
|
63
|
+
hashes = DescribedRoutes::ResourceTemplate.to_parsed(resource_templates)
|
64
64
|
hash["resource_templates"] = hashes if hashes && !hashes.empty?
|
65
65
|
|
66
66
|
hash
|
67
67
|
end
|
68
|
+
|
69
|
+
# Convert to JSON
|
70
|
+
def to_json
|
71
|
+
to_hash.to_json
|
72
|
+
end
|
73
|
+
|
74
|
+
# Convert to YAML
|
75
|
+
def to_yaml
|
76
|
+
to_hash.to_json
|
77
|
+
end
|
78
|
+
|
79
|
+
#
|
80
|
+
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
81
|
+
#
|
82
|
+
def to_xml(xm)
|
83
|
+
xm.ResourceTemplate do |xm|
|
84
|
+
value_tag(xm, "rel")
|
85
|
+
value_tag(xm, "name")
|
86
|
+
value_tag(xm, "path_template")
|
87
|
+
value_tag(xm, "uri_template")
|
88
|
+
|
89
|
+
list_tag(xm, params, "Params", "param")
|
90
|
+
list_tag(xm, optional_params, "OptionalParams", "param")
|
91
|
+
|
92
|
+
# could use a list of elements here, but let's follow HTTP's lead and reduce the verbosity
|
93
|
+
xm.options(options.join(", ")) unless options.empty?
|
94
|
+
|
95
|
+
self.class.to_xml(xm, resource_templates) unless resource_templates.empty?
|
96
|
+
end
|
97
|
+
xm
|
98
|
+
end
|
99
|
+
|
100
|
+
def value_tag(xm, tag) #:nodoc:
|
101
|
+
value = self.send(tag.to_sym)
|
102
|
+
xm.tag!(tag, value) unless value.blank?
|
103
|
+
end
|
104
|
+
|
105
|
+
def list_tag(xm, collection, collection_tag, member_tag) #:nodoc:
|
106
|
+
unless collection.nil? or collection.empty?
|
107
|
+
xm.tag!(collection_tag) do |xm|
|
108
|
+
collection.each do |value|
|
109
|
+
xm.tag!(member_tag, value)
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
# Convert an array of ResourceTemplate objects to array of hashes equivalent to their JSON or YAML representations
|
116
|
+
def self.to_parsed(resource_templates)
|
117
|
+
resource_templates.map{|resource_template| resource_template.to_hash}
|
118
|
+
end
|
119
|
+
|
120
|
+
# Convert an array of ResourceTemplate objects to JSON
|
121
|
+
def self.to_json(resource_templates)
|
122
|
+
self.to_parsed(resource_templates).to_json
|
123
|
+
end
|
124
|
+
|
125
|
+
# Convert an array of ResourceTemplate objects to YAML
|
126
|
+
def self.to_yaml(resource_templates)
|
127
|
+
self.to_parsed(resource_templates).to_yaml
|
128
|
+
end
|
129
|
+
|
130
|
+
# Create an array of ResourceTemplate objects from a JSON string
|
131
|
+
def self.parse_json(json)
|
132
|
+
self.from_parsed(JSON.parse(json))
|
133
|
+
end
|
134
|
+
|
135
|
+
# Create an array of ResourceTemplate objects from a JSON string
|
136
|
+
def self.parse_yaml(yaml)
|
137
|
+
self.from_parsed(YAML::load(yaml))
|
138
|
+
end
|
139
|
+
|
140
|
+
# Create an array of ResourceTemplate objects from an array of hashes
|
141
|
+
def self.from_parsed(parsed)
|
142
|
+
raise ArgumentError.new("not an array") unless parsed.kind_of?(Array)
|
143
|
+
|
144
|
+
parsed.map do |hash|
|
145
|
+
ResourceTemplate.from_hash(hash)
|
146
|
+
end
|
147
|
+
end
|
148
|
+
|
149
|
+
#
|
150
|
+
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
151
|
+
#
|
152
|
+
def self.to_xml(xm, resource_templates)
|
153
|
+
xm.ResourceTemplates do |xm|
|
154
|
+
resource_templates.each do |resource_template|
|
155
|
+
resource_template.to_xml(xm)
|
156
|
+
end
|
157
|
+
end
|
158
|
+
xm
|
159
|
+
end
|
160
|
+
|
161
|
+
# Get a hash of all named ResourceTemplate objects contained in the supplied collection, keyed by name
|
162
|
+
def self.all_by_name(resource_templates, h = {})
|
163
|
+
resource_templates.inject(h) do |hash, resource_template|
|
164
|
+
hash[resource_template.name] = resource_template if resource_template.name
|
165
|
+
all_by_name(resource_template.resource_templates, hash)
|
166
|
+
hash
|
167
|
+
end
|
168
|
+
h
|
169
|
+
end
|
68
170
|
end
|
69
171
|
end
|
70
172
|
|
@@ -6,24 +6,44 @@ namespace :described_routes do
|
|
6
6
|
desc "Describe resource structure in JSON format"
|
7
7
|
|
8
8
|
task :json => :environment do
|
9
|
-
puts DescribedRoutes::
|
9
|
+
puts DescribedRoutes::ResourceTemplate.to_json(
|
10
|
+
DescribedRoutes::RailsRoutes.get_resource_templates)
|
10
11
|
end
|
11
12
|
|
12
13
|
desc "Describe resource structure in YAML format"
|
13
14
|
task :yaml => :environment do
|
14
|
-
puts DescribedRoutes::
|
15
|
+
puts DescribedRoutes::ResourceTemplate.to_yaml(
|
16
|
+
DescribedRoutes::RailsRoutes.get_resource_templates)
|
15
17
|
end
|
16
18
|
|
17
19
|
desc "Describe resource structure in YAML format (basic structure only)"
|
18
20
|
task :yaml_short => :environment do
|
19
|
-
puts DescribedRoutes::
|
21
|
+
puts DescribedRoutes::ResourceTemplate.to_yaml(
|
22
|
+
DescribedRoutes::RailsRoutes.get_resource_templates).grep(
|
23
|
+
/(name|rel|path_template|uri_template|resources):|^---/)
|
20
24
|
end
|
21
25
|
|
22
26
|
desc "Describe resource structure in XML format"
|
23
27
|
task :xml => :environment do
|
24
|
-
puts DescribedRoutes::to_xml(
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
+
puts DescribedRoutes::ResourceTemplate.to_xml(
|
29
|
+
Builder::XmlMarkup.new(:indent => 2),
|
30
|
+
DescribedRoutes::RailsRoutes.get_resource_templates
|
31
|
+
).target!
|
32
|
+
end
|
33
|
+
|
34
|
+
# unsupported, for testing
|
35
|
+
task :ruby => :environment do
|
36
|
+
puts DescribedRoutes::ResourceTemplate.to_parsed(
|
37
|
+
DescribedRoutes::RailsRoutes.get_resource_templates).inspect
|
38
|
+
end
|
39
|
+
|
40
|
+
# unsupported
|
41
|
+
task :get_rails_resources => :environment do
|
42
|
+
puts DescribedRoutes::RailsRoutes.get_rails_resources.inspect
|
43
|
+
end
|
44
|
+
|
45
|
+
# unsupported
|
46
|
+
task :get_parsed_rails_resources => :environment do
|
47
|
+
puts DescribedRoutes::RailsRoutes.get_parsed_rails_resources.inspect
|
28
48
|
end
|
29
49
|
end
|
@@ -0,0 +1 @@
|
|
1
|
+
[{"name":"root","path_template":"\/"},{"name":"admin_products","resource_templates":[{"name":"admin_product","resource_templates":[{"name":"edit_admin_product","options":["GET"],"path_template":"\/admin\/products\/{product_id}\/edit{-prefix|.|format}","rel":"edit"}],"options":["GET","PUT","DELETE"],"path_template":"\/admin\/products\/{product_id}{-prefix|.|format}"},{"name":"new_admin_product","options":["GET"],"path_template":"\/admin\/products\/new{-prefix|.|format}","rel":"new_admin_product"}],"options":["GET","POST"],"path_template":"\/admin\/products{-prefix|.|format}"},{"name":"described_routes","resource_templates":[{"name":"new_described_route","options":["GET"],"path_template":"\/described_routes\/new{-prefix|.|format}","rel":"new_described_route"},{"name":"described_route","resource_templates":[{"name":"edit_described_route","options":["GET"],"path_template":"\/described_routes\/{route_name}\/edit{-prefix|.|format}","rel":"edit"}],"options":["GET","PUT","DELETE"],"path_template":"\/described_routes\/{route_name}{-prefix|.|format}","rel":"described_route"}],"options":["GET","POST"],"path_template":"\/described_routes{-prefix|.|format}"},{"name":"pages","resource_templates":[{"name":"page","resource_templates":[{"name":"edit_page","options":["GET"],"path_template":"\/pages\/{page_id}\/edit{-prefix|.|format}","rel":"edit"},{"name":"summary_page","options":["GET"],"path_template":"\/pages\/{page_id}\/summary{-prefix|.|format}","rel":"summary"},{"name":"toggle_visibility_page","options":["POST"],"path_template":"\/pages\/{page_id}\/toggle_visibility{-prefix|.|format}","rel":"toggle_visibility"}],"options":["GET","PUT","DELETE"],"path_template":"\/pages\/{page_id}{-prefix|.|format}"},{"name":"new_page","options":["GET"],"path_template":"\/pages\/new{-prefix|.|format}","rel":"new_page"}],"options":["GET","POST"],"path_template":"\/pages{-prefix|.|format}"},{"name":"users","resource_templates":[{"name":"user","resource_templates":[{"name":"user_articles","resource_templates":[{"name":"user_article","resource_templates":[{"name":"edit_user_article","options":["GET"],"path_template":"\/users\/{user_id}\/articles\/{article_id}\/edit{-prefix|.|format}","rel":"edit"}],"options":["GET","PUT","DELETE"],"path_template":"\/users\/{user_id}\/articles\/{article_id}{-prefix|.|format}"},{"name":"new_user_article","options":["GET"],"path_template":"\/users\/{user_id}\/articles\/new{-prefix|.|format}","rel":"new_user_article"},{"name":"recent_user_articles","options":["GET"],"path_template":"\/users\/{user_id}\/articles\/recent{-prefix|.|format}","rel":"recent"}],"options":["GET","POST"],"path_template":"\/users\/{user_id}\/articles{-prefix|.|format}","rel":"articles"},{"name":"edit_user","options":["GET"],"path_template":"\/users\/{user_id}\/edit{-prefix|.|format}","rel":"edit"},{"name":"user_profile","resource_templates":[{"name":"edit_user_profile","options":["GET"],"path_template":"\/users\/{user_id}\/profile\/edit{-prefix|.|format}","rel":"edit"},{"name":"new_user_profile","options":["GET"],"path_template":"\/users\/{user_id}\/profile\/new{-prefix|.|format}","rel":"new"}],"options":["GET","PUT","DELETE","POST"],"path_template":"\/users\/{user_id}\/profile{-prefix|.|format}","rel":"profile"}],"options":["GET","PUT","DELETE"],"path_template":"\/users\/{user_id}{-prefix|.|format}"},{"name":"new_user","options":["GET"],"path_template":"\/users\/new{-prefix|.|format}","rel":"new_user"}],"options":["GET","POST"],"path_template":"\/users{-prefix|.|format}"}]
|
@@ -1,2 +1,45 @@
|
|
1
1
|
require 'test/unit'
|
2
2
|
require 'described_routes/resource_template'
|
3
|
+
|
4
|
+
class TestResourceTemplate < Test::Unit::TestCase
|
5
|
+
attr_reader :json, :resource_templates, :resource_templates_by_name, :user_articles, :user_article, :edit_user_article
|
6
|
+
|
7
|
+
|
8
|
+
def setup
|
9
|
+
@json ||= File.read(File.dirname(__FILE__) + "/fixtures/described_routes_test.json")
|
10
|
+
@resource_templates = DescribedRoutes::ResourceTemplate.parse_json(json)
|
11
|
+
@resource_templates_by_name = DescribedRoutes::ResourceTemplate.all_by_name(@resource_templates)
|
12
|
+
@user_articles = @resource_templates_by_name["user_articles"]
|
13
|
+
@user_article = @resource_templates_by_name["user_article"]
|
14
|
+
@edit_user_article = @resource_templates_by_name["edit_user_article"]
|
15
|
+
end
|
16
|
+
|
17
|
+
def test_fixture
|
18
|
+
assert_kind_of(DescribedRoutes::ResourceTemplate, user_articles)
|
19
|
+
assert_kind_of(DescribedRoutes::ResourceTemplate, user_article)
|
20
|
+
assert_kind_of(DescribedRoutes::ResourceTemplate, edit_user_article)
|
21
|
+
|
22
|
+
assert_equal("user_article", user_article.name)
|
23
|
+
assert_equal([], user_article.params)
|
24
|
+
assert_equal([], user_article.optional_params)
|
25
|
+
|
26
|
+
assert_equal("articles", user_articles.rel)
|
27
|
+
assert_nil(user_article.rel)
|
28
|
+
assert_equal("edit", edit_user_article.rel)
|
29
|
+
|
30
|
+
assert(user_articles.resource_templates.member?(user_article))
|
31
|
+
assert(user_article.resource_templates.member?(edit_user_article))
|
32
|
+
end
|
33
|
+
|
34
|
+
def test_json
|
35
|
+
assert_equal(
|
36
|
+
JSON.parse(json),
|
37
|
+
JSON.parse(DescribedRoutes::ResourceTemplate.to_json(resource_templates)))
|
38
|
+
end
|
39
|
+
|
40
|
+
def test_yaml
|
41
|
+
assert_equal(
|
42
|
+
JSON.parse(json),
|
43
|
+
YAML.load(DescribedRoutes::ResourceTemplate.to_yaml(resource_templates)))
|
44
|
+
end
|
45
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: described_routes
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Mike Burrows
|
@@ -9,7 +9,7 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2009-04-
|
12
|
+
date: 2009-04-29 00:00:00 +01:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
@@ -59,6 +59,7 @@ files:
|
|
59
59
|
- script/console
|
60
60
|
- script/destroy
|
61
61
|
- script/generate
|
62
|
+
- test/fixtures/described_routes_test.json
|
62
63
|
- test/test_described_routes.rb
|
63
64
|
- test/test_helper.rb
|
64
65
|
- test/test_resource_template.rb
|