Compare commits

..

3 commits

84 changed files with 1418 additions and 713 deletions

View file

@ -47,6 +47,7 @@
- hosts: music
roles:
- { role: "acme", tags: ["acme"] }
- { role: "go", tags: ["go"] }
- { role: "music", tags: ["music"] }
- hosts: pad
@ -57,7 +58,6 @@
- hosts: services
roles:
- { role: "deb_forgejo", tags: [ "deb_forgejo" ] }
- { role: "services", tags: ["services"] }
- hosts: wiki

View file

@ -37,7 +37,5 @@ debian_repourl: "http://deb.debian.org/debian/"
debian_securityurl: "http://security.debian.org/debian-security"
deb_forgejo_repos:
- host: git.bitlair.nl
owner: bitlair
- host: git.polyfloyd.net
owner: polyfloyd

View file

@ -6,18 +6,12 @@ nft: false
root_access:
- ak
- bob
- eightdot
- foobar
- polyfloyd
nginx_client_max_body_size: 512M
nginx_sites:
- server_name: "music.bitlair.nl"
snippets:
- "music-nginx.j2"
music_domain: music.bitlair.nl
acme_san_domains:
- [ music.bitlair.nl ]
music_bitpanel_host: bitpanel.bitlair.nl
music_bitpanel_port: 1337

7
ldapclient.yaml Normal file
View file

@ -0,0 +1,7 @@
---
- hosts: shell-jessie:shell-stretch:shell-sid:mediaserver:grafiekjes
become: no
user: root
roles:
- ldapclient

View file

@ -0,0 +1 @@
../../../certs/lets-encrypt-x1.pem

View file

@ -0,0 +1 @@
../../../certs/lets-encrypt-x3-cross-signed.pem

View file

@ -0,0 +1 @@
../../../certs/sub.class1.server.sha2.ca.pem

View file

@ -0,0 +1,7 @@
---
- name: reload nslcd
service: name=nslcd state=restarted enabled=true
tags:
- ldapclient
- nslcd

129
ldapclient/tasks/main.yaml Normal file
View file

@ -0,0 +1,129 @@
# LDAP Client role for Revspace LDAP
# Tested on: Debian Stable
---
- name: Install LDAP client software
apt:
state: present
pkg:
- libpam-ldapd
- python3-ldap3
when: ansible_os_family == 'Debian'
tags:
- ldapclient
- apt
- name: Enable pam_mkhomedir module
lineinfile:
dest: /etc/pam.d/common-account
line: "session required pam_mkhomedir.so skel=/etc/skel/ umask=0022"
regexp: "pam_mkhomedir.so"
insertafter: EOF
tags:
- ldapclient
- mkhomedir
- name: Create login.group.allowed file
lineinfile:
dest: /etc/login.group.allowed
line: "board"
regexp: "^board$"
owner: "root"
group: "root"
mode: "0755"
create: true
with_items:
- "{{ login_groups | default('board') }}"
tags:
- ldapclient
- logingroups
when:
- logingroups is defined
- name: Limit access to listed groups
lineinfile:
dest: /etc/pam.d/common-auth
line: 'auth required pam_listfile.so onerr=fail item=group sense=allow file=/etc/login.group.allowed'
insertbefore: EOF
owner: "root"
group: "root"
mode: "0644"
regexp: "pam_listfile.*login.group.allowed"
tags:
- ldapclient
- logingroups
when:
- logingroups is defined
notify:
- reload nslcd
- name: Copy CA certificate
copy:
src: "{{ ldap_cafile }}"
dest: "/etc/ldap/{{ ldap_cafile }}"
owner: "root"
group: "root"
mode: "0644"
- name: Template ldap.conf
template:
src: "{{ item }}.j2"
dest: "/etc/ldap/{{ item }}"
owner: "root"
group: "root"
mode: "0644"
with_items:
- ldap.conf
notify:
- reload nslcd
- name: Template nslcd.conf
template:
src: "{{ item }}.j2"
dest: "/etc/{{ item }}"
owner: "root"
group: "root"
mode: "0644"
with_items:
- nslcd.conf
notify:
- reload nslcd
- name: Update /etc/nsswitch.conf
lineinfile:
dest: /etc/nsswitch.conf
line: "{{ item }}: compat ldap systemd"
regexp: "^{{ item }}"
with_items:
- passwd
- group
- shadow
- name: Template nslcd.conf
template:
src: ssh-getkey-ldap.j2
dest: /usr/sbin/ssh-getkey-ldap
owner: "root"
group: "root"
mode: "0755"
with_items:
- ssh-getkey-ldap
tags:
- ssh-getkey-ldap
- name: Update /etc/nsswitch.conf
lineinfile:
dest: /etc/nsswitch.conf
line: 'sudoers: ldap'
regexp: '^sudoers'
insertbefore: EOF"
- name: Disable nscd service
service:
name: nscd
state: stopped
enabled: false
tags:
- ldapclient
- nscd

View file

@ -0,0 +1,28 @@
# {{ ansible_managed }}
#
# LDAP Defaults
#
# See ldap.conf(5) for details
# This file should be world readable but not world writable.
BASE {{ldap_base}}
URI {{ldap_uri}}
#SIZELIMIT 12
#TIMELIMIT 15
#DEREF never
# TLS certificates (needed for GnuTLS)
TLS_CACERT /etc/ldap/{{ldap_cafile}}
#TLS_CIPHER_SUITE {{ldap_cipher_suite}}
TLS_PROTOCOL_MIN 3.3
TLS_REQCERT demand
TLS_CRLCHECK none
# Sudo settings
SUDOERS_BASE ou=SUDOers,{{ldap_base}}
#SUDOERS_SEARCH_FILTER objectClass=sudoRole
SUDOERS_TIMED yes
#SUDOERS_DEBUG 1

View file

@ -0,0 +1,35 @@
# {{ ansible_managed }}
# /etc/nslcd.conf
# nslcd configuration file. See nslcd.conf(5)
# for details.
# The user and group nslcd should run as.
uid nslcd
gid nslcd
# The location at which the LDAP server(s) should be reachable.
#uri ldap://ldap.space.revspace.nl/
uri {{ldap_uri}}
# The search base that will be used for all queries.
base {{ldap_base}}
# The LDAP protocol version to use.
#ldap_version 3
# The DN to bind with for normal lookups.
#binddn cn=annonymous,dc=example,dc=net
#bindpw secret
# The DN used for password modifications by root.
#rootpwmoddn cn=admin,dc=example,dc=com
# SSL options
ssl on
tls_reqcert demand
tls_cacertfile /etc/ssl/certs/ca-certificates.crt
#tls_ciphers {{ldap_cipher_suite}}
# The search scope.
#scope sub

View file

@ -0,0 +1,33 @@
#!/usr/bin/python3
# {{ansible_managed}}
from ldap3 import Server, Connection, NONE, SUBTREE
import sys
try:
uid=str(sys.argv[1])
except:
print("No user specified")
exit(1)
if ( uid == "root" ):
exit(0)
s = Server('{{ ldap_uri }}', get_info=NONE)
c = Connection(s)
if not c.bind():
print('error in bind', c.result)
exit(1)
c.search(search_base = 'ou=People,{{ ldap_base }}',
search_filter = '(uid=' + uid + ')',
search_scope = SUBTREE,
attributes = ['sshPublicKey'],
time_limit = 2,
paged_size = 5)
keys = c.response[0]['raw_attributes']['sshPublicKey']
for x in range(len(keys)):
print( keys[x].decode('ascii') )

View file

@ -0,0 +1,7 @@
---
ldap_base: dc=space,dc=revspace,dc=nl
ldap_server: ldap.space.revspace.nl
ldap_uri: ldaps://{{ ldap_server }}:636
ldap_cafile: lets-encrypt-x1.pem
ldap_cipher_suite: "SECURE256:!AES-128-CBC:!ARCFOUR-128:!CAMELLIA-128-CBC:!3DES-CBC:!CAMELLIA-128-CBC"

View file

@ -5,5 +5,6 @@
- { role: "common", tags: [ "common" ] }
- { role: "acme", tags: [ "acme" ] }
- { role: "deb_forgejo", tags: [ "deb_forgejo" ] }
- { role: "nginx", tags: [ "nginx" ] }
- { role: "go", tags: [ "go" ] }
# - { role: "nginx", tags: [ "nginx" ] }
- { role: "music", tags: [ "music" ] }

View file

@ -1,3 +1,3 @@
bank_user: bank
bank_revbank_git: https://git.bitlair.nl/bitlair/revbank.git
bank_local_tty: no
bank_revbank_version: "10.5.1"

View file

@ -4,7 +4,7 @@
name: bank
password: $6$idklol$QrOE/21LDR0vhZBAXwgA7AvnmR6Ju4ZqzAzgeazC08i2yw9kyQjgwu.uuV692iL/cyE7AteDYUxCpcorONXom. # "bank"
home: /home/{{ bank_user }}
shell: /usr/local/share/revbank/revbank
shell: /home/{{ bank_user }}/revbank.git/revbank
update_password: always
- name: Allow password auth for bank user
@ -13,7 +13,7 @@
insertafter: EOF
validate: "/usr/sbin/sshd -t -f %s"
block: |-
Match User {{ bank_user }}
Match User bank
PasswordAuthentication yes
notify: reload sshd

View file

