AnsiblePilot — Master Ansible Automation

AnsiblePilot is the leading resource for learning Ansible automation, DevOps, and infrastructure as code. Browse over 1,400 tutorials covering Ansible modules, playbooks, roles, collections, and real-world examples. Whether you are a beginner or an experienced engineer, our step-by-step guides help you automate Linux, Windows, cloud, containers, and network infrastructure.

Popular Topics

About Luca Berton

Luca Berton is an Ansible automation expert, author of 8 Ansible books published by Apress and Leanpub including "Ansible for VMware by Examples" and "Ansible for Kubernetes by Example", and creator of the Ansible Pilot YouTube channel. He shares practical automation knowledge through tutorials, books, and video courses to help IT professionals and DevOps engineers master infrastructure automation.

Ansible win_copy Module: Copy Files to Windows Hosts (ansible.windows.win_copy)

By Luca Berton · Published 2024-01-01 · Category: installation

How to copy files to Windows remote hosts with Ansible win_copy module (ansible.windows.win_copy). Transfer files, directories, set permissions.

Ansible win_copy Module: Copy Files to Windows Hosts (ansible.windows.win_copy)

How to copy files to Windows remote hosts?

I'm going to show you a live Playbook with some simple Ansible code. I'm Luca Berton and welcome to today's episode of Ansible Pilot

See also: Ansible fetch Module: Copy Files from Remote Hosts to Control Node

Ansible copy files to Windows remote hosts

Today we’re talking about Ansible module win_copy. The full name is ansible.windows.win_copy which means is part of the collection of modules “ansible.windows” targeted windows remote hosts. This module is pretty stable and out for years. The purpose is to copy files from the local machine to remote locations. Because win_copy runs over WinRM, it is not a very efficient transfer mechanism. If you plan to send large files consider hosting them on a web service and using ansible.windows.win_get_url instead. Please note that the opposite is done by module win_fetch. On Linux target use the module ansible.builtin.copy.

Please note that the opposite is done by module win_fetch. On Linux target use the Ansible copy module..

Parameters

dest _path_ - remote path • src _string_ - local path • backup _boolean_ - no / yes • force _string_ - yes / no

I'm going to summarize the most useful parameters. The only required parameter is "dest" which specifies the remote absolute path destination. It's better with "\", the Windows way, instead of "/", the Unix way. Please also verify that the remote user has the right to write in this path. The "src" specifies the source file in the controller host. It could be a relative or absolute path. I recommend absolutely. If the source is a directory all the content is copied. Please be more careful with the "/" at the end. If present only the content of the directory is copied, if you want the directory and the content you need to omit the "/" character. The "backup" boolean parameter allows you to create a backup if the utility overwrites any file. The default behavior is to transfer the file only if not present or differ in the target host, the file is also verified by Ansible with a checksum on the source and target host automatically. If you want to transfer the all the time the file you need to toggle the "force" parameter to "no". Please note that setting to "no" also disables the checksum that could speed up the process but also corrupt the file.

See also: Ansible win_stat: Check if File or Directory Exists on Windows (Examples)

Demo

Let's jump in a real-life playbook to copy files to Windows remote hosts with Ansible. • copy.yml
---
- name: win_copy module Playbook
  hosts: all
  become: false
  gather_facts: false
  vars:
    source: "report.txt"
    destination: "Desktop/report.txt"
  tasks:
    - name: copy report.txt
      ansible.windows.win_copy:
        src: "{{ source }}"
        dest: "{{ destination }}"
• report.txt
test report.txt

code with ❤️ in GitHub

Conclusion

Now you know how to copy files to remote Windows hosts with Ansible.

See also: Ansible win_file Module: Create & Manage Files on Windows (Guide)

Copy File to Windows

- name: Copy config file
  ansible.windows.win_copy:
    src: files/app-config.xml
    dest: C:\Program Files\MyApp\config.xml

Copy Directory

- name: Copy entire directory
  ansible.windows.win_copy:
    src: files/webapp/
    dest: C:\inetpub\wwwroot\myapp\

Copy Content (Inline)

- name: Create config from content
  ansible.windows.win_copy:
    content: |
      [database]
      host=db.example.com
      port=5432
      name=myapp
    dest: C:\MyApp\config.ini

Copy with Backup

- name: Copy with backup of existing
  ansible.windows.win_copy:
    src: files/new-config.xml
    dest: C:\MyApp\config.xml
    backup: true

Remote to Remote Copy

- name: Copy file on remote host
  ansible.windows.win_copy:
    src: C:\Temp\installer.exe
    dest: C:\Program Files\MyApp\installer.exe
    remote_src: true

Deployment Pattern

