r3status mostly done
authorChristian Pointner <equinox@realraum.at>
Sun, 7 Jul 2019 00:11:43 +0000 (02:11 +0200)
committerBernhard Tittelbach <bernhard@tittelbach.org>
Wed, 23 Jul 2025 00:23:28 +0000 (02:23 +0200)
ansible/host_playbooks/vex2.yml
ansible/host_vars/vex2/dokuwiki.yml [new file with mode: 0644]
ansible/host_vars/vex2/main.yml
ansible/roles/web/dokuwiki/tasks/nginx.yml
ansible/roles/web/r3status/defaults/main.yml [new file with mode: 0644]
ansible/roles/web/r3status/handlers/main.yml [new file with mode: 0644]
ansible/roles/web/r3status/tasks/main.yml [new file with mode: 0644]
ansible/roles/web/r3status/templates/nginx.j2 [new file with mode: 0644]
ansible/roles/web/r3status/templates/ssh-spaceapi-update.py.j2 [new file with mode: 0644]

index 655b8cb..91649f6 100644 (file)
@@ -7,3 +7,4 @@
   - role: acmetool/base
   - role: nginx
   - role: web/dokuwiki
+  - role: web/r3status
diff --git a/ansible/host_vars/vex2/dokuwiki.yml b/ansible/host_vars/vex2/dokuwiki.yml
new file mode 100644 (file)
index 0000000..2d2b18d
--- /dev/null
@@ -0,0 +1,40 @@
+---
+dokuwiki_urls:
+  - wiki2.realraum.at
+
+dokuwiki_plugins:
+  diagram:
+    url: 'http://nikita.melnichenko.name/download.php?q=dokuwiki-diagram-latest.tgz'
+    sha256: '6485df5eead8a99054fba007a7213d2aeea556b38ccc430586501f712799bcf6'
+  discussion:
+    url: 'https://github.com/dokufreaks/plugin-discussion/archive/5da9673dc41762074e50821627210707fdc6cd62.tar.gz'
+    sha256: '49918e5a0f04598c2544015a601e691c41dc9c0b004592e09932def19c6c83fb'
+  fontawesome:
+    url: 'https://github.com/mmedvede/dokuwiki-plugin-fontawesome/archive/7856ea2c5b2edc90ea6c2a831270e246d50f4519.tar.gz'
+    sha256: 'abeb9f39c8eee2116cb866d57dc8325d904dba497062d81b6576c726c8004fc5'
+  move:
+    url: 'https://github.com/michitux/dokuwiki-plugin-move/archive/80ab123f1c08eabbcae1a6e7bdd42dc4dada14f7.tar.gz'
+    sha256: 'fc151ed43c8e50a29ccde8ec2dc9141a7af2ee772340f5220260e646e258572a'
+  multiorphan:
+    url: 'https://github.com/i-net-software/dokuwiki-plugin-multiorphan/archive/2019-01-09.tar.gz'
+    sha256: '09b447f180654051ba81e378729edc031afc737d0eaa1bd09cdab7728e4afb98'
+  pagelist:
+    url: 'https://github.com/dokufreaks/plugin-pagelist/archive/de0bfb83d573b905ffdd050b535515aad77825dc.tar.gz'
+    sha256: '9596e851e3dfc19d7a41c6ee0794f4b42511660fc98e8723b23f58c0d4622018'
+  tag:
+    url: 'https://github.com/dokufreaks/plugin-tag/archive/0a247c7422fdaf54a89a84b9896981f515303350.tar.gz'
+    sha256: 'dda89afc681db2d03555dad6aacec5afbc06b0c05dfa95998bf7af94a2c2e0ec'
+  wrap:
+    url: 'https://github.com/selfthinker/dokuwiki_plugin_wrap/archive/9ad5fdffdf97087aef0399a82b24053bf58e4298.tar.gz'
+    sha256: '6a1c68b50208fe91bfe2be7ceca735bb45792186e4f07496897769bc82a8be76'
+  include:
+    url: 'https://github.com/dokufreaks/plugin-include/archive/511629d847c1674773a78a880df65b922b44ff7a.tar.gz'
+    sha256: '71e567bc9e2196e42e6089e3c4a1b184cfbf2023ee7e08bb0204e971ab023c57'
+  markdownextra:
+    url: 'https://github.com/naokij/dokuwiki-plugin-markdownextra/archive/6c8bd4029e821219bcb7f7165ad37680c578521e.tar.gz'
+    sha256: '2e8cae229a96f6def547cefb4d0a1c88289b845a04f9da39e7d66d9b2ecd9495'
+
+dokuwiki_templates:
+  bootstrap3:
+    url: 'https://github.com/LotarProject/dokuwiki-template-bootstrap3/archive/v2019-05-22.tar.gz'
+    sha256: 'c54e093d84d88f9c35be9e891362ff49cb630c61b9339d8c1eba9ea7cd3850e8'
index 2d2b18d..aca1996 100644 (file)
@@ -1,40 +1,5 @@
 ---
