arderoma
arderoma

Reputation: 427

Why is this volume mounted as read only?

I got from this link https://hub.docker.com/_/wordpress a docker-compose.yml file like this.

version: '3.1'

services:

  wordpress:
    image: wordpress
    restart: always
    ports:
      - 8080:80
    environment:
      WORDPRESS_DB_HOST: db
      WORDPRESS_DB_USER: exampleuser
      WORDPRESS_DB_PASSWORD: examplepass
      WORDPRESS_DB_NAME: exampledb
    volumes:
      - wordpress:/var/www/html

  db:
    image: mysql:5.7
    restart: always
    environment:
      MYSQL_DATABASE: exampledb
      MYSQL_USER: exampleuser
      MYSQL_PASSWORD: examplepass
      MYSQL_RANDOM_ROOT_PASSWORD: '1'
    volumes:
      - db:/var/lib/mysql

volumes:
  wordpress:
  db:

But the volume is not getting mounted on the wordpress folder, and if I delete "wordpress" to mount the volume on the local folder it gets mounted but it does as read only. I don't have a Dockerfile am I just using the default image and that's the problem?

Upvotes: 1

Views: 1784

Answers (1)

joshmoto
joshmoto

Reputation: 5128

I use docker all the time for wordpress, this is my workflow.. (on a Mac)

Create a project folder and add a docker-compose.yml file with this..

version: '3.7'

services:

  # here is our mysql container
  db:
    image: mysql:5.7
    volumes:
      - ./db:/var/lib/mysql:delegated
    ports:
      - "3306:3306"
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: somewordpress
      MYSQL_DATABASE: wordpress
      MYSQL_USER: wordpress
      MYSQL_PASSWORD: wordpress

  # here is our wordpress container
  wordpress:
    depends_on:
      - db
    image: wordpress:latest
    volumes:
      # our persistent local data re routing
      - .:/var/www/html/wp-content/themes/testing:delegated
      - ./plugins:/var/www/html/wp-content/plugins
      - ./uploads:/var/www/html/wp-content/uploads
      - ./uploads.ini:/usr/local/etc/php/conf.d/uploads.ini
    ports:
      - "80:80"
    restart: always
    environment:
      # our local dev environment
      WORDPRESS_DEBUG: 1
      DEVELOPMENT: 1
      # docker wp config settings
      WORDPRESS_DB_HOST: db:3306
      WORDPRESS_DB_USER: wordpress
      WORDPRESS_DB_PASSWORD: wordpress
      WORDPRESS_DB_NAME: wordpress
      WORDPRESS_AUTH_KEY: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_SECURE_KEY: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_LOGGED_IN_KEY: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_NONCE_KEY: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_SECURE_AUTH_SALT: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_LOGGED_IN_SALT: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_NONCE_SALT: 5f6ede1b94d25a2294e29eeba929a8c80a5ac0fb
      WORDPRESS_CONFIG_EXTRA: |

        /* Development parameters */
        define('WP_CACHE', false);
        define('ENVIRONMENT', 'local');

        /* Configure mailhog server */
        define('WORDPRESS_SMTP_AUTH', false);
        define('WORDPRESS_SMTP_SECURE', '');
        define('WORDPRESS_SMTP_HOST', 'mailhog');
        define('WORDPRESS_SMTP_PORT', '1025');
        define('WORDPRESS_SMTP_USERNAME', null);
        define('WORDPRESS_SMTP_PASSWORD', null);
        define('WORDPRESS_SMTP_FROM', '[email protected]');
        define('WORDPRESS_SMTP_FROM_NAME', 'Whoever');

        /* other wp-config defines here */

  # here is our mailhog container
  mailhog:
    image: mailhog/mailhog:latest
    ports:
      - "8025:8025"

Then in this project folder run this terminal command (with docker app running)..

docker-compose up -d

..and bam you will have a wordpress site at http://localhost/

This docker-compose.yml is configured so you will have..

  • Wordpress site at http://localhost/ or http://localhost:80
  • Mailhog server that captures all outgoing mail at http://localhost:8025/
  • Persistent local database, plugins, uploads and uploads.ini

All persistent data is mapped to this project folder, which is your theme folder. This keeps things nice and collected for each project..

enter image description here

After initial build before you do anything, replace the uploads.ini folder with an actual uploads.ini file..

file_uploads = On
memory_limit = 2000M
upload_max_filesize = 2000M
post_max_size = 2000M
max_execution_time = 600

So your project (theme) folder should look like this..

enter image description here

Now you can start building your theme in this folder like this, keeping everything associated with this local environment here.

enter image description here

Every time you run this command to shut down the environment..

docker-compose down

Next time you run this command on this project..

docker-compose up -d

..all your previous database, plugins and uploads will be exactly where you left off, awesome for wordpress local dev!


A few considerations to take into account..




Using GIT with this local wordpress project

If your using GIT to save this project as a repository, then make sure your .gitignore file excludes these files/folders..

/vendor
/uploads
/db
/dist
/node_modules
/plugins

Worth having an alternate cloud backup solution setup like google drive for your /db, /plugins and /uploads folders, just in case of hard drive failure or something.




Deploying to server, staging and production

