Skip to content

Dev Containers

Thomas Hahn edited this page Dec 12, 2024 · 3 revisions

The Dev Containers extension allows us to use a docker container as a full-featured development environment. The source code can either be mounted into the container from the local filesystem or copied or cloned into it once it is running.

Install the extension

To install/enable the extension, follow the same steps as in the previous sections.

devcont_ext

We also install the Docker extension (although it is not strictly necessary).

docker_ext

Get started

Docker container

In order to use the Dev containers extension, we have to build a docker container beforehand or at least provide a Dockerfile.

For our toy repository, we use the following Dockerfile based on Ubuntu 24.04.

The container can be built by running

cd moderncpp_vscode.src/vscode
docker build -t moderncpp:vscode .

from the terminal.

To take a look around in the container, execute

docker run -it --rm moderncpp:vscode

devcontainer.json file

The devcontainer.json file can be used to specify

  • the container image,
  • the VS Code extensions for the container,
  • the VS Code settings for the container,
  • how to mount/copy/clone the workspace and
  • various other things.

Create a new directory .devcontainer in your local workspace and copy the devcontainer.json file:

mkdir .devcontainer
cp moderncpp_vscode.src/vscode/devcontainer.json .devcontainer/

You should not have to adjust any settings there.

Let's take a look at the most important ones:

  • "image": "moderncpp:vscode": The container image. We use the one that we have built in the previous step.
  • "customizations": { "vscode": { "extensions": [ ... ] } }: The VS Code extensions that we want to use in the container.
  • "customizations": { "vscode": { "settings": { ... } } }: The VS Code settings for the container. We can mostly use the local user settings except for some adjustments to path variables.
  • "workspaceMount": "source=${localWorkspaceFolder},target=/home/thahn/moderncpp_vscode,type=bind": Specifies that we want to mount our local workspace folder in the container at /home/thahn/moderncpp_vscode. Since we mount the workspace, any changes we make to our workspace in the container will also apply to our local workspace.
  • "workspaceFolder": "/home/thahn/moderncpp_vscode": Workspace folder that should open when connecting to the container.

Open the folder in the container

Now we are ready to start our development container.

  • Open our local workspace folder moderncpp_vscode (if it is not opened already)
  • Run >Dev Containers: Reopen in Container

If successful, you should see something like

devcont_status_bar

in the bottom left corner.

Container settings

To check/change the VS Code container settings,

  • Run >Preferences: Open Remote Settings (JSON) (Dev Container: vscode @ desktop-linux)

Extensions

To install/enable/disable extensions in the container,

  • Go to Extensions in the activity bar

Configure CMake

Before running CMake, we have to comment out our project settings in .vscode/settings.json since they are only valid for the local machine:

devcont_project_settings

Then we can follow the same steps as in CMake Tools:

  • Run >CMake: Configure
    • Choose a kit (Clang 18.1.3 in our case)
    • Select the toplevel CMakeLists.txt file: ${workspaceFolder}/moderncpp_vscode.src/CMakeLists.txt
  • Run >CMake: Select a Variant if you want to use a different variant

CMake Tools should now configure your project and create a new build directory (./build.devcont.Clang-18.1.3-Debug in our case):

devcont_cmake_config

Build and Run

  • Run >CMake: Build

This results in a compilation error since we are using Clang 18.1.3 which does not support std::print yet. To fix this, we simply fall back to std::cout:

  • Open ./examples/ex3.cpp
  • Change its content to
#include <iostream>

int main() {
    std::cout<< "Hello world!" << std::endl;
}
  • Run >CMake: Build again

Now everything should compile and you can run tests and examples just like you would locally.

clangd

To check that clangd works as expected, we open again ./src/linalg.cpp and hover over nda::matrix.

clangd should give us some information on the matrix type:

devcont_clangd

CodeLLDB and Debugging

To debug our code in the container, we just have to add a new configuration to the launch.json file in the .vscode folder:

{
    "type": "lldb",
    "request": "launch",
    "name": "Debug ex2 devcont",
    "program": "${workspaceFolder}/build.devcont.Clang-18.1.3-Debug/examples/ex2",
    "args": [],
    "cwd": "${workspaceFolder}/build.devcont.Clang-18.1.3-Debug/examples"
}
devcont_launch_json

Then we can follow the steps described in the Run the debugger section:

devcont_debug
Clone this wiki locally