{"record":{"id":"24c27d5332b463c0","repo":"sj26/mailcatcher","slug":"backtrace","errorCode":null,"errorMessage":"    Backtrace:","messagePattern":"    Backtrace:","errorType":"console","errorClass":null,"httpStatus":null,"severity":"info","filePath":"lib/mail_catcher.rb","lineNumber":63,"sourceCode":"    windows? or which? \"open\"\n  end\n\n  def browse url\n    if windows?\n      system \"start\", \"/b\", url\n    elsif which? \"open\"\n      system \"open\", url\n    end\n  end\n\n  def log_exception(message, context, exception)\n    gems_paths = (Gem.path | [Gem.default_dir]).map { |path| Regexp.escape(path) }\n    gems_regexp = %r{(?:#{gems_paths.join(\"|\")})/gems/([^/]+)-([\\w.]+)/(.*)}\n    gems_replace = '\\1 (\\2) \\3'\n\n    puts \"*** #{message}: #{context.inspect}\"\n    puts \"    Exception: #{exception}\"\n    puts \"    Backtrace:\", *exception.backtrace.map { |line| \"       #{line.sub(gems_regexp, gems_replace)}\" }\n    puts \"    Please submit this as an issue at https://github.com/sj26/mailcatcher/issues\"\n  end\n\n  @@defaults = {\n    :smtp_ip => \"127.0.0.1\",\n    :smtp_port => \"1025\",\n    :http_ip => \"127.0.0.1\",\n    :http_port => \"1080\",\n    :http_path => \"/\",\n    :messages_limit => nil,\n    :verbose => false,\n    :daemon => !windows?,\n    :browse => false,\n    :quit => true,\n  }\n\n  def options\n    @@options","sourceCodeStart":45,"sourceCodeEnd":81,"githubUrl":"https://github.com/sj26/mailcatcher/blob/18a9cb7a79b321b2bcb51608dd793ea51255189e/lib/mail_catcher.rb#L45-L81","documentation":"The backtrace section of log_exception (lib/mail_catcher.rb:63). Each frame of exception.backtrace is printed with gem installation directories rewritten by the regex on line 58 into `gemname (version) relative/path`, so frames read like `mail (2.7.1) lib/mail/message.rb:123` instead of absolute gem paths. It is printed with puts as the label followed by the mapped lines.","triggerScenarios":"Printed automatically on the same conditions as the `***` header: any exception caught by rescue in MailCatcher::Smtp#receive_message (smtp.rb:62) or in the websocket send callback (application.rb:89). The rewriting itself can raise ArgumentError if Gem.path/Gem.default_dir contain regex-metacharacter characters, but in practice it always renders the cleaned trace.","commonSituations":"Needing to know whether the fault is inside mailcatcher, the sqlite3 gem, the mail gem, or faye-websocket when only a one-line symptom is visible; debugging in daemon mode where the report scrolls away; comparing traces across gem versions after a bundle update changed behavior.","solutions":["Read the deepest non-gem frame first — it names the code at fault (e.g. `sqlite3 (1.4.x)` frames point at the DB layer, `mail (...)` frames at MIME parsing).","Reproduce with `mailcatcher --foreground --verbose` to get the trace directly in your terminal.","Pin the guilty gem back to the last working version (common outcome: sqlite3, mail) and restart.","If frames point into mailcatcher's own lib/, file the issue with this trace attached."],"exampleFix":null,"handlingStrategy":"fallback","validationCode":null,"typeGuard":null,"tryCatchPattern":"# Capture the full report (context + exception + rewritten backtrace) yourself when embedding\nbegin\n  MailCatcher::Mail.add_message(msg)\nrescue => e\n  File.write(\"mailcatcher-crash.log\", [e.message, *e.backtrace].join(\"\\n\"))\n  raise unless e.is_a?(SQLite3::Exception) # re-raise what you cannot handle\nend","preventionTips":["Keep daemon logs rotated and retained so rewritten gem traces survive for triage.","Before upgrading Ruby or the mail/mailcatcher gems, note versions; the rewritten frames let you diff which gem moved.","Reproduce crashes with --foreground so the trace lands in a terminal you can copy."],"tags":["logging","stack-trace","diagnostics","rubygems"],"backgroundTag":"stack-trace-logging","analyzedSha":"18a9cb7a79b321b2bcb51608dd793ea51255189e","analyzedAt":"2026-08-21T18:56:10.605Z","schemaVersion":2},"datasetVersion":"2026-08-21T23:17:16.201Z"}