pulse-meter-client-backport 0.1.2 → 0.1.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.
@@ -10,12 +10,23 @@ module PulseMeter
10
10
  module InstanceMethods
11
11
  # Serializes object and saves it to Redis
12
12
  # @raise [DumpError] if dumping fails for any reason
13
- def dump!
13
+ def dump!(safe = true)
14
14
  ensure_storability!
15
- serialized_obj = self.to_yaml
16
- redis.hset(DUMP_REDIS_KEY, self.name, serialized_obj)
17
- rescue
18
- raise DumpError, "object cannot be dumped"
15
+ serialized_obj = to_yaml
16
+ if safe
17
+ unless redis.hsetnx(DUMP_REDIS_KEY, name, serialized_obj)
18
+ stored = self.class.restore(name)
19
+ unless stored.class == self.class
20
+ raise DumpConflictError, "Attempt to create sensor #{name} of class #{self.class} but it already has class #{stored.class}"
21
+ end
22
+ end
23
+ else
24
+ redis.hset(DUMP_REDIS_KEY, name, serialized_obj)
25
+ end
26
+ rescue DumpError, RestoreError => exc
27
+ raise exc
28
+ rescue StandardError => exc
29
+ raise DumpError, "object cannot be dumped: #{exc}"
19
30
  end
20
31
 
21
32
  # Ensures that object is dumpable
@@ -37,6 +37,9 @@ module PulseMeter
37
37
  # Exception to be raised when sensor cannot be dumped
38
38
  class DumpError < SensorError; end
39
39
 
40
+ # Exception to be raised on attempts of using the same key for different sensors
41
+ class DumpConflictError < DumpError; end
42
+
40
43
  # Exception to be raised when sensor cannot be restored
41
44
  class RestoreError < SensorError; end
42
45
 
@@ -1,3 +1,3 @@
1
1
  module PulseMeter
2
- VERSION = "0.1.2"
2
+ VERSION = "0.1.3"
3
3
  end
@@ -8,19 +8,23 @@ describe PulseMeter::Mixins::Dumper do
8
8
  class Bad < Base; end
9
9
 
10
10
  class Good < Base
11
- attr_accessor :foo
12
- def name; foo.to_s; end
11
+ attr_accessor :some_value
12
+ attr_accessor :name
13
13
 
14
14
  def redis; PulseMeter.redis; end
15
15
 
16
- def initialize(foo)
17
- @foo = foo
16
+ def initialize(name)
17
+ @name = name.to_s
18
+ @some_value = name
18
19
  end
19
20
  end
20
21
 
22
+ class GoodButAnother < Good; end
23
+
21
24
  let(:bad_obj){ Bad.new }
22
25
  let(:good_obj){ Good.new(:foo) }
23
26
  let(:another_good_obj){ Good.new(:bar) }
27
+ let(:good_obj_of_another_type){ GoodButAnother.new(:quux) }
24
28
  let(:redis){ PulseMeter.redis }
25
29
 
26
30
  describe '#dump' do
@@ -57,6 +61,23 @@ describe PulseMeter::Mixins::Dumper do
57
61
  expect {good_obj.dump!}.to change {redis.hlen(Good::DUMP_REDIS_KEY)}.by(1)
58
62
  end
59
63
  end
64
+
65
+ context "when dump is safe" do
66
+ it "should not overwrite stored objects of the same type" do
67
+ good_obj.some_value = 123
68
+ good_obj.dump!
69
+ good_obj.some_value = 321
70
+ good_obj.dump!
71
+ Base.restore(good_obj.name).some_value.should == 123
72
+ end
73
+
74
+ it "should raise DumpConflictError exception if sensor with the same name but different type already exists" do
75
+ good_obj.name = "duplicate_name"
76
+ good_obj_of_another_type.name = "duplicate_name"
77
+ good_obj.dump!
78
+ expect{good_obj_of_another_type.dump!}.to raise_exception(PulseMeter::DumpConflictError)
79
+ end
80
+ end
60
81
  end
61
82
 
62
83
  describe ".restore" do
@@ -77,14 +98,14 @@ describe PulseMeter::Mixins::Dumper do
77
98
 
