rhosync 2.1.3 → 2.1.6

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG CHANGED
@@ -1,3 +1,12 @@
1
+ ## 2.1.6
2
+ * #13830841 - fixed issue where current_user.login doesn't match @source.user_id
3
+
4
+ ## 2.1.5
5
+ * #13578473 - fixed "undefined method `user_id' for nil:NilClass" error in server.rb
6
+
7
+ ## 2.1.4
8
+ * #13354369 - bug fix "rhosync bootstrap process shouldn't store sources in redis"
9
+
1
10
  ## 2.1.3
2
11
  * #4398193 - ping should only send push messages to unique device pin list
3
12
  * #13022667 - settings.yml doesn't work for setting external Redis instances
@@ -6,7 +6,7 @@ Server.api :list_sources do |params,user|
6
6
  res = []
7
7
  sources.each do |name|
8
8
  s = Source.load(name,{:app_id => APP_NAME,:user_id => '*'})
9
- if s.partition_type and s.partition_type == params[:partition_type]
9
+ if s.partition_type and s.partition_type == params[:partition_type].to_sym
10
10
  res << name
11
11
  end
12
12
  end
@@ -122,8 +122,8 @@ module Rhosync
122
122
  values (?,?,?,?,?,?,?,?,?,?)") do |stmt|
123
123
  sources_refs.each do |source_name,ref|
124
124
  s = ref[:source]
125
- stmt.execute(s.source_id,s.name,s.priority,s.partition_type,
126
- s.sync_type,refs_to_s(ref[:refs]),s.get_value(:metadata),s.schema,s.blob_attribs,s.has_many)
125
+ stmt.execute(s.source_id,s.name,s.priority,s.partition_type.to_s,
126
+ s.sync_type.to_s,refs_to_s(ref[:refs]),s.get_value(:metadata),s.schema,s.blob_attribs,s.has_many)
127
127
  end
128
128
  end
129
129
  end
data/lib/rhosync/model.rb CHANGED
@@ -59,14 +59,15 @@ module Rhosync
59
59
  res
60
60
  end
61
61
 
62
- def update(attribs)
63
- self.class.fields.each do |field|
64
- if field[:name] != 'name' and field[:name] != 'rho__id'
65
- redis.del field_key(field[:name])
66
- end
67
- end
68
- self.class.populate_attributes(self,attribs)
69
- end
62
+ # TODO: not used anymore
63
+ # def update(attribs)
64
+ # self.class.fields.each do |field|
65
+ # if field[:name] != 'name' and field[:name] != 'rho__id'
66
+ # redis.del field_key(field[:name])
67
+ # end
68
+ # end
69
+ # self.class.populate_attributes(self,attribs)
70
+ # end
70
71
 
71
72
  protected
72
73
  def prefix #:nodoc:
@@ -111,8 +112,7 @@ module Rhosync
111
112
  end
112
113
 
113
114
  def load(id, params={})
114
- return unless self.is_exist?(id)
115
- populate_attributes(self.with_key(id),params)
115
+ populate_attributes(self.with_key(id),params) if self.is_exist?(id)
116
116
  end
117
117
 
118
118
  def populate_attributes(obj,attribs)
@@ -88,7 +88,13 @@ module Rhosync
88
88
  end
89
89
 
90
90
  def api_user
91
- request_action == 'get_api_token' ? current_user : ApiToken.load(params[:api_token]).user
91
+ if request_action == 'get_api_token'
92
+ current_user
93
+ else
94
+ u = ApiToken.load(params[:api_token])
95
+ raise "Wrong API token - #{params[:api_token].inspect}" unless u
96
+ u.user
97
+ end
92
98
  end
93
99
 
94
100
  def current_app
@@ -113,7 +119,9 @@ module Rhosync
113
119
  if @client.nil? and params[:client_id]
114
120
  @client = Client.load(params[:client_id].to_s,
115
121
  params[:source_name] ? {:source_name => current_source.name} : {:source_name => '*'})
116
- @client.switch_user(current_user.login) unless @client.user_id == current_user.login
122
+ if @client and current_user and @client.user_id != current_user.login
123
+ @client.switch_user(current_user.login)
124
+ end
117
125
  @client
118
126
  end
119
127
  end