-dokuwiki_urls:
-  - wiki2.realraum.at
+sshd_allowusers_host:
+  - spaceapi
 
-dokuwiki_plugins:
-  diagram:
-    url: 'http://nikita.melnichenko.name/download.php?q=dokuwiki-diagram-latest.tgz'
-    sha256: '6485df5eead8a99054fba007a7213d2aeea556b38ccc430586501f712799bcf6'
-  discussion:
-    url: 'https://github.com/dokufreaks/plugin-discussion/archive/5da9673dc41762074e50821627210707fdc6cd62.tar.gz'
-    sha256: '49918e5a0f04598c2544015a601e691c41dc9c0b004592e09932def19c6c83fb'
-  fontawesome:
-    url: 'https://github.com/mmedvede/dokuwiki-plugin-fontawesome/archive/7856ea2c5b2edc90ea6c2a831270e246d50f4519.tar.gz'
-    sha256: 'abeb9f39c8eee2116cb866d57dc8325d904dba497062d81b6576c726c8004fc5'
-  move:
-    url: 'https://github.com/michitux/dokuwiki-plugin-move/archive/80ab123f1c08eabbcae1a6e7bdd42dc4dada14f7.tar.gz'
-    sha256: 'fc151ed43c8e50a29ccde8ec2dc9141a7af2ee772340f5220260e646e258572a'
-  multiorphan:
-    url: 'https://github.com/i-net-software/dokuwiki-plugin-multiorphan/archive/2019-01-09.tar.gz'
-    sha256: '09b447f180654051ba81e378729edc031afc737d0eaa1bd09cdab7728e4afb98'
-  pagelist:
-    url: 'https://github.com/dokufreaks/plugin-pagelist/archive/de0bfb83d573b905ffdd050b535515aad77825dc.tar.gz'
-    sha256: '9596e851e3dfc19d7a41c6ee0794f4b42511660fc98e8723b23f58c0d4622018'
-  tag:
-    url: 'https://github.com/dokufreaks/plugin-tag/archive/0a247c7422fdaf54a89a84b9896981f515303350.tar.gz'
-    sha256: 'dda89afc681db2d03555dad6aacec5afbc06b0c05dfa95998bf7af94a2c2e0ec'
-  wrap:
-    url: 'https://github.com/selfthinker/dokuwiki_plugin_wrap/archive/9ad5fdffdf97087aef0399a82b24053bf58e4298.tar.gz'
-    sha256: '6a1c68b50208fe91bfe2be7ceca735bb45792186e4f07496897769bc82a8be76'
-  include:
-    url: 'https://github.com/dokufreaks/plugin-include/archive/511629d847c1674773a78a880df65b922b44ff7a.tar.gz'
-    sha256: '71e567bc9e2196e42e6089e3c4a1b184cfbf2023ee7e08bb0204e971ab023c57'
-  markdownextra:
-    url: 'https://github.com/naokij/dokuwiki-plugin-markdownextra/archive/6c8bd4029e821219bcb7f7165ad37680c578521e.tar.gz'
-    sha256: '2e8cae229a96f6def547cefb4d0a1c88289b845a04f9da39e7d66d9b2ecd9495'
-
-dokuwiki_templates:
-  bootstrap3:
-    url: 'https://github.com/LotarProject/dokuwiki-template-bootstrap3/archive/v2019-05-22.tar.gz'
-    sha256: 'c54e093d84d88f9c35be9e891362ff49cb630c61b9339d8c1eba9ea7cd3850e8'
+r3status_spaceapi_update_user_ssh_key: ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDcwqg/oohCV3sTFHODBPUViOaGsoKL2Vp5suNAdLFJz4pdhfH7n4eXzI/3Ork6mDrDZ8XNmDq9g6jERweWQmS37THL33N2RmyDFfpwyQog/pzvEB6U0BGE6VN2zmgmrmvVZNdhKh/E74dM/22abAt32I6xSJi8C2CfVshHaFzNAV8N4lmGMGi0QXNMkAZDaYG0iptRuZOoZarCkfRybyh8pFkHt4Hl/tWocMOihI1KsWtbIgRUdTTpGMXmxMd0k2t9am+NxiUlBIRE8aEc4nTqcZTqullddEAGoksuUCLc0yYbFCzpTkZ1lrU5+oQhZyPWgnJ7s2yK7M2luBSAle8T realraum@smsgw.realraum.at
index 940ea17..418228b 100644 (file)
@@ -5,13 +5,6 @@
     dest: "/etc/nginx/sites-available/{{ dokuwiki_urls[0] }}"
   notify: reload nginx
 
