Cloud-init user-data not running

I’m trying to follow the instructions here to do some initial configuration of new containers, but I can’t seem to get it to work. Using the image ubuntu:20.04, I’ve created the following profile:

$ lxc profile  show psanford-default 
config:
  user.user-data: |
    runcmd:
      - [touch, /root/hello]
description: psanford cloud-init
devices: {}
name: psanford-default
used_by: []

My default profile (which I don’t believe I’ve changed) looks like this:

config: {}
description: Default LXD profile
devices:
  eth0:
    name: eth0
    nictype: bridged
    parent: lxdbr0
    type: nic
  root:
    path: /
    pool: lxdpool
    type: disk
name: default

I’m launching the container using the following command:

$ lxc launch ubuntu:20.04 user-data-0 --profile=default --profile=psanford-default
Creating user-data-0
Starting user-data-0

Exec’ing into the container, I can see the config gets placed at /var/lib/cloud/seed/nocloud-net/user-data:

root@user-data-0:~# cat /var/lib/cloud/seed/nocloud-net/user-data
runcmd:
  - [touch, /root/hello]

I can also see from the cloud-init.log file that this config gets read, but I don’t see any logs of cloud-init actually attempting to parse and load this config:

2021-08-20 19:10:37,179 - util.py[DEBUG]: Read 33 bytes from /var/lib/cloud/seed/nocloud-net/user-data
2021-08-20 19:10:37,179 - util.py[DEBUG]: Reading from /var/lib/cloud/seed/nocloud-net/meta-data (quiet=False)
2021-08-20 19:10:37,179 - util.py[DEBUG]: Read 54 bytes from /var/lib/cloud/seed/nocloud-net/meta-data
2021-08-20 19:10:37,179 - util.py[DEBUG]: Reading from /var/lib/cloud/seed/nocloud-net/vendor-data (quiet=False)
2021-08-20 19:10:37,179 - util.py[DEBUG]: Read 18 bytes from /var/lib/cloud/seed/nocloud-net/vendor-data
2021-08-20 19:10:37,179 - util.py[DEBUG]: Reading from /var/lib/cloud/seed/nocloud-net/network-config (quiet=False)
2021-08-20 19:10:37,179 - util.py[DEBUG]: Read 121 bytes from /var/lib/cloud/seed/nocloud-net/network-config
2021-08-20 19:10:37,179 - DataSourceNoCloud.py[DEBUG]: Using seeded data from /var/lib/cloud/seed/nocloud-net
2021-08-20 19:10:37,179 - util.py[DEBUG]: Attempting to load yaml from string of length 54 with allowed root types (<class 'dict'>,)
2021-08-20 19:10:37,180 - util.py[DEBUG]: Attempting to load yaml from string of length 121 with allowed root types (<class 'dict'>,)
2021-08-20 19:10:37,197 - util.py[DEBUG]: Reading from /etc/os-release (quiet=False)
2021-08-20 19:10:37,197 - util.py[DEBUG]: Read 382 bytes from /etc/os-release

Note in the above logs, we see cloud-init reading this file, but we don’t have a corresponding Attempting to load yaml from string of length 33 like we do for the meta-data and network-config.

What am I doing wrong that is keeping cloud-init from using my user-data config?

Edit: I’ve uploaded the full contents of cloud-init.log and cloud-init-output.log to here: user-data-0 cloud-init logs · GitHub

And as soon as I post this I noticed the following warning in cloud-init-output.log:

2021-08-20 19:10:39,277 - __init__.py[WARNING]: Unhandled non-multipart (text/x-not-multipart) userdata: 'b'runcmd:'...'

Which led me to this: Can't pass user data to cloudinit - #2 by stgraber

Adding #cloud-config to the first line of my user.user-data indeed fixed the issue.

1 Like