@@ -204,25 +212,33 @@ module Rhosync
204
212
  end
205
213
 
206
214
  post '/application/clientlogin' do
207
- logout
208
- do_login
215
+ catch_all do
216
+ logout
217
+ do_login
218
+ end
209
219
  end
210
220
 
211
221
  get '/application/clientcreate' do
212
- content_type :json
213
- client = Client.create(:user_id => current_user.id,:app_id => current_app.id)
214
- client.update_fields(params)
215
- { "client" => { "client_id" => client.id.to_s } }.merge!(source_config).to_json
222
+ catch_all do
223
+ content_type :json
224
+ client = Client.create(:user_id => current_user.id,:app_id => current_app.id)
225
+ client.update_fields(params)
226
+ { "client" => { "client_id" => client.id.to_s } }.merge!(source_config).to_json
227
+ end
216
228
  end
217
229
 
218
230
  post '/application/clientregister' do
219
- current_client.update_fields(params)
220
- source_config.to_json
231
+ catch_all do
232
+ current_client.update_fields(params)
233
+ source_config.to_json
234
+ end
221
235
  end
222
236
 
223
237
  get '/application/clientreset' do
224
- ClientSync.reset(current_client)
225
- source_config.to_json
238
+ catch_all do
239
+ ClientSync.reset(current_client)
240
+ source_config.to_json
241
+ end
226
242
  end
227
243
 
228
244
  # Member routes
@@ -1,51 +1,117 @@
1
1
  module Rhosync
2
- class Source < Model
3
- field :source_id,:integer
4
- field :name,:string
5
- field :url,:string
6
- field :login,:string
7
- field :password,:string
8
- field :priority,:integer
9
- field :callback_url,:string
10
- field :poll_interval,:integer
11
- field :partition_type,:string
12
- field :sync_type,:string
13
- field :belongs_to,:string
14
- field :has_many,:string
15
- field :queue,:string
16
- field :query_queue,:string
17
- field :cud_queue,:string
18
- attr_accessor :app_id, :user_id
19
- validates_presence_of :name #, :source_id
2
+ class MemoryModel
3
+ @@model_data = {}
4
+ @@string_fields = []
5
+ @@integer_fields = []
6
+ attr_accessor :id
7
+
8
+ class << self
9
+ attr_accessor :validates_presence
10
+
11
+ def define_fields(string_fields = [], integer_fields = [])
12
+ @@string_fields,@@integer_fields = string_fields,integer_fields
13
+ integer_fields.each do |attrib|
14
+ define_method("#{attrib}=") do |value|
15
+ value = (value.nil?) ? nil : value.to_i
16
+ instance_variable_set(:"@#{attrib}", value)
17
+ end
18
+ define_method("#{attrib}") do
19
+ instance_variable_get(:"@#{attrib}")
20
+ end
21
+ end
22
+ string_fields.each do |attrib|
23
+ define_method("#{attrib}=") do |value|
24
+ instance_variable_set(:"@#{attrib}", value)
25
+ end
26
+ define_method("#{attrib}") do
27
+ instance_variable_get(:"@#{attrib}")
28
+ end
29
+ end
30
+ @@string_fields << :id
31
+ @@string_fields << :rho__id
32
+ end
33
+
34
+ def validates_presence_of(*names)
35
+ self.validates_presence ||= []
36
+ names.each do |name|
37
+ self.validates_presence << name
38
+ end
39
+ end
40
+
41
+ def is_exist?(id)
42
+ !@@model_data[id.to_sym].nil?
43
+ end
44
+
45
+ def class_prefix(classname)
46
+ classname.to_s.
47
+ sub(%r{(.*::)}, '').
48
+ gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
49
+ gsub(/([a-z\d])([A-Z])/,'\1_\2').
50
+ downcase
51
+ end
52
+ end
53
+
54
+ def to_array
55
+ res = []
56
+ @@string_fields.each do |field|
57
+ res << {"name" => field, "value" => send(field.to_sym), "type" => "string"}
58
+ end
59
+ @@integer_fields.each do |field|
60
+ res << {"name" => field, "value" => send(field.to_sym), "type" => "integer"}
61
+ end
62
+ res
63
+ end
64
+ end
65
+
66
+ class Source < MemoryModel
67
+ attr_accessor :app_id, :user_id, :rho__id
68
+
69
+ validates_presence_of :name
20
70
 
