Merge pull request #133984 from ju1m/sourcehut

nixos/sourcehut: updates, fixes, hardening
This commit is contained in:
tomberek 2021-12-28 22:29:36 -05:00 committed by GitHub
commit 94cb489156
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
24 changed files with 2149 additions and 283 deletions

View File

@ -20,7 +20,7 @@
<title>Configuration Options</title>
<variablelist xml:id="configuration-variable-list">
<xsl:for-each select="attrs">
<xsl:variable name="id" select="concat('opt-', str:replace(str:replace(str:replace(attr[@name = 'name']/string/@value, '*', '_'), '&lt;', '_'), '>', '_'))" />
<xsl:variable name="id" select="concat('opt-', str:replace(str:replace(str:replace(str:replace(attr[@name = 'name']/string/@value, '*', '_'), '&lt;', '_'), '>', '_'), ':', '_'))" />
<varlistentry>
<term xlink:href="#{$id}">
<xsl:attribute name="xml:id"><xsl:value-of select="$id"/></xsl:attribute>

File diff suppressed because it is too large Load Diff

View File

@ -1,66 +1,375 @@
{ config, pkgs, lib }:
serviceCfg: serviceDrv: iniKey: attrs:
srv:
{ configIniOfService
, srvsrht ? "${srv}srht" # Because "buildsrht" does not follow that pattern (missing an "s").
, iniKey ? "${srv}.sr.ht"
, webhooks ? false
, extraTimers ? {}
, mainService ? {}
, extraServices ? {}
, extraConfig ? {}
, port
}:
{ config, lib, pkgs, ... }:
with lib;
let
inherit (config.services) postgresql;
redis = config.services.redis.servers."sourcehut-${srvsrht}";
inherit (config.users) users;
cfg = config.services.sourcehut;
cfgIni = cfg.settings."${iniKey}";
pgSuperUser = config.services.postgresql.superUser;
setupDB = pkgs.writeScript "${serviceDrv.pname}-gen-db" ''
#! ${cfg.python}/bin/python
from ${serviceDrv.pname}.app import db
db.create()
'';
configIni = configIniOfService srv;
srvCfg = cfg.${srv};
baseService = serviceName: { allowStripe ? false }: extraService: let
runDir = "/run/sourcehut/${serviceName}";
rootDir = "/run/sourcehut/chroots/${serviceName}";
in
mkMerge [ extraService {
after = [ "network.target" ] ++
optional cfg.postgresql.enable "postgresql.service" ++
optional cfg.redis.enable "redis-sourcehut-${srvsrht}.service";
requires =
optional cfg.postgresql.enable "postgresql.service" ++
optional cfg.redis.enable "redis-sourcehut-${srvsrht}.service";
path = [ pkgs.gawk ];
environment.HOME = runDir;
serviceConfig = {
User = mkDefault srvCfg.user;
Group = mkDefault srvCfg.group;
RuntimeDirectory = [
"sourcehut/${serviceName}"
# Used by *srht-keys which reads ../config.ini
"sourcehut/${serviceName}/subdir"
"sourcehut/chroots/${serviceName}"
];
RuntimeDirectoryMode = "2750";
# No need for the chroot path once inside the chroot
InaccessiblePaths = [ "-+${rootDir}" ];
# g+rx is for group members (eg. fcgiwrap or nginx)
# to read Git/Mercurial repositories, buildlogs, etc.
# o+x is for intermediate directories created by BindPaths= and like,
# as they're owned by root:root.
UMask = "0026";
RootDirectory = rootDir;
RootDirectoryStartOnly = true;
PrivateTmp = true;
MountAPIVFS = true;
# config.ini is looked up in there, before /etc/srht/config.ini
# Note that it fails to be set in ExecStartPre=
WorkingDirectory = mkDefault ("-"+runDir);
BindReadOnlyPaths = [
builtins.storeDir
"/etc"
"/run/booted-system"
"/run/current-system"
"/run/systemd"
] ++
optional cfg.postgresql.enable "/run/postgresql" ++
optional cfg.redis.enable "/run/redis-sourcehut-${srvsrht}";
# LoadCredential= are unfortunately not available in ExecStartPre=
# Hence this one is run as root (the +) with RootDirectoryStartOnly=
# to reach credentials wherever they are.
# Note that each systemd service gets its own ${runDir}/config.ini file.
ExecStartPre = mkBefore [("+"+pkgs.writeShellScript "${serviceName}-credentials" ''
set -x
# Replace values begining with a '<' by the content of the file whose name is after.
gawk '{ if (match($0,/^([^=]+=)<(.+)/,m)) { getline f < m[2]; print m[1] f } else print $0 }' ${configIni} |
${optionalString (!allowStripe) "gawk '!/^stripe-secret-key=/' |"}
install -o ${srvCfg.user} -g root -m 400 /dev/stdin ${runDir}/config.ini
'')];
# The following options are only for optimizing:
# systemd-analyze security
AmbientCapabilities = "";
CapabilityBoundingSet = "";
# ProtectClock= adds DeviceAllow=char-rtc r
DeviceAllow = "";
LockPersonality = true;
MemoryDenyWriteExecute = true;
NoNewPrivileges = true;
PrivateDevices = true;
PrivateMounts = true;
PrivateNetwork = mkDefault false;
PrivateUsers = true;
ProcSubset = "pid";
ProtectClock = true;
ProtectControlGroups = true;
ProtectHome = true;
ProtectHostname = true;
ProtectKernelLogs = true;
ProtectKernelModules = true;
ProtectKernelTunables = true;
ProtectProc = "invisible";
ProtectSystem = "strict";
RemoveIPC = true;
RestrictAddressFamilies = [ "AF_UNIX" "AF_INET" "AF_INET6" ];
RestrictNamespaces = true;
RestrictRealtime = true;
RestrictSUIDSGID = true;
#SocketBindAllow = [ "tcp:${toString srvCfg.port}" "tcp:${toString srvCfg.prometheusPort}" ];
#SocketBindDeny = "any";
SystemCallFilter = [
"@system-service"
"~@aio" "~@keyring" "~@memlock" "~@privileged" "~@resources" "~@timer"
"@chown" "@setuid"
];
SystemCallArchitectures = "native";
};
} ];
in
with serviceCfg; with lib; recursiveUpdate
{
environment.HOME = statePath;
path = [ config.services.postgresql.package ] ++ (attrs.path or [ ]);
restartTriggers = [ config.environment.etc."sr.ht/config.ini".source ];
serviceConfig = {
Type = "simple";
User = user;
Group = user;
Restart = "always";
WorkingDirectory = statePath;
} // (if (cfg.statePath == "/var/lib/sourcehut/${serviceDrv.pname}") then {
StateDirectory = [ "sourcehut/${serviceDrv.pname}" ];
} else {})
;
options.services.sourcehut.${srv} = {
enable = mkEnableOption "${srv} service";
preStart = ''
if ! test -e ${statePath}/db; then
# Setup the initial database
${setupDB}
user = mkOption {
type = types.str;
default = srvsrht;
description = ''
User for ${srv}.sr.ht.
'';
};
# Set the initial state of the database for future database upgrades
if test -e ${cfg.python}/bin/${serviceDrv.pname}-migrate; then
# Run alembic stamp head once to tell alembic the schema is up-to-date
${cfg.python}/bin/${serviceDrv.pname}-migrate stamp head
fi
group = mkOption {
type = types.str;
default = srvsrht;
description = ''
Group for ${srv}.sr.ht.
Membership grants access to the Git/Mercurial repositories by default,
but not to the config.ini file (where secrets are).
'';
};
printf "%s" "${serviceDrv.version}" > ${statePath}/db
fi
port = mkOption {
type = types.port;
default = port;
description = ''
Port on which the "${srv}" backend should listen.
'';
};
# Update copy of each users' profile to the latest
# See https://lists.sr.ht/~sircmpwn/sr.ht-admins/<20190302181207.GA13778%40cirno.my.domain>
if ! test -e ${statePath}/webhook; then
# Update ${iniKey}'s users' profile copy to the latest
${cfg.python}/bin/srht-update-profiles ${iniKey}
redis = {
host = mkOption {
type = types.str;
default = "unix:/run/redis-sourcehut-${srvsrht}/redis.sock?db=0";
example = "redis://shared.wireguard:6379/0";
description = ''
The redis host URL. This is used for caching and temporary storage, and must
be shared between nodes (e.g. git1.sr.ht and git2.sr.ht), but need not be
shared between services. It may be shared between services, however, with no
ill effect, if this better suits your infrastructure.
'';
};
};
touch ${statePath}/webhook
fi
postgresql = {
database = mkOption {
type = types.str;
default = "${srv}.sr.ht";
description = ''
PostgreSQL database name for the ${srv}.sr.ht service,
used if <xref linkend="opt-services.sourcehut.postgresql.enable"/> is <literal>true</literal>.
'';
};
};
${optionalString (builtins.hasAttr "migrate-on-upgrade" cfgIni && cfgIni.migrate-on-upgrade == "yes") ''
if [ "$(cat ${statePath}/db)" != "${serviceDrv.version}" ]; then
# Manage schema migrations using alembic
${cfg.python}/bin/${serviceDrv.pname}-migrate -a upgrade head
gunicorn = {
extraArgs = mkOption {
type = with types; listOf str;
default = ["--timeout 120" "--workers 1" "--log-level=info"];
description = "Extra arguments passed to Gunicorn.";
};
};
} // optionalAttrs webhooks {
webhooks = {
extraArgs = mkOption {
type = with types; listOf str;
default = ["--loglevel DEBUG" "--pool eventlet" "--without-heartbeat"];
description = "Extra arguments passed to the Celery responsible for webhooks.";
};
celeryConfig = mkOption {
type = types.lines;
default = "";
description = "Content of the <literal>celeryconfig.py</literal> used by the Celery responsible for webhooks.";
};
};
};
# Mark down current package version
printf "%s" "${serviceDrv.version}" > ${statePath}/db
fi
''}
config = lib.mkIf (cfg.enable && srvCfg.enable) (mkMerge [ extraConfig {
users = {
users = {
"${srvCfg.user}" = {
isSystemUser = true;
group = mkDefault srvCfg.group;
description = mkDefault "sourcehut user for ${srv}.sr.ht";
};
};
groups = {
"${srvCfg.group}" = { };
} // optionalAttrs (cfg.postgresql.enable
&& hasSuffix "0" (postgresql.settings.unix_socket_permissions or "")) {
"postgres".members = [ srvCfg.user ];
} // optionalAttrs (cfg.redis.enable
&& hasSuffix "0" (redis.settings.unixsocketperm or "")) {
"redis-sourcehut-${srvsrht}".members = [ srvCfg.user ];
};
};
${attrs.preStart or ""}
'';
services.nginx = mkIf cfg.nginx.enable {
virtualHosts."${srv}.${cfg.settings."sr.ht".global-domain}" = mkMerge [ {
forceSSL = mkDefault true;
locations."/".proxyPass = "http://${cfg.listenAddress}:${toString srvCfg.port}";
locations."/static" = {
root = "${pkgs.sourcehut.${srvsrht}}/${pkgs.sourcehut.python.sitePackages}/${srvsrht}";
extraConfig = mkDefault ''
expires 30d;
'';
};
} cfg.nginx.virtualHost ];
};
services.postgresql = mkIf cfg.postgresql.enable {
authentication = ''
local ${srvCfg.postgresql.database} ${srvCfg.user} trust
'';
ensureDatabases = [ srvCfg.postgresql.database ];
ensureUsers = map (name: {
inherit name;
ensurePermissions = { "DATABASE \"${srvCfg.postgresql.database}\"" = "ALL PRIVILEGES"; };
}) [srvCfg.user];
};
services.sourcehut.services = mkDefault (filter (s: cfg.${s}.enable)
[ "builds" "dispatch" "git" "hg" "hub" "lists" "man" "meta" "pages" "paste" "todo" ]);
services.sourcehut.settings = mkMerge [
{
"${srv}.sr.ht".origin = mkDefault "https://${srv}.${cfg.settings."sr.ht".global-domain}";
}
(mkIf cfg.postgresql.enable {
"${srv}.sr.ht".connection-string = mkDefault "postgresql:///${srvCfg.postgresql.database}?user=${srvCfg.user}&host=/run/postgresql";
})
];
services.redis.servers."sourcehut-${srvsrht}" = mkIf cfg.redis.enable {
enable = true;
databases = 3;
syslog = true;
# TODO: set a more informed value
save = mkDefault [ [1800 10] [300 100] ];
settings = {
# TODO: set a more informed value
maxmemory = "128MB";
maxmemory-policy = "volatile-ttl";
};
};
systemd.services = mkMerge [
{
"${srvsrht}" = baseService srvsrht { allowStripe = srv == "meta"; } (mkMerge [
{
description = "sourcehut ${srv}.sr.ht website service";
before = optional cfg.nginx.enable "nginx.service";
wants = optional cfg.nginx.enable "nginx.service";
wantedBy = [ "multi-user.target" ];
path = optional cfg.postgresql.enable postgresql.package;
# Beware: change in credentials' content will not trigger restart.
restartTriggers = [ configIni ];
serviceConfig = {
Type = "simple";
Restart = mkDefault "always";
#RestartSec = mkDefault "2min";
StateDirectory = [ "sourcehut/${srvsrht}" ];
StateDirectoryMode = "2750";
ExecStart = "${cfg.python}/bin/gunicorn ${srvsrht}.app:app --name ${srvsrht} --bind ${cfg.listenAddress}:${toString srvCfg.port} " + concatStringsSep " " srvCfg.gunicorn.extraArgs;
};
preStart = let
version = pkgs.sourcehut.${srvsrht}.version;
stateDir = "/var/lib/sourcehut/${srvsrht}";
in mkBefore ''
set -x
# Use the /run/sourcehut/${srvsrht}/config.ini
# installed by a previous ExecStartPre= in baseService
cd /run/sourcehut/${srvsrht}
if test ! -e ${stateDir}/db; then
# Setup the initial database.
# Note that it stamps the alembic head afterward
${cfg.python}/bin/${srvsrht}-initdb
echo ${version} >${stateDir}/db
fi
${optionalString cfg.settings.${iniKey}.migrate-on-upgrade ''
if [ "$(cat ${stateDir}/db)" != "${version}" ]; then
# Manage schema migrations using alembic
${cfg.python}/bin/${srvsrht}-migrate -a upgrade head
echo ${version} >${stateDir}/db
fi
''}
# Update copy of each users' profile to the latest
# See https://lists.sr.ht/~sircmpwn/sr.ht-admins/<20190302181207.GA13778%40cirno.my.domain>
if test ! -e ${stateDir}/webhook; then
# Update ${iniKey}'s users' profile copy to the latest
${cfg.python}/bin/srht-update-profiles ${iniKey}
touch ${stateDir}/webhook
fi
'';
} mainService ]);
}
(mkIf webhooks {
"${srvsrht}-webhooks" = baseService "${srvsrht}-webhooks" {}
{
description = "sourcehut ${srv}.sr.ht webhooks service";
after = [ "${srvsrht}.service" ];
wantedBy = [ "${srvsrht}.service" ];
partOf = [ "${srvsrht}.service" ];
preStart = ''
cp ${pkgs.writeText "${srvsrht}-webhooks-celeryconfig.py" srvCfg.webhooks.celeryConfig} \
/run/sourcehut/${srvsrht}-webhooks/celeryconfig.py
'';
serviceConfig = {
Type = "simple";
Restart = "always";
ExecStart = "${cfg.python}/bin/celery --app ${srvsrht}.webhooks worker --hostname ${srvsrht}-webhooks@%%h " + concatStringsSep " " srvCfg.webhooks.extraArgs;
# Avoid crashing: os.getloadavg()
ProcSubset = mkForce "all";
};
};
})
(mapAttrs (timerName: timer: (baseService timerName {} (mkMerge [
{
description = "sourcehut ${timerName} service";
after = [ "network.target" "${srvsrht}.service" ];
serviceConfig = {
Type = "oneshot";
ExecStart = "${cfg.python}/bin/${timerName}";
};
}
(timer.service or {})
]))) extraTimers)
(mapAttrs (serviceName: extraService: baseService serviceName {} (mkMerge [
{
description = "sourcehut ${serviceName} service";
# So that extraServices have the PostgreSQL database initialized.
after = [ "${srvsrht}.service" ];
wantedBy = [ "${srvsrht}.service" ];
partOf = [ "${srvsrht}.service" ];
serviceConfig = {
Type = "simple";
Restart = mkDefault "always";
};
}
extraService
])) extraServices)
];
systemd.timers = mapAttrs (timerName: timer:
{
description = "sourcehut timer for ${timerName}";
wantedBy = [ "timers.target" ];
inherit (timer) timerConfig;
}) extraTimers;
} ]);
}
(builtins.removeAttrs attrs [ "path" "preStart" ])

