AWS EC2 cloud-init instance setup

Are you still manually checking your cloud-init scripts'  status for success or failure?

If you want to be notified when everything goes the right way, you can use a simple curl command at the end of your setup script:

curl -X POST \
  "${RAW_API_KEY}" \
  -F title="Instance setup: finished" \
  -F content="Instance ${HOSTNAME} has been set up correctly!"

If you want a more precise approach, you can use the following cloud-init example.

It runs:

  • A basic setup script (/root/ that fails.
  • A background script that:
    • Waits for cloud-init to finish its initialization.
    • Checks if there have been any errors.
    • Notifies the user on success or on error (if error, reports the last messages of /var/log/cloud-init-output.log).
  - curl
  # Invokes Notify17 cloud init reporter in background
  - "nohup /root/ &"
  # Actual cloud init startup script
  - "bash /root/"
  # Our sample bash script that fails
  - owner: root:root
    permissions: '0644'
    path: /root/
    content: |
      echo "Hello!"
      exit 1      

  # Cloud init report
  - owner: root:root
    permissions: '0755'
    path: /root/
    content: |
      set -Eeumo pipefail

      # Fetch the EC2 instance private IP
      # Set your Raw API key here

      curl -X POST "$N17_URL" \
        --data-urlencode "title=EC2 cloud-init started: $HOSTNAME ($PRIVATE_IP)" \
        || echo "Failed to report cloud-init started"

      # Block until cloud-init completes
      while [ ! -f /var/lib/cloud/instance/boot-finished ]; do sleep 1; done

      # Check the cloud-init result.json for errors
      if egrep '"errors": \[$' /var/lib/cloud/data/result.json; then
        # Fetch the last 30 rows of cloud-init logs
        LOGS=$(tail -n30 /var/log/cloud-init-output.log)
        CONTENT="Error occurred while initializing instance: $HOSTNAME ($PRIVATE_IP)"
        curl -X POST "$N17_URL" \
          --data-urlencode "title=EC2 cloud-init error: $HOSTNAME ($PRIVATE_IP)" \
          --data-urlencode "content=$CONTENT" \
          || echo "Failed to report cloud-init error"
        exit 0

      CONTENT="Instance initialized successfully: $HOSTNAME ($PRIVATE_IP)"
      curl -X POST "$N17_URL" \
        --data-urlencode "title=EC2 cloud-init success: $HOSTNAME ($PRIVATE_IP)" \
        --data-urlencode "content=$CONTENT" \
        || echo "Failed to report cloud-init success"