rufus-tokyo 1.0.3 → 1.0.4

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.
Files changed (55) hide show
  1. data/.gitignore +4 -0
  2. data/CHANGELOG.txt +6 -0
  3. data/Rakefile +91 -0
  4. data/doc/decision_table.numbers +0 -0
  5. data/lib/rufus/edo/README.txt +101 -0
  6. data/lib/rufus/edo/tabcore.rb +1 -3
  7. data/lib/rufus/tokyo.rb +1 -2
  8. data/lib/rufus/tokyo/cabinet/lib.rb +4 -7
  9. data/lib/rufus/tokyo/cabinet/table.rb +10 -13
  10. data/lib/rufus/tokyo/cabinet/util.rb +4 -1
  11. data/lib/rufus/tokyo/hmethods.rb +4 -4
  12. data/lib/rufus/tokyo/outlen.rb +5 -1
  13. data/lib/rufus/tokyo/tyrant/abstract.rb +8 -0
  14. data/lib/rufus/tokyo/tyrant/lib.rb +6 -6
  15. data/lib/rufus/tokyo/tyrant/table.rb +9 -1
  16. data/lib/rufus/tokyo/version.rb +32 -0
  17. data/rufus-tokyo.gemspec +135 -0
  18. data/spec/cabinet_btree_spec.rb +92 -0
  19. data/spec/cabinet_fixed_spec.rb +33 -0
  20. data/spec/cabinet_spec.rb +291 -0
  21. data/spec/cabinetconfig_spec.rb +82 -0
  22. data/spec/dystopia_core_spec.rb +124 -0
  23. data/spec/edo_cabinet_btree_spec.rb +123 -0
  24. data/spec/edo_cabinet_fixed_spec.rb +42 -0
  25. data/spec/edo_cabinet_spec.rb +286 -0
  26. data/spec/edo_ntyrant_spec.rb +224 -0
  27. data/spec/edo_ntyrant_table_spec.rb +296 -0
  28. data/spec/edo_table_spec.rb +292 -0
  29. data/spec/hmethods_spec.rb +73 -0
  30. data/spec/incr.lua +23 -0
  31. data/spec/openable_spec.rb +51 -0
  32. data/spec/shared_abstract_spec.rb +426 -0
  33. data/spec/shared_table_spec.rb +675 -0
  34. data/spec/shared_tyrant_spec.rb +42 -0
  35. data/spec/spec_base.rb +23 -0
  36. data/spec/start_tyrants.sh +28 -0
  37. data/spec/stop_tyrants.sh +9 -0
  38. data/spec/table_spec.rb +267 -0
  39. data/spec/tyrant_spec.rb +218 -0
  40. data/spec/tyrant_table_spec.rb +298 -0
  41. data/spec/util_list_spec.rb +197 -0
  42. data/spec/util_map_spec.rb +130 -0
  43. data/tasks/dev.rb +70 -0
  44. data/test/bm0.rb +353 -0
  45. data/test/bm1_compression.rb +54 -0
  46. data/test/con0.rb +30 -0
  47. data/test/mem.rb +49 -0
  48. data/test/mem1.rb +44 -0
  49. data/test/readme0.rb +17 -0
  50. data/test/readme1.rb +21 -0
  51. data/test/readme2.rb +15 -0
  52. data/test/readme3.rb +24 -0
  53. data/test/readmes_test.sh +17 -0
  54. metadata +81 -21
  55. data/MIGRATED.txt +0 -1
