From 2bee74ca6e87ce5892dc13d31158c5db63019382 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Aur=C3=A9lien=20Bompard?= Date: Tue, 9 Jul 2024 16:00:47 +0200 Subject: [PATCH] Fix the Vagrant environment MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Aurélien Bompard --- .gitignore | 1 + Vagrantfile | 16 +++---- devel/ansible/playbook.yml | 10 ++-- devel/ansible/roles/dev/files/config.toml | 33 +++++++++++++ devel/ansible/roles/dev/files/w2fm.service | 23 +++++++++ devel/ansible/roles/dev/tasks/main.yml | 47 ++++++++++++++++--- .../ansible/roles/gss-proxy/defaults/main.yml | 5 ++ devel/ansible/roles/gss-proxy/tasks/main.yml | 27 +++++++++++ .../roles/gss-proxy/templates/gssproxy.conf | 12 +++++ .../roles/ipa-keytab/defaults/main.yml | 9 ++++ devel/ansible/roles/ipa-keytab/tasks/main.yml | 34 ++++++++++++++ .../endpoints/__init__.py | 0 webhook_to_fedora_messaging/endpoints/util.py | 29 ------------ 13 files changed, 197 insertions(+), 49 deletions(-) create mode 100644 devel/ansible/roles/dev/files/config.toml create mode 100644 devel/ansible/roles/dev/files/w2fm.service create mode 100644 devel/ansible/roles/gss-proxy/defaults/main.yml create mode 100644 devel/ansible/roles/gss-proxy/tasks/main.yml create mode 100644 devel/ansible/roles/gss-proxy/templates/gssproxy.conf create mode 100644 devel/ansible/roles/ipa-keytab/defaults/main.yml create mode 100644 devel/ansible/roles/ipa-keytab/tasks/main.yml delete mode 100644 webhook_to_fedora_messaging/endpoints/__init__.py delete mode 100644 webhook_to_fedora_messaging/endpoints/util.py diff --git a/.gitignore b/.gitignore index 4dc0601..e66f6a9 100644 --- a/.gitignore +++ b/.gitignore @@ -128,6 +128,7 @@ venv/ ENV/ env.bak/ venv.bak/ +.vagrant # Spyder project settings .spyderproject diff --git a/Vagrantfile b/Vagrantfile index 80c126f..5cc1943 100644 --- a/Vagrantfile +++ b/Vagrantfile @@ -6,21 +6,21 @@ Vagrant.configure(2) do |config| config.hostmanager.manage_host = true config.hostmanager.manage_guest = true - config.vm.define "webhook-to-fedora-messaging" do |webhook-to-fedora-messaging| - webhook-to-fedora-messaging.vm.box_url = "https://download.fedoraproject.org/pub/fedora/linux/releases/40/Cloud/x86_64/images/Fedora-Cloud-Base-Vagrant-libvirt.x86_64-40-1.14.vagrant.libvirt.box" - webhook-to-fedora-messaging.vm.box = "f38-cloud-libvirt" - webhook-to-fedora-messaging.vm.hostname = "webhook-to-fedora-messaging.tinystage.test" + config.vm.define "w2fm" do |w2fm| + w2fm.vm.box_url = "https://download.fedoraproject.org/pub/fedora/linux/releases/40/Cloud/x86_64/images/Fedora-Cloud-Base-Vagrant-libvirt.x86_64-40-1.14.vagrant.libvirt.box" + w2fm.vm.box = "f40-cloud-libvirt" + w2fm.vm.hostname = "w2fm.tinystage.test" - webhook-to-fedora-messaging.vm.synced_folder '.', '/vagrant', disabled: true - webhook-to-fedora-messaging.vm.synced_folder ".", "/home/vagrant/webhook-to-fedora-messaging", type: "sshfs" + w2fm.vm.synced_folder '.', '/vagrant', disabled: true + w2fm.vm.synced_folder ".", "/home/vagrant/webhook-to-fedora-messaging", type: "sshfs" - webhook-to-fedora-messaging.vm.provider :libvirt do |libvirt| + w2fm.vm.provider :libvirt do |libvirt| libvirt.cpus = 2 libvirt.memory = 2048 end - webhook-to-fedora-messaging.vm.provision "ansible" do |ansible| + w2fm.vm.provision "ansible" do |ansible| ansible.playbook = "devel/ansible/playbook.yml" ansible.config_file = "devel/ansible/ansible.cfg" ansible.verbose = true diff --git a/devel/ansible/playbook.yml b/devel/ansible/playbook.yml index 0b7a31b..449b588 100644 --- a/devel/ansible/playbook.yml +++ b/devel/ansible/playbook.yml @@ -4,16 +4,16 @@ become_method: sudo vars: - name: webhook-to-fedora-messaging + app_name: webhook-to-fedora-messaging pkg_name: webhook_to_fedora_messaging ipa_admin_user: admin ipa_admin_password: password krb_realm: TINYSTAGE.TEST + cert_owner: vagrant roles: - core - # If you need Tinystage: - # - ipa-client - # If you need a TLS cert from Tinystage: - # - cert + - ipa-client + - cert + - gss-proxy - dev diff --git a/devel/ansible/roles/dev/files/config.toml b/devel/ansible/roles/dev/files/config.toml new file mode 100644 index 0000000..bf00530 --- /dev/null +++ b/devel/ansible/roles/dev/files/config.toml @@ -0,0 +1,33 @@ +[flaskapp] +DEBUG = true +SECRET_KEY = "vagrant-env" +SQLALCHEMY_DATABASE_URI = "sqlite:////home/vagrant/w2fm.db" + + [flaskapp.logsconf] + version = 1 + disable_existing_loggers = false + + [flaskapp.logsconf.handlers] + + [flaskapp.logsconf.handlers.wsgi] + class = "logging.StreamHandler" + stream = "ext://flask.logging.wsgi_errors_stream" + level = "INFO" + formatter = "default" + + [flaskapp.logsconf.formatters] + + [flaskapp.logsconf.formatters.default] + format = "[W2FM] %(asctime)s - %(name)s - %(levelname)s - %(message)s" + datefmt = "[%Y-%m-%d %I:%M:%S %z]" + + [flaskapp.logsconf.root] + handlers = ["wsgi"] + level = "INFO" + + [flaskapp.logsconf.loggers] + + [flaskapp.logsconf.loggers.werkzeug] + handlers = ["wsgi"] + level = "INFO" + propagate = false diff --git a/devel/ansible/roles/dev/files/w2fm.service b/devel/ansible/roles/dev/files/w2fm.service new file mode 100644 index 0000000..fcc22d7 --- /dev/null +++ b/devel/ansible/roles/dev/files/w2fm.service @@ -0,0 +1,23 @@ +# SPDX-FileCopyrightText: Contributors to the Fedora Project +# +# SPDX-License-Identifier: GPL-3.0-or-later + +[Unit] +Description=fmn-api +After=network-online.target +Wants=network-online.target + +[Service] +AmbientCapabilities = CAP_NET_BIND_SERVICE +User=vagrant +Environment=GSS_USE_PROXY=yes +Environment=REQUESTS_CA_BUNDLE=/etc/pki/tls/certs/ca-bundle.crt +Environment=W2FM_APPCONFIG=/home/vagrant/config.toml +Environment=PYTHONUNBUFFERED=1 +Environment=FLASK_DEBUG=1 +Environment=FLASK_APP=webhook_to_fedora_messaging.main +WorkingDirectory=/home/vagrant/webhook-to-fedora-messaging +ExecStart=poetry run flask run --reload -p 443 -h "0.0.0.0" --cert=/etc/pki/tls/certs/server.pem --key=/etc/pki/tls/private/server.key + +[Install] +WantedBy=multi-user.target diff --git a/devel/ansible/roles/dev/tasks/main.yml b/devel/ansible/roles/dev/tasks/main.yml index cca7d8a..ef24139 100644 --- a/devel/ansible/roles/dev/tasks/main.yml +++ b/devel/ansible/roles/dev/tasks/main.yml @@ -8,6 +8,9 @@ - krb5-devel - libpq-devel - gcc + - sqlite3 + - git + - vim state: present - name: install python deps with poetry @@ -15,12 +18,42 @@ become: true become_user: vagrant args: - chdir: /home/vagrant/{{ name }}/ + chdir: /home/vagrant/webhook-to-fedora-messaging -- name: compile the translations - shell: - cmd: poetry run pybabel compile -d /home/vagrant/{{ name }}/{{ pkg_name }}/translations - # "removes" == "only if the file exists" - removes: /home/vagrant/{{ name }}/{{ pkg_name }}/translations/messages.pot - become: true +- name: copy the config files + copy: + src: config.toml + dest: /home/vagrant/config.toml + mode: 0644 + owner: vagrant + group: vagrant + loop: + - tahrir.cfg + +- name: Create or update the database + command: poetry run flask -A webhook_to_fedora_messaging.main db sync + environment: + W2FM_APPCONFIG: /home/vagrant/config.toml + FLASK_DEBUG: 1 + become: yes become_user: vagrant + args: + chdir: /home/vagrant/webhook-to-fedora-messaging + creates: /home/vagrant/w2fm.db + +- name: Install the systemd unit files + copy: + src: "{{ item }}" + dest: /etc/systemd/system/{{ item }} + mode: 0644 + loop: + - w2fm.service + +- name: Enable and start services using systemd + systemd: + name: "{{ item }}" + daemon_reload: yes + enabled: yes + state: started + loop: + - w2fm.service diff --git a/devel/ansible/roles/gss-proxy/defaults/main.yml b/devel/ansible/roles/gss-proxy/defaults/main.yml new file mode 100644 index 0000000..d42dbbc --- /dev/null +++ b/devel/ansible/roles/gss-proxy/defaults/main.yml @@ -0,0 +1,5 @@ +krb_service: HTTP +ipa_admin_user: admin +ipa_admin_password: password +krb_master_password: "{{ ipa_admin_password }}" +krb_realm: TINYSTAGE.TEST diff --git a/devel/ansible/roles/gss-proxy/tasks/main.yml b/devel/ansible/roles/gss-proxy/tasks/main.yml new file mode 100644 index 0000000..accb5d8 --- /dev/null +++ b/devel/ansible/roles/gss-proxy/tasks/main.yml @@ -0,0 +1,27 @@ +--- +- name: Install RPM packages + dnf: + name: + - gssproxy + state: present + +- name: Get the keytab + import_role: + name: ipa-keytab + vars: + keytab_directory: /var/lib/gssproxy + +- name: Copy gssproxy conf + template: + src: gssproxy.conf + dest: /etc/gssproxy/98-{{ krb_service | lower}}.conf + mode: 0644 + owner: root + group: root + +- name: Enable and restart GSSProxy + systemd: + state: restarted + name: gssproxy + enabled: yes + daemon_reload: yes diff --git a/devel/ansible/roles/gss-proxy/templates/gssproxy.conf b/devel/ansible/roles/gss-proxy/templates/gssproxy.conf new file mode 100644 index 0000000..2c4a307 --- /dev/null +++ b/devel/ansible/roles/gss-proxy/templates/gssproxy.conf @@ -0,0 +1,12 @@ +# +# /etc/gssproxy/99-{{ krb_service }}.conf +# + +[service/{{ krb_service | lower }}] + mechs = krb5 + cred_store = keytab:/var/lib/gssproxy/{{ krb_service }}.keytab + cred_store = client_keytab:/var/lib/gssproxy/{{ krb_service }}.keytab + allow_constrained_delegation = true + allow_client_ccache_sync = true + cred_usage = both + euid = vagrant diff --git a/devel/ansible/roles/ipa-keytab/defaults/main.yml b/devel/ansible/roles/ipa-keytab/defaults/main.yml new file mode 100644 index 0000000..00273d6 --- /dev/null +++ b/devel/ansible/roles/ipa-keytab/defaults/main.yml @@ -0,0 +1,9 @@ +krb_service: HTTP +krb_host_fqdn: "{{ ansible_fqdn }}" +keytab_directory: /etc +keytab_path: "{{ keytab_directory }}/{{ krb_service }}.keytab" +keytab_owner: root +keytab_group: root +ipa_admin_user: admin +ipa_admin_password: password +krb_realm: "{{ ansible_domain | upper }}" diff --git a/devel/ansible/roles/ipa-keytab/tasks/main.yml b/devel/ansible/roles/ipa-keytab/tasks/main.yml new file mode 100644 index 0000000..2cc255d --- /dev/null +++ b/devel/ansible/roles/ipa-keytab/tasks/main.yml @@ -0,0 +1,34 @@ +--- +- name: Install RPM packages + dnf: + name: + - krb5-workstation + state: present + +- name: kinit + shell: echo "{{ ipa_admin_password }}" | kinit {{ ipa_admin_user }}@{{ krb_realm }} + +- name: Create the service in IPA + command: ipa service-add --force {{ krb_service | upper }}/{{ krb_host_fqdn }} + register: service_add_result + changed_when: "'Added service' in service_add_result.stdout" + failed_when: "not ('Added service' in service_add_result.stdout or 'already exists' in service_add_result.stderr)" + +- name: Allow the host to manage the virtual service + shell: ipa service-add-host --hosts={{ ansible_fqdn }} {{ krb_service | upper }}/{{ krb_host_fqdn }} + when: krb_host_fqdn != ansible_fqdn + register: result + changed_when: '"Number of members added 1" in result.stdout' + failed_when: '(ansible_fqdn + ": This entry is already a member") not in result.stdout and result.rc != 0' + +- name: Get service keytab + shell: ipa-getkeytab -p {{ krb_service | upper }}/{{ krb_host_fqdn }}@{{ krb_realm }} -k {{ keytab_path }} + args: + creates: "{{ keytab_path }}" + +- name: Set the correct permissions on keytab + file: + path: "{{ keytab_path }}" + owner: "{{ keytab_owner }}" + group: "{{ keytab_group }}" + mode: 0640 diff --git a/webhook_to_fedora_messaging/endpoints/__init__.py b/webhook_to_fedora_messaging/endpoints/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/webhook_to_fedora_messaging/endpoints/util.py b/webhook_to_fedora_messaging/endpoints/util.py deleted file mode 100644 index 0c0f8c3..0000000 --- a/webhook_to_fedora_messaging/endpoints/util.py +++ /dev/null @@ -1,29 +0,0 @@ -from flask import Response, Request - - -def not_found() -> Response: - return Response({'message': 'Not Found'}, status=404, mimetype='application/json') - - -def success(data: dict) ->Response: - return Response(data, status=200, mimetype='application/json') - - -def bad_request() -> Response: - return Response("{'message': 'Bad Request'}", status=400, mimetype='application/json') - - -def created(data: dict) -> Response: - return Response(data, status=201, mimetype='application/json') - - -def conflict(data: dict) -> Response: - return Response(data, status=409, mimetype='application/json') - - -def unprocessable_entity() -> Response: - return Response("{'message: 'Unprocessable Entity'}", status=429, mimetype="application/json") - - -def validate_request(request: dict, fields=['username']) -> bool: - return all(field in request for field in fields)