Hi!
Sorry for the delay.
The gist of the issue is that when you lxc start
a container, the command returns quickly, but the container may not have actually finished booting. The reason is that LXD gives the instruction to the container to boot and the container is now on its own. It might get ready straight away, or it may take a few moments.
How can you be sure when to start running lxc exec
on a container that you have just lxc start
-ed?
You could put some delay for a few seconds, with lxc exec test -- sleep 5
.
But the elegant way is to make use of cloud-init
. The ubuntu:
repository containers, and also the /cloud
containers from the images:
repository support cloud-init
. cloud-init
is a service that runs at the very end of the startup process. If you run the following, it will wait (will print dots while waiting) until cloud-init
finishes.
lxc exec test -- cloud-init status --wait
Then, if you lxc exec test -- passwd -d ubuntu
will work as expected.
But do you need to wait for the container to boot up before you can run commands?
The answer is no. If the command is lxc exec test -- touch /i_was_here
, then it runs successfully even as soon as you run lxc start test
.
Let’s avoid using passwd -d
to reset the password of an account, but rather run the following. This is a shell command, does not invoke the passwd
command, and directly edits the /etc/shadow
file to remove the password lock.
lxc exec mytest -- sed -i '/^ubuntu\:/{s/\!//g}' /etc/shadow
We run it and let’s see how does the /etc/shadow
line for ubuntu
looks like. That’s weird. Now there are two characters. We are supposed to have removed !
and now we see that character and then an asterisk!
ubuntu:!*:18713:0:99999:7:::
When you copy a LXD container, the copied container apparently runs cloud-init
as soon as it is started for the first time. And per /var/log/cloud-init.log
, the ubuntu:
container images create a non-root account and then lock it. Here is the relevant fragment of /var/log/cloud-init.log
,
2021-03-27 20:14:11,966 - __init__.py[DEBUG]: Adding user ubuntu
2021-03-27 20:14:11,966 - subp.py[DEBUG]: Running hidden command to protect sensitive input/output logstring: ['useradd', 'ubuntu', '--comment', 'Ubuntu', '--groups', 'adm,audio,cdrom,dialout,dip,floppy,lxd,netdev,plugdev,sudo,video', '--shell', '/bin/bash', '-m']
2021-03-27 20:14:12,001 - subp.py[DEBUG]: Running command ['passwd', '-l', 'ubuntu'] with allowed return codes [0] (shell=False, capture=True)
I’ll stop here. The importance of this whole exercise is that the user account files should be considered not ready when a container is starting up. If you want to edit those file, you would need to wait until cloud-init
does its own work, and then you can proceed and make changes.