rhubarb 0.2.5 → 0.2.6
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGES +12 -0
- data/VERSION +1 -1
- data/lib/rhubarb/classmixins.rb +8 -6
- data/lib/rhubarb/util.rb +33 -0
- data/ruby-rhubarb.spec.in +3 -0
- data/test/helper.rb +2 -0
- data/test/test_rhubarb.rb +69 -0
- metadata +2 -2
data/CHANGES
CHANGED
@@ -1,3 +1,15 @@
|
|
1
|
+
version 0.2.6
|
2
|
+
|
3
|
+
* Rhubarb now supports starting arbitrary Ruby objects to fields
|
4
|
+
of type :object --- these are serialized to yaml and gzipped
|
5
|
+
before they enter the database. At the moment, you cannot change
|
6
|
+
such an object in place (accessing a field of type :object will
|
7
|
+
return a frozen object); to change the value of an object field
|
8
|
+
you must dup and reassign. This will probably change in a future
|
9
|
+
release.
|
10
|
+
|
11
|
+
* Rhubarb now supports storing gzipped blobs in fields of type :zblob.
|
12
|
+
|
1
13
|
version 0.2.5
|
2
14
|
|
3
15
|
* Prepared statements are now optional to eliminate a strange bug
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.2.
|
1
|
+
0.2.6
|
data/lib/rhubarb/classmixins.rb
CHANGED
@@ -15,6 +15,8 @@ require 'rhubarb/mixins/freshness'
|
|
15
15
|
module Rhubarb
|
16
16
|
# Methods mixed in to the class object of a persisting class
|
17
17
|
module PersistingClassMixins
|
18
|
+
PCM_INPUT_TRANSFORMERS = {:blob=>Util.blobify_proc, :zblob=>Util.zblobify_proc, :object=>Util.swizzle_object_proc}
|
19
|
+
PCM_OUTPUT_TRANSFORMERS = {:object=>Util.deswizzle_object_proc, :zblob=>Util.dezblobify_proc, }
|
18
20
|
# Returns the name of the database table modeled by this class.
|
19
21
|
# Defaults to the name of the class (sans module names)
|
20
22
|
def table_name
|
@@ -147,19 +149,18 @@ module Rhubarb
|
|
147
149
|
self.colkinds[cname] = kind
|
148
150
|
self.columns << Column.new(cname, kind, quals)
|
149
151
|
|
152
|
+
out_xform = PCM_OUTPUT_TRANSFORMERS[kind]
|
150
153
|
# add accessors
|
151
154
|
define_method get_method_name do
|
152
155
|
freshen
|
153
|
-
return
|
154
|
-
|
156
|
+
return nil unless @tuple
|
157
|
+
out_xform ? out_xform.call(@tuple[cname.to_s]) : @tuple[cname.to_s]
|
155
158
|
end
|
156
159
|
|
157
160
|
if not rf
|
158
161
|
xform = nil
|
159
162
|
|
160
|
-
|
161
|
-
xform = Util::blobify_proc
|
162
|
-
end
|
163
|
+
xform = PCM_INPUT_TRANSFORMERS[kind]
|
163
164
|
|
164
165
|
define_method set_method_name do |arg|
|
165
166
|
@tuple["#{cname}"] = xform ? xform.call(arg) : arg
|
@@ -225,7 +226,8 @@ module Rhubarb
|
|
225
226
|
|
226
227
|
# resolve any references in the args
|
227
228
|
new_row.each do |column,value|
|
228
|
-
|
229
|
+
xform = PCM_INPUT_TRANSFORMERS[colkinds[column]]
|
230
|
+
new_row[column] = xform ? xform.call(value) : Util::rhubarb_fk_identity(value)
|
229
231
|
end
|
230
232
|
|
231
233
|
create_text = "insert into #{table_name} (#{colspec}) values (#{valspec})"
|
data/lib/rhubarb/util.rb
CHANGED
@@ -11,6 +11,8 @@
|
|
11
11
|
# http://www.apache.org/licenses/LICENSE-2.0
|
12
12
|
|
13
13
|
require 'time'
|
14
|
+
require 'yaml'
|
15
|
+
require 'zlib'
|
14
16
|
|
15
17
|
module Rhubarb
|
16
18
|
module Util
|
@@ -32,5 +34,36 @@ module Rhubarb
|
|
32
34
|
def self.blobify_proc
|
33
35
|
@blobify_proc ||= Proc.new {|x| x.is_a?(SQLite3::Blob) ? x : SQLite3::Blob.new(x)}
|
34
36
|
end
|
37
|
+
|
38
|
+
def self.zblobify_proc
|
39
|
+
@zblobify_proc ||= Proc.new {|x| x.is_a?(SQLite3::Blob) ? x : SQLite3::Blob.new(Zlib::Deflate.deflate(x))}
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.dezblobify_proc
|
43
|
+
@dezblobify_proc ||= Proc.new do |x|
|
44
|
+
return nil if x.nil? || x == ""
|
45
|
+
Zlib::Inflate.inflate(x)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def self.swizzle_object_proc
|
50
|
+
@swizzle_object_proc ||= Proc.new do |x|
|
51
|
+
yamlrepr = x.to_yaml
|
52
|
+
SQLite3::Blob.new(Zlib::Deflate.deflate(yamlrepr, Zlib::BEST_COMPRESSION))
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def self.deswizzle_object_proc
|
57
|
+
@deswizzle_object_proc ||= Proc.new do |x|
|
58
|
+
return nil if x.nil? || x == ""
|
59
|
+
|
60
|
+
z = YAML.load(Zlib::Inflate.inflate(x))
|
61
|
+
z.freeze
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def self.identity_proc
|
66
|
+
@identity ||= Proc.new {|x| x}
|
67
|
+
end
|
35
68
|
end
|
36
69
|
end
|
data/ruby-rhubarb.spec.in
CHANGED
data/test/helper.rb
CHANGED
data/test/test_rhubarb.rb
CHANGED
@@ -14,6 +14,9 @@
|
|
14
14
|
require 'helper'
|
15
15
|
require 'fileutils'
|
16
16
|
|
17
|
+
Customer = Struct.new(:name, :address)
|
18
|
+
|
19
|
+
|
17
20
|
class TestClass
|
18
21
|
include Rhubarb::Persisting
|
19
22
|
declare_column :foo, :integer
|
@@ -93,6 +96,17 @@ class BlobTestTable
|
|
93
96
|
declare_column :info, :blob
|
94
97
|
end
|
95
98
|
|
99
|
+
class ZBlobTestTable
|
100
|
+
include Rhubarb::Persisting
|
101
|
+
declare_column :info, :zblob
|
102
|
+
end
|
103
|
+
|
104
|
+
class ObjectTestTable
|
105
|
+
include Rhubarb::Persisting
|
106
|
+
declare_column :otype, :string
|
107
|
+
declare_column :obj, :object
|
108
|
+
end
|
109
|
+
|
96
110
|
class PreparedStmtBackendTests < Test::Unit::TestCase
|
97
111
|
def dbfile
|
98
112
|
ENV['RHUBARB_TEST_DB'] || ":memory:"
|
@@ -119,6 +133,8 @@ class PreparedStmtBackendTests < Test::Unit::TestCase
|
|
119
133
|
klasses << FromRef
|
120
134
|
klasses << FreshTestTable
|
121
135
|
klasses << BlobTestTable
|
136
|
+
klasses << ZBlobTestTable
|
137
|
+
klasses << ObjectTestTable
|
122
138
|
klasses << RhubarbNamespace::NMTC
|
123
139
|
klasses << RhubarbNamespace::NMTC2
|
124
140
|
|
@@ -730,6 +746,59 @@ class PreparedStmtBackendTests < Test::Unit::TestCase
|
|
730
746
|
assert_equal(text, Zlib::Inflate.inflate(cbtrow.info))
|
731
747
|
end
|
732
748
|
|
749
|
+
def test_zblob_data
|
750
|
+
words = %w{the quick brown fox jumps over a lazy dog now is time for all good men to come aid party jackdaws love my big sphinx of quartz}
|
751
|
+
text = ""
|
752
|
+
(0..300).each do
|
753
|
+
text << words[rand(words.length)] << " "
|
754
|
+
end
|
755
|
+
|
756
|
+
compressed_text = Zlib::Deflate.deflate(text)
|
757
|
+
|
758
|
+
row = ZBlobTestTable.create(:info => text)
|
759
|
+
crow = ZBlobTestTable.create(:info => compressed_text)
|
760
|
+
|
761
|
+
btrow = ZBlobTestTable.find(row.row_id)
|
762
|
+
cbtrow = ZBlobTestTable.find(crow.row_id)
|
763
|
+
|
764
|
+
assert_equal(text, btrow.info)
|
765
|
+
assert_equal(text, Zlib::Inflate.inflate(cbtrow.info))
|
766
|
+
end
|
767
|
+
|
768
|
+
|
769
|
+
def test_object_data
|
770
|
+
things = []
|
771
|
+
things << "foo"
|
772
|
+
things << {"foo"=>"bar"}
|
773
|
+
things << ["a", "b", "c", "d"]
|
774
|
+
things << [1]
|
775
|
+
things << {"augh"=>1, "blaugh"=>"quux"}
|
776
|
+
things << [] # empty list
|
777
|
+
things << {} # empty hash
|
778
|
+
things << 49 # int
|
779
|
+
things << {"blah"=>{"foo"=>"bar"}, "argh"=>123, "yuck"=>[1,1,2,3,5,[8]]} # heterogeneous and nested hash
|
780
|
+
things << 0.618 # float
|
781
|
+
things << 99**99 # bignum
|
782
|
+
things << [1,[2,[3,4,[5,6,[7,[8,9,10,[11,12,[13]]]]]]]] # ludicrous list nesting
|
783
|
+
things << {"a"=>{"b"=>{"c"=>{"d"=>{"e"=>["f","g","h","i",{"j"=>["k","l",{"m"=>"n"}]}]}}}}} # ludicrous hash nesting
|
784
|
+
things << Time.now.utc # time
|
785
|
+
things << %w{foo bar blah}.to_set
|
786
|
+
things << Customer.new("Barney Rubble", "303 Cobblestone Way")
|
787
|
+
things << /[1-3]+[A-Z]/
|
788
|
+
|
789
|
+
things.each_with_index do |thing, idx|
|
790
|
+
ObjectTestTable.create(:otype=>thing.class.name.to_s, :obj=>thing)
|
791
|
+
end
|
792
|
+
|
793
|
+
otts = ObjectTestTable.find_all
|
794
|
+
|
795
|
+
assert_equal otts.size, things.size
|
796
|
+
|
797
|
+
things.zip(otts) do |thing, ott|
|
798
|
+
assert_equal thing.class.name.to_s, ott.otype
|
799
|
+
assert_equal thing, ott.obj
|
800
|
+
end
|
801
|
+
end
|
733
802
|
end
|
734
803
|
|
735
804
|
class NoPreparedStmtBackendTests < PreparedStmtBackendTests
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rhubarb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.6
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- William Benton
|
@@ -9,7 +9,7 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2010-04-
|
12
|
+
date: 2010-04-28 00:00:00 -05:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|