tripod 0.9.6 → 0.9.7
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 +4 -4
- data/README.md +2 -0
- data/lib/tripod.rb +4 -1
- data/lib/tripod/cache_stores/memcached_cache_store.rb +26 -8
- data/lib/tripod/components.rb +2 -2
- data/lib/tripod/graphs.rb +12 -0
- data/lib/tripod/persistence.rb +3 -3
- data/lib/tripod/version.rb +1 -1
- data/spec/tripod/eager_loading_spec.rb +4 -4
- data/spec/tripod/graphs_spec.rb +26 -0
- data/spec/tripod/memcached_cache_store_spec.rb +57 -0
- data/spec/tripod/persistence_spec.rb +21 -3
- data/tripod.gemspec +2 -1
- metadata +23 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d0d0bb81441871fbdb4115e399bca413f309c7c4
|
4
|
+
data.tar.gz: 3b72bae40446b70dd252383f82193c4764a2b669
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 614d0632c00fd4b5c99347f035fad525a2e9a9cf9240cd9376bf1c6fa1585ccda99a28ff0c8f74c988f7c8480723845195b6ffc74d05b5a7c1321ba849436062
|
7
|
+
data.tar.gz: 515dafcdb449015ef2b8728b00c65687f3d777e232022e34e9d96311a77229a7c9b2eea7332ea6dae7c19c34ba34a52e2b6117bc038fa81314cbba64b819b795
|
data/README.md
CHANGED
@@ -134,6 +134,8 @@ Tripod doesn't supply a database. You need to install one. I recommend [Fuseki](
|
|
134
134
|
|
135
135
|
With a Fuseki instance ready and up, edit the config in `spec/spec_helper.rb` to reflect your settings. Make sure you `bundle` to pull in all dependencies before trying to run the tests.
|
136
136
|
|
137
|
+
Some tests require memcached to be set up and running. The tests that require memcached are tagged with `:caching_tests => true`; do with this information what you will.
|
138
|
+
|
137
139
|
[Full Documentation](http://rubydoc.info/gems/tripod/frames)
|
138
140
|
|
139
141
|
Copyright (c) 2012 [Swirrl IT Limited](http://swirrl.com). Released under MIT License
|
data/lib/tripod.rb
CHANGED
@@ -70,6 +70,7 @@ module Tripod
|
|
70
70
|
# config.cache_store = nil #e.g Tripod::CacheStores::MemcachedCacheStore.new('localhost:11211')
|
71
71
|
# # note: if using memcached, make sure you set the -I (slab size) to big enough to store each result
|
72
72
|
# # and set the -m (total size) to something quite big (or the cache will recycle too often).
|
73
|
+
# # also note that the connection pool size can be passed in as an optional second parameter.
|
73
74
|
# config.logger = Logger.new(STDOUT) # you can set this to the Rails.logger in a rails app.
|
74
75
|
# end
|
75
76
|
#
|
@@ -100,6 +101,7 @@ require "tripod/persistence"
|
|
100
101
|
require "tripod/eager_loading"
|
101
102
|
require "tripod/serialization"
|
102
103
|
require "tripod/state"
|
104
|
+
require "tripod/graphs"
|
103
105
|
require "tripod/version"
|
104
106
|
|
105
107
|
# these need to be at the end
|
@@ -107,4 +109,5 @@ require "tripod/components"
|
|
107
109
|
require "tripod/resource"
|
108
110
|
|
109
111
|
require 'active_support/i18n'
|
110
|
-
I18n.
|
112
|
+
I18n.enforce_available_locales = true
|
113
|
+
I18n.load_path << File.dirname(__FILE__) + '/tripod/locale/en.yml'
|
@@ -1,4 +1,5 @@
|
|
1
1
|
require 'dalli'
|
2
|
+
require 'connection_pool'
|
2
3
|
|
3
4
|
module Tripod
|
4
5
|
module CacheStores
|
@@ -9,33 +10,50 @@ module Tripod
|
|
9
10
|
class MemcachedCacheStore
|
10
11
|
|
11
12
|
# initialize a memcached cache store at the specified port (default 'localhost:11211')
|
12
|
-
|
13
|
-
|
13
|
+
# a pool size should also be specified (defaults to 1 for development/local use reasons)
|
14
|
+
def initialize(location, size = 1)
|
15
|
+
@dalli_pool = ConnectionPool.new(:size => size, :timeout => 3) { Dalli::Client.new(location, :value_max_bytes => Tripod.response_limit_bytes) }
|
14
16
|
end
|
15
17
|
|
16
18
|
# takes a block
|
17
19
|
def fetch(key)
|
18
20
|
raise ArgumentError.new("expected a block") unless block_given?
|
19
21
|
|
20
|
-
@
|
21
|
-
yield
|
22
|
+
@dalli_pool.with do |client|
|
23
|
+
client.fetch(key) { yield }
|
22
24
|
end
|
23
25
|
end
|
24
26
|
|
25
27
|
def exist?(key)
|
26
|
-
|
28
|
+
@dalli_pool.with do |client|
|
29
|
+
!!client.get(key)
|
30
|
+
end
|
27
31
|
end
|
28
32
|
|
29
33
|
def write(key, data)
|
30
|
-
@
|
34
|
+
@dalli_pool.with do |client|
|
35
|
+
client.set(key, data)
|
36
|
+
end
|
31
37
|
end
|
32
38
|
|
33
39
|
def read(key)
|
34
|
-
@
|
40
|
+
@dalli_pool.with do |client|
|
41
|
+
client.get(key)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def stats
|
46
|
+
output = []
|
47
|
+
@dalli_pool.with do |client|
|
48
|
+
output << client.stats
|
49
|
+
end
|
50
|
+
output
|
35
51
|
end
|
36
52
|
|
37
53
|
def clear!
|
38
|
-
@
|
54
|
+
@dalli_pool.with do |client|
|
55
|
+
client.flush
|
56
|
+
end
|
39
57
|
end
|
40
58
|
|
41
59
|
end
|
data/lib/tripod/components.rb
CHANGED
@@ -0,0 +1,12 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
# This module defines behaviour for resources with data across multiple graphs
|
4
|
+
module Tripod::Graphs
|
5
|
+
extend ActiveSupport::Concern
|
6
|
+
|
7
|
+
def graphs
|
8
|
+
select_query = "SELECT DISTINCT ?g WHERE { GRAPH ?g {<#{uri.to_s}> ?p ?o } }"
|
9
|
+
result = Tripod::SparqlClient::Query.select(select_query)
|
10
|
+
result.map{|r| r["g"]["value"]}
|
11
|
+
end
|
12
|
+
end
|
data/lib/tripod/persistence.rb
CHANGED
@@ -73,9 +73,9 @@ module Tripod::Persistence
|
|
73
73
|
transaction = Tripod::Persistence::Transaction.get_transaction(opts[:transaction])
|
74
74
|
|
75
75
|
if self.valid?
|
76
|
-
|
76
|
+
graph_selector = self.graph_uri.present? ? "<#{graph_uri.to_s}>" : "?g"
|
77
77
|
query = "
|
78
|
-
DELETE {GRAPH
|
78
|
+
DELETE {GRAPH #{graph_selector} {<#{@uri.to_s}> ?p ?o}} WHERE {GRAPH #{graph_selector} {<#{@uri.to_s}> ?p ?o}};
|
79
79
|
INSERT DATA {
|
80
80
|
GRAPH <#{@graph_uri}> {
|
81
81
|
#{ @repository.dump(:ntriples) }
|
@@ -174,4 +174,4 @@ module Tripod::Persistence
|
|
174
174
|
|
175
175
|
end
|
176
176
|
|
177
|
-
end
|
177
|
+
end
|
data/lib/tripod/version.rb
CHANGED
@@ -143,13 +143,13 @@ describe Tripod::EagerLoading do
|
|
143
143
|
context "when eager load not called" do
|
144
144
|
context "and related resource exists" do
|
145
145
|
it "should return false" do
|
146
|
-
@john.has_related_resource?(RDF::URI.new('http://example.com/name'), Resource).should
|
146
|
+
@john.has_related_resource?(RDF::URI.new('http://example.com/name'), Resource).should be false
|
147
147
|
end
|
148
148
|
end
|
149
149
|
|
150
150
|
context "and related resource doesn't exist" do
|
151
151
|
it "should return false" do
|
152
|
-
@john.has_related_resource?(RDF::URI.new('http://example.com/nonexistent/person'), Person).should
|
152
|
+
@john.has_related_resource?(RDF::URI.new('http://example.com/nonexistent/person'), Person).should be false
|
153
153
|
end
|
154
154
|
end
|
155
155
|
end
|
@@ -161,13 +161,13 @@ describe Tripod::EagerLoading do
|
|
161
161
|
|
162
162
|
context "and related resource exists" do
|
163
163
|
it "should return true" do
|
164
|
-
@john.has_related_resource?(RDF::URI.new('http://example.com/name'), Resource).should
|
164
|
+
@john.has_related_resource?(RDF::URI.new('http://example.com/name'), Resource).should be true
|
165
165
|
end
|
166
166
|
end
|
167
167
|
|
168
168
|
context "and related resource doesn't exist" do
|
169
169
|
it "should return false" do
|
170
|
-
@john.has_related_resource?(RDF::URI.new('http://example.com/nonexistent/person'), Person).should
|
170
|
+
@john.has_related_resource?(RDF::URI.new('http://example.com/nonexistent/person'), Person).should be false
|
171
171
|
end
|
172
172
|
end
|
173
173
|
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Tripod::Graphs do
|
4
|
+
describe "#graphs" do
|
5
|
+
let(:uri) { 'http://example.com/foobar' }
|
6
|
+
let(:graph_uri) { 'http://example.com/irl' }
|
7
|
+
let(:another_graph_uri) { 'http://example.com/make-believe' }
|
8
|
+
let(:person) do
|
9
|
+
p = Person.new(uri, graph_uri: graph_uri)
|
10
|
+
p.write_predicate('http://example.com/vocation', RDF::URI.new('http://example.com/accountant'))
|
11
|
+
p.save!
|
12
|
+
p
|
13
|
+
end
|
14
|
+
|
15
|
+
before do
|
16
|
+
p2 = Person.new(uri, graph_uri: another_graph_uri)
|
17
|
+
p2.write_predicate('http://example.com/vocation', RDF::URI.new('http://example.com/lion-tamer'))
|
18
|
+
p2.save!
|
19
|
+
p2
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'should return an array of all the graphs for which there are triples about this URI' do
|
23
|
+
person.graphs.should =~ [graph_uri, another_graph_uri]
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Tripod::CacheStores, :caching_tests => true do
|
4
|
+
|
5
|
+
let(:query) { "SELECT * WHERE {?s ?p ?o}" }
|
6
|
+
let(:accept_header) { "application/sparql-results+json" }
|
7
|
+
let(:params) { {:query => query}.to_query }
|
8
|
+
let(:streaming_opts) { {:accept => accept_header, :timeout_seconds => Tripod.timeout_seconds} }
|
9
|
+
|
10
|
+
before do
|
11
|
+
Tripod.cache_store = Tripod::CacheStores::MemcachedCacheStore.new('localhost:11211', 10)
|
12
|
+
|
13
|
+
p = Person.new('http://example.com/id/garry')
|
14
|
+
p.name = "garry"
|
15
|
+
p.save!
|
16
|
+
p
|
17
|
+
end
|
18
|
+
|
19
|
+
# if Tripod cache_store is not reset to nil, other tests will fail due to caching
|
20
|
+
after(:all) do
|
21
|
+
Tripod.cache_store = nil
|
22
|
+
end
|
23
|
+
|
24
|
+
describe "sending a query with caching enabled" do
|
25
|
+
before do
|
26
|
+
@query_result = Tripod::SparqlClient::Query.query(query, accept_header)
|
27
|
+
@cache_key = 'SPARQL-QUERY-' + Digest::SHA2.hexdigest([accept_header, query].join("-"))
|
28
|
+
@stream_data = -> { Tripod::Streaming.get_data(Tripod.query_endpoint, params, streaming_opts) }
|
29
|
+
end
|
30
|
+
|
31
|
+
it "should set the data in the cache" do
|
32
|
+
Tripod.cache_store.fetch(@cache_key, &@stream_data).should_not be_nil
|
33
|
+
end
|
34
|
+
|
35
|
+
describe "with a large number of subsequent requests" do
|
36
|
+
before do
|
37
|
+
@number_of_memcache_get_calls = Tripod.cache_store.stats[0]["localhost:11211"]["cmd_get"]
|
38
|
+
@number_of_memcache_set_calls = Tripod.cache_store.stats[0]["localhost:11211"]["cmd_set"]
|
39
|
+
|
40
|
+
100.times do
|
41
|
+
Thread.new do
|
42
|
+
Tripod::SparqlClient::Query.query(query, accept_header)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
it "should increase number of memcache get calls" do
|
48
|
+
Tripod.cache_store.stats[0]["localhost:11211"]["cmd_get"].to_i.should be > @number_of_memcache_get_calls.to_i
|
49
|
+
end
|
50
|
+
|
51
|
+
it "should not increase cache size" do
|
52
|
+
Tripod.cache_store.stats[0]["localhost:11211"]["cmd_set"].to_i.should == @number_of_memcache_set_calls.to_i
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
end
|
@@ -63,6 +63,24 @@ describe Tripod::Persistence do
|
|
63
63
|
p2.repository.dump(:ntriples).should == saved_person.repository.dump(:ntriples)
|
64
64
|
end
|
65
65
|
|
66
|
+
context 'given triples about this resource in another graph' do
|
67
|
+
let(:graph_uri) { 'http://example.com/my_other_life' }
|
68
|
+
let(:father) { RDF::URI.new('http://example.com/vader') }
|
69
|
+
|
70
|
+
before do
|
71
|
+
p = Person.new(saved_person.uri, graph_uri: graph_uri)
|
72
|
+
p.father = father
|
73
|
+
p.save!
|
74
|
+
end
|
75
|
+
|
76
|
+
it 'should leave those triples untouched' do
|
77
|
+
saved_person.name = 'Luke'
|
78
|
+
saved_person.save!
|
79
|
+
p = Person.find(saved_person.uri, graph_uri: graph_uri)
|
80
|
+
p.father.should == father
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
66
84
|
it 'runs the callbacks' do
|
67
85
|
unsaved_person.should_receive(:pre_save)
|
68
86
|
unsaved_person.save
|
@@ -95,7 +113,7 @@ describe Tripod::Persistence do
|
|
95
113
|
|
96
114
|
describe '.update_attribute' do
|
97
115
|
let (:person) { Person.new('http://example.com/newperson') }
|
98
|
-
|
116
|
+
|
99
117
|
context 'without transactions' do
|
100
118
|
before { person.stub(:save) }
|
101
119
|
|
@@ -136,7 +154,7 @@ describe Tripod::Persistence do
|
|
136
154
|
|
137
155
|
describe '.update_attributes' do
|
138
156
|
let (:person) { Person.new('http://example.com/newperson') }
|
139
|
-
|
157
|
+
|
140
158
|
context "without transactions" do
|
141
159
|
before { person.stub(:save) }
|
142
160
|
|
@@ -246,4 +264,4 @@ describe Tripod::Persistence do
|
|
246
264
|
|
247
265
|
end
|
248
266
|
|
249
|
-
end
|
267
|
+
end
|
data/tripod.gemspec
CHANGED
@@ -27,5 +27,6 @@ Gem::Specification.new do |gem|
|
|
27
27
|
gem.add_dependency "rdf-json"
|
28
28
|
gem.add_dependency "json-ld", "~> 0.9.1" # use v.0.9 for now, as v1.0 changes what is returned for dumping a resource to include other defined resources.
|
29
29
|
gem.add_dependency "guid"
|
30
|
-
gem.add_dependency "dalli", "~> 2.
|
30
|
+
gem.add_dependency "dalli", "~> 2.7.0"
|
31
|
+
gem.add_dependency "connection_pool", "~> 2.0.0"
|
31
32
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: tripod
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.9.
|
4
|
+
version: 0.9.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ric Roberts
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2014-06-
|
13
|
+
date: 2014-06-19 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: rest-client
|
@@ -144,14 +144,28 @@ dependencies:
|
|
144
144
|
requirements:
|
145
145
|
- - "~>"
|
146
146
|
- !ruby/object:Gem::Version
|
147
|
-
version:
|
147
|
+
version: 2.7.0
|
148
148
|
type: :runtime
|
149
149
|
prerelease: false
|
150
150
|
version_requirements: !ruby/object:Gem::Requirement
|
151
151
|
requirements:
|
152
152
|
- - "~>"
|
153
153
|
- !ruby/object:Gem::Version
|
154
|
-
version:
|
154
|
+
version: 2.7.0
|
155
|
+
- !ruby/object:Gem::Dependency
|
156
|
+
name: connection_pool
|
157
|
+
requirement: !ruby/object:Gem::Requirement
|
158
|
+
requirements:
|
159
|
+
- - "~>"
|
160
|
+
- !ruby/object:Gem::Version
|
161
|
+
version: 2.0.0
|
162
|
+
type: :runtime
|
163
|
+
prerelease: false
|
164
|
+
version_requirements: !ruby/object:Gem::Requirement
|
165
|
+
requirements:
|
166
|
+
- - "~>"
|
167
|
+
- !ruby/object:Gem::Version
|
168
|
+
version: 2.0.0
|
155
169
|
description: RDF ruby ORM
|
156
170
|
email:
|
157
171
|
- ric@swirrl.com
|
@@ -192,6 +206,7 @@ files:
|
|
192
206
|
- lib/tripod/fields.rb
|
193
207
|
- lib/tripod/fields/standard.rb
|
194
208
|
- lib/tripod/finders.rb
|
209
|
+
- lib/tripod/graphs.rb
|
195
210
|
- lib/tripod/locale/en.yml
|
196
211
|
- lib/tripod/persistence.rb
|
197
212
|
- lib/tripod/predicates.rb
|
@@ -214,6 +229,8 @@ files:
|
|
214
229
|
- spec/tripod/eager_loading_spec.rb
|
215
230
|
- spec/tripod/fields_spec.rb
|
216
231
|
- spec/tripod/finders_spec.rb
|
232
|
+
- spec/tripod/graphs_spec.rb
|
233
|
+
- spec/tripod/memcached_cache_store_spec.rb
|
217
234
|
- spec/tripod/persistence_spec.rb
|
218
235
|
- spec/tripod/predicates_spec.rb
|
219
236
|
- spec/tripod/repository_spec.rb
|
@@ -258,6 +275,8 @@ test_files:
|
|
258
275
|
- spec/tripod/eager_loading_spec.rb
|
259
276
|
- spec/tripod/fields_spec.rb
|
260
277
|
- spec/tripod/finders_spec.rb
|
278
|
+
- spec/tripod/graphs_spec.rb
|
279
|
+
- spec/tripod/memcached_cache_store_spec.rb
|
261
280
|
- spec/tripod/persistence_spec.rb
|
262
281
|
- spec/tripod/predicates_spec.rb
|
263
282
|
- spec/tripod/repository_spec.rb
|