@ -1,22 +1,50 @@
---
- name: Install dependencies
ansible.builtin.apt:
name: [ git, libterm-readline-gnu-perl, libcurses-ui-perl ]
name: [ git, libterm-readline-gnu-perl, libcurses-ui-perl, qrencode ]
state: present
- name: Clone revbank source
ansible.builtin.git:
repo: https://github.com/revspace/revbank.git
version: "v{{ bank_revbank_version }}"
dest: /usr/local/share/revbank
repo: "{{ bank_revbank_git }}"
version: master
dest: /home/{{ bank_user }}/revbank.git
accept_hostkey: yes
- name: Clone revbank-plugin source
ansible.builtin.git:
repo: https://git.bitlair.nl/bitlair/revbank-plugins.git
version: main
dest: /usr/local/share/revbank-plugins
accept_hostkey: yes
- name: Create data files
ansible.builtin.command: cp /home/{{ bank_user }}/revbank.git/{{ item }} /home/{{ bank_user }}/{{ item }}
args:
creates: /home/{{ bank_user }}/{{ item }}
with_items:
- revbank.accounts
- revbank.market
- revbank.products
- name: Ensure data file permissions
ansible.builtin.file:
path: /home/{{ bank_user }}/{{ item }}
state: touch
owner: "{{ bank_user }}"
group: "{{ bank_user }}"
mode: 0644
with_items:
- revbank.accounts
- revbank.market
- revbank.products
- name: Link plugins
ansible.builtin.file:
state: link
path: /home/{{ bank_user }}/{{ item }}
src: /home/{{ bank_user }}/revbank.git/{{ item }}
with_items:
- plugins
- revbank.plugins
- name: Create git data dir
ansible.builtin.file:
path: /home/{{ bank_user }}/data.git
state: directory
- name: Install git cronjob
ansible.builtin.template:

View file

@ -1,4 +1,4 @@
SHELL=/bin/bash
#m h dom mon dow user command
*/10 * * * * {{ bank_user }} git -C ~/.revbank pull -r && git -C ~/.revbank push && git -C ~/.revbank gc
*/10 * * * * {{ bank_user }} (cd /home/{{ bank_user }}/data.git && git pull -r && git push && git gc --auto && cp revbank.products ../revbank.products)

View file

@ -0,0 +1 @@
../../../certs/lets-encrypt-x1.pem

View file

@ -0,0 +1 @@
../../../certs/lets-encrypt-x3-cross-signed.pem

View file

@ -0,0 +1 @@
../../../certs/sub.class1.server.sha2.ca.pem

View file

@ -0,0 +1,7 @@
---
- name: reload nslcd
service: name=nslcd state=restarted enabled=true
tags:
- ldapclient
- nslcd

View file

@ -0,0 +1,129 @@
# LDAP Client role for Revspace LDAP
# Tested on: Debian Stable
---
- name: Install LDAP client software
apt:
state: present
pkg:
- libpam-ldapd
- python3-ldap3
when: ansible_os_family == 'Debian'
tags:
- ldapclient
- apt
- name: Enable pam_mkhomedir module
lineinfile:
dest: /etc/pam.d/common-account
line: "session required pam_mkhomedir.so skel=/etc/skel/ umask=0022"
regexp: "pam_mkhomedir.so"
insertafter: EOF
tags:
- ldapclient
- mkhomedir
- name: Create login.group.allowed file
lineinfile:
dest: /etc/login.group.allowed
line: "board"
regexp: "^board$"
owner: "root"
group: "root"
mode: "0755"
create: true
with_items:
- "{{ login_groups | default('board') }}"
tags:
- ldapclient
- logingroups
when:
- logingroups is defined
- name: Limit access to listed groups
lineinfile:
dest: /etc/pam.d/common-auth
line: 'auth required pam_listfile.so onerr=fail item=group sense=allow file=/etc/login.group.allowed'
insertbefore: EOF
owner: "root"
group: "root"
mode: "0644"
regexp: "pam_listfile.*login.group.allowed"
tags:
- ldapclient
- logingroups
when:
- logingroups is defined
notify:
- reload nslcd
- name: Copy CA certificate
copy:
src: "{{ ldap_cafile }}"
dest: "/etc/ldap/{{ ldap_cafile }}"
owner: "root"
group: "root"
mode: "0644"
- name: Template ldap.conf
template:
src: "{{ item }}.j2"
dest: "/etc/ldap/{{ item }}"
owner: "root"
group: "root"
mode: "0644"
with_items:
- ldap.conf
notify:
- reload nslcd
- name: Template nslcd.conf
template:
src: "{{ item }}.j2"
dest: "/etc/{{ item }}"
owner: "root"
group: "root"
mode: "0644"
with_items:
- nslcd.conf
notify:
- reload nslcd
- name: Update /etc/nsswitch.conf
lineinfile:
dest: /etc/nsswitch.conf
line: "{{ item }}: compat ldap systemd"
regexp: "^{{ item }}"
with_items:
- passwd
- group
- shadow
- name: Template nslcd.conf
template:
src: ssh-getkey-ldap.j2
dest: /usr/sbin/ssh-getkey-ldap
owner: "root"
group: "root"
mode: "0755"
with_items:
- ssh-getkey-ldap
tags:
- ssh-getkey-ldap
- name: Update /etc/nsswitch.conf
lineinfile:
dest: /etc/nsswitch.conf
line: 'sudoers: ldap'
regexp: '^sudoers'
insertbefore: EOF"
- name: Disable nscd service
service:
name: nscd
state: stopped
enabled: false
tags:
- ldapclient
- nscd

View file

@ -0,0 +1,28 @@
# {{ ansible_managed }}
#
# LDAP Defaults
#
# See ldap.conf(5) for details
# This file should be world readable but not world writable.
BASE {{ldap_base}}
URI {{ldap_uri}}
#SIZELIMIT 12
#TIMELIMIT 15
#DEREF never
# TLS certificates (needed for GnuTLS)
TLS_CACERT /etc/ldap/{{ldap_cafile}}
#TLS_CIPHER_SUITE {{ldap_cipher_suite}}
TLS_PROTOCOL_MIN 3.3
TLS_REQCERT demand
TLS_CRLCHECK none
# Sudo settings
SUDOERS_BASE ou=SUDOers,{{ldap_base}}
#SUDOERS_SEARCH_FILTER objectClass=sudoRole
SUDOERS_TIMED yes
#SUDOERS_DEBUG 1

View file

@ -0,0 +1,35 @@
# {{ ansible_managed }}
# /etc/nslcd.conf
# nslcd configuration file. See nslcd.conf(5)
# for details.
# The user and group nslcd should run as.
uid nslcd
gid nslcd
# The location at which the LDAP server(s) should be reachable.
#uri ldap://ldap.space.revspace.nl/
uri {{ldap_uri}}
# The search base that will be used for all queries.
base {{ldap_base}}
# The LDAP protocol version to use.
#ldap_version 3
# The DN to bind with for normal lookups.
#binddn cn=annonymous,dc=example,dc=net
#bindpw secret
# The DN used for password modifications by root.
#rootpwmoddn cn=admin,dc=example,dc=com
# SSL options
ssl on
tls_reqcert demand
tls_cacertfile /etc/ssl/certs/ca-certificates.crt
#tls_ciphers {{ldap_cipher_suite}}
# The search scope.
#scope sub

View file

@ -0,0 +1,33 @@
#!/usr/bin/python3
# {{ansible_managed}}
from ldap3 import Server, Connection, NONE, SUBTREE
import sys
try:
uid=str(sys.argv[1])
except:
print("No user specified")
exit(1)
if ( uid == "root" ):
exit(0)
s = Server('{{ ldap_uri }}', get_info=NONE)
c = Connection(s)
if not c.bind():
print('error in bind', c.result)
exit(1)
c.search(search_base = 'ou=People,{{ ldap_base }}',
search_filter = '(uid=' + uid + ')',
search_scope = SUBTREE,
attributes = ['sshPublicKey'],
time_limit = 2,
paged_size = 5)
keys = c.response[0]['raw_attributes']['sshPublicKey']
for x in range(len(keys)):
print( keys[x].decode('ascii') )

View file

@ -0,0 +1,7 @@
---
ldap_base: dc=space,dc=revspace,dc=nl
ldap_server: ldap.space.revspace.nl
ldap_uri: ldaps://{{ ldap_server }}:636
ldap_cafile: lets-encrypt-x1.pem
ldap_cipher_suite: "SECURE256:!AES-128-CBC:!ARCFOUR-128:!CAMELLIA-128-CBC:!3DES-CBC:!CAMELLIA-128-CBC"

View file

