trifle-stats 0.2.1 → 0.3.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 64e5b8835413e4d664240d8b3bcb30f66bc886c139870c5849a1ef0d48ddcdc6
4
- data.tar.gz: 8e499def09294e6b76ec07ea8f906d1b210145a305a82ffabf65665d777786d9
3
+ metadata.gz: 7b1fd5555bb22a06ff4dd05f400d307c5207ee75b2619ed59686ae65ec1d2a35
4
+ data.tar.gz: eaada71f020e696c42d0c89a6e7ce917f7d4377a94b65fe777f8337f747af4e2
5
5
  SHA512:
6
- metadata.gz: e4e9c33a1921fed870c398370e1fc0eeeb1c4f1d33ad1e030ef8a1555cdc5930a4541e2aeae2409ef0738c4b76437a16c195a019cdc8e73752e8e5ae9fda8a78
7
- data.tar.gz: 7b76bf3d1900c3db9c5038ec6c6a4245cfb0ea056385f3dc77f552f6b08f5f0f90816692b21c0763fa91d9ad85c44c0820e85f7824c9b895ed6ecbb54f2adc24
6
+ metadata.gz: 4024c70b822b07415a10e1ae86921d1a0672d4d6ad142205251a4b9d83776362d2c3d2121dbe64a8342fec2421e7521cda1fab8192ecc1370a332b1ee8090d80
7
+ data.tar.gz: 8c05ef417762a1a1bb6919465695301c803d643fd355308a3dbdb74422225942015a89d73fa4f37dd662b38ba018475c9f426b3b8447cc191cebd02885b4aa2c
data/Gemfile.lock CHANGED
@@ -1,7 +1,8 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- trifle-stats (0.2.1)
4
+ trifle-stats (0.3.0)
5
+ pg (>= 1.2)
5
6
  redis (>= 4.2)
6
7
  tzinfo (~> 2.0)
7
8
 
@@ -16,6 +17,7 @@ GEM
16
17
  parallel (1.20.1)
17
18
  parser (3.0.0.0)
18
19
  ast (~> 2.4.1)
20
+ pg (1.2.3)
19
21
  rainbow (3.0.0)
20
22
  rake (12.3.3)
21
23
  redis (4.2.5)
data/lib/trifle/stats.rb CHANGED
@@ -1,6 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'trifle/stats/driver/redis'
4
+ require 'trifle/stats/driver/postgres'
4
5
  require 'trifle/stats/driver/process'
5
6
  require 'trifle/stats/mixins/packer'
6
7
  require 'trifle/stats/nocturnal'
@@ -6,11 +6,9 @@ module Trifle
6
6
  module Stats
7
7
  class Configuration
8
8
  attr_writer :driver
9
- attr_accessor :track_ranges, :separator, :time_zone,
10
- :beginning_of_week
9
+ attr_accessor :track_ranges, :time_zone, :beginning_of_week
11
10
 
12
11
  def initialize
13
- @separator = '::'
14
12
  @ranges = %i[minute hour day week month quarter year]
15
13
  @beginning_of_week = :monday
16
14
  @time_zone = 'GMT'
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'pg'
4
+ require_relative '../mixins/packer'
5
+
6
+ module Trifle
7
+ module Stats
8
+ module Driver
9
+ class Postgres
10
+ include Mixins::Packer
11
+ attr_accessor :client, :table_name, :separator
12
+
13
+ def initialize(client = PG::Connection.new, table_name: 'trifle_stats')
14
+ @client = client
15
+ @table_name = table_name
16
+ @separator = '::'
17
+ end
18
+
19
+ def inc(key:, **values)
20
+ pkey = key.join(separator)
21
+
22
+ self.class.pack(hash: values).each do |k, c|
23
+ _inc_one(key: pkey, name: k, value: c)
24
+ end
25
+ end
26
+
27
+ def _inc_one(key:, name:, value:)
28
+ data = { name => value }
29
+ query = "INSERT INTO trifle_stats(key, data) VALUES ('#{key}', '#{data.to_json}') ON CONFLICT (key) DO UPDATE SET data = jsonb_set(to_jsonb(trifle_stats.data), '{#{name}}', (COALESCE(trifle_stats.data->>'#{name}','0')::int + #{value})::text::jsonb)" # rubocop:disable Metric/LineLength
30
+
31
+ client.exec(query)
32
+ end
33
+
34
+ def set(key:, **values)
35
+ pkey = key.join(separator)
36
+
37
+ _set_all(key: pkey, **values)
38
+ end
39
+
40
+ def _set_all(key:, **values)
41
+ data = self.class.pack(hash: values)
42
+ query = "INSERT INTO trifle_stats(key, data) VALUES ('#{key}', '#{values.to_json}') ON CONFLICT (key) DO UPDATE SET data = '#{data.to_json}'" # rubocop:disable Metric/LineLength
43
+
44
+ client.exec(query)
45
+ end
46
+
47
+ def get(key:)
48
+ pkey = key.join(separator)
49
+
50
+ data = _get(key: pkey)
51
+ return nil if data.nil?
52
+
53
+ self.class.unpack(hash: data)
54
+ end
55
+
56
+ def _get(key:)
57
+ result = client.exec_params(
58
+ "SELECT * FROM #{table_name} WHERE key = $1 LIMIT 1;", [key]
59
+ ).to_a.first
60
+ return nil if result.nil?
61
+
62
+ JSON.parse(result.try(:fetch, 'data'))
63
+ rescue JSON::ParserError
64
+ nil
65
+ end
66
+ end
67
+ end
68
+ end
69
+ end
@@ -9,27 +9,28 @@ module Trifle
9
9
  include Mixins::Packer
