Search code examples
bashdockergulp

How to run node.js with gulp inside docker and find the right bashsrc


I am new to Docker and I do have some problems.

My goal:

  • use the Dockerfile to create a docker-container and stay inside the container / don't drop out of it.
  • running a local Docker-Container
  • installing "gulp" with the package.json
  • installing "gulp global" on Docker
  • copy any files to my Docker container
  • execute "gulp --version" and the default "gulp task" and stay inside the terminal.

Here is my setup:

Dockerfile

FROM node:10
WORKDIR /usr/src/app
COPY package*.json ./
RUN npm install --global gulp-cli
RUN npm install
COPY . .
EXPOSE 3000
CMD ["gulp --version" , "gulp"]  or? [gulp --version , gulp]

package.json

{
  "name": "docker-test",
  "version": "1.0.0",
  "description": "Testing Docker",
  "main": "index.js",
  "scripts": {
    "test": "test"
  },
  "author": "",
  "license": "",
  "devDependencies": {
    "gulp": "^4.0.0"
  }
}

gulpfile.js

function defaultTask(cb) {
 console.log("Default task for gulp 4.0 for docker")
  cb();
} 
exports.default = defaultTask 

docker-compose.yml (I don't think we need this for my question but I will post it anyway since I am not exactly sure If this could make some problems)

version: '3'
services:
  html:
    container_name: gulp-docker-test
    restart: always
    build: .
    ports:
      - '80:3000'

My problems right now:

First of all I am really confused about the workflow of docker. Do I understand it correctly if I run:

docker build . --tag gulp-docker-test 

I will create a new docker-container on my computer with the content of the dockerfile? If I need to update anything inside it I have to run it again so the container is updated?

If I use:

docker start gulp-docker-test

it will start the container? What if I change anything inside it? Will it be back on reboot of the container? Or is it gone because it is only a temporary image?

Beside that if I try to run it I get this error:

ERROR: for gulp-docker-test  Cannot start service html: OCI runtime create failed: container_linux.go:344: starting container process caused "exec: \"gulp --version\": executable file not found in $PATH": unknown

ERROR: for html  Cannot start service html: OCI runtime create failed: container_linux.go:344: starting container process caused "exec: \"gulp --version\": executable file not found in $PATH": unknown

I did try those things: execute it with exec, removing the quotes inside the CMD of the Dockerfile but I think I do have some basic knowledge missing. I don't understand how to boot this container inside the shell so docker knows the $path.

Thank you for your help in advance

Edit:

I did found out how to run docker with the shell.

docker run -it --entrypoint bash  gulp-docker-test3
root@8a27dc3a9c85:/usr/src/app# gulp -v
[15:01:53] CLI version 2.0.1
[15:01:53] Local version 4.0.0
root@8a27dc3a9c85:/usr/src/app# gulp 
[15:02:38] Using gulpfile /usr/src/app/gulpfile.js
[15:02:38] Starting 'default'...
Default Task von Gulp 4.0 für Docker
[15:02:38] Finished 'default' after 4.28 ms
root@8a27dc3a9c85:/usr/src/app# 

It looks like it should work if I can add default bash to the dockerfile.


Solution

  • If I run docker build I will create a new container?

    It will execute the contents of the Dockerfile, and create a new image.

    You need to docker run (or, rarely, docker create) the image to create a container from it. When you update the Dockerfile or your application source, you need to repeat the docker build step, docker stop && docker rm the existing container, and docker run a new one. Your docker-compose.yml fragment encapsulates this, but note that Docker Compose will delete and recreate a container when it's appropriate.

    If I use docker start gulp-docker-test...

    It will start a container with that name. That's a separate namespace from the image namespace. The container has to already exist and be stopped (usually from an explicit docker stop command). This is a slightly unusual state to be in.

    CMD ["gulp --version" , "gulp"]

    This looks for a binary named gulp --version, and runs it with a single parameter gulp. Since you probably don't have a single file named /usr/local/bin/gulp --version (with the spaces and "version" as part of the filename) you get an error.

    You only get one CMD in a Dockerfile. (Or one ENTRYPOINT instead, but I tend to find CMD preferable except in a couple of extremely specific cases.) Each "word" you'd type in a shell becomes a separate "word" in the syntax. So you could, for instance, write

    CMD ["gulp", "--version"]
    

    Alternatively, if you leave off the brackets, Docker will wrap the CMD text in sh -c ..., so something closer to what you actually wrote is

    CMD gulp --version && gulp
    

    In practice you'd usually run build tools like Gulp as part of building the image, and use the CMD to actually start your application.

    RUN gulp
    CMD ["npm", "start"]