believer 0.2.14 → 0.2.15

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/lib/believer/base.rb CHANGED
@@ -23,7 +23,6 @@ module Believer
23
23
  attr_accessor :id
24
24
 
25
25
  def initialize(attrs = {})
26
- @attributes = {}
27
26
  set_attributes(attrs)
28
27
  yield self if block_given?
29
28
  end
@@ -47,6 +46,7 @@ module Believer
47
46
  end
48
47
 
49
48
  def set_attributes(attrs)
49
+ @attributes = {}
50
50
  attrs.each do |name, val|
51
51
  send("#{name}=".to_sym, val)
52
52
  end if attrs.present?
@@ -1,5 +1,6 @@
1
1
  module Believer
2
2
 
3
+ # The counter value
3
4
  class Counter
4
5
 
5
6
  def initialize(v = 0, initial_val = nil)
@@ -7,6 +8,11 @@ module Believer
7
8
  @initial_value = initial_val.nil? ? @value : initial_val
8
9
  end
9
10
 
11
+ def reconcile!
12
+ @initial_value = @value
13
+ self
14
+ end
15
+
10
16
  def reset!
11
17
  @value = 0
12
18
  self
@@ -1,23 +1,29 @@
1
1
  module Believer
2
+ # Model functionality for counter columns
2
3
  module Counting
3
4
  extend ::ActiveSupport::Concern
4
5
 
5
6
  module ClassMethods
6
7
 
8
+ # Returns all the counter columns
9
+ # @return an array of Column
7
10
  def counter_columns
8
11
  columns_with_type(:counter)
9
12
  end
10
13
 
14
+ # Is this a model class with counter columns?
11
15
  def is_counter_table?
12
16
  counter_columns.any?
13
17
  end
14
18
 
15
19
  end
16
20
 
21
+ # Is this a model with counters?
17
22
  def is_counter_instance?
18
23
  self.class.is_counter_table?
19
24
  end
20
25
 
26
+ # Returns true if there are any counter increments or decrements
21
27
  def has_counter_diffs?
22
28
  self.class.counter_columns.any? do |col|
23
29
  counter = self.send(col.name)
@@ -25,5 +31,31 @@ module Believer
25
31
  end
26
32
  end
27
33
 
34
+ # Reloads from DB, resets all counters and saves, which effectively resets all counters
35
+ def reset_counters!
36
+ reload!
37
+ self.class.counter_columns.each do |cc|
38
+ counter = self.send(cc.name)
39
+ counter.reset! unless counter.nil?
40
+ end
41
+ save
42
+ end
43
+
44
+ # Increments a counter and saves the receiver model
45
+ def incr_counter!(name, val = 1)
46
+ counter = self.send(name.to_sym)
47
+ counter.incr(val)
48
+ save
49
+ counter.reconcile!
50
+ end
51
+
52
+ # Increments a counter and saves the receiver model
53
+ def decr_counter!(name, decr = 1)
54
+ counter = self.send(name.to_sym)
55
+ counter.decr(val)
56
+ save
57
+ counter.reconcile!
58
+ end
59
+
28
60
  end
29
61
  end
@@ -10,6 +10,11 @@ module Believer
10
10
  :logger => {
11
11
  :use_environment => true,
12
12
  :level => ::Logger::DEBUG
13
+ },
14
+ :test => {
15
+ :life_cycle => {
16
+ :counters => :destroy
17
+ }
13
18
  }
14
19
  }
15
20
  }
@@ -14,7 +14,7 @@ module Believer
14
14
  keyspace = ::Believer::KeySpace.new(env)
15
15
  # First delete the existing keyspace
16
16
  begin
17
- puts "Dropping keyspace"
17
+ #env.logger.debug "Dropping keyspace"
18
18
  keyspace.drop
19
19
  rescue Cql::QueryError
20
20
  end
@@ -30,7 +30,7 @@ module Believer
30
30
  clazz = cl
31
31
  end
32
32
  if clazz.ancestors.include?(Believer::Base)
33
- puts "Creating table #{clazz.table_name}"
33
+ #puts "Creating table #{clazz.table_name}"
34
34
  clazz.create_table()
35
35
  end
36
36
 
@@ -5,7 +5,7 @@ module Believer
5
5
  extend ActiveSupport::Concern
6
6
 
7
7
  included do