View File

@ -14,13 +14,12 @@
<title>Basic usage</title>
<para>
Sourcehut is a Python and Go based set of applications.
<literal><link linkend="opt-services.sourcehut.enable">services.sourcehut</link></literal>
by default will use
This NixOS module also provides basic configuration integrating Sourcehut into locally running
<literal><link linkend="opt-services.nginx.enable">services.nginx</link></literal>,
<literal><link linkend="opt-services.nginx.enable">services.redis</link></literal>,
<literal><link linkend="opt-services.nginx.enable">services.cron</link></literal>,
<literal><link linkend="opt-services.redis.servers">services.redis.servers.sourcehut</link></literal>,
<literal><link linkend="opt-services.postfix.enable">services.postfix</link></literal>
and
<literal><link linkend="opt-services.postgresql.enable">services.postgresql</link></literal>.
<literal><link linkend="opt-services.postgresql.enable">services.postgresql</link></literal> services.
</para>
<para>
@ -42,18 +41,23 @@ in {
services.sourcehut = {
<link linkend="opt-services.sourcehut.enable">enable</link> = true;
<link linkend="opt-services.sourcehut.originBase">originBase</link> = fqdn;
<link linkend="opt-services.sourcehut.services">services</link> = [ "meta" "man" "git" ];
<link linkend="opt-services.sourcehut.git.enable">git.enable</link> = true;
<link linkend="opt-services.sourcehut.man.enable">man.enable</link> = true;
<link linkend="opt-services.sourcehut.meta.enable">meta.enable</link> = true;
<link linkend="opt-services.sourcehut.nginx.enable">nginx.enable</link> = true;
<link linkend="opt-services.sourcehut.postfix.enable">postfix.enable</link> = true;
<link linkend="opt-services.sourcehut.postgresql.enable">postgresql.enable</link> = true;
<link linkend="opt-services.sourcehut.redis.enable">redis.enable</link> = true;
<link linkend="opt-services.sourcehut.settings">settings</link> = {
"sr.ht" = {
environment = "production";
global-domain = fqdn;
origin = "https://${fqdn}";
# Produce keys with srht-keygen from <package>sourcehut.coresrht</package>.
network-key = "SECRET";
service-key = "SECRET";
network-key = "/run/keys/path/to/network-key";
service-key = "/run/keys/path/to/service-key";
};
webhooks.private-key= "SECRET";
webhooks.private-key= "/run/keys/path/to/webhook-key";
};
};

View File

@ -436,6 +436,7 @@ in
solanum = handleTest ./solanum.nix {};
solr = handleTest ./solr.nix {};
sonarr = handleTest ./sonarr.nix {};
sourcehut = handleTest ./sourcehut.nix {};
spacecookie = handleTest ./spacecookie.nix {};
spark = handleTestOn ["x86_64-linux"] ./spark {};
sslh = handleTest ./sslh.nix {};

View File

@ -1,29 +1,197 @@
import ./make-test-python.nix ({ pkgs, ... }:
import ./make-test-python.nix ({ pkgs, lib, ... }:
let
domain = "sourcehut.localdomain";
# Note that wildcard certificates just under the TLD (eg. *.com)
# would be rejected by clients like curl.
tls-cert = pkgs.runCommand "selfSignedCerts" { buildInputs = [ pkgs.openssl ]; } ''
openssl req -x509 -newkey rsa:4096 -keyout key.pem -out cert.pem -nodes -days 36500 \
-subj '/CN=${domain}' -extensions v3_req \
-addext 'subjectAltName = DNS:*.${domain}'
install -D -t $out key.pem cert.pem
'';
images = {
nixos.unstable.x86_64 =
let
systemConfig = { pkgs, ... }: {
# passwordless ssh server
services.openssh = {
enable = true;
permitRootLogin = "yes";
extraConfig = "PermitEmptyPasswords yes";
};
users = {
mutableUsers = false;
# build user
extraUsers."build" = {
isNormalUser = true;
uid = 1000;
extraGroups = [ "wheel" ];
password = "";
};
users.root.password = "";
};
security.sudo.wheelNeedsPassword = false;
nix.trustedUsers = [ "root" "build" ];
documentation.nixos.enable = false;
# builds.sr.ht-image-specific network settings
networking = {
hostName = "build";
dhcpcd.enable = false;
defaultGateway.address = "10.0.2.2";
usePredictableInterfaceNames = false;
interfaces."eth0".ipv4.addresses = [{
address = "10.0.2.15";
prefixLength = 25;
}];
enableIPv6 = false;
nameservers = [
# OpenNIC anycast
"185.121.177.177"
"169.239.202.202"
# Google
"8.8.8.8"
];
firewall.allowedTCPPorts = [ 22 ];
};
environment.systemPackages = [
pkgs.gitMinimal
#pkgs.mercurial
pkgs.curl
pkgs.gnupg
];
};
qemuConfig = { pkgs, ... }: {
imports = [ systemConfig ];
fileSystems."/".device = "/dev/disk/by-label/nixos";
boot.initrd.availableKernelModules = [
"ahci"
"ehci_pci"
"sd_mod"
"usb_storage"
"usbhid"
"virtio_balloon"
"virtio_blk"
"virtio_pci"
"virtio_ring"
"xhci_pci"
];
boot.loader = {
grub = {
version = 2;
device = "/dev/vda";
};
timeout = 0;
};
};
config = (import (pkgs.path + "/nixos/lib/eval-config.nix") {
inherit pkgs; modules = [ qemuConfig ];
system = "x86_64-linux";
}).config;
in
import (pkgs.path + "/nixos/lib/make-disk-image.nix") {
inherit pkgs lib config;
diskSize = 16000;
format = "qcow2-compressed";
contents = [
{ source = pkgs.writeText "gitconfig" ''
[user]
name = builds.sr.ht
email = build@sr.ht
'';
target = "/home/build/.gitconfig";
user = "build";
group = "users";
mode = "644";
}
];
};
};
in
{
name = "sourcehut";
meta.maintainers = [ pkgs.lib.maintainers.tomberek ];
machine = { config, pkgs, ... }: {
virtualisation.memorySize = 2048;
networking.firewall.allowedTCPPorts = [ 80 ];
machine = { config, pkgs, nodes, ... }: {
# buildsrht needs space
virtualisation.diskSize = 4 * 1024;
virtualisation.memorySize = 2 * 1024;
networking.domain = domain;
networking.extraHosts = ''
${config.networking.primaryIPAddress} meta.${domain}
${config.networking.primaryIPAddress} builds.${domain}
'';
services.sourcehut = {
enable = true;
services = [ "meta" ];
originBase = "sourcehut";
settings."sr.ht".service-key = "8888888888888888888888888888888888888888888888888888888888888888";
settings."sr.ht".network-key = "0000000000000000000000000000000000000000000=";
settings.webhooks.private-key = "0000000000000000000000000000000000000000000=";
services = [ "meta" "builds" ];
nginx.enable = true;
nginx.virtualHost = {
forceSSL = true;
sslCertificate = "${tls-cert}/cert.pem";
sslCertificateKey = "${tls-cert}/key.pem";
};
postgresql.enable = true;
redis.enable = true;
meta.enable = true;
builds = {
enable = true;
# FIXME: see why it does not seem to activate fully.
#enableWorker = true;
inherit images;
};
settings."sr.ht" = {
global-domain = config.networking.domain;
service-key = pkgs.writeText "service-key" "8b327279b77e32a3620e2fc9aabce491cc46e7d821fd6713b2a2e650ce114d01";
network-key = pkgs.writeText "network-key" "cEEmc30BRBGkgQZcHFksiG7hjc6_dK1XR2Oo5Jb9_nQ=";
};
settings."builds.sr.ht" = {
oauth-client-secret = pkgs.writeText "buildsrht-oauth-client-secret" "2260e9c4d9b8dcedcef642860e0504bc";
oauth-client-id = "299db9f9c2013170";
};
settings.webhooks.private-key = pkgs.writeText "webhook-key" "Ra3IjxgFiwG9jxgp4WALQIZw/BMYt30xWiOsqD0J7EA=";
};
networking.firewall.allowedTCPPorts = [ 443 ];
security.pki.certificateFiles = [ "${tls-cert}/cert.pem" ];
services.nginx = {
enable = true;
recommendedGzipSettings = true;
recommendedOptimisation = true;
recommendedTlsSettings = true;
recommendedProxySettings = true;
};
services.postgresql = {
enable = true;
enableTCPIP = false;
settings.unix_socket_permissions = "0770";
};
};
testScript = ''
start_all()
machine.wait_for_unit("multi-user.target")
# Testing metasrht
machine.wait_for_unit("metasrht-api.service")
machine.wait_for_unit("metasrht.service")
machine.wait_for_open_port(5000)
machine.succeed("curl -sL http://localhost:5000 | grep meta.sourcehut")
machine.succeed("curl -sL http://localhost:5000 | grep meta.${domain}")
machine.succeed("curl -sL http://meta.${domain} | grep meta.${domain}")
# Testing buildsrht
machine.wait_for_unit("buildsrht.service")
machine.wait_for_open_port(5002)
machine.succeed("curl -sL http://localhost:5002 | grep builds.${domain}")
#machine.wait_for_unit("buildsrht-worker.service")
'';
})

View File

@ -11,26 +11,31 @@
, python
}:
let
version = "0.66.7";
buildWorker = src: buildGoModule {
inherit src version;
pname = "builds-sr-ht-worker";
vendorSha256 = "sha256-giOaldV46aBqXyFH/cQVsbUr6Rb4VMhbBO86o48tRZY=";
};
in
buildPythonPackage rec {
inherit version;
pname = "buildsrht";
version = "0.74.17";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "builds.sr.ht";
rev = version;
sha256 = "sha256-2MLs/DOXHjEYarXDVUcPZe3o0fmZbzVxn528SE72lhM=";
sha256 = "sha256-6Yc33lkhozpnx8e6yukUfo+/Qw5mwpJQQKuYbC7uqcU=";
};
buildWorker = src: buildGoModule {
inherit src version;
pname = "builds-sr-ht-worker";
vendorSha256 = "sha256-Pf1M9a43eK4jr6QMi6kRHA8DodXQU0pqq9ua5VC3ER0=";
};
in
buildPythonPackage rec {
inherit src version;
pname = "buildsrht";
patches = [
# Revert change breaking Unix socket support for Redis
patches/redis-socket/build/0001-Revert-Add-build-submission-and-queue-monitoring.patch
];
nativeBuildInputs = srht.nativeBuildInputs;
propagatedBuildInputs = [
@ -56,10 +61,12 @@ buildPythonPackage rec {
cp ${buildWorker "${src}/worker"}/bin/worker $out/bin/builds.sr.ht-worker
'';
pythonImportsCheck = [ "buildsrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/builds.sr.ht";
description = "Continuous integration service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -25,17 +25,16 @@
, sassc
, nodejs
, redis
, writeText
}:
buildPythonPackage rec {
pname = "srht";
version = "0.67.4";
version = "0.68.13";
src = fetchgit {
url = "https://git.sr.ht/~sircmpwn/core.sr.ht";
rev = version;
sha256 = "sha256-XvzFfcBK5Mq8p7xEBAF/eupUE1kkUBh5k+ByM/WA9bc=";
sha256 = "sha256-LPyEfpNlmod18Fj16xpihKOrsU/hQUfAeOmWMmUeVPQ=";
fetchSubmodules = true;
};
@ -46,6 +45,7 @@ buildPythonPackage rec {
};
patches = [
# Disable check for npm
./disable-npm-install.patch
];
@ -87,6 +87,7 @@ buildPythonPackage rec {
'';
dontUseSetuptoolsCheck = true;
pythonImportsCheck = [ "srht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/srht";

View File

@ -22,6 +22,7 @@ let
listssrht = self.callPackage ./lists.nix { };
mansrht = self.callPackage ./man.nix { };
metasrht = self.callPackage ./meta.nix { };
pagessrht = self.callPackage ./pages.nix { };
pastesrht = self.callPackage ./paste.nix { };
todosrht = self.callPackage ./todo.nix { };
@ -40,6 +41,7 @@ with python.pkgs; recurseIntoAttrs {
listssrht = toPythonApplication listssrht;
mansrht = toPythonApplication mansrht;
metasrht = toPythonApplication metasrht;
pagessrht = pagessrht;
pastesrht = toPythonApplication pastesrht;
todosrht = toPythonApplication todosrht;
}

View File

@ -9,13 +9,13 @@
buildPythonPackage rec {
pname = "dispatchsrht";
version = "0.15.8";
version = "0.15.34";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "dispatch.sr.ht";
rev = version;
sha256 = "sha256-zWCGPjIgMKHXHJUs9aciV7IFgo0rpahon6KXHDwcfss=";
sha256 = "sha256-bZ4ZKohMozZIyP0TUgxETOECib4XGUv29+Mg8ZsoMf8=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -31,10 +31,12 @@ buildPythonPackage rec {
export SRHT_PATH=${srht}/${python.sitePackages}/srht
'';
pythonImportsCheck = [ "dispatchsrht" ];
meta = with lib; {
homepage = "https://dispatch.sr.ht/~sircmpwn/dispatch.sr.ht";
description = "Task dispatcher and service integration tool for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -8,13 +8,13 @@
, scmsrht
}:
let
version = "0.72.8";
version = "0.76.4";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "git.sr.ht";
rev = version;
sha256 = "sha256-AB2uzajO5PtcpJfbOOTfuDFM6is5K39v3AZJ1hShRNc=";
sha256 = "sha256-diUkQpB/ivg8JTaoTcSyKr9Q9LZiMo6qVInBDPceklc=";
};
buildShell = src: buildGoModule {
@ -32,13 +32,13 @@ let
buildKeys = src: buildGoModule {
inherit src version;
pname = "gitsrht-keys";
vendorSha256 = "1d94cqy7x0q0agwg515xxsbl70b3qrzxbzsyjhn1pbyj532brn7f";
vendorSha256 = "sha256-9pojS69HCKVHUceyOpGtv9ewcxFD4WsOVsEzkmWJkF4=";
};
buildUpdateHook = src: buildGoModule {
inherit src version;
pname = "gitsrht-update-hook";
vendorSha256 = "0fwzqpjv8x5y3w3bfjd0x0cvqjjak23m0zj88hf32jpw49xmjkih";
vendorSha256 = "sha256-sBlG7EFqdDm7CkAHVX50Mf4N3sl1rPNmWExG/bfbfGA=";
};
updateHook = buildUpdateHook "${src}/gitsrht-update-hook";
@ -72,10 +72,12 @@ buildPythonPackage rec {
inherit updateHook;
};
pythonImportsCheck = [ "gitsrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/git.sr.ht";
description = "Git repository hosting service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -10,12 +10,12 @@
buildPythonPackage rec {
pname = "hgsrht";
version = "0.27.4";
version = "0.29.3";
src = fetchhg {
url = "https://hg.sr.ht/~sircmpwn/hg.sr.ht";
rev = version;
sha256 = "1c0qfi0gmbfngvds6917fy9ii2iglawn429757rh7b4bvzn7n6mr";
sha256 = "y8gKaamwD5lsYqO1SkxMcn3E2TWidHAo2slvEU+8ovg=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -32,10 +32,12 @@ buildPythonPackage rec {
export SRHT_PATH=${srht}/${python.sitePackages}/srht
'';
pythonImportsCheck = [ "hgsrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/hg.sr.ht";
description = "Mercurial repository hosting service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -6,13 +6,13 @@
buildPythonPackage rec {
pname = "hubsrht";
version = "0.13.1";
version = "0.14.4";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "hub.sr.ht";
rev = version;
sha256 = "sha256-Kqzy4mh5Nn1emzHBco/LVuXro/tW3NX+OYqdEwBSQ/U=";
sha256 = "sha256-7HF+jykWGqzPWA0YtJZQZU7pnID1yexcqLkEf2HpnSs=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -26,11 +26,12 @@ buildPythonPackage rec {
'';
dontUseSetuptoolsCheck = true;
pythonImportsCheck = [ "hubsrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/hub.sr.ht";
description = "Project hub service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -12,13 +12,13 @@
buildPythonPackage rec {
pname = "listssrht";
version = "0.48.19";
version = "0.51.0";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "lists.sr.ht";
rev = version;
sha256 = "sha256-bsakEMyvWaxiE4/SGcAP4mlGG9jkdHfFxpt9H+TJn/8=";
sha256 = "sha256-iywZ6G5E4AJevg/Q1LoB7JMJxBcsAnbhiND++mFy/bw=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -37,10 +37,12 @@ buildPythonPackage rec {
export SRHT_PATH=${srht}/${python.sitePackages}/srht
'';
pythonImportsCheck = [ "listssrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/lists.sr.ht";
description = "Mailing list service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -8,13 +8,13 @@
buildPythonPackage rec {
pname = "mansrht";
version = "0.15.12";
version = "0.15.22";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "man.sr.ht";
rev = version;
sha256 = "sha256-MqH/8K9XRvEg6P7GHE6XXtWnhDP3wT8iGoNaFtYQbio=";
sha256 = "sha256-curouf+eNCKprDI23blGs4AzJMry6zlCLDt/+0j5c8A=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -29,10 +29,12 @@ buildPythonPackage rec {
export SRHT_PATH=${srht}/${python.sitePackages}/srht
'';
pythonImportsCheck = [ "mansrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/man.sr.ht";
description = "Wiki service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -18,19 +18,19 @@
, python
}:
let
version = "0.53.14";
version = "0.57.2";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "meta.sr.ht";
rev = version;
sha256 = "sha256-/+r/XLDkcSTW647xPMh5bcJmR2xZNNH74AJ5jemna2k=";
sha256 = "sha256-+ksfAOuch/fLkFLYU52Ug0Hf0EoERy+oCwa9g+GKuAA=";
};
buildApi = src: buildGoModule {
inherit src version;
pname = "metasrht-api";
vendorSha256 = "sha256-eZyDrr2VcNMxI++18qUy7LA1Q1YDlWCoRtl00L8lfR4=";
vendorSha256 = "sha256-vo+YbMyo/Eal7hbFxP9hwIW2cePJcGFszoDRCCzFYdM=";
};
in
@ -38,6 +38,11 @@ buildPythonPackage rec {
pname = "metasrht";
inherit version src;
patches = [
# Revert change breaking Unix socket support for Redis
patches/redis-socket/meta/0001-Revert-Add-webhook-queue-monitoring.patch
];
nativeBuildInputs = srht.nativeBuildInputs;
propagatedBuildInputs = [
@ -66,10 +71,12 @@ buildPythonPackage rec {
cp ${buildApi "${src}/api/"}/bin/api $out/bin/metasrht-api
'';
pythonImportsCheck = [ "metasrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/meta.sr.ht";
description = "Account management service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -0,0 +1,30 @@
{ lib
, fetchFromSourcehut
, buildGoModule
}:
buildGoModule rec {
pname = "pagessrht";
version = "0.5.2";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "pages.sr.ht";
rev = version;
sha256 = "sha256-yEM122uhF0MNkMlNXyvBSfkLogRQETeuBl2K66kivac=";
};
vendorSha256 = "sha256-udr+1y5ApQCSPhs3yQTTi9QfzRbz0A9COYuFMjQGa74=";
postInstall = ''
mkdir -p $out/share/sql/
cp -r -t $out/share/sql/ schema.sql migrations
'';
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/pages.sr.ht";
description = "Web hosting service for the sr.ht network";
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -8,13 +8,13 @@
buildPythonPackage rec {
pname = "pastesrht";
version = "0.12.1";
version = "0.13.6";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "paste.sr.ht";
rev = version;
sha256 = "sha256-QQhd2LeH9BLmlHilhsv+9fZ+RPNmEMSmOpFA3dsMBFc=";
sha256 = "sha256-Khcqk86iD9nxiKXN3+8mSLNoDau2qXNFOrLdkVu+rH8=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -29,10 +29,12 @@ buildPythonPackage rec {
export SRHT_PATH=${srht}/${python.sitePackages}/srht
'';
pythonImportsCheck = [ "pastesrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/paste.sr.ht";
description = "Ad-hoc text file hosting service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -0,0 +1,69 @@
From 069b03f85847ed4a9223183b62ee53f420838911 Mon Sep 17 00:00:00 2001
From: Julien Moutinho <julm+srht@sourcephile.fr>
Date: Thu, 16 Dec 2021 04:54:24 +0100
Subject: [PATCH builds.sr.ht] Revert "Add build submission and queue
monitoring"
This reverts commit 690f1aa16c77e418dc40109cd5e8fdf4a7ed947a.
This has broken Unix socket support for Redis
See https://lists.sr.ht/~sircmpwn/sr.ht-dev/%3C20211208082636.65665-1-me%40ignaskiela.eu%3E#%3C20211216033723.wefibfulfjhqnhem@sourcephile.fr%3E
---
buildsrht/app.py | 3 ---
buildsrht/runner.py | 9 +--------
2 files changed, 1 insertion(+), 11 deletions(-)
diff --git a/buildsrht/app.py b/buildsrht/app.py
index e5321a2..7c9977c 100644
--- a/buildsrht/app.py
+++ b/buildsrht/app.py
@@ -36,9 +36,6 @@ class BuildApp(SrhtFlask):
self.register_blueprint(secrets)
self.register_blueprint(gql_blueprint)
- from buildsrht.runner import builds_queue_metrics_collector
- self.metrics_registry.register(builds_queue_metrics_collector)
-
@self.context_processor
def inject():
return {
diff --git a/buildsrht/runner.py b/buildsrht/runner.py
index 7773452..0389c8e 100644
--- a/buildsrht/runner.py
+++ b/buildsrht/runner.py
@@ -5,13 +5,10 @@ from srht.config import cfg
from srht.database import db
from srht.email import send_email
from srht.oauth import UserType
-from srht.metrics import RedisQueueCollector
-from prometheus_client import Counter
allow_free = cfg("builds.sr.ht", "allow-free", default="no") == "yes"
-builds_broker = cfg("builds.sr.ht", "redis")
-runner = Celery('builds', broker=builds_broker, config_source={
+runner = Celery('builds', broker=cfg("builds.sr.ht", "redis"), config_source={
"CELERY_TASK_SERIALIZER": "json",
"CELERY_ACCEPT_CONTENT": ["json"],
"CELERY_RESULT_SERIALIZER": "json",
@@ -19,9 +16,6 @@ runner = Celery('builds', broker=builds_broker, config_source={
"CELERY_TASK_PROTOCOL": 1
})
-builds_queue_metrics_collector = RedisQueueCollector(builds_broker, "buildsrht_builds", "Number of builds currently in queue")
-builds_submitted = Counter("buildsrht_builds_submited", "Number of builds submitted")
-
def queue_build(job, manifest):
from buildsrht.types import JobStatus
job.status = JobStatus.queued
@@ -34,7 +28,6 @@ def queue_build(job, manifest):
cfg("sr.ht", "owner-email"),
"Cryptocurrency mining attempt on builds.sr.ht")
else:
- builds_submitted.inc()
run_build.delay(job.id, manifest.to_dict())
def requires_payment(user):
--
2.34.0

View File

@ -0,0 +1,48 @@
From d88bee195797c6c294320617ff14798da94cd0f3 Mon Sep 17 00:00:00 2001
From: Julien Moutinho <julm+srht@sourcephile.fr>
Date: Thu, 16 Dec 2021 04:52:08 +0100
Subject: [PATCH meta.sr.ht] Revert "Add webhook queue monitoring"
This reverts commit 9931df3c23094af5179df9ef019ca732b8125dac.
This has broken Unix socket support for Redis.
See https://lists.sr.ht/~sircmpwn/sr.ht-dev/%3C20211208082636.65665-1-me%40ignaskiela.eu%3E#%3C20211216033723.wefibfulfjhqnhem@sourcephile.fr%3E
---
metasrht/app.py | 3 ---
metasrht/webhooks.py | 5 +----
2 files changed, 1 insertion(+), 7 deletions(-)
diff --git a/metasrht/app.py b/metasrht/app.py
index b190875..89c59bc 100644
--- a/metasrht/app.py
+++ b/metasrht/app.py
@@ -49,9 +49,6 @@ class MetaApp(SrhtFlask):
from metasrht.blueprints.billing import billing
self.register_blueprint(billing)
- from metasrht.webhooks import webhook_metrics_collector
- self.metrics_registry.register(webhook_metrics_collector)
-
@self.context_processor
def inject():
return {
diff --git a/metasrht/webhooks.py b/metasrht/webhooks.py
index 3e1149e..3f0ba01 100644
--- a/metasrht/webhooks.py
+++ b/metasrht/webhooks.py
@@ -7,11 +7,8 @@ if not hasattr(db, "session"):
db.init()
from srht.webhook import Event
from srht.webhook.celery import CeleryWebhook, make_worker
-from srht.metrics import RedisQueueCollector
-webhook_broker = cfg("meta.sr.ht", "webhooks", "redis://")
-worker = make_worker(broker=webhook_broker)
-webhook_metrics_collector = RedisQueueCollector(webhook_broker, "srht_webhooks", "Webhook queue length")
+worker = make_worker(broker=cfg("meta.sr.ht", "webhooks", "redis://"))
class UserWebhook(CeleryWebhook):
events = [
--
2.34.0

View File

@ -5,18 +5,17 @@
, redis
, pyyaml
, buildsrht
, writeText
}:
buildPythonPackage rec {
pname = "scmsrht";
version = "0.22.9";
version = "0.22.16"; # Untagged version
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "scm.sr.ht";
rev = version;
sha256 = "sha256-327G6C8FW+iZx+167D7TQsFtV6FGc8MpMVo9L/cUUqU=";
sha256 = "sha256-A4Q7wUc4ag7KRWOkdYXCsbzuFHyJJsM15OjrCoVt9UQ=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -33,11 +32,12 @@ buildPythonPackage rec {
'';
dontUseSetuptoolsCheck = true;
pythonImportsCheck = [ "scmsrht" ];
meta = with lib; {
homepage = "https://git.sr.ht/~sircmpwn/git.sr.ht";
homepage = "https://git.sr.ht/~sircmpwn/scm.sr.ht";
description = "Shared support code for sr.ht source control services.";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -12,13 +12,13 @@
buildPythonPackage rec {
pname = "todosrht";
version = "0.64.14";
version = "0.66.1";
src = fetchFromSourcehut {
owner = "~sircmpwn";
repo = "todo.sr.ht";
rev = version;
sha256 = "sha256-huIAhn6h1F5w5ST4/yBwr82kAzyYwhLu+gpRuOQgnsE=";
sha256 = "sha256-P0xaQpK7O9zipGSIa5jL1O0L/fKt51EMNGt7XndYQ+g=";
};
nativeBuildInputs = srht.nativeBuildInputs;
@ -42,11 +42,12 @@ buildPythonPackage rec {
];
dontUseSetuptoolsCheck = true;
pythonImportsCheck = [ "todosrht" ];
meta = with lib; {
homepage = "https://todo.sr.ht/~sircmpwn/todo.sr.ht";
description = "Ticket tracking service for the sr.ht network";
license = licenses.agpl3;
license = licenses.agpl3Only;
maintainers = with maintainers; [ eadwu ];
};
}

View File

@ -1,8 +1,11 @@
#! /usr/bin/env nix-shell
#! nix-shell -i bash -p git mercurial common-updater-scripts
set -eux -o pipefail
cd "$(dirname "${BASH_SOURCE[0]}")"
cd "$(dirname "${BASH_SOURCE[0]}")" || exit 1
root=../../../..
tmp=$(mktemp -d)
trap 'rm -rf "$tmp"' EXIT
default() {
(cd "$root" && nix-instantiate --eval --strict -A "sourcehut.python.pkgs.$1.meta.position" | sed -re 's/^"(.*):[0-9]+"$/\1/')
@ -13,42 +16,61 @@ version() {
}
src_url() {
(cd "$root" && nix-instantiate --eval --strict -A "sourcehut.python.pkgs.$1.src.drvAttrs.url" | tr -d '"')
nix-instantiate --eval --strict --expr " with import $root {}; let src = sourcehut.python.pkgs.$1.drvAttrs.src; in src.url or src.meta.homepage" | tr -d '"'
}
get_latest_version() {
src="$(src_url "$1")"
tmp=$(mktemp -d)
rm -rf "$tmp"
if [ "$1" = "hgsrht" ]; then
hg clone "$src" "$tmp" &> /dev/null
hg clone "$src" "$tmp" >/dev/null
printf "%s" "$(cd "$tmp" && hg log --limit 1 --template '{latesttag}')"
else
git clone "$src" "$tmp"
printf "%s" "$(cd "$tmp" && git describe $(git rev-list --tags --max-count=1))"
git clone "$src" "$tmp" >/dev/null
printf "%s" "$(cd "$tmp" && git describe "$(git rev-list --tags --max-count=1)")"
fi
}
update_version() {
default_nix="$(default "$1")"
version_old="$(version "$1")"
oldVersion="$(version "$1")"
version="$(get_latest_version "$1")"
(cd "$root" && update-source-version "sourcehut.python.pkgs.$1" "$version")
git add "$default_nix"
git commit -m "$1: $version_old -> $version"
# Update vendorSha256 of Go modules
retry=true
while "$retry"; do
retry=false;
exec < <(exec nix -L build -f "$root" sourcehut.python.pkgs."$1" 2>&1)
while IFS=' :' read -r origin hash; do
case "$origin" in
(expected|specified) oldHash="$hash";;
(got) sed -i "s|$oldHash|$hash|" "$default_nix"; retry=true; break;;
(*) printf >&2 "%s\n" "$origin${hash:+:$hash}"
esac
done
done
if [ "$oldVersion" != "$version" ]; then
git add "$default_nix"
git commit -m "sourcehut.$1: $oldVersion -> $version"
fi
}
services=( "srht" "buildsrht" "dispatchsrht" "gitsrht" "hgsrht" "hubsrht" "listssrht" "mansrht"
"metasrht" "pastesrht" "todosrht" "scmsrht" )
# Whether or not a specific service is requested
if [ -n "$1" ]; then
version="$(get_latest_version "$1")"
(cd "$root" && update-source-version "sourcehut.python.pkgs.$1" "$version")
if [ $# -gt 0 ]; then
services=("$@")
else
for service in "${services[@]}"; do
update_version "$service"
done
# Beware that some packages must be updated before others,
# eg. buildsrht must be updated before gitsrht,
# otherwise this script would enter an infinite loop
# because the reported $oldHash to be changed
# may not actually be in $default_nix
# but in the file of one of its dependencies.
services=( "srht" "scmsrht" "buildsrht" "dispatchsrht" "gitsrht" "hgsrht" "hubsrht" "listssrht" "mansrht"
"metasrht" "pagessrht" "pastesrht" "todosrht" )
fi
for service in "${services[@]}"; do
update_version "$service"
done

View File

@ -71,6 +71,7 @@ let
inherit (go) GOOS GOARCH;
patches = args.patches or [];
patchFlags = args.patchFlags or [];
preBuild = args.preBuild or "";
sourceRoot = args.sourceRoot or "";