Search code examples
dockerdocker-composedockerfilenodemon

How to make my server in my Docker container reload with changes


I have created a simple app connected with PostgreSQL and pgAdmin, as well as a web server in a Docker images running in a container.

My question is how I can make it reload, like with nodemon in a local server, without the need of deleting the container everytime.

I have been trying different solutions and methods I have seen around but I haven't been able to make it work.

I have already tried inserting the command: ["npm", "run", "start:dev"] in the docker-compose.file as well...

My files are:

Dockerfile

FROM node:latest

WORKDIR /

COPY package*.json ./
COPY . .
COPY database.json .
COPY .env .

EXPOSE 3000

CMD [ "npm", "run", "watch ]

Docker-compose.file

version: '3.7'
services:
    postgres:
        image: postgres:latest
        environment:
            - POSTGRES_USER=test
            - POSTGRES_PASSWORD=tes
            - POSTGRES_DB=test
        ports:
            - 5432:5432
        logging:
            options:
                max-size: 10m
                max-file: "3"
    pgadmin:
        image: dpage/pgadmin4
        environment:
            - PGADMIN_DEFAULT_EMAIL=test@gmail.com
            - PGADMIN_DEFAULT_PASSWORD=pasword123test
        ports:
            - "5050:80"
    web:
        build: .
        # command: ["npm", "run", "start:dev"]
        links:
        - postgres
        image: prueba
        depends_on: 
        - postgres
        ports: 
        - '3000:3000'
        env_file:
        - .env

Nodemon.json file:

{
    "watch": ["dist"],
    "ext": ".ts,.js",
    "ignore": [],
    "exec": "ts-node ./dist/server.js"
  }

Package.json file:

  "scripts": {
    "start:dev": "nodemon",
    "build": "rimraf ./dist && tsc",
    "start": "npm run build && node dist/server.js",
    "watch": "tsc-watch --esModuleInterop src/server.ts --outDir ./dist --onSuccess \"node ./dist/server.js\"",
    "jasmine": "jasmine",
    "test": "npm run build && npm run jasmine",
    "db-test": "set ENV=test&& db-migrate -e test up && npm run test && db-migrate -e test reset",
    "lint": "eslint . --ext .ts",
    "prettier": "prettier --config .prettierrc src/**/*.ts --write",
    "prettierLint": "prettier --config .prettierrc src/**/*.ts --write && eslint . --ext .ts --fix"
  },

Thanks


Solution

  • The COPY . . command only runs when the image is built, which only happens when you first run docker compose up. In order for the container to be aware of changes, you need the code changes on your host machine to be synchronized with the code inside the container, even after the build is complete.

    Below I've added the volume mount to the web container in your docker compose and uncommented the command that should support hot-reloading. I assumed that the source code you wanted to change lives in a src directory, but feel free to update to reflect how you've organized your source code.

    version: '3.7'
    services:
        postgres:
            image: postgres:latest
            environment:
                - POSTGRES_USER=test
                - POSTGRES_PASSWORD=tes
                - POSTGRES_DB=test
            ports:
                - 5432:5432
            logging:
                options:
                    max-size: 10m
                    max-file: "3"
        pgadmin:
            image: dpage/pgadmin4
            environment:
                - PGADMIN_DEFAULT_EMAIL=test@gmail.com
                - PGADMIN_DEFAULT_PASSWORD=pasword123test
            ports:
                - "5050:80"
        web:
            build: .
            command: ["npm", "run", "start:dev"]
            links:
              - postgres
            image: prueba
            depends_on: 
              - postgres
            ports: 
              - '2000:2000'
            env_file:
              - .env
            volumes:
              # <host-path>:<container-path>
              - ./src:/src/
    

    If that isn't clear, here's an article that might help:

    https://www.freecodecamp.org/news/how-to-enable-live-reload-on-docker-based-applications/