21
71
  include Document
22
72
  include LockOps
73
+
74
+ # source fields
75
+ define_fields([:name, :url, :login, :password, :callback_url, :partition_type, :sync_type,
76
+ :queue, :query_queue, :cud_queue, :belongs_to, :has_many], [:source_id, :priority, :poll_interval])
77
+
78
+ def initialize(fields)
79
+ fields.each do |name,value|
80
+ arg = "#{name}=".to_sym
81
+ self.send(arg, value) if self.respond_to?(arg)
82
+ end
83
+ end
23
84
 
24
85
  def self.set_defaults(fields)
25
86
  fields[:url] ||= ''
26
87
  fields[:login] ||= ''
27
88
  fields[:password] ||= ''
28
89
  fields[:priority] ||= 3
29
- fields[:partition_type] ||= :user
90
+ fields[:partition_type] = fields[:partition_type] ? fields[:partition_type].to_sym : :user
30
91
  fields[:poll_interval] ||= 300
31
- fields[:sync_type] ||= :incremental
92
+ fields[:sync_type] = fields[:sync_type] ? fields[:sync_type].to_sym : :incremental
93
+ fields[:id] = fields[:name]
94
+ fields[:rho__id] = fields[:name]
32
95
  fields[:belongs_to] = fields[:belongs_to].to_json if fields[:belongs_to]
33
96
  fields[:schema] = fields[:schema].to_json if fields[:schema]
34
97
  end
35
98
 
36
99
  def self.create(fields,params)
37
100
  fields = fields.with_indifferent_access # so we can access hash keys as symbols
38
- # validate_attributes(params)
39
- fields[:id] = fields[:name]
40
101
  set_defaults(fields)
41
- super(fields,params)
102
+ obj = new(fields)
103
+ obj.assign_args(params)
104
+ @@model_data[obj.rho__id.to_sym] = obj
105
+ obj
42
106
  end
43
107
 
44
- def self.load(id,params)
108
+ def self.load(obj_id,params)
45
109
  validate_attributes(params)
46
- super(id,params)
110
+ obj = @@model_data[obj_id.to_sym]
111
+ obj.assign_args(params) if obj
112
+ obj
47
113
  end
48
-
114
+
49
115
  def self.update_associations(sources)
50
116
  params = {:app_id => APP_NAME,:user_id => '*'}
51
117
  sources.each { |source| Source.load(source, params).has_many = nil }
@@ -58,7 +124,8 @@ module Rhosync
58
124
  attrib = entry.keys[0]
59
125
  model = entry[attrib]
60
126
  owner = Source.load(model, params)
61
- owner.has_many = owner.has_many.length > 0 ? owner.has_many+',' : ''
127
+ owner.has_many ||= ''
128
+ owner.has_many = owner.has_many+',' if owner.has_many.length > 0
62
129
  owner.has_many += [source,attrib].join(',')
63
130
  end
64
131
  else
@@ -68,6 +135,16 @@ module Rhosync
68
135
  end
69
136
  end
70
137
 
138
+ def self.delete_all
139
+ @@model_data.each { |k,v| v.delete }
140
+ @@model_data = {}
141
+ end
142
+
143
+ def assign_args(params)
144
+ self.user_id = params[:user_id]
145
+ self.app_id = params[:app_id]
146
+ end
147
+
71
148
  def blob_attribs
72
149
  return '' unless self.schema
73
150
  schema = JSON.parse(self.schema)
@@ -82,7 +159,7 @@ module Rhosync
82
159
  def update(fields)
83
160
  fields = fields.with_indifferent_access # so we can access hash keys as symbols
84
161
  self.class.set_defaults(fields)
85
- super(fields)
162
+ #super(fields)
86
163
  end
87
164
 
88
165
  def clone(src_doctype,dst_doctype)
@@ -91,12 +168,12 @@ module Rhosync
91
168
 
92
169
  # Return the user associated with a source
93
170
  def user
94
- @user ||= User.load(self.user_id)
171
+ @user = User.load(self.user_id)
95
172
  end
96
173
 
97
174
  # Return the app the source belongs to
98
175
  def app
