- name: Detect system architecture shell: "echo $(uname -m)/$(uname -p)" register: _arch_result changed_when: false - name: Set arch fact set_fact: arch: "{{ _arch_result.stdout }}" - name: Detect FreeBSD version shell: "uname -r" register: _freebsd_version_result changed_when: false - name: Set FreeBSD version fact set_fact: poudriere_freebsd_version: "{{ _freebsd_version_result.stdout | regex_replace('-p[0-9]+$', '') }}" - name: Disable resolvconf copy: content: "resolvconf=NO\n" dest: /etc/resolvconf.conf owner: root group: wheel mode: "0644" - name: Set up resolv.conf template: src: etc_resolv.conf.j2 dest: /etc/resolv.conf owner: root group: wheel mode: "0644" - name: Install packages package: name: "{{ pkg_name }}" state: present loop: - rsync - dma - jq - curl - bash - git - python312 - python - fastfetch - vim - age - netdata - fd-find - poudriere loop_control: loop_var: pkg_name - name: Set up sshd template: src: etc_ssh_sshd_config.j2 dest: /etc/ssh/sshd_config owner: root group: wheel mode: "0644" notify: Restart sshd - name: Start sshd service: name: sshd state: started - name: Start syslogd service: name: syslogd state: started - name: Start auditd service: name: auditd state: started - name: Set up periodic.conf template: src: etc_periodic.conf.j2 dest: /etc/periodic.conf owner: root group: wheel mode: "0644" - name: Install .bashrc copy: src: root_bashrc dest: /root/.bashrc owner: root group: wheel mode: "0644" # Jail infrastructure # Ports tree management - name: Deploy update-ports script template: src: usr_local_bin_update_ports.sh.j2 dest: /usr/local/bin/update-ports owner: root group: wheel mode: "0755" - name: Deploy jail_net script template: src: "{{ role_path }}/../jail/templates/usr_local_bin_jail_net.j2" dest: /usr/local/bin/jail_net owner: root group: wheel mode: "0755" - name: Check if quarterly ports tree exists stat: path: /usr/ports/quarterly/Mk register: _quarterly_exists - name: Download quarterly ports tree shell: /usr/local/bin/update-ports quarterly when: not _quarterly_exists.stat.exists - name: Check if custom ports overlay exists shell: "ls /usr/ports/custom/ 2>/dev/null | head -1" register: _custom_exists changed_when: false - name: Download custom ports overlay shell: /usr/local/bin/update-ports custom when: _custom_exists.stdout == "" - name: Discover jail directories find: paths: "{{ playbook_dir }}/roles/jails" patterns: "main.yml" recurse: true delegate_to: localhost register: _jail_specs - name: Load jail definitions set_fact: jail_defs: "{{ jail_defs | default([]) + [_content | combine({'num': _num, 'name': _name})] }}" vars: _content: "{{ lookup('file', item.path) | from_yaml }}" _num: "{{ item.path | regex_replace('.*/jails/([^/]+)/.*', '\\1') | split('_') | first | int }}" _name: "{{ item.path | regex_replace('.*/jails/([^/]+)/.*', '\\1') | regex_replace('^[0-9]+_', '') }}" loop: "{{ _jail_specs.files | sort(attribute='path') }}" loop_control: label: "{{ item.path | regex_replace('.*/jails/([^/]+)/.*', '\\1') }}" when: "'/defaults/' in item.path" - name: Collect unique userlands set_fact: jail_userlands: "{{ jail_defs | map(attribute='userland') | unique | list }}" - name: Create base ZFS datasets community.general.zfs: name: "{{ item.name }}" state: present extra_zfs_properties: mountpoint: "{{ item.mountpoint | default(omit) }}" loop: - { name: "zroot/jails", mountpoint: "/usr/local/jails" } - { name: "zroot/jails/media" } - { name: "zroot/jails/templates" } - { name: "zroot/jails/containers" } - { name: "zroot/jails/volumes", mountpoint: "/usr/local/jails/volumes" } - { name: "zroot/storage", mountpoint: "/usr/local/jails/volumes/storage" } - { name: "zroot/netdata_db", mountpoint: "/var/db/netdata" } - { name: "zroot/ports", mountpoint: "/usr/ports" } loop_control: label: "{{ item.name }}" - name: Create storage group group: name: storage gid: 1001 - name: Create storage user user: name: storage uid: 1001 group: storage home: /nonexistent shell: /usr/sbin/nologin create_home: false - name: Set storage volume permissions file: path: /usr/local/jails/volumes/storage state: directory owner: storage group: storage mode: "0777" - name: Create storage directories file: path: "/usr/local/jails/volumes/storage/{{ item.name }}" state: directory owner: "1001" group: "1001" mode: "{{ item.mode }}" loop: - { name: media, mode: "0777" } - { name: docs, mode: "0775" } - { name: downloads, mode: "0777" } - { name: projects-ableton, mode: "0755" } - { name: vault, mode: "0755" } - { name: jan-systems-2025-content, mode: "0755" } - name: Set up userland templates include_tasks: userland.yml loop: "{{ jail_userlands }}" loop_control: loop_var: userland - name: Deploy /etc/jail.conf template: src: jail.conf.j2 dest: /etc/jail.conf owner: root group: wheel mode: "0644" - name: Deploy devfs.rules template: src: devfs.rules.j2 dest: /etc/devfs.rules owner: root group: wheel mode: "0644" - name: Set up crontab template: src: etc_crontab.j2 dest: /etc/crontab owner: root group: wheel mode: "0644" notify: Restart cron - name: Set up poudriere include_tasks: poudriere.yml # Repo validation gate - name: Check if poudriere repo has packages stat: path: "/usr/local/poudriere/data/packages/poudriere_build-quarterly/meta" register: _poudriere_repo - name: "*** POUDRIERE REPO NOT READY ***" fail: msg: | ════════════════════════════════════════════════════════════════ POUDRIERE REPOSITORY NOT READY ════════════════════════════════════════════════════════════════ The local package repository has not been built yet. Run the following command on the host to build packages: poudriere-start-build Then re-run this playbook. ════════════════════════════════════════════════════════════════ when: not _poudriere_repo.stat.exists - name: Install custom packages from poudriere shell: "pkg install -y -r poudriere pylogsentinel" register: _custom_pkg changed_when: "'Number of packages to be installed' in _custom_pkg.stdout" - name: Deploy pylogsentinel.conf template: src: usr_local_etc_pylogsentinel.conf.j2 dest: /usr/local/etc/pylogsentinel.conf owner: root group: wheel mode: "0644" - name: Deploy pylogsentinel-batch-email.sh template: src: usr_local_bin_pylogsentinel-batch-email.sh.j2 dest: /usr/local/bin/pylogsentinel-batch-email.sh owner: root group: wheel mode: "0755"