How to use WebSocket API Docker Image with C# in VS Code Using the Remote — Containers extension

Introduction

Last Updated: January 2022

The original article on the Refinitiv Developer Community is available here.

Visual Studio Code (or just VS Code) is a free source code editor developed and maintained by Microsoft. This cross-platform editor rapidly gained popularity with developers as it is fast and lightweight, supports a variety of programming languages with IntelliSense (a feature that has originated with VS Code’s older sibling, Visual Studio IDE), and enables complete development operations like debugging, task running, and version control.

VS Code provides numerous extensions that add features and expand development workflows (Example: the REST Client and Thunder Client testing tools). VS Code also supports the remote development that lets you use a container, remote machine, or the Windows Subsystem for Linux (WSL) as a full-featured development environment with the Remote Development Extension Pack.

As part of the Remote Development Extension Pack, the Remote — Containers extension lets developers use a Docker container as a full-featured development environment. It allows the developer to open any folder inside (or mounted into) a container and take advantage of Visual Studio Code’s full feature set (IntelliSense, code navigation, debugging, etc) as a local-quality development experience.

Visual Studio Code Remote — Containers diagram

Image from VS Code — Developing inside a Container page.

The previous Develop with Refinitiv Real-Time SDK Docker Image in VS Code article demonstrates how to use Refinitiv Real-Time SDK Java/C++ Docker Images devcontainer with VS Code Remote — Containers extension. This part 2 article shows how to set up a .NET (to be precise, .NET Core) devcontainer with the Remote — Containers extension to for the Refinitiv Real-Time Optimized (RTO) C# WebSocket examples using a Dockerfile. This Dockerfile is built on top of the refinitivapis/websocket_api Docker Image and developers can run the RTO C# WebSocket examples codes directly in VS Code.

Refinitiv WebSocket API Introduction

As part of the Refinitiv Real-Time SDK, the Websocket API for Pricing Streaming and Real-Time Service (aka Websocket API) provides a connection to Refinitiv Real-Time via a standard WebSocket protocol and JSON message format. Developers can use multiple client technology standards such as Python, JavaScript, .Net, etc. to establish WebSocket connections to Refinitiv Real-Time Distribution Systems (RTDS), or Refinitiv Real-Time — Optimized (RTO — cloud solution) available via Refinitiv Data Platform (RDP).

The WebSocket API examples source code for various programming languages is available on GitHub. If developers are new to the Refinitiv Real-Time, they can use the refinitivapis/websocket_api Docker Image to learn the WebSocket API and RTO connection flows quickly. This Docker image contains all WebSocket API Examples, the Python runtime, and dependencies required to run the Python WebSocket examples. You can check my colleague’s Introduction to the refinitivapis/websocket_api Docker Image article for step-by-step guidance on how to deploy and run the RTSDK Docker images via the Docker command line.

If you are using the Refinitiv Real-Time SDK C/C++ or Java, there are the following Docker images that contain the latest version SDK too.

Prerequisite

This devcontainer example requires the following dependencies software and libraries.

  1. Visual Studio Code editor.
  2. Docker Desktop/Engine application.
  3. VS Code — Remote Development extension pack
  4. Access to the Refinitiv Refinitiv Data Platform and Refinitiv Real-Time — Optimized. (for the RTO example only)
  5. Internet connection.

I highly recommend following System requirements and Installation sections to set up your environment.

Please contact your Refinitiv representative to help you to access the RTO account and services. You can find more detail regarding the RDP and RTO access credentials set up from the Getting Started for Machine ID section of the Getting Start with Refinitiv Data Platform article.

RTO C# devcontainer Detail

A devcontainer.json file

The main configuration file that tells VS Code how to access (or create) a devcontainer with a well-defined tool and runtime stack is named the devcontainer.json file. The dev container configuration is either located under .devcontainer/devcontainer.json or stored in a file named .devcontainer.json file (note the dot-prefix) in the root of the project.

devcontainer.json file

Note: Make sure to commit a .devcontainer folder to your version control system.

Let me explain these configurations:

The detail of the configurations above are:

  • name: A display name for the container.
  • build: The location of a Dockerfile that defines the contents of the container.
  • runArgs: An array of Docker CLI arguments that VS Code uses when running the container. I am setting the --env-file option that sets the container's environment variables via a file named .env.devcontainer.
  • extensions: Specify VS Code extension IDs that will be installed inside the container. I am setting the C# extension for Visual Studio Code here.
  • workspaceFolder: Sets the default path that VS Code should open when connecting to the container. This devcontainer sets the default path to /opt/refinitiv/websocket-api/Applications/Examples/RDP/CSharp which is the RTO C# examples location in the container.
  • mounts: Add mount points to the container when created for sharing files between the host and devcontainer. I am mounting the .vscode folder for the C# running/debugging configurations and the shareFolder to share files between host and devcontainer.
  • shutdownAction: set the VS Code stops the container when the editor window is closed/shut down.

