hyperactive 0.2.2 → 0.2.3

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.
data/tests/list_test.rb CHANGED
@@ -1,6 +1,14 @@
1
1
 
2
2
  require File.join(File.dirname(__FILE__), 'test_helper')
3
3
 
4
+ class Collector
5
+ attr_accessor :es
6
+ def call(e)
7
+ @es ||= []
8
+ @es << e
9
+ end
10
+ end
11
+
4
12
  class ListTest < Test::Unit::TestCase
5
13
 
6
14
  def setup
@@ -23,19 +31,69 @@ class ListTest < Test::Unit::TestCase
23
31
 
24
32
  def teardown
25
33
  @c.stop!
26
- @c.persistence_provider.unlink
34
+ @c.persistence_provider.unlink!
27
35
  @c2.stop!
28
- @c2.persistence_provider.unlink
36
+ @c2.persistence_provider.unlink!
29
37
  @tm.stop!
30
- @tm.persistence_provider.unlink
31
- Archipelago::Disco::MC.clear!
32
- Hyperactive::Record::CAPTAIN.update_services!
33
- assert_within(10) do
34
- Hyperactive::Record::CAPTAIN.chests.empty?
35
- end
36
- assert_within(10) do
37
- Hyperactive::Record::CAPTAIN.trannies.empty?
38
- end
38
+ @tm.persistence_provider.unlink!
39
+ end
40
+
41
+ def test_clear
42
+ l = Hyperactive::List::Head.get_instance
43
+ l << (r = Hyperactive::Record::Bass.get_instance)
44
+ assert_equal(1, l.size)
45
+ assert_equal(r, l.first)
46
+ assert_equal(r, l.last)
47
+ l.clear!
48
+ assert_equal(0, l.size)
49
+ assert_equal(nil, l.first)
50
+ assert_equal(nil, l.last)
51
+ end
52
+
53
+ def test_destroy
54
+ l = Hyperactive::List::Head.get_instance
55
+ l << (r = Hyperactive::Record::Bass.get_instance)
56
+ r1 = l.first_element.record_id
57
+ r2 = l.record_id
58
+ l.destroy!
59
+ assert(!Hyperactive::Record::CAPTAIN.include?(r1))
60
+ assert(!Hyperactive::Record::CAPTAIN.include?(r2))
61
+ end
62
+
63
+ def test_each
64
+ l = Hyperactive::List::Head.get_instance
65
+ l << (r = Hyperactive::Record::Bass.get_instance)
66
+ l << (r2 = Hyperactive::Record::Bass.get_instance)
67
+ l << (r3 = Hyperactive::Record::Bass.get_instance)
68
+ c = Collector.new
69
+ l.t_each(c)
70
+ assert_equal(3, c.es.size)
71
+ assert(c.es.include?(r))
72
+ assert(c.es.include?(r2))
73
+ assert(c.es.include?(r3))
74
+ end
75
+
76
+ def test_unlink
77
+ l = Hyperactive::List::Head.get_instance
78
+ l << (r = Hyperactive::Record::Bass.get_instance)
79
+ l << (r2 = Hyperactive::Record::Bass.get_instance)
80
+ e = l.last_element
81
+ l << (r3 = Hyperactive::Record::Bass.get_instance)
82
+ assert_equal([r, r2, r3].sort, l.t_collect do |ec| ec end.sort)
83
+ l.unlink!(e)
84
+ assert_equal(2, l.size)
85
+ assert_equal(r, l.first)
86
+ assert_equal(r3, l.last)
87
+ assert_equal(r3, l.first_element.next.value)
88
+ l.unlink!(l.last_element)
89
+ assert_equal(1, l.size)
90
+ assert_equal(r, l.first)
91
+ assert_equal(r, l.last)
92
+ l.unlink!(l.first_element)
93
+ assert_equal(0, l.size)
94
+ assert_equal(nil, l.first)
95
+ assert_equal(nil, l.last)
96
+ assert_equal([], l.t_collect do |e| e end)
39
97
  end
40
98
 
41
99
  def test_push_unshift_pop_shift
data/tests/record_test.rb CHANGED
@@ -3,7 +3,9 @@ require File.join(File.dirname(__FILE__), 'test_helper')
3
3
 
4
4
  class MyRecord < Hyperactive::Record::Bass
5
5
  attr_accessor :bajs
