coverband-service-client 0.0.10 → 0.0.12.rc.3

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f8d7b393a8c8e038d9ec952cea42d257685e93e68d8e00a1dcd6c5be2c46272c
4
- data.tar.gz: 9aeba81b92f75f43557cbb891b9cee1927e46d03683927d8cfabaad8caf10d46
3
+ metadata.gz: 9fe3bdfd98c39a57b8483038842ddec02d9ba6d64f9aafc9dc47ad5c6d0a07cb
4
+ data.tar.gz: 570f69150be14beb052dc0f218d04782375632ae16a45d8923db8141608c4b21
5
5
  SHA512:
6
- metadata.gz: 466d704e4b97b84c5ae198e997292c3207179cdd185e3087a2067365223cfcb6971b691decb78d7eeb8ed08be88a718c5a448aca5c3abe01c1ff4a76069a9757
7
- data.tar.gz: 0c6b6c7db5364d591c0fbcbcd74e61c04aadebcca9e3ef3dd02b44ae952a6e86e0a800a9110db819bc4cf0d66cd5d43691ad42ad8c157049ba68a1e42ea957f9
6
+ metadata.gz: 73ba2a65ad9c1ed4b0373e22413e26b7d9cf316d4a3885d73aef14e5fed1becdcfffae89df1ef89f71088b0c38c586cd26cd50139eec73410fce68c8859b1696
7
+ data.tar.gz: 9e2293b601ca18ae1db97a0f9d376da80cbfb1b45bc3fdce78106f0c11d8beff2aedff73b6bd77123d92dccfc5ca72d74f2212dc2351b34077180c9c6a87fd1b
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- coverband-service-client (0.0.10)
4
+ coverband-service-client (0.0.12.rc.3)
5
5
  coverband (~> 4.2.4)
6
6
 
7
7
  GEM
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+ require 'socket'
2
3
 
3
4
  COVERBAND_ORIGINAL_START = ENV['COVERBAND_DISABLE_AUTO_START']
4
5
  ENV['COVERBAND_DISABLE_AUTO_START'] = 'true'
@@ -9,7 +10,7 @@ require 'securerandom'
9
10
  module Coverband
10
11
  COVERBAND_ENV = ENV['RACK_ENV'] || ENV['RAILS_ENV'] || (defined?(Rails) ? Rails.env : 'unknown')
11
12
  COVERBAND_SERVICE_URL = ENV['COVERBAND_URL'] || 'https://coverband.io'
12
- COVERBAND_TIMEOUT = (COVERBAND_ENV == 'development') ? 5 : 1
13
+ COVERBAND_TIMEOUT = (COVERBAND_ENV == 'development') ? 5 : 2
13
14
  COVERBAND_ENABLE_DEV_MODE = ENV['COVERBAND_ENABLE_DEV_MODE'] || false
14
15
  COVERBAND_ENABLE_TEST_MODE = ENV['COVERBAND_ENABLE_TEST_MODE'] || false
15
16
  COVERBAND_PROCESS_TYPE = ENV['PROCESS_TYPE'] || 'unknown'
@@ -35,16 +36,38 @@ module Coverband
35
36
  #
36
37
  # NOTES:
37
38
  # * uses net/http to avoid any dependencies
38
- # * currently JSON, but likely better to move to something simpler / faster
39
+ # * currently JSON, but likely better to move to something faster
39
40
  ###
40
41
  class Service < Base
41
- attr_reader :coverband_url, :process_type, :runtime_env
42
+ attr_reader :coverband_url, :process_type, :runtime_env, :hostname, :pid, :stats
42
43
 
43
44
  def initialize(coverband_url, opts = {})
44
45
  super()
45
46
  @coverband_url = coverband_url
46
- @process_type = opts.fetch(:process_type) { COVERBAND_PROCESS_TYPE }
47
+ @process_type = opts.fetch(:process_type) { $PROGRAM_NAME&.split('/')&.last || COVERBAND_PROCESS_TYPE }
48
+ @hostname = opts.fetch(:hostname) { ENV["DYNO"] || Socket.gethostname.force_encoding('utf-8').encode }
49
+ @hostname = @hostname.gsub("'",'').gsub("’",'')
47
50
  @runtime_env = opts.fetch(:runtime_env) { COVERBAND_ENV }
