diff --git a/.agenix_config.nix b/.agenix_config.nix index 13c7930..3b16faa 100644 Binary files a/.agenix_config.nix and b/.agenix_config.nix differ diff --git a/machines/asus-gl553vd/default.nix b/machines/asus-gl553vd/default.nix index 44bb8ab..aac31b3 100644 --- a/machines/asus-gl553vd/default.nix +++ b/machines/asus-gl553vd/default.nix @@ -6,7 +6,7 @@ ./hardware-configuration.nix ../modules/common.nix ../modules/sound.nix - ../modules/window_manager.nix + ../modules/window-manager.nix ../modules/fonts.nix ../modules/gnupg.nix ../modules/nix.nix diff --git a/machines/canigou/default.nix b/machines/canigou/default.nix index c2e0b5c..123159d 100644 --- a/machines/canigou/default.nix +++ b/machines/canigou/default.nix @@ -10,6 +10,7 @@ in ../modules/common.nix ../modules/fail2ban.nix + ../modules/docker-swarm.nix ./services/wireguard.nix ]; diff --git a/machines/canigou/hardware-configuration.nix b/machines/canigou/hardware-configuration.nix index e54b5c4..d6cfa23 100644 --- a/machines/canigou/hardware-configuration.nix +++ b/machines/canigou/hardware-configuration.nix @@ -6,4 +6,8 @@ boot.initrd.availableKernelModules = [ "ata_piix" "uhci_hcd" "xen_blkfront" "vmw_pvscsi" ]; boot.initrd.kernelModules = [ "nvme" ]; fileSystems."/" = { device = "/dev/sda1"; fsType = "ext4"; }; + swapDevices = [ + { device = "/dev/zram0"; } + { device = "/var/swapfile"; size = 1536; } + ]; } diff --git a/machines/home/default.nix b/machines/home/default.nix index cfd6efa..e896386 100644 --- a/machines/home/default.nix +++ b/machines/home/default.nix @@ -6,7 +6,7 @@ ./hardware-configuration.nix ../modules/common.nix ../modules/sound.nix - ../modules/window_manager.nix + ../modules/window-manager.nix ../modules/fonts.nix ../modules/gnupg.nix ../modules/nix.nix diff --git a/machines/magenta/default.nix b/machines/magenta/default.nix index a34ac4b..971143a 100644 --- a/machines/magenta/default.nix +++ b/machines/magenta/default.nix @@ -1,4 +1,4 @@ -{ config, pkgs, ... }: +{ config, pkgs, lib, ... }: let data = import ../../data.nix; @@ -9,13 +9,14 @@ in ./networking.secret.nix # generated at runtime by nixos-infect ../modules/common.nix - ../modules/nix.nix ../modules/fail2ban.nix ../modules/garbage-collector.nix + ../modules/docker-swarm.nix - ./services/traefik.nix ./services/mailserver.nix ./services/gitea.nix + ./services/traefik.nix + ./services/woodpecker ]; boot.kernelPackages = pkgs.linuxPackages_6_1; @@ -33,10 +34,4 @@ in defaults.email = "dmitriy@pleshevski.ru"; }; - # Enable docker - virtualisation.docker = { - enable = true; - liveRestore = false; - }; - networking.firewall.allowedTCPPorts = [ 2377 ]; } diff --git a/machines/magenta/hardware-configuration.nix b/machines/magenta/hardware-configuration.nix index 40c8d65..d611882 100644 --- a/machines/magenta/hardware-configuration.nix +++ b/machines/magenta/hardware-configuration.nix @@ -6,4 +6,8 @@ boot.initrd.availableKernelModules = [ "ata_piix" "uhci_hcd" "xen_blkfront" ]; boot.initrd.kernelModules = [ "nvme" ]; fileSystems."/" = { device = "/dev/sda1"; fsType = "ext4"; }; + swapDevices = [ + { device = "/dev/zram0"; } + { device = "/var/swapfile"; size = 1536; } + ]; } diff --git a/machines/magenta/services/gitea.nix b/machines/magenta/services/gitea.nix index c1cc7f8..1ad2041 100644 --- a/machines/magenta/services/gitea.nix +++ b/machines/magenta/services/gitea.nix @@ -8,6 +8,7 @@ let robotsTxt = pkgs.writeText "robots.txt" '' User-agent: * Disallow: /github + Disallow: /external ''; in { @@ -105,13 +106,11 @@ in ''; services.traefik.dynamicConfigOptions.http = { - routers = { - to_gitea = { - rule = "Host(`${hostname}`)"; - entryPoints = [ "https" ]; - tls.certResolver = "le"; - service = "gitea"; - }; + routers.to_gitea = { + rule = "Host(`${hostname}`)"; + entryPoints = [ "https" ]; + tls.certResolver = "le"; + service = "gitea"; }; services.gitea = { loadBalancer.servers = [ diff --git a/machines/magenta/services/traefik.nix b/machines/magenta/services/traefik.nix index e45b8af..bb66b56 100644 --- a/machines/magenta/services/traefik.nix +++ b/machines/magenta/services/traefik.nix @@ -1,4 +1,4 @@ -{ config, ... }: +{ config, lib, ... }: let traefikCfg = config.services.traefik; @@ -14,6 +14,8 @@ in inherit (traefikCfg) group; }; + users.groups.docker.members = [ "traefik" ]; + services.traefik = { enable = true; staticConfigOptions = { @@ -36,21 +38,26 @@ in email = "dmitriy@pleshevski.ru"; tlschallenge = true; }; + providers.docker = { + network = "rp_public"; + constraints = "Label(`traefik.constraint-label`, `${config.networking.hostName}_public`)"; + exposedByDefault = false; + swarmMode = true; + }; }; - dynamicConfigOptions = { - http = { - routers.to_traefik_dashboard = { - rule = "Host(`${magentaData.addr}`)"; - entryPoints = [ "dashboard" ]; - middlewares = [ "traefik_dashboard_auth" ]; - service = "api@internal"; - }; - middlewares = { - traefik_dashboard_auth.basicAuth = { - usersFile = config.age.secrets.traefik-dashboard-basicauth-users.path; - }; + dynamicConfigOptions.http = { + routers.to_traefik_dashboard = { + rule = "Host(`${magentaData.addr}`)"; + entryPoints = [ "dashboard" ]; + middlewares = [ "traefik_dashboard_auth" ]; + service = "api@internal"; + }; + middlewares = { + traefik_dashboard_auth.basicAuth = { + usersFile = config.age.secrets.traefik-dashboard-basicauth-users.path; }; }; }; }; + } diff --git a/machines/magenta/services/woodpecker/agent-docker.nix b/machines/magenta/services/woodpecker/agent-docker.nix new file mode 100644 index 0000000..633a425 --- /dev/null +++ b/machines/magenta/services/woodpecker/agent-docker.nix @@ -0,0 +1,37 @@ +{ pkgs, config, ... }: + +let + nextPkgs = pkgs.callPackage ../../../../packages/woodpecker { }; + + canigouData = import ../../data.secret.nix; + + data = import ./data.secret.nix; + inherit (data) userAgent group grpcPort; + + dockerSockVolume = "/var/run/docker.sock:/var/run/docker.sock"; + dockerConfVolume = "${config.age.secrets.woodpecker-docker-config.path}:/root/.docker/config.json"; +in +{ + systemd.services.woodpecker-agent = { + enable = true; + wantedBy = [ "multi-user.target" ]; + after = [ "woodpecker-server.service" ]; + restartIfChanged = true; + serviceConfig = { + EnvironmentFile = [ + config.age.secrets.woodpecker-common-env.path + ]; + Environment = [ + "WOODPECKER_DEBUG_PRETTY=true" + "WOODPECKER_LOG_LEVEL=trace" + "WOODPECKER_SERVER=${canigouData.addr}:${toString grpcPort}" + "WOODPECKER_MAX_WORKFLOWS=2" + "WOODPECKER_BACKEND=docker" + "WOODPECKER_BACKEND_DOCKER_VOLUMES=${dockerSockVolume},${dockerConfVolume}" + ]; + ExecStart = "${nextPkgs.woodpecker-agent}/bin/woodpecker-agent"; + User = userAgent; + Group = group; + }; + }; +} diff --git a/machines/magenta/services/woodpecker/common.nix b/machines/magenta/services/woodpecker/common.nix new file mode 100644 index 0000000..9c7026d --- /dev/null +++ b/machines/magenta/services/woodpecker/common.nix @@ -0,0 +1,28 @@ +let + data = import ./data.secret.nix; + inherit (data) userServer userAgent group; +in +{ + users.groups.${group} = { }; + + users.users.${userServer} = { + description = "Woodpecker CI Server"; + isSystemUser = true; + createHome = true; + inherit group; + }; + + users.users.${userAgent} = { + isSystemUser = true; + inherit group; + }; + users.groups.docker.members = [ userAgent userServer ]; + + age.secrets.woodpecker-common-env.file = ../../../../secrets/woodpecker-common-env.age; + age.secrets.woodpecker-server-env.file = ../../../../secrets/woodpecker-server-env.age; + age.secrets.woodpecker-docker-config = { + file = ../../../../secrets/docker-config.json.age; + mode = "440"; + inherit group; + }; +} diff --git a/machines/magenta/services/woodpecker/data.secret.nix b/machines/magenta/services/woodpecker/data.secret.nix new file mode 100644 index 0000000..c86dcc9 Binary files /dev/null and b/machines/magenta/services/woodpecker/data.secret.nix differ diff --git a/machines/magenta/services/woodpecker/default.nix b/machines/magenta/services/woodpecker/default.nix new file mode 100644 index 0000000..b800dfe --- /dev/null +++ b/machines/magenta/services/woodpecker/default.nix @@ -0,0 +1,9 @@ +{ ... }: + +{ + imports = [ + ./common.nix + ./agent-docker.nix + ./server.nix + ]; +} diff --git a/machines/magenta/services/woodpecker/server.nix b/machines/magenta/services/woodpecker/server.nix new file mode 100644 index 0000000..580234c --- /dev/null +++ b/machines/magenta/services/woodpecker/server.nix @@ -0,0 +1,69 @@ +# https://github.com/Mic92/dotfiles/tree/035a2c22e161f4fbe4fcbd038c6464028ddce619/nixos/eve/modules/woodpecker +{ pkgs, config, ... }: + +let + nextPkgs = pkgs.callPackage ../../../../packages/woodpecker { }; + + data = import ./data.secret.nix; + inherit (data) hostname port grpcPort userServer group database; +in +{ + networking.firewall.allowedTCPPorts = [ port grpcPort ]; + + services.postgresql.enable = true; + + systemd.services.woodpecker-server = { + wantedBy = [ "multi-user.target" ]; + after = [ "network.target" "postgresql.service" ]; + serviceConfig = { + # See: https://woodpecker-ci.org/docs/administration/server-config + EnvironmentFile = [ + config.age.secrets.woodpecker-common-env.path + config.age.secrets.woodpecker-server-env.path + ]; + Environment = [ + "WOODPECKER_DEBUG_PRETTY=true" + "WOODPECKER_LOG_LEVEL=trace" + "WOODPECKER_HOST=https://${hostname}" + "WOODPECKER_SERVER_ADDR=:${toString port}" + "WOODPECKER_GRPC_ADDR=:${toString grpcPort}" + "WOODPECKER_ADMIN=pleshevskiy" + "WOODPECKER_DATABASE_DRIVER=postgres" + "WOODPECKER_DATABASE_DATASOURCE=postgres://${userServer}@:${toString config.services.postgresql.port}/${database}?host=/run/postgresql" + "WOODPECKER_GITEA=true" + "WOODPECKER_GITEA_URL=https://git.pleshevski.ru" + "WOODPECKER_DOCKER_CONFIG=${config.age.secrets.woodpecker-docker-config.path}" + "WOODPECKER_AUTHENTICATE_PUBLIC_REPOS=true" + ]; + ExecStart = "${nextPkgs.woodpecker-server}/bin/woodpecker-server"; + User = userServer; + Group = group; + }; + }; + + services.postgresql = { + ensureDatabases = [ database ]; + ensureUsers = [ + { + name = userServer; + ensurePermissions = { + "DATABASE ${database}" = "ALL PRIVILEGES"; + }; + } + ]; + }; + + services.traefik.dynamicConfigOptions.http = { + routers.to_woodpecker_server = { + rule = "Host(`${hostname}`)"; + entryPoints = [ "https" ]; + tls.certResolver = "le"; + service = "woodpecker_server"; + }; + services.woodpecker_server = { + loadBalancer.servers = [ + { url = "http://localhost:${toString port}"; } + ]; + }; + }; +} diff --git a/machines/modules/docker-swarm.nix b/machines/modules/docker-swarm.nix new file mode 100644 index 0000000..3be1e64 --- /dev/null +++ b/machines/modules/docker-swarm.nix @@ -0,0 +1,14 @@ +{ ... }: + +{ + # Enable docker + virtualisation.docker = { + enable = true; + liveRestore = false; + }; + # Source: https://forums.docker.com/t/error-response-from-daemon-rpc-error-code-unavailable-desc-grpc-the-connection-is-unavailable/39066/12 + networking.firewall = { + allowedTCPPorts = [ 2376 2377 7946 ]; + allowedUDPPorts = [ 7946 4789 ]; + }; +} diff --git a/machines/modules/traefik.nix b/machines/modules/traefik.nix new file mode 100644 index 0000000..409f9a7 --- /dev/null +++ b/machines/modules/traefik.nix @@ -0,0 +1,70 @@ +{ config, lib, ... }: + +let + cfg = config.local.traefik; + + traefikCfg = config.services.traefik; +in +{ + options.local.traefik = with lib; { + enable = mkEnableOption "Enable traefik service"; + dashboard = { + enable = mkEnableOption "Enable traefik dashboard"; + host = mkOption { + type = types.nullOr types.str; + description = "Traefik dashboard host"; + }; + }; + }; + + config = lib.mkIf cfg.enable { + networking.firewall.allowedTCPPorts = [ 80 443 ] ++ lib.optional cfg.dashboard.enable 8080; + + services.traefik = { + enable = true; + staticConfigOptions = { + entryPoints = { + http = { + address = ":80"; + http.redirections.entryPoint = { + to = "https"; + scheme = "https"; + }; + }; + https.address = ":443"; + }; + log = { }; + accessLog = { }; + certificatesResolvers.le.acme = { + storage = "${traefikCfg.dataDir}/acme.json"; + email = "dmitriy@pleshevski.ru"; + tlschallenge = true; + }; + providers.docker = { + network = "rp_public"; + constraints = "Label(`traefik.constraint-label`, `${config.networking.hostName}_public`)"; + exposedByDefault = false; + swarmMode = true; + }; + }; + } // lib.mkIf cfg.dashboard.enable { + staticConfigOptions = { + api = { }; + entryPoints.dashboard.address = ":8080"; + }; + dynamicConfigOptions.http = { + routers.to_traefik_dashboard = { + rule = "Host(`${cfg.dashboard.host}`)"; + entryPoints = [ "dashboard" ]; + middlewares = [ "traefik_dashboard_auth" ]; + service = "api@internal"; + }; + middlewares = { + traefik_dashboard_auth.basicAuth = { + usersFile = config.age.secrets.traefik-dashboard-basicauth-users.path; + }; + }; + }; + }; + }; +} diff --git a/machines/modules/window_manager.nix b/machines/modules/window-manager.nix similarity index 100% rename from machines/modules/window_manager.nix rename to machines/modules/window-manager.nix diff --git a/packages/woodpecker/agent.nix b/packages/woodpecker/agent.nix new file mode 100644 index 0000000..2865711 --- /dev/null +++ b/packages/woodpecker/agent.nix @@ -0,0 +1,17 @@ +{ lib, buildGoModule, callPackage, fetchFromGitHub }: +let + common = callPackage ./common.nix { }; +in +buildGoModule { + pname = "woodpecker-agent"; + inherit (common) version src ldflags postBuild; + vendorSha256 = null; + + subPackages = "cmd/agent"; + + CGO_ENABLED = 0; + + meta = common.meta // { + description = "Woodpecker Continuous Integration agent"; + }; +} diff --git a/packages/woodpecker/cli.nix b/packages/woodpecker/cli.nix new file mode 100644 index 0000000..b5eda9e --- /dev/null +++ b/packages/woodpecker/cli.nix @@ -0,0 +1,17 @@ +{ lib, buildGoModule, callPackage, fetchFromGitHub }: +let + common = callPackage ./common.nix { }; +in +buildGoModule { + pname = "woodpecker-cli"; + inherit (common) version src ldflags postBuild; + vendorSha256 = null; + + subPackages = "cmd/cli"; + + CGO_ENABLED = 0; + + meta = common.meta // { + description = "Command line client for the Woodpecker Continuous Integration server"; + }; +} diff --git a/packages/woodpecker/common.nix b/packages/woodpecker/common.nix new file mode 100644 index 0000000..3603781 --- /dev/null +++ b/packages/woodpecker/common.nix @@ -0,0 +1,37 @@ +{ lib, fetchFromGitea }: +let + version = "13f878c10ac77d16ddae994b9253fa8c23c4d5be"; + srcSha256 = "sha256-ifyQK3eCThNPu3Qnfy6WUYba5qvop+6VJmwpWcpWJVE="; + yarnSha256 = "sha256-XsyMw2xqTjng4DoeiUb2+pJ9rGtHw2yZgy7pzLSDkas="; +in +{ + inherit version yarnSha256; + + src = fetchFromGitea { + domain = "git.pleshevski.ru"; + owner = "infra"; + repo = "woodpecker"; + rev = version; + sha256 = srcSha256; + }; + + postBuild = '' + cd $GOPATH/bin + for f in *; do + mv -- "$f" "woodpecker-$f" + done + cd - + ''; + + ldflags = [ + "-s" + "-w" + "-X github.com/woodpecker-ci/woodpecker/version.Version=next" + ]; + + meta = with lib; { + homepage = "https://woodpecker-ci.org/"; + license = licenses.asl20; + maintainers = with maintainers; [ ambroisie techknowlogick ]; + }; +} diff --git a/packages/woodpecker/default.nix b/packages/woodpecker/default.nix new file mode 100644 index 0000000..c0028db --- /dev/null +++ b/packages/woodpecker/default.nix @@ -0,0 +1,11 @@ +{ callPackage }: + +{ + woodpecker-agent = callPackage ./agent.nix { }; + + woodpecker-cli = callPackage ./cli.nix { }; + + woodpecker-server = callPackage ./server.nix { + woodpecker-frontend = callPackage ./frontend.nix { }; + }; +} diff --git a/packages/woodpecker/frontend.nix b/packages/woodpecker/frontend.nix new file mode 100644 index 0000000..267fdc1 --- /dev/null +++ b/packages/woodpecker/frontend.nix @@ -0,0 +1,40 @@ +{ lib, callPackage, fetchFromGitHub, fetchYarnDeps, mkYarnPackage }: +let + common = callPackage ./common.nix { }; +in +mkYarnPackage { + pname = "woodpecker-frontend"; + inherit (common) version; + + src = "${common.src}/web"; + + packageJSON = ./woodpecker-package.json; + offlineCache = fetchYarnDeps { + yarnLock = "${common.src}/web/yarn.lock"; + sha256 = common.yarnSha256; + }; + + buildPhase = '' + runHook preBuild + + yarn build + + runHook postBuild + ''; + + installPhase = '' + runHook preInstall + + cp -R deps/woodpecker-ci/dist $out + echo "${common.version}" > "$out/version" + + runHook postInstall + ''; + + # Do not attempt generating a tarball for woodpecker-frontend again. + doDist = false; + + meta = common.meta // { + description = "Woodpecker Continuous Integration server frontend"; + }; +} diff --git a/packages/woodpecker/server.nix b/packages/woodpecker/server.nix new file mode 100644 index 0000000..d974126 --- /dev/null +++ b/packages/woodpecker/server.nix @@ -0,0 +1,27 @@ +{ lib, buildGoModule, callPackage, fetchFromGitHub, woodpecker-frontend }: +let + common = callPackage ./common.nix { }; +in +buildGoModule { + pname = "woodpecker-server"; + inherit (common) version src ldflags postBuild; + vendorSha256 = null; + + postPatch = '' + cp -r ${woodpecker-frontend} web/dist + ''; + + subPackages = "cmd/server"; + + CGO_ENABLED = 1; + + passthru = { + inherit woodpecker-frontend; + + updateScript = ./update.sh; + }; + + meta = common.meta // { + description = "Woodpecker Continuous Integration server"; + }; +} diff --git a/packages/woodpecker/update.sh b/packages/woodpecker/update.sh new file mode 100755 index 0000000..48f362f --- /dev/null +++ b/packages/woodpecker/update.sh @@ -0,0 +1,47 @@ +#!/usr/bin/env nix-shell +#!nix-shell -i bash -p wget prefetch-yarn-deps nix-prefetch-git jq + +# shellcheck shell=bash + +if [ -n "$GITHUB_TOKEN" ]; then + TOKEN_ARGS=(--header "Authorization: token $GITHUB_TOKEN") +fi + +if [[ $# -gt 1 || $1 == -* ]]; then + echo "Regenerates packaging data for the woodpecker packages." + echo "Usage: $0 " + exit 1 +fi + +set -x + +cd "$(dirname "$0")" +version="$1" + +set -euo pipefail + +if [ -z "$version" ]; then + echo "Usage: $0 " +fi + +# Woodpecker repository +src_hash=$(nix-prefetch-git --url https://git.pleshevski.ru/infra/woodpecker --rev "${version}" | jq -r .sha256) + +# Front-end dependencies +woodpecker_src="https://git.pleshevski.ru/infra/woodpecker/raw/$version" +wget "${TOKEN_ARGS[@]}" "$woodpecker_src/web/package.json" -O woodpecker-package.json + +web_tmpdir=$(mktemp -d) +trap 'rm -rf "$web_tmpdir"' EXIT +pushd "$web_tmpdir" +wget "${TOKEN_ARGS[@]}" "$woodpecker_src/web/yarn.lock" +yarn_hash=$(prefetch-yarn-deps yarn.lock) +popd + +# Use friendlier hashes +src_hash=$(nix hash to-sri --type sha256 "$src_hash") +yarn_hash=$(nix hash to-sri --type sha256 "$yarn_hash") + +sed -i -E -e "s#version = \".*\"#version = \"$version\"#" common.nix +sed -i -E -e "s#srcSha256 = \".*\"#srcSha256 = \"$src_hash\"#" common.nix +sed -i -E -e "s#yarnSha256 = \".*\"#yarnSha256 = \"$yarn_hash\"#" common.nix diff --git a/packages/woodpecker/woodpecker-package.json b/packages/woodpecker/woodpecker-package.json new file mode 100644 index 0000000..9d89a21 --- /dev/null +++ b/packages/woodpecker/woodpecker-package.json @@ -0,0 +1,71 @@ +{ + "name": "woodpecker-ci", + "author": "Woodpecker CI", + "version": "0.0.0", + "license": "Apache-2.0", + "engines": { + "node": ">=14" + }, + "scripts": { + "start": "vite", + "build": "vite build", + "serve": "vite preview", + "lint": "eslint --max-warnings 0 --ext .js,.ts,.vue,.json .", + "formatcheck": "prettier -c .", + "format:fix": "prettier --write .", + "typecheck": "vue-tsc --noEmit", + "test": "echo 'No tests configured' && exit 0" + }, + "dependencies": { + "@intlify/vite-plugin-vue-i18n": "^6.0.3", + "@kyvg/vue3-notification": "^2.4.1", + "@vueuse/core": "^9.3.1", + "ansi_up": "^5.1.0", + "dayjs": "^1.11.5", + "floating-vue": "^2.0.0-beta.20", + "fuse.js": "^6.6.2", + "humanize-duration": "^3.27.3", + "javascript-time-ago": "^2.5.7", + "lodash": "^4.17.21", + "node-emoji": "^1.11.0", + "pinia": "^2.0.23", + "prismjs": "^1.29.0", + "vue": "^3.2.41", + "vue-i18n": "^9.2.2", + "vue-router": "^4.1.5" + }, + "devDependencies": { + "@iconify/json": "^2.1.123", + "@types/humanize-duration": "^3.27.1", + "@types/javascript-time-ago": "^2.0.3", + "@types/lodash": "^4.14.186", + "@types/node": "^18.11.2", + "@types/node-emoji": "^1.8.2", + "@types/prismjs": "^1.26.0", + "@typescript-eslint/eslint-plugin": "^5.40.1", + "@typescript-eslint/parser": "^5.40.1", + "@vitejs/plugin-vue": "^3.1.2", + "@vue/compiler-sfc": "^3.2.41", + "eslint": "^8.25.0", + "eslint-config-airbnb-base": "^15.0.0", + "eslint-config-airbnb-typescript": "^17.0.0", + "eslint-config-prettier": "^8.5.0", + "eslint-plugin-import": "^2.26.0", + "eslint-plugin-prettier": "^4.2.1", + "eslint-plugin-promise": "^6.1.0", + "eslint-plugin-simple-import-sort": "^8.0.0", + "eslint-plugin-vue": "^9.6.0", + "eslint-plugin-vue-scoped-css": "^2.2.0", + "prettier": "^2.7.1", + "typescript": "4.8.3", + "unplugin-icons": "^0.14.12", + "unplugin-vue-components": "^0.22.8", + "vite": "^3.1.8", + "vite-plugin-prismjs": "^0.0.8", + "vite-plugin-windicss": "^1.8.8", + "vite-svg-loader": "^3.6.0", + "vue-eslint-parser": "^9.1.0", + "vue-tsc": "^0.40.13", + "windicss": "^3.5.6" + } +} diff --git a/secrets/docker-config.json.age b/secrets/docker-config.json.age new file mode 100644 index 0000000..8c5c910 Binary files /dev/null and b/secrets/docker-config.json.age differ diff --git a/secrets/gitea-smtp-passfile.age b/secrets/gitea-smtp-passfile.age index 8978c61..ff743b0 100644 Binary files a/secrets/gitea-smtp-passfile.age and b/secrets/gitea-smtp-passfile.age differ diff --git a/secrets/mailserver-users-family-passfile.age b/secrets/mailserver-users-family-passfile.age index 5316910..192e765 100644 Binary files a/secrets/mailserver-users-family-passfile.age and b/secrets/mailserver-users-family-passfile.age differ diff --git a/secrets/mailserver-users-gitea-passfile.age b/secrets/mailserver-users-gitea-passfile.age index e66130a..a830434 100644 Binary files a/secrets/mailserver-users-gitea-passfile.age and b/secrets/mailserver-users-gitea-passfile.age differ diff --git a/secrets/mailserver-users-jan-passfile.age b/secrets/mailserver-users-jan-passfile.age index dc544a2..3f42f7f 100644 Binary files a/secrets/mailserver-users-jan-passfile.age and b/secrets/mailserver-users-jan-passfile.age differ diff --git a/secrets/traefik-dashboard-basicauth-users.age b/secrets/traefik-dashboard-basicauth-users.age index 09a42f6..12d7dca 100644 Binary files a/secrets/traefik-dashboard-basicauth-users.age and b/secrets/traefik-dashboard-basicauth-users.age differ diff --git a/secrets/users-jan-passfile.age b/secrets/users-jan-passfile.age index 231826d..9b432fd 100644 Binary files a/secrets/users-jan-passfile.age and b/secrets/users-jan-passfile.age differ diff --git a/secrets/users-nas-passfile.age b/secrets/users-nas-passfile.age index c5303ab..10ba7e2 100644 Binary files a/secrets/users-nas-passfile.age and b/secrets/users-nas-passfile.age differ diff --git a/secrets/wireguard-asus-gl553vd-private.age b/secrets/wireguard-asus-gl553vd-private.age index dcb8766..cfc6bc2 100644 Binary files a/secrets/wireguard-asus-gl553vd-private.age and b/secrets/wireguard-asus-gl553vd-private.age differ diff --git a/secrets/wireguard-canigou-private.age b/secrets/wireguard-canigou-private.age index d8baa18..4f4fa7e 100644 Binary files a/secrets/wireguard-canigou-private.age and b/secrets/wireguard-canigou-private.age differ diff --git a/secrets/wireguard-home-private.age b/secrets/wireguard-home-private.age index f78a9d3..f01c098 100644 Binary files a/secrets/wireguard-home-private.age and b/secrets/wireguard-home-private.age differ diff --git a/secrets/woodpecker-common-env.age b/secrets/woodpecker-common-env.age new file mode 100644 index 0000000..4d6dac5 Binary files /dev/null and b/secrets/woodpecker-common-env.age differ diff --git a/secrets/woodpecker-server-env.age b/secrets/woodpecker-server-env.age new file mode 100644 index 0000000..944285b Binary files /dev/null and b/secrets/woodpecker-server-env.age differ