The development container is not limited to Docker Images or a Dockerfile, it supports Docker Compose too. You can build your image(s) to match your development requirements, and then share Dockerfile and/or docker-compose.yml inside a .devcontainer folder (with a devcontainer.json file) with your colleagues to help them to set up the same development environment.

Please find more details about all devcontainer.json configuration parameters on the VS Code — devcontainer.json reference page.

An Dockerfile

The refinitivapis/websocket_api Docker Image has the Python runtime and dependencies pre-installed for the Python WebSocket examples. However, it is based on the Linux OS Image, so we can build a new Docker image on top of it and install compilers, SDKs, or runtime for the other WebSocket examples.

A Dockerfile for the RTO C# WebSocket examples is as follows:

The above Dockerfile instructions do the following tasks.

  1. Pull refinitivapis/websocket_api as the Base Image with the FROM instruction.
  2. Install .NET SDK and runtime to the Image (As of April 2022: The RTO C# examples support .NET Core version 2.1).
  3. Install additional packages for VS Code and the Remote — Containers extension.
  4. Set a new working directory to /opt/refinitiv/websocket-api/Applications/Examples/RDP/CSharp folder with the WORKDIR instruction.

Please note that you can build and run this Dockerfile with the Docker engine CLI too.

A Environment Variables file

According to the methodology 3rd factor of the Twelve-Factor App methodology, it is a good practice to keep configuration information and credentials as environment variables, then inject them into the application on runtime.

I am keeping the RTO credentials in a file named .env.devcontainer file under the .devcontainer folder as follows:

# RTO CredentialsRTO_USERNAME=<RTO Machine-ID>
RTO_PASSWORD=<RTO Password>
RTO_CLIENTID=<RTO AppKey>

Then, we set this .env.devcontainer file to Docker on runtime with the devcontainer.json's "runArgs": ["--env-file=.devcontainer/.env.devcontainer"] configuration. Once the devcontainer creation is successful, developers can access RTO credentials via the following methods:

  • In a container’s bash: via the $<variable name> syntax like $RTO_USERNAME
  • In VS Code launch.json: via the ${env:<variable name>} syntax like ${env:RTO_USERNAME}

Caution

You should not share this .env.devcontainer file to your peers or commit/push it to the version control. You should add the file to the .gitignore file to avoid adding it to version control or public repository accidentally.

You can create a .env.devcontainer.example file as a template for environment variables file sharing. The file has the same parameters' keys as a .env.devcontainer file but without sensitive values.

Launch and Tasks Configurations files

VS Code has built-in debugging support for various programming languages. Developers can configure and save their debugging setup detail in a lunch configuration file named launch.json located in a .vscode folder of the workspace (project root folder).

To set a devcontainer to run and debug the MarketPriceRdpGwServiceDiscoveryExample application with the .NET Core runtime, I am setting a launch.json configuration as follows:

Please noticed that the args attribute has been set with the ["--user","${env:RTO_USERNAME}","--password","${env:RTO_PASSWORD}","--clientid","${env:RTO_CLIENTID}","--ric","/EUR="] value. This setting makes VS Code automatic passes the RTO credentials in a devcontainer's environment variables to the MarketPriceRdpGwServiceDiscoveryExample command line options. Developers do not need to manual paste their credentials in a devcontainer anymore.

Developers can save their building, packaging, testing, or deploying steps in a tasks configuration file named tasks.json located in a .vscode folder of the workspace (project root folder). A tasks.json file for automatic builds of the RTO C# WebSocket CSharpRdpGwExamples_VS150 solution with the following configurations:

We mount this .vscode folder to a Docker Container with the devcontainer.json's "mounts": ["source=${localWorkspaceFolder}/.vscode,target=${containerWorkspaceFolder}/.vscode,type=bind,consistency=cached"] configuration. Once the devcontainer creation is successful, developers can start run and debug RTO C# Websocket examples session in VS Code directly.

Please find more detail about VS Code Debugging and Tasks configurations from the following resources:

Running the Development Container

Docker Desktop/engine should be running before the next step.

You can connect to the container and start developing within it by selecting the Remote-Containers: Reopen in Container command from the VS Code Command Palette (F1).

Reopen in Container menu 1

Alternatively, the VS Code can detect whether there is a folder containing a Dev container configuration file, and then asks you if you want to reopen the folder in a container.

Reopen in Container menu 2

Next, the VS Code window (instance) reloads and builds a Docker image from a Dockerfile, then starts a devcontainer. Please note that if the image is already built, the process will be faster.

Pull and Build dev container

There may be a message “There are unresolved dependencies. Please execute the restore command to continue” At this point. This message is generated from VS Code C# extension. Please click the Restore button.

Restore dependencies

Once this build completes, VS Code automatically connects to the container at the path we set to the workspaceFolder property which is the /opt/refinitiv/websocket-api/Applications/Examples/RDP/CSharp folder. You can check the VS Code Remote connection status from the button left toolbar.

DevContainer success

Now VS Code is ready to run the RTO C# WebSocket API devcontainer.

If you click this toolbar, VS Code shows the Container Remote connection menu options at the top of the editor.

Dev Container menu

To close the remote connection, choose the “Close Remote Connection” from the drop-down menu.

Running the MarketPrice RDP Service Discovery Example

This devcontainer already has the C# extension built-in and VS Code’s launch.json and tasks.json configurations files, developers can run the MarketPrice RDP Service Discovery Example (MarketPriceRdpGwServiceDiscoveryExample) by pressing the F5 button or selecting Run then Start Debugging option from VS Code menu.

Run example

VS Code automatic runs the MarketPriceRdpGwServiceDiscoveryExample application with the --user, --password, --clientid, and --ric command-line options set in a launch.json file. All RTO credentials are available in the container environment variables, so developers do not need to manually set them. Developers can change the RIC code or add other options in the args attribute of a launch.json file.

Run example

Please find more detail about other options in the solution readme file.

Alternatively, developers can run the example in bash manually via the following steps:

$>dotnet build CSharpRdpGwExamples_VS150.sln$>cd MarketPriceRdpGwServiceDiscoveryExample/bin/Debug/netcoreapp2.1/$>dotnet MarketPriceRdpGwServiceDiscoveryExample.dll --user $RTO_USERNAME --password $RTO_PASSWORD --clientid $RTO_CLIENTID --ric <RIC Code>

Bonus: Running the WebSocket Python examples

This C# devcontainer is based on the refinitivapis/websocket_api Docker Image, so developers can run the Python WebSocket examples too.

The steps to run the RTO Python WebSocket example are as follows:

$>cd /opt/refinitiv/websocket-api/Applications/Examples/RDP/python$> python market_price_rdpgw_service_discovery.py --user $RTO_USERNAME --password $RTO_PASSWORD --clientid $RTO_CLIENTID --ric <RIC Code>

Troubleshooting

Question: I do not have the RTO credentials.

Answer: Please contact your Refinitiv representative to help you to access the RTO account and services.

Question: When I select the Remote-Containers: Reopen in Container command, VS Code returns an error with Docker returned an error. Make Sure the Docker daemon is running. message.

Answer: Please install and start a Docker desktop or Docker engine on your machine.

Question: When I select the Remote-Containers: Reopen in Container command, VS Code returns an error with Docker returned an error. Make Sure the Docker daemon is running. message.

Answer: Please install and start a Docker desktop or Docker engine on your machine.

Question: VS Code throws an error with the An error occurred setting up the container message.

Build Error

Answer: Please choose the Open devcontainer.json Locally option. Delete Docker container and images (named vsc-XXX), check the error log file, and restart the process.

Question: VS Code throws an error and the log show *docker: open .devcontainer/.env.devcontainer: The system cannot find… message.

Build Error

Answer: This error message means you do not have a .dev.devcontainer environment variables file in the .devcontainer folder. Please create it using the template from a .dev.devcontainer.example file.

Conclusion and Next Steps

Docker is an open containerization platform for developing, testing, deploying, and running any software application. It helps developers create a consistent development environment (aka devcontainer) without manually maintaining dependencies and toolsets for the project. The VS Code Remote — Containers let developers develop applications with a devcontainer using VS Code full-featured sets such as debugging and various extensions. This devcontainer is easy to set up and share among the project team.

This example project is just a brief introduction to the Remote — Containers extension. Developers can work with Docker Compose to build a customized Docker image that matches the development requirements, debugging, install various VS Code extensions to use in the Dev Container (via the GUI or configuration file), clone Docker container from Git repository, attach the VS Code to a running container, port forwarding, and much more. I highly recommend you check the following VS Code resources for more details:

The refinitivapis/websocket_api Docker Image is a good starting point for developers who are new to the WebSocket API. Developers can use the Docker Image with the Remote — Containers extensions to set up a development environment, and run the Python WebSocket examples. Developers who are using other programming languages can install more compilers/runtime to run the WebSocket examples based on their preferred technology too.

VS Code love Docker

References

For further details, please review the following resources:

For any questions related to this project or the WebSocket API page, please use the Developer Community Q&A Forum.

GitHub

Refinitiv-API-Samples/Article.WebSocketAPI.CSharp.DevContainer.RTO

--

--

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store