Breakpoints are not hit when debugging with remote docker-compose ruby

Answered

UPDATE: I've discovered that breakpoints in libraries do work. For example I can set a breakpoint in puma/client.rb, and that breakpoint will be hit. It's code in my own application that won't trigger breakpoints.

I am attempting to follow the instructions here: https://www.jetbrains.com/help/ruby/2019.1/using-docker-as-a-remote-interpreter.html#debug_with_docker_compose

I'm on RubyMine 2019.2 on Windows 10.

To get debugging working with a remote ruby via docker-compose.

The current behavior that I see when starting the debug server is that I can curl the route fine, so the rails server is running, but no breakpoints are ever activated. I don't see any errors in the output.

The only thing I'm doing different from the guide is that I'm using port 8080 instead of 3000, because I have another app (the nuxt front end for my rails app) running on port 3000.

I'm using the 0.7.1.beta1 ruby-debug-ide version here - but this was a last ditch effort to try and fix it. Most of my attempts were with the 0.7.0 version, which is the default when doing gem 'ruby-debug-ide'.

I'm at wit's end trying to figure this out, and I'm out of ideas on what else I can do to try and fix it. Really appreciate any help.

Here are some various files I have set up:

Dockerfile:

FROM ruby:2.6

RUN apt-get update -qq && apt-get install -y postgresql-client
RUN mkdir /railsapp
WORKDIR /railsapp
COPY Gemfile /railsapp/Gemfile
COPY Gemfile.lock /railsapp/Gemfile.lock
RUN bundle install
COPY . /railsapp

COPY entrypoint.sh /usr/bin/
RUN chmod +x /usr/bin/entrypoint.sh
ENTRYPOINT ["entrypoint.sh"]

EXPOSE 8080
EXPOSE 1234
EXPOSE 26166-26168

# CMD ["rails", "server", "-b", "0.0.0.0"]

Docker-compose:

rails:
build: ./back-end
command: tail -f /dev/null
# command: bash -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 8080 -b '0.0.0.0'"
volumes:
- './back-end:/railsapp'
ports:
- '8080:8080'
- "1234:1234"
- "26166:26168"
depends_on:
- db

puma.rb:

# Puma configuration file.
max_threads_count = ENV.fetch("RAILS_MAX_THREADS") { 5 }
min_threads_count = ENV.fetch("RAILS_MIN_THREADS") { max_threads_count }
threads min_threads_count, max_threads_count
port ENV.fetch("PORT") { 8080 }
environment ENV.fetch("RAILS_ENV") { ENV['RACK_ENV'] || "development" }
pidfile ENV.fetch("PIDFILE") { "tmp/pids/server.pid" }
# Note that workers are not supported for JRuby or Windows
#workers ENV.fetch("WEB_CONCURRENCY") { 2 }
preload_app!
plugin :tmp_restart

 

Server output when I start the debugger:

Fast Debugger (ruby-debug-ide 0.7.1.beta1, debase 0.2.5.beta1, file filtering is supported) listens on 0.0.0.0:1234
Connected from 192.168.48.1
14: Starting control thread
14: Processing in control: b /opt/project/back-end/app/models/user.rb:11
14: <breakpointAdded no="1" location="/opt/project/back-end/app/models/user.rb:11"/>
14: Processing in control: b /opt/project/back-end/app/controllers/registrations_controller.rb:7
14: <breakpointAdded no="2" location="/opt/project/back-end/app/controllers/registrations_controller.rb:7"/>
14: Processing in control: start
14: Starting: running program script
=> Booting Puma
=> Rails 5.2.3 application starting in development
=> Run `rails server -h` for more startup options
Puma starting in single mode...
* Version 3.12.1 (ruby 2.5.5-p157), codename: Llamas in Pajamas
* Min threads: 5, max threads: 5
* Environment: development
* Listening on tcp://0.0.0.0:8080
Use Ctrl-C to stop

Server put showing that the code I'm trying to debug is being hit:

rails_1 | Started POST "/users" for 192.168.16.1 at 2019-11-25 13:44:50 +0000
rails_1 | (0.5ms) SELECT "schema_migrations"."version" FROM "schema_migrations" ORDER BY "schema_migrations"."version" ASC
rails_1 | ? /usr/local/bundle/gems/activerecord-5.2.3/lib/active_record/log_subscriber.rb:98
rails_1 | Processing by RegistrationsController#create as JSON
rails_1 | Parameters: {"email"=>"redacted@gmail.com", "password"=>"[FILTERED]", "registration"=>{"email"=>"redacted@gmail.com", "password"=>"[FILTERED]"}}
rails_1 | (0.5ms) BEGIN
rails_1 | ? app/controllers/registrations_controller.rb:9
rails_1 | (0.3ms) ROLLBACK
rails_1 | ? app/controllers/registrations_controller.rb:9
rails_1 | Completed 400 Bad Request in 84ms (Views: 0.6ms | ActiveRecord: 6.1ms)

Editor screenshot to show breakpoints on and before lines shown in the server output log:

 

 

 

0
8 comments

Anyone around on Rubymine support that can help debug this?

I'm also confused by the different sample apps that seem to exist across the various documentation:

One on bitbucket, which seems to be older but is linked to from the documentation about setting up a remote docker-compose interpreter:https://bitbucket.org/rubyminedoc/sample_rails_app_docker/src/master/