data/.gitignore ADDED
@@ -0,0 +1,4 @@
1
+ ext/*
2
+ tmp/*
3
+ pkg/*
4
+ *~
data/CHANGELOG.txt CHANGED
@@ -2,6 +2,12 @@
2
2
  = rufus-tokyo CHANGELOG.txt
3
3
 
4
4
 
5
+ == rufus-tokyo - 1.0.4 released 2009/12/25
6
+
7
+ - bug : memory leak, gotten values not freed
8
+ - todo : Rufus::Tokyo::Tyrant and TyrantTable now reconnets (120 seconds)
9
+
10
+
5
11
  == rufus-tokyo - 1.0.3 released 2009/11/16
6
12
 
7
13
  - bug : newer versions of FFI have [undocumented] bool type. Adapted.
data/Rakefile ADDED
@@ -0,0 +1,91 @@
1
+
2
+
3
+ require 'lib/rufus/tokyo/version.rb'
4
+
5
+ require 'rubygems'
6
+ require 'rake'
7
+
8
+
9
+ #
10
+ # CLEAN
11
+
12
+ require 'rake/clean'
13
+ CLEAN.include('pkg', 'tmp', 'html')
14
+ task :default => [ :clean ]
15
+
16
+
17
+ #
18
+ # GEM
19
+
20
+ require 'jeweler'
21
+
22
+ Jeweler::Tasks.new do |gem|
23
+
24
+ gem.version = Rufus::Tokyo::VERSION
25
+ gem.name = 'rufus-tokyo'
26
+
27
+ gem.summary =
28
+ 'ruby-ffi based lib to access Tokyo Cabinet, Tyrant and Dystopia'
29
+ gem.description = %{
30
+ Ruby-ffi based lib to access Tokyo Cabinet and Tyrant.
31
+
32
+ The ffi-based structures are available via the Rufus::Tokyo namespace.
33
+ There is a Rufus::Edo namespace that interfaces with Hirabayashi-san's native Ruby interface, and whose API is equal to the Rufus::Tokyo one.
34
+
35
+ Finally rufus-tokyo includes ffi-based interfaces to Tokyo Dystopia (thanks to Jeremy Hinegardner).
36
+ }
37
+
38
+ gem.email = 'jmettraux@gmail.com'
39
+ gem.homepage = 'http://github.com/jmettraux/rufus-tokyo/'
40
+
41
+ gem.authors = [
42
+ 'John Mettraux', 'Zev Blut', 'Jeremy Hinegardner', 'James Edward Gray II' ]
43
+
44
+ gem.rubyforge_project = 'rufus'
45
+
46
+ gem.test_file = 'spec/spec.rb'
47
+
48
+ gem.add_dependency 'ffi'
49
+ gem.add_development_dependency 'yard', '>= 0'
50
+
51
+ #gem.files = Dir['lib/**/*.rb'] + Dir['*.txt'] - [ 'lib/tokyotyrant.rb' ]
52
+ #gem.files.reject! { |fn| fn == 'lib/tokyotyrant.rb' }
53
+
54
+ # gemspec spec : http://www.rubygems.org/read/chapter/20
55
+ end
56
+ Jeweler::GemcutterTasks.new
57
+
58
+
59
+ #
60
+ # DOC
61
+
62
+ begin
63
+
64
+ require 'yard'
65
+
66
+ YARD::Rake::YardocTask.new do |doc|
67
+ doc.options = [
68
+ '-o', 'html/rufus-tokyo', '--title',
69
+ "rufus-tokyo #{Rufus::Tokyo::VERSION}"
70
+ ]
71
+ end
72
+
73
+ rescue LoadError
74
+
75
+ task :yard do
76
+ abort "YARD is not available : sudo gem install yard"
77
+ end
78
+ end
79
+
80
+
81
+ #
82
+ # TO THE WEB
83
+
84
+ task :upload_website => [ :clean, :yard ] do
85
+
86
+ account = 'jmettraux@rubyforge.org'
87
+ webdir = '/var/www/gforge-projects/rufus'
88
+
89
+ sh "rsync -azv -e ssh html/rufus-tokyo #{account}:#{webdir}/"
90
+ end
91
+
Binary file
@@ -0,0 +1,101 @@
1
+
2
+ = Rufus::Edo
3
+
4
+ wrapping Hirabayashi-san's 'native' ruby bindings into a rubiyst-friendly set of Ruby classes.
5
+
6
+ In order to use Rufus::Edo, you have to have the libtokyocabinet dynamic library installed on your system :
7
+
8
+ http://openwferu.rubyforge.org/tokyo.html
9
+
10
+ Then you can install the 'native' C bindings.
11
+
12
+ NOTE : I have only tested those native bindings with Ruby 1.8.6. To run them with JRuby, the best option is Rufus::Tokyo and its FFI bindings.
13
+
14
+ NOTE : the Ruby tyrant library provided by Hirabayashi-san is not a C binding, it's a pure Ruby connector. It is slower than Rufus::Tokyo::Tyrant and Rufus::Tokyo::TyrantTable, but the advantage is that there is no need to install cabinet and tyrant C libraries to connect your Ruby code to your Tokyo Tyrant.
15
+
16
+
17
+ == installation of the 'native' C bindings
18
+
19
+ === directly from http://1978th.net/tokyocabinet/
20
+
21
+ Get the tokyocabinet-ruby package at :
22
+
23
+ http://1978th.net/tokyocabinet/rubypkg/
24
+
25
+ unpack it :
26
+
27
+ tar xzvf tokyocabinet-ruby-1.29.tar.gz
28
+ cd tokyocabinet-ruby-1.29
29
+
30
+ and then, as described at : http://tokyocabinet.sourceforge.net/rubydoc/
31
+
32
+ ruby extconf.rb
33
+ make
34
+ sudo make install
35
+
36
+
37
+ == Rufus::Edo::Cabinet
38
+
39
+ require 'rufus/edo' # sudo gem install rufus-tokyo
40
+
41
+ db = Rufus::Edo::Cabinet.new('data.tch')
42
+
43
+ db['a'] = 'alpha'
44
+
45
+ # ...
46
+
47
+ db.close
48
+
49
+
50
+ == Rufus::Edo::Table
51
+
52
+ require 'rufus/edo'
53
+
54
+ db = Rufus::Edo::Table.new('data.tct')
55
+
56
+ db['customer1'] = { 'name' => 'Taira no Kyomori', 'age' => '55' }
57
+
58
+ # ...
59
+
60
+ db.close
61
+
62
+
63
+ == tyrant
64
+
65
+ Hirabayashi-san's pure Ruby gem for accessing Tokyo Tyrant can be installed with :
66
+
67
+ sudo gem install careo-tokyotyrant --source http://gems.github.com
68
+
69
+ It's also available at :
70
+
71
+ http://sourceforge.net/project/showfiles.php?group_id=200242
72
+ http://github.com/careo/tokyotyrant-ruby
73
+
74
+
75
+ == Rufus::Edo::NetTyrant
76
+
77
+ Note : 'NetTyrant' instead of 'Tyrant' to clearly show that this class isn't a C binding but a simple [pure Ruby] network implementation of a connection to a Tyrant.
78
+
79
+
80
+ require 'rufus/edo/ntyrant'
81
+
82
+ db = Rufus::Edo::NetTyrant.new('127.0.0.1', 45000)
83
+
84
+ db['a'] = 'alpha'
85
+
86
+ puts db['a]
87
+ # => 'alpha'
88
+
89
+ db.close
90
+
91
+
92
+ == Rufus::Edo::NetTyrantTable
93
+
94
+ require 'rufus/edo/ntyrant'
95
+
96
+ t = Rufus::Edo::NetTyrantTable.new('127.0.0.1', 44502)
97
+
98
+ t['client0'] = { 'name' => 'Heike no Kyomori', 'country' => 'jp' }
99
+
100
+ t.close
101
+
@@ -533,9 +533,7 @@ module Rufus::Edo
533
533
  #
534
534
  def limit (i, offset=-1)
535
535
 
536
- @query.respond_to?(:setlimit) ?
537
- @query.setlimit(i, offset) :
538
- @query.setmax(i)
536
+ @query.setlimit(i, offset)
539
537
  end
540
538
 
541
539
  # Sets the sort order for the result of the query
data/lib/rufus/tokyo.rb CHANGED
@@ -29,8 +29,6 @@ require 'ffi' # sudo gem install ffi
29
29
  module Rufus
30
30
  module Tokyo
31
31
 
32
- VERSION = '1.0.3'
33
-
34
32
  #
35
33
  # A common error class
36
34
  #
@@ -51,6 +49,7 @@ module Tokyo
51
49
  end
52
50
  end
53
51
 
52
+ require 'rufus/tokyo/version'
54
53
  require 'rufus/tokyo/cabinet/lib'
55
54
  require 'rufus/tokyo/cabinet/util'
56
55
  require 'rufus/tokyo/cabinet/abstract'
@@ -46,7 +46,7 @@ module Rufus::Tokyo
46
46
  rescue LoadError => le
47
47
  raise(
48
48
  "didn't find Tokyo Cabinet libs on your system. " +
49
- "Please install Tokyo Cabinet (http://tokyocabinet.sf.net) " +
49
+ "Please install Tokyo Cabinet (http://1978th.net/tokyocabinet/) " +
50
50
  "(see also http://openwferu.rubyforge.org/tokyo.html)"
51
51
  )
52
52
  end
@@ -66,6 +66,8 @@ module Rufus::Tokyo
66
66
  #
67
67
  attfunc :tcfree, [ :pointer ], :void
68
68
 
69
+ attfunc :free, [ :pointer ], :void
70
+
69
71
  #
70
72
  # tcadb functions
71
73
  #
@@ -177,12 +179,7 @@ module Rufus::Tokyo
177
179
  callback :TDBQRYPROC, [:pointer, :int, :pointer, :pointer], :int
178
180
  attfunc :qry_proc, :tctdbqryproc, [ :pointer, :TDBQRYPROC, :pointer], :bool
179
181
 
180
-
181
- begin # since TC 1.4.10
182
- attfunc :qry_setmax, :tctdbqrysetmax, [ :pointer, :int ], :void
183
- rescue FFI::NotFoundError => nfe
184
- attfunc :qry_setlimit, :tctdbqrysetlimit, [ :pointer, :int, :int ], :void
185
- end
182
+ attfunc :qry_setlimit, :tctdbqrysetlimit, [ :pointer, :int, :int ], :void
186
183
 
187
184
  attfunc :qry_search, :tctdbqrysearch, [ :pointer ], :pointer
188
185
  attfunc :qry_searchout, :tctdbqrysearchout, [ :pointer ], :bool
@@ -43,8 +43,7 @@ module Rufus::Tokyo
43
43
  # require 'rubygems'
44
44
  # require 'rufus/tokyo/cabinet/table'
45
45
  #
46
- # t = Rufus::Tokyo::Table.new('table.tdb', :create, :write)
47
- # # '.tdb' suffix is a must
46
+ # t = Rufus::Tokyo::Table.new('table.tct')
48
47
  #
49
48
  # t['pk0'] = { 'name' => 'alfred', 'age' => '22' }
50
49
  # t['pk1'] = { 'name' => 'bob', 'age' => '18' }
@@ -76,10 +75,10 @@ module Rufus::Tokyo
76
75
  #
77
76
  # For example,
78
77
  #
79
- # t = Rufus::Tokyo::Table.new('table.tdb')
80
- # # '.tdb' suffix is a must
78
+ # t = Rufus::Tokyo::Table.new('table.tct')
79
+ # # '.tct' suffix is a must
81
80
  #
82
- # will create the table.tdb (or simply open it if already present)
81
+ # will create the table.tct (or simply open it if already present)
83
82
  # and make sure we have write access to it.
84
83
  #
85
84
  # == parameters
@@ -118,11 +117,11 @@ module Rufus::Tokyo
118
117
  #
119
118
  # Some examples :
120
119
  #
121
- # t = Rufus::Tokyo::Table.new('table.tdb')
122
- # t = Rufus::Tokyo::Table.new('table.tdb#mode=r')
123
- # t = Rufus::Tokyo::Table.new('table.tdb', :mode => 'r')
124
- # t = Rufus::Tokyo::Table.new('table.tdb#opts=ld#mode=r')
125
- # t = Rufus::Tokyo::Table.new('table.tdb', :opts => 'ld', :mode => 'r')
120
+ # t = Rufus::Tokyo::Table.new('table.tct')
121
+ # t = Rufus::Tokyo::Table.new('table.tct#mode=r')
122
+ # t = Rufus::Tokyo::Table.new('table.tct', :mode => 'r')
123
+ # t = Rufus::Tokyo::Table.new('table.tct#opts=ld#mode=r')
124
+ # t = Rufus::Tokyo::Table.new('table.tct', :opts => 'ld', :mode => 'r')
126
125
  #
127
126
  def initialize (path, params={})
128
127
 
@@ -722,9 +721,7 @@ module Rufus::Tokyo
722
721
  #
723
722
  def limit (i, offset=-1)
724
723
 
725
- lib.respond_to?(:qry_setlimit) ?
726
- lib.qry_setlimit(@query, i, offset) :
727
- lib.qry_setmax(@query, i)
724
+ lib.qry_setlimit(@query, i, offset)
728
725
  end
729
726
 
730
727
  # Sets the sort order for the result of the query
@@ -63,11 +63,14 @@ module Rufus::Tokyo
63
63
 
64
64
  return nil if out.address == 0
65
65
 
66
- return out.get_bytes(0, outlen.get_int(0))
66
+ out.get_bytes(0, outlen.get_int(0))
67
67
 
68
68
  ensure
69
69
 
70
70
  outlen.free
71
+
72
+ #clib.free(out)
73
+ # uncommenting that wreaks havoc
71
74
  end
72
75
  end
73
76
 
@@ -59,19 +59,19 @@ module Tokyo
59
59
  # Our classical 'each'
60
60
  #
61
61
  def each
62
- #
62
+ #
63
63
  # drop to Edo's C API calls to avoid two-step iteration
64
64
  # (keys() then each())
65
- #
65
+ #
66
66
  if defined?(@db) and %w[iterinit iternext].all? { |m| @db.respond_to?(m) }
67
67
  @db.iterinit
68
68
  while k = @db.iternext
69
69
  yield(k, self[k])
70
70
  end
71
- #
71
+ #
72
72
  # drop to Tokyo's FFI calls to avoid two-step iteration
73
73
  # (keys() then each())
74
- #
74
+ #
75
75
  elsif self.class.name != "Rufus::Tokyo::Table" and # use String for Edo
76
76
  defined?(@db) and
77
77
  respond_to?(:lib) and
@@ -37,9 +37,13 @@ module Rufus::Tokyo
37
37
  out = lib.send(method, *args)
38
38
 
39
39
  return nil if out.address == 0
40
- return out.get_bytes(0, outlen.get_int(0))
40
+
41
+ out.get_bytes(0, outlen.get_int(0))
42
+
41
43
  ensure
42
44
  outlen.free
45
+ #lib.tcfree(out)
46
+ lib.free(out)
43
47
  end
44
48
  end
45
49
  end
@@ -114,6 +114,14 @@ module Rufus::Tokyo
114
114
 
115
115
  self.default = params[:default]
116
116
  @default_proc ||= params[:default_proc]
117
+
118
+ #
119
+ # timeout and reconnect
120
+
121
+ # defaults to two minutes
122
+
123
+ timeout = params[:timeout] || 120.0
124
+ lib.tcrdbtune(@db, timeout, 1)
117
125
  end
118
126
 
119
127
  # Using the tyrant lib
@@ -44,7 +44,7 @@ module Rufus::Tokyo
44
44
  rescue LoadError => le
45
45
  raise(
46
46
  "didn't find Tokyo Tyrant libs on your system. " +
47
- "Please install Tokyo Tyrant (http://tokyocabinet.sf.net) " +
47
+ "Please install Tokyo Tyrant (http://1978th.net/tokyotyrant/) " +
48
48
  "(see also http://openwferu.rubyforge.org/tokyo.html)"
49
49
  )
50
50
  end
@@ -54,6 +54,8 @@ module Rufus::Tokyo
54
54
  alias :attfunc :attach_function
55
55
  end
56
56
 
57
+ attfunc :free, [ :pointer ], :void
58
+
57
59
  # http://1978th.net/tokyotyrant/spex.html#tcrdbapi
58
60
 
59
61
  #
@@ -63,6 +65,8 @@ module Rufus::Tokyo
63
65
 
64
66
  attfunc :tcrdbstat, [ :pointer ], :string
65
67
 
68
+ attfunc :tcrdbtune, [ :pointer, :double, :int ], :bool
69
+
66
70
  attfunc :tcrdbopen, [ :pointer, :string, :int ], :bool
67
71
  attfunc :abs_close, :tcrdbclose, [ :pointer ], :bool
68
72
 
@@ -138,11 +142,7 @@ module Rufus::Tokyo
138
142
  attfunc :qry_addcond, :tcrdbqryaddcond, [ :pointer, :string, :int, :string ], :void
139
143
  attfunc :qry_setorder, :tcrdbqrysetorder, [ :pointer, :string, :int ], :void
140
144
 
141
- begin
142
- attfunc :qry_setmax, :tcrdbqrysetmax, [ :pointer, :int ], :void
143
- rescue FFI::NotFoundError => nfe
144
- attfunc :qry_setlimit, :tcrdbqrysetlimit, [ :pointer, :int, :int ], :void
145
- end
145
+ attfunc :qry_setlimit, :tcrdbqrysetlimit, [ :pointer, :int, :int ], :void
146
146
 
147
147
  attfunc :qry_search, :tcrdbqrysearch, [ :pointer ], :pointer
148
148
  attfunc :qry_searchout, :tcrdbqrysearchout, [ :pointer ], :bool
@@ -75,7 +75,7 @@ module Rufus::Tokyo
75
75
  # t['client0'] = { 'name' => 'Theodore Roosevelt', 'country' => 'usa' }
76
76
  # t.close
77
77
  #
78
- def initialize (host, port=0)
78
+ def initialize (host, port=0, params={})
79
79
 
80
80
  @db = lib.tcrdbnew
81
81
 
@@ -95,6 +95,14 @@ module Rufus::Tokyo
95
95
  end
96
96
 
97
97
  @default_proc = nil
98
+
99
+ #
100
+ # timeout and reconnect
101
+
102
+ # defaults to two minutes
103
+
104
+ timeout = params[:timeout] || 120.0
105
+ lib.tcrdbtune(@db, timeout, 1)
98
106
  end
99
107
 
100
108
  #