cs 0.1.0beta3 → 0.1.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.
- checksums.yaml +7 -0
- data/.travis.yml +8 -0
- data/Gemfile +22 -6
- data/README.md +15 -4
- data/cs.gemspec +7 -7
- data/lib/{commonsense-ruby-lib.rb → cs.rb} +80 -31
- data/lib/{commonsense-ruby-lib → cs}/auth/http.rb +52 -33
- data/lib/{commonsense-ruby-lib → cs}/auth/oauth.rb +28 -28
- data/lib/cs/collection.rb +7 -0
- data/lib/cs/collection/sensor_data_collection.rb +61 -0
- data/lib/{commonsense-ruby-lib → cs}/end_point.rb +36 -24
- data/lib/cs/end_point/group.rb +26 -0
- data/lib/cs/end_point/notification.rb +16 -0
- data/lib/{commonsense-ruby-lib → cs}/end_point/sensor.rb +22 -6
- data/lib/{commonsense-ruby-lib → cs}/end_point/sensor_data.rb +17 -6
- data/lib/cs/end_point/trigger.rb +16 -0
- data/lib/{commonsense-ruby-lib → cs}/end_point/user.rb +8 -4
- data/lib/{commonsense-ruby-lib → cs}/error.rb +7 -1
- data/lib/cs/parameter_processor.rb +99 -0
- data/lib/cs/relation.rb +244 -0
- data/lib/cs/relation/group_relation.rb +24 -0
- data/lib/cs/relation/notification_relation.rb +20 -0
- data/lib/{commonsense-ruby-lib → cs}/relation/sensor_data_relation.rb +7 -52
- data/lib/{commonsense-ruby-lib → cs}/relation/sensor_relation.rb +28 -55
- data/lib/cs/relation/trigger_relation.rb +21 -0
- data/lib/cs/relation/user_relation.rb +20 -0
- data/lib/{commonsense-ruby-lib → cs}/serializer.rb +1 -1
- data/lib/cs/session.rb +170 -0
- data/lib/cs/time.rb +45 -0
- data/lib/cs/version.rb +3 -0
- data/spec/features/sensor_management_spec.rb +146 -45
- data/spec/features/user_management_spec.rb +94 -22
- data/spec/lib/cs/collection/sensor_data_collection_spec.rb +27 -0
- data/spec/lib/cs/end_point/group_spec.rb +120 -0
- data/spec/lib/cs/end_point/sensor_data_spec.rb +110 -0
- data/spec/lib/{commonsense-ruby-lib → cs}/end_point/sensor_spec.rb +6 -6
- data/spec/lib/{commonsense-ruby-lib → cs}/end_point/user_spec.rb +14 -7
- data/spec/lib/{commonsense-ruby-lib → cs}/end_point_spec.rb +25 -12
- data/spec/lib/cs/relation/group_relation_spec.rb +103 -0
- data/spec/lib/cs/relation/sensor_data_relation_spec.rb +184 -0
- data/spec/lib/cs/relation/sensor_relation_spec.rb +192 -0
- data/spec/lib/cs/relation/user_relation_spec.rb +81 -0
- data/spec/lib/cs/relation_spec.rb +151 -0
- data/spec/lib/cs/session_spec.rb +91 -0
- data/spec/lib/cs/time_spec.rb +71 -0
- data/spec/lib/cs_spec.rb +85 -0
- data/spec/spec_helper.rb +6 -26
- metadata +69 -86
- data/lib/commonsense-ruby-lib/end_point/group.rb +0 -28
- data/lib/commonsense-ruby-lib/relation.rb +0 -233
- data/lib/commonsense-ruby-lib/session.rb +0 -105
- data/lib/commonsense-ruby-lib/version.rb +0 -3
- data/spec/lib/commonsense-ruby-lib/end_point/sensor_data_spec.rb +0 -68
- data/spec/lib/commonsense-ruby-lib/relation/sensor_data_relation_spec.rb +0 -444
- data/spec/lib/commonsense-ruby-lib/relation/sensor_relation_spec.rb +0 -165
- data/spec/lib/commonsense-ruby-lib/session_spec.rb +0 -43
- data/spec/lib/commonsense-ruby-lib_spec.rb +0 -51
@@ -1,15 +1,15 @@
|
|
1
1
|
require 'digest/md5'
|
2
2
|
|
3
|
-
module
|
3
|
+
module CS
|
4
4
|
module EndPoint
|
5
5
|
class User
|
6
6
|
include EndPoint
|
7
7
|
|
8
|
-
resources
|
9
|
-
resource
|
8
|
+
resources "users"
|
9
|
+
resource "user"
|
10
10
|
|
11
11
|
attribute :email, :username, :name, :surname, :address, :zipcode,
|
12
|
-
:country, :mobile, :
|
12
|
+
:country, :mobile, :UUID, :openid, :password
|
13
13
|
|
14
14
|
def initialize(hash={})
|
15
15
|
if hash[:password]
|
@@ -38,6 +38,10 @@ module CommonSense
|
|
38
38
|
current_user
|
39
39
|
end
|
40
40
|
|
41
|
+
def save!(options={})
|
42
|
+
raise Error::ClientError, "No session found. use Client#new_user instead" unless @session
|
43
|
+
super(options)
|
44
|
+
end
|
41
45
|
|
42
46
|
# get groups that this users belongs to
|
43
47
|
def groups
|
@@ -1,4 +1,4 @@
|
|
1
|
-
module
|
1
|
+
module CS
|
2
2
|
module Error
|
3
3
|
class Error < ::RuntimeError
|
4
4
|
def initialize(message = "")
|
@@ -6,6 +6,12 @@ module CommonSense
|
|
6
6
|
end
|
7
7
|
end
|
8
8
|
|
9
|
+
class ClientError < Error
|
10
|
+
def initialize(message = "Invalid uses of the library : #{self.class}")
|
11
|
+
super(message)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
9
15
|
class ResourceIdError < Error
|
10
16
|
def initialize(message = "No id found for Resrouce: #{self.class}")
|
11
17
|
super(message)
|
@@ -0,0 +1,99 @@
|
|
1
|
+
module CS
|
2
|
+
module ParameterProcessor
|
3
|
+
def process_alias!(params)
|
4
|
+
return if self.class.parameters_alias.nil?
|
5
|
+
|
6
|
+
aliases = params.select { |param| self.class.parameters_alias.include?(param) }
|
7
|
+
aliases.each do |alias_to, value|
|
8
|
+
alias_for = self.class.parameters_alias[alias_to]
|
9
|
+
params[alias_for] = value
|
10
|
+
params.delete(alias_to)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
def process_valid_values(name, value, param_option)
|
15
|
+
return value unless param_option[:valid_values]
|
16
|
+
|
17
|
+
if param_option[:valid_values].include?(value)
|
18
|
+
value
|
19
|
+
elsif !value.nil?
|
20
|
+
raise ArgumentError, "Invalid value for parameter '#{name}'"
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
def process_default_value(name, value, param_option)
|
25
|
+
value.nil? ? param_option[:default] : value
|
26
|
+
end
|
27
|
+
|
28
|
+
|
29
|
+
def process_param(name, value, param_option)
|
30
|
+
retval = value
|
31
|
+
|
32
|
+
# this should be refactored to it's own classes
|
33
|
+
retval = process_param_integer(name, value, param_option) if param_option[:type] == Integer
|
34
|
+
retval = process_param_boolean(name, value, param_option) if param_option[:type] == Boolean
|
35
|
+
retval = process_param_string(name, value, param_option) if param_option[:type] == String
|
36
|
+
retval = process_param_time(name, value, param_option) if param_option[:type] == Time
|
37
|
+
retval
|
38
|
+
end
|
39
|
+
|
40
|
+
def process_param_integer(name, value, param_option)
|
41
|
+
if value.kind_of?(Integer)
|
42
|
+
retval = value
|
43
|
+
retval = process_valid_values(name, value, param_option) if param_option[:valid_values]
|
44
|
+
maximum = param_option[:maximum]
|
45
|
+
retval = maximum if maximum && retval > maximum
|
46
|
+
end
|
47
|
+
|
48
|
+
retval = process_default_value(name, retval, param_option)
|
49
|
+
|
50
|
+
if !value.nil? && !value.kind_of?(Integer)
|
51
|
+
raise ArgumentError, "Received non Integer value for parameter '#{name}'"
|
52
|
+
end
|
53
|
+
|
54
|
+
retval
|
55
|
+
end
|
56
|
+
|
57
|
+
def process_param_boolean(name, value, param_option)
|
58
|
+
retval = nil
|
59
|
+
|
60
|
+
if value.nil?
|
61
|
+
retval = param_option[:default] ? param_option[:default] : nil
|
62
|
+
elsif [0, "0", false, "false"].include?(value)
|
63
|
+
retval = 0
|
64
|
+
else
|
65
|
+
retval = 1
|
66
|
+
end
|
67
|
+
|
68
|
+
retval
|
69
|
+
end
|
70
|
+
|
71
|
+
def process_param_string(name, value, param_option)
|
72
|
+
retval = value
|
73
|
+
retval = process_valid_values(name, value, param_option) if param_option[:valid_values]
|
74
|
+
retval = process_default_value(name, retval, param_option)
|
75
|
+
|
76
|
+
retval
|
77
|
+
end
|
78
|
+
|
79
|
+
# This method prosess assignment for properties with datatype Time.
|
80
|
+
# There are 3 type that is valid for this properties:
|
81
|
+
#
|
82
|
+
# * **Time**
|
83
|
+
# * **Numeric**. It will convert this to ruby {Time}
|
84
|
+
# * **Obejct that respond to #to_time** and return ruby {Time}
|
85
|
+
#
|
86
|
+
def process_param_time(name, value, param_option)
|
87
|
+
retval = value
|
88
|
+
|
89
|
+
if !value.nil?
|
90
|
+
retval = CS::Time.new(value)
|
91
|
+
end
|
92
|
+
|
93
|
+
retval = process_default_value(name, retval, param_option)
|
94
|
+
retval = process_valid_values(name, value, param_option) if param_option[:valid_values]
|
95
|
+
|
96
|
+
retval
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
data/lib/cs/relation.rb
ADDED
@@ -0,0 +1,244 @@
|
|
1
|
+
module CS
|
2
|
+
module Boolean; end
|
3
|
+
module Relation
|
4
|
+
|
5
|
+
def check_session!
|
6
|
+
raise Error::SessionEmptyError unless @session
|
7
|
+
end
|
8
|
+
|
9
|
+
def get_url
|
10
|
+
raise Error::NotImplementedError, "the class #{self.class} does not respond to 'get_url' "
|
11
|
+
end
|
12
|
+
|
13
|
+
def initialize(session=nil)
|
14
|
+
@session = session
|
15
|
+
end
|
16
|
+
|
17
|
+
# Create a new Endpoint object.
|
18
|
+
#
|
19
|
+
# example:
|
20
|
+
#
|
21
|
+
# sensor = client.sensors.build
|
22
|
+
def build(attributes={})
|
23
|
+
resource = resource_class.new(attributes)
|
24
|
+
resource.session = self.session
|
25
|
+
resource
|
26
|
+
end
|
27
|
+
|
28
|
+
def get_data!(params={})
|
29
|
+
check_session!
|
30
|
+
options = get_options(params)
|
31
|
+
session.get(get_url, options)
|
32
|
+
end
|
33
|
+
|
34
|
+
def limit(num)
|
35
|
+
@limit = num
|
36
|
+
return self
|
37
|
+
end
|
38
|
+
|
39
|
+
def parameter(name)
|
40
|
+
self.instance_variable_get("@#{name}")
|
41
|
+
end
|
42
|
+
|
43
|
+
def parameters
|
44
|
+
self.class.parameters
|
45
|
+
end
|
46
|
+
|
47
|
+
def get_data(params={})
|
48
|
+
get_data!(params)
|
49
|
+
end
|
50
|
+
|
51
|
+
def all
|
52
|
+
self.to_a
|
53
|
+
end
|
54
|
+
|
55
|
+
def count
|
56
|
+
check_session!
|
57
|
+
resource = get_single_resource
|
58
|
+
resource["total"] if resource
|
59
|
+
end
|
60
|
+
|
61
|
+
def find_or_new(attribute)
|
62
|
+
check_session!
|
63
|
+
|
64
|
+
self.each do |resource|
|
65
|
+
found = true
|
66
|
+
attribute.each do |key, value|
|
67
|
+
if resource.parameter(key) != value
|
68
|
+
found = false
|
69
|
+
break
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
return resource if found
|
74
|
+
end
|
75
|
+
|
76
|
+
resource = resource_class.new(attribute)
|
77
|
+
resource.session = self.session
|
78
|
+
resource
|
79
|
+
end
|
80
|
+
|
81
|
+
def find_or_create!(attribute)
|
82
|
+
resource = find_or_new(attribute)
|
83
|
+
resource.save! if resource.id.nil?
|
84
|
+
resource
|
85
|
+
end
|
86
|
+
|
87
|
+
def find_or_create(attribute)
|
88
|
+
find_or_create!(attribute) rescue nil
|
89
|
+
end
|
90
|
+
|
91
|
+
def first
|
92
|
+
resource = get_single_resource
|
93
|
+
parse_single_resource(resource)
|
94
|
+
end
|
95
|
+
|
96
|
+
def last
|
97
|
+
resource = get_single_resource(page: count - 1)
|
98
|
+
parse_single_resource(resource)
|
99
|
+
end
|
100
|
+
|
101
|
+
def inspect
|
102
|
+
entries = to_a.take(11).map!(&:inspect)
|
103
|
+
entries[10] = '...' if entries.size == 11
|
104
|
+
|
105
|
+
"#<#{self.class.name} [#{entries.join(", \n")}]>"
|
106
|
+
end
|
107
|
+
|
108
|
+
def get_options(input={})
|
109
|
+
options = {}
|
110
|
+
|
111
|
+
self.class.parameters.each do |name, param_option|
|
112
|
+
value = self.parameter(name) # get value from object
|
113
|
+
value = input[name] if input.has_key?(name) # override
|
114
|
+
|
115
|
+
value = process_param(name, value, param_option)
|
116
|
+
value = value.to_f if value.kind_of?(Time)
|
117
|
+
|
118
|
+
options[name] = value if value
|
119
|
+
end
|
120
|
+
|
121
|
+
options
|
122
|
+
end
|
123
|
+
|
124
|
+
def where(params={})
|
125
|
+
process_alias!(params)
|
126
|
+
params.keep_if {|k| self.class.parameters[k]}
|
127
|
+
|
128
|
+
params.each do |name,value|
|
129
|
+
param_option = self.class.parameters[name]
|
130
|
+
|
131
|
+
value = process_param(name, value, param_option)
|
132
|
+
self.send("#{name}=", value)
|
133
|
+
end
|
134
|
+
|
135
|
+
self
|
136
|
+
end
|
137
|
+
|
138
|
+
def each_batch(params={}, &block)
|
139
|
+
check_session!
|
140
|
+
options = get_options(params)
|
141
|
+
|
142
|
+
self.page ||= 0;
|
143
|
+
|
144
|
+
begin
|
145
|
+
options[:page] = self.page
|
146
|
+
data = get_data(options)
|
147
|
+
|
148
|
+
data = data[resource_class.resources_name] unless data.nil?
|
149
|
+
if !data.nil? && !data.empty?
|
150
|
+
yield data
|
151
|
+
self.page += 1
|
152
|
+
end
|
153
|
+
end while data && data.size == self.per_page
|
154
|
+
end
|
155
|
+
|
156
|
+
def each(&block)
|
157
|
+
counter = 0
|
158
|
+
self.each_batch do |data|
|
159
|
+
data.each do |data_point|
|
160
|
+
resource = resource_class.new(data_point)
|
161
|
+
resource.session = session
|
162
|
+
yield resource
|
163
|
+
counter += 1
|
164
|
+
|
165
|
+
return if @limit && @limit == counter
|
166
|
+
end
|
167
|
+
end
|
168
|
+
end
|
169
|
+
|
170
|
+
module ClassMethod
|
171
|
+
def parameter(name, type, *args)
|
172
|
+
attr_accessor name
|
173
|
+
self.parameters ||= {}
|
174
|
+
|
175
|
+
param = {type: type}
|
176
|
+
param.merge!(args[0]) unless args.empty?
|
177
|
+
|
178
|
+
self.class_eval %{
|
179
|
+
def #{name}
|
180
|
+
if @#{name}.nil? && (default = self.class.parameters[:#{name}][:default])
|
181
|
+
@#{name} = default
|
182
|
+
end
|
183
|
+
|
184
|
+
@#{name}
|
185
|
+
end
|
186
|
+
}
|
187
|
+
|
188
|
+
self.parameters[name] = param
|
189
|
+
end
|
190
|
+
|
191
|
+
def parameter_alias(name, name_alias)
|
192
|
+
attr_accessor name
|
193
|
+
self.parameters_alias ||= {}
|
194
|
+
self.parameters_alias[name] = name_alias
|
195
|
+
end
|
196
|
+
|
197
|
+
def parameters_alias=(parameters_alias)
|
198
|
+
@parameters_alias = parameters_alias
|
199
|
+
end
|
200
|
+
|
201
|
+
def parameters_alias
|
202
|
+
@parameters_alias
|
203
|
+
end
|
204
|
+
|
205
|
+
def parameters=(parameters)
|
206
|
+
@parameters = parameters
|
207
|
+
end
|
208
|
+
|
209
|
+
def parameters
|
210
|
+
@parameters
|
211
|
+
end
|
212
|
+
end
|
213
|
+
|
214
|
+
protected
|
215
|
+
def self.included(base)
|
216
|
+
base.send(:include, Enumerable)
|
217
|
+
base.send(:include, ParameterProcessor)
|
218
|
+
base.extend(ClassMethod)
|
219
|
+
base.class_eval do
|
220
|
+
attr_accessor :session
|
221
|
+
end
|
222
|
+
end
|
223
|
+
|
224
|
+
def resource_class
|
225
|
+
raise Error::NotImplementedError, "resource_class is not implemented for class : #{self.class}"
|
226
|
+
end
|
227
|
+
|
228
|
+
def parse_single_resource(data)
|
229
|
+
resources = data[resource_class.resources_name]
|
230
|
+
if !resources.empty?
|
231
|
+
resource = resource_class.new(resources[0])
|
232
|
+
resource.session = self.session
|
233
|
+
|
234
|
+
return resource
|
235
|
+
end
|
236
|
+
end
|
237
|
+
|
238
|
+
def get_single_resource(params={})
|
239
|
+
options = get_options.merge!({ page: 0, per_page: 1 })
|
240
|
+
options.merge!(params)
|
241
|
+
get_data(options)
|
242
|
+
end
|
243
|
+
end
|
244
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
module CS
|
2
|
+
module Relation
|
3
|
+
class GroupRelation
|
4
|
+
include Relation
|
5
|
+
|
6
|
+
parameter :page, Integer, default: 0, required: true
|
7
|
+
parameter :per_page, Integer, default: 1000, required: true, maximum: 1000
|
8
|
+
parameter :public, Boolean
|
9
|
+
parameter :total, Boolean
|
10
|
+
parameter :sort, String, valid_values: ["ASC", "DESC"]
|
11
|
+
parameter :sort_field, String, valid_values: ["id", "username", "email", "public", "description", "name"]
|
12
|
+
|
13
|
+
|
14
|
+
private
|
15
|
+
def resource_class
|
16
|
+
EndPoint::Group
|
17
|
+
end
|
18
|
+
|
19
|
+
def get_url
|
20
|
+
"/groups.json"
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module CS
|
2
|
+
module Relation
|
3
|
+
class NotificationRelation
|
4
|
+
include Relation
|
5
|
+
|
6
|
+
parameter :page, Integer, default: 0, required: true
|
7
|
+
parameter :per_page, Integer, default: 1000, required: true, maximum: 1000
|
8
|
+
parameter :total, Boolean
|
9
|
+
|
10
|
+
private
|
11
|
+
def resource_class
|
12
|
+
EndPoint::Notification
|
13
|
+
end
|
14
|
+
|
15
|
+
def get_url
|
16
|
+
"/notifications.json"
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|