99
- @app ||= App.load(self.app_id)
176
+ @app = App.load(self.app_id)
100
177
  end
101
178
 
102
179
  def schema
@@ -106,8 +183,7 @@ module Rhosync
106
183
  def read_state
107
184
  id = {:app_id => self.app_id,:user_id => user_by_partition,
108
185
  :source_name => self.name}
109
- @read_state ||= ReadState.load(id)
110
- @read_state ||= ReadState.create(id)
186
+ ReadState.load(id) || ReadState.create(id)
111
187
  end
112
188
 
113
189
  def doc_suffix(doctype)
@@ -116,7 +192,7 @@ module Rhosync
116
192
 
117
193
  def delete
118
194
  flash_data('*')
119
- super
195
+ @@model_data.delete(rho__id.to_sym) if rho__id
120
196
  end
121
197
 
122
198
  def partition
@@ -144,7 +220,7 @@ module Rhosync
144
220
  end
145
221
  yield client_id,params if need_refresh
146
222
  end
147
-
223
+
148
224
  private
149
225
  def self.validate_attributes(params)
150
226
  raise ArgumentError.new('Missing required attribute user_id') unless params[:user_id]
@@ -1,3 +1,3 @@
1
1
  module Rhosync
2
- VERSION = '2.1.3'
2
+ VERSION = '2.1.6'
3
3
  end
data/lib/rhosync.rb CHANGED
@@ -91,15 +91,11 @@ module Rhosync
91
91
  app = App.create(:name => app_name)
92
92
  end
93
93
  sources = config[:sources] || []
94
+ Source.delete_all
94
95
  sources.each do |source_name,fields|
95
96
  check_for_schema_field!(fields)
96
- if Source.is_exist?(source_name)
97
- s = Source.load(source_name,{:app_id => app.name,:user_id => '*'})
98
- s.update(fields)
99
- else
100
- fields[:name] = source_name
101
- Source.create(fields,{:app_id => app.name})
102
- end
97
+ fields[:name] = source_name
98
+ Source.create(fields,{:app_id => app.name})
103
99
  unless app.sources.members.include?(source_name)
104
100
  app.sources << source_name
105
101
  end
@@ -5,13 +5,14 @@ describe "RhosyncApiGetSourceParams" do
5
5
 
6
6
  it "should list source attributes" do
7
7
  post "/api/get_source_params", {:api_token => @api_token, :source_id =>"SampleAdapter"}
8
- JSON.parse(last_response.body).should == [
8
+ result = JSON.parse(last_response.body).sort {|x,y| y["name"] <=> x["name"] }
9
+ result.should == [
9
10
  {"name"=>"rho__id", "value"=>"SampleAdapter", "type"=>"string"},
10
11
  {"name"=>"source_id", "value"=>nil, "type"=>"integer"},
11
12
  {"name"=>"name", "value"=>"SampleAdapter", "type"=>"string"},
12
- {"name"=>"url", "value"=>"", "type"=>"string"},
13
- {"name"=>"login", "value"=>"", "type"=>"string"},
14
- {"name"=>"password", "value"=>"", "type"=>"string"},
13
+ {"name"=>"url", "value"=>"http://example.com", "type"=>"string"},
14
+ {"name"=>"login", "value"=>"testuser", "type"=>"string"},
15
+ {"name"=>"password", "value"=>"testpass", "type"=>"string"},
15
16
  {"name"=>"priority", "value"=>3, "type"=>"integer"},
16
17
  {"name"=>"callback_url", "value"=>nil, "type"=>"string"},
17
18
  {"name"=>"poll_interval", "value"=>300, "type"=>"integer"},
@@ -19,9 +20,10 @@ describe "RhosyncApiGetSourceParams" do
19
20
  {"name"=>"sync_type", "value"=>"incremental", "type"=>"string"},
20
21
  {"name"=>"belongs_to", "type"=>"string", "value"=>nil},
21
22
  {"name"=>"has_many", "type"=>"string", "value"=>"FixedSchemaAdapter,brand"},
23
+ {"name"=>"id", "value"=>"SampleAdapter", "type"=>"string"},
22
24
  {"name"=>"queue", "value"=>nil, "type"=>"string"},
23
25
  {"name"=>"query_queue", "value"=>nil, "type"=>"string"},
24
- {"name"=>"cud_queue", "value"=>nil, "type"=>"string"}]
26
+ {"name"=>"cud_queue", "value"=>nil, "type"=>"string"}].sort {|x,y| y["name"] <=> x["name"] }
25
27
  end