@ -0,0 +1,49 @@
# AUTO-GENERATED FILE - DO NOT EDIT!! Use ldapmodify.
dn: cn={4}revspace
objectClass: olcSchemaConfig
cn: {4}revspace
olcObjectIdentifier: {0}revspaceOID 1.3.6.1.4.1.36206
olcObjectIdentifier: {1}revspaceLDAP revspaceOID:1
olcObjectIdentifier: {2}revspaceAttributeType revspaceLDAP:16
olcObjectIdentifier: {3}revspaceObjectClass revspaceLDAP:17
olcAttributeTypes: {0}( revspaceAttributeType:1 NAME 'accountBalance' DESC '
RevSpace bank account balance in eurocent' EQUALITY integerMatch SYNTAX 1.3
.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE )
olcAttributeTypes: {1}( revspaceAttributeType:2 NAME 'iButtonSerial' DESC 'i
Button serial' EQUALITY caseIgnoreMatch ORDERING caseIgnoreOrderingMatch SU
BSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 )
olcAttributeTypes: {2}( revspaceAttributeType:7 NAME 'tweetEntry' DESC 'Twee
t entry' EQUALITY booleanMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.7 )
olcAttributeTypes: {3}( revspaceAttributeType:8 NAME 'chanmsgEntry' DESC 'An
nounce entry on irc channel' EQUALITY booleanMatch SYNTAX 1.3.6.1.4.1.1466.
115.121.1.7 )
olcAttributeTypes: {4}( revspaceAttributeType:9 NAME 'statusEntry' DESC 'Ann
ounce entry in JSON status' EQUALITY booleanMatch SYNTAX 1.3.6.1.4.1.1466.1
15.121.1.7 )
olcAttributeTypes: {5}( revspaceAttributeType:3 NAME 'articleName' DESC 'Rev
Space stock management item name' EQUALITY caseIgnoreMatch ORDERING caseIgn
oreOrderingMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.1
15.121.1.15 )
olcAttributeTypes: {6}( revspaceAttributeType:6 NAME 'barCode' DESC 'RevSpac
e stock management item barcode' EQUALITY caseIgnoreMatch ORDERING caseIgno
reOrderingMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.11
5.121.1.15 )
olcAttributeTypes: {7}( revspaceAttributeType:4 NAME 'stock' DESC 'Amount of
items in stock' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27
SINGLE-VALUE )
olcAttributeTypes: {8}( revspaceAttributeType:5 NAME 'price' DESC 'Price per
item in eurocent' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.
27 SINGLE-VALUE )
olcObjectClasses: {0}( revspaceObjectClass:1 NAME 'revspaceAccount' DESC 'mi
xin RevSpace account details' AUXILIARY MAY ( accountBalance $ iButtonSeria
l $ tweetEntry $ chanmsgEntry $ statusEntry ) )
olcObjectClasses: {1}( revspaceObjectClass:2 NAME 'revspaceProduct' DESC 'mi
xin RevSpace product details' STRUCTURAL MUST ( articleName $ price ) MAY (
stock $ barCode ) )
structuralObjectClass: olcSchemaConfig
entryUUID: 2d92bbae-fbff-1034-865e-79a954a03d07
creatorsName: cn=config
createTimestamp: 20150930204006Z
entryCSN: 20150930204006.374158Z#000000#000#000000
modifiersName: cn=config
modifyTimestamp: 20150930204006Z

View file

@ -0,0 +1,48 @@
# AUTO-GENERATED FILE - DO NOT EDIT!! Use ldapmodify.
dn: cn={5}sudoers
objectClass: olcSchemaConfig
cn: {5}sudoers
olcAttributeTypes: {0}( 1.3.6.1.4.1.15953.9.1.1 NAME 'sudoUser' DESC 'User(s
) who may run sudo' EQUALITY caseExactIA5Match SUBSTR caseExactIA5Substrin
gsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: {1}( 1.3.6.1.4.1.15953.9.1.2 NAME 'sudoHost' DESC 'Host(s
) who may run sudo' EQUALITY caseExactIA5Match SUBSTR caseExactIA5Substring
sMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: {2}( 1.3.6.1.4.1.15953.9.1.3 NAME 'sudoCommand' DESC 'Com
mand(s) to be executed by sudo' EQUALITY caseExactIA5Match SYNTAX 1.3.6.1.4
.1.1466.115.121.1.26 )
olcAttributeTypes: {3}( 1.3.6.1.4.1.15953.9.1.4 NAME 'sudoRunAs' DESC 'User(
s) impersonated by sudo' EQUALITY caseExactIA5Match SYNTAX 1.3.6.1.4.1.1466
.115.121.1.26 )
olcAttributeTypes: {4}( 1.3.6.1.4.1.15953.9.1.5 NAME 'sudoOption' DESC 'Opti
ons(s) followed by sudo' EQUALITY caseExactIA5Match SYNTAX 1.3.6.1.4.1.1466
.115.121.1.26 )
olcAttributeTypes: {5}( 1.3.6.1.4.1.15953.9.1.6 NAME 'sudoRunAsUser' DESC 'U
ser(s) impersonated by sudo' EQUALITY caseExactIA5Match SYNTAX 1.3.6.1.4.1.
1466.115.121.1.26 )
olcAttributeTypes: {6}( 1.3.6.1.4.1.15953.9.1.7 NAME 'sudoRunAsGroup' DESC '
Group(s) impersonated by sudo' EQUALITY caseExactIA5Match SYNTAX 1.3.6.1.4.
1.1466.115.121.1.26 )
olcAttributeTypes: {7}( 1.3.6.1.4.1.15953.9.1.8 NAME 'sudoNotBefore' DESC 'S
tart of time interval for which the entry is valid' EQUALITY generalizedTim
eMatch ORDERING generalizedTimeOrderingMatch SYNTAX 1.3.6.1.4.1.1466.115.12
1.1.24 )
olcAttributeTypes: {8}( 1.3.6.1.4.1.15953.9.1.9 NAME 'sudoNotAfter' DESC 'En
d of time interval for which the entry is valid' EQUALITY generalizedTimeMa
tch ORDERING generalizedTimeOrderingMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1
.24 )
olcAttributeTypes: {9}( 1.3.6.1.4.1.15953.9.1.10 NAME 'sudoOrder' DESC 'an i
nteger to order the sudoRole entries' EQUALITY integerMatch ORDERING intege
rOrderingMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 )
olcObjectClasses: {0}( 1.3.6.1.4.1.15953.9.2.1 NAME 'sudoRole' DESC 'Sudoer
Entries' SUP top STRUCTURAL MUST cn MAY ( sudoUser $ sudoHost $ sudoCommand
$ sudoRunAs $ sudoRunAsUser $ sudoRunAsGroup $ sudoOption $ sudoNotBefore
$ sudoNotAfter $ sudoOrder $ description ) )
structuralObjectClass: olcSchemaConfig
entryUUID: 3a967b84-0248-1035-954b-037a0fbd2d2a
creatorsName: cn=config
createTimestamp: 20151008203808Z
entryCSN: 20151008203808.446725Z#000000#000#000000
modifiersName: cn=config
modifyTimestamp: 20151008203808Z

View file

@ -0,0 +1,94 @@
#
# Author: "Koen Martens" <gmc@revspace.nl>
# Desc. : RevSpaceBank account balance field definition and
# mixin objectClass for RevSpace ldap directory
# RevSpace stock management object class and attributes
# to be replaced with assigned PEN
objectIdentifier revspaceOID 1.3.6.1.4.1.36206
# some further derived short-hands
objectIdentifier revspaceLDAP revspaceOID:1
objectIdentifier revspaceAttributeType revspaceLDAP:16
objectIdentifier revspaceObjectClass revspaceLDAP:17
# the account balance, in eurocent
#attributetype ( 1.3.6.1.1.1.1.8 NAME 'shadowWarning'
# EQUALITY integerMatch
# SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE )
attributeType ( revspaceAttributeType:1 NAME 'accountBalance'
DESC 'RevSpace bank account balance in eurocent'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.27
EQUALITY integerMatch
SINGLE-VALUE )
attributeType ( revspaceAttributeType:2 NAME 'iButtonSerial'
DESC 'iButton serial'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.15
EQUALITY caseIgnoreMatch
SUBSTR caseIgnoreSubstringsMatch
ORDERING caseIgnoreOrderingMatch )
attributeType ( revspaceAttributeType:7 NAME 'tweetEntry'
DESC 'Tweet entry'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.7
EQUALITY booleanMatch )
attributeType ( revspaceAttributeType:8 NAME 'chanmsgEntry'
DESC 'Announce entry on irc channel'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.7
EQUALITY booleanMatch )
attributeType ( revspaceAttributeType:9 NAME 'statusEntry'
DESC 'Announce entry in JSON status'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.7
EQUALITY booleanMatch )
#attributeType ( revspaceAttributeType:2 NAME 'iButtonSerial'
# DESC 'iButton serial'
# SYNTAX 1.3.6.1.4.1.1466.115.121.1.16
# EQUALITY caseIgnoreMatch
# SUBSTR caseIgnoreSubstringsMatch
# ORDERING caseIgnoreOrderingMatch )
objectclass ( revspaceObjectClass:1 NAME 'revspaceAccount'
DESC 'mixin RevSpace account details'
AUXILIARY
MAY ( accountBalance $ iButtonSerial $ tweetEntry $ chanmsgEntry $ statusEntry ) )
# RevSpace stock management (bar items)
#
attributeType ( revspaceAttributeType:3 NAME 'articleName'
DESC 'RevSpace stock management item name'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.15
EQUALITY caseIgnoreMatch
SUBSTR caseIgnoreSubstringsMatch
ORDERING caseIgnoreOrderingMatch )
attributeType ( revspaceAttributeType:6 NAME 'barCode'
DESC 'RevSpace stock management item barcode'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.15
EQUALITY caseIgnoreMatch
SUBSTR caseIgnoreSubstringsMatch
ORDERING caseIgnoreOrderingMatch )
attributeType ( revspaceAttributeType:4 NAME 'stock'
DESC 'Amount of items in stock'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.27
EQUALITY integerMatch
SINGLE-VALUE )
attributeType ( revspaceAttributeType:5 NAME 'price'
DESC 'Price per item in eurocent'
SYNTAX 1.3.6.1.4.1.1466.115.121.1.27
EQUALITY integerMatch
SINGLE-VALUE )
objectclass ( revspaceObjectClass:2 NAME 'revspaceProduct'
DESC 'mixin RevSpace product details'
STRUCTURAL
MUST ( articleName $ price )
MAY ( stock $ barCode ) )