51
+ initialize_stats
52
+ end
53
+
54
+ def initialize_stats
55
+ return unless ENV['COVERBAND_STATS_KEY']
56
+ return unless defined?(Dogapi::Client)
57
+
58
+ @stats = Dogapi::Client.new(ENV['COVERBAND_STATS_KEY'])
59
+ @app_name = defined?(Rails) ? Rails.application.class.module_parent.to_s : "unknown"
60
+ end
61
+
62
+ def report_timing(timing)
63
+ return unless @stats
64
+
65
+ @stats.emit_point(
66
+ 'coverband.save.time',
67
+ timing,
68
+ host: hostname,
69
+ device: "coverband_#{self.class.name.split("::").last}",
70
+ options: {tags: [runtime_env]})
48
71
  end
49
72
 
50
73
  def logger
@@ -68,27 +91,31 @@ module Coverband
68
91
  ENV['COVERBAND_API_KEY'] || Coverband.configuration.api_key
69
92
  end
70
93
 
71
- # TODO: no longer get by type just get both reports in a single request
94
+ ###
95
+ # Fetch coverband coverage via the API
96
+ ###
72
97
  def coverage(local_type = nil, opts = {})
73
98
  local_type ||= opts.key?(:override_type) ? opts[:override_type] : type
74
- uri = URI("#{coverband_url}/api/coverage/#{ENV['COVERBAND_ID']}?type=#{local_type}")
99
+ env_filter = opts.key?(:env_filter) ? opts[:env_filter] : 'production'
100
+ uri = URI("#{coverband_url}/api/coverage?type=#{local_type}&env_filter=#{env_filter}",)
75
101
  req = Net::HTTP::Get.new(uri, 'Content-Type' => 'application/json', 'Coverband-Token' => api_key)
76
102
  res = Net::HTTP.start(uri.hostname, uri.port, use_ssl: uri.scheme == 'https') do |http|
77
103
  http.request(req)
78
104
  end
79
105
  coverage_data = JSON.parse(res.body)
80
- # puts "coverage data: "
81
- # puts coverage_data
82
106
  coverage_data
83
107
  rescue StandardError => e
84
- puts "Coverband: Error while retrieving coverage #{e}"
108
+ logger&.error "Coverband: Error while retrieving coverage #{e}" if Coverband.configuration.verbose || COVERBAND_ENABLE_DEV_MODE
85
109
  end
86
110
 
87
111
  def save_report(report)
88
112
  return if report.empty?
89
113
 
114
+ # We set here vs initialize to avoid setting on the primary process vs child processes
115
+ @pid ||= ::Process.pid
116
+
90
117
  # TODO: do we need dup
91
- # TODO: remove timestamps, server will track first_seen
118
+ # TODO: remove upstream timestamps, server will track first_seen
92
119
  Thread.new do
93
120
  data = expand_report(report.dup)
94
121
  full_package = {
@@ -97,12 +124,18 @@ module Coverband
97
124
  tags: {
98
125
  process_type: process_type,
99
126
  app_loading: type == Coverband::EAGER_TYPE,
100
- runtime_env: runtime_env
127
+ runtime_env: runtime_env,
128
+ pid: pid,
129
+ hostname: hostname,
101
130
  },
102
131
  file_coverage: data
103
132
  }
104
133
  }
134
+
135
+ starting = Process.clock_gettime(Process::CLOCK_MONOTONIC)
105
136
  save_coverage(full_package)
137
+ ending = Process.clock_gettime(Process::CLOCK_MONOTONIC)
138
+ report_timing((ending - starting))
106
139
  end&.join
107
140
  end
108
141
 
@@ -115,6 +148,7 @@ module Coverband
115
148
  def save_coverage(data)
116
149
  if api_key.nil?
117
150
  puts "Coverband: Error: no Coverband API key was found!"
151
+ return
118
152
  end
119
153
 
120
154
  uri = URI("#{coverband_url}/api/collector")
@@ -138,6 +172,50 @@ module Coverband
138
172
  logger&.info "Coverband: Error while saving coverage #{e}" if Coverband.configuration.verbose || COVERBAND_ENABLE_DEV_MODE
139
173
  end
140
174
  end
