ananke 0.0.1 → 0.0.2
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/Gemfile +2 -2
- data/README.rdoc +29 -4
- data/lib/ananke.rb +160 -33
- data/lib/version.rb +1 -1
- data/spec/call_chain.rb +23 -0
- data/spec/dumping.rb +15 -0
- data/spec/lib/ananke_links_spec.rb +107 -0
- data/spec/lib/ananke_out_spec.rb +20 -0
- data/spec/lib/ananke_spec.rb +57 -17
- data/spec/lib/validation_spec.rb +9 -9
- data/spec/spec_helper.rb +10 -0
- metadata +12 -4
data/Gemfile
CHANGED
@@ -1,10 +1,10 @@
|
|
1
1
|
source "http://rubygems.org"
|
2
2
|
|
3
|
+
gem "colored", "~>1.2"
|
4
|
+
gem "json", "~>1.5.1"
|
3
5
|
gem "sinatra", "~>1.1.2"
|
4
6
|
|
5
7
|
group :development, :test do
|
6
|
-
gem "colored", "~>1.2"
|
7
|
-
gem "json", "~>1.5.1"
|
8
8
|
gem "rack-test", "~>0.5.6"
|
9
9
|
gem "rake", "~>0.8.7"
|
10
10
|
gem "rspec", "~>2.5.0"
|
data/README.rdoc
CHANGED
@@ -43,15 +43,40 @@ based on what's available in it's respective Repository. Routes are:
|
|
43
43
|
put '/name/id' -> Repository::Capitalize(name).edit(id, data)
|
44
44
|
delete '/name/id' -> Repository::Capitalize(name).delete(id)
|
45
45
|
|
46
|
+
== Repositories
|
47
|
+
The Default Repository can be changed:
|
48
|
+
|
49
|
+
ananke.default_repository = 'MyRepository'
|
50
|
+
|
51
|
+
== HyperMedia
|
52
|
+
Current HyperMedia support is very limited. The following example demostrates it's use:
|
53
|
+
|
54
|
+
rest :user do
|
55
|
+
id :id
|
56
|
+
linked :computer
|
57
|
+
end
|
58
|
+
|
59
|
+
To support the above example, the Respository for User needs to have a method that returns an
|
60
|
+
array of id's for use in the HyperMedia links. The method signature is as follows
|
61
|
+
|
62
|
+
def self.computer_id_list
|
63
|
+
[Return an array of single value id's]
|
64
|
+
end
|
65
|
+
|
66
|
+
It get called:
|
67
|
+
|
68
|
+
[ResourceRepository].[link name]_id_list
|
69
|
+
|
70
|
+
We are working on adding lots more HyperMedia Support, especially to get around problems that
|
71
|
+
the current HyperMedia is giving. Stay tuned...
|
72
|
+
|
73
|
+
== Media Type
|
46
74
|
The REST media type can be built up:
|
47
75
|
|
48
76
|
required :name
|
49
77
|
optional :country
|
50
78
|
|
51
|
-
|
52
|
-
The Default Repository can be changed:
|
53
|
-
|
54
|
-
ananke.default_repository = 'MyRepository'
|
79
|
+
Exposing the Media Type is on the cards.
|
55
80
|
|
56
81
|
== Validation
|
57
82
|
Validation can be added on any field by providing arguments after a field declaration:
|
data/lib/ananke.rb
CHANGED
@@ -1,62 +1,158 @@
|
|
1
|
+
require 'colored'
|
2
|
+
require 'json'
|
1
3
|
require 'sinatra/base'
|
2
4
|
|
3
5
|
module Ananke
|
4
6
|
class << self
|
5
|
-
attr_accessor :default_repository, :rules
|
7
|
+
attr_accessor :default_repository, :rules, :settings
|
6
8
|
end
|
7
|
-
|
9
|
+
|
8
10
|
private
|
11
|
+
extend Colored
|
12
|
+
|
9
13
|
@default_repository = 'Repository'
|
10
14
|
@rules = [:length]
|
15
|
+
@settings = {
|
16
|
+
:output => true,
|
17
|
+
:info => true,
|
18
|
+
:warning => true,
|
19
|
+
:error => true,
|
20
|
+
|
21
|
+
:links => true
|
22
|
+
}
|
23
|
+
|
24
|
+
#===========================OUTPUT=============================
|
25
|
+
def out(type, message)
|
26
|
+
return if !Ananke.settings[:output]
|
27
|
+
message = case
|
28
|
+
when type == :info && Ananke.settings[:info]
|
29
|
+
message.blue
|
30
|
+
when type == :warning && Ananke.settings[:warning]
|
31
|
+
message.yellow
|
32
|
+
when type == :error && Ananke.settings[:error]
|
33
|
+
message.red
|
34
|
+
end
|
35
|
+
puts message unless message.nil?
|
36
|
+
message
|
37
|
+
end
|
38
|
+
|
39
|
+
#===========================HELPERS============================
|
40
|
+
def get_mod(path)
|
41
|
+
mod = nil
|
42
|
+
rep = Module.const_get(Ananke.default_repository.to_sym) if Module.const_defined?(Ananke.default_repository.to_sym)
|
43
|
+
mod = rep.const_get("#{path.capitalize}".to_sym) if !rep.nil? && rep.const_defined?("#{path.capitalize}".to_sym)
|
44
|
+
mod
|
45
|
+
end
|
46
|
+
|
47
|
+
def get_json(path, obj)
|
48
|
+
if obj.nil?
|
49
|
+
out :error, "#{path} - No return object"
|
50
|
+
''
|
51
|
+
elsif !obj.respond_to?(:to_json)
|
52
|
+
out :error, "#{path} - Return object cannot be converted to JSON"
|
53
|
+
''
|
54
|
+
else
|
55
|
+
obj.to_json
|
56
|
+
end
|
57
|
+
end
|
11
58
|
|
59
|
+
#===========================BUILDUP============================
|
60
|
+
def build_route(mod, mod_method, verb, route, &block)
|
61
|
+
if mod.respond_to? mod_method
|
62
|
+
Sinatra::Base.send verb, "#{route}", do
|
63
|
+
instance_eval(&block)
|
64
|
+
end
|
65
|
+
else
|
66
|
+
out(:warning, "#{mod} does not respond to '#{mod_method.to_s}'")
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
12
70
|
def build(path)
|
13
|
-
|
14
|
-
mod
|
71
|
+
mod = get_mod(path)
|
72
|
+
if mod.nil?
|
73
|
+
out(:error, "Repository for #{path} not found")
|
74
|
+
return
|
75
|
+
end
|
15
76
|
key = @id[:key]
|
16
77
|
fields = @fields
|
17
|
-
|
78
|
+
linkups = @linkups
|
79
|
+
|
80
|
+
#===========================GET/ID=============================
|
81
|
+
build_route mod, :one, :get, "/#{path}/:#{key}" do
|
82
|
+
param_missing!(key) if params[key].nil?
|
83
|
+
obj = mod.one(params[key])
|
18
84
|
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
85
|
+
json = get_json(path, obj)
|
86
|
+
inject_links!(json, linkups, path, params[key], mod)
|
87
|
+
|
88
|
+
status 200
|
89
|
+
json
|
24
90
|
end
|
25
91
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
92
|
+
#===========================GET================================
|
93
|
+
build_route mod, :all, :get, "/#{path}/?" do
|
94
|
+
obj_list = mod.all
|
95
|
+
|
96
|
+
status 200
|
97
|
+
json_list = []
|
98
|
+
obj_list.each do |obj|
|
99
|
+
id = obj.respond_to?(key) ? obj.instance_variable_get(key) : obj.class == Hash && obj.has_key?(key) ? obj[key] : nil
|
100
|
+
if !id.nil?
|
101
|
+
json = get_json(path, obj)
|
102
|
+
inject_links!(json, linkups, path, id, mod)
|
103
|
+
json_list << json
|
104
|
+
else
|
105
|
+
out :error, "#{path} - Cannot find key(#{key}) on object #{obj}"
|
106
|
+
end
|
107
|
+
end
|
108
|
+
"[#{json_list.join(',')}]"
|
31
109
|
end
|
32
110
|
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
status, message = validate!(fields, params)
|
111
|
+
#===========================POST===============================
|
112
|
+
build_route mod, :add, :post, "/#{path}/?" do
|
113
|
+
status, message = validate(fields, params)
|
37
114
|
error status, message unless status.nil?
|
38
|
-
|
115
|
+
obj = mod.add(params)
|
116
|
+
|
117
|
+
json = get_json(path, obj)
|
118
|
+
inject_links!(json, linkups, path, params[key], mod)
|
119
|
+
|
39
120
|
status 201
|
40
|
-
|
121
|
+
json
|
41
122
|
end
|
42
123
|
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
124
|
+
#===========================PUT================================
|
125
|
+
build_route mod, :edit, :put, "/#{path}/:#{key}" do
|
126
|
+
param_missing!(key) if params[key].nil?
|
127
|
+
status, message = validate(fields, params)
|
128
|
+
error status, message unless status.nil?
|
129
|
+
obj = mod.edit(params[key], params)
|
130
|
+
|
131
|
+
json = get_json(path, obj)
|
132
|
+
inject_links!(json, linkups, path, params[key], mod)
|
133
|
+
|
47
134
|
status 200
|
48
|
-
|
135
|
+
json
|
136
|
+
end
|
137
|
+
|
138
|
+
build_route mod, :edit, :put, "/#{path}/?" do
|
139
|
+
param_missing!(key)
|
49
140
|
end
|
50
141
|
|
51
|
-
|
52
|
-
|
53
|
-
|
142
|
+
#===========================DELETE=============================
|
143
|
+
build_route mod, :delete, :delete, "/#{path}/:#{key}" do
|
144
|
+
param_missing!(key) if params[key].nil?
|
54
145
|
mod.delete(params[key]) if !params[key].nil?
|
55
146
|
status 200
|
56
147
|
end
|
148
|
+
|
149
|
+
build_route mod, :delete, :delete, "/#{path}/?" do
|
150
|
+
param_missing!(key)
|
151
|
+
end
|
57
152
|
end
|
58
153
|
|
59
|
-
|
154
|
+
#===========================Validation=========================
|
155
|
+
def validate(fields, params)
|
60
156
|
errors = []
|
61
157
|
fields.each do |field|
|
62
158
|
value = params[field[:key].to_s]
|
@@ -69,13 +165,38 @@ module Ananke
|
|
69
165
|
end
|
70
166
|
return 400, errors unless errors.empty?
|
71
167
|
end
|
168
|
+
def param_missing!(key)
|
169
|
+
error 400, "Missing Parameter: #{key.to_s}"
|
170
|
+
end
|
171
|
+
|
172
|
+
#===========================LINKING============================
|
173
|
+
def build_links(path, id, mod, linkups)
|
174
|
+
ret = [{:rel => 'self', :uri => "/#{path}/#{id}"}]
|
175
|
+
linkups.each do |l|
|
176
|
+
mod_method = "#{l[:rel]}_id_list"
|
177
|
+
if mod.respond_to?(mod_method)
|
178
|
+
id_list = mod.send(mod_method, id)
|
179
|
+
id_list.each{|i| ret << {:rel => "#{l[:rel]}", :uri => "/#{l[:rel]}/#{i}"}}
|
180
|
+
else
|
181
|
+
out :error, "#{path} - #{mod} does not respond to '#{mod_method.to_s}'"
|
182
|
+
end
|
183
|
+
end
|
184
|
+
ret
|
185
|
+
end
|
186
|
+
|
187
|
+
def inject_links!(json, linkups, path, id, mod)
|
188
|
+
return if !Ananke.settings[:links]
|
189
|
+
links = build_links(path, id, mod, linkups)
|
190
|
+
json.insert(json.length-1, ",\"links\":#{links.to_json}")
|
191
|
+
end
|
72
192
|
|
73
193
|
public
|
74
194
|
|
195
|
+
#===========================DSL================================
|
75
196
|
def rest(path, &block)
|
76
197
|
@id = {}
|
77
198
|
@fields = []
|
78
|
-
@
|
199
|
+
@linkups = []
|
79
200
|
yield block
|
80
201
|
build path
|
81
202
|
end
|
@@ -89,13 +210,14 @@ module Ananke
|
|
89
210
|
def optional(key, *rules)
|
90
211
|
@fields << {:key => key, :type => :optional, :rules => rules}
|
91
212
|
end
|
92
|
-
def
|
93
|
-
@
|
213
|
+
def linkup(rel)
|
214
|
+
@linkups << {:rel => rel}
|
94
215
|
end
|
95
216
|
def rule(name, &block)
|
96
217
|
Ananke::Rules.send(:define_singleton_method, "validate_#{name}", block)
|
97
218
|
end
|
98
219
|
|
220
|
+
#===========================Rules==============================
|
99
221
|
module Rules
|
100
222
|
class << self
|
101
223
|
attr_accessor :value
|
@@ -104,6 +226,11 @@ module Ananke
|
|
104
226
|
value.length >= min ? nil : "Value must be at least #{min} characters long"
|
105
227
|
end
|
106
228
|
end
|
229
|
+
|
230
|
+
#===========================Settings===========================
|
231
|
+
def set(name, val)
|
232
|
+
@settings[name] = val
|
233
|
+
end
|
107
234
|
end
|
108
235
|
|
109
236
|
include Ananke
|
data/lib/version.rb
CHANGED
data/spec/call_chain.rb
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
class CallChain
|
2
|
+
def self.caller_file(depth=1)
|
3
|
+
parse_caller(caller(depth+1).first)[0]
|
4
|
+
end
|
5
|
+
def self.caller_line(depth=1)
|
6
|
+
parse_caller(caller(depth+1).first)[1]
|
7
|
+
end
|
8
|
+
def self.caller_method(depth=1)
|
9
|
+
parse_caller(caller(depth+1).first)[2]
|
10
|
+
end
|
11
|
+
|
12
|
+
private
|
13
|
+
|
14
|
+
#Stolen from ActionMailer, where this was used but was not made reusable
|
15
|
+
def self.parse_caller(at)
|
16
|
+
if /^(.+?):(\d+)(?::in `(.*)')?/ =~ at
|
17
|
+
file = Regexp.last_match[1]
|
18
|
+
line = Regexp.last_match[2].to_i
|
19
|
+
method = Regexp.last_match[3]
|
20
|
+
[file, line, method]
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
data/spec/dumping.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require './spec/call_chain'
|
2
|
+
require 'fileutils'
|
3
|
+
|
4
|
+
def clear_dump
|
5
|
+
dirname = File.join(File.dirname(__FILE__), "..", "dump")
|
6
|
+
FileUtils::rm_rf(dirname)
|
7
|
+
FileUtils::mkdir(dirname)
|
8
|
+
end
|
9
|
+
def dump(content, filename)
|
10
|
+
File.open(File.expand_path(File.join(File.dirname(__FILE__), "..", "dump", "#{filename}")), 'w') {|f| f.write(content) }
|
11
|
+
end
|
12
|
+
def check_status(status)
|
13
|
+
dump(last_response.body, "#{CallChain::caller_file.split('/').last}_#{CallChain::caller_line}.htm") if last_response.status != status
|
14
|
+
last_response.status.should == status
|
15
|
+
end
|
@@ -0,0 +1,107 @@
|
|
1
|
+
require './spec/spec_helper'
|
2
|
+
require './lib/ananke'
|
3
|
+
|
4
|
+
describe 'Resource' do
|
5
|
+
include Rack::Test::Methods
|
6
|
+
include Ananke
|
7
|
+
|
8
|
+
def app
|
9
|
+
Sinatra::Base
|
10
|
+
end
|
11
|
+
|
12
|
+
it """
|
13
|
+
Should be able to Output link to Self and Call that link
|
14
|
+
""" do
|
15
|
+
module Repository
|
16
|
+
module Self
|
17
|
+
def self.one(id) end
|
18
|
+
def self.add(data)
|
19
|
+
{:user_id => 1}
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
rest :self do
|
24
|
+
id :user_id
|
25
|
+
end
|
26
|
+
|
27
|
+
post "/self", body={:user_id => 1, :username => '1234'}
|
28
|
+
check_status(201)
|
29
|
+
last_response.body.should == '{"user_id":1,"links":[{"rel":"self","uri":"/self/1"}]}'
|
30
|
+
|
31
|
+
hash = JSON.parse(last_response.body)
|
32
|
+
uri = hash['links'].map{|l| l['uri'] if l['rel'] == 'self'}[0]
|
33
|
+
get uri
|
34
|
+
check_status(200)
|
35
|
+
end
|
36
|
+
|
37
|
+
module Repository
|
38
|
+
module Linkup
|
39
|
+
def self.one(id)
|
40
|
+
{:user_id => 1}
|
41
|
+
end
|
42
|
+
def self.all
|
43
|
+
[{:user_id => 1}, {:user_id => 2}]
|
44
|
+
end
|
45
|
+
def self.add(data)
|
46
|
+
{:user_id => 1}
|
47
|
+
end
|
48
|
+
def self.edit(id, data)
|
49
|
+
{:user_id => 1}
|
50
|
+
end
|
51
|
+
def self.line_id_list(user_id)
|
52
|
+
[1,2]
|
53
|
+
end
|
54
|
+
end
|
55
|
+
module Line
|
56
|
+
def self.one(id) end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
rest :linkup do
|
60
|
+
id :user_id
|
61
|
+
linkup :line
|
62
|
+
end
|
63
|
+
rest :line do
|
64
|
+
id :line_id
|
65
|
+
end
|
66
|
+
|
67
|
+
it """
|
68
|
+
Should be able to Output links to linkups and Call those links
|
69
|
+
""" do
|
70
|
+
post "/linkup", body={:user_id => 1, :username => '1234'}
|
71
|
+
check_status(201)
|
72
|
+
last_response.body.should == '{"user_id":1,"links":[{"rel":"self","uri":"/linkup/1"},{"rel":"line","uri":"/line/1"},{"rel":"line","uri":"/line/2"}]}'
|
73
|
+
|
74
|
+
hash = JSON.parse(last_response.body)
|
75
|
+
hash['links'].each do |l|
|
76
|
+
get l['uri']
|
77
|
+
check_status(200)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
it "Should return links on Get One" do
|
82
|
+
#get "/linkup/1"
|
83
|
+
#check_status(200)
|
84
|
+
#last_response.body.should == '{"user_id":1,"links":[{"rel":"self","uri":"/linkup/1"},{"rel":"line","uri":"/line/1"},{"rel":"line","uri":"/line/2"}]}'
|
85
|
+
end
|
86
|
+
|
87
|
+
it """
|
88
|
+
Should not inject links where it cannot find Repository Id lookup method
|
89
|
+
""" do
|
90
|
+
module Repository
|
91
|
+
module Linkup_fail
|
92
|
+
def self.one(id) end
|
93
|
+
def self.add(data)
|
94
|
+
{:user_id => 1}
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
rest :linkup_fail do
|
99
|
+
id :user_id
|
100
|
+
linkup :line
|
101
|
+
end
|
102
|
+
|
103
|
+
post "/linkup_fail", body={:user_id => 1, :username => '1234'}
|
104
|
+
check_status(201)
|
105
|
+
last_response.body.should == '{"user_id":1,"links":[{"rel":"self","uri":"/linkup_fail/1"}]}'
|
106
|
+
end
|
107
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require './spec/spec_helper'
|
2
|
+
require './lib/ananke'
|
3
|
+
|
4
|
+
describe 'Ananke Console Output' do
|
5
|
+
include Ananke
|
6
|
+
|
7
|
+
it """
|
8
|
+
Should be able to output in different Colors
|
9
|
+
""" do
|
10
|
+
output = Ananke.settings[:output]
|
11
|
+
Ananke.set :output, true
|
12
|
+
|
13
|
+
Ananke.send(:out, :info, 'test').should == 'test'.blue
|
14
|
+
Ananke.send(:out, :error, 'test').should == 'test'.red
|
15
|
+
Ananke.send(:out, :warning, 'test').should == 'test'.yellow
|
16
|
+
Ananke.send(:out, :some_other, 'test').should == nil
|
17
|
+
|
18
|
+
Ananke.set :output, output
|
19
|
+
end
|
20
|
+
end
|
data/spec/lib/ananke_spec.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
require './spec/spec_helper'
|
2
2
|
require './lib/ananke'
|
3
3
|
|
4
|
-
describe '
|
4
|
+
describe 'Basic Ananke REST' do
|
5
5
|
include Rack::Test::Methods
|
6
6
|
include Ananke
|
7
7
|
|
@@ -10,18 +10,31 @@ describe 'Resource' do
|
|
10
10
|
end
|
11
11
|
|
12
12
|
before(:all) do
|
13
|
+
Ananke.set :links, false
|
14
|
+
end
|
15
|
+
|
16
|
+
after(:all) do
|
17
|
+
Ananke.set :links, true
|
18
|
+
end
|
19
|
+
|
20
|
+
#----------------------------SETUP--------------------------------------
|
21
|
+
it """
|
22
|
+
Should be able to describe a Valid REST Resource
|
23
|
+
""" do
|
13
24
|
rest :user do
|
14
25
|
id :user_id
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
it """
|
30
|
+
Should skip creating Routes for Non-Existing Repositories
|
31
|
+
""" do
|
32
|
+
rest :invalid do
|
20
33
|
end
|
21
34
|
end
|
22
35
|
|
23
36
|
it """
|
24
|
-
Should setup the defaults for
|
37
|
+
Should setup the defaults for REST
|
25
38
|
""" do
|
26
39
|
Ananke.default_repository.should == 'Repository'
|
27
40
|
end
|
@@ -30,7 +43,9 @@ describe 'Resource' do
|
|
30
43
|
Should setup Routes
|
31
44
|
""" do
|
32
45
|
Sinatra::Base.routes["GET"][-1][0].inspect.include?('user').should == true
|
33
|
-
|
46
|
+
count = 0
|
47
|
+
Sinatra::Base.routes["GET"].each_index{|i| count += 1 if Sinatra::Base.routes["GET"][i][0].inspect.include?('user')}
|
48
|
+
count.should == 2
|
34
49
|
Sinatra::Base.routes["POST"][-1][0].inspect.include?('user').should == true
|
35
50
|
Sinatra::Base.routes["PUT"][-1][0].inspect.include?('user').should == true
|
36
51
|
Sinatra::Base.routes["DELETE"][-1][0].inspect.include?('user').should == true
|
@@ -44,7 +59,7 @@ describe 'Resource' do
|
|
44
59
|
- body: [{:id=>1, :name=>'one'}, {:id => 2, :name => 'two'}]
|
45
60
|
""" do
|
46
61
|
get "/user"
|
47
|
-
|
62
|
+
check_status(200)
|
48
63
|
last_response.body.should == Repository::User.data.to_json
|
49
64
|
end
|
50
65
|
|
@@ -55,7 +70,7 @@ describe 'Resource' do
|
|
55
70
|
- body: {user_id: ,username: ,email: ,country: }
|
56
71
|
""" do
|
57
72
|
get "/user/1"
|
58
|
-
|
73
|
+
check_status(200)
|
59
74
|
last_response.body.should == Repository::User.data[0].to_json
|
60
75
|
end
|
61
76
|
|
@@ -68,8 +83,7 @@ describe 'Resource' do
|
|
68
83
|
- body:
|
69
84
|
""" do
|
70
85
|
post "/user", body={:user_id => 3, :username => 'three', :email => '3@three.com', :country => 'USA'}
|
71
|
-
|
72
|
-
last_response.body.should == ''
|
86
|
+
check_status(201)
|
73
87
|
end
|
74
88
|
|
75
89
|
it """
|
@@ -81,8 +95,7 @@ describe 'Resource' do
|
|
81
95
|
- body:
|
82
96
|
""" do
|
83
97
|
put "/user/3", body={:user_id => 3, :username => 'four', :email => '4@four.com', :country => 'Russia'}
|
84
|
-
|
85
|
-
last_response.body.should == ''
|
98
|
+
check_status(200)
|
86
99
|
end
|
87
100
|
|
88
101
|
it """
|
@@ -93,8 +106,33 @@ describe 'Resource' do
|
|
93
106
|
- body:
|
94
107
|
""" do
|
95
108
|
delete "/user/3"
|
96
|
-
|
97
|
-
|
109
|
+
check_status(200)
|
110
|
+
end
|
111
|
+
|
112
|
+
#----------------------------FAILS--------------------------------------
|
113
|
+
it """
|
114
|
+
PUT /user
|
115
|
+
- body: {user_id: ,username: ,email: ,country: }
|
116
|
+
RETURN
|
117
|
+
- code: 400
|
118
|
+
- content-type: text/json
|
119
|
+
- body: Missing Parameter: user_id
|
120
|
+
""" do
|
121
|
+
put "/user", body={:user_id => 3, :username => 'four', :email => '4@four.com', :country => 'Russia'}
|
122
|
+
check_status(400)
|
123
|
+
last_response.body.should == 'Missing Parameter: user_id'
|
124
|
+
end
|
125
|
+
|
126
|
+
it """
|
127
|
+
DELETE /user
|
128
|
+
RETURN
|
129
|
+
- code: 400
|
130
|
+
- content-type: text/json
|
131
|
+
- body: Missing Parameter: user_id
|
132
|
+
""" do
|
133
|
+
delete "/user"
|
134
|
+
check_status(400)
|
135
|
+
last_response.body.should == 'Missing Parameter: user_id'
|
98
136
|
end
|
99
137
|
end
|
100
138
|
|
@@ -113,11 +151,13 @@ module Repository
|
|
113
151
|
def self.all
|
114
152
|
@data
|
115
153
|
end
|
116
|
-
def self.
|
154
|
+
def self.add(data)
|
117
155
|
@data << data
|
156
|
+
data
|
118
157
|
end
|
119
158
|
def self.edit(id, data)
|
120
159
|
@data.each { |d| d = data if d[:user_id] == id}
|
160
|
+
data
|
121
161
|
end
|
122
162
|
def self.delete(id)
|
123
163
|
@data.delete_if { |i| i[:user_id] == id}
|
data/spec/lib/validation_spec.rb
CHANGED
@@ -16,7 +16,7 @@ describe 'Resource' do
|
|
16
16
|
""" do
|
17
17
|
module Repository
|
18
18
|
module Basic
|
19
|
-
def self.
|
19
|
+
def self.add(data)end
|
20
20
|
end
|
21
21
|
end
|
22
22
|
rest :basic do
|
@@ -25,11 +25,11 @@ describe 'Resource' do
|
|
25
25
|
end
|
26
26
|
|
27
27
|
post "/basic", body={:user_id => 1, :username => ''}
|
28
|
-
|
28
|
+
check_status(400)
|
29
29
|
last_response.body.should == 'username: Value must be at least 4 characters long'
|
30
30
|
|
31
31
|
post "/basic", body={:user_id => 1, :username => '1234'}
|
32
|
-
|
32
|
+
check_status(201)
|
33
33
|
end
|
34
34
|
|
35
35
|
it """
|
@@ -46,7 +46,7 @@ describe 'Resource' do
|
|
46
46
|
|
47
47
|
module Repository
|
48
48
|
module Explicit
|
49
|
-
def self.
|
49
|
+
def self.add(data)end
|
50
50
|
end
|
51
51
|
end
|
52
52
|
rest :explicit do
|
@@ -55,11 +55,11 @@ describe 'Resource' do
|
|
55
55
|
end
|
56
56
|
|
57
57
|
post "/explicit", body={:user_id => 1, :email => 'some'}
|
58
|
-
|
58
|
+
check_status(400)
|
59
59
|
last_response.body.should == 'email: Invalid Email: some'
|
60
60
|
|
61
61
|
post "/explicit", body={:user_id => 1, :email => 'some1@some.com'}
|
62
|
-
|
62
|
+
check_status(201)
|
63
63
|
end
|
64
64
|
|
65
65
|
it """
|
@@ -70,7 +70,7 @@ describe 'Resource' do
|
|
70
70
|
end
|
71
71
|
module Repository
|
72
72
|
module Added
|
73
|
-
def self.
|
73
|
+
def self.add(data)end
|
74
74
|
end
|
75
75
|
end
|
76
76
|
rest :added do
|
@@ -80,10 +80,10 @@ describe 'Resource' do
|
|
80
80
|
Ananke::Rules.respond_to?('validate_country').should == true
|
81
81
|
|
82
82
|
post "/added", body={:user_id => 1, :country => 'England'}
|
83
|
-
|
83
|
+
check_status(400)
|
84
84
|
last_response.body.should == 'country: Not from South Africa'
|
85
85
|
|
86
86
|
post "/added", body={:user_id => 1, :country => 'South Africa'}
|
87
|
-
|
87
|
+
check_status(201)
|
88
88
|
end
|
89
89
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -8,10 +8,20 @@ require 'json'
|
|
8
8
|
require 'rack'
|
9
9
|
require 'rspec'
|
10
10
|
require 'rack/test'
|
11
|
+
require './lib/ananke'
|
11
12
|
|
12
13
|
extend Colored
|
13
14
|
|
14
15
|
#==================SETUP TEST ENVIRONMENT======================
|
15
16
|
ENV['RACK_ENV'] = 'test'
|
16
17
|
|
18
|
+
Ananke.set :output, false
|
19
|
+
Ananke.set :info, true
|
20
|
+
Ananke.set :warning, true
|
21
|
+
Ananke.set :error, true
|
22
|
+
|
17
23
|
$LOAD_PATH.unshift File.expand_path(File.join(File.dirname(__FILE__), ".."))
|
24
|
+
|
25
|
+
#==================FOR DUMPING HTTP REQUESTS===================
|
26
|
+
require './spec/dumping'
|
27
|
+
clear_dump
|
metadata
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
name: ananke
|
3
3
|
version: !ruby/object:Gem::Version
|
4
4
|
prerelease:
|
5
|
-
version: 0.0.
|
5
|
+
version: 0.0.2
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Andries Coetzee
|
@@ -10,7 +10,7 @@ autorequire:
|
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
12
|
|
13
|
-
date: 2011-02-
|
13
|
+
date: 2011-02-10 00:00:00 +02:00
|
14
14
|
default_executable:
|
15
15
|
dependencies:
|
16
16
|
- !ruby/object:Gem::Dependency
|
@@ -101,10 +101,14 @@ extra_rdoc_files:
|
|
101
101
|
files:
|
102
102
|
- lib/ananke.rb
|
103
103
|
- lib/version.rb
|
104
|
+
- spec/dumping.rb
|
104
105
|
- spec/cov_adapter.rb
|
105
106
|
- spec/lib/ananke_spec.rb
|
107
|
+
- spec/lib/ananke_out_spec.rb
|
108
|
+
- spec/lib/ananke_links_spec.rb
|
106
109
|
- spec/lib/validation_spec.rb
|
107
110
|
- spec/spec_helper.rb
|
111
|
+
- spec/call_chain.rb
|
108
112
|
- spec/nice_formatter.rb
|
109
113
|
- Gemfile
|
110
114
|
- Rakefile
|
@@ -116,7 +120,7 @@ licenses: []
|
|
116
120
|
post_install_message: |
|
117
121
|
**************************************************
|
118
122
|
|
119
|
-
Thank you for installing ananke-0.0.
|
123
|
+
Thank you for installing ananke-0.0.2
|
120
124
|
|
121
125
|
Please be sure to look at README.rdoc to see what might have changed
|
122
126
|
since the last release and how to use this GEM.
|
@@ -145,10 +149,14 @@ rubyforge_project:
|
|
145
149
|
rubygems_version: 1.5.0
|
146
150
|
signing_key:
|
147
151
|
specification_version: 3
|
148
|
-
summary: ananke-0.0.
|
152
|
+
summary: ananke-0.0.2
|
149
153
|
test_files:
|
154
|
+
- spec/dumping.rb
|
150
155
|
- spec/cov_adapter.rb
|
151
156
|
- spec/lib/ananke_spec.rb
|
157
|
+
- spec/lib/ananke_out_spec.rb
|
158
|
+
- spec/lib/ananke_links_spec.rb
|
152
159
|
- spec/lib/validation_spec.rb
|
153
160
|
- spec/spec_helper.rb
|
161
|
+
- spec/call_chain.rb
|
154
162
|
- spec/nice_formatter.rb
|