-- name: eanble nginx vhost config
-  file:
-    src: "../sites-available/{{ dokuwiki_urls[0] }}"
-    dest: "/etc/nginx/sites-enabled/{{ dokuwiki_urls[0] }}"
-    state: link
-  notify: reload nginx
-
 - name: check if acme certs already exists
   stat:
     path: "/var/lib/acme/live/{{ item }}"
@@ -47,6 +40,7 @@
     src: "../sites-available/{{ dokuwiki_urls[0] }}"
     dest: "/etc/nginx/sites-enabled/{{ dokuwiki_urls[0] }}"
     state: link
+  notify: reload nginx
 
 - name: make sure nginx config has been loaded
   meta: flush_handlers
diff --git a/ansible/roles/web/r3status/defaults/main.yml b/ansible/roles/web/r3status/defaults/main.yml
new file mode 100644 (file)
index 0000000..ed8bd03
--- /dev/null
@@ -0,0 +1,2 @@
+---
+r3status_spaceapi_path: /dev/shm/spaceapi
diff --git a/ansible/roles/web/r3status/handlers/main.yml b/ansible/roles/web/r3status/handlers/main.yml
new file mode 100644 (file)
index 0000000..d4e42ca
--- /dev/null
@@ -0,0 +1,5 @@
+---
+- name: reload nginx
+  service:
+    name: nginx
+    state: reloaded
diff --git a/ansible/roles/web/r3status/tasks/main.yml b/ansible/roles/web/r3status/tasks/main.yml
new file mode 100644 (file)
index 0000000..0e717e2
--- /dev/null
@@ -0,0 +1,85 @@
+---
+- name: create spaceapi service user
+  user:
+    name: spaceapi
+    home: /srv/r3status/spaceapi
+    system: yes
+    shell: /bin/sh
+
+- name: install spaceapi update script
+  template:
+    src: ssh-spaceapi-update.py.j2
+    dest: /usr/local/bin/ssh-spaceapi-update.py
+    mode: 0755
+
+- name: create spaceapi user ssh config directory
+  file:
+    path: /srv/r3status/spaceapi/.ssh
+    state: directory
+    mode: 0750
+    owner: root
+    group: spaceapi
+
+- name: install ssh key for spaceapi update
+  copy:
+    dest: /srv/r3status/spaceapi/.ssh/authorized_keys
+    mode: 0640
+    owner: root
+    group: spaceapi
+    content: |
+      no-agent-forwarding,no-port-forwarding,no-pty,no-X11-forwarding,no-user-rc,command="/usr/local/bin/ssh-spaceapi-update.py" {{ r3status_spaceapi_update_user_ssh_key }}
+
+
+- name: create status web-root directory
+  file:
+    path: /srv/r3status/www
+    state: directory
+
+# TODO: install tar.gz from https://github.com/realraum/infokiosk/tree/master/htdocs
+
+
+- name: install nginx vhost config
+  template:
+    src: nginx.j2
+    dest: /etc/nginx/sites-available/status.realraum.at
+  notify: reload nginx
+
+- name: check if acme certs already exists
+  stat:
+    path: /var/lib/acme/live/status.realraum.at
+  register: r3status_acme_cert
+
+- name: link nonexistent hostname to self-signed interim cert
+  when: r3status_acme_cert.stat.exists == false
+  block:
+    - name: get id of existing selfsigned interim certificate
+      command: cat /var/lib/acme/.selfsigned-interim-cert
+      changed_when: false
+      check_mode: false
+      register: selfsigned_interim_cert_id
+
+    - name: set selfsigned_interim_cert_id variable
+      set_fact:
+        selfsigned_interim_cert_id: "{{ selfsigned_interim_cert_id.stdout }}"
+
+    - name: link to snakeoil cert for nonexistent hostnames
+      file:
+        src: "../certs/{{ selfsigned_interim_cert_id }}"
+        dest: /var/lib/acme/live/status.realraum.at
+        state: link
+
+- name: enable nginx vhost config
+  file:
+    src: ../sites-available/status.realraum.at
+    dest: /etc/nginx/sites-enabled/status.realraum.at
+    state: link
+  notify: reload nginx
+
+- name: make sure nginx config has been loaded
+  meta: flush_handlers
+
+- name: get certificate using acmetool
+  import_role:
+    name: acmetool/cert
+  vars:
+    acmetool_cert_name: status.realraum.at
diff --git a/ansible/roles/web/r3status/templates/nginx.j2 b/ansible/roles/web/r3status/templates/nginx.j2
new file mode 100644 (file)
index 0000000..c0d6fb7
--- /dev/null
@@ -0,0 +1,20 @@
+server {
+    listen [::]:443 ssl;
+    listen 443 ssl;
+
+    server_name status.realraum.at;
+
+    include snippets/acmetool.conf;
+    include snippets/ssl.conf;
+    ssl_certificate /var/lib/acme/live/status.realraum.at/fullchain;
+    ssl_certificate_key /var/lib/acme/live/status.realraum.at/privkey;
+    include snippets/hsts.conf;
+
+    include snippets/security-headers.conf;
+
+    root /srv/r3status;
+
+    location = /spaceapi.json {
+        alias {{ r3status_spaceapi_path }}/spaceapi.json;
+    }
+}
diff --git a/ansible/roles/web/r3status/templates/ssh-spaceapi-update.py.j2 b/ansible/roles/web/r3status/templates/ssh-spaceapi-update.py.j2
new file mode 100644 (file)
index 0000000..a7332a4
--- /dev/null
@@ -0,0 +1,64 @@
+#!/usr/bin/python3
+# (c) Bernhard Tittelbach, 2019
+
+import json
+import sys
+import os
+import shutil
+
+env_ssh_original_command_ = "SSH_ORIGINAL_COMMAND"
+spaceapi_status_dst_filepath_ = "{{ r3status_spaceapi_path }}/spaceapi.json"
+spaceapi_status_tmp_filepath_ = "{{ r3status_spaceapi_path }}/spaceapi.json.tmp"
+
+
+def ensureParentDirExists(filename):
+    dn = os.path.dirname(spaceapi_status_tmp_filepath_)
+    if not os.path.exists(dn):
+        os.makedirs(dn)
+
+
+def cmd_get():
+    try:
+        with open(spaceapi_status_dst_filepath_, "r") as fh:
+            print(fh.read())
+    except Exception as e:
+        print(e)
+        sys.exit(0)
+
+
+def cmd_set():
+    spacestatus = ""
+    try:
+        spacestatus = json.load(sys.stdin)
+    except Exception as e:
+        print("ERROR:", e)
+        sys.exit(0)
+
+    ensureParentDirExists(spaceapi_status_tmp_filepath_)
+    with open(spaceapi_status_tmp_filepath_, "w") as fh:
+        fh.write(json.dumps(spacestatus))
+
+    ensureParentDirExists(spaceapi_status_dst_filepath_)
+    shutil.move(spaceapi_status_tmp_filepath_, spaceapi_status_dst_filepath_)
+
+
+def helpexit():
+    print("Valid commands: get | set")
+    sys.exit(1)
+
+
+def main():
+    if not env_ssh_original_command_ in os.environ:
+        helpexit()
+
+    command = os.environ[env_ssh_original_command_].split(" ")[0]
+    commandset_dict = {"get": cmd_get, "set": cmd_set}
+
+    if command in commandset_dict:
+        commandset_dict[command]()
+    else:
+        helpexit()
+
+
+if __name__ == '__main__':
+    main()