feat(web02): Switch to django-apps for deploying kadenios
All checks were successful
Build all the nodes / ap01 (push) Successful in 31s
Build all the nodes / netaccess01 (push) Successful in 19s
Build all the nodes / netcore01 (push) Successful in 19s
Build all the nodes / netcore02 (push) Successful in 36s
Build all the nodes / bridge01 (push) Successful in 1m51s
Run pre-commit on all files / pre-commit (push) Successful in 24s
Build the shell / build-shell (push) Successful in 34s
Build all the nodes / build01 (push) Successful in 2m11s
Build all the nodes / hypervisor03 (push) Successful in 1m39s
Build all the nodes / geo01 (push) Successful in 2m11s
Build all the nodes / hypervisor01 (push) Successful in 2m13s
Build all the nodes / geo02 (push) Successful in 2m19s
Build all the nodes / tower01 (push) Successful in 1m44s
Build all the nodes / hypervisor02 (push) Successful in 2m22s
Build all the nodes / compute01 (push) Successful in 2m43s
Build all the nodes / vault01 (push) Successful in 1m59s
Build all the nodes / rescue01 (push) Successful in 2m20s
Build all the nodes / storage01 (push) Successful in 2m26s
Build all the nodes / web02 (push) Successful in 2m14s
Build all the nodes / web03 (push) Successful in 2m24s
Build all the nodes / web01 (push) Successful in 2m31s

This commit is contained in:
Tom Hubrecht 2025-02-24 17:46:33 +01:00
parent 6dc90315c5
commit 5a37cf7d64
Signed by: thubrecht
SSH key fingerprint: SHA256:r+nK/SIcWlJ0zFZJGHtlAoRwq1Rm+WcKAm5ADYMoQPc
11 changed files with 152 additions and 193 deletions

View file