26
28
 
27
29
  end
@@ -5,6 +5,7 @@ describe "RhosyncApiPushDeletes" do
5
5
 
6
6
  it "should delete object from :md" do
7
7
  data = {'1' => @product1, '2' => @product2, '3' => @product3}
8
+ @s = Source.load(@s_fields[:name],@s_params)
8
9
  set_state(@s.docname(:md) => data)
9
10
  data.delete('2')
10
11
  post "/api/push_deletes", :api_token => @api_token,
@@ -14,6 +14,7 @@ describe "RhosyncApiPushObjects" do
14
14
  it "should push updates to existing objects to rhosync's :md" do
15
15
  data = {'1' => @product1, '2' => @product2, '3' => @product3}
16
16
  update = {'price' => '0.99', 'new_field' => 'value'}
17
+ @s = Source.load(@s_fields[:name],@s_params)
17
18
  set_state(@s.docname(:md) => data)
18
19
  update.each do |key,value|
19
20
  data['2'][key] = value
@@ -152,13 +152,15 @@ describe "RhosyncApi" do
152
152
  end
153
153
 
154
154
  it "should list source attributes using direct api call" do
155
- RhosyncApi::get_source_params('',@api_token,"SampleAdapter").should == [
155
+ result = RhosyncApi::get_source_params(
156
+ '',@api_token,"SampleAdapter").sort {|x,y| y["name"] <=> x["name"] }
157
+ result.should == [
156
158
  {"name"=>"rho__id", "value"=>"SampleAdapter", "type"=>"string"},
157
159
  {"name"=>"source_id", "value"=>nil, "type"=>"integer"},
158
160
  {"name"=>"name", "value"=>"SampleAdapter", "type"=>"string"},
159
- {"name"=>"url", "value"=>"", "type"=>"string"},
160
- {"name"=>"login", "value"=>"", "type"=>"string"},
161
- {"name"=>"password", "value"=>"", "type"=>"string"},
161
+ {"name"=>"url", "value"=>"http://example.com", "type"=>"string"},
162
+ {"name"=>"login", "value"=>"testuser", "type"=>"string"},
163
+ {"name"=>"password", "value"=>"testpass", "type"=>"string"},
162
164
  {"name"=>"priority", "value"=>3, "type"=>"integer"},
163
165
  {"name"=>"callback_url", "value"=>nil, "type"=>"string"},
164
166
  {"name"=>"poll_interval", "value"=>300, "type"=>"integer"},
@@ -166,9 +168,10 @@ describe "RhosyncApi" do
166
168
  {"name"=>"sync_type", "value"=>"incremental", "type"=>"string"},
167
169
  {"name"=>"belongs_to", "type"=>"string", "value"=>nil},
168
170
  {"name"=>"has_many", "type"=>"string", "value"=>"FixedSchemaAdapter,brand"},
171
+ {"name"=>"id", "value"=>"SampleAdapter", "type"=>"string"},
169
172
  {"name"=>"queue", "value"=>nil, "type"=>"string"},
170
173
  {"name"=>"query_queue", "value"=>nil, "type"=>"string"},
171
- {"name"=>"cud_queue", "value"=>nil, "type"=>"string"}]
174
+ {"name"=>"cud_queue", "value"=>nil, "type"=>"string"}].sort {|x,y| y["name"] <=> x["name"] }
172
175
  end
173
176
 
174
177
  it "should list source attributes using rest call" do
@@ -4,6 +4,10 @@ describe "BulkData" do
4
4
  it_should_behave_like "SpecBootstrapHelper"
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
+ before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
9
+ end
10
+
7
11
  after(:each) do
8
12
  delete_data_directory
9
13
  end
data/spec/client_spec.rb CHANGED
@@ -7,6 +7,10 @@ describe "Client" do
7
7
  it_should_behave_like "SpecBootstrapHelper"
8
8
  it_should_behave_like "SourceAdapterHelper"
9
9
 
