wref 0.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,5 @@
1
+ lib/**/*.rb
2
+ bin/*
3
+ -
4
+ features/**/*.feature
5
+ LICENSE.txt
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --color
data/Gemfile ADDED
@@ -0,0 +1,13 @@
1
+ source "http://rubygems.org"
2
+ # Add dependencies required to use your gem here.
3
+ # Example:
4
+ # gem "activesupport", ">= 2.3.5"
5
+
6
+ # Add dependencies to develop your gem here.
7
+ # Include everything needed to run rake, tests, features, etc.
8
+ group :development do
9
+ gem "rspec", "~> 2.8.0"
10
+ gem "rdoc", "~> 3.12"
11
+ gem "bundler", ">= 1.0.0"
12
+ gem "jeweler", "~> 1.8.3"
13
+ end
@@ -0,0 +1,31 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ diff-lcs (1.1.3)
5
+ git (1.2.5)
6
+ jeweler (1.8.3)
7
+ bundler (~> 1.0)
8
+ git (>= 1.2.5)
9
+ rake
10
+ rdoc
11
+ json (1.7.1)
12
+ rake (0.9.2.2)
13
+ rdoc (3.12)
14
+ json (~> 1.4)
15
+ rspec (2.8.0)
16
+ rspec-core (~> 2.8.0)
17
+ rspec-expectations (~> 2.8.0)
18
+ rspec-mocks (~> 2.8.0)
19
+ rspec-core (2.8.0)
20
+ rspec-expectations (2.8.0)
21
+ diff-lcs (~> 1.1.2)
22
+ rspec-mocks (2.8.0)
23
+
24
+ PLATFORMS
25
+ ruby
26
+
27
+ DEPENDENCIES
28
+ bundler (>= 1.0.0)
29
+ jeweler (~> 1.8.3)
30
+ rdoc (~> 3.12)
31
+ rspec (~> 2.8.0)
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2012 Kasper Johansen
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,19 @@
1
+ = wref
2
+
3
+ Description goes here.
4
+
5
+ == Contributing to wref
6
+
7
+ * Check out the latest master to make sure the feature hasn't been implemented or the bug hasn't been fixed yet.
8
+ * Check out the issue tracker to make sure someone already hasn't requested it and/or contributed it.
9
+ * Fork the project.
10
+ * Start a feature/bugfix branch.
11
+ * Commit and push until you are happy with your contribution.
12
+ * Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.
13
+ * Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.
14
+
15
+ == Copyright
16
+
17
+ Copyright (c) 2012 Kasper Johansen. See LICENSE.txt for
18
+ further details.
19
+
@@ -0,0 +1,49 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+ require 'bundler'
5
+ begin
6
+ Bundler.setup(:default, :development)
7
+ rescue Bundler::BundlerError => e
8
+ $stderr.puts e.message
9
+ $stderr.puts "Run `bundle install` to install missing gems"
10
+ exit e.status_code
11
+ end
12
+ require 'rake'
13
+
14
+ require 'jeweler'
15
+ Jeweler::Tasks.new do |gem|
16
+ # gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
17
+ gem.name = "wref"
18
+ gem.homepage = "http://github.com/kaspernj/wref"
19
+ gem.license = "MIT"
20
+ gem.summary = %Q{Weak references and weak hash for Ruby}
21
+ gem.description = %Q{Lightweight weak reference and weak hash that works in 1.9 and JRuby.}
22
+ gem.email = "k@spernj.org"
23
+ gem.authors = ["Kasper Johansen"]
24
+ # dependencies defined in Gemfile
25
+ end
26
+ Jeweler::RubygemsDotOrgTasks.new
27
+
28
+ require 'rspec/core'
29
+ require 'rspec/core/rake_task'
30
+ RSpec::Core::RakeTask.new(:spec) do |spec|
31
+ spec.pattern = FileList['spec/**/*_spec.rb']
32
+ end
33
+
34
+ RSpec::Core::RakeTask.new(:rcov) do |spec|
35
+ spec.pattern = 'spec/**/*_spec.rb'
36
+ spec.rcov = true
37
+ end
38
+
39
+ task :default => :spec
40
+
41
+ require 'rdoc/task'
42
+ Rake::RDocTask.new do |rdoc|
43
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
44
+
45
+ rdoc.rdoc_dir = 'rdoc'
46
+ rdoc.title = "wref #{version}"
47
+ rdoc.rdoc_files.include('README*')
48
+ rdoc.rdoc_files.include('lib/**/*.rb')
49
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.0.0
@@ -0,0 +1,251 @@
1
+ #A simple weak-reference framework with mapping. Only handles the referencing of objects.
2
+ #===Examples
3
+ # user_obj = ob.get(:User, 1)
4
+ # weak_ref = Wref(user_obj)
5
+ # user_obj = nil
6
+ # sleep 0.5
7
+ # GC.start
8
+ #
9
+ # begin
10
+ # user_obj = weak_ref.get
11
+ # print "The user still exists in memory and has ID #{user.id}."
12
+ # rescue Wref::Recycled
13
+ # print "The user has been removed from memory."
14
+ # end
15
+ class Wref
16
+ #Returns the classname of the object.
17
+ attr_reader :class_name
18
+
19
+ #Returns the object-ID which is used to look up the ObjectSpace (if not running JRuby).
20
+ attr_reader :id
21
+
22
+ #Initializes various variables.
23
+ def initialize(obj)
24
+ @id = obj.__id__
25
+
26
+ if RUBY_ENGINE == "jruby"
27
+ require "java"
28
+ @weakref = java.lang.ref.WeakReference.new(obj)
29
+ else
30
+ @class_name = obj.class.name.to_sym
31
+
32
+ if obj.respond_to?("__object_unique_id__")
33
+ @unique_id = obj.__object_unique_id__
34
+ end
35
+ end
36
+ end
37
+
38
+ #Returns the object that this weak reference holds or raises Wref::Recycled.
39
+ # begin
40
+ # obj = wref.get
41
+ # print "Object still exists in memory."
42
+ # rescue Wref::Recycled
43
+ # print "Object has been garbage-collected."
44
+ # end
45
+ def get
46
+ begin
47
+ raise Wref::Recycled if !@class_name or !@id
48
+
49
+ if RUBY_ENGINE == "jruby"
50
+ obj = @weakref.get
51
+
52
+ if obj == nil
53
+ raise Wref::Recycled
54
+ else
55
+ return obj
56
+ end
57
+ else
58
+ obj = ObjectSpace._id2ref(@id)
59
+ end
60
+
61
+ #Some times this class-name will be nil for some reason - knj
62
+ obj_class_name = obj.class.name
63
+
64
+ if !obj_class_name or @class_name != obj_class_name.to_sym or @id != obj.__id__
65
+ raise Wref::Recycled
66
+ end
67
+
68
+ if @unique_id
69
+ if !obj.respond_to?("__object_unique_id__") or obj.__object_unique_id__ != @unique_id
70
+ raise Wref::Recycled
71
+ end
72
+ end
73
+
74
+ return obj
75
+ rescue RangeError, TypeError
76
+ raise Wref::Recycled
77
+ end
78
+ end
79
+
80
+ #Returns true if the reference is still alive.
81
+ # print "The object still exists in memory." if wref.alive?
82
+ def alive?
83
+ begin
84
+ self.get
85
+ return true
86
+ rescue Wref::Recycled
87
+ return false
88
+ end
89
+ end
90
+
91
+ #Makes Wref compatible with the normal WeakRef.
92
+ alias weakref_alive? alive?
93
+ alias __getobj__ get
94
+ end
95
+
96
+ #A weak hash-map.
97
+ #===Examples
98
+ # map = Wref_map.new
99
+ # map[1] = obj
100
+ # obj = nil
101
+ #
102
+ # sleep 0.5
103
+ #
104
+ # begin
105
+ # obj = map[1]
106
+ # print "Object still exists in memory."
107
+ # rescue Wref::Recycled
108
+ # print "Object has been garbage-collected."
109
+ # end
110
+ #
111
+ # obj = map.get!(1)
112
+ # print "Object still exists in memory." if obj
113
+ class Wref_map
114
+ def initialize(args = nil)
115
+ @map = {}
116
+ @ids = {}
117
+ @mutex = Mutex.new
118
+ end
119
+
120
+ #Sets a new object in the map with a given ID.
121
+ def set(id, obj)
122
+ wref = Wref.new(obj)
123
+
124
+ @mutex.synchronize do
125
+ @map[id] = wref
126
+ @ids[obj.__id__] = id
127
+ end
128
+
129
+ #JRuby cant handle this atm... Dunno why...
130
+ if RUBY_ENGINE != "jruby"
131
+ ObjectSpace.define_finalizer(obj, self.method("delete_by_id"))
132
+ end
133
+
134
+ return nil
135
+ end
136
+
137
+ #Returns a object by ID or raises a RefError.
138
+ #===Examples
139
+ # begin
140
+ # obj = map[1]
141
+ # print "Object still exists in memory."
142
+ # rescue Wref::Recycled
143
+ # print "Object has been garbage-collected."
144
+ # end
145
+ def get(id)
146
+ begin
147
+ @mutex.synchronize do
148
+ raise Wref::Recycled if !@map.key?(id)
149
+ return @map[id].get
150
+ end
151
+ rescue Wref::Recycled => e
152
+ self.delete(id)
153
+ raise e
154
+ end
155
+ end
156
+
157
+ #The same as 'get' but returns nil instead of WeakRef-error. This can be used to avoid writing lots of code.
158
+ #===Examples
159
+ # obj = map.get!(1)
160
+ # print "Object still exists in memory." if obj
161
+ def get!(id)
162
+ begin
163
+ return self.get(id)
164
+ rescue Wref::Recycled
165
+ return nil
166
+ end
167
+ end
168
+
169
+ #Scans the whole map and removes dead references. After the implementation of automatic clean-up by using ObjectSpace.define_finalizer, there should be no reason to call this method.
170
+ def clean
171
+ keys = nil
172
+ @mutex.synchronize do
173
+ keys = @map.keys
174
+ end
175
+
176
+ keys.each do |key|
177
+ begin
178
+ self.get(key) #this will remove the key if the object no longer exists.
179
+ rescue Wref::Recycled
180
+ #ignore.
181
+ end
182
+ end
183
+
184
+ return nil
185
+ end
186
+
187
+ #Returns true if a given key exists and the object it holds is alive.
188
+ def valid?(key)
189
+ @mutex.synchronize do
190
+ return false if !@map.key?(key)
191
+
192
+ begin
193
+ @map[key].get
194
+ return true
195
+ rescue Wref::Recycled
196
+ return false
197
+ end
198
+ end
199
+ end
200
+
201
+ #Returns true if the given key exists in the hash.
202
+ #===Examples
203
+ # print "Key exists but we dont know if the value has been garbage-collected." if map.key?(1)
204
+ def key?(key)
205
+ @mutex.synchronize do
206
+ return @map.key?(key)
207
+ end
208
+ end
209
+
210
+ #Returns the length of the hash. This may not be true since invalid objects is also counted.
211
+ def length
212
+ @mutex.synchronize do
213
+ return @map.length
214
+ end
215
+ end
216
+
217
+ #Cleans the hash and returns the length. This is slower but more accurate than the ordinary length that just returns the hash-length.
218
+ def length_valid
219
+ self.clean
220
+
221
+ @mutex.synchronize do
222
+ return @map.length
223
+ end
224
+ end
225
+
226
+ #Deletes a key in the hash.
227
+ def delete(key)
228
+ @mutex.synchronize do
229
+ wref = @map[key]
230
+ @ids.delete(wref.id) if wref
231
+ @map.delete(key)
232
+ end
233
+ end
234
+
235
+ #This method is supposed to remove objects when finalizer is called by ObjectSpace.
236
+ def delete_by_id(object_id)
237
+ @mutex.synchronize do
238
+ id = @ids[object_id]
239
+ @map.delete(id)
240
+ @ids.delete(object_id)
241
+ end
242
+ end
243
+
244
+ #Make it hash-compatible.
245
+ alias has_key? key?
246
+ alias [] get
247
+ alias []= set
248
+ end
249
+
250
+ #This error is raised when an object in a wref has been garbage-collected.
251
+ class Wref::Recycled < RuntimeError; end
@@ -0,0 +1,12 @@
1
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
2
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+ require 'rspec'
4
+ require 'wref'
5
+
6
+ # Requires supporting files with custom matchers and macros, etc,
7
+ # in ./support/ and its subdirectories.
8
+ Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f}
9
+
10
+ RSpec.configure do |config|
11
+
12
+ end
@@ -0,0 +1,21 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "Wref" do
4
+ it "should not fail" do
5
+ str = "Test"
6
+ ref = Wref.new(str)
7
+ raise "Should have been alive but wasnt." if !ref.alive?
8
+ str = nil
9
+ GC.start
10
+ raise "Should have been GCed but wasnt." if ref.alive?
11
+
12
+
13
+ str = "Test"
14
+ map = Wref_map.new
15
+ map[5] = str
16
+ raise "Should have been valid but wasnt." if !map.valid?(5)
17
+ str = nil
18
+ GC.start
19
+ raise "Should habe been garbage collected but wasnt." if !map.valid?(5)
20
+ end
21
+ end
@@ -0,0 +1,60 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{wref}
8
+ s.version = "0.0.0"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Kasper Johansen"]
12
+ s.date = %q{2012-05-10}
13
+ s.description = %q{Lightweight weak reference and weak hash that works in 1.9 and JRuby.}
14
+ s.email = %q{k@spernj.org}
15
+ s.extra_rdoc_files = [
16
+ "LICENSE.txt",
17
+ "README.rdoc"
18
+ ]
19
+ s.files = [
20
+ ".document",
21
+ ".rspec",
22
+ "Gemfile",
23
+ "Gemfile.lock",
24
+ "LICENSE.txt",
25
+ "README.rdoc",
26
+ "Rakefile",
27
+ "VERSION",
28
+ "lib/wref.rb",
29
+ "spec/spec_helper.rb",
30
+ "spec/wref_spec.rb",
31
+ "wref.gemspec"
32
+ ]
33
+ s.homepage = %q{http://github.com/kaspernj/wref}
34
+ s.licenses = ["MIT"]
35
+ s.require_paths = ["lib"]
36
+ s.rubygems_version = %q{1.6.2}
37
+ s.summary = %q{Weak references and weak hash for Ruby}
38
+
39
+ if s.respond_to? :specification_version then
40
+ s.specification_version = 3
41
+
42
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
43
+ s.add_development_dependency(%q<rspec>, ["~> 2.8.0"])
44
+ s.add_development_dependency(%q<rdoc>, ["~> 3.12"])
45
+ s.add_development_dependency(%q<bundler>, [">= 1.0.0"])
46
+ s.add_development_dependency(%q<jeweler>, ["~> 1.8.3"])
47
+ else
48
+ s.add_dependency(%q<rspec>, ["~> 2.8.0"])
49
+ s.add_dependency(%q<rdoc>, ["~> 3.12"])
50
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
51
+ s.add_dependency(%q<jeweler>, ["~> 1.8.3"])
52
+ end
53
+ else
54
+ s.add_dependency(%q<rspec>, ["~> 2.8.0"])
55
+ s.add_dependency(%q<rdoc>, ["~> 3.12"])
56
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
57
+ s.add_dependency(%q<jeweler>, ["~> 1.8.3"])
58
+ end
59
+ end
60
+
metadata ADDED
@@ -0,0 +1,114 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: wref
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 0.0.0
6
+ platform: ruby
7
+ authors:
8
+ - Kasper Johansen
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2012-05-10 00:00:00 +02:00
14
+ default_executable:
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: rspec
18
+ requirement: &id001 !ruby/object:Gem::Requirement
19
+ none: false
20
+ requirements:
21
+ - - ~>
22
+ - !ruby/object:Gem::Version
23
+ version: 2.8.0
24
+ type: :development
25
+ prerelease: false
26
+ version_requirements: *id001
27
+ - !ruby/object:Gem::Dependency
28
+ name: rdoc
29
+ requirement: &id002 !ruby/object:Gem::Requirement
30
+ none: false
31
+ requirements:
32
+ - - ~>
33
+ - !ruby/object:Gem::Version
34
+ version: "3.12"
35
+ type: :development
36
+ prerelease: false
37
+ version_requirements: *id002
38
+ - !ruby/object:Gem::Dependency
39
+ name: bundler
40
+ requirement: &id003 !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ">="
44
+ - !ruby/object:Gem::Version
45
+ version: 1.0.0
46
+ type: :development
47
+ prerelease: false
48
+ version_requirements: *id003
49
+ - !ruby/object:Gem::Dependency
50
+ name: jeweler
51
+ requirement: &id004 !ruby/object:Gem::Requirement
52
+ none: false
53
+ requirements:
54
+ - - ~>
55
+ - !ruby/object:Gem::Version
56
+ version: 1.8.3
57
+ type: :development
58
+ prerelease: false
59
+ version_requirements: *id004
60
+ description: Lightweight weak reference and weak hash that works in 1.9 and JRuby.
61
+ email: k@spernj.org
62
+ executables: []
63
+
64
+ extensions: []
65
+
66
+ extra_rdoc_files:
67
+ - LICENSE.txt
68
+ - README.rdoc
69
+ files:
70
+ - .document
71
+ - .rspec
72
+ - Gemfile
73
+ - Gemfile.lock
74
+ - LICENSE.txt
75
+ - README.rdoc
76
+ - Rakefile
77
+ - VERSION
78
+ - lib/wref.rb
79
+ - spec/spec_helper.rb
80
+ - spec/wref_spec.rb
81
+ - wref.gemspec
82
+ has_rdoc: true
83
+ homepage: http://github.com/kaspernj/wref
84
+ licenses:
85
+ - MIT
86
+ post_install_message:
87
+ rdoc_options: []
88
+
89
+ require_paths:
90
+ - lib
91
+ required_ruby_version: !ruby/object:Gem::Requirement
92
+ none: false
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ hash: -4333171512268985658
97
+ segments:
98
+ - 0
99
+ version: "0"
100
+ required_rubygems_version: !ruby/object:Gem::Requirement
101
+ none: false
102
+ requirements:
103
+ - - ">="
104
+ - !ruby/object:Gem::Version
105
+ version: "0"
106
+ requirements: []
107
+
108
+ rubyforge_project:
109
+ rubygems_version: 1.6.2
110
+ signing_key:
111
+ specification_version: 3
112
+ summary: Weak references and weak hash for Ruby
113
+ test_files: []
114
+