View file

@ -0,0 +1 @@
../../../../certs/lets-encrypt-x1.pem

View file

@ -0,0 +1 @@
../../../../certs/ldap/ldap.space.revspace.nl.cert

View file

@ -0,0 +1 @@
../../../../certs/ldap/space.revspace.nl.key

View file

@ -0,0 +1,77 @@
dn: cn=sudoers,cn=schema,cn=config
objectClass: olcSchemaConfig
cn: sudoers
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.1
NAME 'sudoUser'
DESC 'User(s) who may run sudo'
EQUALITY caseExactIA5Match
SUBSTR caseExactIA5SubstringsMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.2
NAME 'sudoHost'
DESC 'Host(s) who may run sudo'
EQUALITY caseExactIA5Match
SUBSTR caseExactIA5SubstringsMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.3
NAME 'sudoCommand'
DESC 'Command(s) to be executed by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.4
NAME 'sudoRunAs'
DESC 'User(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.5
NAME 'sudoOption'
DESC 'Options(s) followed by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.6
NAME 'sudoRunAsUser'
DESC 'User(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.7
NAME 'sudoRunAsGroup'
DESC 'Group(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.8
NAME 'sudoNotBefore'
DESC 'Start of time interval for which the entry is valid'
EQUALITY generalizedTimeMatch
ORDERING generalizedTimeOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.9
NAME 'sudoNotAfter'
DESC 'End of time interval for which the entry is valid'
EQUALITY generalizedTimeMatch
ORDERING generalizedTimeOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 )
olcAttributeTypes: ( 1.3.6.1.4.1.15953.9.1.10
NAME 'sudoOrder'
DESC 'an integer to order the sudoRole entries'
EQUALITY integerMatch
ORDERING integerOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 )
olcObjectClasses: ( 1.3.6.1.4.1.15953.9.2.1 NAME 'sudoRole' SUP top STRUCTURAL
DESC 'Sudoer Entries'
MUST ( cn )
MAY ( sudoUser $ sudoHost $ sudoCommand $ sudoRunAs $ sudoRunAsUser $
sudoRunAsGroup $ sudoOption $ sudoNotBefore $ sudoNotAfter $
sudoOrder $ description )
)

View file

@ -0,0 +1,73 @@
attributetype ( 1.3.6.1.4.1.15953.9.1.1
NAME 'sudoUser'
DESC 'User(s) who may run sudo'
EQUALITY caseExactIA5Match
SUBSTR caseExactIA5SubstringsMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.2
NAME 'sudoHost'
DESC 'Host(s) who may run sudo'
EQUALITY caseExactIA5Match
SUBSTR caseExactIA5SubstringsMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.3
NAME 'sudoCommand'
DESC 'Command(s) to be executed by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.4
NAME 'sudoRunAs'
DESC 'User(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.5
NAME 'sudoOption'
DESC 'Options(s) followed by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.6
NAME 'sudoRunAsUser'
DESC 'User(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.7
NAME 'sudoRunAsGroup'
DESC 'Group(s) impersonated by sudo'
EQUALITY caseExactIA5Match
SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 )
attributetype ( 1.3.6.1.4.1.15953.9.1.8
NAME 'sudoNotBefore'
DESC 'Start of time interval for which the entry is valid'
EQUALITY generalizedTimeMatch
ORDERING generalizedTimeOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 )
attributetype ( 1.3.6.1.4.1.15953.9.1.9
NAME 'sudoNotAfter'
DESC 'End of time interval for which the entry is valid'
EQUALITY generalizedTimeMatch
ORDERING generalizedTimeOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 )
attributeTypes ( 1.3.6.1.4.1.15953.9.1.10
NAME 'sudoOrder'
DESC 'an integer to order the sudoRole entries'
EQUALITY integerMatch
ORDERING integerOrderingMatch
SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 )
objectclass ( 1.3.6.1.4.1.15953.9.2.1 NAME 'sudoRole' SUP top STRUCTURAL
DESC 'Sudoer Entries'
MUST ( cn )
MAY ( sudoUser $ sudoHost $ sudoCommand $ sudoRunAs $ sudoRunAsUser $
sudoRunAsGroup $ sudoOption $ sudoNotBefore $ sudoNotAfter $
sudoOrder $ description )
)

View file

@ -0,0 +1,4 @@
---
- name: Restart slapd
service: name=slapd state=restarted

View file

@ -0,0 +1,99 @@
---
- name: Configure debconf items for slapd
debconf:
name: slapd
question: "slapd/{{ item.q }}"
value: "{{ item.v }}"
vtype: "{{ item.t }}"
with_items:
- { q: 'domain', v: "{{ slapd_domain }}", t: 'string' }
- { q: 'backend', v: "MDB", t: 'select' }
notify:
- Restart slapd
- name: Configure debconf items for slapd (passwords)
debconf:
name: slapd
question: "slapd/{{ item.q }}"
value: "{{ item.v }}"
vtype: "{{ item.t }}"
with_items:
- { q: 'password1', v: "{{ slapd_admin_pass }}", t: 'password' }
- { q: 'password2', v: "{{ slapd_admin_pass }}", t: 'password' }
changed_when: false
no_log: "{{ filter_logs|default('true') }}"
- name: Install required software
apt:
pkg:
- slapd
- ldap-utils
state: present
- name: Set ldap OLC password
lineinfile:
dest: "/etc/ldap/slapd.d/cn=config/olcDatabase={0}config.ldif"
line: "olcRootPW: {{ slapd_config_pass }}"
insertafter: "^modifyTimeStamp:"
regexp: "^olcRootPW"
notify:
- Restart slapd
- name: Copy revspace schema and olcConfig
copy:
src: "{{ item.src }}"
dest: "/etc/ldap/{{ item.dst }}"
owner: "openldap"
group: "openldap"
mode: "0644"
with_items:
- { src: "revspace.schema", dst: "schema/revspace.schema" }
- { src: "sudoers.schema", dst: "schema/sudoers.schema" }
- { src: "cn={4}revspace.ldif", dst: "slapd.d/cn=config/cn=schema/cn={4}revspace.ldif" }
- { src: "cn={5}sudoers.ldif", dst: "slapd.d/cn=config/cn=schema/cn={5}sudoers.ldif" }
notify:
- Restart slapd
#- name: Create directory for certificates
# file: path={{ slapd_certpath }} state=directory owner=openldap group=openldap mode=0700
#
#- name: Copy TLS files
# copy: src=ssl/{{ item }} dest={{ slapd_certpath }}/{{ item }} owner=openldap group=openldap mode=0400
# with_items:
# - cacert.pem
# - server-key.pem
# - server-cert.pem
- name: Template olc edits
template:
src: "{{ item }}.j2"
dest: "/etc/ldap/{{ item }}.ldif"
owner: "openldap"
group: "openldap"
mode: "0600"
with_items:
- olcAccess
- olcSSL
register: olcedits
notify:
- Restart slapd
- name: Update olcConfig
command: "ldapmodify -Y EXTERNAL -H ldapi:/// -f /etc/ldap/{{ item }}.ldif"
with_items:
- olcAccess
- olcSSL
when: olcedits is changed
ignore_errors: true
changed_when: false
notify:
- Restart slapd
- name: Enable SSL listener
lineinfile:
dest: "/etc/default/slapd"
line: "SLAPD_SERVICES=\"ldap:/// ldaps:/// ldapi:///\""
regexp: "^SLAPD_SERVICES"
notify:
- Restart slapd

View file

@ -0,0 +1,8 @@
dn: olcDatabase={1}mdb,cn=config
changetype: modify
add: olcAccess
olcAccess: {1}to attrs=loginShell,gecos
by dn="cn=admin,{{slapd_root}}" write
by self write
by * read

View file

@ -0,0 +1,15 @@
# {{ansible_managed }}
dn: cn=config
changetype: modify
replace: olcTLSCACertificateFile
olcTLSCACertificateFile: {{slapd_certpath}}/fullchain.pem
-
replace: olcTLSCertificateKeyFile
olcTLSCertificateKeyFile: {{slapd_certpath}}/privkey.pem
-
replace: olcTLSCertificateFile
olcTLSCertificateFile: {{slapd_certpath}}/cert.pem
-
replace: olcTLSCipherSuite
olcTLSCipherSuite: {{slapd_cipher_suite}}

1
roles/ldapserver/vars/.gitignore vendored Normal file
View file

@ -0,0 +1 @@
secret.yaml

View file

@ -0,0 +1,9 @@
---
slapd_config_pass: "{{ lookup('passwordstore', 'revspace/ldap/config') }}"
slapd_admin_pass: "{{ lookup('passwordstore', 'revspace/ldap/admin') }}"
slapd_domain: "space.revspace.nl"
slapd_root: "dc=space,dc=revspace,dc=nl"
slapd_certpath: "/etc/dehydrated/certs/ldap.space.revspace.nl/"
slapd_cipher_suite: "SECURE256:!AES-128-CBC:!ARCFOUR-128:!CAMELLIA-128-CBC:!3DES-CBC:!CAMELLIA-128-CBC"

View file

@ -0,0 +1 @@
mqtt_bambulab_cafile: /etc/mosquitto/ca_certificates/bambulab.pem

View file