@ -13,7 +13,8 @@ lib.extra.mkConfig {
enabledServices = [
# List of services to enable
"cas-eleves"
"kadenios"
# "kadenios"
"django-apps"
];
extraConfig = {

View file

@ -0,0 +1,22 @@
# SPDX-FileCopyrightText: 2024 Tom Hubrecht <tom.hubrecht@dgnum.eu>
#
# SPDX-License-Identifier: EUPL-1.2
{
imports = [
./kadenios.nix
];
services.django-apps = {
enable = true;
webhook = {
domain = "web02.dj-hooks.dgnum.eu";
nginx = {
enableACME = true;
forceSSL = true;
};
};
};
}

View file

@ -0,0 +1,66 @@
# SPDX-FileCopyrightText: 2024 Tom Hubrecht <tom.hubrecht@dgnum.eu>
#
# SPDX-License-Identifier: EUPL-1.2
{ config, ... }:
{
services.django-apps.sites.kadenios = {
source = "https://git.dgnum.eu/DGNum/kadenios";
branch = "production";
domain = "vote.dgnum.eu";
nginx = {
enableACME = true;
forceSSL = true;
};
webHookSecret = config.age.secrets."webhook-kadenios_token".path;
overlays.nix-pkgs = [
# Required packages
"authens"
"django-background-tasks"
"django-bulma-forms"
"django-translated-fields"
"loadcredential"
# Dependencies
"python-cas"
];
dependencies = ps: [
ps.authens
ps.django
ps.django-background-tasks
ps.django-bulma-forms
ps.django-translated-fields
ps.gunicorn
ps.loadcredential
ps.markdown
ps.networkx
ps.numpy
ps.psycopg
];
environment = {
KADENIOS_EMAIL_HOST_USER = "web-services@infra.dgnum.eu";
KADENIOS_EMAIL_USE_SSL = true;
KADENIOS_FROM_EMAIL = "Kadenios <vote@infra.dgnum.eu>";
KADENIOS_SERVER_EMAIL = "kadenios@infra.dgnum.eu";
};
credentials = {
SECRET_KEY = config.age.secrets."dj_kadenios-secret_key_file".path;
EMAIL_HOST_PASSWORD = config.age.secrets."dj_kadenios-email_password_file".path;
};
extraServices.tasks = {
script = "python3 manage.py process_tasks";
serviceConfig = {
WorkingDirectory = "/var/lib/django-apps/kadenios/source";
};
};
};
}

View file

@ -1,190 +0,0 @@
# SPDX-FileCopyrightText: 2024 Tom Hubrecht <tom.hubrecht@dgnum.eu>
#
# SPDX-License-Identifier: EUPL-1.2
{
config,
lib,
pkgs,
sources,
...
}:
let
inherit (lib) mapAttrsToList optionals;
host = "vote.dgnum.eu";
port = 9888;
python3 =
let
nix-pkgs = import sources.nix-pkgs { inherit pkgs; };
in
pkgs.python3.override {
packageOverrides = _: _: {
inherit (nix-pkgs)
authens
django-background-tasks
django-browser-reload
django-bulma-forms
django-translated-fields
loadcredential
;
};
};
pythonEnv =
{
debug ? false,
}:
python3.withPackages (
ps:
[
ps.django
ps.gunicorn
ps.markdown
ps.numpy
ps.networkx
ps.psycopg
ps.authens
ps.django-background-tasks
ps.django-bulma-forms
ps.django-translated-fields
ps.loadcredential
]
++ (optionals debug [
ps.django-browser-reload
ps.django-debug-toolbar
])
);
manage = pkgs.writeShellApplication {
name = "kadenios-manage";
runtimeInputs = path ++ [
config.systemd.package
pkgs.util-linux
];
text = ''
MainPID=$(systemctl show -p MainPID --value django-kadenios.service)
nsenter -e -a -t "$MainPID" -G follow -S follow python ${sources.kadenios}/manage.py "$@"
'';
};
staticDrv = pkgs.stdenv.mkDerivation {
name = "kadenios-static";
src = sources.kadenios;
nativeBuildInputs = [ (pythonEnv { debug = true; }) ];
configurePhase = ''
export KADENIOS_STATIC_ROOT=$out/static
export KADENIOS_DEBUG=true
export CREDENTIALS_DIRECTORY=$(pwd)/.credentials
'';
doBuild = false;
installPhase = ''
mkdir -p $out/static
python3 manage.py collectstatic
'';
};
environment = builtins.mapAttrs (_: builtins.toJSON) {
KADENIOS_ALLOWED_HOSTS = [ "vote.dgnum.eu" ];
KADENIOS_STATIC_ROOT = staticDrv;
KADENIOS_DATABASES = {
default = {
ENGINE = "django.db.backends.postgresql";
NAME = "kadenios";
};
};
KADENIOS_EMAIL_HOST_USER = "web-services@infra.dgnum.eu";
KADENIOS_EMAIL_USE_SSL = true;
KADENIOS_FROM_EMAIL = "Kadenios <vote@infra.dgnum.eu>";
KADENIOS_SERVER_EMAIL = "kadenios@infra.dgnum.eu";
};
path = [ (pythonEnv { }) ];
in
{
environment.systemPackages = [ manage ];
systemd.services = {
django-kadenios = {
description = "ENS simple voting server";
wantedBy = [ "multi-user.target" ];
after = [
"network.target"
"postgresql.service"
];
serviceConfig = {
DynamicUser = true;
LoadCredential = mapAttrsToList (name: value: "${name}:${value}") {
SECRET_KEY = config.age.secrets."kadenios-secret_key_file".path;
EMAIL_HOST_PASSWORD = config.age.secrets."kadenios-email_password_file".path;
};
StateDirectory = "django-kadenios";
User = "kadenios";
};
inherit environment path;
script = ''
python3 ${sources.kadenios}/manage.py migrate
gunicorn app.wsgi --pythonpath ${sources.kadenios} -b 127.0.0.1:${builtins.toString port} --workers=2 --threads=4
'';
};
django-kadenios-tasks = {
description = "Background tasks worker for Kadenios";
wantedBy = [ "multi-user.target" ];
after = [
"network.target"
"postgresql.service"
"django-kadenios.service"
];
serviceConfig = {
DynamicUser = true;
LoadCredential = mapAttrsToList (name: value: "${name}:${value}") {
SECRET_KEY = config.age.secrets."kadenios-secret_key_file".path;
EMAIL_HOST_PASSWORD = config.age.secrets."kadenios-email_password_file".path;
};
StateDirectory = "django-kadenios";
User = "kadenios";
WorkingDirectory = sources.kadenios;
};
inherit environment path;
script = ''
python3 manage.py process_tasks
'';
};
};
dgn-web.simpleProxies.kadenios = {
inherit host port;
vhostConfig.locations."/static/".root = staticDrv;
};
services.postgresql = {
ensureDatabases = [ "kadenios" ];
ensureUsers = [
{
name = "kadenios";
ensureDBOwnership = true;
}
];
};
}

Binary file not shown.

View file

@ -6,7 +6,9 @@
[ "web02" ]
[
# List of secrets for web02
"bupstash-put_key"
"cas_eleves-secret_key_file"
"kadenios-secret_key_file"
"kadenios-email_password_file"
"dj_kadenios-secret_key_file"
"dj_kadenios-email_password_file"
"webhook-kadenios_token"
]

View file

@ -0,0 +1,29 @@
age-encryption.org/v1
-> ssh-ed25519 jIXfPA miVq8rZazx0Y0NYZklZh8ITlY7fOTwbPsAPcHwvJ3jI
Vs0xx9ulk2++7+DfD+HqhISSvYMtuSJIs9zyGlnW8Wk
-> ssh-ed25519 QlRB9Q z5TQpHovWNJ+Dq4GEcPfByMpTcTojIamJbU3kNKlmHQ
U+ZFJ/0TVcfo85xAWYqcnzpMfU0KcY8QJ8jqWlyt1U0
-> ssh-ed25519 r+nK/Q l5oBCnALC2HSoszpawrJZZUEFHjjGwei4Fd1Y+f7OjI
PLgEu00ItWIbT3ZSNioZ3oXwBBVQTD/wf8I8akEDNWs
-> ssh-rsa krWCLQ
2rt9GmpSxUJSArSOlXKQscrApgLLIWuTo/IXensBP1uCnrpLl4IdcpEJNTs7wtZq
h4OLCaLDoZvB3ZT3k+CXXXeBqLqz1DdBGo08RgfcUADTsm2Z9LsEyLo0GtHGEFjw
m1r/VF8githDxaEK52+znr1FG8CE7+DBQAU9ZydhKKjjFS7ckDHw0qFXyGqpyWk4
KnL7FGPX2z07V3nwauElDbaD1LLt0xHhqqEjmiRskhE2UU6q35IrLyKFHC1VHsFy
ItsONTu8lDiqXSi7Z5b5Iv+iAWWTtt/glTv3WFa8u7CIahuZIfemr8NzjD2Z+Vxh
yOEqBKyVgz8sFh1U7CgxCg
-> ssh-ed25519 /vwQcQ dcnBNyypzMkxHwh76v7bKhGckPjIOL2vP2aDWhB8WxQ
tTxcMXcLrFhD7u2xTOhsjWErSiCOfsVIDZgJldVePMw
-> ssh-ed25519 0R97PA stdF6UFkWDCwNUAv+aAetpku7O9XRvtaxafCjok9yhI
gXVXcwlY4Xue9WGk+WlByXvSgMju+VWKTBTXIngWYvE
-> ssh-ed25519 JGx7Ng e+Ux4HK63pAM4scQCi4wHTUmo28z105Ok59dlki0OS8
ulkU6zhXNpa3OswEC005BZ/YIExPysg25a4/O60fcWQ
-> ssh-ed25519 bUjjig SEnDWloeuVgCGLUJNvsBL1HPYJGBSBhqdDngkQk+KiE
MYL9SudJNuFyS4Inaod2Xxldi3d/kDwlIT9rVWs8vFc
-> ssh-ed25519 IY5FSQ TO9BPLBwdlqyKXOBiohCzfZWrTDwqhLjZYeq9rZgH2c
7Hqrqe+A3wg11H3wg9Cd+6F7mDwsLpzoh70sba32gCw
-> 1DV;-grease
9Ul6qKgH063H/HI1op+Gyk2+JRUGHwRG/SlOPTAnvBtq7xEy7yrR4lblBK8bcJNY
lwmI4xOokAnIveVaPS8SAig
--- GpJyGpk3QxJljiR6FZw8hdX0dXvEAIPZEZpL6oorLcM
}­o÷ÕŸ¦A¹qç ™Ò™ö>áp™€M Õ¬Ía“ zþƒÍT VVƒvI«f®<17>!>µ\Ö-þèÿ

View file

@ -39,6 +39,7 @@ let
compute01 = "*-*-* *:38:00";
storage01 = "*-*-* *:21:00";
web01 = "*-*-* *:47:00";
web02 = "*-*-* *:24:00";
web03 = "*-*-* *:13:00";
};