10
+ before(:each) do
11
+ @s = Source.load(@s_fields[:name],@s_params)
12
+ end
13
+
10
14
  it "should create client with fields" do
11
15
  @c.id.length.should == 32
12
16
  @c.device_type.should == @c_fields[:device_type]
@@ -10,6 +10,7 @@ describe "ClientSync" do
10
10
  end
11
11
 
12
12
  before(:each) do
13
+ @s = Source.load(@s_fields[:name],@s_params)
13
14
  @cs = ClientSync.new(@s,@c,2)
14
15
  end
15
16
 
@@ -341,7 +342,7 @@ describe "ClientSync" do
341
342
  token1.should be_nil
342
343
  Store.get_data(@c.docname(:search)).should == {}
343
344
  end
344
-
345
+
345
346
  end
346
347
 
347
348
  describe "page methods" do
@@ -354,40 +355,40 @@ describe "ClientSync" do
354
355
  Store.get_value(@cs.client.docname(:cd_size)).to_i.should == 0
355
356
  Store.get_data(@cs.client.docname(:page)).should == @expected
356
357
  end
357
-
358
+
358
359
  it "appends diff to the client document" do
359
360
  @cd = {'3'=>@product3}
360
361
  Store.put_data(@c.docname(:cd),@cd)
361
362
  Store.get_data(@c.docname(:cd)).should == @cd
362
-
363
+
363
364
  @page = {'1'=>@product1,'2'=>@product2}
364
365
  @expected = {'1'=>@product1,'2'=>@product2,'3'=>@product3}
365
-
366
+
366
367
  Store.put_data(@c.docname(:cd),@page,true).should == true
367
368
  Store.get_data(@c.docname(:cd)).should == @expected
368
369
  end
369
-
370
+
370
371
  it "should return deleted objects in the client document" do
371
372
  Store.put_data(@s.docname(:md),@data).should == true
372
373
  Store.get_data(@s.docname(:md)).should == @data
373
-
374
+
374
375
  @cd = {'1'=>@product1,'2'=>@product2,'3'=>@product3,'4'=>@product4}
375
376
  Store.put_data(@cs.client.docname(:cd),@cd)
376
377
  Store.get_data(@cs.client.docname(:cd)).should == @cd
377
-
378
+
378
379
  @expected = {'4'=>@product4}
379
380
  @cs.compute_deleted_page.should == @expected
380
381
  Store.get_data(@cs.client.docname(:delete_page)).should == @expected
381
382
  end
382
-
383
+
383
384
  it "should delete objects from client document" do
384
385
  Store.put_data(@s.docname(:md),@data).should == true
385
386
  Store.get_data(@s.docname(:md)).should == @data
386
-
387
+
387
388
  @cd = {'1'=>@product1,'2'=>@product2,'3'=>@product3,'4'=>@product4}
388
389
  Store.put_data(@cs.client.docname(:cd),@cd)
389
390
  Store.get_data(@cs.client.docname(:cd)).should == @cd
390
-
391
+
391
392
  Store.delete_data(@cs.client.docname(:cd),@cs.compute_deleted_page).should == true
392
393
  Store.get_data(@cs.client.docname(:cd)).should == @data
393
394
  end
@@ -4,6 +4,10 @@ describe "Document" do
4
4
  it_should_behave_like "SpecBootstrapHelper"
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
+ before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
9
+ end
10
+
7
11
  it "should generate client docname" do
8
12
  @c.docname(:foo).should == "client:#{@a.id}:#{@u.id}:#{@c.id}:#{@s_fields[:name]}:foo"
9
13
  end
@@ -4,6 +4,10 @@ describe "SourceJob" do
4
4
  it_should_behave_like "SpecBootstrapHelper"
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
+ before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
9
+ end
10
+
7
11
  it "should perform process_query" do
8
12
  set_state('test_db_storage' => @data)
9
13
  SourceJob.perform('query',@s.id,@s.app_id,@s.user_id,nil,nil)
@@ -187,6 +187,12 @@ describe "Server" do
187
187
  get "/application",:client_id => @c.id,:source_name => @s.name,:version => ClientSync::VERSION
188
188
  JSON.parse(last_response.body).last['insert'].should == data
189
189
  end
