Debug dotnet applications in docker remotely using VS code
Recently, the official version of .Net 5 was released, and I will also take a little bit of heat.
As shown in the title, what I am going to talk about this time is the dotnet application in debug docker. In fact, I have written essays on similar topics before, friends who are interested in reviewing can take a look: VS code docker debugging asp.net core
First of all, the previous essay was relatively one-sided, because I was just getting in touch with docker and using vscode to write code at that time, and several problems left over at that time were also solved in this article.
Secondly, with the popularity of docker, vscode natively supports remote debugging. These features reduce the difficulty of debugging applications in docker, and this technology, not only limited to dotnet, can be covered by nodejs, python and other technology stacks.
In this essay, I will not state why we need to debug applications in docker. In short, there is a need.
how is it achieved
Here is a schematic diagram of vs code for remote debugging.
It can be seen that the complete code, workspace extension components, and sdk are all in the remote OS. In our scenario, it is under the docker container.
Under our local operating system, we only need some vs code and simple components.
Native OS essential apps/tools
1. VS code, the version should be as new as possible. I am using version 1.51.0. I really don't know which version of VS code supports remote server.
2. VS code extension :Remote Development. It is a pack that will install remote debugging extensions for container, WSL, and SSH at the same time. It's like the picture below
3. Docker for Desktop. Since the local code will be used in the following to map to the container, you need to use the full docker, not just a CLI.
4. hmm.... that should be all, this machine does not even need to install the c# extension of dotnet sdk and vscode.
5. Since there is no sdk locally, we also need a code that has been created. Due to time constraints, I have already prepared:
build docker image
1. Go to the checkout code on the link , open vs code, and then open src in the git directory.
What I see on vs code is like this, there is a sln file and a csproj in it.
2. Open the terminal window under vs code, or you can open CMD/terminal under the system, and then cd to the src directory.
Execute the following command
If you operate this for the first time, it will take a long time because you have to pull the sdk image on the docker hub.
After the build is successful, the following prompt will appear
3. We use the docker command to check again whether the image we want has been generated
Container up and running
1. Run the container using the following command. We can see output similar to the following image on terminal/CMD
2. Open the address (http://localhost:5155/) through the browser, and you can see that there is some content
Attach to Container
1. Open Remote Explorer from the sidebar of vscode
Then here you can see what Containers are in your docker. If it is used for the first time, under Other Containers, if it has been used before, it will be under Container
2. Right-click the Container to be used, and then click attach to container
3. After a few seconds, a new vscode window will automatically open. (If you did not install the aforementioned Remote Development extension before starting, you will need to wait a few minutes to complete the installation before opening a new vscode window)
After the vs code window is opened, the Start Dev Container prompt will appear in the lower right corner of the window. When we click it, the TermIcal window will appear.
Click the prompt in the lower right corner of the above figure, the Terminal window will appear, and in the lower left corner, it shows that it has been linked to the container kiwiho/remote-debug-sample
4. Click Explorer next to vs code, we can see that the code on the container can be opened, and it is also specially indicated that this is a file in the container
5. If we open one of the C# files at random, the necessary extensions that are not required for C# debugging will be automatically installed. In fact, the automatic installation of extensions can be completed by custom files here, but I will not expand them here.
If it is not installed automatically, please install it yourself
6. After the C# extension is installed, in the debug place, create a debug configuration file in the usual way of using vs code locally.
In the debug window click create a launch.json file.
Then there will be a pop-up window, we choose dotnet Core
Then the configuration file is generated, and we mainly use the .NET Core Attach inside. The rest you don't need can be deleted by yourself
1. Start the .NET Core Attach debug configuration. We choose the first one under the pop-up window, we need to pay attention here, we have to choose the process to run by ourselves. If you are using dotnet run, you need to select the corresponding process
Set a breakpoint on the last line of the Index method of HomeController and open http://localhost:5155/Home
After a while, you can see that the breakpoint has been entered.
The remote debugging we need has been implemented
Hot deployment and debugging
In fact, in the development process, what we need is probably not only debugging, but also code modification.
Then if you haven't changed the code once, you have to go through all the above steps, isn't it a pit.
So we need to introduce the dotnet watch command.
Important: But to use this function, the container and the code must be on the same computer! The previous steps are true remote debugging, and the container can run on other machines. The following steps must be on the same machine! ! !
Modify docker-compose configuration and dockerfile
1. docker-compose.override.yml , remove the code comments of volumes. Change it to the following
2. Modify Dockerfile.Develop, comment on the last 2 paragraphs of code and remove the comments. This is what it looks like after modification.
There are 2 points to pay special attention to here:
The current dotnet sdk image cannot use Debian, I will change it to 5.0-focal here, which is using Ubuntu
The last Entrypoint must be added with --no-launch-profile, otherwise, the launchsetting in the code will be used, which will cause asp.net not to use port 80
Rebuild the Image and deploy the Container
1. Build Image
2. Deploy the Container
Configure remote VS code
1. Follow the steps above, attach to container, install the VS code extension, and configure the .net core attach debug file
2. Start debugging, breakpoints. Here we need to choose the one of dotnet watch run
First, we enter the same address (), and we can see that json returns hello, world! words.
Then we modify the local code and add the code on line 11. It should be noted that we changed the local file! !
Save file changes! Then you can see Application is shutting down... File changed, Started and other prompts under Terminal, which proves that the code has been hot deployed
Let's go to the browser and see the results, it turns out. The code is indeed successfully modified and hot deployed
Disable debugging and attach to container
In fact, in many cases, we do not need to debug, just need to change the code for verification, then there is no need to attach to container and debug.
Just start the container, modify the code you want to change locally, save it and see the result.
Found this article to be very lengthy, consider it a beginner's guide.
Because I did encounter a little difficulty in this area at the beginning, I felt the need to share in detail.
It's not like a few sentences on the Internet, attached to the container, and then debugged.
What else is there that I'm hiding and didn't tell you
First of all, we need to know that the necessary conditions for debugging
1. The code is released with Debug, or after Release, the *.pdb file must be included
2. For debugging, we need sdk, not runtime
1. This time I was debugging the .net5 code for the first time, and found that the Image of sdk:5.0 was faulty, and I couldn't use dotnet watch normally. Later, I chose to use sdk:5.0-focal, and it was fine.
2. Some people must be wondering why I use docker-compose for such a simple project. In fact, the reason is that it is relatively troublesome to use the cache for docker build. So I use docker-compose to speed up the generation of Image each time