Anda di halaman 1dari 7

Containerizing your existing .

NET applications with Visual Studio


Configuring Docker for Windows to use Windows Containers instead of Linux Containers

Before you run the solution, you must make sure that you configure Docker to use Windows Containers. To do
that, you right-click the Docker taskbar icon in Windows and select Switch to Windows Containers, as shown in
the figure below.

If the menu item says "Switch to Linux containers", you are already running Docker with Windows Containers.

Using Visual Studio to add Docker support to the application

Visual Studio 2017 provides great support for containerizing an application. You right-click the project node and
then select Add and Docker Support. The Docker project template adds a new project to the solution called
docker-compose. The project contains the Docker assets (simple .yml metadata files) that compose the Docker
images and containers' startup settings you need, as shown in the figure below.

Then, in the next figure you can see how your project and solution has been modified with the Docker metadata.
In the simplest monolithic scenarios like this one, the application will be the single application service/container
defined at the docker-compose.yml file that you will need to deploy. In other more complex scenarios like N-Tier
applications, you will have a multi-container application defined in the docker-compose.yml file. The template
also changes your startup project to point to the docker-compose project so it will run on Docker when launching
the solution. Pressing Ctrl+F5 or F5 now compiles the .NET application bits, creates the Docker image and
launches the Docker container all in a single step for you, as shown in the next image.

When VS is building the Docker image, the first time you do this, it takes considerable time (a few minutes). This
is because the build process pulls down the base Windows Server Core image and the additional image for
ASP.NET. Subsequent build and run cycles will be much faster. Let’s take a deeper look at the files added by the
Docker project template. It created several files for you. Visual Studio uses these files to create the Docker image
and launch a container. You can use the same files from the CLI to run Docker commands manually with the
Docker CLI commands like “docker run” and “docker-compose up”. For each application or service in your
solution Visual Studio adds a dockerfile to your project’s root folder, similar to the following Dockerfile example
showing the basic settings for building a Docker image based on the Windows ASP.NET image that runs an
ASP.NET site.
Sample Dockerfile:

`FROM microsoft/aspnet
ARG source
WORKDIR /inetpub/wwwroot
COPY ${source:-obj/Docker/publish} . `

If your application were based on an older version of .NET Framework, like .NET Framework 3.5, you could use a
similar base image directive like the following.

FROM microsoft/dotnet-framework:3.5

This previous Dockerfile will look very similar to those created for running an ASP.NET Core application in
Linux containers. However, there are a few important differences. The most important difference is that the base
image is microsoft/aspnet, which is an image based on Windows Server Core image that includes IIS, the .NET
Framework and special optimizations for ASP.NET. The other files in the docker-compose project are the Docker
assets needed to build and configure the containers. Visual Studio puts the various docker-compose.yml files
under one node (project) to highlight how they are used. The base docker-compose file contains the directives that
are common to all configurations/environments. The docker-compose.override.yml file contains environment
variables and related overrides for a by-default developer configuration.

Development and production environments

There are a couple of differences between the development configuration and a production configuration. In the
development environment, you run the ASP.NET application and SQL Server in Windows Containers, within the
same Docker host. In earlier sections, we mentioned that for development environments you could use a SQL
localdb within the same application Windows Container or deploying an independent SQL Server Windows
Container.

The advantage of running the database along with the multiple application containers within the same Docker host
(or even orchestrator cluster looking forward) is that you have a very predictable testing environment with a
consistent database that can have the same pre-generated data generated when deploying to the testing
environment in the Docker host. In the development environment, you usually run all the containers in the same
environment, including the SQL databases, so it’ll be easier while developing and testing.

In a production environment, you can decide if you want to run the application Windows Container in a single
Docker host Azure VM, or in an orchestrator’s cluster like Service Fabric, and most of all, you will usually have
the data stored in a high-available and production ready SQL environment like Azure SQL Database or Azure
SQL Database Managed Instance.

Additional resources

 Lab: Modernize .NET Apps - for Ops https://github.com/docker/labs/tree/master/dockercon-us-


2017/windows-modernize-aspnet-ops
 Lab: Modernize .NET Apps - for Devs https://github.com/docker/labs/tree/master/dockercon-us-
2017/windows-modernize-aspnet-dev

*** Optional finish of the walkthrough *** At this point you already containerized the application. The next
sections focus on alternative approaches and more advanced scenarios you might need and you can also explore.

Containerizing your existing .NET applications with the Docker CLI


and manually adding dockerfiles
While Visual Studio integration is part of adding Docker support to your solution, annd just by running the
dockerized application with VS you are already creating the Docker images and deploying the containers in
Docker, all in a single step ("F5 experience"), you can also containerize your application by manually adding the
dockerfile and docker-compose files to your solution and then building the Docker images with the “docker build”
CLI command and finally running the application from the command line, using the “docker-compose up”
command or the “docker run command” as you can explorer in other Docker guidance like the “Containerized
Docker Application Lifecycle with Microsoft Platform and Tools” eBook.

