stages & assemblers: don't allow additional props

Change all the schemata to not allow additional properties. This
should help with misspelled properties as well as missing schema
information in the stage itself.

Done via a small python3 script:

   --- 8< --- 8< --- 8< --- 8< --- 8< --- 8< --- 8< --- 8< ---

import os
import sys

def list_stages(base):
    return [(base, f) for f in os.listdir(base) if f.startswith("org.osbuild")]

stages = list_stages("stages")
stages += list_stages("assemblers")

def find_line(lines, start):
    for i, l in enumerate(lines):
        if l.startswith(start):
            return i
    return None

NOADD = '"additionalProperties": false'

for stage in stages:
    with open(f"{stage[0]}/{stage[1]}", "r") as f:
        print(f"{stage[0]}/{stage[1]}", file=sys.stderr)
        data = f.readlines()
        i = find_line(data, 'STAGE_OPTS = """')
        if i:
            data.insert(i+1, NOADD + ",\n")
        else:
            i = find_line(data, 'STAGE_OPTS = ""')
            if i:
                data[i] = f'STAGE_OPTS = """\n'
                data.insert(i+1, NOADD + "\n")
                data.insert(i+2, '"""\n')

    with open(f"{stage[0]}/{stage[1]}", "w") as f:
        f.writelines(data)
This commit is contained in:
Christian Kellner 2020-04-25 14:17:57 +02:00
parent 554d8dc868
commit 01ce01b1c7
28 changed files with 32 additions and 2 deletions

View file

@ -8,7 +8,9 @@ STAGE_INFO = """
No-op assembler. Produces no output, just prints a JSON dump of its options
and then exits.
"""
STAGE_OPTS = ""
STAGE_OPTS = """
"additionalProperties": false
"""
def main(_tree, _output_dir, options):
print("Not doing anything with these options:", json.dumps(options))

View file