6
-
6
+ def initialize
7
+ @bajs = nil
8
+ end
7
9
  def self.save_hook(instance, &block)
8
10
  $BEFORE_SAVE += 1
9
11
  yield
@@ -54,19 +56,11 @@ class RecordTest < Test::Unit::TestCase
54
56
 
55
57
  def teardown
56
58
  @c.stop!
57
- @c.persistence_provider.unlink
59
+ @c.persistence_provider.unlink!
58
60
  @c2.stop!
59
- @c2.persistence_provider.unlink
61
+ @c2.persistence_provider.unlink!
60
62
  @tm.stop!
61
- @tm.persistence_provider.unlink
62
- Archipelago::Disco::MC.clear!
63
- Hyperactive::Record::CAPTAIN.update_services!
64
- assert_within(10) do
65
- Hyperactive::Record::CAPTAIN.chests.empty?
66
- end
67
- assert_within(10) do
68
- Hyperactive::Record::CAPTAIN.trannies.empty?
69
- end
63
+ @tm.persistence_provider.unlink!
70
64
  end
71
65
 
72
66
  def test_index_find
@@ -82,18 +76,18 @@ class RecordTest < Test::Unit::TestCase
82
76
  r4 = MyRecord.get_instance
83
77
  r4.bajs = "beige"
84
78
 
85
- assert_equal(Set.new([r2.record_id,r1.record_id]), Set.new(MyRecord.find_by_bajs("brunt").collect(Proc.new do |k,v|
86
- v.record_id
87
- end)))
88
- assert_equal([r3.record_id], MyRecord.find_by_bajs("gult").collect(Proc.new do |k,v|
89
- v.record_id
90
- end))
79
+ assert_equal(Set.new([r2.record_id,r1.record_id]), Set.new(MyRecord.find_by_bajs("brunt").t_collect(Proc.new do |k,v|
80
+ v.record_id
81
+ end)))
82
+ assert_equal([r3.record_id], MyRecord.find_by_bajs("gult").t_collect(Proc.new do |k,v|
83
+ v.record_id
84
+ end))
91
85
 
92
- r1.destroy
86
+ r1.destroy!
93
87
 
94
- assert_equal([r2.record_id], MyRecord.find_by_bajs("brunt").collect(Proc.new do |k,v|
95
- v.record_id
96
- end))
88
+ assert_equal([r2.record_id], MyRecord.find_by_bajs("brunt").t_collect(Proc.new do |k,v|
89
+ v.record_id
90
+ end))
97
91
 
98
92
  end
99
93
 
@@ -115,22 +109,22 @@ class RecordTest < Test::Unit::TestCase
115
109
  r4 = MyRecord.get_instance
116
110
  r4.bajs = "beige"
117
111
 