@ -9,10 +9,8 @@
- name: Install bambulab cafile
# openssl s_client -showcerts -connect <ip>:8883 </dev/null | sed -n -e '/-.BEGIN/,/-.END/ p'
ansible.builtin.copy:
dest: "/etc/mosquitto/ca_certificates/bambu_{{ item.name }}.pem"
content: "{{ item.cafile }}"
notify: restart mosquitto
with_items: "{{ lookup('passwordstore', 'bambulab subkey=printers') }}"
dest: "{{ mqtt_bambulab_cafile }}"
content: "{{ lookup('passwordstore', 'bambulab subkey=cafile') }}"
- name: Configure Mosquitto
ansible.builtin.template:

View file

@ -1,11 +1,10 @@
# {{ ansible_managed }}
{% for bambu in lookup('passwordstore', 'bambulab subkey=printers') %}
connection bambulab_{{ bambu.name }}
address {{ bambu.host }}:8883
bridge_cafile /etc/mosquitto/ca_certificates/bambu_{{ bambu.name }}.pem
connection bambulab
address {{ lookup('passwordstore', 'bambulab subkey=host') }}:8883
bridge_cafile {{ mqtt_bambulab_cafile }}
bridge_insecure true
remote_username bblp
remote_password {{ bambu.key }}
topic # in 2 bambulab/{{ bambu.name }}/ ""
{% endfor %}
remote_password {{ lookup('passwordstore', 'bambulab subkey=key') }}
topic # in 2 bambulab/ ""

View file

@ -1,10 +1,2 @@
music_audio_user: audio
music_audio_user_id: 998
music_audio_group: audio
music_bitvis_user: bitvis
music_librespot_user: librespot
music_trollibox_user: trollibox
music_pulse_server: /tmp/pipewire-pulse-socket
music_mqtt_mpd_volume: bitlair/music/space/volume

View file

@ -2,65 +2,27 @@
- ansible.builtin.import_tasks:
file: ../../common/handlers/main.yaml
- name: restart pipewire
become: true
become_user: "{{ music_audio_user }}"
become_method: machinectl
ansible.builtin.systemd:
name: pipewire
state: restarted
daemon_reload: true
scope: user
- name: restart filter-chain
become: true
become_user: "{{ music_audio_user }}"
become_method: machinectl
ansible.builtin.systemd:
name: filter-chain
state: restarted
daemon_reload: true
scope: user
- name: restart bitvis
ansible.builtin.systemd:
name: bitvis
state: restarted
daemon_reload: true
- name: restart bitvis-tee
ansible.builtin.systemd:
name: bitvis-tee
state: restarted
daemon_reload: true
- name: restart mpd
ansible.builtin.systemd:
name: mpd
state: restarted
daemon_reload: true
- name: restart trollibox
- name: Restart trollibox
ansible.builtin.systemd:
name: trollibox
state: restarted
daemon_reload: true
- name: rebuild librespot
- name: Rebuild librespot
ansible.builtin.command:
cmd: /root/.cargo/bin/cargo build --release --features pulseaudio-backend,jackaudio-backend
cmd: /root/.cargo/bin/cargo build --release --features jackaudio-backend
args:
chdir: /opt/librespot
- name: restart librespot
- name: Restart librespot
ansible.builtin.systemd:
name: librespot
state: restarted
daemon_reload: true
- name: restart mqtt-soundboard
- name: Restart soundboard
ansible.builtin.systemd:
name: mqtt-soundboard
name: soundboard
state: restarted
daemon_reload: true
@ -75,12 +37,3 @@
name: skipbutton
state: restarted
daemon_reload: true
- name: restart ampswitch
ansible.builtin.systemd:
name: "ampswitch-{{ item }}"
state: restarted
daemon_reload: true
with_items:
- librespot
- mpd

View file

@ -1,31 +0,0 @@
---
- name: Install ampswitch
apt:
name: ampswitch
- name: Install ampswitch service file
template:
src: ampswitch.service
dest: /etc/systemd/system/ampswitch-{{ item.instance }}.service
owner: root
group: root
mode: 0755
with_items:
- instance: mpd
pw_inputs:
- "Music Player Daemon:output_FL"
- "Music Player Daemon:output_FR"
- instance: librespot
pw_inputs:
- "librespot:out_0"
- "librespot:out_1"
notify: restart ampswitch
- name: Enable ampswitch
ansible.builtin.systemd:
name: "ampswitch-{{ item }}"
state: started
enabled: true
with_items:
- librespot
- mpd

View file

@ -1,68 +0,0 @@
---
- name: Install pipewire
apt:
name:
- systemd-container
- pipewire
- pipewire-jack
- pipewire-pulse
- pulseaudio-utils
- pulsemixer
- wireplumber
state: present
- name: Add audio group
group:
name: audio
system: true
- name: Add {{ music_audio_user }} user
user:
name: "{{ music_audio_user }}"
uid: "{{ music_audio_user_id }}"
system: true
groups:
- audio
- name: Enable linger for {{ music_audio_user }}
copy:
dest: "/var/lib/systemd/linger/{{ music_audio_user }}"
content: ""
- name: Enable pipewire
become: true
become_user: "{{ music_audio_user }}"
become_method: machinectl
ansible.builtin.systemd:
name: pipewire
state: started
enabled: true
scope: user
- name: Set PULSE_SERVER env var for all shells
copy:
dest: /etc/profile.d/pulse-server.sh
content: |+
# Ansible managed
export PULSE_SERVER={{ music_pulse_server }}
- name: Create pipewire-pulse config dir
file:
path: /etc/pipewire/pipewire-pulse.conf.d/
state: directory
- name: Configure system socket
ansible.builtin.copy:
dest: /etc/pipewire/pipewire-pulse.conf.d/system-socket.conf
content: |+
# Ansible managed
context.exec = [
{ path = "/bin/chgrp" args = "{{ music_audio_group }} {{ music_pulse_server }}" }
{ path = "/bin/chmod" args = "g+rwx,o-rwx {{ music_pulse_server }}" }
]
pulse.properties = {
server.address = [
"unix:{{ music_pulse_server }}"
]
}
notify: restart pipewire

View file

@ -1,72 +0,0 @@
---
- name: Install bitvis dependencies
apt:
name:
- bitvis
- bitvis-http
- swh-plugins
- name: Create bitvis user
user:
name: "{{ music_bitvis_user }}"
system: true
home: /var/lib/bitvis
groups:
- "{{ music_audio_group }}"
- name: Install bitvis-tee
ansible.builtin.template:
src: bitvis-tee.sh
dest: /opt/bitvis-tee.sh
owner: root
group: root
mode: 0755
notify: restart {{ item }}
with_items:
- bitvis
- bitvis-tee
- name: Install service file
ansible.builtin.template:
src: "{{ item }}.service"
dest: /etc/systemd/system/{{ item }}.service
owner: root
group: root
mode: 0644
notify: restart {{ item }}
with_items:
- bitvis
- bitvis-tee
- name: Enable service
ansible.builtin.systemd:
name: "{{ item }}"
state: started
enabled: true
daemon_reload: true
with_items:
- bitvis
- bitvis-tee
- name: Install bitvis gain filter
ansible.builtin.template:
src: pw-bitvis-mixer.conf
dest: /etc/pipewire/filter-chain.conf.d/bitvis-mixer.conf
owner: root
group: root
mode: 0644
notify:
- restart filter-chain
- restart bitvis
- name: Enable filter-chain
become: true
become_user: "{{ music_audio_user }}"
become_method: machinectl
ansible.builtin.systemd:
name: filter-chain
state: started
enabled: true
scope: user
- meta: flush_handlers

View file

@ -1,18 +1,8 @@
---
- name: Install apt dependencies
apt:
name:
- libasound2-dev
- libjack-dev
- pkg-config
- name: Create librespot user
user:
name: "{{ music_librespot_user }}"
system: true
home: /var/lib/librespot
groups:
- "{{ music_audio_group }}"
- name: Install dependencies
ansible.builtin.apt:
name: libjack-jackd2-dev
state: present
- name: Clone librespot source
ansible.builtin.git:
@ -21,8 +11,8 @@
dest: /opt/librespot
accept_hostkey: yes
notify:
- rebuild librespot
- restart librespot
- Rebuild librespot
- Restart librespot
- name: Install service file
ansible.builtin.template:
@ -31,7 +21,7 @@
owner: root
group: root
mode: 0644
notify: restart librespot
notify: Restart librespot
- name: Enable Librespot
ansible.builtin.systemd:
@ -39,5 +29,3 @@
state: started
enabled: true
daemon_reload: true
- meta: flush_handlers

View file

@ -1,9 +1,4 @@
---
- name: Import base
ansible.builtin.import_tasks:
file: base.yaml
tags:
- music_base
- name: Import mpd
ansible.builtin.import_tasks:
@ -11,18 +6,6 @@
tags:
- music_mpd
- name: Bitvis
ansible.builtin.import_tasks:
file: bitvis.yaml
tags:
- music_bitvis
- name: Import airplay
ansible.builtin.import_tasks:
file: airplay.yaml
tags:
- music_airplay
- name: Import trollibox
ansible.builtin.import_tasks:
file: trollibox.yaml
@ -41,8 +24,11 @@
tags:
- music_soundboard
- name: Ampswitch
ansible.builtin.import_tasks:
file: ampswitch.yaml
tags:
- music_ampswitch
- name: Install nginx config
ansible.builtin.template:
src: nginx-site.conf
dest: /etc/nginx/sites-enabled/trollibox
owner: root
group: root
mode: 0644
notify: Reload nginx

View file

