sqlcached_client 1.0.0 → 1.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/sqlcached_client/attachment.rb +54 -0
- data/lib/sqlcached_client/attachments.rb +36 -0
- data/lib/sqlcached_client/entity.rb +32 -8
- data/lib/sqlcached_client/proxy_object.rb +29 -0
- data/lib/sqlcached_client/resultset.rb +32 -3
- data/lib/sqlcached_client/server.rb +36 -22
- data/lib/sqlcached_client/server_responses/query_response.rb +52 -0
- data/lib/sqlcached_client/version.rb +1 -1
- data/spec/sqlcached_client/attachment_spec.rb +68 -0
- data/spec/sqlcached_client/attachments_spec.rb +19 -0
- data/spec/sqlcached_client/entity_spec.rb +7 -1
- data/spec/sqlcached_client/proxy_object_spec.rb +35 -0
- data/spec/sqlcached_client/resultset_spec.rb +39 -2
- data/spec/sqlcached_client/server_responses/query_response_spec.rb +79 -0
- data/spec/sqlcached_client/server_spec.rb +5 -30
- metadata +14 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e1f725ac30395fee0332b228f2f7afba9a8e3f63
|
4
|
+
data.tar.gz: 6c8f3618babaf1f18b1295d75bb86a89c84007ca
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e7759cc739a2e3d14bc63c294b84cc1096ed7c97f877e4e86210d3e792bfc61e95cab515b7a7a0362e87aaab382cad539305e5caf0eaf0beacdd8aeb860a848b
|
7
|
+
data.tar.gz: 26d535fd6114978514c5b726755bdfd69a30458955a31259ccfc4f86d6baf7dc1dde767f501e392c91cad7e7ffb62077f03e6eaba14e9705fb7998bb2bce9915
|
@@ -0,0 +1,54 @@
|
|
1
|
+
require 'active_support/core_ext/hash'
|
2
|
+
|
3
|
+
module SqlcachedClient
|
4
|
+
class Attachment
|
5
|
+
|
6
|
+
PREDICATES = ['=', '<=', '>']
|
7
|
+
|
8
|
+
attr_reader :name, :conditions
|
9
|
+
attr_accessor :content
|
10
|
+
|
11
|
+
# @param conditions [Hash] { var_1: 'value 1', var_2: 'value 2' }
|
12
|
+
def initialize(name, conditions, content)
|
13
|
+
@name = name
|
14
|
+
@conditions = conditions.with_indifferent_access
|
15
|
+
@content = content
|
16
|
+
end
|
17
|
+
|
18
|
+
class << self
|
19
|
+
|
20
|
+
attr_reader :variables
|
21
|
+
|
22
|
+
def add_variable(variable_name, predicate)
|
23
|
+
raise "Invalid predicate" if !PREDICATES.include?(predicate)
|
24
|
+
@variables = [] if @variables.nil?
|
25
|
+
@variables << OpenStruct.new(name: variable_name, predicate: predicate)
|
26
|
+
end
|
27
|
+
|
28
|
+
alias_method :depends_on, :add_variable
|
29
|
+
end # class << self
|
30
|
+
|
31
|
+
def variables
|
32
|
+
self.class.variables
|
33
|
+
end
|
34
|
+
|
35
|
+
def to_query_format
|
36
|
+
{
|
37
|
+
name: name,
|
38
|
+
condition_values: Hash[
|
39
|
+
variables.map { |v| [v.name, conditions[v.name]] }
|
40
|
+
]
|
41
|
+
}
|
42
|
+
end
|
43
|
+
|
44
|
+
def to_save_format
|
45
|
+
{
|
46
|
+
name: name,
|
47
|
+
attachment: content,
|
48
|
+
conditions: variables.map do |v|
|
49
|
+
"#{v.name} #{v.predicate} #{conditions[v.name]}"
|
50
|
+
end
|
51
|
+
}
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
require 'sqlcached_client/attachment'
|
2
|
+
|
3
|
+
module SqlcachedClient
|
4
|
+
module Attachments
|
5
|
+
|
6
|
+
module ClassMethods
|
7
|
+
|
8
|
+
def has_attachment(name, &block)
|
9
|
+
@attachment_classes ||= {}
|
10
|
+
@attachment_classes[name] =
|
11
|
+
Class.new(Attachment) do
|
12
|
+
|
13
|
+
@attachment_name = name
|
14
|
+
class << self
|
15
|
+
attr_reader :attachment_name
|
16
|
+
end
|
17
|
+
|
18
|
+
def initialize(conditions, content)
|
19
|
+
super(self.class.attachment_name, conditions, content)
|
20
|
+
end
|
21
|
+
|
22
|
+
instance_exec(&block)
|
23
|
+
end
|
24
|
+
attr_accessor(name)
|
25
|
+
end
|
26
|
+
|
27
|
+
def build_attachments(name, conditions, size)
|
28
|
+
size.times.map { @attachment_classes[name].new(conditions, nil) }
|
29
|
+
end
|
30
|
+
end # module ClassMethods
|
31
|
+
|
32
|
+
def self.included(base)
|
33
|
+
base.extend ClassMethods
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -2,6 +2,7 @@ require 'sqlcached_client/resultset'
|
|
2
2
|
require 'sqlcached_client/server'
|
3
3
|
require 'sqlcached_client/arel'
|
4
4
|
require 'sqlcached_client/tree_visitor'
|
5
|
+
require 'sqlcached_client/proxy_object'
|
5
6
|
|
6
7
|
module SqlcachedClient
|
7
8
|
class Entity
|
@@ -85,6 +86,19 @@ module SqlcachedClient
|
|
85
86
|
server.session(&block)
|
86
87
|
end
|
87
88
|
|
89
|
+
|
90
|
+
def transaction(&block)
|
91
|
+
proxy = ProxyObject.new(self)
|
92
|
+
srv_local = server
|
93
|
+
session = server.get_session
|
94
|
+
proxy.plug_method(:server_session) do |server_session_block|
|
95
|
+
instance_exec(srv_local, session, &server_session_block)
|
96
|
+
end
|
97
|
+
result = proxy.execute(srv_local, session, &block)
|
98
|
+
session.finish
|
99
|
+
result
|
100
|
+
end
|
101
|
+
|
88
102
|
# Runs the entity query with the provided parameters
|
89
103
|
# @return [Resultset]
|
90
104
|
def where(params, dry_run = false)
|
@@ -102,14 +116,14 @@ module SqlcachedClient
|
|
102
116
|
if dry_run
|
103
117
|
request
|
104
118
|
else
|
105
|
-
|
106
|
-
|
119
|
+
server_resp =
|
120
|
+
server_session do |server, session|
|
107
121
|
server.run_query(session, server.build_request(
|
108
122
|
request.is_a?(Array) ? request : [request]
|
109
123
|
))
|
110
124
|
end
|
111
|
-
|
112
|
-
Resultset.new(self,
|
125
|
+
server_resp.flatten!(1) if server_resp.is_array?
|
126
|
+
Resultset.new(self, server_resp)
|
113
127
|
end
|
114
128
|
end
|
115
129
|
|
@@ -272,14 +286,24 @@ module SqlcachedClient
|
|
272
286
|
# Like 'where' but loads every associated entity recursively at any level,
|
273
287
|
# with only one interaction with the server
|
274
288
|
# @param root_conditions [Array]
|
275
|
-
def load_tree(root_conditions
|
276
|
-
|
289
|
+
def load_tree(root_conditions, attachment_name = nil,
|
290
|
+
attachment_conditions = nil)
|
291
|
+
attachments =
|
292
|
+
if attachment_name.present?
|
293
|
+
build_attachments(attachment_name, attachment_conditions,
|
294
|
+
root_conditions.size)
|
295
|
+
else
|
296
|
+
nil
|
297
|
+
end
|
298
|
+
server_session do |server, session|
|
277
299
|
Resultset.new(
|
278
300
|
self,
|
279
301
|
server.run_query(
|
280
302
|
session,
|
281
|
-
server.build_tree_request(build_query_tree, root_conditions
|
282
|
-
|
303
|
+
server.build_tree_request(build_query_tree, root_conditions,
|
304
|
+
attachments)
|
305
|
+
),
|
306
|
+
attachments
|
283
307
|
)
|
284
308
|
end
|
285
309
|
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
module SqlcachedClient
|
2
|
+
class ProxyObject < BasicObject
|
3
|
+
|
4
|
+
def initialize(context)
|
5
|
+
@context = context
|
6
|
+
end
|
7
|
+
|
8
|
+
def method_missing(symbol, *args)
|
9
|
+
@context.send(symbol, *args)
|
10
|
+
end
|
11
|
+
|
12
|
+
def execute(*args, &block)
|
13
|
+
instance_exec(*args, &block)
|
14
|
+
end
|
15
|
+
|
16
|
+
def plug_method(method_name, &method_body)
|
17
|
+
memoize_var = "@m_#{method_name}"
|
18
|
+
instance_variable_set(memoize_var, method_body)
|
19
|
+
eval(
|
20
|
+
<<-RUBY
|
21
|
+
def self.#{method_name}(*args, &block)
|
22
|
+
instance_exec(*args, block, &#{memoize_var})
|
23
|
+
end
|
24
|
+
RUBY
|
25
|
+
)
|
26
|
+
method_name.to_sym
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -5,10 +5,13 @@ module SqlcachedClient
|
|
5
5
|
attr_reader :entity_class, :entities, :count
|
6
6
|
|
7
7
|
# @param entity_class [Class]
|
8
|
-
# @param
|
9
|
-
def initialize(entity_class,
|
8
|
+
# @param data [Array] or [ServerResponse]
|
9
|
+
def initialize(entity_class, data, attachments = nil)
|
10
|
+
# set entity class
|
10
11
|
@entity_class = entity_class
|
11
|
-
|
12
|
+
# build the entities
|
13
|
+
ents = data.respond_to?(:entities) ? data.entities : data
|
14
|
+
@entities = (ents || []).map do |item|
|
12
15
|
if item.is_a?(Hash)
|
13
16
|
entity_class.new(item)
|
14
17
|
elsif item.is_a?(entity_class)
|
@@ -17,7 +20,10 @@ module SqlcachedClient
|
|
17
20
|
raise "Cannot handle: #{item.inspect}"
|
18
21
|
end
|
19
22
|
end
|
23
|
+
# record collection size
|
20
24
|
@count = @entities.size
|
25
|
+
# set up attachments
|
26
|
+
set_entities_attachments(@entities, attachments, data.try(:attachments))
|
21
27
|
end
|
22
28
|
|
23
29
|
class << self
|
@@ -69,5 +75,28 @@ module SqlcachedClient
|
|
69
75
|
entity.get_association_requests
|
70
76
|
end
|
71
77
|
end
|
78
|
+
|
79
|
+
def set_entities_attachments(entities, attachments, contents)
|
80
|
+
if attachments.is_a?(Array) && contents.is_a?(Array)
|
81
|
+
entities.each_with_index do |entity, i|
|
82
|
+
attachment = attachments[i]
|
83
|
+
entity.send("#{attachment.name}=", attachment)
|
84
|
+
attachment.content = contents[i] if attachment.respond_to?(:content=)
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
def store_attachments(attachment_name, server, session)
|
90
|
+
entities_with_a = entities.select do |entity|
|
91
|
+
!entity.send(attachment_name).nil?
|
92
|
+
end
|
93
|
+
server.store_attachments(
|
94
|
+
session,
|
95
|
+
server.build_store_attachments_request(
|
96
|
+
entities_with_a.map { |e| e.attributes },
|
97
|
+
entities_with_a.map { |e| e.send(attachment_name).to_save_format }
|
98
|
+
)
|
99
|
+
)
|
100
|
+
end
|
72
101
|
end
|
73
102
|
end
|
@@ -1,6 +1,7 @@
|
|
1
1
|
require 'uri'
|
2
2
|
require 'net/http'
|
3
3
|
require 'json'
|
4
|
+
require 'sqlcached_client/server_responses/query_response'
|
4
5
|
|
5
6
|
module SqlcachedClient
|
6
7
|
class Server
|
@@ -12,37 +13,32 @@ module SqlcachedClient
|
|
12
13
|
@port = config[:port]
|
13
14
|
end
|
14
15
|
|
15
|
-
|
16
|
+
# @return [ServerResponses::QueryResponse]
|
16
17
|
def run_query(session, http_req_body)
|
17
18
|
req = Net::HTTP::Post.new(data_batch_url)
|
18
19
|
req.set_content_type('application/json')
|
19
20
|
req.body = http_req_body.to_json
|
20
21
|
resp = session.request(req)
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
22
|
+
resp_body =
|
23
|
+
if (resp['Content-Type'] || '') =~ /application\/json/
|
24
|
+
JSON.parse(resp.body)
|
25
|
+
else
|
26
|
+
resp.body
|
27
|
+
end
|
26
28
|
if 200 == resp.code.to_i
|
27
|
-
resp_body
|
29
|
+
ServerResponses::QueryResponse.new(resp_body)
|
28
30
|
else
|
29
31
|
raise "Got HTTP response #{resp.code} from server - #{resp_body.inspect}"
|
30
32
|
end
|
31
33
|
end
|
32
34
|
|
33
35
|
|
34
|
-
def
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
else
|
41
|
-
resultset
|
42
|
-
end
|
43
|
-
else
|
44
|
-
body
|
45
|
-
end
|
36
|
+
def store_attachments(session, http_req_body)
|
37
|
+
req = Net::HTTP::Post.new(store_attachments_url)
|
38
|
+
req.set_content_type('application/json')
|
39
|
+
req.body = http_req_body.to_json
|
40
|
+
resp = session.request(req)
|
41
|
+
201 == resp.code.to_i || raise("Failed to save attachments - server answered with #{resp.body.inspect}")
|
46
42
|
end
|
47
43
|
|
48
44
|
# Builds a 'standard' request body
|
@@ -56,8 +52,12 @@ module SqlcachedClient
|
|
56
52
|
# @param tree [Hash]
|
57
53
|
# @param root_parameters [Array] a vector of actual condition parameters
|
58
54
|
# for the root query
|
59
|
-
def build_tree_request(tree, root_parameters)
|
60
|
-
{ tree: tree, root_parameters: root_parameters }
|
55
|
+
def build_tree_request(tree, root_parameters, attachments = nil)
|
56
|
+
h = { tree: tree, root_parameters: root_parameters }
|
57
|
+
if !attachments.nil?
|
58
|
+
h[:attachments] = attachments.map(&:to_query_format)
|
59
|
+
end
|
60
|
+
h
|
61
61
|
end
|
62
62
|
|
63
63
|
# Formats the parameters passed in the way the server expects
|
@@ -75,6 +75,14 @@ module SqlcachedClient
|
|
75
75
|
}
|
76
76
|
end
|
77
77
|
|
78
|
+
|
79
|
+
def build_store_attachments_request(entities, attachments)
|
80
|
+
{
|
81
|
+
resultset: entities,
|
82
|
+
attachments: attachments
|
83
|
+
}
|
84
|
+
end
|
85
|
+
|
78
86
|
# @return [Net::HTTP] an http session on the server
|
79
87
|
def get_session
|
80
88
|
url = server_url
|
@@ -99,7 +107,13 @@ module SqlcachedClient
|
|
99
107
|
|
100
108
|
def data_batch_url
|
101
109
|
url = server_url
|
102
|
-
url.path =
|
110
|
+
url.path = '/data-batch'
|
111
|
+
url
|
112
|
+
end
|
113
|
+
|
114
|
+
def store_attachments_url
|
115
|
+
url = server_url
|
116
|
+
url.path = '/resultset-attachments'
|
103
117
|
url
|
104
118
|
end
|
105
119
|
end
|
@@ -0,0 +1,52 @@
|
|
1
|
+
module SqlcachedClient
|
2
|
+
module ServerResponses
|
3
|
+
|
4
|
+
class QueryResponse
|
5
|
+
include Enumerable
|
6
|
+
|
7
|
+
attr_reader :body
|
8
|
+
|
9
|
+
# @param body [Hash]
|
10
|
+
def initialize(body)
|
11
|
+
@body = body
|
12
|
+
end
|
13
|
+
|
14
|
+
def each(&block)
|
15
|
+
block ? entities.each(&block) : entities.each
|
16
|
+
end
|
17
|
+
|
18
|
+
def attachments
|
19
|
+
body.is_a?(Hash) ? body['attachments'] : nil
|
20
|
+
end
|
21
|
+
|
22
|
+
def entities
|
23
|
+
@entities ||= get_entities(body)
|
24
|
+
end
|
25
|
+
|
26
|
+
def is_array?
|
27
|
+
entities.is_a?(Array)
|
28
|
+
end
|
29
|
+
|
30
|
+
def flatten!(level = nil)
|
31
|
+
entities if @entities.nil?
|
32
|
+
@entities.flatten!(level)
|
33
|
+
end
|
34
|
+
|
35
|
+
private
|
36
|
+
|
37
|
+
def get_entities(data)
|
38
|
+
if data.is_a?(Array)
|
39
|
+
data.map { |item| get_entities(item) }
|
40
|
+
elsif data.is_a?(Hash)
|
41
|
+
if (resultset = data['resultset']).is_a?(String)
|
42
|
+
JSON.parse(resultset)
|
43
|
+
else
|
44
|
+
resultset
|
45
|
+
end
|
46
|
+
else
|
47
|
+
data
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end # class QueryResponse
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,68 @@
|
|
1
|
+
require 'sqlcached_client/attachment'
|
2
|
+
|
3
|
+
describe SqlcachedClient::Attachment do
|
4
|
+
|
5
|
+
let(:described_class) { SqlcachedClient::Attachment }
|
6
|
+
|
7
|
+
describe :initialize do
|
8
|
+
it "accepts name, conditions and content" do
|
9
|
+
attachment = described_class.new('name', { 'foo' => 'bar'}, 'content')
|
10
|
+
expect(attachment.name).to eq('name')
|
11
|
+
expect(attachment.conditions).to eq({ 'foo' => 'bar' })
|
12
|
+
expect(attachment.content).to eq('content')
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
describe :variables do
|
17
|
+
it "returns the variables added to the class" do
|
18
|
+
attachment = described_class.new(nil, {}, nil)
|
19
|
+
allow(described_class).to receive(:variables).and_return('foo')
|
20
|
+
expect(attachment.variables).to eq('foo')
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
describe :to_query_format do
|
25
|
+
it "is an hash with name and condition values" do
|
26
|
+
attachment = described_class.new('foo', { v1: 'bar', v2: 'baz'}, nil)
|
27
|
+
allow(attachment).to receive(:variables).and_return([
|
28
|
+
double(name: 'v1'), double(name: 'v2')
|
29
|
+
])
|
30
|
+
expect(attachment.to_query_format).to eq({
|
31
|
+
name: 'foo',
|
32
|
+
condition_values: {
|
33
|
+
'v1' => 'bar', 'v2' => 'baz'
|
34
|
+
}
|
35
|
+
})
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
describe :to_save_format do
|
40
|
+
it "is an hash with name, attachment and conditions" do
|
41
|
+
attachment = described_class.new('foo', { v1: 'bar', v2: 'baz'},
|
42
|
+
'content')
|
43
|
+
allow(attachment).to receive(:variables).and_return([
|
44
|
+
double(name: 'v1', predicate: '='), double(name: 'v2', predicate: '<=')
|
45
|
+
])
|
46
|
+
expect(attachment.to_save_format).to eq({
|
47
|
+
name: 'foo',
|
48
|
+
attachment: 'content',
|
49
|
+
conditions: ['v1 = bar', 'v2 <= baz']
|
50
|
+
})
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
describe :add_variable do
|
55
|
+
it "adds a new variable in the class list" do
|
56
|
+
described_class.add_variable('foo', '=')
|
57
|
+
v = described_class.variables.first
|
58
|
+
expect(v.name).to eq('foo')
|
59
|
+
expect(v.predicate).to eq('=')
|
60
|
+
end
|
61
|
+
|
62
|
+
context "if predicate symbol is not allowed" do
|
63
|
+
it "raises an exception" do
|
64
|
+
expect { described_class.add_variable('foo', 'X') }.to raise_exception
|
65
|
+
end
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'sqlcached_client/attachments'
|
2
|
+
|
3
|
+
describe SqlcachedClient::Attachments do
|
4
|
+
let(:klass) do
|
5
|
+
Class.new do
|
6
|
+
include SqlcachedClient::Attachments
|
7
|
+
|
8
|
+
has_attachment :foo do
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
context "after including the module" do
|
14
|
+
it "add methods 'has_attachment' and 'build_attachments' to the class" do
|
15
|
+
expect(klass.respond_to?(:has_attachment)).to eq(true)
|
16
|
+
expect(klass.respond_to?(:build_attachments)).to eq(true)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -154,7 +154,8 @@ describe SqlcachedClient::Entity do
|
|
154
154
|
entity_class.server(double(
|
155
155
|
build_request_item: "this is the request",
|
156
156
|
build_request: "request body",
|
157
|
-
session:
|
157
|
+
session: double(is_array?: false,
|
158
|
+
entities: [{ key: "value" }, { key: "value" }])
|
158
159
|
))
|
159
160
|
expect(entity_class.server).to receive(:build_request_item).with(
|
160
161
|
"foo", "bar", { baz: "biz" }, true)
|
@@ -224,4 +225,9 @@ describe SqlcachedClient::Entity do
|
|
224
225
|
describe :build_query_tree do
|
225
226
|
pending
|
226
227
|
end
|
228
|
+
|
229
|
+
|
230
|
+
describe :transaction do
|
231
|
+
pending
|
232
|
+
end
|
227
233
|
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'sqlcached_client/proxy_object'
|
2
|
+
|
3
|
+
describe SqlcachedClient::ProxyObject do
|
4
|
+
let(:klass) do
|
5
|
+
Class.new do
|
6
|
+
def foo
|
7
|
+
'bar'
|
8
|
+
end
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
it "forwards method calls to the proxied object" do
|
13
|
+
f = klass.new
|
14
|
+
p = SqlcachedClient::ProxyObject.new(f)
|
15
|
+
expect(p.foo).to eq('bar')
|
16
|
+
end
|
17
|
+
|
18
|
+
describe :execute do
|
19
|
+
it "executes the block provided in the context of the instance" do
|
20
|
+
f = klass.new
|
21
|
+
p = SqlcachedClient::ProxyObject.new(f)
|
22
|
+
expect(p.execute { foo }).to eq('bar')
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
describe :plug_method do
|
27
|
+
it "defines a singleton method on the proxy object" do
|
28
|
+
p = SqlcachedClient::ProxyObject.new(Object.new)
|
29
|
+
p.plug_method(:sum) do |a, b|
|
30
|
+
a + b
|
31
|
+
end
|
32
|
+
expect(p.sum(2, 3)).to eq(5)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -26,12 +26,10 @@ describe SqlcachedClient::Resultset do
|
|
26
26
|
end
|
27
27
|
end
|
28
28
|
|
29
|
-
|
30
29
|
describe :build_associations do
|
31
30
|
pending
|
32
31
|
end
|
33
32
|
|
34
|
-
|
35
33
|
describe :[] do
|
36
34
|
it "should be entities[i]" do
|
37
35
|
entities = [Object.new] * 3
|
@@ -39,4 +37,43 @@ describe SqlcachedClient::Resultset do
|
|
39
37
|
3.times { |i| expect(r[i]).to eq(entities[i]) }
|
40
38
|
end
|
41
39
|
end
|
40
|
+
|
41
|
+
describe :set_entities_attachments do
|
42
|
+
let(:resultset) { SqlcachedClient::Resultset.new(nil, nil) }
|
43
|
+
|
44
|
+
let(:entities) do
|
45
|
+
[double(:attach1=)]
|
46
|
+
end
|
47
|
+
|
48
|
+
let(:attachment) { double(:content=, name: 'attach1') }
|
49
|
+
|
50
|
+
it "sets each attachment to the corresponding entity and saves the content" do
|
51
|
+
expect(entities.first).to receive(:attach1=).with(attachment)
|
52
|
+
expect(attachment).to receive(:content=).with('content')
|
53
|
+
resultset.set_entities_attachments(entities, [attachment], ['content'])
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
describe :store_attachments do
|
58
|
+
let(:resultset) { SqlcachedClient::Resultset.new(nil, nil) }
|
59
|
+
|
60
|
+
let(:entities) do
|
61
|
+
[
|
62
|
+
double(att1: double(to_save_format: 'value a'), attributes: 'attrs a'),
|
63
|
+
double(att1: double(to_save_format: 'value b'), attributes: 'attrs b')
|
64
|
+
]
|
65
|
+
end
|
66
|
+
|
67
|
+
let(:server) { double }
|
68
|
+
|
69
|
+
it "calls server.store_attachments" do
|
70
|
+
expect(server).to receive(:build_store_attachments_request).with(
|
71
|
+
['attrs a', 'attrs b'], ['value a', 'value b']
|
72
|
+
).and_return('attachment request')
|
73
|
+
expect(server).to receive(:store_attachments).with('session',
|
74
|
+
'attachment request')
|
75
|
+
allow(resultset).to receive(:entities).and_return(entities)
|
76
|
+
resultset.store_attachments(:att1, server, 'session')
|
77
|
+
end
|
78
|
+
end
|
42
79
|
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
require 'sqlcached_client/server_responses/query_response'
|
2
|
+
|
3
|
+
describe SqlcachedClient::ServerResponses::QueryResponse do
|
4
|
+
let(:described_class) { SqlcachedClient::ServerResponses::QueryResponse }
|
5
|
+
|
6
|
+
describe :entities do
|
7
|
+
context "if body is an array" do
|
8
|
+
it "parses each item recoursively" do
|
9
|
+
query_response = described_class.new([[1, 2, [3, 4]], 5])
|
10
|
+
expect(query_response.entities).to eq(
|
11
|
+
[[1, 2, [3, 4]], 5])
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
context "if body is an hash" do
|
16
|
+
it "returns the value corresponding to the key 'resultset'" do
|
17
|
+
query_response = described_class.new({ 'resultset' => 1 })
|
18
|
+
expect(query_response.entities).to eq(1)
|
19
|
+
end
|
20
|
+
|
21
|
+
context "if key 'resultset' is not present" do
|
22
|
+
it "is nil" do
|
23
|
+
query_response = described_class.new({ foo: 'bar' })
|
24
|
+
expect(query_response.entities).to be_nil
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
context "if resultset is a string" do
|
29
|
+
it "is parsed as json" do
|
30
|
+
query_response = described_class.new({
|
31
|
+
'resultset' => "{ \"foo\": \"bar\", \"baz\": 1 }"
|
32
|
+
})
|
33
|
+
expect(query_response.entities).to eq({
|
34
|
+
"foo" => "bar", "baz" => 1 })
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
describe :attachments do
|
41
|
+
context "when body is an Hash" do
|
42
|
+
it "is body.attachments" do
|
43
|
+
query_response = described_class.new({ 'attachments' => 'foo' })
|
44
|
+
expect(query_response.attachments).to eq('foo')
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
context "when body is not an Hash" do
|
49
|
+
it "is nil" do
|
50
|
+
query_response = described_class.new(['foo', 'bar'])
|
51
|
+
expect(query_response.attachments).to be_nil
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
describe :is_array? do
|
57
|
+
context "when entities is an Array" do
|
58
|
+
it "is true" do
|
59
|
+
query_response = described_class.new(['foo'])
|
60
|
+
expect(query_response.is_array?).to eq(true)
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
context "when entities is not an Array" do
|
65
|
+
it "is false" do
|
66
|
+
query_response = described_class.new({})
|
67
|
+
expect(query_response.is_array?).to eq(false)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
describe :flatten! do
|
73
|
+
it "flattens the entities in place" do
|
74
|
+
query_response = described_class.new([[1, [2]], [3]])
|
75
|
+
query_response.flatten!
|
76
|
+
expect(query_response.entities).to eq([1, 2, 3])
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
@@ -12,14 +12,12 @@ describe SqlcachedClient::Server do
|
|
12
12
|
end
|
13
13
|
end
|
14
14
|
|
15
|
-
|
16
15
|
describe :build_request do
|
17
16
|
it "should put the passed value into an hash" do
|
18
17
|
expect(server.build_request("foo")).to eq({ batch: "foo" })
|
19
18
|
end
|
20
19
|
end
|
21
20
|
|
22
|
-
|
23
21
|
describe :build_tree_request do
|
24
22
|
it "should be an Hash with 'tree' and 'root_parameters' keys" do
|
25
23
|
expect(server.build_tree_request('tree', 'root')).to eq({
|
@@ -28,7 +26,6 @@ describe SqlcachedClient::Server do
|
|
28
26
|
end
|
29
27
|
end
|
30
28
|
|
31
|
-
|
32
29
|
describe :build_request_item do
|
33
30
|
it "should be an hash with id, template, params keys" do
|
34
31
|
expect(server.build_request_item("foo", "bar", "baz", "cache")).to eq({
|
@@ -40,33 +37,11 @@ describe SqlcachedClient::Server do
|
|
40
37
|
end
|
41
38
|
end
|
42
39
|
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
[[1, 2, [3, 4]], 5])
|
49
|
-
end
|
50
|
-
end
|
51
|
-
|
52
|
-
context "if body is an hash" do
|
53
|
-
it "should return the value corresponding to the key 'resultset'" do
|
54
|
-
expect(server.parse_response_body({ 'resultset' => 1 })).to eq(1)
|
55
|
-
end
|
56
|
-
|
57
|
-
context "if key 'resultset' is not present" do
|
58
|
-
it "should be nil" do
|
59
|
-
expect(server.parse_response_body({ foo: 'bar' })).to be_nil
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
|
-
context "if resultset is a string" do
|
64
|
-
it "should be parsed as json" do
|
65
|
-
expect(server.parse_response_body({
|
66
|
-
'resultset' => "{ \"foo\": \"bar\", \"baz\": 1 }" })).to eq({
|
67
|
-
"foo" => "bar", "baz" => 1 })
|
68
|
-
end
|
69
|
-
end
|
40
|
+
describe :build_store_attachments_request do
|
41
|
+
it "contains keys resultset and attachments" do
|
42
|
+
expect(server.build_store_attachments_request('e', 'a')).to eq({
|
43
|
+
resultset: 'e', attachments: 'a'
|
44
|
+
})
|
70
45
|
end
|
71
46
|
end
|
72
47
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sqlcached_client
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Roberto Maestroni
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-08-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -122,13 +122,21 @@ files:
|
|
122
122
|
- Rakefile
|
123
123
|
- lib/sqlcached_client.rb
|
124
124
|
- lib/sqlcached_client/arel.rb
|
125
|
+
- lib/sqlcached_client/attachment.rb
|
126
|
+
- lib/sqlcached_client/attachments.rb
|
125
127
|
- lib/sqlcached_client/entity.rb
|
128
|
+
- lib/sqlcached_client/proxy_object.rb
|
126
129
|
- lib/sqlcached_client/resultset.rb
|
127
130
|
- lib/sqlcached_client/server.rb
|
131
|
+
- lib/sqlcached_client/server_responses/query_response.rb
|
128
132
|
- lib/sqlcached_client/tree_visitor.rb
|
129
133
|
- lib/sqlcached_client/version.rb
|
134
|
+
- spec/sqlcached_client/attachment_spec.rb
|
135
|
+
- spec/sqlcached_client/attachments_spec.rb
|
130
136
|
- spec/sqlcached_client/entity_spec.rb
|
137
|
+
- spec/sqlcached_client/proxy_object_spec.rb
|
131
138
|
- spec/sqlcached_client/resultset_spec.rb
|
139
|
+
- spec/sqlcached_client/server_responses/query_response_spec.rb
|
132
140
|
- spec/sqlcached_client/server_spec.rb
|
133
141
|
- spec/sqlcached_client/tree_visitor_spec.rb
|
134
142
|
- sqlcached_client.gemspec
|
@@ -157,7 +165,11 @@ signing_key:
|
|
157
165
|
specification_version: 4
|
158
166
|
summary: A Ruby client for sqlcached
|
159
167
|
test_files:
|
168
|
+
- spec/sqlcached_client/attachment_spec.rb
|
169
|
+
- spec/sqlcached_client/attachments_spec.rb
|
160
170
|
- spec/sqlcached_client/entity_spec.rb
|
171
|
+
- spec/sqlcached_client/proxy_object_spec.rb
|
161
172
|
- spec/sqlcached_client/resultset_spec.rb
|
173
|
+
- spec/sqlcached_client/server_responses/query_response_spec.rb
|
162
174
|
- spec/sqlcached_client/server_spec.rb
|
163
175
|
- spec/sqlcached_client/tree_visitor_spec.rb
|