118
- assert_equal(Set.new([r2.record_id,r1.record_id]), Set.new(MyRecord.brunt.collect(Proc.new do |k,v|
112
+ assert_equal(Set.new([r2.record_id,r1.record_id]), Set.new(MyRecord.brunt.t_collect(Proc.new do |k,v|
119
113
  v.record_id
120
114
  end)))
121
- assert_equal(Set.new([r3.record_id,r4.record_id]), Set.new(MyRecord.not_brunt.collect(Proc.new do |k,v|
115
+ assert_equal(Set.new([r3.record_id,r4.record_id]), Set.new(MyRecord.not_brunt.t_collect(Proc.new do |k,v|
122
116
  v.record_id
123
117
  end)))
124
118
 
125
- r1.destroy
126
- r2.destroy
127
- r3.destroy
128
- r4.destroy
119
+ r1.destroy!
120
+ r2.destroy!
121
+ r3.destroy!
122
+ r4.destroy!
129
123
 
130
- assert_equal(Set.new, Set.new(MyRecord.brunt.collect(Proc.new do |k,v|
124
+ assert_equal(Set.new, Set.new(MyRecord.brunt.t_collect(Proc.new do |k,v|
131
125
  v.record_id
132
126
  end)))
133
- assert_equal(Set.new, Set.new(MyRecord.not_brunt.collect(Proc.new do |k,v|
127
+ assert_equal(Set.new, Set.new(MyRecord.not_brunt.t_collect(Proc.new do |k,v|
134
128
  v.record_id
135
129
  end)))
136
130
  end
@@ -149,7 +143,7 @@ class RecordTest < Test::Unit::TestCase
149
143
  assert_equal("brunt", Hyperactive::Record::CAPTAIN[r.record_id].bajs)
150
144
  i = r.record_id
151
145
  assert_equal(r, Hyperactive::Record::CAPTAIN[i])
152
- r.destroy
146
+ r.destroy!
153
147
  assert_equal(1, $BEFORE_DESTROY)
154
148
  assert_equal(1, $AFTER_DESTROY)
155
149
  assert_equal(nil, Hyperactive::Record::CAPTAIN[i])
metadata CHANGED
@@ -3,8 +3,8 @@ rubygems_version: 0.8.11
3
3
  specification_version: 1
4
4
  name: hyperactive
5
5
  version: !ruby/object:Gem::Version
6
- version: 0.2.2
7
- date: 2006-11-28 00:00:00 +01:00
6
+ version: 0.2.3
7
+ date: 2006-11-29 00:00:00 +01:00
8
8
  summary: A base class for persistent objects that uses archipelago for persistence. Useful for Ruby on Rails models for example.
9
9
  require_paths:
10
10
  - lib
@@ -29,21 +29,22 @@ authors:
29
29
  - Martin Kihlgren
30
30
  files:
31
31
  - lib/hyperactive.rb
32
+ - lib/hyperactive/hash.rb
32
33
  - lib/hyperactive/hooker.rb
33
34
  - lib/hyperactive/list.rb
34
35
  - lib/hyperactive/record.rb
35
- - lib/hyperactive/tree.rb
36
+ - tests/hash_benchmark.rb
37
+ - tests/hash_test.rb
38
+ - tests/list_benchmark.rb
36
39
  - tests/list_test.rb
37
40
  - tests/record_test.rb
38
41
  - tests/test_helper.rb
39
- - tests/tree_benchmark.rb
40
- - tests/tree_test.rb
41
42
  - GPL-2
42
43
  - README
43
44
  test_files:
45
+ - tests/hash_test.rb
44
46
  - tests/list_test.rb
45
47
  - tests/record_test.rb
46
- - tests/tree_test.rb
47
48
  - tests/test_helper.rb
48
49
  rdoc_options:
49
50
  - --line-numbers
@@ -1,241 +0,0 @@
1
- # Archipelago - a distributed computing toolkit for ruby
2
- # Copyright (C) 2006 Martin Kihlgren <zond at troja dot ath dot cx>
3
- #
4
- # This program is free software; you can redistribute it and/or
5
- # modify it under the terms of the GNU General Public License
6
- # as published by the Free Software Foundation; either version 2
7
- # of the License, or (at your option) any later version.
8
- #
9
- # This program is distributed in the hope that it will be useful,
10
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
- # GNU General Public License for more details.
13
- #
14
- # You should have received a copy of the GNU General Public License
15
- # along with this program; if not, write to the Free Software
16
- # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17
-
18
-
19
- require 'rubygems'
20
- require 'archipelago'
21
- require 'rbtree'
22
-
23
- module Hyperactive
24
-
25
- #
26
- # The package containing the Hash-like Tree class that provides any
27
- # kind of index for your Hyperactive classes.
28
- #
29
- module Tree
30
-
31
- #
32
- # A class suitable for storing large and often-changing datasets in
33
- # an Archipelago environment.
34
- #
35
- # Is constructed like a set of nested Hashes that automatically create
36
- # new children on demand, and will thusly only have to check the path from
37
- # the root node to the leaf for changes when method calls return (see Archipelago::Treasure::Chest)
38
- # and will only have to actually store into database the leaf itself if it
39
- # has changed.
40
- #
41
- class Root < Hyperactive::Record::Bass
42
-
43
- attr_accessor :elements, :subtrees
44
-
45
- WIDTH = 1 << 3
46
-
47
- #
48
- # Dont call this! Call <i>Root.get_instance(options)</i> instead!
49
- #
50
- def initialize(options = {})
51
- @width = options[:width] || WIDTH
52
- @elements = {}
53
- @subtrees = nil
54
- end
55
-
56
- #
57
- # Deletes +key+ in this Root.
58
- #
59
- def delete(key)
60
- if @elements
61
- @elements.delete(key)
62
- else
63
- subtree_for(key).delete(key)
64
- end
65
- end
66
-
67
- #
68
- # Returns the size of this Root.
69
- #
70
- def size
71
- if @elements
72
- @elements.size
73
- else
74
- @subtrees.t_collect do |tree_id, tree|
75
- tree.size
76
- end.inject(0) do |sum, size|
77
- sum + size
78
- end
79
- end
80
- end
81
-
82
- #
83
- # Returns all keys and values returning true for +callable+.call(key, value) in this Root.
84
- #
85
- def select(callable)
86
- if @elements
87
- @elements.select do |k,v|
88
- callable.call(k,v)
89
- end
90
- else
91
- @subtrees.t_collect do |tree_id, tree|
92
- tree.select(callable)
93
- end.inject([]) do |sum, match|
94
- sum + match
95
- end
96
- end
97
- end
98
-
99
- #
100
- # Returns all keys and values returning false for +callable+.call(key, value) in this Root.
101
- #
102
- def reject(callable)
103
- if @elements
104
- @elements.reject do |k,v|
105
- callable.call(k,v)
106
- end
107
- else
108
- @subtrees.t_collect do |tree_id, tree|
109
- tree.reject(callable)
110
- end.inject([]) do |sum, match|
111
- sum + match
112
- end
113
- end
114
- end
115
-
116
- #
117
- # Puts +value+ under +key+ in this Root.
118
- #
119
- def []=(key, value)
120
- if @elements
121
- if @elements.size < @width
122
- @elements[key] = value
123
- else
124
- split!
125
- subtree_for(key)[key] = value
126
- end
127
- else
128
- subtree_for(key)[key] = value
129
- end
130
- return value
131
- end
132
-
133
- #
134
- # Returns the value for +key+ in this Root.
135
- #
136
- def [](key)
137
- if @elements
138
- return @elements[key]
139
- else
140
- return subtree_for(key)[key]
141
- end
142
- end
143
-
144
- #
145
- # Returns an Array containing +callable+.call(key, value) from all values in this Root.
146
- #
147
- def collect(callable)
148
- rval = []
149
- self.each(Proc.new do |k,v|
150
- rval << callable.call(k,v)
151
- end)
152
- return rval
153
- end
154
-
155
- #
156
- # Does +callable+.call(key, value) on all values in this Root.
157
- #
158
- def each(callable)
159
- if @elements
160
- @elements.each do |key, value|
161
- callable.call(key, value)
162
- end
163
- else
164
- @subtrees.t_each do |tree_id, tree|
165
- tree.each(callable)
166
- end
167
- nil
168
- end
169
- end
170
-
171
- #
172
- # Clear everything from this Tree and destroy it.
173
- #
174
- def destroy
175
- if @elements
176
- @elements.each do |key, value|
177
- value.destroy if value.respond_to?(:destroy)
178
- end
179
- else
180
- @subtrees.each do |tree_id, tree|
181
- tree.destroy
182
- end
183
- end
184
- freeze
185
- super
186
- end
187
-
188
- #
189
- # Clear everything from this Root.
190
- #
191
- def clear
192
- unless @elements
193
- @subtrees.each do |tree_id, tree|
194
- tree.clear
195
- end
196
- @subtrees = nil
197
- end
198
- @elements = {}
199
- end
200
-
201
- private
202
-
203
- #
204
- # Finds the subtree responsible for +key+.
205
- #
206
- # Does it in this ugly way cause the nice way of just doing modulo gave
207
- # really odd results since all hashes seem to give some modulo values
208
- # a lot more often than expected.
209
- #
210
- def subtree_for(key)
211
- key_id = Digest::SHA1.new("#{key.hash}#{self.record_id}").to_s
212
- @subtrees.each do |tree_id, tree|
213
- return tree if tree_id > key_id
214
- end
215
- return @subtrees.values.first
216
- end
217
-
218
- #
219
- # Split this Tree by creating @subtrees,
220
- # then putting all @elements in them and then emptying @elements.
221
- #
222
- def split!
223
- raise "Cant split twice!" unless @elements
224
-
225
- @subtrees = RBTree.new
226
- @subtrees.extend(Archipelago::Current::ThreadedCollection)
227
- step = (1 << 160) / @width
228
- 0.upto(@width - 1) do |n|
229
- @subtrees["%x" % (n * step)] = Root.get_instance(:width => @width)
230
- end
231
- @elements.each do |key, value|
232
- subtree_for(key)[key] = value
233
- end
234
- @elements = nil
235
- end
236
-
237
- end
238
-
239
- end
240
-
241
- end