described_routes 0.4.1 → 0.5.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/History.txt +7 -0
- data/Manifest.txt +1 -4
- data/README.rdoc +0 -3
- data/lib/described_routes/rails_controller.rb +10 -24
- data/lib/described_routes/rails_routes.rb +3 -3
- data/lib/described_routes/rake_task_methods.rb +9 -17
- data/lib/described_routes.rb +2 -2
- data/lib/resource_template.rb +258 -0
- data/lib/tasks/described_routes.rb +1 -6
- data/test/test_resource_template.rb +25 -25
- data/test_rails_app/test/integration/described_routes_run_time_test.rb +0 -6
- data/test_rails_app/test/integration/rake_tasks_test.rb +0 -9
- metadata +3 -6
- data/lib/described_routes/resource_template.rb +0 -248
- data/test_rails_app/test/fixtures/build_time/described_routes.yaml_short +0 -72
- data/test_rails_app/test/fixtures/build_time/described_routes.yaml_short_no_admin +0 -62
- data/test_rails_app/test/fixtures/run_time/described_routes.yaml_short +0 -99
data/History.txt
CHANGED
|
@@ -1,3 +1,10 @@
|
|
|
1
|
+
== 0.5.0 2009-05-22
|
|
2
|
+
|
|
3
|
+
* API refactor, a possible prelude to new resource_template gem:
|
|
4
|
+
* Top level class ResourceTemplate (was DescribedRoutes::ResourceTemplate)
|
|
5
|
+
* New class ResourceTemplate::ResourceTemplates to which most of ResourceTemplate's class methods have been moved
|
|
6
|
+
* Removed the yaml_short format (superseded by the plain text format)
|
|
7
|
+
|
|
1
8
|
== 0.4.1 2009-05-20
|
|
2
9
|
|
|
3
10
|
* Configure gem dependency on addressable 2.1.0 (now available on RubyForge)
|
data/Manifest.txt
CHANGED
|
@@ -8,7 +8,7 @@ lib/described_routes.rb
|
|
|
8
8
|
lib/described_routes/rails_controller.rb
|
|
9
9
|
lib/described_routes/rails_routes.rb
|
|
10
10
|
lib/described_routes/rake_task_methods.rb
|
|
11
|
-
lib/
|
|
11
|
+
lib/resource_template.rb
|
|
12
12
|
lib/tasks/described_routes.rb
|
|
13
13
|
script/console
|
|
14
14
|
script/destroy
|
|
@@ -38,13 +38,10 @@ test_rails_app/test/fixtures/build_time/described_routes.json
|
|
|
38
38
|
test_rails_app/test/fixtures/build_time/described_routes.text
|
|
39
39
|
test_rails_app/test/fixtures/build_time/described_routes.xml
|
|
40
40
|
test_rails_app/test/fixtures/build_time/described_routes.yaml
|
|
41
|
-
test_rails_app/test/fixtures/build_time/described_routes.yaml_short
|
|
42
|
-
test_rails_app/test/fixtures/build_time/described_routes.yaml_short_no_admin
|
|
43
41
|
test_rails_app/test/fixtures/run_time/described_routes.json
|
|
44
42
|
test_rails_app/test/fixtures/run_time/described_routes.text
|
|
45
43
|
test_rails_app/test/fixtures/run_time/described_routes.xml
|
|
46
44
|
test_rails_app/test/fixtures/run_time/described_routes.yaml
|
|
47
|
-
test_rails_app/test/fixtures/run_time/described_routes.yaml_short
|
|
48
45
|
test_rails_app/test/integration/described_routes_run_time_test.rb
|
|
49
46
|
test_rails_app/test/integration/rake_tasks_test.rb
|
|
50
47
|
test_rails_app/test/test_helper.rb
|
data/README.rdoc
CHANGED
|
@@ -22,7 +22,6 @@ Then:
|
|
|
22
22
|
rake described_routes:json # Describe resource structure in JSON format
|
|
23
23
|
rake described_routes:xml # Describe resource structure in XML format
|
|
24
24
|
rake described_routes:yaml # Describe resource structure in YAML format
|
|
25
|
-
rake described_routes:yaml_short # Describe resource structure in YAML format (basic structure only)
|
|
26
25
|
rake described_routes:text # Describe resource structure in text (comparable to "rake routes")
|
|
27
26
|
|
|
28
27
|
The text output looks like this:
|
|
@@ -76,7 +75,6 @@ You (or your client application) can now browse to any of the following top leve
|
|
|
76
75
|
* .../described_routes.json
|
|
77
76
|
* .../described_routes.xml
|
|
78
77
|
* .../described_routes.yaml
|
|
79
|
-
* .../described_routes.yaml?short=true
|
|
80
78
|
* .../described_routes.ytxt
|
|
81
79
|
|
|
82
80
|
and for the named route "users" (say):
|
|
@@ -84,7 +82,6 @@ and for the named route "users" (say):
|
|
|
84
82
|
* .../described_routes/users.json
|
|
85
83
|
* .../described_routes/users.xml
|
|
86
84
|
* .../described_routes/users.yaml
|
|
87
|
-
* .../described_routes/users.yaml?short=true
|
|
88
85
|
* .../described_routes/users.txt
|
|
89
86
|
|
|
90
87
|
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.
|
|
@@ -5,44 +5,30 @@ module DescribedRoutes
|
|
|
5
5
|
class RailsController < ActionController::Base
|
|
6
6
|
def index
|
|
7
7
|
base_url = root_url rescue nil
|
|
8
|
-
resource_templates =
|
|
8
|
+
resource_templates = RailsRoutes.get_resource_templates(base_url).partial_expand(request.query_parameters)
|
|
9
9
|
|
|
10
10
|
respond_to do |format|
|
|
11
11
|
format.html # index.html.erb
|
|
12
|
-
format.json { render :json =>
|
|
13
|
-
format.text { render :text =>
|
|
14
|
-
format.yaml
|
|
15
|
-
|
|
16
|
-
yaml = yaml.grep(/(name|rel|path_template|uri_template|resources):|^---/).to_s if ['true', '1'].member?(params["short"])
|
|
17
|
-
render :text => yaml
|
|
18
|
-
end
|
|
19
|
-
format.xml do
|
|
20
|
-
render :xml => ResourceTemplate::to_xml(
|
|
21
|
-
Builder::XmlMarkup.new(:indent => 2),
|
|
22
|
-
resource_templates).target!
|
|
23
|
-
end
|
|
12
|
+
format.json { render :json => resource_templates.to_json }
|
|
13
|
+
format.text { render :text => resource_templates.to_text }
|
|
14
|
+
format.yaml { render :text => resource_templates.to_yaml }
|
|
15
|
+
format.xml { render :xml => resource_templates.to_xml(Builder::XmlMarkup.new(:indent => 2)).target! }
|
|
24
16
|
end
|
|
25
17
|
end
|
|
26
18
|
|
|
27
19
|
def show
|
|
28
20
|
base_url = root_url rescue nil
|
|
29
|
-
|
|
30
|
-
resource_template =
|
|
21
|
+
resource_templates = RailsRoutes.get_resource_templates(base_url).partial_expand(request.query_parameters)
|
|
22
|
+
resource_template = resource_templates.all_by_name[params[:id]]
|
|
31
23
|
# TODO 404 if nil
|
|
32
24
|
resource_template = resource_template.partial_expand(request.query_parameters)
|
|
33
25
|
|
|
34
26
|
respond_to do |format|
|
|
35
27
|
format.html # show.html.erb
|
|
36
28
|
format.json { render :json => resource_template.to_json }
|
|
37
|
-
format.text { render :text =>
|
|
38
|
-
format.
|
|
39
|
-
|
|
40
|
-
end
|
|
41
|
-
format.yaml do
|
|
42
|
-
yaml = resource_template.to_yaml
|
|
43
|
-
yaml = yaml.grep(/(name|rel|path_template|uri_template|resources):|^---/).to_s if ['true', '1'].member?(params["short"])
|
|
44
|
-
render :text => yaml
|
|
45
|
-
end
|
|
29
|
+
format.text { render :text => resource_template.to_text }
|
|
30
|
+
format.yaml { render :text => resource_template.to_yaml }
|
|
31
|
+
format.xml { render :xml => resource_template.to_xml(Builder::XmlMarkup.new(:indent => 2)).target! }
|
|
46
32
|
end
|
|
47
33
|
end
|
|
48
34
|
end
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
require '
|
|
1
|
+
require 'resource_template'
|
|
2
2
|
|
|
3
3
|
module DescribedRoutes
|
|
4
4
|
module RailsRoutes
|
|
@@ -11,12 +11,12 @@ module DescribedRoutes
|
|
|
11
11
|
mattr_accessor :parsed_hook
|
|
12
12
|
|
|
13
13
|
#
|
|
14
|
-
# Process Rails routes and return an array of
|
|
14
|
+
# Process Rails routes and return an array of ResourceTemplate objects
|
|
15
15
|
#
|
|
16
16
|
def self.get_resource_templates(base_url = nil)
|
|
17
17
|
parsed = get_parsed_rails_resources(base_url)
|
|
18
18
|
parsed = parsed_hook.call(parsed) if parsed_hook
|
|
19
|
-
|
|
19
|
+
ResourceTemplate::ResourceTemplates.new(parsed)
|
|
20
20
|
end
|
|
21
21
|
|
|
22
22
|
#
|
|
@@ -4,35 +4,27 @@ module DescribedRoutes
|
|
|
4
4
|
module RakeTaskMethods
|
|
5
5
|
# Describe resource structure in JSON format
|
|
6
6
|
def self.json
|
|
7
|
-
|
|
8
|
-
DescribedRoutes::RailsRoutes.get_resource_templates(ENV['BASE']))
|
|
7
|
+
get_routes.to_json
|
|
9
8
|
end
|
|
10
9
|
|
|
11
10
|
# "Describe resource structure in YAML format
|
|
12
11
|
def self.yaml
|
|
13
|
-
|
|
14
|
-
DescribedRoutes::RailsRoutes.get_resource_templates(ENV['BASE']))
|
|
15
|
-
end
|
|
16
|
-
|
|
17
|
-
# Describe resource structure in YAML format (basic structure only)
|
|
18
|
-
def self.yaml_short
|
|
19
|
-
DescribedRoutes::ResourceTemplate.to_yaml(
|
|
20
|
-
DescribedRoutes::RailsRoutes.get_resource_templates(ENV['BASE'])).grep(
|
|
21
|
-
/(name|rel|path_template|uri_template|resources):|^---/).join
|
|
12
|
+
get_routes.to_yaml
|
|
22
13
|
end
|
|
23
14
|
|
|
24
15
|
# Describe resource structure in XML format
|
|
25
16
|
def self.xml
|
|
26
|
-
|
|
27
|
-
Builder::XmlMarkup.new(:indent => 2),
|
|
28
|
-
DescribedRoutes::RailsRoutes.get_resource_templates(ENV['BASE'])
|
|
29
|
-
).target!
|
|
17
|
+
get_routes.to_xml(Builder::XmlMarkup.new(:indent => 2)).target!
|
|
30
18
|
end
|
|
31
19
|
|
|
32
20
|
# Describe resource structure in text format
|
|
33
21
|
def self.text
|
|
34
|
-
|
|
35
|
-
|
|
22
|
+
get_routes.to_text
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
# Gets the application's routes
|
|
26
|
+
def self.get_routes
|
|
27
|
+
DescribedRoutes::RailsRoutes.get_resource_templates(ENV['BASE'])
|
|
36
28
|
end
|
|
37
29
|
end
|
|
38
30
|
end
|
data/lib/described_routes.rb
CHANGED
|
@@ -0,0 +1,258 @@
|
|
|
1
|
+
require "json"
|
|
2
|
+
require "addressable/template"
|
|
3
|
+
|
|
4
|
+
class ResourceTemplate
|
|
5
|
+
# The template's name. Optional. Making these unique across the application is helpful for clients
|
|
6
|
+
# that may wish to pick out nested templates by name.
|
|
7
|
+
attr_reader :name
|
|
8
|
+
|
|
9
|
+
# Optional attribute that describes a resource's relationship to its parent. For example:
|
|
10
|
+
# * a nested route to a resource's edit page would have rel of "edit"
|
|
11
|
+
# * a nested collection of articles under a "user" resource would have have a rel of "articles"
|
|
12
|
+
# Collection members generally don't need a rel as they are identified by their params
|
|
13
|
+
attr_reader :rel
|
|
14
|
+
|
|
15
|
+
# A template for generating URIs.
|
|
16
|
+
attr_reader :uri_template
|
|
17
|
+
|
|
18
|
+
# A template for generating paths relative to the application's base.
|
|
19
|
+
attr_reader :path_template
|
|
20
|
+
|
|
21
|
+
# The parameters required by the path template
|
|
22
|
+
attr_reader :params
|
|
23
|
+
|
|
24
|
+
# Optional paramaters that may be used by the path template
|
|
25
|
+
attr_reader :optional_params
|
|
26
|
+
|
|
27
|
+
# "options" in the sense of the HTTP option request - i.e. a list of HTTP methods. Optional.
|
|
28
|
+
attr_reader :options
|
|
29
|
+
|
|
30
|
+
# Nested resource templates, a Resources object
|
|
31
|
+
attr_reader :resource_templates
|
|
32
|
+
|
|
33
|
+
# Initialize a ResourceTemplate. See the attribute descriptions above for explanations of the parameters.
|
|
34
|
+
def initialize(name, rel, uri_template, path_template, params, optional_params, options, resource_templates)
|
|
35
|
+
@name, @rel, @uri_template, @path_template = name, rel, uri_template, path_template
|
|
36
|
+
@params = params || []
|
|
37
|
+
@optional_params = optional_params || []
|
|
38
|
+
@options = options || []
|
|
39
|
+
@resource_templates = resource_templates || Resources.new
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Create a ResourceTemplate from its Hash representation
|
|
43
|
+
def self.from_hash(hash)
|
|
44
|
+
attributes = %w(name rel uri_template path_template params optional_params options).map{|k| hash[k]}
|
|
45
|
+
attributes << ResourceTemplates.new(hash["resource_templates"])
|
|
46
|
+
self.new(*attributes)
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
# Convert to a hash (equivalent to its JSON or YAML representation)
|
|
50
|
+
def to_hash
|
|
51
|
+
hash = {}
|
|
52
|
+
hash["name"] = name if name && !name.empty?
|
|
53
|
+
hash["rel"] = rel if rel && !rel.empty?
|
|
54
|
+
hash["uri_template"] = uri_template if uri_template && !uri_template.empty?
|
|
55
|
+
hash["path_template"] = path_template if path_template && !path_template.empty?
|
|
56
|
+
|
|
57
|
+
hash["params"] = params if params && !params.empty?
|
|
58
|
+
hash["optional_params"] = optional_params if optional_params && !optional_params.empty?
|
|
59
|
+
|
|
60
|
+
hash["options"] = options if options && !options.empty?
|
|
61
|
+
|
|
62
|
+
hash["resource_templates"] = resource_templates.to_parsed if !resource_templates.empty?
|
|
63
|
+
|
|
64
|
+
hash
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
# Convert to JSON
|
|
68
|
+
def to_json
|
|
69
|
+
to_hash.to_json
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Convert to YAML
|
|
73
|
+
def to_yaml
|
|
74
|
+
to_hash.to_yaml
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
# Text report
|
|
78
|
+
def to_text
|
|
79
|
+
ResourceTemplates.new([self]).to_text
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
#
|
|
83
|
+
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
|
84
|
+
#
|
|
85
|
+
def to_xml(xm)
|
|
86
|
+
xm.ResourceTemplate do |xm|
|
|
87
|
+
value_tag(xm, "rel")
|
|
88
|
+
value_tag(xm, "name")
|
|
89
|
+
value_tag(xm, "path_template")
|
|
90
|
+
value_tag(xm, "uri_template")
|
|
91
|
+
|
|
92
|
+
list_tag(xm, params, "Params", "param")
|
|
93
|
+
list_tag(xm, optional_params, "OptionalParams", "param")
|
|
94
|
+
|
|
95
|
+
# could use a list of elements here, but let's follow HTTP's lead and reduce the verbosity
|
|
96
|
+
xm.options(options.join(", ")) unless options.empty?
|
|
97
|
+
|
|
98
|
+
resource_templates.to_xml(xm) unless resource_templates.empty?
|
|
99
|
+
end
|
|
100
|
+
xm
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def value_tag(xm, tag) #:nodoc:
|
|
104
|
+
value = self.send(tag.to_sym)
|
|
105
|
+
xm.tag!(tag, value) unless value.blank?
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
def list_tag(xm, collection, collection_tag, member_tag) #:nodoc:
|
|
109
|
+
unless collection.nil? or collection.empty?
|
|
110
|
+
xm.tag!(collection_tag) do |xm|
|
|
111
|
+
collection.each do |value|
|
|
112
|
+
xm.tag!(member_tag, value)
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
end
|
|
116
|
+
end
|
|
117
|
+
|
|
118
|
+
# returns params and any optional_params in order, removing the parent's params
|
|
119
|
+
def positional_params(parent)
|
|
120
|
+
all_params = params + optional_params
|
|
121
|
+
if parent
|
|
122
|
+
all_params - parent.params
|
|
123
|
+
else
|
|
124
|
+
all_params
|
|
125
|
+
end
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
# Return a new resource template with the path_template or uri_template partially expanded with the given params
|
|
129
|
+
def partial_expand(actual_params)
|
|
130
|
+
self.class.new(
|
|
131
|
+
name,
|
|
132
|
+
rel,
|
|
133
|
+
partial_expand_uri_template(uri_template, actual_params),
|
|
134
|
+
partial_expand_uri_template(path_template, actual_params),
|
|
135
|
+
params - actual_params.keys,
|
|
136
|
+
optional_params - actual_params.keys,
|
|
137
|
+
options,
|
|
138
|
+
resource_templates.partial_expand(actual_params))
|
|
139
|
+
end
|
|
140
|
+
|
|
141
|
+
# Partially expand a URI template
|
|
142
|
+
def partial_expand_uri_template(template, params)#:nodoc:
|
|
143
|
+
template && Addressable::Template.new(template).partial_expand(params).pattern
|
|
144
|
+
end
|
|
145
|
+
|
|
146
|
+
class ResourceTemplates < Array
|
|
147
|
+
# Initialize Resources (i.e. a new collection of ResourceTemplate objects) from given collection of ResourceTemplates or hashes
|
|
148
|
+
def initialize(collection=[])
|
|
149
|
+
if collection
|
|
150
|
+
raise ArgumentError.new("#{collection.inspect} is not a collection") unless collection.kind_of?(Enumerable)
|
|
151
|
+
|
|
152
|
+
collection.each do |r|
|
|
153
|
+
if r.kind_of?(ResourceTemplate)
|
|
154
|
+
push(r)
|
|
155
|
+
elsif r.kind_of?(Hash)
|
|
156
|
+
push(ResourceTemplate.from_hash(r))
|
|
157
|
+
else
|
|
158
|
+
raise ArgumentError.new("#{r.inspect} is neither a ResourceTemplate nor a Hash")
|
|
159
|
+
end
|
|
160
|
+
end
|
|
161
|
+
end
|
|
162
|
+
end
|
|
163
|
+
|
|
164
|
+
# Create Resources from a YAML string
|
|
165
|
+
def self.parse_yaml(yaml)
|
|
166
|
+
new(YAML::load(yaml))
|
|
167
|
+
end
|
|
168
|
+
|
|
169
|
+
# Create Resources from a JSON string
|
|
170
|
+
def self.parse_json(json)
|
|
171
|
+
new(JSON.parse(json))
|
|
172
|
+
end
|
|
173
|
+
|
|
174
|
+
# Create Resources from an XML string
|
|
175
|
+
def self.parse_xml
|
|
176
|
+
raise NotImplementedError.new
|
|
177
|
+
end
|
|
178
|
+
|
|
179
|
+
# Convert member ResourceTemplate objects to array of hashes equivalent to their JSON or YAML representations
|
|
180
|
+
def to_parsed
|
|
181
|
+
map {|resource_template| resource_template.to_hash}
|
|
182
|
+
end
|
|
183
|
+
|
|
184
|
+
# Convert an array of ResourceTemplate objects to JSON
|
|
185
|
+
def to_json
|
|
186
|
+
to_parsed.to_json
|
|
187
|
+
end
|
|
188
|
+
|
|
189
|
+
# Convert an array of ResourceTemplate objects to YAML
|
|
190
|
+
def to_yaml
|
|
191
|
+
to_parsed.to_yaml
|
|
192
|
+
end
|
|
193
|
+
|
|
194
|
+
#
|
|
195
|
+
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
|
196
|
+
#
|
|
197
|
+
def to_xml(xm)
|
|
198
|
+
xm.ResourceTemplates do |xm|
|
|
199
|
+
each do |resource_template|
|
|
200
|
+
resource_template.to_xml(xm)
|
|
201
|
+
end
|
|
202
|
+
end
|
|
203
|
+
xm
|
|
204
|
+
end
|
|
205
|
+
|
|
206
|
+
# Get a hash of all named ResourceTemplate objects contained in the supplied collection, keyed by name
|
|
207
|
+
def all_by_name(h = {})
|
|
208
|
+
inject(h) do |hash, resource_template|
|
|
209
|
+
hash[resource_template.name] = resource_template if resource_template.name
|
|
210
|
+
resource_template.resource_templates.all_by_name(hash)
|
|
211
|
+
hash
|
|
212
|
+
end
|
|
213
|
+
h
|
|
214
|
+
end
|
|
215
|
+
|
|
216
|
+
# for #to_text
|
|
217
|
+
def to_table(parent_template = nil, t = [], indent = '')
|
|
218
|
+
inject(t) do |table, resource_template|
|
|
219
|
+
if parent_template
|
|
220
|
+
link = (resource_template.rel || '')
|
|
221
|
+
new_params = resource_template.params - parent_template.params
|
|
222
|
+
else
|
|
223
|
+
link = resource_template.name
|
|
224
|
+
new_params = resource_template.params
|
|
225
|
+
end
|
|
226
|
+
link += new_params.map{|p| "{#{p}}"}.join(', ')
|
|
227
|
+
table << [
|
|
228
|
+
indent + link,
|
|
229
|
+
resource_template.name || '',
|
|
230
|
+
resource_template.options.join(', '),
|
|
231
|
+
resource_template.uri_template || resource_template.path_template
|
|
232
|
+
]
|
|
233
|
+
resource_template.resource_templates.to_table(resource_template, t, indent + ' ')
|
|
234
|
+
end
|
|
235
|
+
t
|
|
236
|
+
end
|
|
237
|
+
|
|
238
|
+
# text report
|
|
239
|
+
def to_text
|
|
240
|
+
table = self.to_table
|
|
241
|
+
|
|
242
|
+
0.upto(2) do |i|
|
|
243
|
+
width = table.map{|row| row[i].length}.max
|
|
244
|
+
table.each do |row|
|
|
245
|
+
row[i] = row[i].ljust(width)
|
|
246
|
+
end
|
|
247
|
+
end
|
|
248
|
+
|
|
249
|
+
table.map{|row| row.join(' ')}.join("\n") + "\n"
|
|
250
|
+
end
|
|
251
|
+
|
|
252
|
+
# Partially expand the path_template or uri_template of the given resource templates with the given params,
|
|
253
|
+
# returning new resource templates
|
|
254
|
+
def partial_expand(actual_params)
|
|
255
|
+
self.class.new(map{|resource_template| resource_template.partial_expand(actual_params)})
|
|
256
|
+
end
|
|
257
|
+
end
|
|
258
|
+
end
|
|
@@ -12,11 +12,6 @@ namespace :described_routes do
|
|
|
12
12
|
puts DescribedRoutes::RakeTaskMethods.yaml
|
|
13
13
|
end
|
|
14
14
|
|
|
15
|
-
desc 'Describe resource structure in YAML format (basic structure only) (optional: add "BASE=http://...")'
|
|
16
|
-
task :yaml_short => :environment do
|
|
17
|
-
puts DescribedRoutes::RakeTaskMethods.yaml_short
|
|
18
|
-
end
|
|
19
|
-
|
|
20
15
|
desc 'Describe resource structure in XML format (optional: add "BASE=http://...")'
|
|
21
16
|
task :xml => :environment do
|
|
22
17
|
puts DescribedRoutes::RakeTaskMethods.xml
|
|
@@ -29,7 +24,7 @@ namespace :described_routes do
|
|
|
29
24
|
|
|
30
25
|
# unsupported
|
|
31
26
|
task :ruby => :environment do
|
|
32
|
-
puts
|
|
27
|
+
puts ResourceTemplate.to_parsed(
|
|
33
28
|
DescribedRoutes::RailsRoutes.get_resource_templates).inspect
|
|
34
29
|
end
|
|
35
30
|
|
|
@@ -1,33 +1,33 @@
|
|
|
1
1
|
require 'test/unit'
|
|
2
|
-
require '
|
|
2
|
+
require 'resource_template'
|
|
3
3
|
|
|
4
4
|
class TestResourceTemplate < Test::Unit::TestCase
|
|
5
5
|
attr_reader :json, :resource_templates, :resource_templates_by_name, :user_articles, :user_article, :edit_user_article
|
|
6
6
|
|
|
7
7
|
def setup
|
|
8
|
-
@json ||= File.read(File.dirname(__FILE__) +
|
|
9
|
-
@resource_templates =
|
|
10
|
-
@resource_templates_by_name =
|
|
11
|
-
@user_articles = @resource_templates_by_name[
|
|
12
|
-
@user_article = @resource_templates_by_name[
|
|
13
|
-
@edit_user_article = @resource_templates_by_name[
|
|
8
|
+
@json ||= File.read(File.dirname(__FILE__) + '/fixtures/described_routes_test.json')
|
|
9
|
+
@resource_templates = ResourceTemplate::ResourceTemplates.parse_json(json)
|
|
10
|
+
@resource_templates_by_name = @resource_templates.all_by_name
|
|
11
|
+
@user_articles = @resource_templates_by_name['user_articles']
|
|
12
|
+
@user_article = @resource_templates_by_name['user_article']
|
|
13
|
+
@edit_user_article = @resource_templates_by_name['edit_user_article']
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
def test_fixture
|
|
17
|
-
assert_kind_of(
|
|
18
|
-
assert_kind_of(
|
|
19
|
-
assert_kind_of(
|
|
17
|
+
assert_kind_of(ResourceTemplate, user_articles)
|
|
18
|
+
assert_kind_of(ResourceTemplate, user_article)
|
|
19
|
+
assert_kind_of(ResourceTemplate, edit_user_article)
|
|
20
20
|
|
|
21
|
-
assert_equal(
|
|
22
|
-
assert_equal([
|
|
23
|
-
assert_equal([
|
|
21
|
+
assert_equal('user_article', user_article.name)
|
|
22
|
+
assert_equal(['user_id', 'article_id'], user_article.params)
|
|
23
|
+
assert_equal(['format'], user_article.optional_params)
|
|
24
24
|
|
|
25
|
-
assert_equal(
|
|
25
|
+
assert_equal('articles', user_articles.rel)
|
|
26
26
|
assert_nil(user_article.rel)
|
|
27
|
-
assert_equal(
|
|
27
|
+
assert_equal('edit', edit_user_article.rel)
|
|
28
28
|
|
|
29
|
-
assert_equal(
|
|
30
|
-
assert_equal(
|
|
29
|
+
assert_equal('/users/{user_id}/articles{-prefix|.|format}', user_articles.path_template)
|
|
30
|
+
assert_equal('http://localhost:3000/users/{user_id}/articles{-prefix|.|format}', user_articles.uri_template)
|
|
31
31
|
|
|
32
32
|
assert(user_articles.resource_templates.member?(user_article))
|
|
33
33
|
assert(user_article.resource_templates.member?(edit_user_article))
|
|
@@ -36,26 +36,26 @@ class TestResourceTemplate < Test::Unit::TestCase
|
|
|
36
36
|
def test_json
|
|
37
37
|
assert_equal(
|
|
38
38
|
JSON.parse(json),
|
|
39
|
-
JSON.parse(
|
|
39
|
+
JSON.parse(resource_templates.to_json))
|
|
40
40
|
end
|
|
41
41
|
|
|
42
42
|
def test_yaml
|
|
43
43
|
assert_equal(
|
|
44
44
|
JSON.parse(json),
|
|
45
|
-
YAML.load(
|
|
45
|
+
YAML.load(resource_templates.to_yaml))
|
|
46
46
|
end
|
|
47
47
|
|
|
48
48
|
def test_positional_params
|
|
49
|
-
assert_equal([
|
|
50
|
-
assert_equal([
|
|
49
|
+
assert_equal(['user_id', 'article_id', 'format'], user_article.positional_params(nil))
|
|
50
|
+
assert_equal(['article_id', 'format'], user_article.positional_params(user_articles))
|
|
51
51
|
end
|
|
52
52
|
|
|
53
53
|
def test_partial_expand
|
|
54
|
-
|
|
55
|
-
expanded_edit_user_article =
|
|
54
|
+
expanded_user_articles = user_articles.partial_expand('user_id' => 'dojo', 'format' => 'json')
|
|
55
|
+
expanded_edit_user_article = expanded_user_articles.resource_templates.all_by_name['edit_user_article']
|
|
56
56
|
|
|
57
|
-
assert_equal([
|
|
57
|
+
assert_equal(['article_id'], expanded_edit_user_article.params)
|
|
58
58
|
assert(expanded_edit_user_article.optional_params.empty?)
|
|
59
|
-
assert_equal(
|
|
59
|
+
assert_equal('/users/dojo/articles/{article_id}/edit.json', expanded_edit_user_article.path_template)
|
|
60
60
|
end
|
|
61
61
|
end
|
|
@@ -29,12 +29,6 @@ class DescribedRoutesRunTimeTest < ActionController::IntegrationTest
|
|
|
29
29
|
assert_equal(read_fixture("yaml"), body)
|
|
30
30
|
end
|
|
31
31
|
|
|
32
|
-
def test_yaml_short
|
|
33
|
-
get "/described_routes.yaml?short=1"
|
|
34
|
-
assert_response :success
|
|
35
|
-
assert_equal(read_fixture("yaml_short"), body)
|
|
36
|
-
end
|
|
37
|
-
|
|
38
32
|
def test_partial_expand
|
|
39
33
|
get "/described_routes/new_user_profile.text?user_id=dojo&format=json"
|
|
40
34
|
assert_equal("new_user_profile new_user_profile GET http://www.example.com/users/dojo/profile/new.json", body.chomp)
|
|
@@ -27,16 +27,7 @@ class RakeTasksTest < Test::Unit::TestCase
|
|
|
27
27
|
assert_equal(read_fixture("yaml"), DescribedRoutes::RakeTaskMethods.yaml)
|
|
28
28
|
end
|
|
29
29
|
|
|
30
|
-
def test_yaml_short
|
|
31
|
-
assert_equal(read_fixture("yaml_short"), DescribedRoutes::RakeTaskMethods.yaml_short)
|
|
32
|
-
end
|
|
33
|
-
|
|
34
30
|
def test_xml
|
|
35
31
|
assert_equal(read_fixture("xml"), DescribedRoutes::RakeTaskMethods.xml)
|
|
36
32
|
end
|
|
37
|
-
|
|
38
|
-
def test_parsed_hook
|
|
39
|
-
DescribedRoutes::RailsRoutes.parsed_hook = lambda {|a| a.reject{|h| h["name"] =~ /^admin/}}
|
|
40
|
-
assert_equal(read_fixture("yaml_short_no_admin"), DescribedRoutes::RakeTaskMethods.yaml_short)
|
|
41
|
-
end
|
|
42
33
|
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.5.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-05-
|
|
12
|
+
date: 2009-05-22 00:00:00 +01:00
|
|
13
13
|
default_executable:
|
|
14
14
|
dependencies:
|
|
15
15
|
- !ruby/object:Gem::Dependency
|
|
@@ -70,7 +70,7 @@ files:
|
|
|
70
70
|
- lib/described_routes/rails_controller.rb
|
|
71
71
|
- lib/described_routes/rails_routes.rb
|
|
72
72
|
- lib/described_routes/rake_task_methods.rb
|
|
73
|
-
- lib/
|
|
73
|
+
- lib/resource_template.rb
|
|
74
74
|
- lib/tasks/described_routes.rb
|
|
75
75
|
- script/console
|
|
76
76
|
- script/destroy
|
|
@@ -100,13 +100,10 @@ files:
|
|
|
100
100
|
- test_rails_app/test/fixtures/build_time/described_routes.text
|
|
101
101
|
- test_rails_app/test/fixtures/build_time/described_routes.xml
|
|
102
102
|
- test_rails_app/test/fixtures/build_time/described_routes.yaml
|
|
103
|
-
- test_rails_app/test/fixtures/build_time/described_routes.yaml_short
|
|
104
|
-
- test_rails_app/test/fixtures/build_time/described_routes.yaml_short_no_admin
|
|
105
103
|
- test_rails_app/test/fixtures/run_time/described_routes.json
|
|
106
104
|
- test_rails_app/test/fixtures/run_time/described_routes.text
|
|
107
105
|
- test_rails_app/test/fixtures/run_time/described_routes.xml
|
|
108
106
|
- test_rails_app/test/fixtures/run_time/described_routes.yaml
|
|
109
|
-
- test_rails_app/test/fixtures/run_time/described_routes.yaml_short
|
|
110
107
|
- test_rails_app/test/integration/described_routes_run_time_test.rb
|
|
111
108
|
- test_rails_app/test/integration/rake_tasks_test.rb
|
|
112
109
|
- test_rails_app/test/test_helper.rb
|
|
@@ -1,248 +0,0 @@
|
|
|
1
|
-
require "json"
|
|
2
|
-
require "addressable/template"
|
|
3
|
-
|
|
4
|
-
module DescribedRoutes
|
|
5
|
-
class ResourceTemplate
|
|
6
|
-
# The template's name. Optional. Making these unique across the application is helpful for clients
|
|
7
|
-
# that may wish to pick out nested templates by name.
|
|
8
|
-
attr_reader :name
|
|
9
|
-
|
|
10
|
-
# Optional attribute that describes a resource's relationship to its parent. For example:
|
|
11
|
-
# * a nested route to a resource's edit page would have rel of "edit"
|
|
12
|
-
# * a nested collection of articles under a "user" resource would have have a rel of "articles"
|
|
13
|
-
# Collection members generally don't need a rel as they are identified by their params
|
|
14
|
-
attr_reader :rel
|
|
15
|
-
|
|
16
|
-
# A template for generating URIs.
|
|
17
|
-
attr_reader :uri_template
|
|
18
|
-
|
|
19
|
-
# A template for generating paths relative to the application's base.
|
|
20
|
-
attr_reader :path_template
|
|
21
|
-
|
|
22
|
-
# The parameters required by the path template
|
|
23
|
-
attr_reader :params
|
|
24
|
-
|
|
25
|
-
# Optional paramaters that may be used by the path template
|
|
26
|
-
attr_reader :optional_params
|
|
27
|
-
|
|
28
|
-
# "options" in the sense of the HTTP option request - i.e. a list of HTTP methods. Optional.
|
|
29
|
-
attr_reader :options
|
|
30
|
-
|
|
31
|
-
# An optional list of nested resource templates
|
|
32
|
-
attr_reader :resource_templates
|
|
33
|
-
|
|
34
|
-
# Initialize a ResourceTemplate. See the attribute descriptions above for explanations of the parameters.
|
|
35
|
-
def initialize(name, rel, uri_template, path_template, params, optional_params, options, resource_templates)
|
|
36
|
-
@name, @rel, @uri_template, @path_template = name, rel, uri_template, path_template
|
|
37
|
-
@params = params || []
|
|
38
|
-
@optional_params = optional_params || []
|
|
39
|
-
@options = options || []
|
|
40
|
-
@resource_templates = resource_templates || []
|
|
41
|
-
end
|
|
42
|
-
|
|
43
|
-
# Create a ResourceTemplate from its Hash representation
|
|
44
|
-
def self.from_hash(hash)
|
|
45
|
-
attributes = %w(name rel uri_template path_template params optional_params options).map{|k| hash[k]}
|
|
46
|
-
if hash["resource_templates"]
|
|
47
|
-
attributes << hash["resource_templates"].map{|h| from_hash(h)} if hash["resource_templates"]
|
|
48
|
-
else
|
|
49
|
-
attributes << nil
|
|
50
|
-
end
|
|
51
|
-
self.new(*attributes)
|
|
52
|
-
end
|
|
53
|
-
|
|
54
|
-
# Convert to a hash (equivalent to its JSON or YAML representation)
|
|
55
|
-
def to_hash
|
|
56
|
-
hash = {}
|
|
57
|
-
hash["name"] = name if name && !name.empty?
|
|
58
|
-
hash["rel"] = rel if rel && !rel.empty?
|
|
59
|
-
hash["uri_template"] = uri_template if uri_template && !uri_template.empty?
|
|
60
|
-
hash["path_template"] = path_template if path_template && !path_template.empty?
|
|
61
|
-
|
|
62
|
-
hash["params"] = params if params && !params.empty?
|
|
63
|
-
hash["optional_params"] = optional_params if optional_params && !optional_params.empty?
|
|
64
|
-
|
|
65
|
-
hash["options"] = options if options && !options.empty?
|
|
66
|
-
|
|
67
|
-
hashes = DescribedRoutes::ResourceTemplate.to_parsed(resource_templates)
|
|
68
|
-
hash["resource_templates"] = hashes if hashes && !hashes.empty?
|
|
69
|
-
|
|
70
|
-
hash
|
|
71
|
-
end
|
|
72
|
-
|
|
73
|
-
# Convert to JSON
|
|
74
|
-
def to_json
|
|
75
|
-
to_hash.to_json
|
|
76
|
-
end
|
|
77
|
-
|
|
78
|
-
# Convert to YAML
|
|
79
|
-
def to_yaml
|
|
80
|
-
to_hash.to_yaml
|
|
81
|
-
end
|
|
82
|
-
|
|
83
|
-
#
|
|
84
|
-
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
|
85
|
-
#
|
|
86
|
-
def to_xml(xm)
|
|
87
|
-
xm.ResourceTemplate do |xm|
|
|
88
|
-
value_tag(xm, "rel")
|
|
89
|
-
value_tag(xm, "name")
|
|
90
|
-
value_tag(xm, "path_template")
|
|
91
|
-
value_tag(xm, "uri_template")
|
|
92
|
-
|
|
93
|
-
list_tag(xm, params, "Params", "param")
|
|
94
|
-
list_tag(xm, optional_params, "OptionalParams", "param")
|
|
95
|
-
|
|
96
|
-
# could use a list of elements here, but let's follow HTTP's lead and reduce the verbosity
|
|
97
|
-
xm.options(options.join(", ")) unless options.empty?
|
|
98
|
-
|
|
99
|
-
self.class.to_xml(xm, resource_templates) unless resource_templates.empty?
|
|
100
|
-
end
|
|
101
|
-
xm
|
|
102
|
-
end
|
|
103
|
-
|
|
104
|
-
def value_tag(xm, tag) #:nodoc:
|
|
105
|
-
value = self.send(tag.to_sym)
|
|
106
|
-
xm.tag!(tag, value) unless value.blank?
|
|
107
|
-
end
|
|
108
|
-
|
|
109
|
-
def list_tag(xm, collection, collection_tag, member_tag) #:nodoc:
|
|
110
|
-
unless collection.nil? or collection.empty?
|
|
111
|
-
xm.tag!(collection_tag) do |xm|
|
|
112
|
-
collection.each do |value|
|
|
113
|
-
xm.tag!(member_tag, value)
|
|
114
|
-
end
|
|
115
|
-
end
|
|
116
|
-
end
|
|
117
|
-
end
|
|
118
|
-
|
|
119
|
-
# Convert an array of ResourceTemplate objects to array of hashes equivalent to their JSON or YAML representations
|
|
120
|
-
def self.to_parsed(resource_templates)
|
|
121
|
-
resource_templates.map{|resource_template| resource_template.to_hash}
|
|
122
|
-
end
|
|
123
|
-
|
|
124
|
-
# Convert an array of ResourceTemplate objects to JSON
|
|
125
|
-
def self.to_json(resource_templates)
|
|
126
|
-
self.to_parsed(resource_templates).to_json
|
|
127
|
-
end
|
|
128
|
-
|
|
129
|
-
# Convert an array of ResourceTemplate objects to YAML
|
|
130
|
-
def self.to_yaml(resource_templates)
|
|
131
|
-
self.to_parsed(resource_templates).to_yaml
|
|
132
|
-
end
|
|
133
|
-
|
|
134
|
-
# Create an array of ResourceTemplate objects from a JSON string
|
|
135
|
-
def self.parse_json(json)
|
|
136
|
-
self.from_parsed(JSON.parse(json))
|
|
137
|
-
end
|
|
138
|
-
|
|
139
|
-
# Create an array of ResourceTemplate objects from a JSON string
|
|
140
|
-
def self.parse_yaml(yaml)
|
|
141
|
-
self.from_parsed(YAML::load(yaml))
|
|
142
|
-
end
|
|
143
|
-
|
|
144
|
-
# Create an array of ResourceTemplate objects from an array of hashes
|
|
145
|
-
def self.from_parsed(parsed)
|
|
146
|
-
raise ArgumentError.new("not an array") unless parsed.kind_of?(Array)
|
|
147
|
-
|
|
148
|
-
parsed.map do |hash|
|
|
149
|
-
ResourceTemplate.from_hash(hash)
|
|
150
|
-
end
|
|
151
|
-
end
|
|
152
|
-
|
|
153
|
-
#
|
|
154
|
-
# Produces the XML format, given an XML builder object and an array of ResourceTemplate objects
|
|
155
|
-
#
|
|
156
|
-
def self.to_xml(xm, resource_templates)
|
|
157
|
-
xm.ResourceTemplates do |xm|
|
|
158
|
-
resource_templates.each do |resource_template|
|
|
159
|
-
resource_template.to_xml(xm)
|
|
160
|
-
end
|
|
161
|
-
end
|
|
162
|
-
xm
|
|
163
|
-
end
|
|
164
|
-
|
|
165
|
-
# Get a hash of all named ResourceTemplate objects contained in the supplied collection, keyed by name
|
|
166
|
-
def self.all_by_name(resource_templates, h = {})
|
|
167
|
-
resource_templates.inject(h) do |hash, resource_template|
|
|
168
|
-
hash[resource_template.name] = resource_template if resource_template.name
|
|
169
|
-
all_by_name(resource_template.resource_templates, hash)
|
|
170
|
-
hash
|
|
171
|
-
end
|
|
172
|
-
h
|
|
173
|
-
end
|
|
174
|
-
|
|
175
|
-
# for #to_text
|
|
176
|
-
def self.to_table(resource_templates, parent_template = nil, t = [], indent = '')
|
|
177
|
-
resource_templates.inject(t) do |table, resource_template|
|
|
178
|
-
if parent_template
|
|
179
|
-
link = (resource_template.rel || '')
|
|
180
|
-
new_params = resource_template.params - parent_template.params
|
|
181
|
-
else
|
|
182
|
-
link = resource_template.name
|
|
183
|
-
new_params = resource_template.params
|
|
184
|
-
end
|
|
185
|
-
link += new_params.map{|p| "{#{p}}"}.join(', ')
|
|
186
|
-
table << [
|
|
187
|
-
indent + link,
|
|
188
|
-
resource_template.name || '',
|
|
189
|
-
resource_template.options.join(', '),
|
|
190
|
-
resource_template.uri_template || resource_template.path_template
|
|
191
|
-
]
|
|
192
|
-
to_table(resource_template.resource_templates, resource_template, t, indent + ' ')
|
|
193
|
-
end
|
|
194
|
-
t
|
|
195
|
-
end
|
|
196
|
-
|
|
197
|
-
# text report
|
|
198
|
-
def self.to_text(resource_templates)
|
|
199
|
-
table = self.to_table(resource_templates)
|
|
200
|
-
|
|
201
|
-
0.upto(2) do |i|
|
|
202
|
-
width = table.map{|row| row[i].length}.max
|
|
203
|
-
table.each do |row|
|
|
204
|
-
row[i] = row[i].ljust(width)
|
|
205
|
-
end
|
|
206
|
-
end
|
|
207
|
-
|
|
208
|
-
table.map{|row| row.join(' ')}.join("\n") + "\n"
|
|
209
|
-
end
|
|
210
|
-
|
|
211
|
-
# returns params and any optional_params in order, removing the parent's params
|
|
212
|
-
def positional_params(parent)
|
|
213
|
-
all_params = params + optional_params
|
|
214
|
-
if parent
|
|
215
|
-
all_params - parent.params
|
|
216
|
-
else
|
|
217
|
-
all_params
|
|
218
|
-
end
|
|
219
|
-
end
|
|
220
|
-
|
|
221
|
-
# Partially expand the path_template or uri_template of the given resource templates with the given params,
|
|
222
|
-
# returning new resource templates
|
|
223
|
-
def self.partial_expand(resource_templates, actual_params)
|
|
224
|
-
resource_templates.map do |resource_template|
|
|
225
|
-
resource_template.partial_expand(actual_params)
|
|
226
|
-
end
|
|
227
|
-
end
|
|
228
|
-
|
|
229
|
-
# Return a new resource template with the path_template or uri_template partially expanded with the given params
|
|
230
|
-
def partial_expand(actual_params)
|
|
231
|
-
self.class.new(
|
|
232
|
-
name,
|
|
233
|
-
rel,
|
|
234
|
-
partial_expand_uri_template(uri_template, actual_params),
|
|
235
|
-
partial_expand_uri_template(path_template, actual_params),
|
|
236
|
-
params - actual_params.keys,
|
|
237
|
-
optional_params - actual_params.keys,
|
|
238
|
-
options,
|
|
239
|
-
self.class.partial_expand(resource_templates, actual_params))
|
|
240
|
-
end
|
|
241
|
-
|
|
242
|
-
# Partially expand a URI template
|
|
243
|
-
def partial_expand_uri_template(template, params)#:nodoc:
|
|
244
|
-
template && Addressable::Template.new(template).partial_expand(params).pattern
|
|
245
|
-
end
|
|
246
|
-
end
|
|
247
|
-
end
|
|
248
|
-
|
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
- name: root
|
|
3
|
-
path_template: /
|
|
4
|
-
- name: admin_products
|
|
5
|
-
- name: new_admin_product
|
|
6
|
-
path_template: /admin/products/new{-prefix|.|format}
|
|
7
|
-
rel: new_admin_product
|
|
8
|
-
- name: admin_product
|
|
9
|
-
- name: edit_admin_product
|
|
10
|
-
path_template: /admin/products/{product_id}/edit{-prefix|.|format}
|
|
11
|
-
rel: edit
|
|
12
|
-
path_template: /admin/products/{product_id}{-prefix|.|format}
|
|
13
|
-
path_template: /admin/products{-prefix|.|format}
|
|
14
|
-
- name: described_routes
|
|
15
|
-
- name: new_described_route
|
|
16
|
-
path_template: /described_routes/new{-prefix|.|format}
|
|
17
|
-
rel: new_described_route
|
|
18
|
-
- name: described_route
|
|
19
|
-
- name: edit_described_route
|
|
20
|
-
path_template: /described_routes/{route_name}/edit{-prefix|.|format}
|
|
21
|
-
rel: edit
|
|
22
|
-
path_template: /described_routes/{route_name}{-prefix|.|format}
|
|
23
|
-
path_template: /described_routes{-prefix|.|format}
|
|
24
|
-
- name: pages
|
|
25
|
-
- name: new_page
|
|
26
|
-
path_template: /pages/new{-prefix|.|format}
|
|
27
|
-
rel: new_page
|
|
28
|
-
- name: page
|
|
29
|
-
- name: edit_page
|
|
30
|
-
path_template: /pages/{page_id}/edit{-prefix|.|format}
|
|
31
|
-
rel: edit
|
|
32
|
-
- name: summary_page
|
|
33
|
-
path_template: /pages/{page_id}/summary{-prefix|.|format}
|
|
34
|
-
rel: summary
|
|
35
|
-
- name: toggle_visibility_page
|
|
36
|
-
path_template: /pages/{page_id}/toggle_visibility{-prefix|.|format}
|
|
37
|
-
rel: toggle_visibility
|
|
38
|
-
path_template: /pages/{page_id}{-prefix|.|format}
|
|
39
|
-
path_template: /pages{-prefix|.|format}
|
|
40
|
-
- name: users
|
|
41
|
-
- name: new_user
|
|
42
|
-
path_template: /users/new{-prefix|.|format}
|
|
43
|
-
rel: new_user
|
|
44
|
-
- name: user
|
|
45
|
-
- name: edit_user
|
|
46
|
-
path_template: /users/{user_id}/edit{-prefix|.|format}
|
|
47
|
-
rel: edit
|
|
48
|
-
- name: user_articles
|
|
49
|
-
- name: new_user_article
|
|
50
|
-
path_template: /users/{user_id}/articles/new{-prefix|.|format}
|
|
51
|
-
rel: new_user_article
|
|
52
|
-
- name: recent_user_articles
|
|
53
|
-
path_template: /users/{user_id}/articles/recent{-prefix|.|format}
|
|
54
|
-
rel: recent
|
|
55
|
-
- name: user_article
|
|
56
|
-
- name: edit_user_article
|
|
57
|
-
path_template: /users/{user_id}/articles/{article_id}/edit{-prefix|.|format}
|
|
58
|
-
rel: edit
|
|
59
|
-
path_template: /users/{user_id}/articles/{article_id}{-prefix|.|format}
|
|
60
|
-
path_template: /users/{user_id}/articles{-prefix|.|format}
|
|
61
|
-
rel: articles
|
|
62
|
-
- name: user_profile
|
|
63
|
-
- name: edit_user_profile
|
|
64
|
-
path_template: /users/{user_id}/profile/edit{-prefix|.|format}
|
|
65
|
-
rel: edit
|
|
66
|
-
- name: new_user_profile
|
|
67
|
-
path_template: /users/{user_id}/profile/new{-prefix|.|format}
|
|
68
|
-
rel: new
|
|
69
|
-
path_template: /users/{user_id}/profile{-prefix|.|format}
|
|
70
|
-
rel: profile
|
|
71
|
-
path_template: /users/{user_id}{-prefix|.|format}
|
|
72
|
-
path_template: /users{-prefix|.|format}
|
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
- name: root
|
|
3
|
-
path_template: /
|
|
4
|
-
- name: described_routes
|
|
5
|
-
- name: new_described_route
|
|
6
|
-
path_template: /described_routes/new{-prefix|.|format}
|
|
7
|
-
rel: new_described_route
|
|
8
|
-
- name: described_route
|
|
9
|
-
- name: edit_described_route
|
|
10
|
-
path_template: /described_routes/{route_name}/edit{-prefix|.|format}
|
|
11
|
-
rel: edit
|
|
12
|
-
path_template: /described_routes/{route_name}{-prefix|.|format}
|
|
13
|
-
path_template: /described_routes{-prefix|.|format}
|
|
14
|
-
- name: pages
|
|
15
|
-
- name: new_page
|
|
16
|
-
path_template: /pages/new{-prefix|.|format}
|
|
17
|
-
rel: new_page
|
|
18
|
-
- name: page
|
|
19
|
-
- name: edit_page
|
|
20
|
-
path_template: /pages/{page_id}/edit{-prefix|.|format}
|
|
21
|
-
rel: edit
|
|
22
|
-
- name: summary_page
|
|
23
|
-
path_template: /pages/{page_id}/summary{-prefix|.|format}
|
|
24
|
-
rel: summary
|
|
25
|
-
- name: toggle_visibility_page
|
|
26
|
-
path_template: /pages/{page_id}/toggle_visibility{-prefix|.|format}
|
|
27
|
-
rel: toggle_visibility
|
|
28
|
-
path_template: /pages/{page_id}{-prefix|.|format}
|
|
29
|
-
path_template: /pages{-prefix|.|format}
|
|
30
|
-
- name: users
|
|
31
|
-
- name: new_user
|
|
32
|
-
path_template: /users/new{-prefix|.|format}
|
|
33
|
-
rel: new_user
|
|
34
|
-
- name: user
|
|
35
|
-
- name: edit_user
|
|
36
|
-
path_template: /users/{user_id}/edit{-prefix|.|format}
|
|
37
|
-
rel: edit
|
|
38
|
-
- name: user_articles
|
|
39
|
-
- name: new_user_article
|
|
40
|
-
path_template: /users/{user_id}/articles/new{-prefix|.|format}
|
|
41
|
-
rel: new_user_article
|
|
42
|
-
- name: recent_user_articles
|
|
43
|
-
path_template: /users/{user_id}/articles/recent{-prefix|.|format}
|
|
44
|
-
rel: recent
|
|
45
|
-
- name: user_article
|
|
46
|
-
- name: edit_user_article
|
|
47
|
-
path_template: /users/{user_id}/articles/{article_id}/edit{-prefix|.|format}
|
|
48
|
-
rel: edit
|
|
49
|
-
path_template: /users/{user_id}/articles/{article_id}{-prefix|.|format}
|
|
50
|
-
path_template: /users/{user_id}/articles{-prefix|.|format}
|
|
51
|
-
rel: articles
|
|
52
|
-
- name: user_profile
|
|
53
|
-
- name: edit_user_profile
|
|
54
|
-
path_template: /users/{user_id}/profile/edit{-prefix|.|format}
|
|
55
|
-
rel: edit
|
|
56
|
-
- name: new_user_profile
|
|
57
|
-
path_template: /users/{user_id}/profile/new{-prefix|.|format}
|
|
58
|
-
rel: new
|
|
59
|
-
path_template: /users/{user_id}/profile{-prefix|.|format}
|
|
60
|
-
rel: profile
|
|
61
|
-
path_template: /users/{user_id}{-prefix|.|format}
|
|
62
|
-
path_template: /users{-prefix|.|format}
|
|
@@ -1,99 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
- name: root
|
|
3
|
-
path_template: /
|
|
4
|
-
uri_template: http://www.example.com/
|
|
5
|
-
- name: admin_products
|
|
6
|
-
- name: new_admin_product
|
|
7
|
-
path_template: /admin/products/new{-prefix|.|format}
|
|
8
|
-
uri_template: http://www.example.com/admin/products/new{-prefix|.|format}
|
|
9
|
-
rel: new_admin_product
|
|
10
|
-
- name: admin_product
|
|
11
|
-
- name: edit_admin_product
|
|
12
|
-
path_template: /admin/products/{product_id}/edit{-prefix|.|format}
|
|
13
|
-
uri_template: http://www.example.com/admin/products/{product_id}/edit{-prefix|.|format}
|
|
14
|
-
rel: edit
|
|
15
|
-
path_template: /admin/products/{product_id}{-prefix|.|format}
|
|
16
|
-
uri_template: http://www.example.com/admin/products/{product_id}{-prefix|.|format}
|
|
17
|
-
path_template: /admin/products{-prefix|.|format}
|
|
18
|
-
uri_template: http://www.example.com/admin/products{-prefix|.|format}
|
|
19
|
-
- name: described_routes
|
|
20
|
-
- name: new_described_route
|
|
21
|
-
path_template: /described_routes/new{-prefix|.|format}
|
|
22
|
-
uri_template: http://www.example.com/described_routes/new{-prefix|.|format}
|
|
23
|
-
rel: new_described_route
|
|
24
|
-
- name: described_route
|
|
25
|
-
- name: edit_described_route
|
|
26
|
-
path_template: /described_routes/{route_name}/edit{-prefix|.|format}
|
|
27
|
-
uri_template: http://www.example.com/described_routes/{route_name}/edit{-prefix|.|format}
|
|
28
|
-
rel: edit
|
|
29
|
-
path_template: /described_routes/{route_name}{-prefix|.|format}
|
|
30
|
-
uri_template: http://www.example.com/described_routes/{route_name}{-prefix|.|format}
|
|
31
|
-
path_template: /described_routes{-prefix|.|format}
|
|
32
|
-
uri_template: http://www.example.com/described_routes{-prefix|.|format}
|
|
33
|
-
- name: pages
|
|
34
|
-
- name: new_page
|
|
35
|
-
path_template: /pages/new{-prefix|.|format}
|
|
36
|
-
uri_template: http://www.example.com/pages/new{-prefix|.|format}
|
|
37
|
-
rel: new_page
|
|
38
|
-
- name: page
|
|
39
|
-
- name: edit_page
|
|
40
|
-
path_template: /pages/{page_id}/edit{-prefix|.|format}
|
|
41
|
-
uri_template: http://www.example.com/pages/{page_id}/edit{-prefix|.|format}
|
|
42
|
-
rel: edit
|
|
43
|
-
- name: summary_page
|
|
44
|
-
path_template: /pages/{page_id}/summary{-prefix|.|format}
|
|
45
|
-
uri_template: http://www.example.com/pages/{page_id}/summary{-prefix|.|format}
|
|
46
|
-
rel: summary
|
|
47
|
-
- name: toggle_visibility_page
|
|
48
|
-
path_template: /pages/{page_id}/toggle_visibility{-prefix|.|format}
|
|
49
|
-
uri_template: http://www.example.com/pages/{page_id}/toggle_visibility{-prefix|.|format}
|
|
50
|
-
rel: toggle_visibility
|
|
51
|
-
path_template: /pages/{page_id}{-prefix|.|format}
|
|
52
|
-
uri_template: http://www.example.com/pages/{page_id}{-prefix|.|format}
|
|
53
|
-
path_template: /pages{-prefix|.|format}
|
|
54
|
-
uri_template: http://www.example.com/pages{-prefix|.|format}
|
|
55
|
-
- name: users
|
|
56
|
-
- name: new_user
|
|
57
|
-
path_template: /users/new{-prefix|.|format}
|
|
58
|
-
uri_template: http://www.example.com/users/new{-prefix|.|format}
|
|
59
|
-
rel: new_user
|
|
60
|
-
- name: user
|
|
61
|
-
- name: edit_user
|
|
62
|
-
path_template: /users/{user_id}/edit{-prefix|.|format}
|
|
63
|
-
uri_template: http://www.example.com/users/{user_id}/edit{-prefix|.|format}
|
|
64
|
-
rel: edit
|
|
65
|
-
- name: user_articles
|
|
66
|
-
- name: new_user_article
|
|
67
|
-
path_template: /users/{user_id}/articles/new{-prefix|.|format}
|
|
68
|
-
uri_template: http://www.example.com/users/{user_id}/articles/new{-prefix|.|format}
|
|
69
|
-
rel: new_user_article
|
|
70
|
-
- name: recent_user_articles
|
|
71
|
-
path_template: /users/{user_id}/articles/recent{-prefix|.|format}
|
|
72
|
-
uri_template: http://www.example.com/users/{user_id}/articles/recent{-prefix|.|format}
|
|
73
|
-
rel: recent
|
|
74
|
-
- name: user_article
|
|
75
|
-
- name: edit_user_article
|
|
76
|
-
path_template: /users/{user_id}/articles/{article_id}/edit{-prefix|.|format}
|
|
77
|
-
uri_template: http://www.example.com/users/{user_id}/articles/{article_id}/edit{-prefix|.|format}
|
|
78
|
-
rel: edit
|
|
79
|
-
path_template: /users/{user_id}/articles/{article_id}{-prefix|.|format}
|
|
80
|
-
uri_template: http://www.example.com/users/{user_id}/articles/{article_id}{-prefix|.|format}
|
|
81
|
-
path_template: /users/{user_id}/articles{-prefix|.|format}
|
|
82
|
-
uri_template: http://www.example.com/users/{user_id}/articles{-prefix|.|format}
|
|
83
|
-
rel: articles
|
|
84
|
-
- name: user_profile
|
|
85
|
-
- name: edit_user_profile
|
|
86
|
-
path_template: /users/{user_id}/profile/edit{-prefix|.|format}
|
|
87
|
-
uri_template: http://www.example.com/users/{user_id}/profile/edit{-prefix|.|format}
|
|
88
|
-
rel: edit
|
|
89
|
-
- name: new_user_profile
|
|
90
|
-
path_template: /users/{user_id}/profile/new{-prefix|.|format}
|
|
91
|
-
uri_template: http://www.example.com/users/{user_id}/profile/new{-prefix|.|format}
|
|
92
|
-
rel: new
|
|
93
|
-
path_template: /users/{user_id}/profile{-prefix|.|format}
|
|
94
|
-
uri_template: http://www.example.com/users/{user_id}/profile{-prefix|.|format}
|
|
95
|
-
rel: profile
|
|
96
|
-
path_template: /users/{user_id}{-prefix|.|format}
|
|
97
|
-
uri_template: http://www.example.com/users/{user_id}{-prefix|.|format}
|
|
98
|
-
path_template: /users{-prefix|.|format}
|
|
99
|
-
uri_template: http://www.example.com/users{-prefix|.|format}
|