@ -22,6 +22,7 @@ the commit id and the compose information respectively.
[1] https://ostree.readthedocs.io/en/stable/manual/adapting-existing/
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["ref"],
"properties": {
"ref": {

View file

@ -30,6 +30,7 @@ Buildhost commands used: `truncate`, `mount`, `umount`, `sfdisk`,
`grub2-mkimage`, `mkfs.ext4` or `mkfs.xfs`, `qemu-img`.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["format", "filename", "ptuuid", "size"],
"oneOf": [{
"required": ["root_fs_uuid"]

View file

@ -26,6 +26,7 @@ generate with uuid.uuid4() in Python, `uuidgen(1)` in a shell script, or
read from `/proc/sys/kernel/random/uuid` if your kernel provides it.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["filename", "root_fs_uuid", "size"],
"properties": {
"filename": {

View file

@ -22,6 +22,7 @@ caller is responsible for making sure that `compression` and `filename` match.
Buildhost commands used: `tar` and any named `compression` program.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["filename"],
"properties": {
"filename": {

View file

@ -11,6 +11,7 @@ Modifies /etc/chrony.conf, removing all "server" or "pool" lines and adding
a "server" line for each server listed in `timeservers`.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["timeservers"],
"properties": {
"timeservers": {

View file

@ -12,6 +12,7 @@ which starts an early-boot root shell on the given `tty`.
Also symlinks the service file into /etc/systemd/system/sysinit.target.wants/.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["tty"],
"properties": {
"tty": {

View file

@ -9,6 +9,7 @@ Error stage. Return the given error. Useful for testing, debugging, and
wasting time.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"returncode": {
"description": "What to return code to use",

View file

@ -29,6 +29,7 @@ target tree, which means it may fail unexpectedly when the buildhost and target
are different arches or OSes.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"ports": {
"description": "Ports (or port ranges) to open",

View file

@ -19,6 +19,7 @@ If the flag-file cannot be removed, the service fails without executing
any further first-boot commands.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["commands"],
"properties": {
"commands": {

View file

@ -22,6 +22,7 @@ By default it is `/boot`, i.e. assumes `/boot` is on the root file-system.
This stage reads and (re)writes all .conf files in /boot/loader/entries.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"prefix": {
"description": "Prefix to use, normally `/boot`",

View file

@ -13,6 +13,7 @@ a `path` (mount point).
This stage replaces /etc/fstab, removing any existing entries.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["filesystems"],
"properties": {
"filesystems": {

View file

@ -13,6 +13,7 @@ If no `gid` is given, `groupadd` will choose one.
If the specified group name or GID is already in use, this stage will fail.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"groups": {
"type": "object",

View file

@ -42,6 +42,7 @@ and accompanying data can be installed from the built root via `uefi.install`.
Both UEFI and Legacy can be specified at the same time.
"""
STAGE_OPTS = """
"additionalProperties": false,
"oneOf": [{
"required": ["root_fs_uuid"]
}, {

View file

@ -14,6 +14,7 @@ buildhost with `--hostname={hostname}`, which checks the validity of the
hostname and writes it to /etc/hostname.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["hostname"],
"properties": {
"hostname": {

View file

@ -11,6 +11,7 @@ command line.
https://www.kernel.org/doc/html/latest/admin-guide/kernel-parameters.html
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"root_fs_uuid": {
"description": "UUID of the root filesystem image",

View file

@ -15,6 +15,7 @@ Removes any existing /etc/vconsole.conf, then runs `systemd-firstboot` with the
Valid keymaps are generally found in /lib/kbd/keymaps.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["keymap"],
"properties": {
"keymap": {

View file

@ -15,6 +15,7 @@ with the `--locale` flag, which will write a new `/etc/locale.conf` in the
target system with `LANG={language}`.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["language"],
"properties": {
"language": {

View file

@ -8,7 +8,9 @@ STAGE_INFO = """
No-op stage. Prints a JSON dump of the options passed into this stage and
leaves the tree untouched. Useful for testing, debugging, and wasting time.
"""
STAGE_OPTS = ""
STAGE_OPTS = """
"additionalProperties": false
"""
def main(_tree, options):
print("Not doing anything with these options:", json.dumps(options))

View file

@ -34,6 +34,7 @@ Uses the following binaries from the host:
* `rpm` to install packages into the target tree
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"gpgkeys": {
"description": "Array of GPG key contents to import",

View file

@ -38,6 +38,7 @@ human users need to be part of.
[2] https://rpm-ostree.readthedocs.io/en/latest/manual/treefile/
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"etc_group_members": {
"description": "Array of group names to still keep in /etc/group",

View file

@ -25,6 +25,7 @@ through `/bin/sh` in that case, so it might still work, but that behavior is
not guaranteed.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["script"],
"properties": {
"script": {

View file

@ -24,6 +24,7 @@ labels for newly-created files are determined by the host's SELinux policy and
may not match the tree's policy.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["file_contexts"],
"properties": {
"file_contexts": {

View file

@ -16,6 +16,7 @@ items, which will delete _all_ symlinks to the named services.
Uses `systemctl` from the buildhost.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["enabled_services"],
"properties": {
"enabled_services": {

View file

@ -13,6 +13,7 @@ Creates `/etc/systemd/system/osbuild-test.service`, and a symlink to it in
`/etc/systemd/system/multi-user.target.wants/`.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["script"],
"properties": {
"script": {

View file

@ -14,6 +14,7 @@ Removes `/etc/localtime`, then runs the host's `systemd-firstboot` binary with
the `--timezone` option, which will re-create `/etc/localtime`.
"""
STAGE_OPTS = """
"additionalProperties": false,
"required": ["zone"],
"properties": {
"zone": {

View file

@ -15,6 +15,7 @@ misbehave if the `usermod`/`useradd` binary inside the tree makes incorrect
assumptions about its host system.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"users": {
"type": "object",

View file

@ -10,6 +10,7 @@ Configures `zipl` with a minimal config so it can be used in
the assembler to write the bootmap and bootloader code.
"""
STAGE_OPTS = """
"additionalProperties": false,
"properties": {
"timeout": {
"description": "Boot loader timeout value",