190
+
191
+ it "should return error on routes if client doesn't exist" do
192
+ get "/application",:client_id => "missingclient",:source_name => @s.name,:version => ClientSync::VERSION
193
+ last_response.body.should == "Unknown client"
194
+ last_response.status.should == 500
195
+ end
190
196
  end
191
197
 
192
198
  describe "source routes" do
@@ -16,6 +16,7 @@ describe "SourceAdapter" do
16
16
  it_should_behave_like "SourceAdapterHelper"
17
17
 
18
18
  before(:each) do
19
+ @s = Source.load(@s_fields[:name],@s_params)
19
20
  @s.name = 'SimpleAdapter'
20
21
  @sa = SourceAdapter.create(@s,nil)
21
22
  end
@@ -37,6 +38,7 @@ describe "SourceAdapter" do
37
38
  @s_fields[:name] = 'Broken'
38
39
  broken_source = Source.create(@s_fields,@s_params)
39
40
  lambda { SourceAdapter.create(broken_source) }.should raise_error(Exception)
41
+ broken_source.delete
40
42
  end
41
43
 
42
44
  it "should create SourceAdapter with trailing spaces" do
data/spec/source_spec.rb CHANGED
@@ -4,6 +4,10 @@ describe "Source" do
4
4
  it_should_behave_like "SpecBootstrapHelper"
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
+ before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
9
+ end
10
+
7
11
  it "should create and load source with @s_fields and @s_params" do
8
12
  @s.name.should == @s_fields[:name]
9
13
  @s.url.should == @s_fields[:url]
@@ -30,6 +34,7 @@ describe "Source" do
30
34
  @s1.poll_interval.should == 300
31
35
  @s1.app_id.should == @s_params[:app_id]
32
36
  @s1.user_id.should == @s_params[:user_id]
37
+ # puts "#{@s1.inspect()}" # FIXME:
33
38
  end
34
39
 
35
40
  it "should create source with user" do
@@ -40,17 +45,31 @@ describe "Source" do
40
45
  @s.app.name.should == @a_fields[:name]
41
46
  @s.docname(:md).should == "source:#{@s.app.id}:#{@u.id}:#{@s_fields[:name]}:md"
42
47
  end
48
+
49
+ it 'should return values that set by setter method' do
50
+ @s.login = "shurab"
51
+ @s.login.should == "shurab"
52
+ @s.poll_interval = 350
53
+ @s.poll_interval.should == 350
54
+ @s.poll_interval = nil
55
+ @s.poll_interval.should == nil
56
+ @s.url = nil
57
+ @s.url.should be_nil
58
+ end
43
59
 
44
60
  it "should delete source" do
45
61
  @s.delete
46
62
  Source.is_exist?(@s_fields[:name]).should == false
63
+ @s = Source.create(@s_fields,@s_params)
47
64
  end
48
65
 
49
66
  it "should delete master and all documents associated with source" do
50
- set_state(@s.docname(:md) => @data)
67
+ key = @s.docname('*')
68
+ set_state(key => @data)
51
69
  @s.delete
52
- verify_result(@s.docname(:md) => {})
53
- Store.db.keys(@s.docname('*')).should == []
70
+ verify_result(key => {})
71
+ Store.db.keys(key).should == []
72
+ @s = Source.create(@s_fields,@s_params)
54
73
  end
55
74
 
56
75
  it "should create source with default partition user" do
@@ -68,16 +87,17 @@ describe "Source" do
68
87
  @s_fields[:queue] = :default
69
88
  @s_fields[:query_queue] = :query
70
89
  @s_fields[:cud_queue] = :cud
71
- Source.create(@s_fields,@s_params)
90
+ @s = Source.create(@s_fields,@s_params)
72
91
  s = Source.load(@s_fields[:name],@s_params)
73
- s.queue.should == 'default'
74
- s.query_queue.should == 'query'
75
- s.cud_queue.should == 'cud'
92
+ s.queue.should == :default
93
+ s.query_queue.should == :query
94
+ s.cud_queue.should == :cud
76
95
  end
77
96
 
78
97
  it "should add associations based on belongs_to field for a source" do
79
98
  @s2 = Source.create({:name => 'SimpleAdapter'}, @s_params)
80
99
  @s2.belongs_to = [{'product_id' => 'SampleAdapter'}].to_json