8
- #Believer::Base.observers = Destructor
8
+
9
9
  Believer::Base.after_save do |model|
10
10
  Destructor.instance.after_save(model)
11
11
  end
@@ -16,21 +16,44 @@ module Believer
16
16
  end
17
17
 
18
18
  # Detroys all CqlRecord::Base instances created
19
- class Destructor# < Believer::Observer
19
+ class Destructor
20
20
  include Singleton
21
- # observe Believer::Base
21
+
22
+ def counters_action
23
+ if @counters_action.nil?
24
+ begin
25
+ @counters_action = Believer::Base.environment.believer_configuration[:test][:life_cycle][:counters].to_sym
26
+ rescue
27
+ @counters_action = :destroy
28
+ end
29
+ end
30
+ @counters_action
31
+ end
32
+
33
+ def should_destroy?(model)
34
+ #return false if model.is_counter_instance? && retain_counter_models?
35
+ true
36
+ end
22
37
 
23
38
  def cleanup
24
- unless @observed_models.nil? || @observed_models.empty?
25
- @observed_models.each do |model|
26
- begin
27
- model.destroy
28
- rescue Exception => e
29
- puts "Could not destroy model #{model}: #{e}\n#{e.backtrace.join("\n")}"
39
+ @observed_models.each do |model|
40
+ begin
41
+ if model.is_counter_instance?
42
+ case counters_action
43
+ when :destroy
44
+ model.destroy if should_destroy?(model)
45
+ when :reset
46
+ model.reset_counters!
47
+ when :retain
48
+ end
49
+ else
50
+ model.destroy if should_destroy?(model)
30
51
  end
52
+ rescue Exception => e
53
+ puts "Could not destroy model #{model}: #{e}\n#{e.backtrace.join("\n")}"
31
54
  end
32
- @observed_models = nil
33
- end
55
+ end unless @observed_models.nil? || @observed_models.empty?
56
+ @observed_models = nil
34
57
  end
35
58
 
36
59
  def observed_models
@@ -1,5 +1,5 @@
1
1
  module Believer
2
2
  module Version
3
- VERSION = '0.2.14'
3
+ VERSION = '0.2.15'
4
4
  end
5
5
  end
@@ -14,8 +14,10 @@ describe Believer::Columns do
14
14
  string_cols = Test::Song.columns_with_type(:string)
15
15
  expect(string_cols.size).to eql 4
16
16
 
17
- counter_cols = Test::AlbumSales.columns_with_type(:counter)
18
- expect(counter_cols).to eql [Test::AlbumSales.columns[:sales]]
17
+ counter_cols = Test::AlbumStatistics.columns_with_type(:counter)
18
+ expect(counter_cols.size).to eql 2
19
+ expect(counter_cols).to include Test::AlbumStatistics.columns[:sold]
20
+ expect(counter_cols).to include Test::AlbumStatistics.columns[:produced]
19
21
  end
20
22
 
21
23
  end
@@ -4,58 +4,72 @@ describe Believer::Counting do
4
4
 
5
5
  it 'should detect a counter table' do
6
6
  expect(Test::Artist.is_counter_table?).to eql false
7
- expect(Test::AlbumSales.is_counter_table?).to eql true
7
+ expect(Test::AlbumStatistics.is_counter_table?).to eql true
8
8
  end
9
9
 
10
10
  it 'should detect a changed counter instance' do
11
- album_sales = Test::AlbumSales.new
11
+ album_sales = Test::AlbumStatistics.new
12
12
  expect(album_sales.has_counter_diffs?).to eql false
13
- album_sales.sales.incr
13
+ album_sales.sold.incr
14
14
  expect(album_sales.has_counter_diffs?).to eql true
15
15
  end
16
16
 
17
17
  it 'should be able to set a counter using a number' do
18
- album_sales = Test::AlbumSales.new
19
- album_sales.sales = 2
20
- expect(album_sales.sales.to_i).to eql 2
18
+ album_sales = Test::AlbumStatistics.new
19
+ album_sales.sold = 2
20
+ expect(album_sales.sold.to_i).to eql 2
21
21
  end
22
22
 
23
23
  it 'should be able to undo changes in a counter' do
24
- album_sales = Test::AlbumSales.new
25
- album_sales.sales.incr
24
+ album_sales = Test::AlbumStatistics.new
25
+ album_sales.sold.incr
26
26
  expect(album_sales.has_counter_diffs?).to eql true