175
+
176
+ class PersistentService < Service
177
+ attr_reader :http, :stats
178
+
179
+ def initialize(coverband_url, opts = {})
180
+ super
181
+ initiate_http
182
+ end
183
+
184
+ private
185
+
186
+ def initiate_http
187
+ @http = Net::HTTP::Persistent.new name: 'coverband_persistent'
188
+ @http.headers['Content-Type'] = 'application/json'
189
+ @http.headers['Coverband-Token'] = api_key
190
+ @http.open_timeout = COVERBAND_TIMEOUT
191
+ @http.read_timeout = COVERBAND_TIMEOUT
192
+ @http.ssl_timeout = COVERBAND_TIMEOUT
193
+ end
194
+
195
+ def save_coverage(data)
196
+ persistent_attempts = 0
197
+ begin
198
+ if api_key.nil?
199
+ puts "Coverband: Error: no Coverband API key was found!"
200
+ return
201
+ end
202
+
203
+ post_uri = URI("#{coverband_url}/api/collector")
204
+ post = Net::HTTP::Post.new post_uri.path
205
+ body = { remote_uuid: SecureRandom.uuid, data: data }.to_json
206
+ post.body = body
207
+ logger&.info "Coverband: saving (#{post_uri}) #{body}" if Coverband.configuration.verbose
208
+ res = http.request post_uri, post
209
+ rescue Net::HTTP::Persistent::Error => e
210
+ persistent_attempts += 1
211
+ http.shutdown
212
+ initiate_http
213
+ retry if persistent_attempts < 2
214
+ end
215
+ rescue StandardError => e
216
+ logger&.info "Coverband: Error while saving coverage #{e}" if Coverband.configuration.verbose || COVERBAND_ENABLE_DEV_MODE
217
+ end
218
+ end
141
219
  end
142
220
 
143
221
  module Service
@@ -174,13 +252,17 @@ module Coverband
174
252
 
175
253
  private
176
254
 
255
+ def api_key
256
+ ENV['COVERBAND_API_KEY'] || Coverband.configuration.api_key
257
+ end
258
+
177
259
  def logger
178
260
  Coverband.configuration.logger
179
261
  end
180
262
 
181
263
  def save_tracked_views(views:, reported_time:)
182
264
  uri = URI("#{COVERBAND_SERVICE_URL}/api/collector")
183
- req = Net::HTTP::Post.new(uri, 'Content-Type' => 'application/json', 'Coverband-Token' => ENV['COVERBAND_API_KEY'])
265
+ req = Net::HTTP::Post.new(uri, 'Content-Type' => 'application/json', 'Coverband-Token' => api_key)
184
266
  data = {
185
267
  collection_type: 'view_tracker_delta',
186
268
  collection_data: {
@@ -211,8 +293,12 @@ end
211
293
 
212
294
  ENV['COVERBAND_DISABLE_AUTO_START'] = COVERBAND_ORIGINAL_START
213
295
  Coverband.configure do |config|
214
- # Use The Test Service Adapter
215
- config.store = Coverband::Adapters::Service.new(Coverband::COVERBAND_SERVICE_URL)
296
+ # Use the Service Adapter
297
+ if defined?(Net::HTTP::Persistent)
298
+ config.store = Coverband::Adapters::PersistentService.new(Coverband::COVERBAND_SERVICE_URL)
299
+ else
300
+ config.store = Coverband::Adapters::Service.new(Coverband::COVERBAND_SERVICE_URL)
301
+ end
216
302
 
217
303
  # default to tracking views true
218
304
  config.track_views = if ENV['COVERBAND_DISABLE_VIEW_TRACKER']
@@ -1,7 +1,7 @@
1
1
  module Coverband
2
2
  module Service
3
3
  module Client
4
- VERSION = '0.0.10'
4
+ VERSION = '0.0.12.rc.3'
5
5
  end
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: coverband-service-client
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.10
4
+ version: 0.0.12.rc.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dan Mayer
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: exe
11
11
  cert_chain: []
12
- date: 2020-05-21 00:00:00.000000000 Z
12
+ date: 2020-06-21 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: bundler
@@ -106,9 +106,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
106
106
  version: '0'
107
107
  required_rubygems_version: !ruby/object:Gem::Requirement
108
108
  requirements:
109
- - - ">="
109
+ - - ">"
110
110
  - !ruby/object:Gem::Version
111
- version: '0'
111
+ version: 1.3.1
112
112
  requirements: []
113
113
  rubygems_version: 3.0.3
114
114
  signing_key: