class ChefCore::CLIUX::UI::ErrorPrinter
Constants
- DEFAULT_ERROR_NO
Attributes
config[R]
exception[R]
id[R]
pastel[R]
target_host[R]
translation[R]
Public Class Methods
capture_multiple_failures(e, config)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 56 def self.capture_multiple_failures(e, config) e.params << config[:error_output_path] # Tell the operator where to find this info File.open(config[:error_output_path], "w") do |out| e.jobs.each do |j| wrapped = ChefCore::Errors::StandardErrorResolver.wrap_exception(j.exception, j.target_host) ep = ErrorPrinter.new(wrapper: wrapped, config: config) msg = ep.format_body.tr("\n", " ").gsub(/ {2,}/, " ").chomp.strip out.write("Host: #{j.target_host.hostname} ") if ep.exception.respond_to? :id out.write("Error: #{ep.exception.id}: ") else out.write(": ") end out.write("#{msg}\n") end end end
dump_unexpected_error(e)
click to toggle source
Use this to dump an an exception to output. useful if an error occurs in the error handling itself.
# File lib/chef_core/cliux/ui/error_printer.rb, line 86 def self.dump_unexpected_error(e) Terminal.output "INTERNAL ERROR" Terminal.output "-=" * 30 Terminal.output "Message:" Terminal.output e.message if e.respond_to?(:message) Terminal.output "Backtrace:" Terminal.output e.backtrace if e.respond_to?(:backtrace) Terminal.output "=-" * 30 end
error_summary(e)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 185 def self.error_summary(e) if e.is_a? ChefCore::Error # By convention, all of our defined messages have a short summary on the first line. ChefCore::Text.errors.send(e.id).text(*e.params).split("\n").first elsif e.is_a? String e else if e.respond_to? :message e.message else ChefCore::Text.errors.UNKNOWN end end end
new(wrapper: nil, config: nil, exception: nil)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 96 def initialize(wrapper: nil, config: nil, exception: nil) @exception = exception || wrapper.contained_exception @target_host = wrapper.target_host || target_host @command = @exception.respond_to?(:command) ? @exception.command : nil @pastel = Pastel.new @content = StringIO.new @config = config @id = if @exception.is_a? ChefCore::Error @exception.id else DEFAULT_ERROR_NO end @translation = ChefCore::Text::ErrorTranslation.new(id) rescue => e ErrorPrinter.dump_unexpected_error(e) exit! 128 end
show_error(e, config)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 40 def self.show_error(e, config) # Name is misleading - it's unwrapping but also doing further # error resolution for common errors: unwrapped = ChefCore::Errors::StandardErrorResolver.unwrap_exception(e) if unwrapped.class == ChefCore::MultiJobFailure capture_multiple_failures(unwrapped, config) end formatter = ErrorPrinter.new(wrapper: e, exception: unwrapped, config: config) Terminal.output(formatter.format_error) rescue => ex dump_unexpected_error(ex) end
write_backtrace(e, args, config)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 74 def self.write_backtrace(e, args, config) formatter = ErrorPrinter.new(wrapper: e, config: config) out = StringIO.new formatter.add_backtrace_header(out, args) formatter.add_formatted_backtrace(out) formatter.save_backtrace(out, config) rescue => ex dump_unexpected_error(ex) end
Public Instance Methods
_format_single(out, exception, backtrace = nil)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 249 def _format_single(out, exception, backtrace = nil) out.puts "#{exception.class}: #{exception.message}" backtrace ||= exception.backtrace.to_a backtrace.each { |trace| out.puts "\t#{trace}" } end
_unique_trace(backtrace1, backtrace2)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 255 def _unique_trace(backtrace1, backtrace2) i = 1 while i <= backtrace1.size && i <= backtrace2.size break if backtrace1[-i] != backtrace2[-i] i += 1 end backtrace1[0..-i] end
add_backtrace_header(out, args)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 172 def add_backtrace_header(out, args) out.write("\n#{"-" * 80}\n") out.print("#{Time.now}: Error encountered while running the following:\n") out.print(" #{args.join(" ")}\n") out.print("Backtrace:\n") end
add_formatted_backtrace(out)
click to toggle source
mostly copied from gist.github.com/stanio/13d74294ca1868fed7fb
# File lib/chef_core/cliux/ui/error_printer.rb, line 231 def add_formatted_backtrace(out) _format_single(out, exception) current_backtrace = exception.backtrace cause = exception.cause until cause.nil? cause_trace = _unique_trace(cause.backtrace.to_a, current_backtrace) out.print "Caused by: " _format_single(out, cause, cause_trace) backtrace_length = cause.backtrace.length if backtrace_length > cause_trace.length out.print "\t... #{backtrace_length - cause_trace.length} more" end out.print "\n" current_backtrace = cause.backtrace cause = cause.cause end end
format_body()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 146 def format_body if exception.is_a? ChefCore::Error format_workstation_exception elsif exception.is_a? Train::Error format_train_exception else format_other_exception end end
format_decorated()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 132 def format_decorated @content << "\n" @content << format_header @content << "\n\n" @content << format_body @content << "\n" @content << format_footer @content << "\n" end
format_error()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 114 def format_error if translation.decorations format_decorated else format_undecorated end @content.string end
format_header()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 142 def format_header pastel.decorate(@id, :bold) end
format_other_exception()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 216 def format_other_exception t.send(DEFAULT_ERROR_NO).text(exception.message) end
format_train_exception()
click to toggle source
TODO this gets moved to trainerrormapper or simply removed since
many of these issues are now handled in the RemoteTarget::ConnectionFailure
# File lib/chef_core/cliux/ui/error_printer.rb, line 207 def format_train_exception backend, host = formatted_host if host.nil? t.CHEFTRN002.text(exception.message) else t.CHEFTRN001.text(backend, host, exception.message) end end
format_undecorated()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 123 def format_undecorated @content << "\n" @content << format_body if @command @content << "\n" @content << @command.usage end end
format_workstation_exception()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 200 def format_workstation_exception params = exception.params t.send(@id).text(*params) end
formatted_host()
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 220 def formatted_host return nil if target_host.nil? cfg = target_host.config port = cfg[:port].nil? ? "" : ":#{cfg[:port]}" user = cfg[:user].nil? ? "" : "#{cfg[:user]}@" "#{user}#{target_host.hostname}#{port}" end
save_backtrace(output, config)
click to toggle source
# File lib/chef_core/cliux/ui/error_printer.rb, line 179 def save_backtrace(output, config) File.open(config[:stack_trace_path], "ab+") do |f| f.write(output.string) end end
t()
click to toggle source
't' is a convenience method for accessing error i18n error definitions. It also serves as a workaround to let us verify that correct text key lookups happen in unit tests.
# File lib/chef_core/cliux/ui/error_printer.rb, line 34 def t ChefCore::Text.errors end