cybercoach 0.2.0 → 0.3.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +45 -0
- data/.rspec +2 -0
- data/CHANGELOG.md +8 -0
- data/Gemfile +23 -0
- data/LICENSE.txt +22 -0
- data/README.md +31 -0
- data/Rakefile +2 -0
- data/cybercoach.gemspec +27 -0
- data/lib/cybercoach/abstract_resource.rb +162 -0
- data/lib/cybercoach/entry.rb +166 -0
- data/lib/cybercoach/format_not_supported_error.rb +7 -0
- data/lib/cybercoach/http_error.rb +27 -0
- data/lib/cybercoach/pageable.rb +38 -0
- data/lib/cybercoach/partnership.rb +151 -0
- data/lib/cybercoach/post_createable.rb +49 -0
- data/lib/cybercoach/privacy_level.rb +21 -0
- data/lib/cybercoach/put_createable.rb +48 -0
- data/lib/cybercoach/resource.rb +94 -0
- data/lib/cybercoach/resource_page.rb +191 -0
- data/lib/cybercoach/settings.rb +16 -0
- data/lib/cybercoach/sport.rb +104 -0
- data/lib/cybercoach/subclass_responsibility_error.rb +7 -0
- data/lib/cybercoach/subscription.rb +145 -0
- data/lib/cybercoach/user.rb +159 -0
- data/lib/cybercoach/version.rb +10 -0
- data/lib/cybercoach.rb +19 -0
- data/spec/lib/cybercoach/entry_spec.rb +95 -0
- data/spec/lib/cybercoach/partnership_spec.rb +79 -0
- data/spec/lib/cybercoach/privacy_level_spec.rb +15 -0
- data/spec/lib/cybercoach/resource_helper.rb +11 -0
- data/spec/lib/cybercoach/resource_page_spec.rb +44 -0
- data/spec/lib/cybercoach/settings_spec.rb +10 -0
- data/spec/lib/cybercoach/sport_spec.rb +29 -0
- data/spec/lib/cybercoach/subscription_spec.rb +129 -0
- data/spec/lib/cybercoach/user_helper.rb +22 -0
- data/spec/lib/cybercoach/user_spec.rb +82 -0
- data/spec/lib/cybercoach_helper.rb +2 -0
- data/spec/lib/integration_spec.rb +56 -0
- data/spec/spec_helper.rb +19 -0
- metadata +56 -4
@@ -0,0 +1,151 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# A Partnership consists of two Users, which participate in different Sport
|
4
|
+
# with Subscriptions, to which Entries are submitted.
|
5
|
+
#
|
6
|
+
class Partnership < Resource
|
7
|
+
#
|
8
|
+
# It is pageable.
|
9
|
+
#
|
10
|
+
include Pageable
|
11
|
+
|
12
|
+
#
|
13
|
+
# It is creatable by PUT.
|
14
|
+
#
|
15
|
+
include PutCreateable
|
16
|
+
|
17
|
+
#
|
18
|
+
# :attr: proposer
|
19
|
+
# The User who proposed it.
|
20
|
+
#
|
21
|
+
|
22
|
+
#
|
23
|
+
# :attr: proposed
|
24
|
+
# The User it is proposed to.
|
25
|
+
#
|
26
|
+
|
27
|
+
#
|
28
|
+
# :attr: subscriptions
|
29
|
+
# The Subscriptions.
|
30
|
+
#
|
31
|
+
|
32
|
+
#
|
33
|
+
# :attr: confirmed_by_proposer
|
34
|
+
# True if the proposing User has confirmed it, false otherwise.
|
35
|
+
#
|
36
|
+
|
37
|
+
#
|
38
|
+
# :attr: confirmed_by_proposed
|
39
|
+
# True if the proposed User has confirmed it, false otherwise.
|
40
|
+
#
|
41
|
+
|
42
|
+
#
|
43
|
+
# :attr: privacy_level
|
44
|
+
# The privacy level, see PrivacyLevel constants.
|
45
|
+
#
|
46
|
+
|
47
|
+
attr_accessor :proposer,
|
48
|
+
:proposed,
|
49
|
+
:subscriptions,
|
50
|
+
:confirmed_by_proposer,
|
51
|
+
:confirmed_by_proposed,
|
52
|
+
:privacy_level
|
53
|
+
|
54
|
+
#
|
55
|
+
# :category: Serialization
|
56
|
+
#
|
57
|
+
# Creates itself from a serializable representation, which only contains
|
58
|
+
# simple data types.
|
59
|
+
# serializable:: A hash with the keys:
|
60
|
+
# * uri:: The URI.
|
61
|
+
# * id:: The identifier.
|
62
|
+
# * user1:: A User serializable of the proposer.
|
63
|
+
# * user2:: A User serializable of the proposed.
|
64
|
+
# * subscriptions:: Subscription serializables.
|
65
|
+
# * userconfirmed1:: True if the proposing User has confirmed it, false otherwise.
|
66
|
+
# * userconfirmed2:: True if the proposed User has confirmed it, false otherwise.
|
67
|
+
# * publicvisible:: The privacy level, see PrivacyLevel constants.
|
68
|
+
#
|
69
|
+
def from_serializable(serializable)
|
70
|
+
super(serializable)
|
71
|
+
@proposer = nil
|
72
|
+
unless serializable['user1'].nil?
|
73
|
+
@proposer = User.new
|
74
|
+
@proposer.from_serializable(serializable['user1'])
|
75
|
+
end
|
76
|
+
@proposed = nil
|
77
|
+
unless serializable['user2'].nil?
|
78
|
+
@proposed = User.new
|
79
|
+
@proposed.from_serializable(serializable['user2'])
|
80
|
+
end
|
81
|
+
@subscriptions = []
|
82
|
+
unless serializable['subscriptions'].nil?
|
83
|
+
@subscriptions = serializable['subscriptions'].map do
|
84
|
+
|subscription_serializable|
|
85
|
+
subscription = Subscription.new
|
86
|
+
subscription.from_serializable(subscription_serializable)
|
87
|
+
subscription
|
88
|
+
end
|
89
|
+
end
|
90
|
+
@confirmed_by_proposer = serializable['userconfirmed1']
|
91
|
+
@confirmed_by_proposed = serializable['userconfirmed2']
|
92
|
+
@privacy_level = serializable['publicvisible']
|
93
|
+
end
|
94
|
+
|
95
|
+
#
|
96
|
+
# :category: Serialization
|
97
|
+
#
|
98
|
+
# Returns a serializable representation, which only contains simple data
|
99
|
+
# types.
|
100
|
+
# The hash has the keys:
|
101
|
+
# * uri:: The URI.
|
102
|
+
# * id:: The identifier.
|
103
|
+
# * user1:: A User serializable of the proposer.
|
104
|
+
# * user2:: A User serializable of the proposed.
|
105
|
+
# * publicvisible:: The privacy level, see PrivacyLevel constants.
|
106
|
+
#
|
107
|
+
def to_serializable
|
108
|
+
serializable = super
|
109
|
+
unless @proposer.nil?
|
110
|
+
serializable['user1'] = @proposer.to_serializable
|
111
|
+
end
|
112
|
+
unless @proposed.nil?
|
113
|
+
serializable['user2'] = @proposed.to_serializable
|
114
|
+
end
|
115
|
+
serializable['publicvisible'] = @privacy_level
|
116
|
+
serializable
|
117
|
+
end
|
118
|
+
|
119
|
+
#
|
120
|
+
# :category: Configuration
|
121
|
+
#
|
122
|
+
# Returns 'partnership'.
|
123
|
+
#
|
124
|
+
def singular_name
|
125
|
+
'partnership'
|
126
|
+
end
|
127
|
+
|
128
|
+
#
|
129
|
+
# :category: Configuration
|
130
|
+
#
|
131
|
+
# Returns 'partnerships'.
|
132
|
+
#
|
133
|
+
def plural_name
|
134
|
+
'partnerships'
|
135
|
+
end
|
136
|
+
|
137
|
+
protected
|
138
|
+
|
139
|
+
#
|
140
|
+
# :category: Invalidation
|
141
|
+
#
|
142
|
+
# Sets the uri to the base uri and the proposer's and proposed's username if
|
143
|
+
# neither of them is nil.
|
144
|
+
#
|
145
|
+
def invalidate_uri
|
146
|
+
unless @proposer.nil? || @proposed.nil?
|
147
|
+
@uri = "#{resource_base_uri}#{@proposer.username};#{@proposed.username}/"
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# Mixin for a resource that gets its URI assigned from the server.
|
4
|
+
# Include it in a class to use it.
|
5
|
+
#
|
6
|
+
module PostCreateable
|
7
|
+
#
|
8
|
+
# Installs class and instance methods in the class it is included in.
|
9
|
+
#
|
10
|
+
def self.included(base)
|
11
|
+
base.extend ClassMethods
|
12
|
+
base.send :include, InstanceMethods
|
13
|
+
end
|
14
|
+
|
15
|
+
#
|
16
|
+
# The class methods to install.
|
17
|
+
#
|
18
|
+
module ClassMethods
|
19
|
+
end
|
20
|
+
|
21
|
+
#
|
22
|
+
# The instance methods to install.
|
23
|
+
#
|
24
|
+
module InstanceMethods
|
25
|
+
#
|
26
|
+
# :category: CRUD
|
27
|
+
#
|
28
|
+
# Creates it.
|
29
|
+
# Gets the URI from the response and reads itself again.
|
30
|
+
# Raises HttpError if the request is unsuccessful.
|
31
|
+
# options:: A hash of options to send with the request.
|
32
|
+
#
|
33
|
+
def create(options = {})
|
34
|
+
invalidate_uri
|
35
|
+
invalidate_options
|
36
|
+
options = @options.merge(options).merge(
|
37
|
+
body: serialize
|
38
|
+
)
|
39
|
+
response = self.class.post(resource_base_uri, options)
|
40
|
+
if response.success?
|
41
|
+
@uri = response.headers['location']
|
42
|
+
read(options)
|
43
|
+
else
|
44
|
+
raise HttpError.new(response.response)
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# The CyberCoach privacy levels.
|
4
|
+
#
|
5
|
+
module PrivacyLevel
|
6
|
+
#
|
7
|
+
# Only the owner of the resource can access its properties.
|
8
|
+
#
|
9
|
+
OWNER = 0
|
10
|
+
|
11
|
+
#
|
12
|
+
# Only registered users can access the resource's properties.
|
13
|
+
#
|
14
|
+
REGISTERED_USER = 1
|
15
|
+
|
16
|
+
#
|
17
|
+
# Everybody can access the resource's properties.
|
18
|
+
#
|
19
|
+
EVERYBODY = 2
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# Mixin for a resource that gets its URI assigned from the client.
|
4
|
+
# Include it in a class to use it.
|
5
|
+
#
|
6
|
+
module PutCreateable
|
7
|
+
#
|
8
|
+
# Installs class and instance methods in the class it is included in.
|
9
|
+
#
|
10
|
+
def self.included(base)
|
11
|
+
base.extend ClassMethods
|
12
|
+
base.send :include, InstanceMethods
|
13
|
+
end
|
14
|
+
|
15
|
+
#
|
16
|
+
# The class methods to install.
|
17
|
+
#
|
18
|
+
module ClassMethods
|
19
|
+
end
|
20
|
+
|
21
|
+
#
|
22
|
+
# The instance methods to install.
|
23
|
+
#
|
24
|
+
module InstanceMethods
|
25
|
+
#
|
26
|
+
# :category: CRUD
|
27
|
+
#
|
28
|
+
# Creates it.
|
29
|
+
# Reads itself from the response.
|
30
|
+
# Raises HttpError if the request is unsuccessful.
|
31
|
+
# options:: A hash of options to send with the request.
|
32
|
+
#
|
33
|
+
def create(options = {})
|
34
|
+
invalidate_uri
|
35
|
+
invalidate_options
|
36
|
+
options = @options.merge(options).merge(
|
37
|
+
body: serialize
|
38
|
+
)
|
39
|
+
response = self.class.put(@uri, options)
|
40
|
+
if response.success?
|
41
|
+
deserialize(response)
|
42
|
+
else
|
43
|
+
raise HttpError.new(response.response)
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
@@ -0,0 +1,94 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# A Resource can be created, read, updated and deleted.
|
4
|
+
#
|
5
|
+
class Resource < AbstractResource
|
6
|
+
#
|
7
|
+
# The identifier.
|
8
|
+
#
|
9
|
+
attr_accessor :id
|
10
|
+
|
11
|
+
#
|
12
|
+
# :category: CRUD
|
13
|
+
#
|
14
|
+
# Creates it.
|
15
|
+
# Must be overridden in a subclass.
|
16
|
+
# May use PutCreateable or PostCreateable.
|
17
|
+
# options:: A hash of options to send with the request.
|
18
|
+
#
|
19
|
+
def create(_options = {})
|
20
|
+
raise SubclassResponsibilityError.new
|
21
|
+
end
|
22
|
+
|
23
|
+
#
|
24
|
+
# :category: CRUD
|
25
|
+
#
|
26
|
+
# Updates it.
|
27
|
+
# Reads itself from the response.
|
28
|
+
# Raises HttpError if the request is unsuccessful.
|
29
|
+
# options:: A hash of options to send with the request.
|
30
|
+
#
|
31
|
+
def update(options = {})
|
32
|
+
invalidate_uri
|
33
|
+
invalidate_options
|
34
|
+
options = @options.merge(options).merge(
|
35
|
+
body: serialize
|
36
|
+
)
|
37
|
+
response = self.class.put(@uri, options)
|
38
|
+
if response.success?
|
39
|
+
deserialize(response)
|
40
|
+
else
|
41
|
+
raise HttpError.new(response.response)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
#
|
46
|
+
# :category: CRUD
|
47
|
+
#
|
48
|
+
# Deletes it.
|
49
|
+
# Reads itself from the response.
|
50
|
+
# Raises HttpError if the request is unsuccessful.
|
51
|
+
# options:: A hash of options to send with the request.
|
52
|
+
#
|
53
|
+
def delete(options = {})
|
54
|
+
invalidate_uri
|
55
|
+
invalidate_options
|
56
|
+
options = @options.merge(options)
|
57
|
+
response = self.class.delete(@uri, options)
|
58
|
+
if response.success?
|
59
|
+
deserialize(response)
|
60
|
+
else
|
61
|
+
raise HttpError.new(response.response)
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
#
|
66
|
+
# :category: Serialization
|
67
|
+
#
|
68
|
+
# Creates itself from a serializable representation, which only contains
|
69
|
+
# simple data types.
|
70
|
+
# serializable:: A hash with the keys:
|
71
|
+
# * uri:: The URI.
|
72
|
+
# * id:: The identifier.
|
73
|
+
#
|
74
|
+
def from_serializable(serializable)
|
75
|
+
super(serializable)
|
76
|
+
@id = serializable['id']
|
77
|
+
end
|
78
|
+
|
79
|
+
#
|
80
|
+
# :category: Serialization
|
81
|
+
#
|
82
|
+
# Returns a serializable representation, which only contains simple data
|
83
|
+
# types.
|
84
|
+
# The hash has the keys:
|
85
|
+
# * uri:: The URI.
|
86
|
+
# * id:: The identifier.
|
87
|
+
#
|
88
|
+
def to_serializable
|
89
|
+
serializable = super
|
90
|
+
serializable['id'] = @id
|
91
|
+
serializable
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
@@ -0,0 +1,191 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# A ResourcePage can be used to navigate through many resources of a type.
|
4
|
+
#
|
5
|
+
class ResourcePage < AbstractResource
|
6
|
+
#
|
7
|
+
# Raised when trying to get the next page from the last page.
|
8
|
+
#
|
9
|
+
class NoNextPageError < StandardError
|
10
|
+
end
|
11
|
+
|
12
|
+
#
|
13
|
+
# Raised when trying to get the previous page from the first page.
|
14
|
+
#
|
15
|
+
class NoPreviousPageError < StandardError
|
16
|
+
end
|
17
|
+
|
18
|
+
#
|
19
|
+
# :attr: start
|
20
|
+
# The start index.
|
21
|
+
#
|
22
|
+
|
23
|
+
#
|
24
|
+
# :attr: end
|
25
|
+
# The end index.
|
26
|
+
#
|
27
|
+
|
28
|
+
#
|
29
|
+
# :attr: size
|
30
|
+
# The size.
|
31
|
+
#
|
32
|
+
|
33
|
+
#
|
34
|
+
# :attr: available
|
35
|
+
# The resources available.
|
36
|
+
#
|
37
|
+
|
38
|
+
#
|
39
|
+
# :attr: type
|
40
|
+
# The class of the resource to page.
|
41
|
+
#
|
42
|
+
|
43
|
+
#
|
44
|
+
# :attr: resources
|
45
|
+
# The resources.
|
46
|
+
#
|
47
|
+
|
48
|
+
attr_accessor :start, :end, :size, :available, :type, :resources
|
49
|
+
|
50
|
+
#
|
51
|
+
# Create a ResourcePage of the specified type.
|
52
|
+
# type:: The class of resource to page.
|
53
|
+
#
|
54
|
+
def initialize(type)
|
55
|
+
super()
|
56
|
+
@type = type
|
57
|
+
end
|
58
|
+
|
59
|
+
#
|
60
|
+
# :category: CRUD
|
61
|
+
#
|
62
|
+
# Returns the next page.
|
63
|
+
# Raises NoNextPageError if the is none.
|
64
|
+
# options:: A hash of options to send with the request.
|
65
|
+
#
|
66
|
+
def next(options = {})
|
67
|
+
if @next.nil?
|
68
|
+
raise NoNextPageError.new
|
69
|
+
end
|
70
|
+
invalidate_options
|
71
|
+
options = @options.merge(options)
|
72
|
+
response = self.class.get(@next['href'], options)
|
73
|
+
if response.success?
|
74
|
+
page = self.class.new(@type)
|
75
|
+
page.deserialize(response)
|
76
|
+
page
|
77
|
+
else
|
78
|
+
raise HttpError.new(response.response)
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
#
|
83
|
+
# :category: CRUD
|
84
|
+
#
|
85
|
+
# Returns the previous page.
|
86
|
+
# Raises NoPreviousPageError if the is none.
|
87
|
+
# options:: A hash of options to send with the request.
|
88
|
+
#
|
89
|
+
def previous(options = {})
|
90
|
+
if @previous.nil?
|
91
|
+
raise NoPreviousPageError.new
|
92
|
+
end
|
93
|
+
invalidate_options
|
94
|
+
options = @options.merge(options)
|
95
|
+
response = self.class.get(@previous['href'], options)
|
96
|
+
if response.success?
|
97
|
+
page = self.class.new(@type)
|
98
|
+
page.deserialize(response)
|
99
|
+
page
|
100
|
+
else
|
101
|
+
raise HttpError.new(response.response)
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
#
|
106
|
+
# :category: Serialization
|
107
|
+
#
|
108
|
+
# Creates itself from a serializable representation, which only contains
|
109
|
+
# simple data types.
|
110
|
+
# serializable:: A hash with the keys:
|
111
|
+
# * uri:: The URI.
|
112
|
+
# * start:: The start index.
|
113
|
+
# * end:: The end index.
|
114
|
+
# * size:: The size.
|
115
|
+
# * available:: The resources available.
|
116
|
+
# * links:: Links as hashes with the keys:
|
117
|
+
# * description:: May be 'next' or 'previous'.
|
118
|
+
# * href:: The URI of the referenced page.
|
119
|
+
# * @plural_name:: Items mapped to the plural name of the @type.
|
120
|
+
#
|
121
|
+
def from_serializable(serializable)
|
122
|
+
super(serializable)
|
123
|
+
@start = serializable['start']
|
124
|
+
@end = serializable['end']
|
125
|
+
@size = serializable['size']
|
126
|
+
@available = serializable['available']
|
127
|
+
if serializable['links'].nil?
|
128
|
+
@next = nil
|
129
|
+
@previous = nil
|
130
|
+
else
|
131
|
+
@next = serializable['links'].find { |link| link['description'] == 'next' }
|
132
|
+
@previous = serializable['links'].find { |link| link['description'] == 'previous' }
|
133
|
+
end
|
134
|
+
@resources = serializable[plural_name].map do |resource_serializable|
|
135
|
+
resource = @type.new
|
136
|
+
resource.from_serializable(resource_serializable)
|
137
|
+
resource
|
138
|
+
end
|
139
|
+
end
|
140
|
+
|
141
|
+
#
|
142
|
+
# :category: Configuration
|
143
|
+
#
|
144
|
+
# Return the singular name of the type.
|
145
|
+
#
|
146
|
+
def singular_name
|
147
|
+
@type.new.singular_name
|
148
|
+
end
|
149
|
+
|
150
|
+
#
|
151
|
+
# :category: Configuration
|
152
|
+
#
|
153
|
+
# Return the plural name of the type.
|
154
|
+
#
|
155
|
+
def plural_name
|
156
|
+
@type.new.plural_name
|
157
|
+
end
|
158
|
+
|
159
|
+
#
|
160
|
+
# :category: Configuration
|
161
|
+
#
|
162
|
+
# Return the resource's base URI of the type.
|
163
|
+
#
|
164
|
+
def resource_base_uri
|
165
|
+
@type.new.resource_base_uri
|
166
|
+
end
|
167
|
+
|
168
|
+
protected
|
169
|
+
|
170
|
+
#
|
171
|
+
# :category: Invalidation
|
172
|
+
#
|
173
|
+
# Sets the start and size attributes as query parameters.
|
174
|
+
#
|
175
|
+
def invalidate_options
|
176
|
+
@options[:query] = {
|
177
|
+
start: @start,
|
178
|
+
size: @size
|
179
|
+
}
|
180
|
+
end
|
181
|
+
|
182
|
+
#
|
183
|
+
# :category: Invalidation
|
184
|
+
#
|
185
|
+
# Sets the URI to the types' base URI.
|
186
|
+
#
|
187
|
+
def invalidate_uri
|
188
|
+
@uri = resource_base_uri
|
189
|
+
end
|
190
|
+
end
|
191
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# Settings to access CyberCoach.
|
4
|
+
#
|
5
|
+
class Settings
|
6
|
+
#
|
7
|
+
# The URI to the server.
|
8
|
+
#
|
9
|
+
SERVER_URI = 'diufvm31.unifr.ch:8090'
|
10
|
+
|
11
|
+
#
|
12
|
+
# The URI to the resources, relative to the server URI.
|
13
|
+
#
|
14
|
+
BASE_URI = '/CyberCoachServer/resources'
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,104 @@
|
|
1
|
+
module CyberCoach
|
2
|
+
#
|
3
|
+
# A Sport has Subscriptions to which Entries are submitted.
|
4
|
+
#
|
5
|
+
class Sport < Resource
|
6
|
+
#
|
7
|
+
# It is pageable.
|
8
|
+
#
|
9
|
+
include Pageable
|
10
|
+
|
11
|
+
#
|
12
|
+
# :attr: name
|
13
|
+
# The name.
|
14
|
+
#
|
15
|
+
|
16
|
+
#
|
17
|
+
# :attr: description
|
18
|
+
# The description.
|
19
|
+
#
|
20
|
+
|
21
|
+
#
|
22
|
+
# :attr: subscriptions
|
23
|
+
# The Subscriptions to it.
|
24
|
+
#
|
25
|
+
|
26
|
+
attr_accessor :name, :description, :subscriptions
|
27
|
+
|
28
|
+
#
|
29
|
+
# :category: Serialization
|
30
|
+
#
|
31
|
+
# Creates itself from a serializable representation, which only contains
|
32
|
+
# simple data types.
|
33
|
+
# serializable:: A hash with the keys:
|
34
|
+
# * uri:: The URI.
|
35
|
+
# * id:: The identifier.
|
36
|
+
# * name:: The name.
|
37
|
+
# * description:: The description.
|
38
|
+
# * subscriptions:: Subscription serializables.
|
39
|
+
#
|
40
|
+
def from_serializable(serializable)
|
41
|
+
super(serializable)
|
42
|
+
@name = serializable['name']
|
43
|
+
@description = serializable['description']
|
44
|
+
@subscriptions = []
|
45
|
+
unless serializable['subscriptions'].nil?
|
46
|
+
@subscriptions = serializable['subscriptions'].map do
|
47
|
+
|subscription_serializable|
|
48
|
+
subscription = Subscription.new
|
49
|
+
subscription.from_serializable(subscription_serializable)
|
50
|
+
subscription
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
#
|
56
|
+
# :category: Serialization
|
57
|
+
#
|
58
|
+
# Returns a serializable representation, which only contains simple data
|
59
|
+
# types.
|
60
|
+
# The hash has the keys:
|
61
|
+
# * uri:: The URI.
|
62
|
+
# * id:: The identifier.
|
63
|
+
# * name:: The name.
|
64
|
+
# * description:: The description.
|
65
|
+
#
|
66
|
+
def to_serializable
|
67
|
+
serializable = super
|
68
|
+
serializable['name'] = @name
|
69
|
+
serializable['description'] = @description
|
70
|
+
serializable
|
71
|
+
end
|
72
|
+
|
73
|
+
#
|
74
|
+
# :category: Configuration
|
75
|
+
#
|
76
|
+
# Returns 'sport'.
|
77
|
+
#
|
78
|
+
def singular_name
|
79
|
+
'sport'
|
80
|
+
end
|
81
|
+
|
82
|
+
#
|
83
|
+
# :category: Configuration
|
84
|
+
#
|
85
|
+
# Returns 'sports'.
|
86
|
+
#
|
87
|
+
def plural_name
|
88
|
+
'sports'
|
89
|
+
end
|
90
|
+
|
91
|
+
protected
|
92
|
+
|
93
|
+
#
|
94
|
+
# :category: Invalidation
|
95
|
+
#
|
96
|
+
# Sets the uri to the base uri and the name.
|
97
|
+
#
|
98
|
+
def invalidate_uri
|
99
|
+
unless @name.nil?
|
100
|
+
@uri = "#{resource_base_uri}#{@name}/"
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|