perobs 4.1.0 → 4.2.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 +5 -5
- data/lib/perobs/BTree.rb +33 -13
- data/lib/perobs/BTreeBlob.rb +3 -2
- data/lib/perobs/BTreeDB.rb +4 -3
- data/lib/perobs/BTreeNode.rb +107 -78
- data/lib/perobs/BTreeNodeLink.rb +10 -0
- data/lib/perobs/BigArray.rb +19 -1
- data/lib/perobs/BigArrayNode.rb +13 -9
- data/lib/perobs/BigHash.rb +8 -24
- data/lib/perobs/BigTree.rb +14 -1
- data/lib/perobs/BigTreeNode.rb +2 -2
- data/lib/perobs/Cache.rb +31 -6
- data/lib/perobs/EquiBlobsFile.rb +12 -1
- data/lib/perobs/FlatFile.rb +197 -45
- data/lib/perobs/FlatFileBlobHeader.rb +20 -5
- data/lib/perobs/FlatFileDB.rb +8 -4
- data/lib/perobs/FuzzyStringMatcher.rb +192 -0
- data/lib/perobs/Hash.rb +4 -0
- data/lib/perobs/IDListPageFile.rb +1 -2
- data/lib/perobs/ObjectBase.rb +1 -1
- data/lib/perobs/PersistentObjectCache.rb +7 -4
- data/lib/perobs/SpaceManager.rb +273 -0
- data/lib/perobs/SpaceTree.rb +1 -1
- data/lib/perobs/Store.rb +67 -25
- data/lib/perobs/version.rb +1 -1
- data/perobs.gemspec +2 -2
- data/test/BTree_spec.rb +1 -0
- data/test/BigArray_spec.rb +53 -6
- data/test/BigHash_spec.rb +8 -0
- data/test/FlatFileDB_spec.rb +108 -3
- data/test/FuzzyStringMatcher_spec.rb +171 -0
- data/test/LegacyDBs/LegacyDB.rb +4 -0
- data/test/SpaceManager_spec.rb +176 -0
- data/test/Store_spec.rb +2 -5
- metadata +12 -6
@@ -0,0 +1,171 @@
|
|
1
|
+
# encoding: UTF-8
|
2
|
+
#
|
3
|
+
# Copyright (c) 2020 by Chris Schlaeger <chris@taskjuggler.org>
|
4
|
+
#
|
5
|
+
# MIT License
|
6
|
+
#
|
7
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
8
|
+
# a copy of this software and associated documentation files (the
|
9
|
+
# "Software"), to deal in the Software without restriction, including
|
10
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
11
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
12
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
13
|
+
# the following conditions:
|
14
|
+
#
|
15
|
+
# The above copyright notice and this permission notice shall be
|
16
|
+
# included in all copies or substantial portions of the Software.
|
17
|
+
#
|
18
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
19
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
20
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
21
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
22
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
23
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
24
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
25
|
+
|
26
|
+
require 'spec_helper'
|
27
|
+
require 'perobs/Store'
|
28
|
+
require 'perobs/FuzzyStringMatcher'
|
29
|
+
|
30
|
+
module PEROBS
|
31
|
+
|
32
|
+
describe FuzzyStringMatcher do
|
33
|
+
|
34
|
+
before(:all) do
|
35
|
+
@db_name = generate_db_name(__FILE__)
|
36
|
+
@store = PEROBS::Store.new(@db_name)
|
37
|
+
@fsm = FuzzyStringMatcher.new(@store, 'test')
|
38
|
+
@fsm2 = FuzzyStringMatcher.new(@store, 'test', true, 2)
|
39
|
+
end
|
40
|
+
|
41
|
+
after(:all) do
|
42
|
+
@store.delete_store
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'should have no matches for empty dict' do
|
46
|
+
expect(@fsm.best_matches('foobar')).to eql([])
|
47
|
+
expect(stats = @fsm.stats).not_to be_nil
|
48
|
+
expect(stats['dictionary_size']).to eql(0)
|
49
|
+
expect(stats['max_list_size']).to eql(0)
|
50
|
+
expect(stats['avg_list_size']).to eql(0)
|
51
|
+
end
|
52
|
+
|
53
|
+
it 'should learn a word' do
|
54
|
+
@fsm.learn('kindergarten')
|
55
|
+
expect(stats = @fsm.stats).not_to be_nil
|
56
|
+
expect(stats['dictionary_size']).to eql(11)
|
57
|
+
expect(stats['max_list_size']).to eql(1)
|
58
|
+
expect(stats['avg_list_size']).to eql(1.0)
|
59
|
+
end
|
60
|
+
|
61
|
+
it 'should clear the dictionary' do
|
62
|
+
@fsm.clear
|
63
|
+
expect(stats = @fsm.stats).not_to be_nil
|
64
|
+
expect(stats['dictionary_size']).to eql(0)
|
65
|
+
expect(stats['max_list_size']).to eql(0)
|
66
|
+
expect(stats['avg_list_size']).to eql(0)
|
67
|
+
end
|
68
|
+
|
69
|
+
it 'should learn some words' do
|
70
|
+
%w( one two three four five six seven eight nine ten
|
71
|
+
eleven twelve thirteen fourteen fifteen sixteen
|
72
|
+
seventeen eighteen nineteen twenty ).each do |w|
|
73
|
+
@fsm.learn(w, w)
|
74
|
+
end
|
75
|
+
expect(stats = @fsm.stats).not_to be_nil
|
76
|
+
expect(stats['dictionary_size']).to eql(65)
|
77
|
+
expect(stats['max_list_size']).to eql(7)
|
78
|
+
expect(stats['avg_list_size']).to be_within(0.001).of(1.415)
|
79
|
+
end
|
80
|
+
|
81
|
+
it 'should find a match' do
|
82
|
+
dut = {
|
83
|
+
[ 'one' ] => [ [ 'one', 1.0 ] ],
|
84
|
+
[ 'three' ] => [ [ 'three', 1.0 ] ],
|
85
|
+
[ 'four' ]=> [ [ 'four', 1.0 ], [ 'fourteen', 0.666 ] ],
|
86
|
+
[ 'four', 1.0 ]=> [ [ 'four', 1.0 ] ],
|
87
|
+
[ 'even' ] => [ [ 'seven', 0.666 ], [ 'eleven', 0.666 ] ],
|
88
|
+
[ 'teen' ] => [ ['thirteen', 0.6666666666666666],
|
89
|
+
['fourteen', 0.6666666666666666],
|
90
|
+
['fifteen', 0.6666666666666666],
|
91
|
+
['sixteen', 0.6666666666666666],
|
92
|
+
['seventeen', 0.6666666666666666],
|
93
|
+
['eighteen', 0.6666666666666666],
|
94
|
+
['nineteen', 0.6666666666666666] ],
|
95
|
+
[ 'aight' ] => [ [ 'eight', 0.5 ] ],
|
96
|
+
[ 'thirdteen' ] => [ [ 'thirteen', 0.5 ] ],
|
97
|
+
[ 'shirt teen', 0.3 ] => [ [ 'thirteen', 0.333 ] ]
|
98
|
+
}
|
99
|
+
check_data_under_test(@fsm, dut)
|
100
|
+
end
|
101
|
+
|
102
|
+
it 'should not find an unknown match' do
|
103
|
+
expect(@fsm.best_matches('foobar')).to eql([])
|
104
|
+
end
|
105
|
+
|
106
|
+
it 'should handle a larger text' do
|
107
|
+
text =<<-EOT
|
108
|
+
MIT License
|
109
|
+
|
110
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
111
|
+
a copy of this software and associated documentation files (the
|
112
|
+
"Software"), to deal in the Software without restriction, including
|
113
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
114
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
115
|
+
permit persons to whom the Software is furnished to do so, subject to
|
116
|
+
the following conditions:
|
117
|
+
|
118
|
+
The above copyright notice and this permission notice shall be
|
119
|
+
included in all copies or substantial portions of the Software.
|
120
|
+
|
121
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
122
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
123
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
124
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
125
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
126
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
127
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
128
|
+
EOT
|
129
|
+
|
130
|
+
text.split.each do |word|
|
131
|
+
@fsm2.learn(word, word)
|
132
|
+
end
|
133
|
+
stats = @fsm2.stats
|
134
|
+
expect(stats['dictionary_size']).to eql(363)
|
135
|
+
expect(stats['max_list_size']).to eql(22)
|
136
|
+
expect(stats['avg_list_size']).to be_within(0.001).of(2.366)
|
137
|
+
end
|
138
|
+
|
139
|
+
it 'should find case sensitive matches' do
|
140
|
+
dut = {
|
141
|
+
[ 'SOFTWARE', 0.5, 20 ] => [ [ 'SOFTWARE', 1.0 ], [ 'SOFTWARE.', 0.888 ] ],
|
142
|
+
[ 'three', 0.5, 20 ] => [ [ 'the', 0.5 ], [ 'free', 0.5 ] ]
|
143
|
+
}
|
144
|
+
|
145
|
+
check_data_under_test(@fsm2, dut)
|
146
|
+
end
|
147
|
+
|
148
|
+
def check_data_under_test(fsm, dut)
|
149
|
+
dut.each do |inputs, reference|
|
150
|
+
key = inputs[0]
|
151
|
+
results = fsm.best_matches(*inputs)
|
152
|
+
|
153
|
+
expect(results.length).to eql(reference.length),
|
154
|
+
"Wrong number of results for '#{key}': \n#{results}\n#{reference}"
|
155
|
+
|
156
|
+
reference.each do |key, rating|
|
157
|
+
match = results.find { |v| v[0] == key}
|
158
|
+
expect(match).not_to be_nil,
|
159
|
+
"result is missing key #{key}: #{results}"
|
160
|
+
expect(match[0]).to eql(key),
|
161
|
+
"Wrong match returned for key #{key}: #{match}"
|
162
|
+
expect(match[1]).to be_within(0.001).of(rating),
|
163
|
+
"Wrong rating returend for key #{key}: #{match}"
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
end
|
169
|
+
|
170
|
+
end
|
171
|
+
|
data/test/LegacyDBs/LegacyDB.rb
CHANGED
@@ -0,0 +1,176 @@
|
|
1
|
+
# encoding: UTF-8
|
2
|
+
#
|
3
|
+
# Copyright (c) 2020 by Chris Schlaeger <chris@taskjuggler.org>
|
4
|
+
#
|
5
|
+
# MIT License
|
6
|
+
#
|
7
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
8
|
+
# a copy of this software and associated documentation files (the
|
9
|
+
# "Software"), to deal in the Software without restriction, including
|
10
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
11
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
12
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
13
|
+
# the following conditions:
|
14
|
+
#
|
15
|
+
# The above copyright notice and this permission notice shall be
|
16
|
+
# included in all copies or substantial portions of the Software.
|
17
|
+
#
|
18
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
19
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
20
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
21
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
22
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
23
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
24
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
25
|
+
|
26
|
+
require 'fileutils'
|
27
|
+
|
28
|
+
require 'spec_helper'
|
29
|
+
require 'perobs/SpaceManager'
|
30
|
+
require 'perobs/ProgressMeter'
|
31
|
+
|
32
|
+
describe PEROBS::SpaceManager do
|
33
|
+
|
34
|
+
before(:all) do
|
35
|
+
@db_dir = generate_db_name('SpaceManager')
|
36
|
+
FileUtils.mkdir_p(@db_dir)
|
37
|
+
@m = PEROBS::SpaceManager.new(@db_dir, PEROBS::ProgressMeter.new, 5)
|
38
|
+
PEROBS.log.level = Logger::ERROR
|
39
|
+
PEROBS.log.open($stderr)
|
40
|
+
end
|
41
|
+
|
42
|
+
after(:all) do
|
43
|
+
FileUtils.rm_rf(@db_dir)
|
44
|
+
end
|
45
|
+
|
46
|
+
it 'should open the space manager' do
|
47
|
+
@m.open
|
48
|
+
expect(@m.to_a).to eql([])
|
49
|
+
end
|
50
|
+
|
51
|
+
it 'should support adding spaces' do
|
52
|
+
@m.add_space(80, 8)
|
53
|
+
expect(@m.has_space?(80, 8)).to be true
|
54
|
+
expect(@m.to_a).to eql([[80, 8]])
|
55
|
+
expect(@m.check).to be true
|
56
|
+
@m.add_space(40, 4)
|
57
|
+
expect(@m.has_space?(40, 4)).to be true
|
58
|
+
expect(@m.to_a).to eql([[40, 4], [80, 8]])
|
59
|
+
@m.add_space(20, 2)
|
60
|
+
expect(@m.has_space?(20, 2)).to be true
|
61
|
+
expect(@m.to_a).to eql([[20, 2], [40, 4], [80, 8]])
|
62
|
+
@m.add_space(160, 16)
|
63
|
+
expect(@m.has_space?(160, 16)).to be true
|
64
|
+
expect(@m.to_a).to eql([[20, 2], [40, 4], [80, 8], [160, 16]])
|
65
|
+
@m.add_space(320, 32)
|
66
|
+
expect(@m.has_space?(320, 32)).to be true
|
67
|
+
expect(@m.to_a).to eql([[20, 2], [40, 4], [80, 8], [160, 16], [320, 32]])
|
68
|
+
@m.add_space(100, 10)
|
69
|
+
expect(@m.has_space?(100, 10)).to be true
|
70
|
+
expect(@m.to_a).to eql([[20, 2], [40, 4], [80, 8], [100, 10], [160, 16], [320, 32]])
|
71
|
+
@m.add_space(81, 8)
|
72
|
+
expect(@m.has_space?(81, 8)).to be true
|
73
|
+
expect(@m.to_a).to eql([[20, 2], [40, 4], [80, 8], [81, 8], [100, 10], [160, 16], [320, 32]])
|
74
|
+
expect(@m.check).to be true
|
75
|
+
end
|
76
|
+
|
77
|
+
it 'should keep values over an close/open' do
|
78
|
+
@m.add_space(1, 15)
|
79
|
+
expect(@m.check).to be true
|
80
|
+
@m.close
|
81
|
+
@m.open
|
82
|
+
expect(@m.check).to be true
|
83
|
+
expect(@m.to_a).to eql([[1, 15], [20, 2], [40, 4], [80, 8], [81, 8], [100, 10], [160, 16], [320, 32]])
|
84
|
+
end
|
85
|
+
|
86
|
+
it 'should support clearing all spaces' do
|
87
|
+
@m.clear
|
88
|
+
expect(@m.to_a).to eql([])
|
89
|
+
@m.add_space(1, 1)
|
90
|
+
@m.add_space(2, 2)
|
91
|
+
@m.clear
|
92
|
+
expect(@m.to_a).to eql([])
|
93
|
+
end
|
94
|
+
|
95
|
+
it 'should return exactly matching spaces' do
|
96
|
+
@m.clear
|
97
|
+
add_sizes([ 10, 5, 15, 10 ])
|
98
|
+
expect(@m.to_a).to eql([[0, 10], [1, 5], [2, 15], [3, 10]])
|
99
|
+
expect(@m.get_space(10)).to eql([3, 10])
|
100
|
+
expect(@m.get_space(10)).to eql([0, 10])
|
101
|
+
expect(@m.to_a).to eql([[1, 5], [2, 15]])
|
102
|
+
expect(@m.added_spaces).to eql(4)
|
103
|
+
expect(@m.recycled_spaces).to eql(2)
|
104
|
+
expect(@m.failed_requests).to eql(0)
|
105
|
+
|
106
|
+
@m.clear
|
107
|
+
add_sizes([ 10, 5, 15, 10, 10 ])
|
108
|
+
expect(@m.to_a).to eql([[0, 10], [1, 5], [2, 15], [3, 10], [4, 10]])
|
109
|
+
expect(@m.get_space(10)).to eql([4, 10])
|
110
|
+
expect(@m.get_space(10)).to eql([3, 10])
|
111
|
+
expect(@m.get_space(10)).to eql([0, 10])
|
112
|
+
expect(@m.to_a).to eql([[1, 5], [2, 15]])
|
113
|
+
expect(@m.added_spaces).to eql(5)
|
114
|
+
expect(@m.recycled_spaces).to eql(3)
|
115
|
+
expect(@m.failed_requests).to eql(0)
|
116
|
+
end
|
117
|
+
|
118
|
+
it "should return nil if no space can be found" do
|
119
|
+
expect(@m.get_space(42)).to be nil
|
120
|
+
expect(@m.get_space(9)).to be nil
|
121
|
+
expect(@m.get_space(11)).to be nil
|
122
|
+
expect(@m.recycled_spaces).to eql(3)
|
123
|
+
expect(@m.failed_requests).to eql(3)
|
124
|
+
end
|
125
|
+
|
126
|
+
it 'should support a real-world traffic pattern' do
|
127
|
+
address = 0
|
128
|
+
spaces = []
|
129
|
+
@m.clear
|
130
|
+
0.upto(1500) do
|
131
|
+
case rand(4)
|
132
|
+
when 0
|
133
|
+
# Insert new values
|
134
|
+
rand(9).times do
|
135
|
+
size = 20 + rand(80)
|
136
|
+
@m.add_space(address, size)
|
137
|
+
spaces << [ address, size ]
|
138
|
+
address += size
|
139
|
+
end
|
140
|
+
when 1
|
141
|
+
# Remove some values
|
142
|
+
rand(7).times do
|
143
|
+
size = rand(110)
|
144
|
+
if (space = @m.get_space(size))
|
145
|
+
expect(spaces.include?(space)).to be true
|
146
|
+
spaces.delete(space)
|
147
|
+
end
|
148
|
+
end
|
149
|
+
when 2
|
150
|
+
if rand(10) == 0
|
151
|
+
expect(@m.check).to be true
|
152
|
+
spaces.each do |address, size|
|
153
|
+
expect(@m.has_space?(address, size)).to be true
|
154
|
+
end
|
155
|
+
@m.to_a.each do |address, size|
|
156
|
+
expect(spaces.include?([ address, size ])).to be true
|
157
|
+
end
|
158
|
+
end
|
159
|
+
when 3
|
160
|
+
if rand(200) == 0
|
161
|
+
expect(@m.check).to be true
|
162
|
+
@m.close
|
163
|
+
@m.open
|
164
|
+
expect(@m.check).to be true
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|
168
|
+
end
|
169
|
+
|
170
|
+
def add_sizes(sizes)
|
171
|
+
sizes.each_with_index do |size, i|
|
172
|
+
@m.add_space(i, size)
|
173
|
+
end
|
174
|
+
end
|
175
|
+
|
176
|
+
end
|
data/test/Store_spec.rb
CHANGED
@@ -271,7 +271,6 @@ describe PEROBS::Store do
|
|
271
271
|
capture_io { expect(store.gc).to eq(0) }
|
272
272
|
p0 = p1 = p2 = nil
|
273
273
|
capture_io { store.exit }
|
274
|
-
GC.start
|
275
274
|
store = PEROBS::Store.new(@db_file)
|
276
275
|
expect(store['person0']._id).to eq(id0)
|
277
276
|
expect(store['person0'].related._id).to eq(id1)
|
@@ -279,9 +278,8 @@ describe PEROBS::Store do
|
|
279
278
|
|
280
279
|
store['person0'].related = nil
|
281
280
|
capture_io { expect(store.gc).to eq(2) }
|
282
|
-
|
283
|
-
expect(
|
284
|
-
expect(store.object_by_id(id2)).to be_nil
|
281
|
+
stats = store.statistics
|
282
|
+
expect(stats.swept_objects).to eql(2)
|
285
283
|
capture_io { store.exit }
|
286
284
|
|
287
285
|
store = PEROBS::Store.new(@db_file)
|
@@ -494,7 +492,6 @@ describe PEROBS::Store do
|
|
494
492
|
# We have the root hash and the Person object.
|
495
493
|
expect(store.statistics[:in_memory_objects]).to eq(2)
|
496
494
|
store.sync
|
497
|
-
GC.start
|
498
495
|
# Now the Person should be gone from memory.
|
499
496
|
# Ruby 2.3 and later has changed the GC so that this does not work
|
500
497
|
# reliably anymore. The GC seems to operate lazyly.
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: perobs
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 4.
|
4
|
+
version: 4.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Chris Schlaeger
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2020-05-02 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -44,14 +44,14 @@ dependencies:
|
|
44
44
|
requirements:
|
45
45
|
- - "~>"
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version:
|
47
|
+
version: 12.3.3
|
48
48
|
type: :development
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
52
|
- - "~>"
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version:
|
54
|
+
version: 12.3.3
|
55
55
|
description: Library to provide a persistent object store
|
56
56
|
email:
|
57
57
|
- chris@linux.com
|
@@ -87,6 +87,7 @@ files:
|
|
87
87
|
- lib/perobs/FlatFile.rb
|
88
88
|
- lib/perobs/FlatFileBlobHeader.rb
|
89
89
|
- lib/perobs/FlatFileDB.rb
|
90
|
+
- lib/perobs/FuzzyStringMatcher.rb
|
90
91
|
- lib/perobs/Handle.rb
|
91
92
|
- lib/perobs/Hash.rb
|
92
93
|
- lib/perobs/IDList.rb
|
@@ -101,6 +102,7 @@ files:
|
|
101
102
|
- lib/perobs/PersistentObjectCacheLine.rb
|
102
103
|
- lib/perobs/ProgressMeter.rb
|
103
104
|
- lib/perobs/RobustFile.rb
|
105
|
+
- lib/perobs/SpaceManager.rb
|
104
106
|
- lib/perobs/SpaceTree.rb
|
105
107
|
- lib/perobs/SpaceTreeNode.rb
|
106
108
|
- lib/perobs/SpaceTreeNodeLink.rb
|
@@ -123,6 +125,7 @@ files:
|
|
123
125
|
- test/EquiBlobsFile_spec.rb
|
124
126
|
- test/FNV_Hash_1a_64_spec.rb
|
125
127
|
- test/FlatFileDB_spec.rb
|
128
|
+
- test/FuzzyStringMatcher_spec.rb
|
126
129
|
- test/Hash_spec.rb
|
127
130
|
- test/IDList_spec.rb
|
128
131
|
- test/LegacyDBs/LegacyDB.rb
|
@@ -134,6 +137,7 @@ files:
|
|
134
137
|
- test/LegacyDBs/version_3/version
|
135
138
|
- test/LockFile_spec.rb
|
136
139
|
- test/Object_spec.rb
|
140
|
+
- test/SpaceManager_spec.rb
|
137
141
|
- test/SpaceTree_spec.rb
|
138
142
|
- test/StackFile_spec.rb
|
139
143
|
- test/Store_spec.rb
|
@@ -151,7 +155,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
151
155
|
requirements:
|
152
156
|
- - ">="
|
153
157
|
- !ruby/object:Gem::Version
|
154
|
-
version: '2.
|
158
|
+
version: '2.4'
|
155
159
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
156
160
|
requirements:
|
157
161
|
- - ">="
|
@@ -159,7 +163,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
159
163
|
version: '0'
|
160
164
|
requirements: []
|
161
165
|
rubyforge_project:
|
162
|
-
rubygems_version: 2.2
|
166
|
+
rubygems_version: 2.7.6.2
|
163
167
|
signing_key:
|
164
168
|
specification_version: 4
|
165
169
|
summary: Persistent Ruby Object Store
|
@@ -175,6 +179,7 @@ test_files:
|
|
175
179
|
- test/EquiBlobsFile_spec.rb
|
176
180
|
- test/FNV_Hash_1a_64_spec.rb
|
177
181
|
- test/FlatFileDB_spec.rb
|
182
|
+
- test/FuzzyStringMatcher_spec.rb
|
178
183
|
- test/Hash_spec.rb
|
179
184
|
- test/IDList_spec.rb
|
180
185
|
- test/LegacyDBs/LegacyDB.rb
|
@@ -186,6 +191,7 @@ test_files:
|
|
186
191
|
- test/LegacyDBs/version_3/version
|
187
192
|
- test/LockFile_spec.rb
|
188
193
|
- test/Object_spec.rb
|
194
|
+
- test/SpaceManager_spec.rb
|
189
195
|
- test/SpaceTree_spec.rb
|
190
196
|
- test/StackFile_spec.rb
|
191
197
|
- test/Store_spec.rb
|