<commit_before>---
author: neilpeterson
---

# Dockerfile on Windows

**This is preliminary content and subject to change.** 

The Docker engine includes tools for automating the creation of container images. While container images can be created manually using the ‘docker commit’ command, adopting an automated image creation process provides many benefits, including:

- Storing container images as code.
- Rapid and precise recreation of container images for maintenance and upgrade purposes.
- Continuous integration between container images and the development cycle.

The Docker components that drive this automation are the Dockerfile and the Docker build command.

- **Dockerfile** – a text file containing the instruction needed to create a new container image. These instructions include identification of an existing image to be used as a base, commands to be run during the image creation process, and run time commands for running instances of the new container image.
- **Docker build** - the Docker engine command that consumes a Dockerfile, and triggers the image creation process.

This document will introduce using a Dockerfile with Windows containers, discuss syntax, and detail commonly used Dockerfile instructions. 

Throughout this document, the concept of container images and container image layers will be discussed. For more information on images and image layering see [Manage Windows Container Images](./manage_images). 

For a complete look at the Docker engine and Dockerfile, see the [Dockerfile reference at docker.com]( https://docs.docker.com/engine/reference/builder/).

## Dockerfile Introduction

### Basic Syntax

In its most basic form, a Dockerfile can be very simple. The following example creates a new image, which includes IIS, and a new ‘hello world’ site. This example includes comments (indicated with a ‘#’), that explain each line. Subsequent sections of this article will detail syntax rules and Dockerfile instructions.

```none
# Sample Dockerfile

# Indicates that the windowsservercore image will be used as the base image.
FROM windowsservercore

# Metadata indicating an image maintainer.
MAINTAINER <EMAIL>

# Uses dism.exe to install the IIS role.
RUN dism.exe /online /enable-feature /all /featurename:iis-webserver /NoRestart

# Creates an html file and adds content to this file.
RUN echo "Hello World - Dockerfile" > c:\inetpub\wwwroot\index.html

# Sets a command or process that will run each time a container is run from the new image.
CMD [ "cmd" ]
```

For additional examples of Dockerfiles for Windows, see the [Dockerfile for Windows Repository] (https://github.com/Microsoft/Virtualization-Documentation/tree/master/windows-server-container-samples).

## Instructions

Dockerfile instructions provide the Docker Engine with the steps needed to create a container image. These instructions are performed in order, and one-by-one. Here are the details for some basic Dockerfile instructions. For a complete list of Dockerfile instructions, see [Dockerfile Reference on Docker.com] (https://docs.docker.com/engine/reference/builder/).

### FROM

The FROM instruction sets the container image that will be used during the new image creation process. For instance, when using the instruction `FROM windowsservercore`, the resulting image will be derived from, and have a dependency on, the Windows Server Core Base OS image. If the specified image is not present on the system where the Docker build process is being run, the Docker engine will attempt to download the image from a public or private image registry.

**Format**

The FROM instruction takes a format of: 

```
FROM <image>
```

**Example**

```
FROM windowsservercore
```

For detailed information on the FROM instruction, see the [FROM Reference on Docker.com]( https://docs.docker.com/engine/reference/builder/#from). 

### RUN

The RUN instruction specifies commands to be run, and captured into the new container image. These commands can include items such as installing software, creating files and directories, and creating environment configuration.

**Format**

The RUN instruction takes a format of: 

```none
# exec form

RUN ["<executable", "<param 1>", "<param 2>"

# shell form

RUN <command>
```

**Examples**

This example uses DISM to install IIS in the container image.<commit_msg>RUN exec method clarification<commit_after>---
author: neilpeterson
---

# Dockerfile on Windows

**This is preliminary content and subject to change.** 

The Docker engine includes tools for automating the creation of container images. While container images can be created manually using the ‘docker commit’ command, adopting an automated image creation process provides many benefits including:

- Storing container images as code.
- Rapid and precise recreation of container images for maintenance and upgrade purposes.
- Continuous integration between container images and the development cycle.

The Docker components that drive this automation are the Dockerfile and the Docker build command.

- **Dockerfile** – a text file containing the instruction needed to create a new container image. These instructions include identification of an existing image to be used as a base, commands to be run during the image creation process, and run time commands for running instances of the new container image.
- **Docker build** - the Docker engine command that consumes a Dockerfile, and triggers the image creation process.

This document will introduce using a Dockerfile with Windows containers, discuss syntax, and detail commonly used Dockerfile instructions. 

Throughout this document, the concept of container images and container image layers will be discussed. For more information on images and image layering see [Manage Windows Container Images](./manage_images). 

For a complete look at Dockerfiles, see the [Dockerfile reference at docker.com]( https://docs.docker.com/engine/reference/builder/).

## Dockerfile Introduction

### Basic Syntax

In its most basic form, a Dockerfile can be very simple. The following example creates a new image, which includes IIS, and a ‘hello world’ site. This example includes comments (indicated with a ‘#’), that explain each line. Subsequent sections of this article will detail syntax rules and Dockerfile instructions.

```none
# Sample Dockerfile

# Indicates that the windowsservercore image will be used as the base image.
FROM windowsservercore

# Metadata indicating an image maintainer.
MAINTAINER <EMAIL>

# Uses dism.exe to install the IIS role.
RUN dism.exe /online /enable-feature /all /featurename:iis-webserver /NoRestart

# Creates an html file and adds content to this file.
RUN echo "Hello World - Dockerfile" > c:\inetpub\wwwroot\index.html

# Sets a command or process that will run each time a container is run from the new image.
CMD [ "cmd" ]
```

For additional examples of Dockerfiles for Windows, see the [Dockerfile for Windows Repository] (https://github.com/Microsoft/Virtualization-Documentation/tree/master/windows-server-container-samples).

## Instructions

Dockerfile instructions provide the Docker Engine with the steps needed to create a container image. These instructions are performed in order, and one-by-one. Here are the details for some basic Dockerfile instructions. For a complete list of Dockerfile instructions, see [Dockerfile Reference on Docker.com] (https://docs.docker.com/engine/reference/builder/).

### FROM

The FROM instruction sets the container image that will be used during the new image creation process. For instance, when using the instruction `FROM windowsservercore`, the resulting image is derived from, and has a dependency on, the Windows Server Core base OS image. If the specified image is not present on the system where the Docker build process is being run, the Docker engine will attempt to download the image from a public or private image registry.

**Format**

The FROM instruction takes a format of: 

```
FROM <image>
```

**Example**

```
FROM windowsservercore
```

For detailed information on the FROM instruction, see the [FROM Reference on Docker.com]( https://docs.docker.com/engine/reference/builder/#from). 

### RUN

The RUN instruction specifies commands to be run, and captured into the new container image. These commands can include items such as installing software, creating files and directories, and creating environment configuration.

**Format**

The RUN instruction takes a format of: 

```none
# exec form

RUN ["<executable", "<param 1>", "<param 2>"

# shell form

RUN <command>
```

The difference between the exec and shell form, is in how the RUN instruction is executed. When using the exec method, the specified program is run explicitly. The following example used the exec form.

```
FROM windowsservercore
RUN ["powershell","New-Item","c:/test"]
```

Examining the resulting image, the command the was run is `poweshell new-item c:/test’.

```
C:\> docker history doc-exe-method

IMAGE               CREATED             CREATED BY                    SIZE                COMMENT
b3452b13e472        2 minutes ago       powershell New-Item c:/test   30.76 MB
```

To contrast, the following example runs the same operation, however using the shell form.

```
FROM windowsservercore

RUN powershell new-item c:\test
```

Which results in a run instruction of `cmd /S /C powershell new-item c:\test`. 

```
C:\> docker history doc-shell-method

IMAGE               CREATED             CREATED BY                              SIZE                COMMENT
062a543374fc        19 seconds ago      cmd /S /C powershell new-item c:\test   30.76 MB
```

**Windows Considerations**
 
On Windows, when using the RUN instruction with the exec format, forward slashes must be used. These are valid RUN instructions.

```none
RUN ["powershell","New-Item","c:/test"]
RUN powershell new-item c:\test
```

However, the following will not work.

```none
RUN ["powershell","New-Item","c:\test"]
```

**Examples**

This example uses DISM to install IIS in the container image.
{'fraction_non_alphanumeric': 0.06793991843230876, 'fraction_numerical': 0.003282602208296031, 'mean_word_length': 4.286014721345952, 'pattern_counts': {'":': 0, '<': 15, '<?xml version=': 0, '>': 17, 'https://': 8, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2015902', 'n_tokens_mistral': 2544, 'n_tokens_neox': 2364, 'n_words': 1316}