raml_ruby 0.1.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +19 -0
- data/.travis.yml +6 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +71 -0
- data/Rakefile +1 -0
- data/fixtures/include_1.raml +7 -0
- data/fixtures/schemas/canonicalSchemas.raml +3 -0
- data/fixtures/schemas/filesystem/file.json +1 -0
- data/fixtures/schemas/filesystem/files.json +1 -0
- data/fixtures/schemas/filesystem/fileupdate.json +1 -0
- data/fixtures/schemas/filesystem/relative/test.json +1 -0
- data/lib/raml.rb +104 -0
- data/lib/raml/exceptions.rb +27 -0
- data/lib/raml/mixin/bodies.rb +32 -0
- data/lib/raml/mixin/documentable.rb +32 -0
- data/lib/raml/mixin/global.rb +20 -0
- data/lib/raml/mixin/headers.rb +22 -0
- data/lib/raml/mixin/merge.rb +24 -0
- data/lib/raml/mixin/parent.rb +54 -0
- data/lib/raml/mixin/validation.rb +49 -0
- data/lib/raml/node.rb +219 -0
- data/lib/raml/node/abstract_method.rb +61 -0
- data/lib/raml/node/abstract_resource.rb +165 -0
- data/lib/raml/node/abstract_resource_circular.rb +5 -0
- data/lib/raml/node/body.rb +94 -0
- data/lib/raml/node/documentation.rb +28 -0
- data/lib/raml/node/header.rb +4 -0
- data/lib/raml/node/method.rb +106 -0
- data/lib/raml/node/parameter/abstract_parameter.rb +251 -0
- data/lib/raml/node/parameter/base_uri_parameter.rb +6 -0
- data/lib/raml/node/parameter/form_parameter.rb +6 -0
- data/lib/raml/node/parameter/query_parameter.rb +6 -0
- data/lib/raml/node/parameter/uri_parameter.rb +7 -0
- data/lib/raml/node/parametized_reference.rb +15 -0
- data/lib/raml/node/reference.rb +4 -0
- data/lib/raml/node/resource.rb +26 -0
- data/lib/raml/node/resource_type.rb +20 -0
- data/lib/raml/node/resource_type_reference.rb +5 -0
- data/lib/raml/node/response.rb +32 -0
- data/lib/raml/node/root.rb +246 -0
- data/lib/raml/node/schema.rb +41 -0
- data/lib/raml/node/schema_reference.rb +5 -0
- data/lib/raml/node/template.rb +55 -0
- data/lib/raml/node/trait.rb +18 -0
- data/lib/raml/node/trait_reference.rb +5 -0
- data/lib/raml/parser.rb +57 -0
- data/lib/raml/parser/include.rb +25 -0
- data/lib/raml/patch/hash.rb +6 -0
- data/lib/raml/patch/module.rb +12 -0
- data/lib/raml/version.rb +3 -0
- data/raml_ruby.gemspec +35 -0
- data/raml_spec_reqs.md +276 -0
- data/templates/abstract_parameter.slim +68 -0
- data/templates/body.slim +15 -0
- data/templates/collapse.slim +10 -0
- data/templates/documentation.slim +2 -0
- data/templates/method.slim +38 -0
- data/templates/resource.slim +33 -0
- data/templates/response.slim +13 -0
- data/templates/root.slim +39 -0
- data/templates/style.sass +119 -0
- data/test/apis/box-api.raml +4224 -0
- data/test/apis/instagram-api.raml +3378 -0
- data/test/apis/stripe-api.raml +12227 -0
- data/test/apis/twilio-rest-api.raml +6618 -0
- data/test/apis/twitter-rest-api.raml +34284 -0
- data/test/raml/body_spec.rb +268 -0
- data/test/raml/documentation_spec.rb +49 -0
- data/test/raml/header_spec.rb +17 -0
- data/test/raml/include_spec.rb +40 -0
- data/test/raml/method_spec.rb +701 -0
- data/test/raml/parameter/abstract_parameter_spec.rb +564 -0
- data/test/raml/parameter/form_parameter_spec.rb +17 -0
- data/test/raml/parameter/query_parameter_spec.rb +33 -0
- data/test/raml/parameter/uri_parameter_spec.rb +44 -0
- data/test/raml/parser_spec.rb +53 -0
- data/test/raml/raml_spec.rb +32 -0
- data/test/raml/resource_spec.rb +440 -0
- data/test/raml/resource_type_spec.rb +51 -0
- data/test/raml/response_spec.rb +251 -0
- data/test/raml/root_spec.rb +655 -0
- data/test/raml/schema_spec.rb +110 -0
- data/test/raml/spec_helper.rb +11 -0
- data/test/raml/template_spec.rb +98 -0
- data/test/raml/trait_spec.rb +31 -0
- metadata +337 -0
@@ -0,0 +1,49 @@
|
|
1
|
+
module Raml
|
2
|
+
# @private
|
3
|
+
module Validation
|
4
|
+
def validate_property(name, value, classes)
|
5
|
+
classes = [ classes ] unless classes.is_a? Array
|
6
|
+
raise InvalidProperty, "#{camel_case name} property must be an #{classes_to_s classes}" unless classes.include? value.class
|
7
|
+
end
|
8
|
+
|
9
|
+
def validate_string(name, string)
|
10
|
+
validate_property name, string, String
|
11
|
+
raise InvalidProperty, "#{camel_case name} property must be a non-empty string." if string.empty?
|
12
|
+
end
|
13
|
+
|
14
|
+
def validate_array(name, array, element_classes=nil)
|
15
|
+
raise InvalidProperty, "#{camel_case name} property must be an array" unless
|
16
|
+
array.is_a? Array
|
17
|
+
|
18
|
+
if element_classes
|
19
|
+
element_classes = [ element_classes ] unless element_classes.is_a? Array
|
20
|
+
raise InvalidProperty, "#{camel_case name} property must be an array of #{classes_to_s element_classes}" unless
|
21
|
+
array.all? { |element| element_classes.include? element.class }
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
def validate_hash(name, hash, key_class=nil, value_class=nil)
|
26
|
+
raise InvalidProperty, "#{camel_case name} property must be a map" unless
|
27
|
+
hash.is_a? Hash
|
28
|
+
|
29
|
+
if key_class
|
30
|
+
if key_class.is_a? Array
|
31
|
+
raise InvalidProperty, "#{camel_case name} property must be a map with #{key_class} keys" unless
|
32
|
+
hash.keys.all? {|key| key_class.any? { |kc| key.is_a? kc } }
|
33
|
+
else
|
34
|
+
raise InvalidProperty, "#{camel_case name} property must be a map with #{key_class} keys" unless
|
35
|
+
hash.keys.all? {|key| key.is_a? key_class }
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
if value_class
|
40
|
+
raise InvalidProperty, "#{camel_case name} property must be a map with map values: #{hash}" unless
|
41
|
+
hash.values.all? {|value| value.is_a? Hash }
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def classes_to_s(classes)
|
46
|
+
classes.join(', ').gsub(/, (\w)\z/, ' or \1')
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
data/lib/raml/node.rb
ADDED
@@ -0,0 +1,219 @@
|
|
1
|
+
require 'active_support'
|
2
|
+
require 'active_support/core_ext/class/attribute'
|
3
|
+
require 'rouge'
|
4
|
+
require 'slim'
|
5
|
+
|
6
|
+
module Raml
|
7
|
+
class Node
|
8
|
+
class_attribute :doc_template, :doc_template_compiled
|
9
|
+
|
10
|
+
class << self
|
11
|
+
# @private
|
12
|
+
def relative_path(file)
|
13
|
+
File.join(
|
14
|
+
*File.dirname(__FILE__).
|
15
|
+
split(File::SEPARATOR).
|
16
|
+
reverse.
|
17
|
+
drop_while { |p| p != 'lib' }.
|
18
|
+
drop(1).
|
19
|
+
reverse,
|
20
|
+
'templates',
|
21
|
+
file
|
22
|
+
)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
# @!attribute [r] name
|
27
|
+
# @return [String,Integer] the node name (e.g. resource path, header name, etc). Usually a
|
28
|
+
# String. Can be an Integer for methods.
|
29
|
+
attr_reader :name
|
30
|
+
# @!attribute [rw] parent
|
31
|
+
# @return [Raml::Node] the node's parent.
|
32
|
+
attr_accessor :parent
|
33
|
+
|
34
|
+
def initialize(name, parent)
|
35
|
+
@name = name
|
36
|
+
@parent = parent
|
37
|
+
end
|
38
|
+
|
39
|
+
# Returns HTML documenting the node and child nodes.
|
40
|
+
# @return [String] HTML documentation.
|
41
|
+
def document
|
42
|
+
if doc_template
|
43
|
+
self.doc_template_compiled ||= Slim::Template.new(doc_template, format: :html5, pretty: true)
|
44
|
+
doc_template_compiled.render self
|
45
|
+
else
|
46
|
+
nil
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
private
|
51
|
+
|
52
|
+
def underscore(camel_cased_word)
|
53
|
+
camel_cased_word.to_s.gsub(/::/, '/').
|
54
|
+
gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
|
55
|
+
gsub(/([a-z\d])([A-Z])/,'\1_\2').
|
56
|
+
tr("-", "_").
|
57
|
+
downcase
|
58
|
+
end
|
59
|
+
|
60
|
+
def camel_case(underscored_word)
|
61
|
+
w = underscored_word.to_s.split('_')
|
62
|
+
(w[0...1] + w[1..-1].map(&:capitalize)).join
|
63
|
+
end
|
64
|
+
|
65
|
+
def collapse(level, title, display_name=nil, &block)
|
66
|
+
@@cid ||= 0
|
67
|
+
@@cid += 1
|
68
|
+
|
69
|
+
@@context_class ||= Struct.new(:cid, :title, :level, :display_name, :content) do
|
70
|
+
def highlight_url_params(url)
|
71
|
+
url.gsub(/({[^}]+})/, '<span class="url_param">\1</span>')
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
context = @@context_class.new @@cid, title, level, display_name, yield
|
76
|
+
|
77
|
+
@@collapse ||= Slim::Template.new(self.class.relative_path('collapse.slim'), format: :html5, pretty: true)
|
78
|
+
@@collapse.render context
|
79
|
+
end
|
80
|
+
|
81
|
+
def highlight_url_params(url)
|
82
|
+
url.gsub(/({[^}]+})/, '<span class="url_param">\1</span>')
|
83
|
+
end
|
84
|
+
|
85
|
+
def highlight(source, mimetype=nil)
|
86
|
+
opts = { source: source }
|
87
|
+
opts[:mimetype] = mimetype if mimetype
|
88
|
+
|
89
|
+
formatter = Rouge::Formatters::HTML.new css_class: 'highlight'
|
90
|
+
lexer = Rouge::Lexer.guess(opts).new
|
91
|
+
formatter.format lexer.lex source
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
class ValueNode < Node
|
96
|
+
attr_accessor :value
|
97
|
+
|
98
|
+
def initialize(name, value, parent)
|
99
|
+
super name, parent
|
100
|
+
@value = value
|
101
|
+
|
102
|
+
validate_value if respond_to? :validate_value, true
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
class PropertiesNode < Node
|
107
|
+
class_attribute :scalar_properties, :non_scalar_properties, :_regexp_property
|
108
|
+
self.scalar_properties = []
|
109
|
+
self.non_scalar_properties = []
|
110
|
+
self._regexp_property = nil
|
111
|
+
|
112
|
+
class << self
|
113
|
+
private
|
114
|
+
def inherit_class_attributes
|
115
|
+
self.scalar_properties = self.scalar_properties.dup
|
116
|
+
self.non_scalar_properties = self.non_scalar_properties.dup
|
117
|
+
end
|
118
|
+
|
119
|
+
def scalar_property(*properties)
|
120
|
+
attr_accessor(*properties.map(&:to_sym))
|
121
|
+
_property(scalar_properties, *properties)
|
122
|
+
end
|
123
|
+
|
124
|
+
def non_scalar_property(*properties)
|
125
|
+
_property(non_scalar_properties, *properties)
|
126
|
+
end
|
127
|
+
|
128
|
+
def _property(type, *properties)
|
129
|
+
properties.map(&:to_s).each { |prop| type << prop unless type.include? prop }
|
130
|
+
end
|
131
|
+
|
132
|
+
def regexp_property(regexp, parse)
|
133
|
+
self._regexp_property = [ regexp, parse ]
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
# @private
|
138
|
+
def scalar_properties ; self.class.scalar_properties ; end
|
139
|
+
# @private
|
140
|
+
def non_scalar_properties; self.class.non_scalar_properties; end
|
141
|
+
# @private
|
142
|
+
def _regexp_property ; self.class._regexp_property ; end
|
143
|
+
|
144
|
+
# @!attribute [rw] optional
|
145
|
+
# @return [Boolean] whether the property is optional. Only valid
|
146
|
+
# for decendant nodes a {Trait::Instance} or {ResourceType::Instance}.
|
147
|
+
# Indicated by a trailing "?" on the property name in the RAML source.
|
148
|
+
attr_accessor :optional
|
149
|
+
|
150
|
+
def initialize(name, properties, parent)
|
151
|
+
if name.is_a? String and name.end_with? '?'
|
152
|
+
allow_optional? parent
|
153
|
+
name = name.dup.chomp! '?'
|
154
|
+
@optional = true
|
155
|
+
else
|
156
|
+
@optional = false
|
157
|
+
end
|
158
|
+
|
159
|
+
super name, parent
|
160
|
+
|
161
|
+
@children ||= []
|
162
|
+
parse_and_validate_props properties
|
163
|
+
end
|
164
|
+
|
165
|
+
private
|
166
|
+
|
167
|
+
def allow_optional?(parent)
|
168
|
+
until parent == parent.parent or parent.is_a? Root
|
169
|
+
return if parent.is_a? Trait::Instance or parent.is_a? ResourceType::Instance
|
170
|
+
parent = parent.parent
|
171
|
+
end
|
172
|
+
raise InvalidProperty, 'Optional properties are only allowed within a trait or resource type specification.'
|
173
|
+
end
|
174
|
+
|
175
|
+
def parse_and_validate_props(properties)
|
176
|
+
maybe_exec :validate_name
|
177
|
+
maybe_exec :validate_parent
|
178
|
+
|
179
|
+
properties.each do |prop_name, prop_value|
|
180
|
+
prop_name = prop_name.to_s
|
181
|
+
under_prop_name = underscore prop_name
|
182
|
+
|
183
|
+
if scalar_properties.include? under_prop_name
|
184
|
+
send "#{under_prop_name}=", prop_value
|
185
|
+
maybe_exec "validate_#{under_prop_name}"
|
186
|
+
|
187
|
+
elsif non_scalar_properties.include? under_prop_name
|
188
|
+
parsed = send "parse_#{under_prop_name}", prop_value
|
189
|
+
parsed = [ parsed ] unless parsed.is_a? Array
|
190
|
+
@children += parsed
|
191
|
+
|
192
|
+
elsif _regexp_property and _regexp_property[0].match prop_name
|
193
|
+
parsed = self.instance_exec(prop_name, prop_value, &_regexp_property[1])
|
194
|
+
parsed = [ parsed ] unless parsed.is_a? Array
|
195
|
+
@children += parsed
|
196
|
+
|
197
|
+
else
|
198
|
+
raise UnknownProperty, "#{prop_name} is an unknown property with value of #{prop_value}."
|
199
|
+
end
|
200
|
+
end
|
201
|
+
|
202
|
+
validate if respond_to? :validate, true
|
203
|
+
end
|
204
|
+
|
205
|
+
def maybe_exec(method, *args)
|
206
|
+
send(method,*args) if respond_to? method, true
|
207
|
+
end
|
208
|
+
|
209
|
+
def initialize_clone(other)
|
210
|
+
super
|
211
|
+
@children = @children.clone
|
212
|
+
@children.map! do |child|
|
213
|
+
child = child.clone
|
214
|
+
child.parent = self
|
215
|
+
child
|
216
|
+
end
|
217
|
+
end
|
218
|
+
end
|
219
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
module Raml
|
2
|
+
class AbstractMethod < PropertiesNode
|
3
|
+
inherit_class_attributes
|
4
|
+
|
5
|
+
include Documentable
|
6
|
+
include Global
|
7
|
+
include Merge
|
8
|
+
include Parent
|
9
|
+
include Validation
|
10
|
+
include Bodies
|
11
|
+
include Headers
|
12
|
+
|
13
|
+
# @!attribute [rw] protocols
|
14
|
+
# @return [Array<String>, nil] the supported protocols. Nil or an array of up to two string
|
15
|
+
# elements from the set "HTTP" and "HTTPS".
|
16
|
+
|
17
|
+
# @!attribute [r] query_parameters
|
18
|
+
# @return [Hash<String, Raml::Parameter::QueryParameter>] the method query parameters, keyed
|
19
|
+
# by the parameter name.
|
20
|
+
|
21
|
+
# @!attribute [r] responses
|
22
|
+
# @return [Hash<Integer, Raml::Response>] the method responses, keyed by the HTTP status code.
|
23
|
+
|
24
|
+
scalar_property :protocols
|
25
|
+
non_scalar_property :query_parameters, :responses, :secured_by
|
26
|
+
|
27
|
+
attr_reader_default :protocols, []
|
28
|
+
|
29
|
+
children_by :query_parameters , :name , Parameter::QueryParameter
|
30
|
+
children_by :responses , :name , Response
|
31
|
+
|
32
|
+
private
|
33
|
+
|
34
|
+
def validate_protocols
|
35
|
+
if @protocols
|
36
|
+
validate_array :protocols, @protocols, String
|
37
|
+
|
38
|
+
@protocols.map!(&:upcase)
|
39
|
+
|
40
|
+
raise InvalidProperty, 'protocols property elements must be HTTP or HTTPS' unless
|
41
|
+
@protocols.all? { |p| [ 'HTTP', 'HTTPS'].include? p }
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def parse_query_parameters(value)
|
46
|
+
validate_hash 'queryParameters', value, String, Hash
|
47
|
+
value.map { |p_name, p_data| Parameter::QueryParameter.new p_name, p_data, self }
|
48
|
+
end
|
49
|
+
|
50
|
+
def parse_responses(value)
|
51
|
+
validate_hash 'responses', value, [Integer, String], Hash
|
52
|
+
value.map { |r_name, r_data| Response.new r_name, r_data, self }
|
53
|
+
end
|
54
|
+
|
55
|
+
def parse_secured_by(data)
|
56
|
+
# XXX ignored for now
|
57
|
+
[]
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
61
|
+
end
|
@@ -0,0 +1,165 @@
|
|
1
|
+
module Raml
|
2
|
+
class AbstractResource < PropertiesNode
|
3
|
+
inherit_class_attributes
|
4
|
+
|
5
|
+
include Documentable
|
6
|
+
include Global
|
7
|
+
include Merge
|
8
|
+
include Parent
|
9
|
+
include Validation
|
10
|
+
|
11
|
+
# @!attribute [r] base_uri_parameters
|
12
|
+
# @return [Hash<String, Raml::Parameter::BaseUriParameter>] the base URI parameters, keyed
|
13
|
+
# by the parameter name.
|
14
|
+
|
15
|
+
# @!attribute [r] uri_parameters
|
16
|
+
# @return [Hash<String, Raml::Parameter::UriParameter>] the URI parameters, keyed
|
17
|
+
# by the parameter name.
|
18
|
+
|
19
|
+
# @!attribute [r] methods
|
20
|
+
# @return [Hash<String, Raml::Method>] the methods, keyed by the method name.
|
21
|
+
|
22
|
+
# @!attribute [r] traits
|
23
|
+
# @return [Array<Raml::Trait, Raml::TraitReference>] the traits and trait references.
|
24
|
+
|
25
|
+
non_scalar_property :uri_parameters, :base_uri_parameters, :is, :type, :secured_by,
|
26
|
+
*Raml::Method::NAMES, *Raml::Method::NAMES.map { |m| "#{m}?" }
|
27
|
+
|
28
|
+
children_by :methods , :name, Raml::Method
|
29
|
+
children_by :base_uri_parameters, :name, Parameter::BaseUriParameter, true
|
30
|
+
children_by :uri_parameters , :name, Parameter::UriParameter , true
|
31
|
+
|
32
|
+
children_of :traits, [ Raml::Trait, Raml::TraitReference ]
|
33
|
+
|
34
|
+
# @private
|
35
|
+
def apply_resource_type
|
36
|
+
if type
|
37
|
+
# We clone the resource as it currently is; apply the resource type to the
|
38
|
+
# resource, so that optional properties are correctly evaluated; then we
|
39
|
+
# apply the cloned resource with the initial state, so that scalar properties
|
40
|
+
# in the resource override the ones in the resource type.
|
41
|
+
cloned_self = self.clone
|
42
|
+
merge instantiate_resource_type
|
43
|
+
merge cloned_self
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
# @private
|
48
|
+
def merge(other)
|
49
|
+
raise MergeError, "Trying to merge #{other.class} into Resource." unless other.is_a? ResourceType::Instance or other.is_a? Resource
|
50
|
+
|
51
|
+
super
|
52
|
+
|
53
|
+
merge_properties other, :methods
|
54
|
+
merge_properties other, :base_uri_parameters
|
55
|
+
merge_properties other, :uri_parameters
|
56
|
+
|
57
|
+
# merge traits. insert the non-matching ones in the front, so they have the least priority.
|
58
|
+
match, no_match = other.traits.partition do |other_trait|
|
59
|
+
if other_trait.is_a? Trait
|
60
|
+
false
|
61
|
+
else # TraitReference
|
62
|
+
self.traits.any? do |self_trait|
|
63
|
+
self_trait.is_a?(TraitReference) &&
|
64
|
+
self_trait.name == other_trait.name &&
|
65
|
+
self_trait.parameters == other_trait.parameters
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
@children.unshift(*no_match)
|
70
|
+
|
71
|
+
self
|
72
|
+
end
|
73
|
+
|
74
|
+
# Returns the resource's full path.
|
75
|
+
# @return [String] the resource's full path.
|
76
|
+
def resource_path
|
77
|
+
@parent.resource_path + self.name
|
78
|
+
end
|
79
|
+
|
80
|
+
private
|
81
|
+
|
82
|
+
def validate_parent
|
83
|
+
raise InvalidParent, "Parent of resource cannot be nil." if @parent.nil?
|
84
|
+
end
|
85
|
+
|
86
|
+
def parse_uri_parameters(value)
|
87
|
+
validate_hash :uri_parameters, value, String, Hash
|
88
|
+
value.map { |uname, udata| Parameter::UriParameter.new uname, udata, self }
|
89
|
+
end
|
90
|
+
|
91
|
+
def parse_base_uri_parameters(value)
|
92
|
+
validate_hash :base_uri_parameters, value, String, Hash
|
93
|
+
|
94
|
+
raise InvalidProperty, 'baseUriParameters property can\'t contain reserved "version" parameter' if
|
95
|
+
value.include? 'version'
|
96
|
+
|
97
|
+
value.map { |bname, bdata| Parameter::BaseUriParameter.new bname, bdata, self }
|
98
|
+
end
|
99
|
+
|
100
|
+
def parse_is(value)
|
101
|
+
validate_array :is, value, [String, Hash]
|
102
|
+
|
103
|
+
value.map do |trait|
|
104
|
+
if trait.is_a? Hash
|
105
|
+
if trait.keys.size == 1 and trait_declarations.include? trait.keys.first
|
106
|
+
raise InvalidProperty, 'is property with map of trait name but params are not a map' unless
|
107
|
+
trait.values[0].is_a? Hash
|
108
|
+
TraitReference.new( *trait.first, self )
|
109
|
+
else
|
110
|
+
Trait.new '_', trait, self
|
111
|
+
end
|
112
|
+
else
|
113
|
+
raise UnknownTraitReference, "#{trait} referenced in resource but not found in traits declaration." unless
|
114
|
+
trait_declarations.include? trait
|
115
|
+
TraitReference.new trait, self
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
Raml::Method::NAMES.each do |method|
|
121
|
+
define_method("parse_#{method}") do |value|
|
122
|
+
Method.new method, value, self
|
123
|
+
end
|
124
|
+
|
125
|
+
define_method("parse_#{method}?") do |value|
|
126
|
+
Method.new "#{method}?", value, self
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
130
|
+
def parse_type(value)
|
131
|
+
validate_property :type, value, [ Hash, String ]
|
132
|
+
|
133
|
+
if value.is_a? Hash
|
134
|
+
if value.keys.size == 1 and resource_type_declarations.include? value.keys.first
|
135
|
+
raise InvalidProperty, 'type property with map of resource type name but params are not a map' unless
|
136
|
+
value.values[0].is_a? Hash
|
137
|
+
ResourceTypeReference.new( *value.first, self )
|
138
|
+
else
|
139
|
+
ResourceType.new '_', value, self
|
140
|
+
end
|
141
|
+
else
|
142
|
+
raise UnknownResourceTypeReference, "#{value} referenced in resource but not found in resource types declaration." unless
|
143
|
+
resource_type_declarations.include? value
|
144
|
+
ResourceTypeReference.new value, self
|
145
|
+
end
|
146
|
+
end
|
147
|
+
|
148
|
+
def parse_secured_by(data)
|
149
|
+
# XXX ignored for now
|
150
|
+
[]
|
151
|
+
end
|
152
|
+
|
153
|
+
def instantiate_resource_type
|
154
|
+
reserved_params = {
|
155
|
+
'resourcePath' => resource_path,
|
156
|
+
'resourcePathName' => resource_path.split('/')[-1]
|
157
|
+
}
|
158
|
+
if ResourceTypeReference === type
|
159
|
+
resource_type_declarations[type.name].instantiate type.parameters.merge reserved_params
|
160
|
+
else
|
161
|
+
type.instantiate reserved_params
|
162
|
+
end
|
163
|
+
end
|
164
|
+
end
|
165
|
+
end
|