In your IDE settings for this project you may want exclude certain files and folder from being deployed to staging and production server environments, this is what I normally exclude..

/Users/joshmoto/Sites/demo/db
/Users/joshmoto/Sites/demo/node_modules
/Users/joshmoto/Sites/demo/src
/Users/joshmoto/Sites/demo/uploads
/Users/joshmoto/Sites/demo/composer.json
/Users/joshmoto/Sites/demo/composer.lock
/Users/joshmoto/Sites/demo/docker-compose.yml
/Users/joshmoto/Sites/demo/package-lock.json
/Users/joshmoto/Sites/demo/package.json
/Users/joshmoto/Sites/demo/uploads.ini
/Users/joshmoto/Sites/demo/webpack.mix.js
/Users/joshmoto/Sites/demo/plugins
/Users/joshmoto/Sites/demo/.gitignore
/Users/joshmoto/Sites/demo/vendor
  • /plugins I manually manage by uploading through cPanel or wordpress dashboard, because the indexing is so heavy when syncing to remote.
  • /vendors is generate from composer and the same problem, the indexing is crazy so best to manually zip this up and upload through cPanel or whatever server admin you use.



If you have problems uploading media and plugins locally via the wordpress dashboard

You may be faced with some permission problems sometimes with dockers wordpress container wp-content folder. It is an easy fix. While your project is up and running in docker, in the project run these docker compose commands to change permissions on wp-content folder..

Show running docker containers command..

docker ps

Returned result..

CONTAINER ID        IMAGE                    COMMAND                  CREATED             STATUS              PORTS                               NAMES
4052536e574a        wordpress:latest         "docker-entrypoint.s…"   1 hour ago          Up 1 hour           0.0.0.0:80->80/tcp                  demo_wordpress_1
b0fbb0a8f9e6        mysql:5.7                "docker-entrypoint.s…"   1 hour ago          Up 1 hour           0.0.0.0:3306->3306/tcp, 33060/tcp   demo_db_1
769262e584e7        mailhog/mailhog:latest   "MailHog"                1 hour ago          Up 1 hour           1025/tcp, 0.0.0.0:8025->8025/tcp    demo_mailhog_1

Copy and take note the wordpress:latest container ID, in this example my container ID is..

4052536e574a

Now run this command using this wordpress container ID to execute stuff in this container directory..

docker exec -it 4052536e574a /bin/bash

Returned result..

root@4052536e574a:/var/www/html#

Now we are in the containers root directory you can now run this command which will change the permissions recursively on the wp-content and fix the uploading permissions issue in the local wordpress dashboard.

chown -R www-data:www-data wp-content

You may have to run docker-compose down and docker-compose up -d commands on the project folder for these changes to take effect but I don't think you need too.




If you want a local custom URL instead of http://localhost

In terminal (not in your project folder this time) run this command to edit your hosts file..

sudo nano /etc/hosts

Then add your custom url to your hosts file via terminal and WriteOut before you Exit..

127.0.0.1  local.demo.com

Now your redirect mask is saved in your hosts you will need to add this to your docker-compose.yml below /* other wp-config defines here */..

define('WP_HOME','http://local.demo.com');
define('WP_SITEURL','http://local.demo.com');

Unfortunately you can't use https, you have to use http.

You will need to docker-compose down and docker-compose up -d for these newly define configs to run in your local wp-config.php.




Handling your Staging and Production wp-config

Your server environments should be independently installed with unique salts etc, you should not take anything from the docker-compose.yml config, really you only want to add these extra defines initially..

Staging wp-config.php

define('ENVIRONMENT', 'staging');
define('WP_DEBUG', true);
define('WP_HOME','https://staging.demo.com');
define('WP_SITEURL','https://staging.demo.com');

Production wp-config.php

define('ENVIRONMENT', 'production');
define('WP_DEBUG', false);
define('WP_HOME','https://www.demo.com');
define('WP_SITEURL','https://www.demo.com');



Updating dockers wordpress image

You can't update your local wordpress site via the wordpress dashboard. In my docker-compose.yml example I am defining image: wordpress:latest which gets the latest wordpress image installed on your docker app.

This means if you docker-compose up -d on a project that was using an older version of wordpress at the time, this project would update to the latest wordpress image installed on docker.

I've not personally defined wordpress image versions in docker-compose.yml but you can if you do not want certain projects to use the latest image when you next docker-compose up -d a project.

You have to update the wordpress docker image manually using this command..

docker pull wordpress

And you will have to docker-compose down and docker-compose up -d for your project to use the latest update, which some times requires a wordpress database update when accessing the site for the first time through your browser.




Permission issues when uploading / deleting plugins via dashboard

To change the permissions on the wp-content folder so uploads and plugins can be written via the dashboard.

Make sure you run these commands below while the containers are running...

  1. Show containers command...
    docker ps
  2. Make a note of the container ID for the running wordpress image
  3. Execute in container command (replace [container_id] with your ID with no brackets)...
    docker exec -it [container_id] /bin/bash
  4. Change permissions on wp-content folder...
    chown -R www-data:www-data wp-content

This should resolve any problems uploading and deleting files via the dashboard for uploads and plugins locally with docker compose.

Upvotes: 4

Related Questions