strutta-api 1.0.1
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.
- checksums.yaml +7 -0
- data/.gitignore +18 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +55 -0
- data/Rakefile +7 -0
- data/lib/strutta-api.rb +109 -0
- data/lib/strutta-api/api_object.rb +58 -0
- data/lib/strutta-api/entries.rb +35 -0
- data/lib/strutta-api/errors.rb +47 -0
- data/lib/strutta-api/flow.rb +35 -0
- data/lib/strutta-api/games.rb +159 -0
- data/lib/strutta-api/judging.rb +29 -0
- data/lib/strutta-api/moderation.rb +29 -0
- data/lib/strutta-api/participants.rb +60 -0
- data/lib/strutta-api/points.rb +22 -0
- data/lib/strutta-api/rounds.rb +17 -0
- data/lib/strutta-api/version.rb +9 -0
- data/spec/entries_spec.rb +168 -0
- data/spec/errors_spec.rb +55 -0
- data/spec/fixtures/entries_fixtures.rb +64 -0
- data/spec/fixtures/flow_fixtures.rb +34 -0
- data/spec/fixtures/games_fixtures.rb +131 -0
- data/spec/fixtures/judging_fixtures.rb +72 -0
- data/spec/fixtures/moderation_fixtures.rb +56 -0
- data/spec/fixtures/participants_fixtures.rb +43 -0
- data/spec/fixtures/points_fixtures.rb +4 -0
- data/spec/fixtures/rounds_fixtures.rb +68 -0
- data/spec/flow_spec.rb +122 -0
- data/spec/games_spec.rb +176 -0
- data/spec/judging_spec.rb +122 -0
- data/spec/moderation_spec.rb +114 -0
- data/spec/participants_spec.rb +191 -0
- data/spec/points_spec.rb +99 -0
- data/spec/rounds_spec.rb +123 -0
- data/spec/spec_helper.rb +16 -0
- data/strutta-api.gemspec +31 -0
- metadata +211 -0
@@ -0,0 +1,29 @@
|
|
1
|
+
module Strutta
|
2
|
+
# Entries belong to a Strutta::Games object
|
3
|
+
# Instance methods found in Strutta::APIObject
|
4
|
+
class Judging < APIObject
|
5
|
+
# Initializes the Strutta::Entries object
|
6
|
+
#
|
7
|
+
# @param id [Integer, nil] Entry id
|
8
|
+
# @param game [Strutta::Games] Master Strutta::Games object
|
9
|
+
# @return [Strutta::Points] instantiated Strutta::Points object
|
10
|
+
def initialize(id = nil, game)
|
11
|
+
@id = id
|
12
|
+
@game = game
|
13
|
+
@root_path = 'judging'
|
14
|
+
end
|
15
|
+
|
16
|
+
# GET request for Judging (no ID required)
|
17
|
+
#
|
18
|
+
# @return [Hash] Parsed body of the API response
|
19
|
+
def get(params = {})
|
20
|
+
@game.verify_no_id(@id)
|
21
|
+
@game.get(params, @root_path)
|
22
|
+
end
|
23
|
+
|
24
|
+
# Disbled methods
|
25
|
+
alias_method :all, :method_disabled
|
26
|
+
alias_method :update, :method_disabled
|
27
|
+
alias_method :delete, :method_disabled
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
module Strutta
|
2
|
+
# Entries belong to a Strutta::Games object
|
3
|
+
# Instance methods found in Strutta::APIObject
|
4
|
+
class Moderation < APIObject
|
5
|
+
# Initializes the Strutta::Entries object
|
6
|
+
#
|
7
|
+
# @param id [Integer, nil] Entry id
|
8
|
+
# @param game [Strutta::Games] Master Strutta::Games object
|
9
|
+
# @return [Strutta::Points] instantiated Strutta::Points object
|
10
|
+
def initialize(id = nil, game)
|
11
|
+
@id = id
|
12
|
+
@game = game
|
13
|
+
@root_path = 'moderation'
|
14
|
+
end
|
15
|
+
|
16
|
+
# GET request for Moderation (no ID required)
|
17
|
+
#
|
18
|
+
# @return [Hash] Parsed body of the API response
|
19
|
+
def get(params = {})
|
20
|
+
@game.verify_no_id(@id)
|
21
|
+
@game.get(params, @root_path)
|
22
|
+
end
|
23
|
+
|
24
|
+
# Disbled methods
|
25
|
+
alias_method :all, :method_disabled
|
26
|
+
alias_method :update, :method_disabled
|
27
|
+
alias_method :delete, :method_disabled
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
module Strutta
|
2
|
+
# Participants belong to a Strutta::Games object
|
3
|
+
# Instance methods found in Strutta::APIObject
|
4
|
+
class Participants < APIObject
|
5
|
+
# Initializes the Strutta::Participants object
|
6
|
+
#
|
7
|
+
# @param id [Integer, nil] Entry id
|
8
|
+
# @param game [Strutta::Games] Master Strutta::Games object
|
9
|
+
# @return [Strutta::Participants] instantiated Strutta::Participants object
|
10
|
+
def initialize(id = nil, game)
|
11
|
+
@id = id
|
12
|
+
@game = game
|
13
|
+
@root_path = "participants/#{@id}"
|
14
|
+
@no_id_error = Errors::PARTICIPANT_ID_REQUIRED
|
15
|
+
end
|
16
|
+
|
17
|
+
# GET participant by email address
|
18
|
+
# games/:game_id/participants/search
|
19
|
+
#
|
20
|
+
# @return [Hash] Parsed body of the API response
|
21
|
+
def search(params)
|
22
|
+
fail Errors::InvalidSearchParameters, Errors::INVALID_SEARCH unless params.key? :email
|
23
|
+
@game.verify_no_id(@id)
|
24
|
+
@game.get(params, 'participants/search')
|
25
|
+
end
|
26
|
+
|
27
|
+
# PATCH update Participant token
|
28
|
+
# games/:game_id/participants/:id/token
|
29
|
+
#
|
30
|
+
# @return [Hash] Parsed body of the API response
|
31
|
+
def token_renew(params = {})
|
32
|
+
participant_id_required
|
33
|
+
@game.update(params, "participants/#{@id}/token")
|
34
|
+
end
|
35
|
+
|
36
|
+
# GET participant permissions
|
37
|
+
# games/:game_id/participants/:id/permissions
|
38
|
+
#
|
39
|
+
# @return [Hash] Parsed body of the API response
|
40
|
+
def permissions(params = {})
|
41
|
+
participant_id_required
|
42
|
+
@game.get(params, "participants/#{@id}/permissions")
|
43
|
+
end
|
44
|
+
|
45
|
+
# PATCH participant permissions
|
46
|
+
# games/:game_id/participants/:id/permissions
|
47
|
+
#
|
48
|
+
# @return [Hash] Parsed body of the API response
|
49
|
+
def permissions_update(params = {})
|
50
|
+
participant_id_required
|
51
|
+
@game.update(params, "participants/#{@id}/permissions")
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def participant_id_required
|
57
|
+
@game.verify_id(@id, Errors::PARTICIPANT_ID_REQUIRED)
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module Strutta
|
2
|
+
# Entries belong to a Strutta::Games object
|
3
|
+
# Instance methods found in Strutta::APIObject
|
4
|
+
class Points < APIObject
|
5
|
+
# Initializes the Strutta::Entries object
|
6
|
+
#
|
7
|
+
# @param id [Integer, nil] Entry id
|
8
|
+
# @param game [Strutta::Games] Master Strutta::Games object
|
9
|
+
# @return [Strutta::Points] instantiated Strutta::Points object
|
10
|
+
def initialize(id = nil, game)
|
11
|
+
@id = id
|
12
|
+
@game = game
|
13
|
+
@root_path = 'points'
|
14
|
+
end
|
15
|
+
|
16
|
+
# Disbled methods
|
17
|
+
alias_method :all, :method_disabled
|
18
|
+
alias_method :get, :method_disabled
|
19
|
+
alias_method :update, :method_disabled
|
20
|
+
alias_method :delete, :method_disabled
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module Strutta
|
2
|
+
# Rounds belong to a Strutta::Games object
|
3
|
+
# Instance methods found in Strutta::APIObject
|
4
|
+
class Rounds < APIObject
|
5
|
+
# Initializes the Strutta::Rounds object
|
6
|
+
#
|
7
|
+
# @param id [Integer, nil] Entry id
|
8
|
+
# @param game [Strutta::Games] Master Strutta::Games object
|
9
|
+
# @return [Strutta::Rounds] instantiated Strutta::Rounds object
|
10
|
+
def initialize(id = nil, game)
|
11
|
+
@id = id
|
12
|
+
@game = game
|
13
|
+
@root_path = "rounds/#{@id}"
|
14
|
+
@no_id_error = Errors::ROUND_ID_REQUIRED
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,168 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'Strutta API Wrapper' do
|
4
|
+
|
5
|
+
before { WebMock.disable_net_connect!(allow_localhost: true, allow: /codeclimate/) }
|
6
|
+
after { WebMock.allow_net_connect! }
|
7
|
+
|
8
|
+
let(:token) { 'dc1479c52801fbfa0975947de092a1e7' }
|
9
|
+
let(:host) { 'http://api.strutta.dev:4000' }
|
10
|
+
let(:path) { '/v2/' }
|
11
|
+
let(:strutta) { Strutta::API.new token, host, path }
|
12
|
+
|
13
|
+
describe 'games(:id).entries' do
|
14
|
+
context 'when no id is given' do
|
15
|
+
context '.get' do
|
16
|
+
it 'should throw error' do
|
17
|
+
expect { strutta.games.entries.get }.to raise_error(Strutta::Errors::ObjectIDRequired)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
context '.update' do
|
22
|
+
it 'should throw error' do
|
23
|
+
expect { strutta.games.entries.update(title: 'title') }.to raise_error(Strutta::Errors::ObjectIDRequired)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
context '.delete' do
|
28
|
+
it 'should throw error' do
|
29
|
+
expect { strutta.games.entries.delete }.to raise_error(Strutta::Errors::ObjectIDRequired)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
context '.transitions' do
|
34
|
+
it 'should throw error' do
|
35
|
+
expect { strutta.games.entries.transitions }.to raise_error(Strutta::Errors::ObjectIDRequired)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
context '.all' do
|
40
|
+
before do
|
41
|
+
stub_request(:get, /.*entries/)
|
42
|
+
.to_return(status: 200, body: ENTRY_INDEX.to_json, headers: {})
|
43
|
+
end
|
44
|
+
it 'should return array of entries' do
|
45
|
+
entries = strutta.games(VALID_GAME_01[:id]).entries.all
|
46
|
+
results = entries['results']
|
47
|
+
expect(results.is_a? Array).to be true
|
48
|
+
end
|
49
|
+
|
50
|
+
context 'when state is passed' do
|
51
|
+
before do
|
52
|
+
stub_request(:get, /.*entries/)
|
53
|
+
.with(body: hash_including(state: 111))
|
54
|
+
.to_return(status: 200, body: ENTRY_INDEX.to_json, headers: {})
|
55
|
+
end
|
56
|
+
it 'should return entries with that state' do
|
57
|
+
entries = strutta.games(VALID_GAME_01[:id]).entries.all(state: 111)
|
58
|
+
results = entries['results']
|
59
|
+
expect(results.is_a? Array).to be true
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
context 'when participant is passed' do
|
64
|
+
before do
|
65
|
+
stub_request(:get, /.*entries/)
|
66
|
+
.to_return(status: 200, body: ENTRY_INDEX.to_json, headers: {})
|
67
|
+
end
|
68
|
+
it 'should return entries with that state' do
|
69
|
+
entries = strutta.games(VALID_GAME_01[:id]).entries.all(participant: SUBMISSION_ROUND[:id])
|
70
|
+
results = entries['results']
|
71
|
+
expect(results.is_a? Array).to be true
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
context '.leaderboard' do
|
77
|
+
before do
|
78
|
+
stub_request(:get, /.*entries\/leaderboard/)
|
79
|
+
.to_return(status: 200, body: ENTRY_LEADERBOARD.to_json, headers: {})
|
80
|
+
end
|
81
|
+
it 'should return a leaderboard of entries' do
|
82
|
+
leaderboard = strutta.games(VALID_GAME_01[:id]).entries.leaderboard
|
83
|
+
results = leaderboard['results']
|
84
|
+
expect(results.is_a? Array).to be true
|
85
|
+
expect(leaderboard['paging']['top_rank'].is_a? Integer).to be true
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
context '.create' do
|
90
|
+
context 'with valid parameters' do
|
91
|
+
before do
|
92
|
+
stub_request(:post, /.*entries/)
|
93
|
+
.to_return(status: 201, body: ENTRY_01.to_json, headers: {})
|
94
|
+
end
|
95
|
+
it 'should return a new entry hash' do
|
96
|
+
entry = strutta.games(VALID_GAME_01[:id]).entries.create(participant: PARTICIPANT_01[:id])
|
97
|
+
expect(entry['id']).to_not be nil
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
context 'when id is given' do
|
104
|
+
context '.get' do
|
105
|
+
before do
|
106
|
+
stub_request(:get, /.*entries\/\d+/)
|
107
|
+
.to_return(status: 200, body: ENTRY_01.to_json, headers: {})
|
108
|
+
end
|
109
|
+
it 'should return entry hash' do
|
110
|
+
e = strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).get
|
111
|
+
expect(e['id']).to_not be nil
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
context '.update' do
|
116
|
+
before do
|
117
|
+
stub_request(:patch, /.*entries\/\d+/)
|
118
|
+
.to_return(status: 200, body: ENTRY_01_UPDATED.to_json, headers: {})
|
119
|
+
end
|
120
|
+
it 'should return updated entry hash' do
|
121
|
+
metadata = { age: 20 }
|
122
|
+
updated = strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).update(metadata: metadata)
|
123
|
+
expect(updated['metadata']['age']).to eq(20)
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
context '.delete' do
|
128
|
+
before do
|
129
|
+
stub_request(:delete, /.*entries\/\d+/)
|
130
|
+
.to_return(status: 204, body: '', headers: {})
|
131
|
+
end
|
132
|
+
it 'should delete entry' do
|
133
|
+
expect(strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).delete).to be true
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
context '.transitions' do
|
138
|
+
before do
|
139
|
+
stub_request(:get, %r{.*entries\/\d+\/transitions})
|
140
|
+
.to_return(status: 200, body: ENTRY_TRANSITIONS.to_json, headers: {})
|
141
|
+
end
|
142
|
+
it 'should get list of entry transitions' do
|
143
|
+
body = strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).transitions
|
144
|
+
expect(body['transitions'].is_a? Array).to be true
|
145
|
+
expect(body['transitions'].first['from'].is_a? Integer).to be true
|
146
|
+
end
|
147
|
+
end
|
148
|
+
|
149
|
+
context '.all' do
|
150
|
+
it 'should throw error' do
|
151
|
+
expect { strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).all }.to raise_error(Strutta::Errors::ObjectIDNotAllowed)
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
context '.leaderboard' do
|
156
|
+
it 'should throw error' do
|
157
|
+
expect { strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).leaderboard }.to raise_error(Strutta::Errors::ObjectIDNotAllowed)
|
158
|
+
end
|
159
|
+
end
|
160
|
+
|
161
|
+
context '.create' do
|
162
|
+
it 'should throw error' do
|
163
|
+
expect { strutta.games(VALID_GAME_01[:id]).entries(ENTRY_01[:id]).create(email: 'my@email.com') }.to raise_error(Strutta::Errors::ObjectIDNotAllowed)
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|
168
|
+
end
|
data/spec/errors_spec.rb
ADDED
@@ -0,0 +1,55 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'Strutta API Wrapper' do
|
4
|
+
|
5
|
+
before { WebMock.disable_net_connect!(allow_localhost: true, allow: /codeclimate/) }
|
6
|
+
after { WebMock.allow_net_connect! }
|
7
|
+
|
8
|
+
let(:token) { 'dc1479c52801fbfa0975947de092a1e7' }
|
9
|
+
let(:host) { 'http://api.strutta.dev:4000' }
|
10
|
+
let(:path) { '/v2/' }
|
11
|
+
let(:strutta) { Strutta::API.new token, host, path }
|
12
|
+
|
13
|
+
describe 'Errors' do
|
14
|
+
before do
|
15
|
+
stub_request(:get, /.*games/)
|
16
|
+
.to_return(status: 401, body: '{}', headers: {})
|
17
|
+
end
|
18
|
+
context 'when token is invalid' do
|
19
|
+
it 'should throw Unauthorized error' do
|
20
|
+
invalid_strutta = Strutta::API.new 'not_a_token', host, path
|
21
|
+
expect { invalid_strutta.games.all }.to raise_error(Strutta::Errors::Unauthorized)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
context 'when object does not exist' do
|
26
|
+
before do
|
27
|
+
stub_request(:get, /.*games\/\d+/)
|
28
|
+
.to_return(status: 404, body: '{}', headers: {})
|
29
|
+
end
|
30
|
+
it 'should throw ObjectNotFoundError error' do
|
31
|
+
expect { strutta.games(345).get }.to raise_error(Strutta::Errors::ObjectNotFoundError)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
context 'when parameters are missing' do
|
36
|
+
before do
|
37
|
+
stub_request(:post, %r{.*games\/\d+\/rounds})
|
38
|
+
.to_return(status: 422, body: '{}', headers: {})
|
39
|
+
end
|
40
|
+
it 'should throw UnprocessableEntityError error' do
|
41
|
+
expect { strutta.games(VALID_GAME_01[:id]).rounds.create(type: 'submission') }.to raise_error(Strutta::Errors::UnprocessableEntityError)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
context 'when parameters are missing' do
|
46
|
+
before do
|
47
|
+
stub_request(:post, %r{.*games\/\d+\/rounds})
|
48
|
+
.to_return(status: 400, body: '{}', headers: {})
|
49
|
+
end
|
50
|
+
it 'should throw BadRequestError error' do
|
51
|
+
expect { strutta.games(VALID_GAME_01[:id]).rounds.create(type: 'not_a_type') }.to raise_error(Strutta::Errors::BadRequestError)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,64 @@
|
|
1
|
+
ENTRY_01 = {
|
2
|
+
id: 6191,
|
3
|
+
game_id: 3922,
|
4
|
+
metadata: {
|
5
|
+
title: 'My entry'
|
6
|
+
},
|
7
|
+
state: 4281,
|
8
|
+
participant: 6736,
|
9
|
+
points: 111,
|
10
|
+
rank: 3
|
11
|
+
}
|
12
|
+
ENTRY_01_UPDATED = {
|
13
|
+
id: 6191,
|
14
|
+
game_id: 3922,
|
15
|
+
metadata: {
|
16
|
+
age: 20
|
17
|
+
},
|
18
|
+
state: 4281,
|
19
|
+
participant: 6736
|
20
|
+
}
|
21
|
+
ENTRY_02 = {
|
22
|
+
id: 6192,
|
23
|
+
game_id: 3922,
|
24
|
+
metadata: {
|
25
|
+
title: 'My entry 2'
|
26
|
+
},
|
27
|
+
state: 4281,
|
28
|
+
participant: 6736,
|
29
|
+
points: 222,
|
30
|
+
rank: 2
|
31
|
+
}
|
32
|
+
ENTRY_03 = {
|
33
|
+
id: 6193,
|
34
|
+
game_id: 3922,
|
35
|
+
metadata: {
|
36
|
+
title: 'My entry 3'
|
37
|
+
},
|
38
|
+
state: 4281,
|
39
|
+
participant: 6736,
|
40
|
+
points: 333,
|
41
|
+
rank: 1
|
42
|
+
}
|
43
|
+
ENTRY_TRANSITIONS = {
|
44
|
+
transitions: [
|
45
|
+
{ from: 555, to: 666 },
|
46
|
+
{ from: 666, to: 777 }
|
47
|
+
]
|
48
|
+
}
|
49
|
+
ENTRY_INDEX = {
|
50
|
+
results: [ENTRY_01, ENTRY_02, ENTRY_03],
|
51
|
+
paging: {
|
52
|
+
min_id: ENTRY_01[:id],
|
53
|
+
max_id: ENTRY_03[:id],
|
54
|
+
min_id: ENTRY_01[:id] - 1
|
55
|
+
}
|
56
|
+
}
|
57
|
+
ENTRY_LEADERBOARD = {
|
58
|
+
results: [ENTRY_01, ENTRY_02, ENTRY_03],
|
59
|
+
paging: {
|
60
|
+
top_rank: ENTRY_03[:rank],
|
61
|
+
bottom_rank: ENTRY_01[:rank],
|
62
|
+
next_top_rank: ENTRY_01[:rank] + 1
|
63
|
+
}
|
64
|
+
}
|