78
99
  it "should restore object data" do
79
100
  restored = Base.restore(good_obj.name)
80
- restored.foo.should == good_obj.foo
101
+ restored.some_value.should == good_obj.some_value
81
102
  end
82
103
 
83
104
  it "should restore last dumped object" do
84
- good_obj.foo = :bar
85
- good_obj.dump!
105
+ good_obj.some_value = :bar
106
+ good_obj.dump!(false)
86
107
  restored = Base.restore(good_obj.name)
87
- restored.foo.should == :bar
108
+ restored.some_value.should == :bar
88
109
  end
89
110
  end
90
111
  end
@@ -106,8 +127,8 @@ describe PulseMeter::Mixins::Dumper do
106
127
  end
107
128
 
108
129
  it "should return list of registered objects" do
109
- good_obj.dump!
110
- another_good_obj.dump!
130
+ good_obj.dump!(false)
131
+ another_good_obj.dump!(false)
111
132
  Base.list_names.should =~ [good_obj.name, another_good_obj.name]
112
133
  end
113
134
  end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pulse-meter-client-backport
3
3
  version: !ruby/object:Gem::Version
4
- hash: 31
4
+ hash: 29
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 1
9
- - 2
10
- version: 0.1.2
9
+ - 3
10
+ version: 0.1.3
11
11
  platform: ruby
12
12
  authors:
13
13
  - Ilya Averyanov
@@ -16,12 +16,10 @@ autorequire:
16
16
  bindir: bin
17
17
  cert_chain: []
18
18
 
19
- date: 2012-06-06 00:00:00 Z
19
+ date: 2012-06-08 00:00:00 Z
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
22
- name: json
23
- prerelease: false
24
- requirement: &id001 !ruby/object:Gem::Requirement
22
+ version_requirements: &id001 !ruby/object:Gem::Requirement
25
23
  none: false
26
24
  requirements:
27
25
  - - ">="
@@ -30,12 +28,12 @@ dependencies:
30
28
  segments:
31
29
  - 0
32
30
  version: "0"
31
+ prerelease: false
33
32
  type: :runtime
34
- version_requirements: *id001
33
+ name: json
34
+ requirement: *id001
35
35
  - !ruby/object:Gem::Dependency
36
- name: redis
37
- prerelease: false
38
- requirement: &id002 !ruby/object:Gem::Requirement
36
+ version_requirements: &id002 !ruby/object:Gem::Requirement
39
37
  none: false
40
38
  requirements:
41
39
  - - ">="
@@ -44,12 +42,12 @@ dependencies:
44
42
  segments:
45
43
  - 0
46
44
  version: "0"
45
+ prerelease: false
47
46
  type: :runtime
48
- version_requirements: *id002
47
+ name: redis
48
+ requirement: *id002
49
49
  - !ruby/object:Gem::Dependency
50
- name: hashie
51
- prerelease: false
52
- requirement: &id003 !ruby/object:Gem::Requirement
50
+ version_requirements: &id003 !ruby/object:Gem::Requirement
53
51
  none: false
54
52
  requirements:
55
53
  - - ">="
@@ -58,12 +56,12 @@ dependencies:
58
56
  segments:
59
57
  - 0
60
58
  version: "0"
59
+ prerelease: false
61
60
  type: :development
62
- version_requirements: *id003
61
+ name: hashie
62
+ requirement: *id003
63
63
  - !ruby/object:Gem::Dependency
64
- name: foreman
65
- prerelease: false
66
- requirement: &id004 !ruby/object:Gem::Requirement
64
+ version_requirements: &id004 !ruby/object:Gem::Requirement
67
65
  none: false
68
66
  requirements:
69
67
  - - ">="
@@ -72,12 +70,12 @@ dependencies:
72
70
  segments:
73
71
  - 0
74
72
  version: "0"
73
+ prerelease: false
75
74
  type: :development
76
- version_requirements: *id004
75
+ name: foreman
76
+ requirement: *id004
77
77
  - !ruby/object:Gem::Dependency