10
10
  def initialize
11
11
  @data = {}
12
+ @separator = '::'
12
13
  end
13
14
 
14
15
  def inc(key:, **values)
15
16
  self.class.pack(hash: values).each do |k, c|
16
- d = @data.fetch(key, {})
17
+ d = @data.fetch(key.join(@separator), {})
17
18
  d[k] = d[k].to_i + c
18
- @data[key] = d
19
+ @data[key.join(@separator)] = d
19
20
  end
20
21
  end
21
22
 
22
23
  def set(key:, **values)
23
24
  self.class.pack(hash: values).each do |k, c|
24
- d = @data.fetch(key, {})
25
+ d = @data.fetch(key.join(@separator), {})
25
26
  d[k] = c
26
- @data[key] = d
27
+ @data[key.join(@separator)] = d
27
28
  end
28
29
  end
29
30
 
30
31
  def get(key:)
31
32
  self.class.unpack(
32
- hash: @data.fetch(key, {})
33
+ hash: @data.fetch(key.join(@separator), {})
33
34
  )
34
35
  end
35
36
  end
@@ -8,32 +8,33 @@ module Trifle
8
8
  module Driver
9
9
  class Redis
10
10
  include Mixins::Packer
11
- attr_accessor :prefix
11
+ attr_accessor :client, :prefix, :separator
12
12
 
13
13
  def initialize(client = ::Redis.current, prefix: 'trfl')
14
14
  @client = client
15
15
  @prefix = prefix
16
+ @separator = '::'
16
17
  end
17
18
 
18
19
  def inc(key:, **values)
19
- pkey = [@prefix, key].join('::')
20
+ pkey = ([prefix] + key).join(separator)
20
21
 
21
22
  self.class.pack(hash: values).each do |k, c|
22
- @client.hincrby(pkey, k, c)
23
+ client.hincrby(pkey, k, c)
23
24
  end
24
25
  end
25
26
 
26
27
  def set(key:, **values)
27
- pkey = [@prefix, key].join('::')
28
+ pkey = ([prefix] + key).join(separator)
28
29
 
29
- @client.hmset(pkey, *self.class.pack(hash: values))
30
+ client.hmset(pkey, *self.class.pack(hash: values))
30
31
  end
31
32
 
32
33
  def get(key:)
33
- pkey = [@prefix, key].join('::')
34
+ pkey = ([prefix] + key).join(separator)
34
35
 
35
36
  self.class.unpack(
36
- hash: @client.hgetall(pkey)
37
+ hash: client.hgetall(pkey)
37
38
  )
38
39
  end
39
40
  end
@@ -22,7 +22,7 @@ module Trifle
22
22
  config.ranges.map do |range|
23
23
  at = Nocturnal.new(@at, config: config).send(range)
24
24
  config.driver.inc(
25
- key: [key, range, at.to_i].join(config.separator),
25
+ key: [key, range, at.to_i],
26
26
  **values
27
27
  )
28
28
  end
@@ -22,7 +22,7 @@ module Trifle
22
22
  config.ranges.map do |range|
23
23
  at = Nocturnal.new(@at, config: config).send(range)
24
24
  config.driver.set(
25
- key: [key, range, at.to_i].join(config.separator),
25
+ key: [key, range, at.to_i],
26
26
  **values
27
27
  )
28
28
  end
@@ -27,7 +27,7 @@ module Trifle
27
27
  timeline.map do |at|
28
28
  {
29
29
  at => config.driver.get(
30
- key: [key, range, at.to_i].join(config.separator)
30
+ key: [key, range, at.to_i]
31
31
  )
32
32
  }
33
33
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Trifle
4
4
  module Stats
5
- VERSION = '0.2.1'
5
+ VERSION = '0.3.0'
6
6
  end
7
7
  end
data/trifle-stats.gemspec CHANGED
@@ -34,5 +34,6 @@ Gem::Specification.new do |spec|
34
34
  spec.add_development_dependency('rspec', '~> 3.2')
35
35
  spec.add_development_dependency('rubocop', '1.0.0')
36
36
  spec.add_runtime_dependency('redis', '>= 4.2')
37
+ spec.add_runtime_dependency('pg', '>= 1.2')
37
38
  spec.add_runtime_dependency('tzinfo', '~> 2.0')
38
39
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: trifle-stats
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.1
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jozef Vaclavik
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-04-14 00:00:00.000000000 Z
11
+ date: 2021-04-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -108,6 +108,20 @@ dependencies:
108
108
  - - ">="
109
109
  - !ruby/object:Gem::Version
110
110
  version: '4.2'
111
+ - !ruby/object:Gem::Dependency
112
+ name: pg
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '1.2'
118
+ type: :runtime
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '1.2'
111
125
  - !ruby/object:Gem::Dependency
112
126
  name: tzinfo
113
127
  requirement: !ruby/object:Gem::Requirement
@@ -150,6 +164,7 @@ files:
150
164
  - lib/trifle/stats.rb
151
165
  - lib/trifle/stats/configuration.rb
152
166
  - lib/trifle/stats/driver/README.md
167
+ - lib/trifle/stats/driver/postgres.rb
153
168
  - lib/trifle/stats/driver/process.rb
154
169
  - lib/trifle/stats/driver/redis.rb
155
170
  - lib/trifle/stats/mixins/packer.rb