picostitch
crafting (and) JavaScript

docker-compose and Export $PATH

All my projects use docker-compose. In my setup I want every nodejs packages that provides an executable, such as mocha or tsc to be available globally on the command line.

So I can type

$ mocha
...

I don't want to have to type the long version:

$ ./node_module/.bin/mocha
...

How to Expose nodejs Executables?

I don't want to cd into the project directory and call the executable via ./node_module/.bin/mocha or ./node_module/.bin/tsc from there. I can set this up by extending my machine's path like this PATH=$PATH:./node_modules/.bin.

The according Dockerfile looks like this:

FROM node
ENV PATH=$PATH:./node_modules/.bin

Define Path Export in docker-compose

I was searching the docker-compose docs but I could not find how to add a path to the existing path inside a docker-compose setup. The typical docker-compose setup is stored in a docker-compose.yml file and for nodejs it might look like this (very simplified):

version: '3'
services:
  picostitch:
    image: nodejs
    ports:
      - "5000:5000"
    volumes:
      - '.:/app'    

see the complete file running this blog, here.

In a docker-compose you can configure (multiple) services. The one I need here is picostitch, which is just a simple nodejs container, it exposes the port 5000 and maps the local directory . into the container under /app.

Beside ports, volumes docker-compose also provides environment where one can define environment variables to be set inside the running container. But I did not find a way to export a path.

Use docker-compose's build Option

In this case I used the build option, which takes a directory where it looks for a Dockerfile, in which I set the path accordingly.

version: '3'
services:
  picostitch:
    build: .

In the end I do use exactly the Dockerfile as mentioned above, so docker-compose can use it to build my picostitch service.

FROM node:15
ENV PATH=$PATH:./node_modules/.bin

See the files in the repo;

Multiple Containers

When I have multiple containers that need a customized Dockerfile, I create a directory docker-files/<service-name> where I put the Dockerfile in each directory. docker-compose also needs that for building the image in that directory and use it as it's context.