78
- name: mock_redis
79
- prerelease: false
80
- requirement: &id005 !ruby/object:Gem::Requirement
78
+ version_requirements: &id005 !ruby/object:Gem::Requirement
81
79
  none: false
82
80
  requirements:
83
81
  - - ">="
@@ -86,12 +84,12 @@ dependencies:
86
84
  segments:
87
85
  - 0
88
86
  version: "0"
87
+ prerelease: false
89
88
  type: :development
90
- version_requirements: *id005
89
+ name: mock_redis
90
+ requirement: *id005
91
91
  - !ruby/object:Gem::Dependency
92
- name: rack-test
93
- prerelease: false
94
- requirement: &id006 !ruby/object:Gem::Requirement
92
+ version_requirements: &id006 !ruby/object:Gem::Requirement
95
93
  none: false
96
94
  requirements:
97
95
  - - ">="
@@ -100,12 +98,12 @@ dependencies:
100
98
  segments:
101
99
  - 0
102
100
  version: "0"
101
+ prerelease: false
103
102
  type: :development
104
- version_requirements: *id006
103
+ name: rack-test
104
+ requirement: *id006
105
105
  - !ruby/object:Gem::Dependency
106
- name: rake
107
- prerelease: false
108
- requirement: &id007 !ruby/object:Gem::Requirement
106
+ version_requirements: &id007 !ruby/object:Gem::Requirement
109
107
  none: false
110
108
  requirements:
111
109
  - - ">="
@@ -114,12 +112,12 @@ dependencies:
114
112
  segments:
115
113
  - 0
116
114
  version: "0"
115
+ prerelease: false
117
116
  type: :development
118
- version_requirements: *id007
117
+ name: rake
118
+ requirement: *id007
119
119
  - !ruby/object:Gem::Dependency
120
- name: redcarpet
121
- prerelease: false
122
- requirement: &id008 !ruby/object:Gem::Requirement
120
+ version_requirements: &id008 !ruby/object:Gem::Requirement
123
121
  none: false
124
122
  requirements:
125
123
  - - ">="
@@ -128,12 +126,12 @@ dependencies:
128
126
  segments:
129
127
  - 0
130
128
  version: "0"
129
+ prerelease: false
131
130
  type: :development
132
- version_requirements: *id008
131
+ name: redcarpet
132
+ requirement: *id008
133
133
  - !ruby/object:Gem::Dependency
134
- name: rspec
135
- prerelease: false
136
- requirement: &id009 !ruby/object:Gem::Requirement
134
+ version_requirements: &id009 !ruby/object:Gem::Requirement
137
135
  none: false
138
136
  requirements:
139
137
  - - ">="
@@ -142,12 +140,12 @@ dependencies:
142
140
  segments:
143
141
  - 0
144
142
  version: "0"
143
+ prerelease: false
145
144
  type: :development
146
- version_requirements: *id009
145
+ name: rspec
146
+ requirement: *id009
147
147
  - !ruby/object:Gem::Dependency
148
- name: timecop
149
- prerelease: false
150
- requirement: &id010 !ruby/object:Gem::Requirement
148
+ version_requirements: &id010 !ruby/object:Gem::Requirement
151
149
  none: false
152
150
  requirements:
153
151
  - - ">="
@@ -156,12 +154,12 @@ dependencies:
156
154
  segments:
157
155
  - 0
158
156
  version: "0"
157
+ prerelease: false
159
158
  type: :development
160
- version_requirements: *id010
159
+ name: timecop
160
+ requirement: *id010
161
161
  - !ruby/object:Gem::Dependency
162
- name: yard
163
- prerelease: false
164
- requirement: &id011 !ruby/object:Gem::Requirement
162
+ version_requirements: &id011 !ruby/object:Gem::Requirement
165
163
  none: false
166
164
  requirements:
167
165
  - - ">="
@@ -170,8 +168,10 @@ dependencies:
170
168
  segments:
171
169
  - 0
172
170
  version: "0"
171
+ prerelease: false
173
172
  type: :development
174
- version_requirements: *id011
173
+ name: yard
174
+ requirement: *id011
175
175
  description: Ruby 1.8 compatible PulseMeter client
176
176
  email:
177
177
  - av@fun-box.ru