headcount 0.6.0 → 0.7.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.
@@ -1,5 +1,13 @@
1
1
  # Changelog
2
2
 
3
+ # Version 0.7.0 - 2012-04-06
4
+
5
+ * Added seeding support and ability to get a headcount for any given time
6
+
7
+ # Version 0.6.0 - 2012-04-06
8
+
9
+ * What was added?
10
+
3
11
  # Version 0.5.0 - 2012-04-06
4
12
 
5
13
  * Added timestamping
data/README.md CHANGED
@@ -25,7 +25,7 @@ Configure Headcount through a rails initializer. Here's an example:
25
25
  # config/initializers/headcount.rb
26
26
  Headcount.configure do |config|
27
27
  config.path = 'db/headcount.json' # default
28
- config.timestamp = '' # default (YYYY-MM-DD HH:MM:SS)
28
+ config.timestamp = '%Y-%m-%d %H:%M:%S' # default (YYYY-MM-DD HH:MM:SS)
29
29
 
30
30
  # by default Headcount will use the underlying table name for the key
31
31
  count User # :users key implied
@@ -58,6 +58,23 @@ If you'd like to have the results written to disk instead just use the bang vers
58
58
  Headcount.count! # will append the results to the output file
59
59
  ```
60
60
 
61
+ ## Seeding
62
+
63
+ If you have a history of data that you'd like to generate headcounts you can give the `seed` method a try.
64
+
65
+ **Notice** For seeding to work your queries must respond to `where` and the underlying table must have a `created_at` column. If resulting historical query is invalid, the headcount will just fall back to the original query.
66
+
67
+ ```
68
+ Headcount.seed(2.years.ago, 1.day) # preview the historical headcounts
69
+ ```
70
+
71
+ If you're happy with the data, simply call the bang version to write it to disk:
72
+
73
+ ```
74
+ Headcount.seed!(2.years.ago, 1.day) # WARNING: this will overwrite any existing data
75
+ ```
76
+
77
+
61
78
  ## Scheduling
62
79
 
63
80
  Your options are open as far as scheduling goes. If you like [crontab](http://crontab.org/), use crontab. If you prefer [clockwork](https://github.com/tomykaira/clockwork), use clockwork.
@@ -2,11 +2,14 @@ require 'headcount/support'
2
2
  require 'headcount/registry'
3
3
  require 'headcount/persistence'
4
4
  require 'headcount/configuration'
5
+ require 'headcount/history'
5
6
  require 'headcount/railtie' if defined?(Rails)
6
7
 
7
8
  module Headcount
8
9
  @@registry = Headcount::Registry.new
9
-
10
+
11
+ include Headcount::History
12
+
10
13
  class << self
11
14
  def register(key, query)
12
15
  key.to_sym.tap do |key|
@@ -17,15 +20,23 @@ module Headcount
17
20
  def find(key)
18
21
  @@registry[key.to_sym]
19
22
  end
20
-
21
- def count(key = nil)
22
- if key
23
+
24
+ # this method is getting a little messy -- need to clean it up
25
+ # arg can either be a symbol or a time instance
26
+ def count(arg = nil)
27
+ if arg.is_a?(Symbol)
28
+ key = arg
23
29
  count_for(key)
24
30
  else
25
31
  {}.tap do |headcount|
26
- headcount[:timestamp] = Headcount::Support.timestamp_for(DateTime.now)
32
+ now = DateTime.now
33
+ time = arg || now
34
+ headcount[:timestamp] = Headcount::Support.timestamp_for(time)
27
35
 
28
36
  @@registry.each do |key, query| # using map would return an array here
37
+ query = query_for_time(query, time) unless time == now
38
+ query = yield query if block_given? # can alter the query at execution
39
+
29
40
  headcount[key] = query.count
30
41
  end
31
42
  end
@@ -33,7 +44,9 @@ module Headcount
33
44
  end
34
45
 
35
46
  def count!
36
- persist(count)
47
+ count.tap do |headcount|
48
+ persist(headcount)
49
+ end
37
50
  end
38
51
 
39
52
  def reset
@@ -0,0 +1,37 @@
1
+ module Headcount
2
+ module History
3
+ extend ActiveSupport::Concern
4
+
5
+ module ClassMethods
6
+ def seed(start, interval)
7
+ time = start
8
+ now = DateTime.now
9
+ headcounts = []
10
+
11
+ while time < now
12
+ headcounts << Headcount.count(time)
13
+ time += interval
14
+ end
15
+
16
+ headcounts
17
+ end
18
+
19
+ def seed!(start, interval)
20
+ seed(start, interval).tap do |headcounts|
21
+ persist(headcounts, {:reset => true})
22
+ end
23
+ end
24
+
25
+ private
26
+ def query_for_time(query, time)
27
+ begin
28
+ query.where('created_at <= ?', time).tap do |modified_query|
29
+ modified_query.count # will trigger an error immediately so we can handle it below
30
+ end
31
+ rescue
32
+ query # just return the original query
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -3,8 +3,9 @@ require 'headcount/persistence/file'
3
3
  module Headcount
4
4
  class << self
5
5
  private
6
- def persist(headcount)
7
- persistence_handler.save(count)
6
+ def persist(headcounts, options = {})
7
+ headcounts = Array.wrap(headcounts)
8
+ persistence_handler.save(headcounts, options)
8
9
  end
9
10
  end
10
11
  end
@@ -6,9 +6,13 @@ module Headcount
6
6
  @format = format
7
7
  end
8
8
 
9
- def save(headcount)
9
+ def save(headcounts, options = {})
10
+ ::File.delete(@path) if ::File.exists?(@path) if options[:reset]
11
+
10
12
  ::File.open(@path, 'a') do |file|
11
- file.puts headcount.to_json
13
+ headcounts.each do |headcount|
14
+ file.puts headcount.to_json
15
+ end
12
16
  end
13
17
  end
14
18
  end
@@ -1,3 +1,3 @@
1
1
  module Headcount
2
- VERSION = "0.6.0"
2
+ VERSION = "0.7.0"
3
3
  end
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: headcount
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 0.6.0
5
+ version: 0.7.0
6
6
  platform: ruby
7
7
  authors:
8
8
  - Ryan Mohr
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2012-04-06 00:00:00 Z
13
+ date: 2012-04-07 00:00:00 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rails
@@ -101,6 +101,7 @@ extra_rdoc_files: []
101
101
  files:
102
102
  - lib/headcount/configuration.rb
103
103
  - lib/headcount/exceptions.rb
104
+ - lib/headcount/history.rb
104
105
  - lib/headcount/persistence/file.rb
105
106
  - lib/headcount/persistence.rb
106
107
  - lib/headcount/railtie.rb