require 'cgi' require 'base64' module Spectre::Reporter class HTML def initialize config @config = config @date_format = '%FT%T.%L' end def get_error_info error non_spectre_files = error.backtrace.select { |x| !x.include? 'lib/spectre' } if non_spectre_files.count > 0 causing_file = non_spectre_files.first else causing_file = error.backtrace[0] end matches = causing_file.match(/(.*\.rb):(\d+)/) return [nil, nil] unless matches file, line = matches.captures file.slice!(Dir.pwd + '/') return [file, line] end def read_resource filename file_path = File.join(__dir__, '../../../resources/', filename) File.open(file_path, 'rb') do |file| return file.read end end def report run_infos now = Time.now failures = run_infos.select { |x| x.failure != nil } errors = run_infos.select { |x| x.error != nil } skipped = run_infos.select { |x| x.skipped? } succeeded_count = run_infos.count - failures.count - errors.count - skipped.count if failures.count > 0 overall_status = 'failed' elsif errors.count > 0 overall_status = 'error' elsif skipped.count > 0 overall_status = 'skipped' else overall_status = 'success' end json_report = { command: $COMMAND, project: @config['project'], date: now.strftime(@date_format), environment: @config['environment'], hostname: Socket.gethostname, duration: run_infos.sum { |x| x.duration }, failures: failures.count, errors: errors.count, skipped: skipped.count, succeeded: succeeded_count, total: run_infos.count, overall_status: overall_status, tags: run_infos .map { |x| x.spec.tags } .flatten .uniq .sort, run_infos: run_infos.map do |run_info| failure = nil error = nil if run_info.failed? and not run_info.failure.cause failure_message = "Expected #{run_info.failure.expectation}" failure_message += " with #{run_info.data}" if run_info.data failure_message += " but it failed" failure_message += " with message: #{run_info.failure.message}" if run_info.failure.message failure = { message: failure_message, expected: run_info.failure.expected, actual: run_info.failure.actual, } end if run_info.error or (run_info.failed? and run_info.failure.cause) error = run_info.error || run_info.failure.cause file, line = get_error_info(error) error = { type: error.class.name, message: error.message, file: file, line: line, stack_trace: error.backtrace, } end { status: run_info.status, subject: run_info.spec.subject.desc, context: run_info.spec.context.__desc, tags: run_info.spec.tags, name: run_info.spec.name, desc: run_info.spec.desc, file: run_info.spec.file, started: run_info.started.strftime(@date_format), finished: run_info.finished.strftime(@date_format), duration: run_info.duration, properties: run_info.properties, data: run_info.data, failure: failure, error: error, # the
#{ CGI::escapeHTML(YAML.dump json_report[:config]) }