---
- name: Deploy app to Windows
  hosts: windows
  tasks:
    - name: Stop service
      ansible.windows.win_service:
        name: MyAppService
        state: stopped

- name: Backup current config ansible.windows.win_copy: src: C:\MyApp\config.xml dest: C:\Backup\config-{{ ansible_date_time.date }}.xml remote_src: true ignore_errors: true

- name: Deploy application files ansible.windows.win_copy: src: dist/ dest: C:\MyApp\

- name: Deploy configuration ansible.windows.win_template: src: config.xml.j2 dest: C:\MyApp\config.xml

- name: Start service ansible.windows.win_service: name: MyAppService state: started

win_copy vs win_template

| Module | Use Case | |--------|----------| | win_copy | Static files (as-is) | | win_template | Files with Jinja2 variables | | win_get_url | Download from URL | | win_robocopy | Large directory sync |

Key Parameters

| Parameter | Description | |-----------|-------------| | src | Source file/directory (controller) | | dest | Destination path (Windows) | | content | Inline content to write | | remote_src | Source is on remote host | | backup | Create backup of existing file | | force | Replace if different (default: true) |

FAQ

How do I copy large files efficiently?

For large directories, community.windows.win_robocopy is faster:

- community.windows.win_robocopy:
    src: C:\Source
    dest: C:\Destination
    flags: /MIR /MT:8

Linux copy vs win_copy?

Use copy for Linux, win_copy for Windows. They have the same interface but different backends.

How do I set file permissions on Windows?

Use win_acl after copying:

- ansible.windows.win_acl:
    path: C:\MyApp\config.xml
    user: AppUser
    rights: Read
    type: allow

Copy File to Windows

- name: Copy config to Windows
  ansible.windows.win_copy:
    src: files/app.config
    dest: C:\MyApp\app.config

Copy with Content

- win_copy:
    content: |
      [database]
      host=db.internal
      port=5432
    dest: C:\MyApp\config.ini

Copy Directory

# Copy entire directory
- win_copy:
    src: files/webapp/
    dest: C:\inetpub\wwwroot\myapp\

Remote to Remote

- win_copy:
    src: C:\Backups\config.bak
    dest: C:\MyApp\config.ini
    remote_src: true

Force and Backup

# Don't overwrite existing
- win_copy:
    src: files/initial-config.ini
    dest: C:\MyApp\config.ini
    force: false

# Create backup before overwrite - win_copy: src: files/new-config.ini dest: C:\MyApp\config.ini backup: true

Copy Multiple Files

- win_copy:
    src: "{{ item.src }}"
    dest: "{{ item.dest }}"
  loop:
    - { src: files/web.config, dest: 'C:\inetpub\wwwroot\web.config' }
    - { src: files/app.config, dest: 'C:\MyApp\app.config' }
    - { src: files/nlog.config, dest: 'C:\MyApp\nlog.config' }

Deploy Application Files

- name: Create app directory
  win_file:
    path: C:\MyApp
    state: directory

- name: Copy application win_copy: src: dist/myapp/ dest: C:\MyApp\

- name: Copy config template win_template: src: appsettings.json.j2 dest: C:\MyApp\appsettings.json

- name: Restart app service win_service: name: MyAppService state: restarted

win_copy vs win_template

| Module | Use Case | |--------|----------| | win_copy | Static files, binaries, inline content | | win_template | Files with Jinja2 variables/logic | | win_get_url | Download from HTTP/S | | win_robocopy | Large directory sync |

Fetch from Windows

# Copy FROM Windows TO controller
- fetch:
    src: C:\Logs\app.log
    dest: /tmp/windows-logs/{{ inventory_hostname }}/
    flat: true

Key Parameters

| Parameter | Description | |-----------|-------------| | src | Source file/dir on controller | | dest | Destination on Windows host | | content | Inline content (instead of src) | | backup | Keep backup of original | | force | Overwrite if different | | remote_src | Source is on remote Windows |

FAQ

Path format — forward or backslash?

Both work in YAML. Use backslash for clarity: C:\MyApp\config. In YAML, single-quote paths to avoid escape issues.

Large files are slow?

WinRM has overhead for large transfers. For large files, use win_get_url to download from a file share or HTTP server.

How do I set Windows file permissions?

- win_acl:
    path: C:\MyApp\secrets.config
    user: DOMAIN\AppUser
    rights: Read
    type: allow

Related Articles

sudo and become in Ansible playbookscreating an Ansible role from scratchconfiguring Windows services via Ansible

Category: installation

Watch the video: Ansible win_copy Module: Copy Files to Windows Hosts (ansible.windows.win_copy) — Video Tutorial

Browse all Ansible tutorials · AnsiblePilot Home