Overview

In this article we are going to go through the steps how to deploy Nextcloud on Docker using Ansible. Purpose of this procedure is to automatize the deployment process of Nextcloud on Docker with the Ansible playbook.

In order to deploy nextcloud on docker using ansible successfully, there are some requirements first to configure(listed bellow in the prerequisites)

Prerequisites

  • Docker installed and running on the target host machine(Docker installation can also be automated with Ansible - link to the POST)
  • SSH access enabled on the remote hosts with the login parameters preset in the Ansible hosts file
  • Ansible installed on client machine(your machine)
  • Installed Python and Python docker module for Ansible on target machine
  • Installed Python on your local machine

Install Python Docker module for Ansible

Most Linux distros have Python3 preinstalled but for others the Python Docker module that Ansible uses may be missing. You’ll know that it’s if you get an error mentioning that the module is missing or not found. Picture example of the error bellow:

The mentioned module is actually the Docker SDK that Python uses to work with Docker. The easiest way to install the Python Docker module is with the “pip” tool. If the “pip” tool is missing, you can easily install and then with it to install the python docker module:

Debian/Ubuntu

sudo apt install python3-pip

Fedora

sudo dnf install python3-pip

CentOS/RedHat

sudo yum python3-pip

After you installed the pip, then run the command to install docker module:

pip3 install docker

If by any chance, you encounter an error in Ansible that the it cannot find the Python module, add a python interpreter variable in your hosts file. In most cases it’s located either in “/usr/bin/python3” or “/usr/lib/python3”.

Error looks something like this:

[Deploy Nextcloud on Docker using Ansible]

The interpreter variable in the hosts file looks something like this:

ansible_python_interpreter=/usr/bin/python3

Write down the hosts in the hosts file with the login parameters

First step – Adding the necessary parameters in hosts file so that the Ansible can reach, login and interact with our machine:

sudo nano /etc/ansible/hosts

In the hosts file, add the parameters to look something like this:

[Deploy Nextcloud on Docker using Ansible]

After the necessary parameters for our remote host are added, save the file and exit.

Ansible playbook for Nextcloud deployment on Docker

For this deployment, we’ll be using the following playbook:

---
- hosts: docker
    vars:
      db_volume: mariadb
      nextcloud: nextcloud
    tasks:
      - name: Deploy MariaDB server
        docker_container:
          image: mariadb
          name: mariadb
          volumes:
            - "{{db_volume}}:/var/lib/mysql"
          env:
            MYSQL_ROOT_PASSWORD: somerootpassword
            MYSQL_PASSWORD: somemysqlpassword
            MYSQL_DATABASE: db
            MYSQL_USER: mysqluser

      - name: Deploy Nextcloud
        docker_container:
          image: nextcloud
          name: nextcloud
          restart_policy: always
          ports:
            - "8080:80"
          links:
            - "{{db_volume}}:/var/lib/mysql"
          volumes:
            - "{{nextcloud}}:/var/www/html"
          env:
            MYSQL_PASSWORD: somemysqlpassword
            MYSQL_DATABASE: db
            MYSQL_USER: mysqluser
            MYSQL_HOST: mariadb

Feel free to just copy it.

Playbook breakdown:


**hosts: docker** // variable to target only machine hosts that are in the docker group

**vars:** 

**db_volume: mariadb** 

**nextcloud: nextcloud  // [OPTIONAL]** defined variables for each container. These are used for setting volumes on the host and are matching the container names.

tasks: // Defined a task which will deploy a MariaDB container(MariaDB database server in container form). Task will pull down the official Docker image of MariaDB from the Docker hub, set a name container name "mariadb" and set a persistent volume on the host machine for the database storage.

- name: Deploy MariaDB server // Task name

docker_container: // Docker function that Ansible will use

image: mariadb  // Docker image to pull down

name: mariadb // Specify the container name

volumes: - "{{db_volume}}:/var/lib/mysql" // Specify a volume on the host machine for persistent storage

