diff --git a/CHANGELOG.md b/CHANGELOG.md index af25e2044..ff1163894 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ - Add `include_sentry_event` matcher for RSpec [#2424](https://github.com/getsentry/sentry-ruby/pull/2424) - Add support for Sentry Cache instrumentation, when using Rails.cache ([#2380](https://github.com/getsentry/sentry-ruby/pull/2380)) - Add support for Queue Instrumentation for Sidekiq. [#2403](https://github.com/getsentry/sentry-ruby/pull/2403) +- Add support for string errors in error reporter ([#2464](https://github.com/getsentry/sentry-ruby/pull/2464)) - Reset trace_id and add root transaction for sidekiq-cron [#2446](https://github.com/getsentry/sentry-ruby/pull/2446) Note: MemoryStore and FileStore require Rails 8.0+ diff --git a/sentry-rails/lib/sentry/rails/error_subscriber.rb b/sentry-rails/lib/sentry/rails/error_subscriber.rb index dad598c51..5a10e3322 100644 --- a/sentry-rails/lib/sentry/rails/error_subscriber.rb +++ b/sentry-rails/lib/sentry/rails/error_subscriber.rb @@ -27,7 +27,16 @@ def report(error, handled:, severity:, context:, source: nil) hint.merge!(context.delete(:hint)) end - Sentry::Rails.capture_exception(error, level: severity, contexts: { "rails.error" => context }, tags: tags, hint: hint) + options = { level: severity, contexts: { "rails.error" => context }, tags: tags, hint: hint } + + case error + when String + Sentry::Rails.capture_message(error, **options) + when Exception + Sentry::Rails.capture_exception(error, **options) + else + raise ArgumentError, "Expected an Exception or a String, got: #{error.inspect}" + end end end end diff --git a/sentry-rails/spec/sentry/rails_spec.rb b/sentry-rails/spec/sentry/rails_spec.rb index dd069db81..fe53b2b1c 100644 --- a/sentry-rails/spec/sentry/rails_spec.rb +++ b/sentry-rails/spec/sentry/rails_spec.rb @@ -356,6 +356,25 @@ def capture_in_separate_process(exit_code:) expect(transport.events.count).to eq(0) end + + it "captures string messages through error reporter" do + Rails.error.report("Test message", severity: :info, context: { foo: "bar" }) + + expect(transport.events.count).to eq(1) + event = transport.events.first + + expect(event.message).to eq("Test message") + expect(event.level).to eq(:info) + expect(event.contexts).to include({ "rails.error" => { foo: "bar" } }) + expect(event.tags).to include({ handled: true }) + end + + it "crashes if the message is not a string or an exception" do + # Subscriber crashes are handled and logged as fatal, so this doesn't raise here + Rails.error.report(312, severity: :info, context: { foo: "bar" }) + + expect(transport.events.count).to eq(0) + end end end end