Set {{ pillar['network']['wireless'] }} to not be managed by NetworkManager: cmd.run: - name: nmcli device set {{ pillar['network']['wireless'] }} managed no - unless: bash -c "if [[ \"$(nmcli device show {{ pillar['network']['wireless'] }} | sed -n 's/^GENERAL.STATE.*(\(.*\)).*$/\1/p')\" == \"unmanaged\" ]]; then exit 0; else exit 1; fi" Configure keyfile block in NetworkManager.conf: file.append: - name: /etc/NetworkManager/NetworkManager.conf - text: | [keyfile] unmanaged-devices=interface-name:{{ pillar['network']['wireless'] }} Delete {{ pillar['network']['interface'] }} connection: cmd.run: - name: nmcli connection delete {{ pillar['network']['interface'] }} - onlyif: nmcli connection show {{ pillar['network']['interface'] }} > /dev/null Install hostapd: pkg.installed: - name: hostapd Configure hostapd: file.managed: - name: /etc/hostapd.conf - source: salt://hostapd/files/hostapd.conf.jinja - template: jinja - user: root - group: root - mode: "0600" Create hostapd service unit file: file.managed: - name: /etc/systemd/system/hostapd.service - source: salt://hostapd/files/hostapd.service.jinja - template: jinja - user: root - group: root - mode: "0644" Reload systemd daemon: cmd.run: - name: systemctl daemon-reload - onchanges: - file: Create hostapd service unit file Start hostapd: service.running: - name: hostapd - enable: True - watch: - file: Configure hostapd Set {{ pillar['network']['bridge'] }} to be managed by NetworkManager: cmd.run: - name: nmcli device set {{ pillar['network']['bridge'] }} managed yes - unless: bash -c "if [[ \"$(nmcli device show {{ pillar['network']['bridge'] }} | sed -n 's/^GENERAL.STATE.*(\(.*\)).*$/\1/p')\" == \"unmanaged\" ]]; then exit 1; else exit 0; fi" Configure {{ pillar['network']['bridge'] }} connection: cmd.run: - name: nmcli connection add con-name {{ pillar['network']['bridge'] }} type bridge ifname {{ pillar['network']['bridge'] }} ipv4.method manual ipv4.addresses {{ pillar['network']['ip'] }}/24 ipv4.dns "127.0.0.1, 1.1.1.1, 1.1.1.2" ipv6.method disabled connection.autoconnect yes stp no - unless: nmcli connection show {{ pillar['network']['bridge'] }} > /dev/null Add {{ pillar['network']['interface'] }} to bridge {{ pillar['network']['bridge'] }}: cmd.run: - name: nmcli connection add con-name {{ pillar['network']['bridge'] }}-{{ pillar['network']['interface'] }} ifname {{ pillar['network']['interface'] }} type bridge-slave master {{ pillar['network']['bridge'] }} connection.autoconnect yes - unless: nmcli connection show {{ pillar['network']['bridge'] }}-{{ pillar['network']['interface'] }} > /dev/null