27
- album_sales.sales.undo_changes!
27
+ album_sales.sold.undo_changes!
28
28
  expect(album_sales.has_counter_diffs?).to eql false
29
29
  end
30
30
 
31
31
  it 'should be able to reset a counter' do
32
32
  album_attrs = {:artist_name => 'CSNY', :name => 'Deja vu'}
33
- album_sales = Test::AlbumSales.new(album_attrs)
34
- album_sales.sales.incr(4)
35
- expect(album_sales.has_counter_diffs?).to eql true
33
+ album_sales = Test::AlbumStatistics.new(album_attrs)
34
+ album_sales.incr_counter!(:sold, 4)
35
+
36
+ album_sales = Test::AlbumStatistics.where(album_attrs).first
37
+ expect(album_sales.sold.value).to eql 4
38
+ album_sales.sold.reset!
36
39
  album_sales.save
37
40
 
38
- album_sales = Test::AlbumSales.where(album_attrs).first
39
- expect(album_sales.sales.value).to eql 4
40
- album_sales.sales.reset!
41
+ album_sales = Test::AlbumStatistics.where(album_attrs).first
42
+ expect(album_sales.sold.value).to eql 0
43
+ end
44
+
45
+ it 'should be able to reset all counters in one go' do
46
+ album_attrs = {:artist_name => 'CSNY', :name => 'Deja vu'}
47
+ album_sales = Test::AlbumStatistics.new(album_attrs)
48
+ album_sales.sold.incr(4)
49
+ album_sales.produced.incr(7)
50
+ expect(album_sales.has_counter_diffs?).to eql true
41
51
  album_sales.save
42
52
 
43
- album_sales = Test::AlbumSales.where(album_attrs).first
44
- expect(album_sales.sales.value).to eql 0
53
+ album_sales = Test::AlbumStatistics.where(album_attrs).first
54
+ expect(album_sales.sold.value).to eql 4
55
+ expect(album_sales.produced.value).to eql 7
56
+ album_sales.reset_counters!
57
+
58
+ album_sales = Test::AlbumStatistics.where(album_attrs).first
59
+ expect(album_sales.sold.value).to eql 0
60
+ expect(album_sales.produced.value).to eql 0
45
61
  end
46
62
 
47
63
  it 'should be able to persist a counter value' do
48
- album_sales = Test::AlbumSales.new(:artist_name => 'CSNY', :name => 'Deja vu')
49
- album_sales.sales.incr
50
- album_sales.save
51
- expect(album_sales.sales.value).to eql 1
64
+ album_sales = Test::AlbumStatistics.new(:artist_name => 'CSNY', :name => 'Deja vu')
65
+ album_sales.incr_counter!(:sold)
66
+ expect(album_sales.sold.value).to eql 1
52
67
 
53
- album_sales = Test::AlbumSales.where(:artist_name => 'CSNY', :name => 'Deja vu').first
54
- album_sales.sales.incr
55
- album_sales.save
68
+ album_sales = Test::AlbumStatistics.where(:artist_name => 'CSNY', :name => 'Deja vu').first
69
+ album_sales.incr_counter!(:sold)
56
70
 
57
- album_sales = Test::AlbumSales.where(:artist_name => 'CSNY', :name => 'Deja vu').first
58
- expect(album_sales.sales.value).to eql 2
71
+ album_sales = Test::AlbumStatistics.where(:artist_name => 'CSNY', :name => 'Deja vu').first
72
+ expect(album_sales.sold.value).to eql 2
59
73
  end
60
74
 
61
75
  end
@@ -6,8 +6,8 @@ describe Believer::Update do
6
6
  Test::Artist.create(:name => 'Beatles', :label => 'Apple')
7
7
  end
8
8
 
9
- let :album_sales do
10
- Test::AlbumSales.create(:artist_name => 'Beatles', :name => 'Revolver')
9
+ let :album_statistics do
10
+ Test::AlbumStatistics.create(:artist_name => 'Beatles', :name => 'Revolver')
11
11
  end
12
12
 
13
13
  it "should create statement based on hash" do
@@ -21,37 +21,36 @@ describe Believer::Update do
21
21
  end
22
22
 
23
23
  it "should create create a correct statement for a counter increment" do
