Saving bash output in Dockerfile as ENV var - bash

I am setting up a random password to be used on the initial login within my Dockerfile. I have tried
ENV PASSWORD=RUN date +%s | sha256sum | base64 | head -c 32
Which does not work because Docker commands are in separate containers. I also tried
RUN export PASSWORD= date +%s | sha256sum | base64 | head -c 32
Which has also failed.
I have also tried to redirect my output to a file, which also fails, the file stays empty and no error is given.
RUN date +%s | sha256sum | base64 | head -c 32 > test.txt
How can I save the output from this command as an ENV var to be used in my Docker container?

The following Dockerfile:
FROM alpine:latest
RUN echo "bd" > /test.txt
when run has the test.txt file present:
docker build . -t test:latest
docker run -it --rm test:latest
> cat /test.txt
> 'bd'
You could change your command to write a file in a sourceable manner (RUN echo "my_env_var=$(echo 'stuff')" > /test.txt) and then have your entrypoint include . /test.txt

Related

Automating password change inside a Docker container

I need to use a bash script:
Launch the container
Generate a password
Enter the container
Run the 'cd /' command
Change the password using htpasswd to the generated one
I tried it like this:
docker restart c1
a = date +%s | sha256sum | base64 | head -c 32 ; echo
docker exec -u 0 -it c1 bash 'echo cd /'
htpasswd user.passwd webdav a
And so:
docker restart c1
docker exec -u 0 -it c1 bash
cd /
a = date +%s | sha256sum | base64 | head -c 32 ; echo
htpasswd user.passwd webdav a
With the first option , I get:
bash: echo cd /: No such file or directory
With the second one, it enters the container and does nothing
I will be grateful for any help
I tried many variations of the script, which did not help me
You do not need Docker or debugging tools like docker exec just to generate an htpasswd file.
htpasswd is part of the Apache distribution, and you should be able to install it on your host system using your OS package manager. Since it just manipulates a credential file it doesn't need the actual server.
# On the host system, without using Docker at all
sudo apt-get update && apt-get install apache2-utils
# Make sure to wrap the password-generating command in `$()`
a=$(date +%s | sha256sum | base64 | head -c 32)
# Make sure to use a variable reference `$a`
htpasswd user.passwd webdav "$a"
This gives you a user.passwd file on your local system. Now when you launch your container, you can bind-mount the file into the container:
docker run -d -p 80:80 ... \
-v "$PWD/user.passwd:/usr/local/apache2/conf/user.passwd" \
httpd
The container will be immediately ready to use. If you delete and recreate this container, you do not need to repeat the manual setup step. If you need to launch multiple copies of the container, they can all have the same credentials file without doing manual steps.

Shell script works from command line but not from cron

I am using https://stackoverflow.com/a/42955871/308851 and it works from command line but not from cron. I even tried running the script with env -i but it stubbornly works.
#!/bin/bash
filename=$(date '+%Y-%m-%d').gz
docker exec -t elastic_db.1.$(docker service ps -f 'name=elastic_db.1' elastic_db -q --no-trunc | head -n1) mysqldump example |gzip -9 > /container/$filename
docker exec -t elastic_drupal.1.$(docker service ps -f 'name=elastic_drupal.1' elastic_drupal -q --no-trunc |head -n1) rclone --config /etc/rclone.conf move /app/$filename example:example/dump/
This compresses a 0 byte file when ran from cron but works just fine otherwise. What am I doing wrong?
Gordon Davisson's comment is correct: changing docker to /usr/bin/docker worked.

Grep on docker image names in package.json

I want to set a script in the package.json that starts the container based on image-name that I grep after piping the docker images command, something like this:
"docker:run": "docker run -it -v /$(pwd):/app $(docker images | grep 'online-check-in-frontend' | awk '{ print $1 }') sh",
also tried :
"docker:run": "docker run -it -v /$(pwd):/app $(docker images | grep \"online-check-in-frontend\" | awk \"{ print $1 }\") sh",
The commands above is not working, i get the following error:
Im using windows, and bash. :S
Br

Shell : How to get a container's name containing some string

I have a list of containers where names are like following :
container 1: myApp_ihm.dfgdfgdfgdfvdfdfbvdfvdfv
container 2: myApp_back.uirthjhiliszfhjuioomlui
...
container 3: myApp_database.piyrjfhjyukyujfkgft
I have to execute some string on the container where the name contains ihm (the first one in my example)
In order to exec my commands , I'm used to do:
docker exec -it ihm bash
so ihm should by replaced by some test to get the first one name :
myApp_ihm.dfgdfgdfgdfvdfdfbvdfvdfv
Suggestions?
docker exec -it $(docker ps | grep myApp_ihm | awk '{print $1}') /bin/bash
docker exec -it $(docker ps --format "{{.Names}}" | grep "ihm") bash
This worked for me, added that to a bash script and saved myself 30-60 seconds of typing/copy-pasting every time I want to go into my container.
docker exec -it $(docker ps --format "{{.ID}} {{.Command}}" | grep /home/app/ | awk '{print $1}') /bin/bash

`docker run` output to bash variable - strange behaviour

I'm seeing some strange behaviour getting the output from docker run into a bash variable.
Simple example:
#!/bin/bash
PWD=$(docker run --rm -ti ubuntu pwd 2>&1)
# also tried with PWD=`docker run ...` with same behaviour
echo $PWD
echo abc $PWD
echo abc $PWD xyz
output
/
abc /
xyz/
The problem is on the last echo...
you need to modify the docker run --rm -ti ubuntu pwd 2>&1 with docker run --rm ubuntu pwd 2>&1
probabilly the interactive and tty mode doesn't work fine in a shell variables
Dockers -t option allocates a pseudo terminal for the process to output to. A TTY uses a CRLF for a line ending unlike the usual LF in unix.
The " xyz" in your example output is overwriting the rest of the text from the start of the line due to the carriage return stored in the variable.
The od utility can dump the hex or octal values.
$ docker run -t busybox pwd | od -b
0000000 057 015 012
0000003
057 = / 015 = CR 012 = LF
Then the normal output.
$ docker run busybox pwd | od -b
0000000 057 012
0000002
Remove the -t and possibly check for errors rather than redirecting stderr to stdout. -i is not required unless the process requires stdin.
PWD=$(docker run --rm ubuntu pwd)
[ "$?" == "0" ] || exit 1
echo "[$PWD]"
The characters \r\n are present in the output:
$ docker run --rm -ti ubuntu pwd 2>&1 > /tmp/docker.out
$ cat -A /tmp/docker.out
/^M$
$ python -c "import sys; print repr(sys.stdin.read())" < /tmp/docker.out
'/\r\n'
Also, don't rely on the output for docker run, because if the ubuntu image is not already present, it will also be pulled and the messages of "Pulling image" will be part of the output.

Resources