lib/oneshot_coverage.rb in oneshot_coverage-0.2.2 vs lib/oneshot_coverage.rb in oneshot_coverage-0.3.0

- old
+ new

@@ -17,93 +17,104 @@ OneshotCoverage.emit end end end + OneshotLog = Struct.new(:path, :md5_hash, :lines) + class Reporter - def initialize(target_path:, logger:, max_emit_at_once:) + def initialize(target_path:, logger:, emit_term: nil) @target_path = target_path @logger = logger - @buffer = [] - @max_emit_at_once = max_emit_at_once + @emit_term = emit_term + if @emit_term + @next_emit_time = Time.now.to_i + rand(@emit_term) + end + if defined?(Bundler) @bundler_path = Bundler.bundle_path.to_s end end - def emit - Coverage.result(clear: true, stop: false). + def emit(force_emit) + if !force_emit + if !time_to_emit? + return true + end + end + + logs = + Coverage.result(clear: true, stop: false). select { |k, v| is_target?(k, v) }. - flat_map { |k, v| transform(k, v) }. - each { |row| @buffer << row } + map do |filepath, v| + OneshotLog.new(relative_path(filepath), md5_hash_for(filepath), v[:oneshot_lines]) + end - @buffer.shift(emit_at_once).each do |row| - # Retry when fail to post - unless @logger.post(row) - @buffer << row + @logger.post(logs) + end + + private + + def time_to_emit? + if @emit_term + if @next_emit_time > Time.now.to_i + return false # Do not emit until next_emit_time + else + @next_emit_time += @emit_term end end + true end def is_target?(filepath, value) return false if value[:oneshot_lines].empty? return false if !filepath.start_with?(@target_path) return false if @bundler_path && filepath.start_with?(@bundler_path) true end - def transform(filepath, value) - rel_path = filepath[@target_path.size..-1] - md5_hash = - if md5_hash_cache.key?(filepath) - md5_hash_cache[filepath] - else - md5_hash_cache[filepath] = Digest::MD5.file(filepath).hexdigest - end - - value[:oneshot_lines].map do |line| - { - path: rel_path, - md5_hash: md5_hash, - lineno: line - } - end + def relative_path(filepath) + filepath[@target_path.size..-1] end def md5_hash_cache @md5_hash_cache ||= {} end - def emit_at_once - @max_emit_at_once || @buffer.size + def md5_hash_for(filepath) + if md5_hash_cache.key? filepath + md5_hash_cache[filepath] + else + md5_hash_cache[filepath] = Digest::MD5.file(filepath).hexdigest + end end end module_function def start Coverage.start(oneshot_lines: true) # To handle execution with exit immediatly at_exit do - OneshotCoverage.emit + OneshotCoverage.emit(force_emit: true) end end - def emit - @reporter&.emit + def emit(force_emit: false) + @reporter&.emit(force_emit) end - def configure(target_path:, logger: OneshotCoverage::Logger::NullLogger.new, max_emit_at_once: nil) + def configure(target_path:, logger: OneshotCoverage::Logger::NullLogger.new, emit_term: nil) target_path_by_pathname = if target_path.is_a? Pathname target_path else Pathname.new(target_path) end @reporter = OneshotCoverage::Reporter.new( target_path: target_path_by_pathname.cleanpath.to_s + "/", logger: logger, - max_emit_at_once: max_emit_at_once + emit_term: emit_term, ) end end