env: // Environment variables to define parameters for the database such as the root password, admin user password, name of the database and the user name of the new user on the MariaDB server

MYSQL_ROOT_PASSWORD: somerootpassword // MySQL root password

MYSQL_PASSWORD: somemysqlpassword // MySQL admin/standard user password to be used by Nextcloud

MYSQL_DATABASE: db // MySQL database name

MYSQL_USER: mysqluser // Admin/standard user username for Nextcloud to use

// This is the task that will deploy the Nextcloud Docker container. Same just like for the MariaDB container, Ansible will pull down the official Nextcloud image from the Docker hub. Here we also specified the container restart policy(when to restart the container) and also set number of ports to expose on the container and bind to the host, so that the container can be accessible via browser and http protocol. 

name: Deploy Nextcloud // Task name

docker_container: // Docker function that Ansible will use

image: nextcloud // Docker image to pull down

name: nextcloud // Specify the container name

restart_policy: always // Set attribute for container restart

ports: - "8080:80" // Specify ports to expose on the container to be accessible via web browser 
links:
- "{{db_volume}}:/var/lib/mysql // Variable to specify the link to the MySQL server so that Nextcloud can connect to the database

volumes: - "{{nextcloud}}:/var/www/html" // Specify a volume on the host machine for persistent storage

// Environment variables for the MariaDB database, for Nextcloud to use in order to connect to the database and use the database for data storage. 

env: 

MYSQL_PASSWORD: somemysqlpassword // Variable to specify MySQL for Nextcloud to use

MYSQL_DATABASE: db // MySQL database name which will Nextcloud connect to 

MYSQL_USER: mysqluser // MySQL user for Nextcloud to use

MYSQL_HOST: mariadb // MySQL database server to connect to(docker container name we previously set)

Deploy Nextcloud on Docker using Ansible

Now that we have our playbook, we can now run it:

ansible-playbook nextcloud-ansible -l docker

Expected result and check if the containers are deployed and running:

[Deploy Nextcloud on Docker using Ansible]

Deploy Nextcloud on Docker using Ansible

Check if the Nextcloud is accessible via browser:

Deploy Nextcloud on Docker using Ansible

Small note on the possible issue with the database:

You may get a following error on the finish setup page while trying to create an account for Nextcloud:

“InnoDB refuses to write tables with ROW_FORMAT=COMPRESSED or KEY_BLOCK_SIZE”

[Deploy Nextcloud on Docker using Ansible]

This started to happen on Nextcloud version 21 and later. Essentially, Nextcloud does not support InnoDB compression on the databases. The workaround for this is to just disable the InnoDB compression and to do that, add the following the configuration in the Ansible .yaml file at the MariaDB config an re-run the deployment:

“command: –transaction-isolation=READ-COMMITTED –binlog-format=ROW –innodb-file-per-table=1 –skip-innodb-read-only-compressed”

The full MariaDB config should look like this:

tasks:
  - name: Deploy MariaDB server
    docker_container:
      image: mariadb
      name: mariadb
      command: --transaction-isolation=READ-COMMITTED --binlog-format=ROW --innodb-file-per-table=1 --skip-innodb-read-only-compressed
      volumes:
        - "{{db_volume}}:/var/lib/mysql"
      env:
        MYSQL_ROOT_PASSWORD: somerootpassword
        MYSQL_PASSWORD: somemysqlpassword
        MYSQL_DATABASE: db
        MYSQL_USER: mysqluser

After you run this config again, the issue should be resolved.

Summary

To summarize the article - we managed to successfully deploy Nextcloud on Docker using Ansible and with that we have automated the process of deploying Nextcloud on Docker.

Though Ansible environment was required to setup with Python and Python Docker module for this process to be successful.

Afterward we wrote and ran the Ansible playbook which deploys Nextcloud with the database and also have data persistence so that the data and files are not stored within the Docker container.

Thank you for your time…