@ -1,32 +1,14 @@
---
- name: Install MPD
ansible.builtin.apt:
name: mpd
name:
- jackd
- mpd
- python3-mpd
- python3-serial
state: present
- name: Add mpd user to the {{ music_audio_group }} group
user:
name: mpd
groups:
- "{{ music_audio_group }}"
notify: restart mpd
- name: Install mpd file
ansible.builtin.template:
src: "{{ item.src }}"
dest: "{{ item.dest }}"
owner: root
group: root
mode: 0644
notify: restart mpd
with_items:
- src: mpd.conf
dest: /etc/mpd.conf
- src: mpd.service
dest: /etc/systemd/system/mpd.service
- src: mpd_state
dest: /var/lib/mpd/state.default
- name: Install mpd-volume-to-mqtt script
ansible.builtin.template:
src: mpd-volume-to-mqtt.sh
@ -51,3 +33,27 @@
state: started
enabled: true
daemon_reload: true
- name: Clone skipbutton source
ansible.builtin.git:
repo: https://github.com/bitlair/skipbutton.git
version: master
dest: /opt/skipbutton
accept_hostkey: yes
notify: Restart skipbutton
- name: Install skipbutton service
ansible.builtin.template:
src: skipbutton.service
dest: /etc/systemd/system/skipbutton.service
owner: root
group: root
mode: 0644
notify: Restart skipbutton
- name: Enable skipbutton
ansible.builtin.systemd:
name: skipbutton
state: started
enabled: true
daemon_reload: true

View file

@ -6,23 +6,25 @@
- mplayer
state: present
- ansible.builtin.file:
path: "{{ item }}"
state: absent
with_items:
- /opt/soundboard
- /etc/systemd/system/soundboard.service
- name: Install soundboard config file
ansible.builtin.template:
src: "{{ item.src }}"
dest: "{{ item.dest }}"
src: soundboard.yaml
dest: /etc/soundboard.yaml
owner: root
group: root
mode: 0644
notify: restart mqtt-soundboard
with_items:
- src: mqtt-soundboard.service
dest: /etc/systemd/system/mqtt-soundboard.service
- src: mqtt-soundboard.yaml
dest: /etc/mqtt-soundboard.yaml
notify: Restart soundboard
- name: Enable soundboard
ansible.builtin.systemd:
name: mqtt-soundboard
name: soundboard
state: started
enabled: true
daemon_reload: true

View file

@ -1,10 +1,4 @@
---
- name: Create trollibox user
user:
name: "{{ music_trollibox_user }}"
system: true
home: /var/lib/trollibox
- name: Install Trollibox config
ansible.builtin.template:
src: trollibox.yaml
@ -12,29 +6,27 @@
owner: root
group: root
mode: "0644"
notify: restart trollibox
notify: Restart trollibox
- name: Get latest Trollibox version from Github API
uri:
ansible.builtin.get_url:
url: "https://api.github.com/repos/polyfloyd/trollibox/releases/latest"
return_content: true
register: response
changed_when: false
check_mode: false
failed_when: "response is failed or 'json' not in response"
dest: "/tmp/_ansible_trollibox_latest_release.json"
- name: Format trollibox latest version
set_fact:
trollibox_version: "{{ response['json']['tag_name'] | trim('v') }}"
- name: Get download url
ansible.builtin.shell:
cmd: cat /tmp/_ansible_trollibox_latest_release.json | jq .assets[] | select(.name
| contains("linux-amd64")) | .browser_download_url -r
register: "trollibox_download_url"
- name: Download Trollibox
ansible.builtin.unarchive:
src: "https://github.com/polyfloyd/trollibox/releases/download/v{{ trollibox_version }}/trollibox-x86_64-unknown-linux-gnu.tar.gz"
src: "{{ trollibox_download_url.stdout }}"
remote_src: yes
dest: /usr/local/bin
include: [ trollibox ]
mode: "0755"
notify: restart trollibox
notify: Restart trollibox
- name: Install service file
ansible.builtin.template:
@ -43,7 +35,7 @@
owner: root
group: root
mode: "0644"
notify: restart trollibox
notify: Restart trollibox
- name: Enable Trollibox
ansible.builtin.systemd:

View file

@ -1,20 +0,0 @@
[Unit]
Description=Script hook for {{ item }} playback
After=network.target {{ item.instance }}.service
Requires={{ item.instance }}.service
StopPropagatedFrom={{ item.instance }}.service
[Service]
Type=simple
Restart=always
RestartSec=10s
ExecStart=/usr/bin/pw-jack ampswitch --jack-name ampswitch-{{ item.instance }} --on-command /opt/on-{{ item.instance }}-start.sh --switch-time 10 --trigger-level 0.001
ExecStartPost=/usr/bin/sleep 4
{% for pw_input in item.pw_inputs %}
ExecStartPost=-/usr/bin/pw-link "{{ pw_input }}" ampswitch-{{ item.instance }}:Input
{% endfor %}
User=root
Environment="XDG_RUNTIME_DIR=/run/user/{{ music_audio_user_id }}"
[Install]
WantedBy=multi-user.target

View file

@ -1,15 +0,0 @@
[Unit]
Description=Multiplexer for bitvis
Before=bitvis.service
After=bitvis-http.service
Requires=bitvis-http.service
PropagatesStopTo=bitvis.service
StopPropagatedFrom=bitvis.service
[Service]
Type=forking
ExecStart=/usr/bin/screen -dmS bitvis-tee /opt/bitvis-tee.sh
User={{ music_bitvis_user }}
[Install]
WantedBy=multi-user.target

View file

@ -1,10 +0,0 @@
#!/bin/bash
# {{ ansible_managed }}
loop=`mktemp --suffix -bitvis`
mkfifo -f "$loop"
trap "rm -f $loop" EXIT TERM
cat "$loop" | while true; do nc -4 -w 2 localhost 1338; done &
nc -klp 1337 | tee "$loop" | while true; do nc -w 2 {{ music_bitpanel_host }} {{ music_bitpanel_port }}; done

View file

@ -1,19 +0,0 @@
[Unit]
Description=Audio visualizer for the bitpanel
After=network.target
[Service]
Type=simple
Restart=always
RestartSec=10s
ExecStart=/usr/bin/pw-jack bitvis -a localhost -p 1337 -m localhost -o 6600
ExecStartPost=/usr/bin/sleep 4
ExecStartPost=-/usr/bin/pw-link bitvis-mixer:output_FL bitvis:input
ExecStartPost=-/usr/bin/pw-link alsa_output.usb-ASUS_Xonar_U7_MKII-00.analog-stereo:monitor_FL bitvis-mixer:playback_FL
ExecStartPost=-/usr/bin/pw-link alsa_output.usb-ASUS_Xonar_U7_MKII-00.analog-stereo:monitor_FR bitvis-mixer:playback_FR
User={{ music_audio_user }}
Environment="XDG_RUNTIME_DIR=/run/user/{{ music_audio_user_id }}"
[Install]
WantedBy=multi-user.target

View file

@ -3,18 +3,16 @@
[Unit]
Description=Spotify through Librespot
After=network.target
Requires=jackd.service
[Service]
Type=simple
Restart=always
RestartSec=10s
ExecStart=/usr/bin/pw-jack -s 44100 /opt/librespot/target/release/librespot --name Trollibox --backend jackaudio
ExecStartPost=/usr/bin/sleep 4
ExecStartPost=-/usr/bin/pw-link librespot:out_0 alsa_output.usb-ASUS_Xonar_U7_MKII-00.analog-stereo:playback_FL
ExecStartPost=-/usr/bin/pw-link librespot:out_1 alsa_output.usb-ASUS_Xonar_U7_MKII-00.analog-stereo:playback_FR
# User={{ music_librespot_user }}
User=root
Environment="XDG_RUNTIME_DIR=/run/user/{{ music_audio_user_id }}"
RestartSec=2s
ExecStart=/opt/librespot/target/release/librespot --name Trollibox --backend jackaudio
User={{ music_audio_user }}
Group={{ music_audio_user }}
AmbientCapabilities=CAP_IPC_LOCK,CAP_SYS_NICE
[Install]
WantedBy=multi-user.target

View file

@ -14,7 +14,7 @@ prev_volume=x
if [ $event = "mixer" ]; then
volume=`mpc volume | sed -nr 's/^volume: ([0-9]+)%$/\1/p'`
if [ "$prev_volume" != "$volume" ]; then
mqtt-simple -h {{ mqtt_internal_host }} -p '{{ music_mqtt_mpd_volume }}' -r -m "$volume"
mqtt-simple -h {{ mqtt_internal_host }} -p '{{ music_mqtt_mpd_volume }} -r' -m "$volume"
fi
prev_volume=$volume
fi

View file

@ -1,40 +0,0 @@
# {{ ansible_managed }}
user "mpd"
group "{{ music_audio_group }}"
bind_to_address "any"
port "6600"
max_connections "20"
zeroconf_enabled "yes"
zeroconf_name "MPD @ %h"
music_directory "/srv/media/music"
auto_update "yes"
filesystem_charset "UTF-8"
playlist_directory "/var/lib/mpd/playlists"
db_file "/var/lib/mpd/tag_cache"
state_file "/var/lib/mpd/state"
sticker_file "/var/lib/mpd/sticker.sql"
input {
plugin "curl" # Required for web streams.
}
decoder {
plugin "hybrid_dsd"
enabled "no"
}
decoder {
plugin "wildmidi"
enabled "no"
}
audio_output {
type "pulse"
name "Pulse"
server "{{ music_pulse_server }}"
}