View file

@ -0,0 +1,28 @@
age-encryption.org/v1
-> ssh-ed25519 jIXfPA qaesYQqsDj6Ge1W2i9ybqYhJBlv2aK+fcEyYHZxIsFY
A1eY+mjxvegSggMoA2SGGMClZgGjJoXtS5hE2dWcFcY
-> ssh-ed25519 QlRB9Q BeT/ig3ncj89SmQzxqA6DZK331rY4nbV57I21PqhUGg
77F6y4dmTLCYgQISZ+hnNbEMLw20nTlfRsMeAstNKkY
-> ssh-ed25519 r+nK/Q u2UBdCaBhXHqiz1ILFoxMejypZ/1seeYMnK3GZV4fmE
F0r4s+GE7k+lNyTyOQQJF3tQcucSWIafMx9VYtffn9E
-> ssh-rsa krWCLQ
NKJOxCuoVAqDKel1DFMk3rYMdHUcnCjggORnbEO2TpG8O5oJba1NgSaggpnjPmYm
ldlH+egg++pHyB4hYgjEhHoIe3yVu/1Z564rdqDfVo9k4x8+OeAM0ot7ZpUVh837
DVXozkoGy5axomm9vRrr1iTty/NpPV1aw0AAiS2ZH9WR5k1llkvjioPBUHYAyG3z
jBwLnwZxPCtoV88KB8p1a7NFjhl0RLnKfwEHYXlne5wqNrY/LxUzyhnoMLNCQKMr
CNhbSFAUugIpEeNb080Ints0uoyobNIg51CTwC1bHiZc4IeRsSrLCKf8gYJS56C+
Plm2VT6OfnqnBOTkEj01GA
-> ssh-ed25519 /vwQcQ vJcgz/8/7obl6MC0+JqK13wPSemboL8Ira6HmEWUrXs
frPre2spFABGvhWw1mEicQ7lSOtFNGgtbPAQRslatYM
-> ssh-ed25519 0R97PA TLAeNtje+bRkMwfXKAe577YqqO5cJPsssmfzaJyFwRQ
aCK/T9fzqVmUw3mjg74E21en+ou7ejBA/YP3ZlA+PFI
-> ssh-ed25519 JGx7Ng GyUFqicloCYpZkob7q3ZEF7lDqV8Ba6l1hWVMbnpxjE
ZmhxO+CJkOojI7xJVlrtxBr4JcfFj3aUoebUsCFfN3Y
-> ssh-ed25519 bUjjig eIHvVkqVZlgv436Ngmb0hHoiWpVbcyIrGebAAk3h5CA
OTldbCB5FHH+h1kJ2E0yW3cH7ewj8x7Zaj3vgxtmyKs
-> YgdS1!-grease f3Y= A16Y4nx #KU[cj
zFjgcHxRy1VF4b1126NNnXdPoWzs+NGSTAKhBuHDANyQdLzKkyMsp3bTi/+VcdXJ
90mGF6TsW/cp5m7WPVH1FTdw9YuESm0dPZseB8FgJuu8aD8TniO+
--- 2bqNg8bNpi8mkW3J7fUdQ9GvlCO4CM1Uyn+WctT4FTg
*Ž<E28098>X[u8 $ò ¡uÎÚ­[rÈV¼Âæ´Ã»:?æ«‘Ÿ*¹ïó>Ýî‡]ƱïÒµ…ƒ,µ¸ ù¾¬€<C2AC>5éÄN„ò*˜.ŠwtRZX—²AIòqÊÝåÒMK;é^K‰ S_Ás2ÕéVµ®`çrjZ2¾ÑÝ­³}<07>uh¯AÙ?±ü§K;ÂO#†žý&§ÈÊḄ- &HÈè ,O6“º MÛ8úÆ0>þc±üìÉ<C3AC>ú%äèX¨SÏûæ×Ýp<E280BA>­î€$'yj¸ÌìÏ·”ÒKî´ôÖ ¢þ$ùsÛå0\Ê)Ë­<C38B>³oöÑDB±™Ëgßw¸ÒóÆÙÑ<C399>§l60%?32
è&eZá˜z®õ@÷Ýðµªp§Ä|s;uјîoRù½  hƒôå»ÐÃç<C383>ÄzF<7A>ûÝÉ A¬"­ <®£Þ.1ôÏÃÉVÞ<>"MFúm<6D> «n0£ÌfƒÖnW7í"œÎlyp@ᦠÙI8X´5üSAJ‡ÍK6Ã^\¢hªósP¬Njsí舳Õ_öÒCÍ´ÐZºe ᄇbWâI°i¸ð_½ÅhÓ%B‡¯Mw¯mî†Taãy͘T³&0'÷j@â8,ÍœÞõɧ4Z+0tžj°KüÞ¿W<Tw,<2C>´]]r48½¼SÚ©„qŠãž<C3A3>G~,Oež—ŒLÇÑ<C387>sŒ¿z<C2BF> P“õ5¤ñl`Z}xP©žAøÉE“ž<E2809C>¥ÙfW„Ž|2°Xé };™">ëß>ã› ÐüáÒÃë?TìA%ždêó¥ãÈ”€RÓ'<27>©¦•ý2jäjóü$uì æZ¥Ž°Ù6e¸â:ZµZæ•¡)~à?>¯²['gêQÔ;}1Éa`FJ¢d­ØŸ-÷g«ž6~ÿ¨YtSÁþ/‰úÖX<e4·-´ãZ':žç@Gõz;ºÁÝÔmú‡,¾ýFÛ0jµ)ÒĂÎá’ô•Ÿ:vÀÊ~:÷1¦9ˆÓÍGİL‰\©<><C2A9>[ÿÉ_>#UDžO sN½ƒq¦œ ÙJLŠŽ¨n½±•‡zòâxøZùšêñ'5mz$9