And one on github, which is more recently updated: https://github.com/JetBrains/sample_rails_app.git

Seem to be very similar applications... one is just older, but the older one is the one linked in the docs.

Regardless, I tried to set up the newer one on github, just to see if it would reveal something about my current problem, but you can't actually docker-compose build that application:

docker-compose build
db uses an image, skipping
Building web
Step 1/17 : FROM ruby:2.6
---> f1c13927d193
Step 2/17 : RUN curl -sL https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add -
---> Using cache
---> 6c54c1c5aa08
Step 3/17 : RUN echo "deb https://dl.yarnpkg.com/debian/ stable main" | tee /etc/apt/sources.list.d/yarn.list
---> Using cache
---> 557fd4422978
Step 4/17 : RUN apt-get update -qq && apt-get install -y build-essential libpq-dev nodejs postgresql-client yarn
---> Running in cacd5b4bbe08
E: The method driver /usr/lib/apt/methods/https could not be found.
E: Failed to fetch https://dl.yarnpkg.com/debian/dists/stable/InRelease
E: Some index files failed to download. They have been ignored, or old ones used instead.
ERROR: Service 'web' failed to build: The command '/bin/sh -c apt-get update -qq && apt-get install -y build-essential libpq-dev nodejs postgresql-client yarn' returned a non-zero code: 100
0

Hello Zachary,

we have a corresponding tutorial for setting docker compose SDK and debugging with it:
https://www.jetbrains.com/help/ruby/using-docker-compose-as-a-remote-interpreter.html

Could you please check it? In addition, how does in go in RubyMine 2019.3 RC?

0

Olga Kuvardina That was the tutorial I linked in my first post, the one I was following all along.

 

In a stroke of luck I was able to figure this out, but I think there's a bug or issue in rubymine.

What led to the answer was I noticed the output from the debugger with verbose logging turned on:

<breakpointAdded no="1" location="/opt/project/back-end/app/models/user.rb:11"/>

Note that the location of the breakpoint is in a file in `/opt/project/back-end`.

My local project structure is that I have a parent directory with two sub-directories: a front-end directory that contains my nuxt app, and a back-end directory that contains my rails app. I have this back-end directory configured as the rails root.

If you look at my docker-compose.yml, I mount this back-end directory into `/railsapp` on the container:

volumes:
- './back-end:/railsapp'

That's where my app lives on the container, so I was surprised to see that the breakpoint was being created in `/opt/project/back-end`, not in `/railsapp`.

So I created a path mapping in my run configuration:

 

So this maps my local `back-end` directory to the one that Rubymine, evidently, creates in `/opt/project/back-end`.

With this path mapping in place, I started my debug server, curled the endpoint where I had the breakpoint set, and voila, it hits the breakpoint.

This doesn't seem like it should be necessary, though. This opt/project/back-end directory seems like something rubymine creates for its own internal use - as an end user I probably shouldn't have to be aware of it and configure something specially for it in order for the debugger to work.

If it is required, it definitely needs to be added to the documentation.

Is this a bug - should I open an issue for it?

0

To further illustrate what my project structure looks like:

 

Notice how `back-end` is bolded - that's because I set it as the rails root and it is the directory that contains all my Rails application code. My docker-compose.yml and Dockerfile do not live in that directory though, since I use them to to start my entire application cluster, which includes a nuxt front end service and a rails backend service.

I have no idea if this setup confuses rubymine or what, it's just a guess on my part since it's probably outside the norm for most rails setups.

Here is my full docker-compose.yml, to further illustrate my app layout:

version: '3'
services:
db:
image: postgres
volumes:
- 'pgdata:/var/lib/postgresql/data'
ports:
- '5432:5432'
nuxt:
build: ./front-end
command: bash -c "yarn run dev"
volumes:
- './front-end:/nuxtapp'
ports:
- '3000:3000'
rails:
build: ./back-end
command: tail -f /dev/null
# command: bash -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 8080 -b '0.0.0.0'"
volumes:
- './back-end:/railsapp'
ports:
- '8080:8080'
- "1234:1234"
- "26166:26168"
depends_on:
- db
volumes:
pgdata:
external: true
0

Hi, 

Could you check if it helps to add volume

- './back-end:/opt/project'

?

0

I've found out that RubyMine doesn't handle well multi-module project with docker-compose SDK. I'm working of the problem. Fix will be ported to one of bug-fix update of RubyMine 2019.3

0

Andrey Vokin Great to here that it's being worked on, hopefully my report is helpful.

I tried adding the volume mount, but it didn't resolve the issue.

However, if I replace my old volume mount with a new one:

volumes:
- './back-end:/opt/project/back-end'

And then modify my dockerfile/entrypoint to use `/opt/project/backend-end` as the default workdir, I'm able to start a regular server and a debug server with the same run configuration, so that's nice. Before, with the path mapping, I had to use the run config with it to start a debug server and the run config without it to start a regular server.

However I still seem to need the path mapping because its trying to start the server `/railsapp` by default, which doesn't make sense because I removed all references to it and did a `docker-compose build`. I even restarted rubymine, but maybe it has some cached reference to this directory? I don't remember configuring it anywhere else.

0

Zachary Wright, we've submitted a corresponding issue on our tracker so you can follow it there as well: https://youtrack.jetbrains.com/issue/RUBY-25431

0

Please sign in to leave a comment.