key_value 0.1.4 → 0.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.
data/Gemfile CHANGED
@@ -4,6 +4,8 @@ gem 'activerecord'
4
4
 
5
5
  group :dev do # not development <-> would add unneeded development dependencies in gemspec
6
6
  gem 'sqlite3'
7
+ gem 'mysql2', '~>0.2.0'
8
+ gem 'handlersocket'
7
9
  gem 'rake'
8
10
  gem 'rspec', '~>2'
9
11
  gem 'jeweler'
data/Gemfile.lock CHANGED
@@ -15,20 +15,22 @@ GEM
15
15
  builder (2.1.2)
16
16
  diff-lcs (1.1.2)
17
17
  git (1.2.5)
18
+ handlersocket (0.0.2)
18
19
  i18n (0.5.0)
19
20
  jeweler (1.6.0)
20
21
  bundler (~> 1.0.0)
21
22
  git (>= 1.2.5)
22
23
  rake
24
+ mysql2 (0.2.7)
23
25
  rake (0.8.7)
24
- rspec (2.5.0)
25
- rspec-core (~> 2.5.0)
26
- rspec-expectations (~> 2.5.0)
27
- rspec-mocks (~> 2.5.0)
28
- rspec-core (2.5.1)
29
- rspec-expectations (2.5.0)
26
+ rspec (2.6.0)
27
+ rspec-core (~> 2.6.0)
28
+ rspec-expectations (~> 2.6.0)
29
+ rspec-mocks (~> 2.6.0)
30
+ rspec-core (2.6.0)
31
+ rspec-expectations (2.6.0)
30
32
  diff-lcs (~> 1.1.2)
31
- rspec-mocks (2.5.0)
33
+ rspec-mocks (2.6.0)
32
34
  sqlite3 (1.3.3)
33
35
  tzinfo (0.3.27)
34
36
 
@@ -37,7 +39,9 @@ PLATFORMS
37
39
 
38
40
  DEPENDENCIES
39
41
  activerecord
42
+ handlersocket
40
43
  jeweler
44
+ mysql2 (~> 0.2.0)
41
45
  rake
42
46
  rspec (~> 2)
43
47
  sqlite3
data/Readme.md CHANGED
@@ -24,23 +24,40 @@ Migration
24
24
 
25
25
  Usage
26
26
  =====
27
- KeyValue['xxx'] = {:baz=>'foo'})
28
- or KeyValue.set('xxx', {:baz=>'foo'})
29
-
27
+ # get
30
28
  KeyValue['xxx'] -> {:baz=>'foo'}
31
29
  or KeyValue.get('xxx') -> {:baz=>'foo'}
32
30
 
31
+ # set
32
+ KeyValue['xxx'] = {:baz=>'foo'})
33
+ or KeyValue.set('xxx', {:baz=>'foo'})
34
+
35
+ # delete
33
36
  KeyValue['xxx'] = nil
34
37
  or KeyValue.del('xxx')
35
38
 
39
+ # increment
36
40
  KeyValue.inc('xxx') # !! Not atomic
37
41
  or KeyValue.inc('xxx', 5)
38
42
 
43
+ # cache
39
44
  KeyValue.cache('xxx'){ ..something expensive.. }
40
45
 