In order to generate your application's .NET bits, you can do so from VS and the menu option "Publish", then with
the option "to folder" as used in this other Wiki procedure.

As an alternative option, in order to build the .NET bits from the CLI or from a CI pipeline, you need a build
container or Docker build agent that will be internally using MSBuild to compile your .NET code. You can
explore this walkthrough on "How to create a custom image for a .NET Framework build container internally
using MSBuild".

Once you produced the .NET bits of your application, ready for you, in a directory, you’d build the Docker images
with the CLI command “docker image build”, also explained in the same article/walkthrough.

Containerizing your existing .NET applications with Image2Docker


Another way to migrate existing .NET application from Windows VM running IIS towards Windows Containers,
without using a developer tool like Visual Studio, is to use Image2Docker, an open-source tool originally created
and provided by Docker (the company).

In this case you don’t even need to see the code or open any solution like when using Visual Studio and it has the
advantage of having a tool that explores existing installation and configuration in Windows and will generate the
dockerfile config for that specific configuration.

What is Image2Docker?

Image2Docker is basically a PowerShell module that migrates existing Windows application from VMs to
Windows Container images. Although it supports multiple application types, the main focus is on IIS. You can use
Image2Docker to export ASP.NET websites from a VM, so you can run them in a Windows Container with no
application changes.

Requirements for Image2Docker:

 Windows Server 2016


 Windows 10 with Docker for Windows installed
 PowerShell 5.0, or later

How does Image2Docker work?

Image2Docker first inspects the artifacts in a Windows Server VM image. This original VM could be a Windows
Server 2003, 2008, 2012 or 2016 and its VM format could be WIM, VHD or VHDX.

Image2Docker will extract either an entire VM or specific components from a VHD file. Next, it will generate a
Dockerfile which you can build into a Windows Container image.

For instance, if you have a VM disk image (VHD, VHDX or WIM), you can extract all the IIS websites from it by
installing Image2Docker and running ConvertTo-Dockerfile like this:

`Install-Module Image2Docker
Import-Module Image2Docker
ConvertTo-Dockerfile -ImagePath C:\my-windows-2016.vhd -Artifact IIS -OutputPath
c:\docker\W216iis`

That will produce a Dockerfile which you can use to build a Windows container image, using docker build.

Image2Docker, as of mid-2017, currently supports discovery of the following Windows artifacts:


 Microsoft Windows Server Roles and Features
 Microsoft Windows Add/Remove Programs (ARP)
 Microsoft Windows Server Domain Name Server (DNS)
 Microsoft Windows Internet Information Services (IIS)
 HTTP Handlers in IIS configuration
 IIS Websites and filesystem paths
 ASP.NET web applications
 Microsoft SQL Server instances
 Apache Web Server

Additional resources for Image2Docker

 Image2Docker PowerShell Module https://www.powershellgallery.com/packages/Image2Docker/


 Image2Docker official repo maintained by Docker https://github.com/docker/communitytools-
image2docker-win
 Convert ASP.NET Web Servers to Docker with Image2docker https://blog.docker.com/2016/12/convert-
asp-net-web-servers-docker-image2docker/
 Working with Windows Containers and Docker: Into your Stride https://www.red-gate.com/simple-
talk/sysadmin/virtualization/working-windows-containers-docker-stride/

Installing custom dependencies within your Windows Containers


In many cases, your existing .NET applications are not based just on your .NET code solution and the .NET
Framework libraries but also based on additional artifacts from Windows that have to be enabled (IIS, .NET WCF
HTTP Activation, Server roles, etc.) and even additional components from third parties that you need to install in
windows through .MSI setups. You can perform those steps in a declarative way within the declared commands
within your dockerfiles.

Installing MSIs in Docker images

In order to install an MSI within a Windows Container you just need to copy in the .msi file and run msiexec to
install it. For instance, the following dockerfile specifies how to install a .msi in your container.

`# escape=`
FROM microsoft/aspnet:windowsservercore
COPY MySetupSample-1.0.0.0.msi /
RUN msiexec /i c:\ MySetupSample-1.0.0.0.msi RELEASENAME=2017.01 /qn `

There are just three lines of Dockerfile instructions:

 FROM specifies the base image to use, in this case a specific version of the ASP.NET image using
Windows Server Core.
 COPY copies the existing MSI from the local machine into the Docker image
 RUN installs the MSI using msiexec, with the qn switch to install silently, and passing a value to the
custom RELEASENAME variable that the MSI uses.

That .msi setup could install whatever dependency you might need for your application, like the .DLLS of a PDF
creator library (or any other comparable case) that you might need to use from your ASP.NET application.

You can also, of course, add these steps to your previous dockerfile so you may end up with multiple COPY
commands (your application plus additional .MSIs) and therefore you could also execute multiple RUN
commands from your dockerfile.

Enabling Windows features in Docker images


In order to enable Windows features or artifacts (like .NET WCF HTTP Activation, IIS configuration, etc.) in a
Windows Container, you need to specify those dependencies in your dockerfile so they will be installed when the
container is deployed.

For instance, the following dockerfile would enable .NET WCF HTTP Activation in your Windows Container:

`# Base image is Windows Server Core image since WCF does not need ASP.NET
FROM microsoft/windowsservercore

RUN powershell -Command Add-WindowsFeature NET-WCF-HTTP-Activation45

# Creates a directory for the Host


WORKDIR app
# Listen on port 88.
EXPOSE 88
# Copy the WCF host into the container.
COPY Bin/ .
ENTRYPOINT BasicHttpHost.exe`

The important line in that dockerfile is the line with the RUN command that specifies to add certain Windows
Feature, in this case, .NET WCF HTTP Activation. Note that not all the Windows features can be activated in
Windows Containers since some of them are not supported, like MSMQ or other cases.

Other supported cases for Windows Containers can be the following:

 Like ISAPI handler in IIS.


 A .PDF creation service program installed with a .MSI.
 Office Automation.
 ASP.NET Controls.
 IIS enable and configured.
 WCF HTTP Activation – Program – Windows Settings (Kind of IIS activation)
 List of dockerfiles with many dependencies and settings being configured.
 Have .NET 3.5 in the Docker image.

Additional resources:

 WCF Self-Hosted Services in a Container https://blogs.msdn.microsoft.com/webdev/2017/02/20/lets-try-


wcf-self-hosted-services-in-a-container/
 How to: Install and Configure WCF Activation Components https://docs.microsoft.com/en-
us/dotnet/framework/wcf/feature-details/how-to-install-and-configure-wcf-activation-components

How to create Windows Container images with your infrastructure


dependencies (Database Server, Messaging Server, etc.)
TBD:

 Chocolatey for creating Windows Containers images for infrastructure assets (DBs, RabbitMQ, etc.)

... CONTENT TO BE DEFINED ...

--- Older simplified procedure - TO BE REMOVED


How to: dockerize the app
1. Add Docker files to the project:
o In Visual Studio right click on the project -> Add-> Docker support
o The docker-compose files are created plus the dcproj.
2. Add the environment variables to the docker-compose.override by using the .env file. Containers will use
docker-compose environment variables and settings overriding values at the web.config, so the needed
settings must be set at the docker-compose files and .env file. This environment variables must be setin the
application and used instead of the web.config application settings. In our apps this is done in the
CatalogConfiguration class.

How to: run application in Windows Server 2016 with Containers


1. Create the docker image:
o Build the solution in Release to build the eshopmodernizedmvc image.
o When the build is done, open a Powershell prompt and execute docker images and in the list of
images must appear eshopmodernizedmvc with tag latest
2. Publish the image in the Container Registry, in this case ACR:
o Create one ACR on Azure. Take note of the address (e.g. myprivateacr.azurecr.io) and the user and
password of the registry.
o Login to the container registry. From a Powershell execute docker login -u dockerUser -p
dockerPassword myprivateacr.azurecr.io using the values of your ACR
o Add to the image our ACR address as a prefix to indicate where it must be published. Execute
docker tag eshopmodernizedmvc myprivateacr.azurecr.io/eshopmodernizedmvc to mark
it for publishing in the ACR. After this if you execute docker images this new
_myprivateacr.azurecr.io/eshop/modernizedmvc must appear in the list of images.
o Publish the tagged image executing docker push
myprivateacr.azurecr.io/eshopmodernizedmvc
o Note: to publish in Docker hub instead of ACR, the login step is the same (with Docker Hub
credentials), and skip the tag step because by default docker will publish to Docker Hub.
3. Run the image in the VM:
o Create one VM in Azure. Select Windows Server 2016 Datacenter with containers. This way
Docker is already installed and configured.
o Install docker-compose. Following this link. Basically execute with admin rights from Powershell,
with the last version, this command:

Invoke-WebRequest
"https://github.com/docker/compose/releases/download/$dockerComposeVersion/docke
r-compose-Windows-x86_64.exe" -UseBasicParsing -OutFile
$Env:ProgramFiles\docker\docker-compose.exe

o Copy the files docker-compose.nobuild.yml, docker-compose.override.yml and .env to the VM in a


folder.
o Edit the .env to put the IP of the VM in the variable.
o Edit the docker-compose.nobuild file to add the prefix of your ACR eshop/modernizedmvc:
o > image:myprivateacr.azurecr.io/eshop/modernizedmvc
o If your image is in a private registry, login first. For ACR would be to execute in the VM docker
login -u dockerUser -p dockerPassword myprivateacr.azurecr.io.
o Run docker-compose -f .\docker-compose.nobuild.yml -f .\docker-
compose.override.yml up. The first time the images will be downloaded from the registry, so
this step can take some minutes the initial execution.
o After this open the browser and write http://{ip of the VM}:5114 and the app should open.

Anda mungkin juga menyukai