100
+ sf = Source.load(@s1.name,{:app_id => @a.id,:user_id => '*'})
81
101
  Source.update_associations([@s.name,@s1.name, @s2.name])
82
102
  s = Source.load(@s.name,{:app_id => @a.id,:user_id => '*'})
83
103
  s.has_many.should == "#{@s1.name},brand,#{@s2.name},product_id"
@@ -5,6 +5,7 @@ describe "SourceSync" do
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
7
  before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
8
9
  @ss = SourceSync.new(@s)
9
10
  end
10
11
 
@@ -51,7 +52,7 @@ describe "SourceSync" do
51
52
  @ss.process_query
52
53
  verify_result(@s.docname(:md) => expected)
53
54
  end
54
-
55
+
55
56
  it "should never call read on any call of process" do
56
57
  @s.poll_interval = -1
57
58
  Store.put_data('test_db_storage',{'1'=>@product1})
@@ -207,7 +208,7 @@ describe "SourceSync" do
207
208
 
208
209
  describe "app-level partitioning" do
209
210
  it "should create app-level masterdoc with '__shared__' docname" do
210
- @s1 = Source.load(@s_fields[:name],@s_params)
211
+ @s1 = Source.load(@s_fields[:name],{:user_id => "testuser",:app_id => @a.id})
211
212
  @s1.partition = :app
212
213
  @ss1 = SourceSync.new(@s1)
213
214
  expected = {'1'=>@product1,'2'=>@product2}
data/spec/spec_helper.rb CHANGED
@@ -209,6 +209,7 @@ describe "RhosyncHelper", :shared => true do
209
209
  before(:each) do
210
210
  Store.create
211
211
  Store.db.flushdb
212
+ # Source.delete_all # TODO: should have this
212
213
  end
213
214
  end
214
215
 
@@ -284,10 +285,8 @@ describe "DBObjectsHelper", :shared => true do
284
285
  :app_id => @a.id
285
286
  }
286
287
  @c = Client.create(@c_fields,{:source_name => @s_fields[:name]})
287
- @s = Source.load(@s_fields[:name],@s_params)
288
- @s = Source.create(@s_fields,@s_params) if @s.nil?
288
+ @s = Source.create(@s_fields,@s_params)
289
289
  @s1 = Source.load('FixedSchemaAdapter',@s_params)
290
- @s1 = Source.create({:name => 'FixedSchemaAdapter'},@s_params) if @s1.nil?
291
290
  config = Rhosync.source_config["sources"]['FixedSchemaAdapter']
292
291
  @s1.update(config)
293
292
  @r = @s.read_state
@@ -5,6 +5,7 @@ describe "Sync Server States" do
5
5
  it_should_behave_like "SourceAdapterHelper"
6
6
 
7
7
  before(:each) do
8
+ @s = Source.load(@s_fields[:name],@s_params)
8
9
  @cs = ClientSync.new(@s,@c,2)
9
10
  end
10
11
 
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rhosync
3
3
  version: !ruby/object:Gem::Version
4
- hash: 13
4
+ hash: 7
5
5
  prerelease:
6
6
  segments:
7
7
  - 2
8
8
  - 1
9
- - 3
10
- version: 2.1.3
9
+ - 6
10
+ version: 2.1.6
11
11
  platform: ruby
12
12
  authors:
13
13
  - Rhomobile
@@ -15,8 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-05-05 00:00:00 -07:00
19
- default_executable: rhosync
18
+ date: 2011-05-25 00:00:00 Z
20
19
  dependencies:
21
20
  - !ruby/object:Gem::Dependency
22
21
  name: json
@@ -544,7 +543,6 @@ files:
544
543
  - examples/simple/application.rb
545
544
  - examples/simple/sources/sample_adapter.rb
546
545
  - examples/simple/sources/simple_adapter.rb
547
- has_rdoc: true
548
546
  homepage: http://rhomobile.com/products/rhosync
549
547
  licenses: []
550
548
 
@@ -574,7 +572,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
574
572
  requirements: []
575
573
 
576
574
  rubyforge_project:
577
- rubygems_version: 1.6.2
575
+ rubygems_version: 1.8.3
578
576
  signing_key:
579
577
  specification_version: 3
580
578
  summary: RhoSync Synchronization Framework