24
- album_sales.sales.incr(2)
25
- update = Believer::Update.create(album_sales)
26
- expect(update.to_cql).to eql "UPDATE album_sales SET sales = sales + 2 WHERE artist_name = '#{album_sales.artist_name}' AND name = '#{album_sales.name}'"
24
+ album_statistics.sold.incr(2)
25
+ update = Believer::Update.create(album_statistics)
26
+ expect(update.to_cql).to eql "UPDATE album_statistics SET sold = sold + 2 WHERE artist_name = '#{album_statistics.artist_name}' AND name = '#{album_statistics.name}'"
27
27
  end
28
28
 
29
29
  it "should create create a correct statement for a counter decrement" do
30
- album_sales.sales.decr(2)
31
- update = Believer::Update.create(album_sales)
32
- expect(update.to_cql).to eql "UPDATE album_sales SET sales = sales - 2 WHERE artist_name = '#{album_sales.artist_name}' AND name = '#{album_sales.name}'"
30
+ album_statistics.sold.decr(2)
31
+ update = Believer::Update.create(album_statistics)
32
+ expect(update.to_cql).to eql "UPDATE album_statistics SET sold = sold - 2 WHERE artist_name = '#{album_statistics.artist_name}' AND name = '#{album_statistics.name}'"
33
33
  end
34
34
 
35
35
  it "should execute a counter change" do
36
- cur_val = album_sales.sales.to_i
37
- album_sales.sales.incr(2)
38
- update = Believer::Update.create(album_sales)
36
+ cur_val = album_statistics.sold.to_i
37
+ album_statistics.sold.incr(2)
38
+ update = Believer::Update.create(album_statistics)
39
39
  update.execute
40
- cur_album_sales = Test::AlbumSales.where(album_sales.key_values).first
41
- expect(cur_album_sales.sales.to_i).to eql (cur_val + 2)
40
+ cur_album_statistics = Test::AlbumStatistics.where(album_statistics.key_values).first
41
+ expect(cur_album_statistics.sold.to_i).to eql (cur_val + 2)
42
42
  end
43
43
 
44
44
  it "should not execute if no changes are detected in any counter" do
45
- cur_val = album_sales.reload!.sales.to_i
46
- puts "Cur val: #{cur_val}"
47
- album_sales.sales.incr(2)
48
- album_sales.sales.decr(2)
49
- expect(album_sales.sales.to_i).to eql cur_val
50
- update = Believer::Update.create(album_sales)
45
+ cur_val = album_statistics.reload!.sold.to_i
46
+ album_statistics.sold.incr(2)
47
+ album_statistics.sold.decr(2)
48
+ expect(album_statistics.sold.to_i).to eql cur_val
49
+ update = Believer::Update.create(album_statistics)
51
50
  expect(update.execute).to eql false
52
51
 
53
- cur_album_sales = Test::AlbumSales.where(album_sales.key_values).first
54
- expect(cur_album_sales.sales.to_i).to eql cur_val
52
+ cur_album_statistics = Test::AlbumStatistics.where(album_statistics.key_values).first
53
+ expect(cur_album_statistics.sold.to_i).to eql cur_val
55
54
  end
56
55
 
57
56
  it "should update the values" do
@@ -34,11 +34,12 @@ module Test
34
34
  has_single :album, :class => 'Test::Album', :key => [:artist_name, :album_name], :foreign_key => [:artist_name, :name]
35
35
  end
36
36
 
37
- class AlbumSales < Believer::Base
37
+ class AlbumStatistics < Believer::Base
38
38
  column :artist_name
39
39
  column :name
40
40
 
41
- column :sales, :type => :counter
41
+ column :sold, :type => :counter
42
+ column :produced, :type => :counter
42
43
 
43
44
  primary_key :artist_name, :name
44
45
  end
@@ -93,7 +94,7 @@ module Test
93
94
  end
94
95
 
95
96
  Believer::Base.environment = test_environment
96
- CLASSES = [Artist, Album, Song, AlbumSales, Event, Person, Child]
97
+ CLASSES = [Artist, Album, Song, AlbumStatistics, Event, Person, Child]
97
98
  #CLASSES.each {|cl| cl.environment = test_environment}
98
99
 
99
100
  def self.classes
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: believer
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.14
4
+ version: 0.2.15
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors: