{"id":78494,"date":"2018-04-25T14:48:58","date_gmt":"2018-04-25T14:48:58","guid":{"rendered":"https:\/\/www.red-gate.com\/simple-talk\/?p=78494"},"modified":"2026-05-08T09:41:41","modified_gmt":"2026-05-08T09:41:41","slug":"working-windows-containers-docker-save-data","status":"publish","type":"post","link":"https:\/\/www.red-gate.com\/simple-talk\/devops\/containers-and-virtualization\/working-windows-containers-docker-save-data\/","title":{"rendered":"Docker Volumes on Windows: Persisting Container Data"},"content":{"rendered":"\n<p id=\"h-\"><strong>Docker containers are ephemeral &#8211; data disappears when a container is removed. Docker volumes persist data independently of the container lifecycle. This article covers creating independent volumes, sharing between containers, copying from host, and defining volumes in Dockerfiles. Also: learn about Linux containers on Windows (LCOW).<\/strong><\/p>\n\n\n<ul>\n<li><a href=\"https:\/\/www.simple-talk.com\/sysadmin\/virtualization\/working-windows-containers-docker-basics\/\">First Part \u2013 The basics<\/a>: the basic principles of how container virtualization is implemented in Windows Server 2016 operating system.<\/li>\n<li><a href=\"https:\/\/www.simple-talk.com\/sysadmin\/virtualization\/working-windows-containers-docker-running\/\">Second part \u2013 Up and Running<\/a>: creating and managing Windows Server Containers using Docker.<\/li>\n<li><a href=\"https:\/\/www.red-gate.com\/simple-talk\/sysadmin\/virtualization\/working-windows-containers-docker-stride\/\">Third part \u2013 Into your Stride<\/a> Working with Windows Containers and Docker<\/li>\n<li><a href=\"https:\/\/www.red-gate.com\/simple-talk\/sysadmin\/containerization\/working-windows-containers-docker-save-data\/\">Fourth part<\/a> -- Save the Container Data<\/li>\n<\/ul>\n\n\n\n\n<p>This is my latest article in this series about Windows Containers and Docker. I began writing this series one year ago, and since then there have been some great improvements. Before going deeper, I just want to describe the different versions of Docker that exist today in case you were not in the Docker \u2018sphere\u2019 or if you have just started using Docker. On March 2nd 2017, Docker changed their <a href=\"https:\/\/goto.docker.com\/Docker-Weekly_03082017.html\">version format<\/a>, and also changed the name of the Docker Engine package to either Docker Community Edition or Docker Enterprise Edition.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"h-installing-docker-community-edition-on-windows-10\">Installing Docker Community Edition on Windows 10<\/h2>\n\n\n\n<p>The first edition is called <em>Docker Community Edition (CE)<\/em>. Docker (CE) is the new name for the free Docker products. Docker CE is compatible with the following OS Platform: Mac OS, Windows 10, Amazon AWS, Azure, CentOS, Debian, Fedora, and Ubuntu. On Top of that, Docker CE comes in two variants, Edge and Stable:<\/p>\n\n\n<div class=\"block-core-list\">\n<ul class=\"wp-block-list\">\n<li><strong>Edge<\/strong> is for users wanting a drop of the latest and greatest features every month<\/li>\n\n\n\n<li><strong>Stable<\/strong> is released quarterly and is for users that want an easier-to-maintain release pace<\/li>\n<\/ul>\n<\/div>\n\n\n<p>As Docker said, the Community Edition is great for developers and ops teams starting to build container apps. If you want to download this edition, go to the <a href=\"https:\/\/store.docker.com\/search?offering=community&amp;type=edition\">Docker Store<\/a>. Once the download and installation are completed, you can run the package called <strong>Docker For Windows<\/strong>. At the time of writing this article, I installed Docker CE v18.03.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  PS &gt; Enable-WindowsOptionalFeature -Online -FeatureName Microsoft-Hyper-V \u2013All\n  PS &gt; Get-Service *docker*\n  \n  Status   Name               DisplayName\n  ------   ----               -----------\n  Running  com.docker.service Docker for Windows Service<\/pre>\n\n\n\n<p>Confirm that you can run a simple container:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  PS &gt; Docker run --rm -v c:\/Users:\/data alpine ls \/data\n  \n  Unable to find image 'alpine:latest' locally\n  latest: Pulling from library\/alpine\n  ff3a5c916c92: Pull complete\n  Digest: sha256:7b848083f93822dd21b0a2f14a110bd99f6efb4b838d499df6d04a49d0debf8b\n  Status: Downloaded newer image for alpine:latest\n  All Users\n  Default\n  Default User\n  Nicolas\n  Public\n  defaultuser0\n  desktop.ini<\/pre>\n\n\n\n<p>If you work with Docker v18.03, then one of the main features is the ability to run both Windows and Linux images side by side, instead of having to switch Docker from Linux to Windows mode. Let\u2019s confirm you are running the daemon in experimental mode:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  PS &gt; docker version -f '{{.Server.Experimental}}'\n   \n  True<\/pre>\n\n\n\n<p>Or through the GUI:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"832\" height=\"573\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-220.png\" alt=\"\" class=\"wp-image-78495\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Now, use the <strong>platform=linux<\/strong> parameter in Windows Container mode to run Linux images.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"1129\" height=\"499\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-221.png\" alt=\"\" class=\"wp-image-78496\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>If you work with a previous version of Docker, it will run Linux containers by default. So, you must modify this setting and switch to Windows Container mode using either the Docker tray-menu:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"255\" height=\"342\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-222.png\" alt=\"\" class=\"wp-image-78497\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>or by running the following command in a PowerShell prompt<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">&amp; $Env:ProgramFiles\\Docker\\Docker\\DockerCli.exe \u2013SwitchDaemon<\/pre>\n\n\n\n<p>And that\u2019s all. Docker CE is up and running on your Windows 10!<\/p>\n\n\n\n<p>Now, you can go to the <a href=\"https:\/\/hub.docker.com\/\">Docker Hub<\/a> to find out which Container Images are available. For instance, you can run a simple Windows Container that contains PowerShell Core:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  PS &gt; docker pull microsoft\/powershell\n  \n  Using default tag: latest\n  latest: Pulling from microsoft\/powershell\n  1be7f2b886e8: Pull complete\n  6fbc4a21b806: Pull complete\n  [\u2026]\n  74ebbb198c87: Pull complete\n  Digest: sha256:38ac64ecec7e36b1868458b6b49e9d41332de56da2053c14830ef4915d909813\n  Status: Downloaded newer image for microsoft\/powershell:latest\n  PS &gt; docker run --name PSCore -it microsoft\/powershell\n  PowerShell v6.0.1\n  Copyright (c) Microsoft Corporation. All rights reserved.\n  https:\/\/aka.ms\/pscore6-docs\n  Type 'help' to get help.\n  \n  PS &gt; $PSVersionTable \n                                                                                                                           \n  Name                           Value\n  ----                           -----\n  PSVersion                      6.0.1\n  PSEdition                      Core\n  GitCommitId                    v6.0.1\n  OS                             Linux 4.9.75-linuxkit-aufs #1 SMP Tue Jan 9 10:58:17 UTC 2018\n  Platform                       Unix\n  PSCompatibleVersions           {1.0, 2.0, 3.0, 4.0...}\n  PSRemotingProtocolVersion      2.3\n  SerializationVersion           1.1.0.1\n  WSManStackVersion              3.0<\/pre>\n\n\n\n<p>And you can very easily configure your Docker engine using the GUI <em>Docker For Windows<\/em>:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"832\" height=\"573\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-223.png\" alt=\"\" class=\"wp-image-78498\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"h-installing-docker-enterprise-edition-on-windows-server-2016\">Installing Docker Enterprise Edition on Windows Server 2016<\/h2>\n\n\n\n<p>The second edition is called <em>Docker Enterprise Edition (EE)<\/em> and is a certified container platform for: CentOS, Red Hat Enterprise Linux (RHEL), Ubuntu, SUSE Linux Enterprise Server (SLES), Oracle Linux, Windows Server 2016, IBM Z, Amazon AWS, and Azure (Docker EE for Azure). Docker EE is available in three tiers: <strong>Basic<\/strong>, <strong>Standard<\/strong> and <strong>Advanced<\/strong>. Standard and Advanced tiers add advanced container management (Docker Datacenter) and Docker Security Scanning. You can find more <a href=\"https:\/\/store.docker.com\/search?offering=enterprise&amp;q=&amp;type=edition\">information on the Docker Store<\/a> about Docker EE and how to install it on other Operating Systems. In this case, you just need to run the following commands as administrator to install Docker EE on Windows Server 2016:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  PS &gt; Install-Module DockerProvider\n  PS &gt; Install-Package Docker -ProviderName DockerProvider -RequiredVersion preview -Force\n  \n  WARNING: A restart is required to enable the one or more features. \n  Please restart your machine.\n  Name       Version          Source       Summary\n  ----       -------          ------       -------\n  Docker     17.10.0-ee-pr... Docker       Docker Enterprise Edition for Windows Server...\n  \n  PS &gt; Restart-Computer<\/pre>\n\n\n\n<p>As you may notice, the <strong>\u2013Force<\/strong> parameter is used to install the very latest version of Docker EE. And then a restart of the Windows container Host is performed. This article will demonstrate using Docker EE v17.10 on Windows Server 2016.<\/p>\n\n\n\n<p>Below is the release cycle for Docker in 2017. For example, v17.03 means that this release was released in March 2017.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"771\" height=\"292\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-224.png\" alt=\"\" class=\"wp-image-78499\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Docker release cycle from <a href=\"https:\/\/goto.docker.com\/Docker-Weekly_03082017.html\"><em>the Docker website<\/em><\/a><\/p>\n\n\n\n<p>To summarize, Docker CE has the same core features as Docker Enterprise Edition, so don\u2019t be afraid, you can use Docker CE instead of Docker EE. Nonetheless, if you want to run Docker in production, I recommend installing at least Docker EE Basic.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"h-where-s-my-data\">Where\u2019s My Data?<\/h2>\n\n\n\n<p>Imagine that you run a Windows Container and have some important data inside the container. Yes, containers are ephemeral, but you may want to save this data outside the container for many reasons. Well, you can easily share data between the Container Host and a Windows Container. Furthermore, you can also share data between two Windows Containers if you need to. This feature is very useful for Multi-Container Applications. For instance, applications need to share access to data or persist data after a container is deleted such as for databases or log files. This feature is called \u2018Docker Volumes\u2019.<\/p>\n\n\n\n<p>In this section, I will describe how Docker Volumes work and explain four different ways to share data with containers:<\/p>\n\n\n<div class=\"block-core-list\">\n<ol class=\"wp-block-list\">\n<li>Creating an independent Docker Volume<\/li>\n\n\n\n<li>Sharing a Docker Volume with multiple containers<\/li>\n\n\n\n<li>Copying data from the Container Host to a container<\/li>\n\n\n\n<li>Creating a Docker Volume from a Dockerfile<\/li>\n<\/ol>\n<\/div>\n\n\n<p>When using Windows containers, it is still a good idea to use Docker Volumes to keep the data on the container host instead of on the container. You could also create multiple containers that will share the same Docker Volume. A Docker Volume will be visible both on the container host and on the container. The first thing to know is that Docker Volumes are stored in the following hidden path on the container host:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"1052\" height=\"68\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-225.png\" alt=\"\" class=\"wp-image-78500\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p><em>Note: Given that I will switch between the container host and containers, I will add a comment before each command.<\/em><\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"h-creating-an-independent-docker-volume\">Creating an Independent Docker Volume<\/h3>\n\n\n\n<p>To create a Docker Volume, type the following command:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  Docker volume create --name vol01\n  \n  Vol01<\/pre>\n\n\n\n<p>To view all the existing Docker Volumes on the container host, type:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker volume ls\n  \n  DRIVER              VOLUME NAME\n  local               vol01<\/pre>\n\n\n\n<p>Now you can attach the existing Docker Volume to a new container, <em>iis01<\/em>, using the <strong>\u2013v<\/strong> parameter. The syntax is simple, you must specify the folder on the <a id=\"post-78494-_Hlk512409727\"><\/a>container host followed by the folder on the container:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker run --name iis01 -it -v C:\\ProgramData\\Docker\\Volumes\\Vol01:C:\\Vol01 nanoserver\/iis PowerShell<\/pre>\n\n\n\n<p>By including the <strong>-it<\/strong> switch and specifying <strong>PowerShell, <\/strong>the current PowerShell console will be used to connect automatically to your container once it is created. If you want to exit from your container, type <strong>Exit<\/strong> and your container will be stopped. To leave the container running in background, use <strong>CTRL+P+Q<\/strong>. To open a new PowerShell session running in the container use <strong>Docker attach &lt;container name&gt; <\/strong> and press <strong>ENTER<\/strong> twice. When in a PowerShell session for an existing container, <strong>Exit<\/strong> will just switch back to the host but leave the container running. To start up a container use <strong>Docker start &lt;container name&gt;<\/strong>.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"867\" height=\"436\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-226.png\" alt=\"\" class=\"wp-image-78501\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Now, create a simple text file on the container host:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"777\" height=\"169\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-227.png\" alt=\"\" class=\"wp-image-78502\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Confirm that the file exists on the Container as well:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the iis01 container\n  PS C:\\&gt; Get-ChildItem .\\vol01\\_data\n \n     Directory: C:\\vol01\\_data\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  -a----         3\/2\/2018   8:49 PM             19 TestFile.txt<\/pre>\n\n\n\n<p>In order to inspect the Container, run the following command and check the <strong>Mounts<\/strong> section:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker inspect iis01<\/pre>\n\n\n\n<p><img loading=\"lazy\" decoding=\"async\" width=\"926\" height=\"449\" class=\"wp-image-78503\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-228.png\"><br>Some of you are probably wondering if it\u2019s possible to move the storage location? Fortunately, yes! To perform this task, you will need to create a configuration file called <em>daemon.json<\/em>:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; New-Item -Type File -Path \"C:\\ProgramData\\Docker\\config\" -Name daemon.json\n \n     Directory: C:\\ProgramData\\Docker\\config\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  -a----         3\/2\/2018   9:00 PM              0 daemon.json<\/pre>\n\n\n\n<p>Then, provide the new storage location by adding this to the <em>daemon.json<\/em> file:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  {\n  \"data-root\": \"D:\\\\DockerVolumes\"\n  }<\/pre>\n\n\n\n<p>Next, restart the Docker service. Create a new volume to confirm that the volume is created under the new Data Root folder:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Get-Service *Docker* | Restart-Service\n  PS &gt; Docker volume create --name newvolume<\/pre>\n\n\n\n<p>The folder for the new Data Root folder will be created automatically. Be careful, older volumes are not moved automatically and existing containers and volumes will no longer be seen by Docker. Note that you can remove an existing Docker Volume using <strong>Docker volume rm &lt;volume name&gt;<\/strong>.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"592\" height=\"231\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-229.png\" alt=\"\" class=\"wp-image-78504\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"h-sharing-a-docker-volume-with-multiple-containers\">Sharing a Docker Volume with Multiple Containers<\/h3>\n\n\n\n<p>Start by creating a new Container called <em>iis02<\/em> based on the <em>nanoserver\/iis<\/em> image and attach a volume to it. Note that you don\u2019t need to specify the Data Root folder because Docker will create the directory with a random folder name. Then create a file on the new volume.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker run -it --name iis02 --volume c:\/vol03 nanoserver\/iis powershell\n  \n  \n  #On the \"iis02\" Container\n  PS &gt; \"Welcome vol03\" &gt; .\\vol03\\vol03.txt\n  PS &gt; dir .\\vol03\n \n     Directory: C:\\vol03\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  -a----         3\/3\/2018   2:24 PM             32 vol03.txt<\/pre>\n\n\n\n<p>Confirm that the file exists on the container host:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"811\" height=\"173\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-230.png\" alt=\"\" class=\"wp-image-78505\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>During the last step, you created a new Container and attached a new Docker Volume. Now, you will create a second Container called <strong>iis03<\/strong> and attach the same Docker Volume <strong>C:\/vol03<\/strong> using the <strong>&#8211;volumes-from<\/strong> parameter:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; docker run -it --name iis03 --volumes-from iis02 nanoserver\/iis powershell<\/pre>\n\n\n\n<p>Confirm that the volume is mounted. Create a new text file called <em>vol03-from-iis03.txt<\/em>:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the iis03 container\n  PS C:\\&gt; dir .\\vol03\n\n      Directory: C:\\vol03\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  -a----         3\/3\/2018   2:24 PM             32 vol03.txt\n  \n\n  #The text file created on iis02 is visible on iis03 thanks to the \"--volumes-from\" parameter\n  #On the \"iis03\" Container\n  PS C:\\&gt; \"Hello\" &gt; .\\vol03\\vol03-from-iis03.txt<\/pre>\n\n\n\n<p>On the container host, both files are visible:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"795\" height=\"177\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-231.png\" alt=\"\" class=\"wp-image-78506\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>By default, access on a Docker Volume is in Read\/Write mode. In some cases, you will need to limit access to the Docker Volume. You can set a volume as Read Only. Create a Container called db01 and attach a volume with Read Only (RO) access:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker run -it --name db01 --volumes-from iis02:ro nanoserver\/iis powershell<\/pre>\n\n\n\n<p>Now, try to create a file on this volume, but the task will fail:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the db01 container\n  PS C:\\&gt; dir .\\vol03\n\n      Directory: C:\\vol03\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  -a----         3\/3\/2018   2:36 PM             16 vol03-from-iis03.txt\n  -a----         3\/3\/2018   2:24 PM             32 vol03.txt\n \n PS C:\\&gt; \"Welcome\" &gt; .\\vol03\\vol03-from-db01.txt\n  \n  out-file : Access to the path 'C:\\vol03\\vol03-from-db01.txt' is denied.\n  At line:1 char:1\n  + \"Welcome\" &gt; .\\vol03\\vol03-from-db01.txt\n  + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n      + CategoryInfo          : OpenError: (:) [Out-File], UnauthorizedAccessException\n      + FullyQualifiedErrorId : FileOpenFailure,Microsoft.PowerShell.Commands.OutFileCommand<\/pre>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"h-copying-data-from-the-container-host-to-a-container\">Copying Data from the Container Host to a Container<\/h3>\n\n\n\n<p>Here is another interesting way to share data between the container host and a Windows Container. The <strong>Docker cp<\/strong> utility copies from the container\u2019s file system to the container host or the reverse, from the container host to the Container. Create a new file, <em>MyPackage.zip<\/em> in the <em>C:\\Packages<\/em> folder. Then copy the Zip file from the container host to the iis02 Container:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker cp C:\\Packages\\MyPackage.zip iis02:\/inetpub\n  PS &gt; Docker attach iis02<\/pre>\n\n\n\n<p>The <strong>Docker Attach<\/strong> command will connect to the iis02 Container. Be careful, you must press <strong>ENTER<\/strong> twice to connect to your container. Check to see if the package exists in the Container:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"827\" height=\"507\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-232.png\" alt=\"\" class=\"wp-image-78507\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<h3 class=\"wp-block-heading\" id=\"h-creating-a-docker-volume-from-a-dockerfile\">Creating a Docker Volume from a DockerFile<\/h3>\n\n\n\n<p>You can mount a Docker Volume using a DockerFile. In the following example, you will create a nanoserver\/iis image using the <strong>VOLUME<\/strong> keyword to mount a folder. Be sure to create the <em>C:\\Volume directory<\/em> on the host if it doesn&#8217;t exist.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; New-Item C:\\Volume\\Dockerfile -ItemType file\n  PS &gt; Add-Content -Path \"C:\\Volume\\Dockerfile\" -Value \"FROM nanoserver\/iis\"\n  PS &gt; Add-Content -Path \"C:\\Volume\\Dockerfile\" -Value \"VOLUME C:\/Vol03\"\n  PS &gt; Add-Content -Path \"C:\\Volume\\Dockerfile\" -Value \"RUN powershell -Command gci\"<\/pre>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"290\" height=\"109\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-233.png\" alt=\"\" class=\"wp-image-78508\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Navigate to the directory where this Dockerfile is located and run the following command:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS C:\\Volume&gt; docker build -t volumeimg .\n\n  Sending build context to Docker daemon  2.048kB\n  Step 1\/3 : FROM nanoserver\/iis\n   ---&gt; 234e90a5d146\n  Step 2\/3 : VOLUME C:\/Vol03\n   ---&gt; Using cache\n   ---&gt; 9acd2015fab2\n  Step 3\/3 : RUN powershell -Command gci\n   ---&gt; Running in 98c4a64d54e2\n      Directory: C:\\\n  Mode                LastWriteTime         Length Name\n  ----                -------------         ------ ----\n  d-----         3\/3\/2018   4:37 PM                inetpub\n  d-----         3\/3\/2018   4:37 PM                Program Files\n  d-----        7\/16\/2016  12:09 PM                Program Files (x86)\n  d-r---         3\/3\/2018   4:37 PM                Users\n  d----l         3\/3\/2018   4:37 PM                vol03\n  d-----         3\/3\/2018   4:37 PM                Windows\n  -a----       11\/20\/2016  11:32 AM           1894 License.txt\n  [\u2026]\n  Successfully tagged vol3:latest<\/pre>\n\n\n\n<p>A custom Docker image has been created:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"908\" height=\"156\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-234.png\" alt=\"\" class=\"wp-image-78509\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>So now, every container created using this image will automatically mount the volume:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; docker run --rm -it --name srv01 volumeimg powershell\n \n #On the \"srv01\" Container\n  PS &gt; cd vol03\n  PS C:\\vol03&gt; \"Mount from Container\" &gt; mount.txt<\/pre>\n\n\n\n<p>A new file called <em>mount.txt<\/em> has been successfully created on the container host. You can confirm the mount path with <strong>Docker inspect<\/strong>:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"1049\" height=\"473\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/word-image-235.png\" alt=\"\" class=\"wp-image-78510\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>This method is very useful in DevOps mode or when you want to deploy multiple Windows Containers in bulk mode. The Volume will be mounted automatically during the deployment.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"h-linux-containers-on-windows\">Linux Containers on Windows?<\/h2>\n\n\n\n<p>Another great improvement is Linux containers. You can now run Linux containers on a Windows container host. However, it can only be run in a dev\/test environment because it is still in experimental version. So, what does it mean? Well, you will be able to deploy your Windows Containers Host, then install the Docker engine, and finally run a Linux container or a Windows container. Thanks to <a href=\"https:\/\/blog.docker.com\/2017\/04\/introducing-linuxkit-container-os-toolkit\/\">LinuxKit<\/a> and the <a href=\"https:\/\/github.com\/moby\/moby\">Moby Project<\/a>, you can use Linux containers on Windows using one of the following Windows builds to support the feature:<\/p>\n\n\n<div class=\"block-core-list\">\n<ul class=\"wp-block-list\">\n<li>Windows 10 Fall Creators Update<\/li>\n\n\n\n<li>Windows Server 2016 1709 (new core edition)<\/li>\n<\/ul>\n<\/div>\n\n\n<p>In order to run Linux containers on Windows, Microsoft uses the Linux Containers on Windows (LCOW) feature. LCOW will use Hyper-V isolation, so you must install Hyper-V before using Linux containers:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Install-WindowsFeature Hyper-V -IncludeManagementTools -Restart<\/pre>\n\n\n\n<p>Then the Docker daemon runs as a Windows process, and every time you start a Linux container, Docker launches a minimal Virtual Machine with a Linux kernel. However, the \u2018VM\u2019 is not user-visible in the Hyper-V console! It is still not possible to run Windows and Linux Docker containers side-by-side. It means that you must enable LCOW to run Linux containers, and disable LCOW to run Windows containers. If you work on Windows 10, please note that LCOW support is only available on the Edge channel.<\/p>\n\n\n\n<p>Start by enabling the LCOW feature with the following commands.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; [Environment]::SetEnvironmentVariable(\"LCOW_SUPPORTED\", \"1\", \"Machine\")\n  PS &gt; Restart-Service Docker<\/pre>\n\n\n\n<p>The feature has been enabled, so you can create a Linux container based on Ubuntu using the following command:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the contaner host\n  PS &gt; Docker run \u2013it ubuntu<\/pre>\n\n\n\n<p>At this step, you are running in the Ubuntu container on your Windows Server:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  root@58e001fba499:\/# pwd\n  \/\n  root@58e001fba499:\/# mkdir \/tmp\/Linux\n  root@58e001fba499:\/# ls \/tmp\n  linux<\/pre>\n\n\n\n<p>To finish with a funny Linux container, you can run the NyanCat container:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">  #On the container host\n  PS &gt; Docker run -it supertest2014\/nyan<\/pre>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"989\" height=\"514\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2018\/04\/linux-container-based-on-nyan-cat-2.png\" alt=\"Linux Container based on Nyan Cat\" class=\"wp-image-78511\"\/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<h2 class=\"wp-block-heading\" id=\"h-conclusion\">Conclusion<\/h2>\n\n\n\n<p>This article of the series discussed the new Docker versions that you can use depending your needs. The first one is Docker CE which is for development and testing environment, and the second one is Docker EE which is for production use. Then you saw:<\/p>\n\n\n<div class=\"block-core-list\">\n<ul class=\"wp-block-list\">\n<li>How to share data between the container host and a container.<\/li>\n\n\n\n<li>How to share data between two containers.<\/li>\n<\/ul>\n<\/div>\n\n\n<p>And to finish, you ran Linux containers on a Windows container host, which is a great improvement for sysadmin and developers. Currently, LCOW is still in beta and not supported In a production environment so please use it for dev purposes.<\/p>\n\n\n\n<p>In the next article, I will discuss about how to manage and orchestrate our Windows containers with Kubernetes and Swarm.<\/p>\n\n\n\n<section id=\"faq\" class=\"faq-block my-5xl\">\n    <h2>FAQs: Working with Windows Containers and Docker: Save the Data<\/h2>\n\n                        <h3 class=\"mt-4xl\">1. How do you persist data in Docker containers on Windows?<\/h3>\n            <div class=\"faq-answer\">\n                <p>Use Docker volumes &#8211; storage outside the container filesystem. Create with docker volume create, mount with -v flag. Data persists even after container removal. Share a single volume between multiple containers.<\/p>\n            <\/div>\n                    <h3 class=\"mt-4xl\">2. Can you share data between Docker containers?<\/h3>\n            <div class=\"faq-answer\">\n                <p>Yes. Create a named volume, mount to multiple containers simultaneously. Each can read\/write. Useful for shared config, common data stores, log aggregation.<\/p>\n            <\/div>\n            <\/section>\n","protected":false},"excerpt":{"rendered":"<p>Persist data in Windows Docker containers: create independent volumes, share volumes between multiple containers, copy data from the container host, and define volumes in Dockerfiles. Also covers Docker CE vs EE editions and running Linux containers on Windows (LCOW).&hellip;<\/p>\n","protected":false},"author":158223,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[143513],"tags":[95506],"coauthors":[6804],"class_list":["post-78494","post","type-post","status-publish","format-standard","hentry","category-containers-and-virtualization","tag-automate"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/78494","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/users\/158223"}],"replies":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/comments?post=78494"}],"version-history":[{"count":19,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/78494\/revisions"}],"predecessor-version":[{"id":110383,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/78494\/revisions\/110383"}],"wp:attachment":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/media?parent=78494"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/categories?post=78494"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/tags?post=78494"},{"taxonomy":"author","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/coauthors?post=78494"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}