View file

@ -1,21 +0,0 @@
# {{ ansible_managed }}
[Unit]
Description=Music Player Daemon
After=network.target
[Service]
Type=simple
ExecStartPre=/bin/mkdir -p /run/mpd
ExecStartPre=/bin/chown -R mpd:nogroup /run/mpd
ExecStartPre=/bin/touch /var/log/mpd.log
ExecStartPre=/bin/chown mpd:nogroup /var/log/mpd.log
ExecStartPre=/usr/bin/cp /var/lib/mpd/state.default /var/lib/mpd/state
ExecStart=/usr/bin/mpd --no-daemon /etc/mpd.conf
# MDP will fork itself to the user defined in its config
User=root
LimitMEMLOCK=infinity
LimitRTPRIO=99
[Install]
WantedBy=multi-user.target

View file

@ -1,17 +0,0 @@
sw_volume: 20
audio_device_state:1:Pulse
state: play
current: 0
time: 0
random: 0
repeat: 0
single: 0
consume: 0
crossfade: 0
mixrampdb: 0.000000
mixrampdelay: -1.000000
playlist_begin
song_begin: http://ice4.somafm.com/groovesalad-256-mp3
Name: SomaFM Groove Salad
song_end
playlist_end

View file

@ -0,0 +1,70 @@
# {{ ansible_managed }}
server {
listen 80 default_server;
listen [::]:80 default_server;
listen 443 ssl default_server;
listen [::]:443 ssl default_server;
server_name {{ music_domain }};
{% if acme_bootstrap_certs %}
include "snippets/snakeoil.conf";
{% else %}
ssl_certificate "/var/lib/dehydrated/certs/{{ music_domain }}/fullchain.pem";
ssl_certificate_key "/var/lib/dehydrated/certs/{{ music_domain }}/privkey.pem";
{% endif %}
{% for range in trusted_ranges %}
allow {{ range.cidr }};
{% endfor %}
deny all;
location / {
rewrite ^/(.*) https://{{ music_domain }}/trollibox/player/space?;
}
location /trollibox/ {
proxy_pass http://[::1]:3000/;
client_max_body_size 512M;
include proxy_params;
}
location ~ ^/trollibox/(.+/events)$ {
proxy_pass http://[::1]:3000/$1;
include proxy_params;
proxy_http_version 1.1;
chunked_transfer_encoding off;
add_header X-Test "123";
proxy_set_header Connection '';
proxy_buffering off;
proxy_read_timeout 7d;
}
location ~ ^/trollibox/(.+/listen)$ {
proxy_pass http://[::1]:3000/$1;
include proxy_params;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_read_timeout 7d;
}
location /bobdsp/ {
proxy_pass http://[::1]:8081/;
include proxy_params;
}
location /vis/ {
allow all;
proxy_pass http://[::1]:13378/;
include proxy_params;
}
location = /vis/ {
rewrite ^(.*)$ /vis/index.html;
include proxy_params;
}
include "snippets/acme.conf";
}

View file

@ -1,49 +0,0 @@
# {{ ansible_managed }}
context.modules = [
{
name = libpipewire-module-filter-chain
args = {
node.description = "bitvis-mixer"
media.name = "bitvis-mixer"
filter.graph = {
nodes = [
{
name = normalize
type = ladspa
plugin = fast_lookahead_limiter_1913
label = fastLookaheadLimiter
control = {
"Input gain (dB)" = 40
"Limit (dB)" = 0
"Release time (s)" = 1
}
}
{
name = mono
type = builtin
label = mixer
}
]
links = [
{ output = "normalize:Output 1", input = "mono:In 1" }
{ output = "normalize:Output 2", input = "mono:In 2" }
]
inputs = [ "normalize:Input 1" "normalize:Input 2" ]
outputs = [ "mono:Out" ]
}
capture.props = {
node.name = "mix_input.bitvis"
audio.position = [ FL FR ]
media.class = "Audio/Sink"
}
playback.props = {
node.name = "mix_output.bitvis"
audio.position = [ FL ]
stream.dont-remix = true
node.passive = true
node.autoconnect = false
}
}
}
]

View file

@ -0,0 +1,17 @@
# {{ ansible_managed }}
[Unit]
Description=MPD Skipbutton
After=network.target
Requires=mpd.service
[Service]
Type=simple
Restart=always
RestartSec=10s
ExecStart=/opt/skipbutton/skipbutton.py /dev/ttyS0
DynamicUser=true
Group=dialout
[Install]
WantedBy=multi-user.target

View file

@ -6,11 +6,12 @@ After=network.target
[Service]
Type=simple
ExecStart=/lib/python3/dist-packages/mqtt-soundboard.py /etc/mqtt-soundboard.yaml
ExecStart=/opt/soundboard/.venv/bin/python /opt/soundboard/soundboard.py /etc/soundboard.yaml
Restart=always
RestartSec=10
User=root
Environment="XDG_RUNTIME_DIR=/run/user/{{ music_audio_user_id }}"
User=audio
LimitMEMLOCK=infinity
LimitRTPRIO=99
[Install]
WantedBy=multi-user.target

View file

@ -1,13 +1,13 @@
# {{ ansible_managed }}
loglevel: DEBUG
loglevel: INFO
mqtt:
host: {{ mqtt_internal_host }}
sounds:
directory: /opt/sounds
play_cmd: "pw-jack mplayer -volume 20 -ao jack:name=MPlayer %s"
play_cmd: "mplayer -volume 10 -ao jack:name=MPlayer %s"
topic: bitlair/soundboard
aliases:

View file

@ -10,7 +10,8 @@ Type=simple
Restart=always
RestartSec=2s
ExecStart=/usr/local/bin/trollibox -conf /etc/trollibox.yaml
User={{ music_trollibox_user }}
User={{ music_audio_user }}
Group={{ music_audio_user }}
[Install]
WantedBy=multi-user.target

View file

@ -2,24 +2,30 @@
- ansible.builtin.import_tasks:
file: ../../common/handlers/main.yaml
- name: Restart ircbot
ansible.builtin.systemd:
name: ircbot
state: restarted
daemon_reload: true
- name: restart discord-bot
ansible.builtin.systemd:
name: discord-bot
state: restarted
daemon_reload: true
- name: restart irc-bot
- name: Restart irc-bot
ansible.builtin.systemd:
name: irc-bot
state: restarted
daemon_reload: true
- name: Restart irc-photos
ansible.builtin.systemd:
name: irc-photos
state: restarted
daemon_reload: true
- name: Restart irc-doorduino
ansible.builtin.systemd:
name: irc-doorduino
state: restarted
daemon_reload: true
- name: Restart discord-bot
ansible.builtin.systemd:
name: discord-bot
state: restarted
daemon_reload: true
- name: Restart siahsd
ansible.builtin.systemd:
name: siahsd

View file

@ -3,58 +3,39 @@
- name: Install dependencies
ansible.builtin.apt:
name:
- openscad
- python3-paho-mqtt
- python3-tz
- virtualenv
- name: Create virtualenv
ansible.builtin.command:
cmd: virtualenv /var/lib/discord-bot/.venv
cmd: virtualenv /opt/miflora_exporter/.venv
args:
creates: /var/lib/discord-bot/.venv
- name: Clone bottleclip source
ansible.builtin.git:
repo: https://git.bitlair.nl/bitlair/bottle-clip.git
version: main
dest: /var/lib/bottle-clip
accept_hostkey: yes
- name: Install Python dependencies
ansible.builtin.shell:
cmd: . .venv/bin/activate && pip install -r requirements.txt
args:
chdir: /var/lib/discord-bot
- name: Clone discord-bot source
- name: Clone source
ansible.builtin.git:
repo: https://git.bitlair.nl/bitlair/discord-bot.git
version: main
dest: /var/lib/discord-bot
accept_hostkey: yes
notify:
- restart discord-bot
- restart irc-bot
notify: Restart discord-bot
ignore_errors: true
- name: Install Python dependencies
ansible.builtin.shell:
cmd: . .venv/bin/activate && pip install -e .
args:
chdir: /var/lib/discord-bot
notify:
- restart discord-bot
- restart irc-bot
- name: Install discord-bot service file
- name: Install service file
ansible.builtin.template:
src: discord-bot.service
dest: /etc/systemd/system/discord-bot.service
owner: root
group: root
mode: "0644"
notify: restart discord-bot
- name: Install irc-bot service file
ansible.builtin.template:
src: irc-bot.service
dest: /etc/systemd/system/irc-bot.service
owner: root
group: root
mode: "0644"
notify: restart irc-bot
notify: Restart discord-bot
- name: Start discord-bot
ansible.builtin.systemd:
@ -62,10 +43,3 @@
state: started
enabled: true
daemon_reload: true
- name: Start irc-bot
ansible.builtin.systemd:
name: irc-bot
state: started
enabled: true
daemon_reload: true

View file