46
+ HandlerSocket for [750k-qps](http://yoshinorimatsunobu.blogspot.com/2010/10/using-mysql-as-nosql-story-for.html),
47
+ [Ubuntu natty guide](http://grosser.it/2011/05/14/installing-mysql-handlersocket-in-ubuntu-natty-for-ruby/)
48
+
49
+ KeyValue.handler_socket = {:host => '127.0.0.1', :port=>'9998', :database => 'foo_development'}
50
+
51
+ # all read requests use HandlerSocket
52
+ KeyValue['xxx'] # -> same as before but faster :)
53
+
41
54
  TODO
42
55
  ====
43
- - HandlerSocket support
56
+ - nice error handling for HandlerSocket
57
+ - reuse host/database from normal connection for HandlerSocket
58
+ - HandlerSocket write support
59
+ - use 'key' column as primary key <-> any problems with that ?
60
+ - make test database configurable
44
61
 
45
62
  Authors
46
63
  =======
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.4
1
+ 0.2.0
data/key_value.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{key_value}
8
- s.version = "0.1.4"
8
+ s.version = "0.2.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Roman Heinrich", "Michael Grosser"]
12
- s.date = %q{2011-05-13}
12
+ s.date = %q{2011-05-14}
13
13
  s.email = %q{michael@grosser.it}
14
14
  s.files = [
15
15
  "Gemfile",
@@ -19,6 +19,7 @@ Gem::Specification.new do |s|
19
19
  "VERSION",
20
20
  "key_value.gemspec",
21
21
  "lib/key_value.rb",
22
+ "spec/Readme.md",
22
23
  "spec/key_value_spec.rb",
23
24
  "spec/spec_helper.rb"
24
25
  ]
data/lib/key_value.rb CHANGED
@@ -1,11 +1,15 @@
1
1
  require 'active_record'
2
2
 
3
3
  class KeyValue < ActiveRecord::Base
4
+ HS_DEFAULT_CONFIG = {:port => '9998'}
5
+ HS_INDEX = 31234 # just some high number...
4
6
  VERSION = File.read( File.join(File.dirname(__FILE__),'..','VERSION') ).strip
5
7
  validates_presence_of :key
6
8
 
7
9
  serialize :value
8
10
 
11
+ cattr_accessor :handler_socket
12
+
9
13
  # serialize would treat false the same as nil
10
14
  def value=(x)
11
15
  x = x.to_yaml unless x.nil?
@@ -13,7 +17,14 @@ class KeyValue < ActiveRecord::Base
13
17
  end
14
18
 
15
19
  def self.get(key)
16
- KeyValue.find_by_key(key).try(:value)
20
+ if handler_socket
21
+ hs_connection.open_index(HS_INDEX, handler_socket[:database], 'key_values', 'index_key_values_on_key', 'value')
22
+ result = hs_connection.execute_single(HS_INDEX, '=', [key])
23
+ return unless result = result[1][0]
24
+ YAML.load(result[0])
25
+ else
26
+ KeyValue.find_by_key(key).try(:value)
27
+ end
17
28
  end
18
29
 
19
30
  def self.set(key, value)
@@ -48,4 +59,13 @@ class KeyValue < ActiveRecord::Base
48
59
  value
49
60
  end
50
61
  end
62
+
63
+ private
64
+
65
+ def self.hs_connection
66
+ @@hs_connection ||= begin
67
+ require 'handlersocket'
68
+ HandlerSocket.new(HS_DEFAULT_CONFIG.merge(handler_socket).slice(:host, :port))
69
+ end
70
+ end
51
71
  end
data/spec/Readme.md ADDED
@@ -0,0 +1,4 @@
1
+ You can run the tests with sqlite.
2
+
3
+ To get full handlersocket coverage, use `DB=mysql rake`.
4
+ Handlersocket should be configured on localhost prot 9998 with database key_value_test.
@@ -2,6 +2,7 @@ require File.expand_path('spec/spec_helper')
2
2
 
3
3
  describe KeyValue do
4
4
  before do
5
+ KeyValue.handler_socket = false
5
6
  KeyValue.delete_all
6
7
  end
7
8
 
@@ -99,4 +100,31 @@ describe KeyValue do
99
100
  KeyValue.cache('xxx'){true}.should == false
100
101
  end
101
102
  end
103
+
104
+ if ENV['DB'] == 'mysql'
105
+ describe 'with handlersocket' do
106
+ before do
107
+ KeyValue.handler_socket = {:host => '127.0.0.1', :port => '9998', :database => 'key_values_test'}
108
+ KeyValue.delete_all
109
+ end
110
+
111
+ it "can get" do
112
+ KeyValue['xxx'] = '123'
113
+ KeyValue.should_not_receive(:find_by_key)
114
+ KeyValue['xxx'].should == '123'
115
+ end
116
+
117
+ it "can get nil" do
118
+ KeyValue['xxx'].should == nil
119
+ end
120
+
121
+ it "can get false" do
122
+ KeyValue['xxx'] = false
123
+ KeyValue.should_not_receive(:find_by_key)
124
+ KeyValue['xxx'].should == false
125
+ end
126
+ end
127
+ else
128
+ puts 'not running HandlerSocket specs'
129
+ end
102
130
  end
data/spec/spec_helper.rb CHANGED
@@ -1,13 +1,24 @@
1
1
  require 'active_record'
2
2
 
3
- # connect
4
- ActiveRecord::Base.establish_connection(
5
- :adapter => "sqlite3",
6
- :database => ":memory:"
7
- )
3
+ # connect
4
+ if ENV['DB'] == 'mysql'
5
+ puts 'using mysql'
6
+ ActiveRecord::Base.establish_connection(
7
+ :adapter => "mysql2",
8
+ :database => "key_values_test"
9
+ )
10
+ else
11
+ puts 'using sqlite'
12
+ ActiveRecord::Base.establish_connection(
13
+ :adapter => "sqlite3",
14
+ :database => ":memory:"
15
+ )
16
+ end
8
17
 
9
18
  # create tables
10
19
  ActiveRecord::Schema.define(:version => 1) do
20
+ drop_table :key_values rescue nil
21
+
11
22
  create_table :key_values do |t|
12
23
  t.string :key, :null => false
13
24
  t.text :value, :null => false
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: key_value
3
3
  version: !ruby/object:Gem::Version
4
- hash: 19
4
+ hash: 23
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
- - 1
9
- - 4
10
- version: 0.1.4
8
+ - 2
9
+ - 0
10
+ version: 0.2.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - Roman Heinrich
@@ -16,7 +16,7 @@ autorequire:
16
16
  bindir: bin
17
17
  cert_chain: []
18
18
 
19
- date: 2011-05-13 00:00:00 +02:00
19
+ date: 2011-05-14 00:00:00 +02:00
20
20
  default_executable:
21
21
  dependencies:
22
22
  - !ruby/object:Gem::Dependency
@@ -49,6 +49,7 @@ files:
49
49
  - VERSION
50
50
  - key_value.gemspec
51
51
  - lib/key_value.rb
52
+ - spec/Readme.md
52
53
  - spec/key_value_spec.rb
53
54
  - spec/spec_helper.rb
54
55
  has_rdoc: true