On irb:rdbg: IRB commands run in a different thread than the debugged program

Open
#1,158 1 comment 4 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Assessment

Difficulty
4/5
Estimated time
3-5 days
Newbie friendliness
35/100
Issue type
Bug
Clarity
Needs clarification
Activity status
Stale
Tech stack
ruby
Domain
devtools

Research direction

Start with the IRB integration enabled by RUBY_DEBUG_IRB_CONSOLE and reproduce the issue using the shown .irbrc command and script.rb. Trace how commands entered in the irb:rdbg console are evaluated relative to the current debug frame and thread. Done means thread-local state is changed in the debugged program context, or an explicit opt-in is provided and covered by a regression test.

Written by the indexing model from the issue text.

Description

Your environment

  • ruby -v: 3.3.7
  • rdbg -v: 1.11.0
  • IRB integration: enabled

Describe the bug
When using debug with IRB integration (RUBY_DEBUG_IRB_CONSOLE=true), commands from IRB entered in the irb:rdbg console are evaluated on a different thread from the currently debugged program thread.

This causes problems when commands depend on thread-local data (Thread.current[:foo]), ActiveRecord::Base.connection (which may be bound per-thread), or other thread-local behaviors, like Apartment gem in our case.

To Reproduce
For example, having this on

# .irbrc
command = Class.new(IRB::Command::Base) do
  category "Helpers"
  description "Testing thread behaviour"
  help_message "Testing thread behaviour"
  define_method(:execute) do |arg|
    puts "Modifying thread variables on: #{Thread.current.object_id}"
    Thread.current[:testing_variable] = arg
  end
end

IRB::Command.register "st", command

with this script

require 'debug'
require 'irb'

debugger;
x=1

Run
RUBY_DEBUG_IRB_CONSOLE=1 bundle exec ruby script.rb

Image

As you can see in the image, the thread variable :testing_variable got modified on another thread different from the current session (1140 instead of 1120)

Expected behavior
When inside an interactive irb:rdbg session, commands should execute on the same thread and binding as the current debug frame (or at least provide a way to opt into that).

Additional context
This happened to us in a helper moving from binding.pry to debugger, the helper uses Apartment::Tenant.switch! from apartment gem which uses Thread variables to know in which tenant is currenly on

Because of this bug, the helper stop working and our state of the current_tenant on the debugger session gets corrupted, inside the db the schema_search_path is right but on the debugger the switch did not happen...

Questions
I’m not fully clear on how debug and IRB interact. I tried to trace where command execution is split so I could make an IRB command run in the debugger’s context, but I couldn’t figure it out. Could you briefly explain the execution flow?

Dominant language
Ruby
Stars
1.3k
Forks
146
PR merge metrics
No merged PRs in 30d

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

More from ruby/debug

All issues in ruby/debug

Similar issues

More Ruby issues

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.