@ -1,12 +1,12 @@
---
- name: Clone source
ansible.builtin.git:
repo: https://git.bitlair.nl/bitlair/irc-bot.git
version: main
repo: https://github.com/bitlair/irc-bot.git
version: master
dest: /var/lib/irc-bot
accept_hostkey: yes
ignore_errors: true
notify: Restart ircbot
notify: Restart irc-bot
- name: Link irc-say
ansible.builtin.file:
@ -17,18 +17,81 @@
- name: Install service file
ansible.builtin.template:
src: generic.service
dest: /etc/systemd/system/ircbot.service
dest: /etc/systemd/system/irc-bot.service
owner: root
group: root
mode: 0644
vars:
description: Bitlair IRC bot
exec: /bin/bash /var/lib/irc-bot/irc-bot
notify: Restart ircbot
notify: Restart irc-bot
- name: Start ircbot
- name: Start irc-bot
ansible.builtin.systemd:
name: ircbot
name: irc-bot
state: started
enabled: true
daemon_reload: true
- name: Create helpers dir
ansible.builtin.file:
path: /var/lib/irc-helpers
state: directory
- name: Install photos notification
ansible.builtin.template:
src: irc-photos.sh
dest: /var/lib/irc-helpers/photos.sh
owner: root
group: root
mode: 0755
notify: Restart irc-photos
- name: Install photos notification service
ansible.builtin.template:
src: generic.service
dest: /etc/systemd/system/irc-photos.service
owner: root
group: root
mode: 0644
vars:
description: Bitlair IRC photos notification
requires: irc-bot.service
exec: /bin/bash /var/lib/irc-helpers/photos.sh
notify: Restart irc-photos
- name: Start irc-photos
ansible.builtin.systemd:
name: irc-photos
state: started
enabled: true
daemon_reload: true
- name: Install doorduino notification
ansible.builtin.template:
src: irc-doorduino.sh
dest: /var/lib/irc-helpers/doorduino.sh
owner: root
group: root
mode: 0755
notify: Restart irc-doorduino
- name: Install doorduino notification service
ansible.builtin.template:
src: generic.service
dest: /etc/systemd/system/irc-doorduino.service
owner: root
group: root
mode: 0644
vars:
description: Bitlair IRC doorduino notification
requires: irc-bot.service
exec: /bin/bash /var/lib/irc-helpers/doorduino.sh
notify: Restart irc-doorduino
- name: Start irc-doorduino
ansible.builtin.systemd:
name: irc-doorduino
state: started
enabled: true
daemon_reload: true

View file

@ -1,24 +1,16 @@
---
- name: Install siahsd
apt:
name:
- debianutils
- siahsd
# TODO: Install and build
- name: Clone alarm-handlers
ansible.builtin.git:
repo: https://git.bitlair.nl/bitlair/alarm-handlers.git
version: main
dest: /opt/alarm
accept_hostkey: yes
- name: Create log directory
- name: Create directories
ansible.builtin.file:
path: /var/log/siahsd
path: "{{ item }}"
state: directory
owner: siahsd
group: nogroup
mode: "0750"
with_items:
- /var/log/siahsd
- /var/lib/siahsd
- name: Install config file
ansible.builtin.template:
@ -29,9 +21,19 @@
mode: "0644"
notify: Restart siahsd
- name: Install service file
ansible.builtin.template:
src: siahsd.service
dest: /etc/systemd/system/siahsd.service
owner: root
group: root
mode: "0644"
notify: Restart siahsd
- name: Start siahsd
ansible.builtin.systemd:
name: siahsd
state: started
enabled: true
daemon_reload: true

View file

@ -1,17 +1,16 @@
# {{ ansible_managed }}
# Managed by Ansible
[Unit]
Description=Bitlair Discord Bot
Description=HobbyBot
After=network.target
[Service]
Type=simple
Restart=always
Restart=on-failure
RestartSec=10s
ExecStart=/var/lib/discord-bot/.venv/bin/python /var/lib/discord-bot/discordbot.py
ExecStart=/var/lib/discord-bot/.venv/bin/python /var/lib/discord-bot/main.py
DynamicUser=true
Environment="MQTT_HOST={{ mqtt_internal_host }}"
Environment="BOTTLECLIP_RESOURCES=/var/lib/bottle-clip"
Environment="DISCORD_WEBHOOK_URL={{ lookup('passwordstore', 'services/discord', subkey='webhook_url') }}"
Environment="DISCORD_TOKEN={{ lookup('passwordstore', 'services/discord', subkey='token') }}"

View file

@ -1,20 +0,0 @@
# {{ ansible_managed }}
[Unit]
Description=Bitlair IRC Bot
After=network.target
[Service]
Type=simple
Restart=always
RestartSec=10s
ExecStart=/var/lib/discord-bot/.venv/bin/python /var/lib/discord-bot/ircbot.py
DynamicUser=true
Environment="MQTT_HOST={{ mqtt_internal_host }}"
Environment="BOTTLECLIP_RESOURCES=/var/lib/bottle-clip"
Environment="IRC_SERVER=irc.smurfnet.ch"
Environment="IRC_CHANNEL=#bitlair"
Environment="IRC_NICK=bitlair"
[Install]
WantedBy=multi-user.target

View file

@ -0,0 +1,24 @@
#!/bin/bash
# Managed by Ansible
set -eu
set -o pipefail
initial=1
mqtt-simple -h {{ mqtt_internal_host }} -t "bitlair/doorduino/+" |
while read line; do
topic=$(echo "$line" | cut -d' ' -f1 | sed "s/bitlair\/doorduino\///")
value=$(echo "$line" | cut -s -d' ' -f2-)
if [ $initial == 0 ] && [ $value != 0 ]; then
if [ $topic == "doorbell" ]; then
irc-say "DEURBEL! Open de deur beneden!"
elif [ $topic != "dooropen" ]; then
irc-say "Doorduino: $topic $value"
fi
fi
initial=0
done

View file

@ -0,0 +1,13 @@
#!/bin/bash
# Managed by Ansible
set -eu
set -o pipefail
mqtt-simple -h {{ mqtt_internal_host }} -s "bitlair/photos" |
while read event; do
path=$(echo $event | cut -d ' ' -f 2)
url="https://bitlair.nl/fotos/view/$path"
irc-say "WIP: $url"
done

View file

@ -1,5 +1,3 @@
# {{ ansible_managed }}
[siahsd]
pid file = /var/lib/siahsd/siahsd.pid
log file = /var/log/siahsd/siahsd.log
@ -7,6 +5,13 @@ log level = 3
foreground = 0
event handlers = script
#[database]
#driver = mysql
#host = localhost
#name = siahsd
#username = siahsd
#password = MysbJxAaawmwKPqD
[siahs]
port = 4000
@ -14,5 +19,21 @@ port = 4000
port = 9000
rsa key file = something.sexp
#[jsonbot]
#address = 192.168.88.15
#port = 5500
#aes key = blablablablablaz
#password = mekker
#privmsg to = #bitlair
#[spacestate]
#driver = mysql
#host = localhost
#name = bitwifi
#username = bitwifi
#password = aGWERQpLEQPUaXJV
#open script = /opt/alarm/disarmed.sh
#close script = /opt/alarm/armed.sh
[script]
path = /opt/alarm/siahsd_handler.sh

View file

@ -0,0 +1,17 @@
# Managed by Ansible
[Unit]
Description=Siahsd
After=network.target
[Service]
Type=forking
PIDFile=/var/lib/siahsd/siahsd.pid
Restart=always
RestartSec=10s
ExecStartPre=-/bin/rm /var/lib/siahsd/siahsd.pid
ExecStart=/usr/local/src/siahsd/build/siahsd
User=siahsd
[Install]
WantedBy=multi-user.target

View file

@ -0,0 +1,3 @@
{
"m.server": "matrix.bitlair.nl"
}

View file

@ -119,6 +119,13 @@ server {
rewrite ^/Pages/(.*) https://$server_name/$1$args redirect;
}
# Matrix realm delegation
location = /.well-known/matrix/server {
add_header "Content-Type" "application/json";
add_header "Access-Control-Allow-Origin" "*";
alias /opt/matrix-delegation.json;
}
location = /.well-known/security.txt {
alias /opt/security.txt;
}

View file

@ -3,5 +3,4 @@
- hosts: services
roles:
- { role: "common", tags: [ "common" ] }
- { role: "deb_forgejo", tags: [ "deb_forgejo" ] }
- { role: "services", tags: [ "services" ] }

View file

@ -1,44 +0,0 @@
{% for range in trusted_ranges %}
allow {{ range.cidr }};
{% endfor %}
deny all;
location / {
rewrite ^/(.*) https://{{ music_domain }}/trollibox/player/space?;
}
location /trollibox/ {
proxy_pass http://[::1]:3000/;
include proxy_params;
}
location ~ ^/trollibox/(.+/events)$ {
proxy_pass http://[::1]:3000/$1;
include proxy_params;
proxy_http_version 1.1;
chunked_transfer_encoding off;
add_header X-Test "123";
proxy_set_header Connection '';
proxy_buffering off;
proxy_read_timeout 7d;
}
location ~ ^/trollibox/(.+/listen)$ {
proxy_pass http://[::1]:3000/$1;
include proxy_params;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_read_timeout 7d;
}
location /vis/ {
allow all;
proxy_pass http://[::1]:13378/;
include proxy_params;
}
location = /vis/ {
rewrite ^(.*)$ /vis/index.html;
include proxy_params;
}

View file

@ -1,4 +1,4 @@
root /opt/mediawiki-1.43.0/;
root /opt/mediawiki-1.41.1/;
index index.php index.html index.htm;
# Photo gallery
@ -78,6 +78,13 @@ location /Pages/ {
rewrite ^/Pages/(.*) https://$server_name/$1$args redirect;
}
# Matrix realm delegation
location = /.well-known/matrix/server {
add_header "Content-Type" "application/json";
add_header "Access-Control-Allow-Origin" "*";
alias /opt/matrix-delegation.json;
}
location = /.well-known/security.txt {
alias /opt/security.txt;
}