Remote deployment and debugging of dotnet core applications on * nix

  • Tutorial


Solving a rather elementary problem and not having mastered the Spartan development conditions for ESP8266, I decided to return to the cozy world of .Net in which there is also auto-completion and debugging.

So, we have on hand:

  • Computer with Windows 10 Pro Build 1803 (however, almost everything written below can be done on * nix with minimal changes)
  • Orange Pi Zero with Raspbian Server installed
  • The desire to write C # code and debug on the device simply by pressing F5

Environment preparation

Developer's computer

Development will be conducted in Visual Studio Code with the extension installed C#.

Requires installed .NET Core SDK .

It is also desirable to have a version of Windows 10 1803 , since OpenSSH is installed by default into it. In earlier versions of Windows 10, OpenSSH can be installed via Manage Add-ons. However, this does not prohibit the use of third-party SSH clients.

Target device


The first step is to configure SSH access by key. Excellent instructions from Digital Ocean perfectly help with this .


Private keys can be stored as separate files in the .ssh folder, but I recommend using the pretty convenient KeePass + KeeAgent combination . KeePass provides secure key storage, and KeeAgent provides keys. In order for it to work with the client built into Windows SSH, you need to activate the appropriate experimental setting. *

Installing the .NET Core SDK

Since the official Microsoft repository does not contain packages compiled for ARM32, you need to install the .NET Core SDK manually.

First of all, we need to install the dependencies listed in the documentation .

apt-get install liblttng-ust0 libcurl3 libssl1.0.0 libkrb5-3 zlib1g libicu52 gettext

Now you can install the SDK.

Direct link to the archive with the SDK can be taken from the SDK page on GitHub .

curl -sSL -o dotnet.tar.gz
sudo mkdir -p /opt/dotnet && sudo tar zxf dotnet.tar.gz -C /opt/dotnet
sudo ln -s /opt/dotnet/dotnet /usr/local/bin

Installing Remote Debugger

The install script of the remote debugger uses unzip:

sudo apt-get install unzip

To install the remote debugger, run the following command:

curl -sSL | bash /dev/stdin -r linux-arm -v latest -l ~/vsdbg

Configure VS Core for remote deployment and debugging on linux

1. Create a project

It's all very simple:

mkdir DemoProject
cd DemoProject
dotnet new console

2. Create configuration files

Open the folder with the project. The C # extension automatically downloads the OmniSharp and .NET Core Debuger packages, if it hasn’t been done before. After that, we will be asked to create assets for building and debugging the project. We agree to this. As a result, a folder .vscodewith files tasks.jsonand launch.json. These files describe the tasks you can perform and launch configurations. By default, a debugger launch configuration is created, depending on the build task.

3. Rules configuration files

The basic idea of ​​launching and debugging on a remote device is to create tasks that collect the project and copy it to the device and launch configuration using a remote debugger.
I will give a description of the finished tasks:

    "version": "2.0.0",
    "tasks": [
            "label": "publish",
            "command": "dotnet",
            "type": "process",
            "args": [
            "label": "copy-to-device",
            "dependsOn": "publish",
            "command": "scp",
            "type": "process",
            "args": [

The task publishinvokes a command dotnet publishthat packs the application and its dependencies in the deployment folder.

The team copy-to-deviceuses scpto copy the published application to a remote device. Pay attention to the point at the end of the path from which copying takes place. If you do not specify it, then at subsequent copies the folder publishwill be placed in DemoProject, and will not overwrite it. The parameter dependsOnindicates what is copy-to-devicedependent on publish. Thus before performing copy-to-deviceexecuted publish.

Next, you need to configure the remote launch and debug configuration:

   "version": "0.2.0",
   "configurations": [
            "name": ".NET Core Launch (console)",
            "type": "coreclr",
            "request": "launch",
            "preLaunchTask": "copy-to-device",
            "program": "~/DemoProject/DemoProject.dll",
            "args": [],
            "cwd": "~/DemoProject",
            "console": "internalConsole",
            "stopAtEntry": false,
            "internalConsoleOptions": "openOnSessionStart",
            "pipeTransport": {
                "pipeCwd": "${workspaceRoot}",
                "pipeProgram": "ssh",
                "pipeArgs": [ "-T", "<target_user>@<target_ip>" ],
                "debuggerPath": "~/vsdbg/vsdbg",
                "quoteArgs": true

The parameter "preLaunchTask": "copy-to-device"indicates that a task must be completed before starting a debugging session copy-to-device. Thus, each time before debugging, the project will be published and copied to the target device.

This parameter pipeTransportallows you to configure the use of a remote debugger. In this case, as a program that provides transport is used ssh, but nothing does not prevent the use plink.exeof a set of programs putty.

4. Debugging

After pressing F5, the project builds, copies and launches the application on the remote device. Debugging is completely identical to local.

After completing the application, I received a message every time Error from pipe program 'ssh': Process is terminating due to StackOverflowException . Judging by the open issue on GitHub, this is a known debugger problem. But since the error occurs after the debugging is completed, you can ignore this.

Resources used

Setting up a Raspberry Pi
Omnisharp-vscode Remote Debugging On Linux Arm
dotnet publish command help
Configuring launch.json for C # debugging
Visual Studio Integrated with External Tools via Tasks

Also popular now: