about summary refs log tree commit diff
path: root/nixpkgs/pkgs/tools/networking
diff options
context:
space:
mode:
Diffstat (limited to 'nixpkgs/pkgs/tools/networking')
-rw-r--r--nixpkgs/pkgs/tools/networking/aardvark-dns/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/airgeddon/default.nix2
-rw-r--r--nixpkgs/pkgs/tools/networking/boundary/default.nix10
-rw-r--r--nixpkgs/pkgs/tools/networking/dd-agent/datadog-agent.nix1
-rw-r--r--nixpkgs/pkgs/tools/networking/ddclient/default.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/ddns-go/default.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/httptunnel/default.nix22
-rw-r--r--nixpkgs/pkgs/tools/networking/hysteria/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/ipfetch/default.nix1
-rw-r--r--nixpkgs/pkgs/tools/networking/ipinfo/default.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/kea/default.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/allow-building-plugins-from-nix-store.patch13
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/default.nix39
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/plugins/default.nix68
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/plugins/generated.json2225
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/plugins/generated.nix74
-rwxr-xr-xnixpkgs/pkgs/tools/networking/maubot/plugins/update.py200
-rw-r--r--nixpkgs/pkgs/tools/networking/maubot/wrapper.nix70
-rw-r--r--nixpkgs/pkgs/tools/networking/muffet/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/netbird/default.nix8
-rw-r--r--nixpkgs/pkgs/tools/networking/netifd/default.nix2
-rw-r--r--nixpkgs/pkgs/tools/networking/ngrep/default.nix10
-rw-r--r--nixpkgs/pkgs/tools/networking/ockam/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/oha/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/ooniprobe-cli/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/opendrop/default.nix41
-rw-r--r--nixpkgs/pkgs/tools/networking/opensnitch/daemon.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/opensnitch/ui.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/pgrok/build-deps/package.json2
-rw-r--r--nixpkgs/pkgs/tools/networking/pgrok/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/q/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/requestly/default.nix4
-rw-r--r--nixpkgs/pkgs/tools/networking/sing-box/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/tridactyl-native/default.nix29
-rw-r--r--nixpkgs/pkgs/tools/networking/uqmi/default.nix2
-rw-r--r--nixpkgs/pkgs/tools/networking/v2raya/default.nix8
-rw-r--r--nixpkgs/pkgs/tools/networking/v2raya/package.json3
-rw-r--r--nixpkgs/pkgs/tools/networking/wg-friendly-peer-names/default.nix6
-rw-r--r--nixpkgs/pkgs/tools/networking/wol/default.nix1
39 files changed, 2786 insertions, 133 deletions
diff --git a/nixpkgs/pkgs/tools/networking/aardvark-dns/default.nix b/nixpkgs/pkgs/tools/networking/aardvark-dns/default.nix
index ea43200b5349..8ecc0442ecc3 100644
--- a/nixpkgs/pkgs/tools/networking/aardvark-dns/default.nix
+++ b/nixpkgs/pkgs/tools/networking/aardvark-dns/default.nix
@@ -6,16 +6,16 @@
 
 rustPlatform.buildRustPackage rec {
   pname = "aardvark-dns";
-  version = "1.8.0";
+  version = "1.9.0";
 
   src = fetchFromGitHub {
     owner = "containers";
     repo = pname;
     rev = "v${version}";
-    hash = "sha256-7nuLHhkVwMc2RYq3rS9bZl39asjFAnsHxnecPypT1HM=";
+    hash = "sha256-ZpZlmAlHtlg7a/81TEGRj80Z6Vahk0CFgQmjU9W/tc8=";
   };
 
-  cargoHash = "sha256-WwM4lPWQmfsBjL4M/j3sZkLtH+Wdy9LTv4M4AF0Z6oo=";
+  cargoHash = "sha256-6OMiLcSTndX/c5xHe896PMuRpvT21jFpDfCxH15UQIA=";
 
   passthru.tests = { inherit (nixosTests) podman; };
 
diff --git a/nixpkgs/pkgs/tools/networking/airgeddon/default.nix b/nixpkgs/pkgs/tools/networking/airgeddon/default.nix
index 5574a877c0d0..cba25cae74f0 100644
--- a/nixpkgs/pkgs/tools/networking/airgeddon/default.nix
+++ b/nixpkgs/pkgs/tools/networking/airgeddon/default.nix
@@ -161,7 +161,7 @@ stdenv.mkDerivation rec {
     homepage = "https://github.com/v1s1t0r1sh3r3/airgeddon";
     changelog = "https://github.com/v1s1t0r1sh3r3/airgeddon/blob/v${version}/CHANGELOG.md";
     license = licenses.gpl3Plus;
-    maintainers = with maintainers; [ pedrohlc ];
+    maintainers = with maintainers; [ ];
     platforms = platforms.linux;
   };
 }
diff --git a/nixpkgs/pkgs/tools/networking/boundary/default.nix b/nixpkgs/pkgs/tools/networking/boundary/default.nix
index 7aeed0b339b4..e867f2f8ac8f 100644
--- a/nixpkgs/pkgs/tools/networking/boundary/default.nix
+++ b/nixpkgs/pkgs/tools/networking/boundary/default.nix
@@ -2,7 +2,7 @@
 
 stdenv.mkDerivation rec {
   pname = "boundary";
-  version = "0.14.1";
+  version = "0.14.2";
 
   src =
     let
@@ -15,10 +15,10 @@ stdenv.mkDerivation rec {
         aarch64-darwin = "darwin_arm64";
       };
       sha256 = selectSystem {
-        x86_64-linux = "sha256-z4pBC/igKpwe1zJpOP8VqBOybtIq0wVaz+rfOwPzht4=";
-        aarch64-linux = "sha256-f3ofThBmBfV6Fr9FHfAsNz6w1Od0QM9fE8tFVB01PzM=";
-        x86_64-darwin = "sha256-iU/t35ibkTjgNV3E0xzdrMw63TKVzSlJjhZTxGzHSz0=";
-        aarch64-darwin = "sha256-213e3J2e9fvuoGPkeeKV46eWxR0nP+uh0f+INeZG738=";
+        x86_64-linux = "sha256-UR34PX3GChOTM4ROcvlghXOv4M8CYgiCvQaR/BRRvzs=";
+        aarch64-linux = "sha256-5q5Zz+/klgwbBvE40aMCw+ulv+g9Yhpcsn31PPCp9S4=";
+        x86_64-darwin = "sha256-NH1/QKqmaKGL35verE2sRXUwXePJoQk5kiUEIA5Xxn8=";
+        aarch64-darwin = "sha256-PpZ1dbT57+cdmLTvxo0/HY0lKoa+/N4cSfTNhbE6LLo=";
       };
     in
     fetchzip {
diff --git a/nixpkgs/pkgs/tools/networking/dd-agent/datadog-agent.nix b/nixpkgs/pkgs/tools/networking/dd-agent/datadog-agent.nix
index 8a40b290ae48..aac49a7b83b2 100644
--- a/nixpkgs/pkgs/tools/networking/dd-agent/datadog-agent.nix
+++ b/nixpkgs/pkgs/tools/networking/dd-agent/datadog-agent.nix
@@ -64,6 +64,7 @@ in buildGoModule rec {
     "process"
     "log"
     "secrets"
+    "zlib"
   ]
   ++ lib.optionals withSystemd [ "systemd" ]
   ++ extraTags;
diff --git a/nixpkgs/pkgs/tools/networking/ddclient/default.nix b/nixpkgs/pkgs/tools/networking/ddclient/default.nix
index 53401cf4acf3..ec84c7c526cb 100644
--- a/nixpkgs/pkgs/tools/networking/ddclient/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ddclient/default.nix
@@ -5,7 +5,7 @@ let
 in
 perlPackages.buildPerlPackage rec {
   pname = "ddclient";
-  version = "3.11.1";
+  version = "3.11.2";
 
   outputs = [ "out" ];
 
@@ -13,7 +13,7 @@ perlPackages.buildPerlPackage rec {
     owner = "ddclient";
     repo = "ddclient";
     rev = "v${version}";
-    sha256 = "sha256-OM+JW3HP0llzyJNqmP5PLZ30TOvC2nA1bWwOspTbZZM=";
+    sha256 = "sha256-d1G+AM28nBpMWh1QBjm78KKeOL5b5arxERYRCXohwBg=";
   };
 
   postPatch = ''
diff --git a/nixpkgs/pkgs/tools/networking/ddns-go/default.nix b/nixpkgs/pkgs/tools/networking/ddns-go/default.nix
index fb4adc99fa3c..84f63e579e62 100644
--- a/nixpkgs/pkgs/tools/networking/ddns-go/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ddns-go/default.nix
@@ -5,13 +5,13 @@
 
 buildGoModule rec {
   pname = "ddns-go";
-  version = "5.6.4";
+  version = "5.6.6";
 
   src = fetchFromGitHub {
     owner = "jeessy2";
     repo = pname;
     rev = "v${version}";
-    hash = "sha256-wE4xzAH31yQ8xrA0dI7f961KNwK84gRSit+XNoW37pc=";
+    hash = "sha256-4OBY2Bj23uOBOAHKmOpecFXu0Lr8sLrwiU3/BdHpGOQ=";
   };
 
   vendorHash = "sha256-e4mmUneFZCsteSrxfSeeky/pFc0sgNs0eRVnZQuG1ZI=";
diff --git a/nixpkgs/pkgs/tools/networking/httptunnel/default.nix b/nixpkgs/pkgs/tools/networking/httptunnel/default.nix
index 13ef64175358..c8ff4fa7719d 100644
--- a/nixpkgs/pkgs/tools/networking/httptunnel/default.nix
+++ b/nixpkgs/pkgs/tools/networking/httptunnel/default.nix
@@ -1,17 +1,27 @@
-{ lib, stdenv, fetchurl }:
+{ lib
+, stdenv
+, fetchFromGitHub
+, autoreconfHook
+}:
 
 stdenv.mkDerivation rec {
-  version = "3.3";
+  version = "3.3-unstable-2023-05-08";
   pname = "httptunnel";
 
-  src = fetchurl {
-    url    = "http://www.nocrew.org/software/httptunnel/${pname}-${version}.tar.gz";
-    sha256 = "0mn5s6p68n32xzadz6ds5i6bp44dyxzkq68r1yljlv470jr84bql";
+  src = fetchFromGitHub {
+    owner = "larsbrinkhoff";
+    repo = "httptunnel";
+    rev = "d8f91af976c97a6006a5bd1ad7149380c39ba454";
+    hash = "sha256-fUaVHE3nxq3fU7DYCvaQTOoMzax/qFH8cMegFLLybNk=";
   };
 
+  nativeBuildInputs = [
+    autoreconfHook
+  ];
+
   meta = with lib; {
     description = "Creates a bidirectional virtual data connection tunnelled in HTTP requests";
-    homepage    = "http://www.nocrew.org/software/httptunnel";
+    homepage    = "http://www.gnu.org/software/httptunnel/httptunnel.html";
     license     = licenses.gpl2;
     maintainers = with maintainers; [ koral ];
     platforms   = platforms.unix;
diff --git a/nixpkgs/pkgs/tools/networking/hysteria/default.nix b/nixpkgs/pkgs/tools/networking/hysteria/default.nix
index bcfd588245e4..dd088b1ec539 100644
--- a/nixpkgs/pkgs/tools/networking/hysteria/default.nix
+++ b/nixpkgs/pkgs/tools/networking/hysteria/default.nix
@@ -4,16 +4,16 @@
 }:
 buildGoModule rec {
   pname = "hysteria";
-  version = "2.2.0";
+  version = "2.2.2";
 
   src = fetchFromGitHub {
     owner = "apernet";
     repo = pname;
     rev = "app/v${version}";
-    hash = "sha256-v9W1/1AIcYKYxVnFFXZdwQC50FWJCMQ0OXCmlfmXWQk=";
+    hash = "sha256-5j24wIZ4LloE9t0sv5p+oiYmexOaORASNN9JylXxrk4=";
   };
 
-  vendorHash = "sha256-/lFDCOkwkBKq1GJA1F7Lyhw++X1G1pld6JXNEdKue/E=";
+  vendorHash = "sha256-ErU1yEtSuMVkoJv9hyaE4OZS5o7GxuleoK0Q9BI2skw=";
   proxyVendor = true;
 
   ldflags = [
diff --git a/nixpkgs/pkgs/tools/networking/ipfetch/default.nix b/nixpkgs/pkgs/tools/networking/ipfetch/default.nix
index b9b675366e56..f264deaa8a35 100644
--- a/nixpkgs/pkgs/tools/networking/ipfetch/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ipfetch/default.nix
@@ -31,6 +31,7 @@ stdenv.mkDerivation rec {
 
   meta = with lib; {
     description = "Neofetch but for ip addresses";
+    homepage = "https://github.com/trakBan/ipfetch";
     license = licenses.gpl3Only;
     platforms = platforms.all;
     maintainers = with maintainers; [ annaaurora ];
diff --git a/nixpkgs/pkgs/tools/networking/ipinfo/default.nix b/nixpkgs/pkgs/tools/networking/ipinfo/default.nix
index 663c898935da..16b68e4801c6 100644
--- a/nixpkgs/pkgs/tools/networking/ipinfo/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ipinfo/default.nix
@@ -5,13 +5,13 @@
 
 buildGoModule rec {
   pname = "ipinfo";
-  version = "3.1.2";
+  version = "3.2.0";
 
   src = fetchFromGitHub {
     owner = pname;
     repo = "cli";
     rev = "refs/tags/${pname}-${version}";
-    hash = "sha256-KCdKfZs1u3ZLaG+Lmod/vV0T0LaW8hs4ReGlVA7A9pA=";
+    hash = "sha256-bqA8Y3mVHSwhUcvr3biWbH6K73MYmo3f7wSMS4J+Bk8=";
   };
 
   vendorHash = null;
diff --git a/nixpkgs/pkgs/tools/networking/kea/default.nix b/nixpkgs/pkgs/tools/networking/kea/default.nix
index 2e642b17f87c..574afb68e237 100644
--- a/nixpkgs/pkgs/tools/networking/kea/default.nix
+++ b/nixpkgs/pkgs/tools/networking/kea/default.nix
@@ -23,11 +23,11 @@
 
 stdenv.mkDerivation rec {
   pname = "kea";
-  version = "2.4.0"; # only even minor versions are stable
+  version = "2.4.1"; # only even minor versions are stable
 
   src = fetchurl {
     url = "https://ftp.isc.org/isc/${pname}/${version}/${pname}-${version}.tar.gz";
-    hash = "sha256-OjPNCNwzGf9UTmu/LAQpBCEG9AUevhFdwbsmJclQA/c=";
+    hash = "sha256-gVxh9cJxyqSh2zHdZW61Cn9uqXPaNpD3yFgUCOGAExo=";
   };
 
   patches = [
diff --git a/nixpkgs/pkgs/tools/networking/maubot/allow-building-plugins-from-nix-store.patch b/nixpkgs/pkgs/tools/networking/maubot/allow-building-plugins-from-nix-store.patch
deleted file mode 100644
index 1df88b92aa51..000000000000
--- a/nixpkgs/pkgs/tools/networking/maubot/allow-building-plugins-from-nix-store.patch
+++ /dev/null
@@ -1,13 +0,0 @@
-diff --git a/maubot/cli/commands/build.py b/maubot/cli/commands/build.py
-index ec3ac26..4de85f2 100644
---- a/maubot/cli/commands/build.py
-+++ b/maubot/cli/commands/build.py
-@@ -84,7 +84,7 @@ def read_output_path(output: str, meta: PluginMeta) -> str | None:
- 
- 
- def write_plugin(meta: PluginMeta, output: str | IO) -> None:
--    with zipfile.ZipFile(output, "w") as zip:
-+    with zipfile.ZipFile(output, "w", strict_timestamps=False) as zip:
-         meta_dump = BytesIO()
-         yaml.dump(meta.serialize(), meta_dump)
-         zip.writestr("maubot.yaml", meta_dump.getvalue())
diff --git a/nixpkgs/pkgs/tools/networking/maubot/default.nix b/nixpkgs/pkgs/tools/networking/maubot/default.nix
index e2b9e543a8b4..acee6f1dedb3 100644
--- a/nixpkgs/pkgs/tools/networking/maubot/default.nix
+++ b/nixpkgs/pkgs/tools/networking/maubot/default.nix
@@ -1,6 +1,7 @@
 { lib
 , fetchPypi
 , fetchpatch
+, callPackage
 , runCommand
 , python3
 , encryptionSupport ? true
@@ -55,8 +56,6 @@ let
         url = "https://github.com/maubot/maubot/commit/283f0a3ed5dfae13062b6f0fd153fbdc477f4381.patch";
         sha256 = "0yn5357z346qzy5v5g124mgiah1xsi9yyfq42zg028c8paiw8s8x";
       })
-      # allow running "mbc build" in a nix derivation
-      ./allow-building-plugins-from-nix-store.patch
     ];
 
     propagatedBuildInputs = with python.pkgs; [
@@ -88,21 +87,41 @@ let
       rm $out/example-config.yaml
     '';
 
-    passthru = {
-      inherit python;
+    # Setuptools is trying to do python -m maubot test
+    dontUseSetuptoolsCheck = true;
+
+    pythonImportsCheck = [
+      "maubot"
+    ];
+
+    passthru = let
+      wrapper = callPackage ./wrapper.nix {
+        unwrapped = maubot;
+        python3 = python;
+      };
+    in
+    {
       tests = {
         simple = runCommand "${pname}-tests" { } ''
           ${maubot}/bin/mbc --help > $out
         '';
       };
-    };
 
-    # Setuptools is trying to do python -m maubot test
-    dontUseSetuptoolsCheck = true;
+      inherit python;
 
-    pythonImportsCheck = [
-      "maubot"
-    ];
+      plugins = callPackage ./plugins {
+        maubot = maubot;
+        python3 = python;
+      };
+
+      withPythonPackages = pythonPackages: wrapper { inherit pythonPackages; };
+
+      # This adds the plugins to lib/maubot-plugins
+      withPlugins = plugins: wrapper { inherit plugins; };
+
+      # This changes example-config.yaml in module directory
+      withBaseConfig = baseConfig: wrapper { inherit baseConfig; };
+    };
 
     meta = with lib; {
       description = "A plugin-based Matrix bot system written in Python";
diff --git a/nixpkgs/pkgs/tools/networking/maubot/plugins/default.nix b/nixpkgs/pkgs/tools/networking/maubot/plugins/default.nix
new file mode 100644
index 000000000000..b60589b9df7e
--- /dev/null
+++ b/nixpkgs/pkgs/tools/networking/maubot/plugins/default.nix
@@ -0,0 +1,68 @@
+{ lib
+, fetchgit
+, fetchFromGitHub
+, fetchFromGitLab
+, fetchFromGitea
+, stdenvNoCC
+, callPackage
+, ensureNewerSourcesForZipFilesHook
+, maubot
+, python3
+, poetry
+, formats
+}:
+
+let
+  # pname: plugin id (example: xyz.maubot.echo)
+  # version: plugin version
+  # other attributes are passed directly to stdenv.mkDerivation (you at least need src)
+  buildMaubotPlugin = attrs@{ version, pname, base_config ? null, ... }:
+    stdenvNoCC.mkDerivation (builtins.removeAttrs attrs [ "base_config" ] // {
+      pluginName = "${pname}-v${version}.mbp";
+      nativeBuildInputs = (attrs.nativeBuildInputs or [ ]) ++ [
+        ensureNewerSourcesForZipFilesHook
+        maubot
+      ];
+      buildPhase = ''
+        runHook preBuild
+
+        mbc build
+
+        runHook postBuild
+      '';
+
+      postPatch = lib.optionalString (base_config != null) ''
+        [ -e base-config.yaml ] || (echo "base-config.yaml doesn't exist, can't override it" && exit 1)
+        cp "${if builtins.isPath base_config || lib.isDerivation base_config then base_config
+          else if builtins.isString base_config then builtins.toFile "base-config.yaml" base_config
+          else (formats.yaml { }).generate "base-config.yaml" base_config}" base-config.yaml
+      '' + attrs.postPatch or "";
+
+      installPhase = ''
+        runHook preInstall
+
+        mkdir -p $out/lib/maubot-plugins
+        install -m 444 $pluginName $out/lib/maubot-plugins
+
+        runHook postInstall
+      '';
+    });
+
+  generated = import ./generated.nix {
+    inherit lib fetchgit fetchFromGitHub fetchFromGitLab
+      fetchFromGitea python3 poetry buildMaubotPlugin;
+  };
+in
+generated // {
+  inherit buildMaubotPlugin;
+
+  allOfficialPlugins =
+    builtins.filter
+      (x: x.isOfficial && !x.meta.broken)
+      (builtins.attrValues generated);
+
+  allPlugins =
+    builtins.filter
+      (x: !x.meta.broken)
+      (builtins.attrValues generated);
+}
diff --git a/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.json b/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.json
new file mode 100644
index 000000000000..555de6c05821
--- /dev/null
+++ b/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.json
@@ -0,0 +1,2225 @@
+{
+  "URLDownload": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://codeberg.org/LukeLR/matrix-url-download/releases",
+        "description": "A plugin for the maubot bot framework implementing URL downloads in matrix rooms.",
+        "downloadPage": "https://codeberg.org/LukeLR/matrix-url-download/releases",
+        "homepage": "https://codeberg.org/LukeLR/matrix-url-download"
+      }
+    },
+    "gitea": {
+      "domain": "codeberg.org",
+      "hash": "sha256-JLYhoQKxsYO46mqRJZEcWTHck6bli6itYGu8ZPbxyjg=",
+      "owner": "LukeLR",
+      "repo": "matrix-url-download",
+      "rev": "3a006d98faa6950edab1a45b7a8c6a6d7d908bff"
+    },
+    "manifest": {
+      "config": true,
+      "database": true,
+      "database_type": "asyncpg",
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "de.lukelr.urldownload",
+      "license": "LGPL-3.0-only",
+      "main_class": "URLDownloadBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "urldownload"
+      ],
+      "version": "0.0.3"
+    }
+  },
+  "activity-tracker": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-kickbot/releases",
+        "description": "A plugin that minimally tracks user activity within a space. Useful for kicking inactive users from a private community.",
+        "downloadPage": "https://github.com/williamkray/maubot-kickbot/releases",
+        "homepage": "https://github.com/williamkray/maubot-kickbot"
+      }
+    },
+    "github": {
+      "hash": "sha256-TLaGpLrTR4TLR0TjY3v9FFST8JxEP4swJ7kzt0fDwJI=",
+      "owner": "williamkray",
+      "repo": "maubot-kickbot",
+      "rev": "a4c31c7a1492585f2155705be8cab7e3f73f6b69"
+    },
+    "manifest": {
+      "database": true,
+      "database_type": "asyncpg",
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.kickbot",
+      "license": "MIT",
+      "main_class": "KickBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "kickbot"
+      ],
+      "version": "0.0.10"
+    }
+  },
+  "alertbot": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/moan0s/alertbot/blob/v1.1.1/CHANGELOG.md",
+        "description": "A bot that recives monitoring alerts via alertmanager and forwards them to a matrix room.",
+        "downloadPage": "https://github.com/moan0s/alertbot/releases",
+        "homepage": "https://github.com/moan0s/alertbot"
+      }
+    },
+    "github": {
+      "hash": "sha256-hA4Wl1mrIuThQVHTPhMAVsvdbhhx/rHqpOResWO8xiI=",
+      "owner": "moan0s",
+      "repo": "alertbot",
+      "rev": "v1.1.1"
+    },
+    "manifest": {
+      "id": "de.hyteck.alertbot",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "AlertBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "alertbot"
+      ],
+      "version": "1.1.1",
+      "webapp": true
+    }
+  },
+  "altalias": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/altalias/releases",
+        "description": "A bot that lets users publish alternate aliases in rooms.",
+        "downloadPage": "https://github.com/maubot/altalias/releases",
+        "homepage": "https://github.com/maubot/altalias"
+      }
+    },
+    "github": {
+      "hash": "sha256-+qW3CX2ae86jc5l/7poyLs2cQycLjft9l3rul9eYby4=",
+      "owner": "maubot",
+      "repo": "altalias",
+      "rev": "b07b7866c9647612bfe784700b37087855432028"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.altalias",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "AltAliasBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "altalias"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "alternatingcaps": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/rom4nik/maubot-alternatingcaps/releases",
+        "description": "A bot repeating last message using aLtErNaTiNg cApS.",
+        "downloadPage": "https://github.com/rom4nik/maubot-alternatingcaps/releases",
+        "homepage": "https://github.com/rom4nik/maubot-alternatingcaps"
+      }
+    },
+    "github": {
+      "hash": "sha256-O3FhZ6US4iACEzEKdHLjBZfOJlHNGEeLSrHdqWULFvk=",
+      "owner": "rom4nik",
+      "repo": "maubot-alternatingcaps",
+      "rev": "v0.1.2"
+    },
+    "manifest": {
+      "id": "pl.rom4nik.maubot.alternatingcaps",
+      "license": "MIT",
+      "main_class": "AlternatingCaps",
+      "modules": [
+        "alternatingcaps"
+      ],
+      "version": "0.1.2"
+    }
+  },
+  "animemanga": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "An anime/manga bot for Matrix. Search anime, manga (manhwa/manhua), and light novels from Anilist. See series info, status, and episodes/chapters.",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/animemanga"
+      },
+      "postPatch": "cd animemanga"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "coffee.maubot.animemanga",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "AnimeMangaBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "animemanga"
+      ],
+      "version": "0.1.1.216"
+    }
+  },
+  "antithread": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/antithread/releases",
+        "description": "A bot that redacts all messages in threads.",
+        "downloadPage": "https://github.com/maubot/antithread/releases",
+        "homepage": "https://github.com/maubot/antithread"
+      }
+    },
+    "github": {
+      "hash": "sha256-O6rxvxR62DboRGaNevJRCZynGl3xthRICaxRCvLScdM=",
+      "owner": "maubot",
+      "repo": "antithread",
+      "rev": "0577b8eefcf01925452678b9fe380aac4270c672"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.antithread",
+      "license": "MIT",
+      "main_class": "AntiThreadBot",
+      "modules": [
+        "antithread"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "autoreply": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/babolivier/maubot-autoreply/releases",
+        "description": "A bot that sends automated replies when you're away, and shows you a summary of missed messages when you come back.",
+        "downloadPage": "https://github.com/babolivier/maubot-autoreply/releases",
+        "homepage": "https://github.com/babolivier/maubot-autoreply"
+      }
+    },
+    "github": {
+      "hash": "sha256-ULOL5C1tzH4g0IWu+GmMdl3+aCZK0n/G4I8wIvd7f6U=",
+      "owner": "babolivier",
+      "repo": "maubot-autoreply",
+      "rev": "v1.0.0"
+    },
+    "manifest": {
+      "config": true,
+      "database": true,
+      "database_type": "asyncpg",
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "bzh.abolivier.autoreply",
+      "license": "Apache-2.0",
+      "main_class": "AutoReplyBot",
+      "maubot": "v0.1.0",
+      "modules": [
+        "autoreply"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "bard": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/ser/maubot-bard/releases",
+        "description": "Allow your maubot instance to return queries from Google(TM) Bard(TM) pseudoAI",
+        "downloadPage": "https://github.com/ser/maubot-bard/releases",
+        "homepage": "https://github.com/ser/maubot-bard/",
+        "license": "MIT"
+      }
+    },
+    "github": {
+      "hash": "sha256-E8pz71wfH+SmFNzBcPUrnqK0xs7wlyB6SaRXH/PDqKw=",
+      "owner": "ser",
+      "repo": "maubot-bard",
+      "rev": "4ff3ce8d86ed19c973dee89228779fed74811341"
+    },
+    "manifest": {
+      "config": true,
+      "dependencies": [
+        "bardapi"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "sergevictor.eu.maubot.bard",
+      "main_class": "BardPlugin",
+      "modules": [
+        "bard"
+      ],
+      "version": "0.99.100"
+    }
+  },
+  "characterai": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/Matthieu-LAURENT39/maubot-characterai/releases",
+        "description": "Chat with characters from [character.ai](https://character.ai/) in your Matrix rooms! Very customizable.",
+        "downloadPage": "https://github.com/Matthieu-LAURENT39/maubot-characterai/releases",
+        "homepage": "https://github.com/Matthieu-LAURENT39/maubot-characterai"
+      }
+    },
+    "github": {
+      "hash": "sha256-nyVz0PDyNGAIFCxakWzEe8AG/PU+HlZJQQ85SL1bEvs=",
+      "owner": "Matthieu-LAURENT39",
+      "repo": "maubot-characterai",
+      "rev": "v0.2.1"
+    },
+    "manifest": {
+      "config": true,
+      "database": true,
+      "database_type": "asyncpg",
+      "dependencies": [
+        "characterai"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "com.github.Matthieu-LAURENT39.maubot-characterai",
+      "license": "MIT",
+      "main_class": "CAIBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "cai"
+      ],
+      "version": "0.2.1"
+    }
+  },
+  "chatgpt": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-chatgpt/releases",
+        "description": "ChatGPT plugin for maubot. Multi-user aware for use in group rooms! Customize your prompts to \"train\" your assistant contextually.",
+        "downloadPage": "https://github.com/williamkray/maubot-chatgpt/releases",
+        "homepage": "https://github.com/williamkray/maubot-chatgpt",
+        "license": "MIT"
+      }
+    },
+    "github": {
+      "hash": "sha256-iRo4oFOOXgISALFskPZUonV4cBn7HmBACdi5uhgQq8o=",
+      "owner": "williamkray",
+      "repo": "maubot-chatgpt",
+      "rev": "f3974dc3818da170a3f1e091359d31f3140245e0"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.chatgpt",
+      "main_class": "GPTPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "gpt"
+      ],
+      "version": "0.0.9"
+    }
+  },
+  "choose": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "Have the bot choose for you ( item1 | item2 | item3 ) with a divider",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/choose"
+      },
+      "postPatch": "cd choose"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "id": "coffee.maubot.choose",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ChooseBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "choose"
+      ],
+      "version": "0.1.0.3"
+    }
+  },
+  "commitstrip": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/commitstrip/releases",
+        "description": "A bot to view CommitStrips.",
+        "downloadPage": "https://github.com/maubot/commitstrip/releases",
+        "homepage": "https://github.com/maubot/commitstrip"
+      }
+    },
+    "github": {
+      "hash": "sha256-P5u4oDmsMj4r48JZIZ1Cg8cX11aimv9dGI+J0lJrY34=",
+      "owner": "maubot",
+      "repo": "commitstrip",
+      "rev": "28ab63c2725aa989a151f5659cb37a674b002a80"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.commitstrip",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "CommitBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "commitstrip"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "create-room": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-createroom/releases",
+        "description": "A plugin that creates new rooms and automatically sets them to be part of a private Matrix Space.",
+        "downloadPage": "https://github.com/williamkray/maubot-createroom/releases",
+        "homepage": "https://github.com/williamkray/maubot-createroom"
+      }
+    },
+    "github": {
+      "hash": "sha256-x1eoUX8u1IR/hLgS8YcpSoTByl+m3GoTW3fnFMDs1XA=",
+      "owner": "williamkray",
+      "repo": "maubot-createroom",
+      "rev": "4eecdcffa6c06276287c2a3d4e65905a72ad18ad"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.createspaceroom",
+      "license": "MIT",
+      "main_class": "CreateSpaceRoom",
+      "maubot": "0.1.0",
+      "modules": [
+        "createspaceroom"
+      ],
+      "version": "0.1.2"
+    }
+  },
+  "dice": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/dice/releases",
+        "description": "A combined dice rolling and calculator bot.",
+        "downloadPage": "https://github.com/maubot/dice/releases",
+        "homepage": "https://github.com/maubot/dice"
+      }
+    },
+    "github": {
+      "hash": "sha256-xnqcxOXHhsHR9RjLaOa6QZOx87V6kLQJW+mRWF/S5eM=",
+      "owner": "maubot",
+      "repo": "dice",
+      "rev": "v1.1.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.dice",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "DiceBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "dice"
+      ],
+      "version": "1.1.0"
+    }
+  },
+  "disruptor": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/disruptor/releases",
+        "description": "A bot that disrupts monologues with cat pictures.",
+        "downloadPage": "https://github.com/maubot/disruptor/releases",
+        "homepage": "https://github.com/maubot/disruptor"
+      }
+    },
+    "github": {
+      "hash": "sha256-/wm/CNl4XzRBClhW+jOp9S7P/nIz65aOtt+E9AnIPNA=",
+      "owner": "maubot",
+      "repo": "disruptor",
+      "rev": "v0.2.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.disruptor",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "DisruptorBot",
+      "maubot": "0.4.1",
+      "modules": [
+        "disruptor"
+      ],
+      "version": "0.2.0"
+    }
+  },
+  "echo": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/echo/releases",
+        "description": "A bot that echoes pings and other stuff.\n\nSee [#ping:maunium.net](https://matrix.to/#/#ping:maunium.net) for a room\nwith lots of echo bots.\n",
+        "downloadPage": "https://github.com/maubot/echo/releases",
+        "homepage": "https://github.com/maubot/echo"
+      }
+    },
+    "github": {
+      "hash": "sha256-/ajDs2vpWqejxDF7naXtKi1nYRs2lJpuc0R0dV7oVHI=",
+      "owner": "maubot",
+      "repo": "echo",
+      "rev": "v1.4.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.echo",
+      "license": "MIT",
+      "main_class": "EchoBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "echo"
+      ],
+      "version": "1.4.0"
+    }
+  },
+  "exec": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/exec/releases",
+        "description": "A bot that executes code.",
+        "downloadPage": "https://github.com/maubot/exec/releases",
+        "homepage": "https://github.com/maubot/exec"
+      }
+    },
+    "github": {
+      "hash": "sha256-bwy3eB7ULYTGeJXtTNFMfry9dWQmnTjcU6HWdRznWxc=",
+      "owner": "maubot",
+      "repo": "exec",
+      "rev": "475d0fe70dc30e1c14e29028694fd4ac38690932"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.exec",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ExecBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "exec"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "factorial": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/factorial/releases",
+        "description": "A bot to calculate unexpected factorials.",
+        "downloadPage": "https://github.com/maubot/factorial/releases",
+        "homepage": "https://github.com/maubot/factorial"
+      }
+    },
+    "github": {
+      "hash": "sha256-XHAwAloJZpFdY0kRrUjkEGJoryHK4PSQgBf2QH9C/6o=",
+      "owner": "maubot",
+      "repo": "factorial",
+      "rev": "v3.0.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.factorial",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "FactorialBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "factorial"
+      ],
+      "version": "3.0.0"
+    }
+  },
+  "gifme": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-gifme/releases",
+        "description": "Superior gif responses. Save your own library of image or video responses.\nAllows fallback behavior to Giphy or Tenor, optionally saves quotes from\nusers for comedic effect or to be used as an FAQ bot!\n",
+        "downloadPage": "https://github.com/williamkray/maubot-gifme/releases",
+        "homepage": "https://github.com/williamkray/maubot-gifme"
+      }
+    },
+    "github": {
+      "hash": "sha256-5MHLtm3qktUyvWyuwQEUQWL8fxszZ6h/hHClLLr0Uvs=",
+      "owner": "williamkray",
+      "repo": "maubot-gifme",
+      "rev": "6dbbb9ebce903887b62f95b04f4640779762e57a"
+    },
+    "manifest": {
+      "database": true,
+      "database_type": "asyncpg",
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.gifme",
+      "license": "MIT",
+      "main_class": "GifMe",
+      "maubot": "0.4.0",
+      "modules": [
+        "gifme"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "giphy": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/TomCasavant/GiphyMaubot/releases",
+        "description": "A bot that generates a gif (from giphy) given search terms.",
+        "downloadPage": "https://github.com/TomCasavant/GiphyMaubot/releases",
+        "homepage": "https://github.com/TomCasavant/GiphyMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-bY9jCHwI2UZwn+W02hSEAD0aRRsM7cAeeYpnk3jTTBY=",
+      "owner": "TomCasavant",
+      "repo": "GiphyMaubot",
+      "rev": "3.3.0"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "casavant.tom.giphy",
+      "license": "MIT",
+      "main_class": "GiphyPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "giphy"
+      ],
+      "version": "3.3.0"
+    }
+  },
+  "github": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/github/releases",
+        "description": "A GitHub client and webhook receiver.",
+        "downloadPage": "https://github.com/maubot/github/releases",
+        "homepage": "https://github.com/maubot/github"
+      }
+    },
+    "github": {
+      "hash": "sha256-Qc0KH8iGqMDa+1BXaB5fHtRIcsZRpTF2IufGMEXqV6Q=",
+      "owner": "maubot",
+      "repo": "github",
+      "rev": "v0.1.2"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "config": true,
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.github",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "GitHubBot",
+      "maubot": "0.3.0",
+      "modules": [
+        "github"
+      ],
+      "version": "0.1.2",
+      "webapp": true
+    }
+  },
+  "gitlab": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/gitlab/releases",
+        "description": "A GitLab client and webhook receiver.",
+        "downloadPage": "https://github.com/maubot/gitlab/releases",
+        "homepage": "https://github.com/maubot/gitlab"
+      }
+    },
+    "github": {
+      "hash": "sha256-lkHGR+uLnT3f7prWDAbJplwzwAyOfMCwf8B2LeiJzIo=",
+      "owner": "maubot",
+      "repo": "gitlab",
+      "rev": "v0.2.1"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "config": true,
+      "database": true,
+      "extra_files": [
+        "base-config.yaml",
+        "templates/macros.html",
+        "templates/messages/*.html",
+        "templates/mixins/*.html"
+      ],
+      "id": "xyz.maubot.gitlab",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "GitlabBot",
+      "maubot": "0.1.2",
+      "modules": [
+        "gitlab_matrix"
+      ],
+      "soft_dependencies": [
+        "python-gitlab"
+      ],
+      "version": "0.2.1",
+      "webapp": true
+    }
+  },
+  "hasswebhookbot": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/v411e/hasswebhookbot/releases",
+        "description": "A bot receiving webhooks from [Home Assistant](https://github.com/home-assistant).",
+        "downloadPage": "https://github.com/v411e/hasswebhookbot/releases",
+        "homepage": "https://github.com/v411e/hasswebhookbot"
+      }
+    },
+    "github": {
+      "hash": "sha256-Tjr2sbFMpasBy4dR1Lqxt/jnO3ay26XY2d263JkFyKg=",
+      "owner": "v411e",
+      "repo": "hasswebhookbot",
+      "rev": "v0.0.15"
+    },
+    "manifest": {
+      "config": true,
+      "database": true,
+      "dependencies": [
+        "Markdown",
+        "pytz"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "com.valentinriess.hasswebhook",
+      "license": "MIT",
+      "main_class": "HassWebhook",
+      "maubot": "0.1.0",
+      "modules": [
+        "hasswebhook"
+      ],
+      "soft_dependencies": [
+        "Pillow"
+      ],
+      "version": "0.0.15",
+      "webapp": true
+    }
+  },
+  "hateheif": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/ser/maubot-hateheif/releases",
+        "description": "A bot which sends converted HEIF into JPEG. Works in encrypted and unencrypted rooms.",
+        "downloadPage": "https://github.com/ser/maubot-hateheif/releases",
+        "homepage": "https://github.com/ser/maubot-hateheif/"
+      }
+    },
+    "github": {
+      "hash": "sha256-twvVeMD2nRwpazc21inbdr6mUjMXJ4T6v5ieNrwB+O4=",
+      "owner": "ser",
+      "repo": "maubot-hateheif",
+      "rev": "52cf166960ac3fb71d291e13d5f3621caa9d7af1"
+    },
+    "manifest": {
+      "config": true,
+      "dependencies": [
+        "pillow-heif"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "eu.sergevictor.hateheif",
+      "license": "MIT",
+      "main_class": "HateHeifBot",
+      "modules": [
+        "hateheif"
+      ],
+      "version": "0.99.100"
+    }
+  },
+  "help": {
+    "attrs": {
+      "meta": {
+        "description": "A plugin to add a `!help` command to maubot. Returns all built-in help commands for all plugins loaded in the client instance.",
+        "homepage": "https://git.skeg1.se/vondassendorf/maubot_mauhelp"
+      }
+    },
+    "gitlab": {
+      "domain": "git.skeg1.se",
+      "hash": "sha256-xQ0GzdWPHstMSEOXwmW/DFxClK/oEwfyTrm752S5iFQ=",
+      "owner": "vondassendorf",
+      "repo": "maubot_mauhelp",
+      "rev": "v0.2.0"
+    },
+    "manifest": {
+      "database": false,
+      "id": "se.skeg1.mauhelp",
+      "license": "MIT",
+      "main_class": "MauHelp",
+      "maubot": "0.3.1",
+      "modules": [
+        "mauhelp"
+      ],
+      "version": "0.2.0"
+    }
+  },
+  "holopin": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/itrich/HolopinMaubot/releases",
+        "description": "A plugin to issue [Holopin](https://holopin.io) badges to users.",
+        "downloadPage": "https://github.com/itrich/HolopinMaubot/releases",
+        "homepage": "https://github.com/itrich/HolopinMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-fQDa4e2hN5WFXwPVqefCU9YBzXHxvtXntAta0oZxp5M=",
+      "owner": "itrich",
+      "repo": "HolopinMaubot",
+      "rev": "v0.0.1"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "dependencies": null,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "net.itrich.maubot.holopin",
+      "license": "MIT",
+      "main_class": "HolopinPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "holopin"
+      ],
+      "soft_dependencies": null,
+      "version": "0.0.1",
+      "webapp": false
+    }
+  },
+  "invite": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-invite/releases",
+        "description": "A bot to generate invitation tokens from [matrix-registration](https://github.com/ZerataX/matrix-registration).",
+        "downloadPage": "https://github.com/williamkray/maubot-invite/releases",
+        "homepage": "https://github.com/williamkray/maubot-invite"
+      }
+    },
+    "github": {
+      "hash": "sha256-VQufveYgxVOoMWtfNJ8LYWvjbFtboSNZzdRn7MA7DLA=",
+      "owner": "williamkray",
+      "repo": "maubot-invite",
+      "rev": "v0.3.1"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.invitebot",
+      "license": "MIT",
+      "main_class": "Invite",
+      "maubot": "0.1.0",
+      "modules": [
+        "invite"
+      ],
+      "version": "0.3.1"
+    }
+  },
+  "jadict": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "A Japanese dictionary Matrix bot for searching and translating Japanese vocabulary (Hiragana, Katakana, Kanji, Romaji). Searches Jisho using Jisho API.",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/jadict"
+      },
+      "postPatch": "cd jadict"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "coffee.maubot.jadict",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "JadictBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "jadict"
+      ],
+      "version": "0.1.0.10"
+    }
+  },
+  "join": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-join/releases",
+        "description": "A plugin that restricts who can convince your bot to join new rooms to certain users.",
+        "downloadPage": "https://github.com/williamkray/maubot-join/releases",
+        "homepage": "https://github.com/williamkray/maubot-join"
+      }
+    },
+    "github": {
+      "hash": "sha256-aqpL+KO5p0hre7RCUZrM270Ah+cR4cQxZn7LTXLT79k=",
+      "owner": "williamkray",
+      "repo": "maubot-join",
+      "rev": "1b57758dfe3a2191588bb903ea546328146e69d8"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.join",
+      "license": "MIT",
+      "main_class": "Join",
+      "maubot": "0.1.0",
+      "modules": [
+        "join"
+      ],
+      "version": "0.3.0"
+    }
+  },
+  "karma": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/karma/releases",
+        "description": "A user karma tracker bot.",
+        "downloadPage": "https://github.com/maubot/karma/releases",
+        "homepage": "https://github.com/maubot/karma"
+      }
+    },
+    "github": {
+      "hash": "sha256-7CK4NReLhU/d0FXTWj9eM7C5yL9nXkM+vpPExv4VPfE=",
+      "owner": "maubot",
+      "repo": "karma",
+      "rev": "v1.0.1"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.karma",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "KarmaBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "karma"
+      ],
+      "version": "1.0.1"
+    }
+  },
+  "ldap-ad-inviterbot": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/SAPUCC/inviterbot/blob/v0.1.5/CHANGELOG.md",
+        "description": "A plugin to sync users from Microsoft Azure AD and LDAP into matrix rooms. (Membership, Power-Levels)",
+        "downloadPage": "https://github.com/SAPUCC/inviterbot/releases",
+        "homepage": "https://github.com/SAPUCC/inviterbot",
+        "license": "GPL-3.0-or-later"
+      }
+    },
+    "github": {
+      "hash": "sha256-Ve420Mfa+Ikxp0P/8b6rZIu54VOfKhH3sWDNNMClj9E=",
+      "owner": "SAPUCC",
+      "repo": "inviterbot",
+      "rev": "v0.1.5"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "dependencies": [
+        null
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "de.in4md-service.inviterbot",
+      "license": "GPLv3",
+      "main_class": "InviterBot",
+      "maubot": "0.2.0",
+      "modules": [
+        "inviter"
+      ],
+      "version": "0.1.5"
+    }
+  },
+  "local-stt": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/ElishaAz/mau_local_stt/releases",
+        "description": "A Maubot to transcribe audio messages in matrix rooms using local open-source libraries",
+        "downloadPage": "https://github.com/ElishaAz/mau_local_stt/releases",
+        "homepage": "https://github.com/ElishaAz/mau_local_stt",
+        "license": "GPL-3.0-only"
+      }
+    },
+    "github": {
+      "hash": "sha256-EyDJ4RtQjBl7BQ7Y/0LWfX4zkVVqBOqjnhb9tXhFxio=",
+      "owner": "ElishaAz",
+      "repo": "mau_local_stt",
+      "rev": "v1.0.2"
+    },
+    "manifest": {
+      "config": true,
+      "dependencies": [
+        "whispercpp",
+        "numpy",
+        "vosk"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "com.elishaaz.maulocalstt",
+      "license": "GPLv3",
+      "main_class": "MauLocalSTT",
+      "maubot": "0.1.0",
+      "modules": [
+        "maulocalstt"
+      ],
+      "version": "1.0.2"
+    }
+  },
+  "manhole": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/manhole/releases",
+        "description": "A plugin that lets you access a Python shell inside maubot.",
+        "downloadPage": "https://github.com/maubot/manhole/releases",
+        "homepage": "https://github.com/maubot/manhole"
+      }
+    },
+    "github": {
+      "hash": "sha256-F3Nrl6NOUmwDuBsCxIfopRnLU9rltdaCJL/OcNGzw1Q=",
+      "owner": "maubot",
+      "repo": "manhole",
+      "rev": "47f1f7501b5b353a0fa74bf5929cead559496174"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.manhole",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ManholeBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "manhole"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "media": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/media/releases",
+        "description": "A bot that replies with the MXC URI of images you send it.",
+        "downloadPage": "https://github.com/maubot/media/releases",
+        "homepage": "https://github.com/maubot/media"
+      }
+    },
+    "github": {
+      "hash": "sha256-00zESMN2WxKYPAQbpyvDpkyJIFkILLOP+m256k0Avzk=",
+      "owner": "maubot",
+      "repo": "media",
+      "rev": "v1.0.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.media",
+      "license": "MIT",
+      "main_class": "MediaBot",
+      "modules": [
+        "media"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "metric": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/edwardsdean/maubot_metric_bot/releases",
+        "description": "A bot that will reply to a message that contains imperial units and replace them with metric units.",
+        "downloadPage": "https://github.com/edwardsdean/maubot_metric_bot/releases",
+        "homepage": "https://github.com/edwardsdean/maubot_metric_bot"
+      }
+    },
+    "github": {
+      "hash": "sha256-qtGGCaATIzJMRhLWzFN0kSa6P/tlckCkxatKEfXyi0E=",
+      "owner": "edwardsdean",
+      "repo": "maubot_metric_bot",
+      "rev": "0.0.4"
+    },
+    "manifest": {
+      "database": false,
+      "id": "me.edwardsdean.maubot.metric",
+      "license": "MIT",
+      "main_class": "MetricPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "metric"
+      ],
+      "version": "0.0.4"
+    }
+  },
+  "ntfy": {
+    "attrs": {
+      "meta": {
+        "description": "A bot for subscribing to [ntfy](https://ntfy.sh) topics and posting messages to Matrix.",
+        "homepage": "https://gitlab.com/999eagle/maubot-ntfy"
+      }
+    },
+    "gitlab": {
+      "hash": "sha256-6522dVqhGoPc/qjz65D3kXHks5LLb3yVe0K5abqdXrw=",
+      "owner": "999eagle",
+      "repo": "maubot-ntfy",
+      "rev": "256aa8f315cbb184eba0256c2ec818abbdd2d408"
+    },
+    "manifest": {
+      "config": true,
+      "database": true,
+      "database_type": "asyncpg",
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "cloud.catgirl.ntfy",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "NtfyBot",
+      "maubot": "0.3.0",
+      "modules": [
+        "ntfy"
+      ],
+      "soft_dependencies": [
+        "emoji>=2.0"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "ovgumensabot": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/v411e/ovgumensabot/releases",
+        "description": "A bot that automatically sends meals from OvGU canteen every day.",
+        "downloadPage": "https://github.com/v411e/ovgumensabot/releases",
+        "homepage": "https://github.com/v411e/ovgumensabot"
+      }
+    },
+    "github": {
+      "hash": "sha256-nuOLUPwE0F15FgOtbq3+qmNNd2eHRrRNJPMM+v1Ksy0=",
+      "owner": "v411e",
+      "repo": "ovgumensabot",
+      "rev": "v0.0.8"
+    },
+    "manifest": {
+      "database": true,
+      "dependencies": [
+        "requests",
+        "beautifulsoup4"
+      ],
+      "extra_files": [
+        "LICENSE.txt"
+      ],
+      "id": "com.valentinriess.mensa",
+      "license": "MIT",
+      "main_class": "MensaBot",
+      "maubot": "0.2.0",
+      "modules": [
+        "ovgumensabot"
+      ],
+      "version": "0.0.8"
+    }
+  },
+  "pingcheck": {
+    "attrs": {
+      "meta": {
+        "description": "A bot to ping the echo bot and send rtt to Icinga passive check.",
+        "homepage": "https://edugit.org/nik/maubot-pingcheck"
+      }
+    },
+    "gitlab": {
+      "domain": "edugit.org",
+      "hash": "sha256-ljNi4si7ZkcCidO5l9jJcgdrj4P8RESB1wznxJvzPNQ=",
+      "owner": "nik",
+      "repo": "maubot-pingcheck",
+      "rev": "0.1.0"
+    },
+    "manifest": {
+      "dependencie": [
+        "requests"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.pingcheck",
+      "license": "MIT",
+      "main_class": "PingcheckBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "pingcheck"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "pocket": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/jaywink/maubot-pocket/blob/v0.2.5/CHANGELOG.md",
+        "description": "A bot integrating with Pocket to fetch articles and archive them.",
+        "downloadPage": "https://github.com/jaywink/maubot-pocket/releases",
+        "homepage": "https://github.com/jaywink/maubot-pocket"
+      }
+    },
+    "github": {
+      "hash": "sha256-I3+nfdkW9WkscsAYN2E1jEyoVujaN/zOTJ8HLReqq44=",
+      "owner": "jaywink",
+      "repo": "maubot-pocket",
+      "rev": "v0.2.5"
+    },
+    "manifest": {
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "me.jasonrobinson.pocket",
+      "license": "MIT",
+      "main_class": "PocketPlugin",
+      "maubot": "0.3.1",
+      "modules": [
+        "pocket"
+      ],
+      "version": "0.2.5",
+      "webapp": true
+    }
+  },
+  "poll": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/TomCasavant/PollMaubot/releases",
+        "description": "A bot that will create a simple poll for users in a room.",
+        "downloadPage": "https://github.com/TomCasavant/PollMaubot/releases",
+        "homepage": "https://github.com/TomCasavant/PollMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-o+9DP9QHZEibmAhy13/fJn72r8hLPY1uuOrTXchjRmw=",
+      "owner": "TomCasavant",
+      "repo": "PollMaubot",
+      "rev": "3.0.1"
+    },
+    "manifest": {
+      "database": false,
+      "id": "casavant.tom.poll",
+      "license": "MIT",
+      "main_class": "PollPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "poll"
+      ],
+      "version": "3.0.1"
+    }
+  },
+  "random-quote": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/itrich/QuoteMaubot/releases",
+        "description": "A plugin to answer with a random quote from a configurable list.",
+        "downloadPage": "https://github.com/itrich/QuoteMaubot/releases",
+        "homepage": "https://github.com/itrich/QuoteMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-NJ6sUC7L4f7ERDAKNcs2RD8q4mGzW0d4rhxh+wqzhVw=",
+      "owner": "itrich",
+      "repo": "QuoteMaubot",
+      "rev": "v0.0.1"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "dependencies": null,
+      "extra_files": null,
+      "id": "net.itrich.maubot.quote",
+      "license": "MIT",
+      "main_class": "QuotePlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "quote"
+      ],
+      "soft_dependencies": null,
+      "version": "0.0.1",
+      "webapp": false
+    }
+  },
+  "random-subreddit-post": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-reddit/releases",
+        "description": "A plugin that returns a random post from a given subreddit.",
+        "downloadPage": "https://github.com/williamkray/maubot-reddit/releases",
+        "homepage": "https://github.com/williamkray/maubot-reddit"
+      }
+    },
+    "github": {
+      "hash": "sha256-xinkSNTWTdKSNE0YFLS3yy26HbqD+I11Z8dGVh/tHNw=",
+      "owner": "williamkray",
+      "repo": "maubot-reddit",
+      "rev": "v0.3.6"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.reddit",
+      "license": "MIT",
+      "main_class": "Post",
+      "maubot": "0.1.0",
+      "modules": [
+        "reddit"
+      ],
+      "version": "0.3.6"
+    }
+  },
+  "reactbot": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/reactbot/releases",
+        "description": "A bot that responds to messages that match predefined rules.",
+        "downloadPage": "https://github.com/maubot/reactbot/releases",
+        "homepage": "https://github.com/maubot/reactbot"
+      }
+    },
+    "github": {
+      "hash": "sha256-ARN9zbOFJCVoqz6ooLRm9DDKUZpbQf7KcfsfoOxeeLE=",
+      "owner": "maubot",
+      "repo": "reactbot",
+      "rev": "v2.2.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.reactbot",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ReactBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "reactbot"
+      ],
+      "version": "2.2.0"
+    }
+  },
+  "redactbot": {
+    "attrs": {
+      "meta": {
+        "description": "A bot that immediately redacts any posted file (except for whitelisted types).",
+        "homepage": "https://gitlab.com/sspaeth/redactbot"
+      }
+    },
+    "gitlab": {
+      "hash": "sha256-uIcXnD3nXVT7mA9SgdyrXGIZuW4CgnCVbCP7TxxnziM=",
+      "owner": "sspaeth",
+      "repo": "redactbot",
+      "rev": "2bca49b14024844c0aa53b9c4802ef6f8702d99d"
+    },
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.redactbot",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "RedactBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "redactbot"
+      ],
+      "version": "2.2.0"
+    }
+  },
+  "reminder": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/reminder/releases",
+        "description": "A bot to remind you about things.",
+        "downloadPage": "https://github.com/maubot/reminder/releases",
+        "homepage": "https://github.com/maubot/reminder"
+      }
+    },
+    "github": {
+      "hash": "sha256-BCyeWl5xPKvUGWkrnuGh498gKxfhfNZ7oBrsZzpKxkg=",
+      "owner": "maubot",
+      "repo": "reminder",
+      "rev": "v0.2.2"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "database": true,
+      "dependencies": [
+        "python-dateutil",
+        "pytz"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.reminder",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ReminderBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "reminder"
+      ],
+      "version": "0.2.2"
+    }
+  },
+  "reminder-agenda": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/MxMarx/reminder/releases",
+        "description": "Create reminders, recurring reminders, and agenda items. A maubot port of [matrix-reminder-bot](https://github.com/anoadragon453/matrix-reminder-bot/tree/master) combined with [maubot/reminder](https://github.com/maubot/reminder)",
+        "downloadPage": "https://github.com/MxMarx/reminder/releases",
+        "homepage": "https://github.com/MxMarx/reminder"
+      }
+    },
+    "github": {
+      "hash": "sha256-3I2EIbyGgtj1NblLAEKCVLSDFnT25YRAp5RXvFHdu2w=",
+      "owner": "MxMarx",
+      "repo": "reminder",
+      "rev": "v0.1.1"
+    },
+    "manifest": {
+      "database": true,
+      "database_type": "asyncpg",
+      "dependencies": [
+        "pytz",
+        "dateparser",
+        "apscheduler"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.bytemarx.reminder",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "ReminderBot",
+      "maubot": "0.4.1",
+      "modules": [
+        "reminder"
+      ],
+      "soft_dependencies": [
+        "cron_descriptor"
+      ],
+      "version": "0.1.1"
+    }
+  },
+  "rss": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/rss/releases",
+        "description": "A bot that posts RSS feed updates to Matrix.",
+        "downloadPage": "https://github.com/maubot/rss/releases",
+        "homepage": "https://github.com/maubot/rss"
+      }
+    },
+    "github": {
+      "hash": "sha256-p/xJpJbzsOeQGcowvOhJSclPtmZyNyBaZBz+mexVqIY=",
+      "owner": "maubot",
+      "repo": "rss",
+      "rev": "v0.3.2"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "database": true,
+      "database_type": "asyncpg",
+      "dependencies": [
+        "feedparser>=5.1"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.rss",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "RSSBot",
+      "maubot": "0.3.0",
+      "modules": [
+        "rss"
+      ],
+      "version": "0.3.2"
+    }
+  },
+  "satwcomic": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/satwcomic/releases",
+        "description": "A bot to view SatWComics.",
+        "downloadPage": "https://github.com/maubot/satwcomic/releases",
+        "homepage": "https://github.com/maubot/satwcomic"
+      }
+    },
+    "github": {
+      "hash": "sha256-TyXrPUUQdLC0IXbpQquA9eegzDoBm1g2WaeQuqhYPco=",
+      "owner": "maubot",
+      "repo": "satwcomic",
+      "rev": "0241bce4807ce860578e2f4fde76bb043bcebe95"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "database": true,
+      "dependencies": [
+        "pyquery"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.satwcomic",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "SatWBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "satwcomic"
+      ],
+      "soft_dependencies": [
+        "Pillow"
+      ],
+      "version": "1.0.0"
+    }
+  },
+  "sed": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/sed/releases",
+        "description": "A bot to do sed-like replacements.",
+        "downloadPage": "https://github.com/maubot/sed/releases",
+        "homepage": "https://github.com/maubot/sed"
+      }
+    },
+    "github": {
+      "hash": "sha256-raVUYEEuNHDFEE+b/yb8DyokFOrbVn0miul+2tJbR+s=",
+      "owner": "maubot",
+      "repo": "sed",
+      "rev": "v1.1.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.sed",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "SedBot",
+      "modules": [
+        "sed"
+      ],
+      "version": "1.1.0"
+    }
+  },
+  "send-custom-html": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "Have the bot send a message as custom HTML. Test and preview formatted HTML body in Matrix.",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/send-custom-html"
+      },
+      "postPatch": "cd send-custom-html"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "coffee.maubot.sendcustomhtml",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "SendCustomHtmlBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "sendcustomhtml"
+      ],
+      "version": "0.1.0.6"
+    }
+  },
+  "social-media-download": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/ggogel/SocialMediaDownloadMaubot/releases",
+        "description": "A bot that that downloads content from various social media websites given a link.",
+        "downloadPage": "https://github.com/ggogel/SocialMediaDownloadMaubot/releases",
+        "homepage": "https://github.com/ggogel/SocialMediaDownloadMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-RMyQzGz2Z4m9FN0Nt5E6Tj0yZarysygCtvEZDfG143M=",
+      "owner": "ggogel",
+      "repo": "SocialMediaDownloadMaubot",
+      "rev": "1.2.0"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "me.gogel.maubot.socialmediadownload",
+      "license": "MIT",
+      "main_class": "socialmediadownload/SocialMediaDownloadPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "instaloader",
+        "socialmediadownload"
+      ],
+      "version": "1.2.0"
+    }
+  },
+  "songwhip": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/songwhip/releases",
+        "description": "A bot to post Songwhip links.",
+        "downloadPage": "https://github.com/maubot/songwhip/releases",
+        "homepage": "https://github.com/maubot/songwhip"
+      }
+    },
+    "github": {
+      "hash": "sha256-oghM1IECN88KhwRhGZCTJo4uMwc495sWNHeK9KaK4FU=",
+      "owner": "maubot",
+      "repo": "songwhip",
+      "rev": "c8d00999ab77a77d0036ee6c71b2cf11583f8edd"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "id": "xyz.maubot.songwhip",
+      "license": "MIT",
+      "main_class": "SongwhipBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "songwhip"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "subreddit-linkifier": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/TomCasavant/RedditMaubot/releases",
+        "description": "A bot that condescendingly corrects a user when they enter an r/subreddit without providing a link to that subreddit.",
+        "downloadPage": "https://github.com/TomCasavant/RedditMaubot/releases",
+        "homepage": "https://github.com/TomCasavant/RedditMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-4F59gCmSl7FNWTys5c9r4Ha0gschDyiYjsX7emhRwuU=",
+      "owner": "TomCasavant",
+      "repo": "RedditMaubot",
+      "rev": "1.5.0"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "casavant.tom.reddit",
+      "license": "MIT",
+      "main_class": "RedditPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "reddit"
+      ],
+      "version": "1.5.0"
+    }
+  },
+  "supportportal": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/supportportal/releases",
+        "description": "A bot to manage customer support on Matrix.",
+        "downloadPage": "https://github.com/maubot/supportportal/releases",
+        "homepage": "https://github.com/maubot/supportportal"
+      }
+    },
+    "github": {
+      "hash": "sha256-9CmA9KfkOkzqTycAGE8jaZuDwS7IvFwWGUer3iR8ooM=",
+      "owner": "maubot",
+      "repo": "supportportal",
+      "rev": "v0.1.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "config": true,
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.supportportal",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "SupportPortalBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "supportportal"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "tex": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/tex/releases",
+        "description": "A bot that renders LaTeX.",
+        "downloadPage": "https://github.com/maubot/tex/releases",
+        "homepage": "https://github.com/maubot/tex"
+      }
+    },
+    "github": {
+      "hash": "sha256-6Iq/rOiMQiFtKvAYeYuF+2xXVcR7VIxQTejbpYBpy2A=",
+      "owner": "maubot",
+      "repo": "tex",
+      "rev": "a6617da41409b5fc5960dc8de06046bbac091318"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "dependencies": [
+        "matplotlib",
+        "Pillow"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.tex",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "TexBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "tex"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "ticker": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-ticker/releases",
+        "description": "A bot to return financial data about a stock or cryptocurrency.",
+        "downloadPage": "https://github.com/williamkray/maubot-ticker/releases",
+        "homepage": "https://github.com/williamkray/maubot-ticker"
+      }
+    },
+    "github": {
+      "hash": "sha256-o/AjzuNaVzHKnpV10p19vDJthEUZ75nAg3KT0Ff3LEg=",
+      "owner": "williamkray",
+      "repo": "maubot-ticker",
+      "rev": "v0.0.6"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.tickerbot",
+      "license": "MIT",
+      "main_class": "TickerBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "tickerbot"
+      ],
+      "version": "0.0.6"
+    }
+  },
+  "timein": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "Get the time in specific cities. Check timezones.  !timein New York  (Python 3.9+) (Python <3.9 requires pytz, fuzzywuzzy)",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/timein"
+      },
+      "postPatch": "cd timein"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "dependencies": [
+        "pytz",
+        "fuzzywuzzy"
+      ],
+      "id": "coffee.maubot.timein",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "TimeinBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "timein"
+      ],
+      "version": "0.1.0.6"
+    }
+  },
+  "tmdb": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://codeberg.org/lomion/tmdb-bot/releases",
+        "description": "A bot that posts information about movies fetched from TheMovieDB.org.",
+        "downloadPage": "https://codeberg.org/lomion/tmdb-bot/releases",
+        "homepage": "https://codeberg.org/lomion/tmdb-bot",
+        "license": "AGPL-3.0-only"
+      }
+    },
+    "gitea": {
+      "domain": "codeberg.org",
+      "hash": "sha256-QeKpIukLCeJOxi/+H+Hukf7mA38gvf8q37o4FOuigAU=",
+      "owner": "lomion",
+      "repo": "tmdb-bot",
+      "rev": "rel.1.3.0"
+    },
+    "manifest": {
+      "database": true,
+      "id": "lomion.tmdb",
+      "license": "AGPL 3.0",
+      "main_class": "TmdbBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "tmdb"
+      ],
+      "version": "1.3.0"
+    }
+  },
+  "token": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/yoxcu/maubot-token/releases",
+        "description": "A maubot to create and manage your synapse user registration tokens.",
+        "downloadPage": "https://github.com/yoxcu/maubot-token/releases",
+        "homepage": "https://github.com/yoxcu/maubot-token"
+      }
+    },
+    "github": {
+      "hash": "sha256-8ZAH9Kn0EQYY9gLx48gF+aEsFOdlZlrbUIvLMP0uwi4=",
+      "owner": "yoxcu",
+      "repo": "maubot-token",
+      "rev": "v1.1.0"
+    },
+    "manifest": {
+      "config": true,
+      "database": false,
+      "extra_files": [
+        "base-config.yaml",
+        "LICENSE"
+      ],
+      "id": "de.yoxcu.token",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "TokenBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "tokenbot"
+      ],
+      "version": "1.1.0"
+    }
+  },
+  "translate": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/translate/releases",
+        "description": "A bot to translate words.",
+        "downloadPage": "https://github.com/maubot/translate/releases",
+        "homepage": "https://github.com/maubot/translate"
+      }
+    },
+    "github": {
+      "hash": "sha256-eaiTNjnBa0r2zeCzYZH/k04dGftBSGuGaDvwOGKKZDA=",
+      "owner": "maubot",
+      "repo": "translate",
+      "rev": "v0.1.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.translate",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "TranslatorBot",
+      "modules": [
+        "translate"
+      ],
+      "version": "0.1.0"
+    }
+  },
+  "trump": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/jeffcasavant/MaubotTrumpTweet/releases",
+        "description": "A bot that generates a Trump tweet with the given content.",
+        "downloadPage": "https://github.com/jeffcasavant/MaubotTrumpTweet/releases",
+        "homepage": "https://github.com/jeffcasavant/MaubotTrumpTweet"
+      }
+    },
+    "github": {
+      "hash": "sha256-WlrFt+uj6E7Ecg+3KW6fjrMXSUP5YFA5ZyitvBON3pA=",
+      "owner": "jeffcasavant",
+      "repo": "MaubotTrumpTweet",
+      "rev": "v1.1.2"
+    },
+    "isPoetry": true,
+    "manifest": {
+      "database": false,
+      "dependencies": [
+        "Pillow>=9.0.1, <10.0.0"
+      ],
+      "extra_files": [
+        "res/font/Roboto-Black.ttf",
+        "res/font/Roboto-Regular.ttf",
+        "res/img/avatars/cartoon0.jpg",
+        "res/img/avatars/cartoon1.jpg",
+        "res/img/avatars/cartoon2.jpg",
+        "res/img/avatars/cartoon3.jpg",
+        "res/img/avatars/cartoon4.jpg",
+        "res/img/avatars/cartoon5.jpg",
+        "res/img/avatars/cartoon6.jpg",
+        "res/img/avatars/cartoon7.jpg",
+        "res/img/avatars/cartoon8.jpg",
+        "res/img/avatars/cartoon9.jpg",
+        "res/img/avatars/default.png",
+        "res/img/avatars/real0.jpg",
+        "res/img/avatars/real1.jpg",
+        "res/img/avatars/real10.jpg",
+        "res/img/avatars/real11.jpg",
+        "res/img/avatars/real12.jpg",
+        "res/img/avatars/real13.jpg",
+        "res/img/avatars/real14.jpg",
+        "res/img/avatars/real15.jpeg",
+        "res/img/avatars/real16.jpg",
+        "res/img/avatars/real17.jpg",
+        "res/img/avatars/real18.jpg",
+        "res/img/avatars/real19.jpeg",
+        "res/img/avatars/real2.jpg",
+        "res/img/avatars/real20.jpg",
+        "res/img/avatars/real21.jpg",
+        "res/img/avatars/real22.jpg",
+        "res/img/avatars/real23.jpg",
+        "res/img/avatars/real24.jpg",
+        "res/img/avatars/real25.jpg",
+        "res/img/avatars/real26.jpg",
+        "res/img/avatars/real27.jpg",
+        "res/img/avatars/real28.jpeg",
+        "res/img/avatars/real29.jpg",
+        "res/img/avatars/real3.jpeg",
+        "res/img/avatars/real4.jpg",
+        "res/img/avatars/real5.jpg",
+        "res/img/avatars/real6.jpeg",
+        "res/img/avatars/real7.jpg",
+        "res/img/avatars/real8.jpeg",
+        "res/img/avatars/real9.jpg",
+        "res/img/like.png",
+        "res/img/reply.png",
+        "res/img/retweet.png",
+        "res/img/trump.jpg",
+        "res/img/verified.png"
+      ],
+      "id": "casavant.jeff.trumptweet",
+      "license": "MIT",
+      "main_class": "TrumpTweetPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "trumptweet"
+      ],
+      "version": "1.1.2"
+    }
+  },
+  "twilio": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/jeffcasavant/MaubotTwilio/releases",
+        "description": "Maubot-based SMS bridge.",
+        "downloadPage": "https://github.com/jeffcasavant/MaubotTwilio/releases",
+        "homepage": "https://github.com/jeffcasavant/MaubotTwilio"
+      }
+    },
+    "github": {
+      "hash": "sha256-b1M9+uXVq3yb4IgcoL/5YqRZ8a13HfyqMw6QFBuBLAM=",
+      "owner": "jeffcasavant",
+      "repo": "MaubotTwilio",
+      "rev": "0.1.0"
+    },
+    "manifest": {
+      "database": true,
+      "dependencies": [
+        "maubot==0.1.0b1",
+        "mautrix==0.5.0b2"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.casavant.jeff.twilio",
+      "license": "MIT",
+      "main_class": "TwilioPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "twilio_plugin"
+      ],
+      "version": "0.1.0",
+      "webapp": true
+    }
+  },
+  "urban": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/dvdgsng/UrbanMaubot/releases",
+        "description": "A bot that fetches definitions from [Urban Dictionary](https://www.urbandictionary.com/).",
+        "downloadPage": "https://github.com/dvdgsng/UrbanMaubot/releases",
+        "homepage": "https://github.com/dvdgsng/UrbanMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-JQ2PpsH/Nno7XqcF1HpZHM/Qv/gta/xGPjfIKtY+pxM=",
+      "owner": "dvdgsng",
+      "repo": "UrbanMaubot",
+      "rev": "1.0.2"
+    },
+    "manifest": {
+      "id": "com.dvdgsng.maubot.urban",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "UrbanDictBot",
+      "modules": [
+        "urban"
+      ],
+      "version": "1.0.2"
+    }
+  },
+  "urlpreview": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/coffeebank/coffee-maubot/releases",
+        "description": "Add URL preview embeds to Matrix! A bot that responds to links with a link preview embed, using Matrix API to fetch meta tags. Supports fetching JSON previews.",
+        "downloadPage": "https://github.com/coffeebank/coffee-maubot/releases",
+        "homepage": "https://github.com/coffeebank/coffee-maubot/tree/master/urlpreview"
+      },
+      "postPatch": "cd urlpreview"
+    },
+    "github": {
+      "hash": "sha256-k+M/Wk4nyXUZBJxmxQr64dPp3rK7i1oQeLFtncle3dI=",
+      "owner": "coffeebank",
+      "repo": "coffee-maubot",
+      "rev": "b25112508d65f7560910e67d3074dd60f4048821"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "coffee.maubot.urlpreview",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "UrlPreviewBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "urlpreview"
+      ],
+      "version": "0.3.4.26"
+    }
+  },
+  "weather": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/kellya/maubot-weather/blob/v0.4.1/CHANGELOG.md",
+        "description": "A bot to get the weather from wttr.in and return a single line of text for the location specified.",
+        "downloadPage": "https://github.com/kellya/maubot-weather/releases",
+        "homepage": "https://github.com/kellya/maubot-weather"
+      }
+    },
+    "github": {
+      "hash": "sha256-DHMsemVbiXONeg45IpeaP477fbgkftz5mZdI6OhRHOI=",
+      "owner": "kellya",
+      "repo": "maubot-weather",
+      "rev": "v0.4.1"
+    },
+    "manifest": {
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "com.arachnitech.weather",
+      "license": "MIT",
+      "main_class": "WeatherBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "weather"
+      ],
+      "version": "0.4.1"
+    }
+  },
+  "webhook": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/jkhsjdhjs/maubot-webhook/releases",
+        "description": "Send messages to rooms via user-defined webhooks.",
+        "downloadPage": "https://github.com/jkhsjdhjs/maubot-webhook/releases",
+        "homepage": "https://github.com/jkhsjdhjs/maubot-webhook"
+      }
+    },
+    "github": {
+      "hash": "sha256-GGbd7PvW2P0u1h7Cp1GMuEg3uQ0osZBWWHzSW524aBc=",
+      "owner": "jkhsjdhjs",
+      "repo": "maubot-webhook",
+      "rev": "v0.2.0"
+    },
+    "manifest": {
+      "config": true,
+      "dependencies": [
+        "Jinja2~=3.1"
+      ],
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "me.jkhsjdhjs.maubot.webhook",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "WebhookPlugin",
+      "maubot": "0.3.1",
+      "modules": [
+        "plugin"
+      ],
+      "version": "0.2.0",
+      "webapp": true
+    }
+  },
+  "welcome": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/williamkray/maubot-welcome/releases",
+        "description": "A plugin that greets new people with a configurable message when they join a room.",
+        "downloadPage": "https://github.com/williamkray/maubot-welcome/releases",
+        "homepage": "https://github.com/williamkray/maubot-welcome"
+      }
+    },
+    "github": {
+      "hash": "sha256-8BIDj/kHys/Pw1n1lLtxjYOstI/UG5UAlxD+3rpKj0Q=",
+      "owner": "williamkray",
+      "repo": "maubot-welcome",
+      "rev": "a6d3e6cbea87056a1d4694f5379c9ae9d9cdf1c5"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "org.jobmachine.welcome",
+      "license": "MIT",
+      "main_class": "Greeter",
+      "maubot": "0.1.0",
+      "modules": [
+        "welcome"
+      ],
+      "version": "0.0.4"
+    }
+  },
+  "wolframalpha": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/ggogel/WolframAlphaMaubot/releases",
+        "description": "A bot that allows requesting information from [WolframAlpha](https://www.wolframalpha.com/).",
+        "downloadPage": "https://github.com/ggogel/WolframAlphaMaubot/releases",
+        "homepage": "https://github.com/ggogel/WolframAlphaMaubot"
+      }
+    },
+    "github": {
+      "hash": "sha256-2GJPAHc9xY7uznALpjzxkpAX16PBxMMSl3QMzjudA+w=",
+      "owner": "ggogel",
+      "repo": "WolframAlphaMaubot",
+      "rev": "v0.0.4"
+    },
+    "manifest": {
+      "database": false,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "me.gogel.maubot.wolframalpha",
+      "license": "MIT",
+      "main_class": "WolframAlphaPlugin",
+      "maubot": "0.1.0",
+      "modules": [
+        "wolframalpha"
+      ],
+      "version": "0.0.4"
+    }
+  },
+  "xkcd": {
+    "attrs": {
+      "meta": {
+        "changelog": "https://github.com/maubot/xkcd/releases",
+        "description": "A bot to view xkcd comics.",
+        "downloadPage": "https://github.com/maubot/xkcd/releases",
+        "homepage": "https://github.com/maubot/xkcd"
+      }
+    },
+    "github": {
+      "hash": "sha256-dtst/QuIZrMjk5RdbXjTksCbGwf8HCBsECDWtp70W1U=",
+      "owner": "maubot",
+      "repo": "xkcd",
+      "rev": "v1.2.0"
+    },
+    "isOfficial": true,
+    "manifest": {
+      "config": true,
+      "database": true,
+      "extra_files": [
+        "base-config.yaml"
+      ],
+      "id": "xyz.maubot.xkcd",
+      "license": "AGPL-3.0-or-later",
+      "main_class": "XKCDBot",
+      "maubot": "0.1.0",
+      "modules": [
+        "xkcd"
+      ],
+      "soft_dependencies": [
+        "python-magic>=0.4",
+        "Pillow>=5.1"
+      ],
+      "version": "1.2.0"
+    }
+  }
+}
diff --git a/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.nix b/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.nix
new file mode 100644
index 000000000000..241151eb6ca0
--- /dev/null
+++ b/nixpkgs/pkgs/tools/networking/maubot/plugins/generated.nix
@@ -0,0 +1,74 @@
+{ lib
+, fetchgit
+, fetchFromGitHub
+, fetchFromGitLab
+, fetchFromGitea
+, python3
+, poetry
+, buildMaubotPlugin
+}:
+
+let
+  json = builtins.fromJSON (builtins.readFile ./generated.json);
+in
+
+lib.flip builtins.mapAttrs json (name: entry:
+let
+  inherit (entry) manifest;
+
+  resolveDeps = deps: map
+    (name:
+      let
+        packageName = builtins.head (builtins.match "([^~=<>]*).*" name);
+        lower = lib.toLower packageName;
+        dash = builtins.replaceStrings ["_"] ["-"] packageName;
+        lowerDash = builtins.replaceStrings ["_"] ["-"] lower;
+      in
+        python3.pkgs.${packageName}
+        or python3.pkgs.${lower}
+        or python3.pkgs.${dash}
+        or python3.pkgs.${lowerDash}
+        or null)
+    (builtins.filter (x: x != "maubot" && x != null) deps);
+
+  reqDeps = resolveDeps (lib.toList (manifest.dependencies or null));
+  optDeps = resolveDeps (lib.toList (manifest.soft_dependencies or null));
+in
+
+lib.makeOverridable buildMaubotPlugin (entry.attrs // {
+  pname = manifest.id;
+  inherit (manifest) version;
+
+  src =
+    if entry?github then fetchFromGitHub entry.github
+    else if entry?git then fetchgit entry.git
+    else if entry?gitlab then fetchFromGitLab entry.gitlab
+    else if entry?gitea then fetchFromGitea entry.gitea
+    else throw "Invalid generated entry for ${manifest.id}: missing source";
+
+  propagatedBuildInputs = builtins.filter (x: x != null) (reqDeps ++ optDeps);
+
+  passthru.isOfficial = entry.isOfficial or false;
+
+  meta = entry.attrs.meta // {
+    license =
+      let
+        spdx = entry.attrs.meta.license or manifest.license or "unfree";
+        spdxLicenses = builtins.listToAttrs
+          (map (x: lib.nameValuePair x.spdxId x) (builtins.filter (x: x?spdxId) (builtins.attrValues lib.licenses)));
+      in
+      spdxLicenses.${spdx};
+    broken = builtins.any (x: x == null) reqDeps;
+  };
+} // lib.optionalAttrs (entry.isPoetry or false) {
+  nativeBuildInputs = [
+    poetry
+    (python3.withPackages (p: with p; [ toml ruamel-yaml isort ]))
+  ];
+
+  preBuild = lib.optionalString (entry?attrs.preBuild) (entry.attrs.preBuild + "\n") + ''
+    export HOME=$(mktemp -d)
+    [[ ! -d scripts ]] || patchShebangs --build scripts
+    make maubot.yaml
+  '';
+}))
diff --git a/nixpkgs/pkgs/tools/networking/maubot/plugins/update.py b/nixpkgs/pkgs/tools/networking/maubot/plugins/update.py
new file mode 100755
index 000000000000..a430753870fb
--- /dev/null
+++ b/nixpkgs/pkgs/tools/networking/maubot/plugins/update.py
@@ -0,0 +1,200 @@
+#!/usr/bin/env nix-shell
+#!nix-shell -i python3 -p git nurl "(python3.withPackages (ps: with ps; [ toml gitpython requests ruamel-yaml ]))"
+
+import git
+import json
+import os
+import subprocess
+import ruamel.yaml
+import sys
+import toml
+import zipfile
+
+from typing import Dict, List
+
+HOSTNAMES = {
+    'git.skeg1.se': 'gitlab',
+    'edugit.org': 'gitlab',
+    'codeberg.org': 'gitea',
+}
+PLUGINS: Dict[str, dict] = {}
+
+yaml = ruamel.yaml.YAML(typ='safe')
+
+TMP = os.environ.get('TEMPDIR', '/tmp')
+
+def process_repo(path: str, official: bool):
+    global PLUGINS
+    with open(path, 'rt') as f:
+        data = yaml.load(f)
+    name, repourl, license, desc = data['name'], data['repo'], data['license'], data['description']
+    origurl = repourl
+    if '/' in name or ' ' in name:
+        name = os.path.split(path)[-1].removesuffix('.yaml')
+    name = name.replace('_', '-')
+    if name in PLUGINS.keys():
+        raise ValueError(f'Duplicate plugin {name}, refusing to continue')
+    repodir = os.path.join(TMP, 'maubot-plugins', name)
+    plugindir = repodir
+    if '/tree/' in repourl:
+        repourl, rev_path = repourl.split('/tree/')
+        rev, subdir = rev_path.strip('/').split('/')
+        plugindir = os.path.join(plugindir, subdir)
+    else:
+        rev = None
+        subdir = None
+
+    if repourl.startswith('http:'):
+        repourl = 'https' + repourl[4:]
+    repourl = repourl.rstrip('/')
+    if not os.path.exists(repodir):
+        print('Fetching', name)
+        repo = git.Repo.clone_from(repourl + '.git', repodir)
+    else:
+        repo = git.Repo(repodir)
+    tags = sorted(repo.tags, key=lambda t: t.commit.committed_datetime)
+    tags = list(filter(lambda x: 'rc' not in str(x), tags))
+    if tags:
+        repo.git.checkout(tags[-1])
+        rev = str(tags[-1])
+    else:
+        rev = str(repo.commit('HEAD'))
+    ret: dict = {'attrs':{}}
+    if subdir:
+        ret['attrs']['postPatch'] = f'cd {subdir}'
+    domain, query = repourl.removeprefix('https://').split('/', 1)
+    hash = subprocess.run([
+        'nurl',
+        '--hash',
+        f'file://{repodir}',
+        rev
+    ], capture_output=True, check=True).stdout.decode('utf-8')
+    ret['attrs']['meta'] = {
+        'description': desc,
+        'homepage': origurl,
+    }
+    if domain.endswith('github.com'):
+        owner, repo = query.split('/')
+        ret['github'] = {
+            'owner': owner,
+            'repo': repo,
+            'rev': rev,
+            'hash': hash,
+        }
+        ret['attrs']['meta']['downloadPage'] = f'{repourl}/releases'
+        ret['attrs']['meta']['changelog'] = f'{repourl}/releases'
+        repobase = f'{repourl}/blob/{rev}'
+    elif HOSTNAMES.get(domain, 'gitea' if 'gitea.' in domain or 'forgejo.' in domain else None) == 'gitea':
+        owner, repo = query.split('/')
+        ret['gitea'] = {
+            'domain': domain,
+            'owner': owner,
+            'repo': repo,
+            'rev': rev,
+            'hash': hash,
+        }
+        repobase = f'{repourl}/src/commit/{rev}'
+        ret['attrs']['meta']['downloadPage'] = f'{repourl}/releases'
+        ret['attrs']['meta']['changelog'] = f'{repourl}/releases'
+    elif HOSTNAMES.get(domain, 'gitlab' if 'gitlab.' in domain else None) == 'gitlab':
+        owner, repo = query.split('/')
+        ret['gitlab'] = {
+            'owner': owner,
+            'repo': repo,
+            'rev': rev,
+            'hash': hash,
+        }
+        if domain != 'gitlab.com':
+            ret['gitlab']['domain'] = domain
+        repobase = f'{repourl}/-/blob/{rev}'
+    else:
+        raise ValueError(f'Is {domain} Gitea or Gitlab, or something else? Please specify in the Python script!')
+    if os.path.exists(os.path.join(plugindir, 'CHANGELOG.md')):
+        ret['attrs']['meta']['changelog'] = f'{repobase}/CHANGELOG.md'
+    if os.path.exists(os.path.join(plugindir, 'maubot.yaml')):
+        with open(os.path.join(plugindir, 'maubot.yaml'), 'rt') as f:
+            ret['manifest'] = yaml.load(f)
+    elif os.path.exists(os.path.join(plugindir, 'pyproject.toml')):
+        ret['isPoetry'] = True
+        with open(os.path.join(plugindir, 'pyproject.toml'), 'rt') as f:
+            data = toml.load(f)
+        deps = []
+        for key, val in data['tool']['poetry'].get('dependencies', {}).items():
+            if key in ['maubot', 'mautrix', 'python']:
+                continue
+            reqs = []
+            for req in val.split(','):
+                reqs.extend(poetry_to_pep(req))
+            deps.append(key + ', '.join(reqs))
+        ret['manifest'] = data['tool']['maubot']
+        ret['manifest']['id'] = data['tool']['poetry']['name']
+        ret['manifest']['version'] = data['tool']['poetry']['version']
+        ret['manifest']['license'] = data['tool']['poetry']['license']
+        if deps:
+            ret['manifest']['dependencies'] = deps
+    else:
+        raise ValueError(f'No maubot.yaml or pyproject.toml found in {repodir}')
+    # normalize non-spdx-conformant licenses this way
+    # (and fill out missing license info)
+    if 'license' not in ret['manifest'] or ret['manifest']['license'] in ['GPLv3', 'AGPL 3.0']:
+        ret['attrs']['meta']['license'] = license
+    elif ret['manifest']['license'] != license:
+        print(f"Warning: licenses for {repourl} don't match! {ret['manifest']['license']} != {license}")
+    if official:
+        ret['isOfficial'] = official
+    PLUGINS[name] = ret
+
+def next_incomp(ver_s: str) -> str:
+    ver = ver_s.split('.')
+    zero = False
+    for i in range(len(ver)):
+        try:
+            seg = int(ver[i])
+        except ValueError:
+            if zero:
+                ver = ver[:i]
+                break
+            continue
+        if zero:
+            ver[i] = '0'
+        elif seg:
+            ver[i] = str(seg + 1)
+            zero = True
+    return '.'.join(ver)
+
+def poetry_to_pep(ver_req: str) -> List[str]:
+    if '*' in ver_req:
+        raise NotImplementedError('Wildcard poetry versions not implemented!')
+    if ver_req.startswith('^'):
+        return ['>=' + ver_req[1:], '<' + next_incomp(ver_req[1:])]
+    if ver_req.startswith('~'):
+        return ['~=' + ver_req[1:]]
+    return [ver_req]
+
+def main():
+    cache_path = os.path.join(TMP, 'maubot-plugins')
+    if not os.path.exists(cache_path):
+        os.makedirs(cache_path)
+        git.Repo.clone_from('https://github.com/maubot/plugins.maubot.xyz', os.path.join(cache_path, '_repo'))
+    else:
+        pass
+
+    repodir = os.path.join(cache_path, '_repo')
+
+    for suffix, official in (('official', True), ('thirdparty', False)):
+        directory = os.path.join(repodir, 'data', 'plugins', suffix)
+        for plugin_name in os.listdir(directory):
+            process_repo(os.path.join(directory, plugin_name), official)
+
+    if os.path.isdir('pkgs/tools/networking/maubot/plugins'):
+        generated = 'pkgs/tools/networking/maubot/plugins/generated.json'
+    else:
+        script_dir = os.path.dirname(os.path.realpath(__file__))
+        generated = os.path.join(script_dir, 'generated.json')
+
+    with open(generated, 'wt') as file:
+        json.dump(PLUGINS, file, indent='  ', separators=(',', ': '), sort_keys=True)
+        file.write('\n')
+
+if __name__ == '__main__':
+    main()
diff --git a/nixpkgs/pkgs/tools/networking/maubot/wrapper.nix b/nixpkgs/pkgs/tools/networking/maubot/wrapper.nix
new file mode 100644
index 000000000000..baa0c29052e9
--- /dev/null
+++ b/nixpkgs/pkgs/tools/networking/maubot/wrapper.nix
@@ -0,0 +1,70 @@
+{ lib
+, symlinkJoin
+, runCommand
+, unwrapped
+, python3
+, formats
+}:
+
+let wrapper = { pythonPackages ? (_: [ ]), plugins ? (_: [ ]), baseConfig ? null }:
+  let
+    plugins' = plugins unwrapped.plugins;
+    extraPythonPackages = builtins.concatLists (map (p: p.propagatedBuildInputs or [ ]) plugins');
+  in
+  symlinkJoin {
+    name = "${unwrapped.pname}-with-plugins-${unwrapped.version}";
+
+    inherit unwrapped;
+    paths = lib.optional (baseConfig != null) unwrapped ++ plugins';
+    pythonPath = lib.optional (baseConfig == null) unwrapped ++ pythonPackages python3.pkgs ++ extraPythonPackages;
+
+    nativeBuildInputs = [ python3.pkgs.wrapPython ];
+
+    postBuild = ''
+      rm -f $out/nix-support/propagated-build-inputs
+      rmdir $out/nix-support || true
+      ${lib.optionalString (baseConfig != null) ''
+        rm $out/${python3.sitePackages}/maubot/example-config.yaml
+        substituteAll ${(formats.yaml { }).generate "example-config.yaml" (lib.recursiveUpdate baseConfig {
+          plugin_directories = lib.optionalAttrs (plugins' != []) {
+            load = [ "@out@/lib/maubot-plugins" ] ++ (baseConfig.plugin_directories.load or []);
+          };
+          # Normally it should be set to false by default to take it from package
+          # root, but aiohttp doesn't follow symlinks when serving static files
+          # unless follow_symlinks=True is passed. Instead of patching maubot, use
+          # this non-invasive approach
+          # XXX: would patching maubot be better? See:
+          # https://github.com/maubot/maubot/blob/75879cfb9370aade6fa0e84e1dde47222625139a/maubot/server.py#L106
+          server.override_resource_path =
+            if builtins.isNull (baseConfig.server.override_resource_path or null)
+            then "${unwrapped}/${python3.sitePackages}/maubot/management/frontend/build"
+            else baseConfig.server.override_resource_path;
+        })})} $out/${python3.sitePackages}/maubot/example-config.yaml
+        rm -rf $out/bin
+      ''}
+      mkdir -p $out/bin
+      cp $unwrapped/bin/.mbc-wrapped $out/bin/mbc
+      cp $unwrapped/bin/.maubot-wrapped $out/bin/maubot
+      wrapPythonProgramsIn "$out/bin" "${lib.optionalString (baseConfig != null) "$out "}$pythonPath"
+    '';
+
+    passthru = {
+      inherit unwrapped;
+      python = python3;
+      withPythonPackages = filter: wrapper {
+        pythonPackages = pkgs: pythonPackages pkgs ++ filter pkgs;
+        inherit plugins baseConfig;
+      };
+      withPlugins = filter: wrapper {
+        plugins = pkgs: plugins pkgs ++ filter pkgs;
+        inherit pythonPackages baseConfig;
+      };
+      withBaseConfig = baseConfig: wrapper {
+        inherit baseConfig pythonPackages plugins;
+      };
+    };
+
+    meta.priority = (unwrapped.meta.priority or 0) - 1;
+  };
+in
+wrapper
diff --git a/nixpkgs/pkgs/tools/networking/muffet/default.nix b/nixpkgs/pkgs/tools/networking/muffet/default.nix
index 19458f6461bb..133eaf3b27ba 100644
--- a/nixpkgs/pkgs/tools/networking/muffet/default.nix
+++ b/nixpkgs/pkgs/tools/networking/muffet/default.nix
@@ -5,16 +5,16 @@
 
 buildGoModule rec {
   pname = "muffet";
-  version = "2.9.2";
+  version = "2.9.3";
 
   src = fetchFromGitHub {
     owner = "raviqqe";
     repo = "muffet";
     rev = "v${version}";
-    hash = "sha256-M+yId2cNTO1n+E0UmMJK7aLmeDdXnI3McqTxL5EvB+A=";
+    hash = "sha256-w9PoKGxZdP/sKdlTlnWBMqDPDLUvcYubkCyNHUm3AAc=";
   };
 
-  vendorHash = "sha256-NTQlhLlSPh9+Il08T9I2qc+BqIo9RniOFG9Dgeez1QA=";
+  vendorHash = "sha256-2an4xj1gqQqj9NrSdTAss7hn6SiWoiq3RQ2xxUlSuaE=";
 
   meta = with lib; {
     description = "A website link checker which scrapes and inspects all pages in a website recursively";
diff --git a/nixpkgs/pkgs/tools/networking/netbird/default.nix b/nixpkgs/pkgs/tools/networking/netbird/default.nix
index b9a9aa78d6fc..c74d08029986 100644
--- a/nixpkgs/pkgs/tools/networking/netbird/default.nix
+++ b/nixpkgs/pkgs/tools/networking/netbird/default.nix
@@ -30,16 +30,16 @@ let
 in
 buildGoModule rec {
   pname = "netbird";
-  version = "0.24.2";
+  version = "0.24.3";
 
   src = fetchFromGitHub {
     owner = "netbirdio";
     repo = pname;
     rev = "v${version}";
-    hash = "sha256-/gSQiBlcOeQQud8rXPIjY88+jjC0/6S+OTmFqhQxQVM=";
+    hash = "sha256-r/2P0QeILO0t5GIXD6yrqdUdOpPzNfBIniPhKdlJ+0g=";
   };
 
-  vendorHash = "sha256-mSK5qQqPd6pTDLIBUa2MK8nNdi1VzNRU+GEaW+lGLpY=";
+  vendorHash = "sha256-FTr36gndWTrpEKo7KXdZJIR7aM0jrEOTFm1JlxokRaw=";
 
   nativeBuildInputs = [ installShellFiles ] ++ lib.optional ui pkg-config;
 
@@ -89,7 +89,7 @@ buildGoModule rec {
       '')
       modules) + lib.optionalString (stdenv.isLinux && ui) ''
     mkdir -p $out/share/pixmaps
-    cp $src/client/ui/disconnected.png $out/share/pixmaps/netbird.png
+    cp $src/client/ui/netbird-systemtray-default.png $out/share/pixmaps/netbird.png
 
     mkdir -p $out/share/applications
     cp $src/client/ui/netbird.desktop $out/share/applications/netbird.desktop
diff --git a/nixpkgs/pkgs/tools/networking/netifd/default.nix b/nixpkgs/pkgs/tools/networking/netifd/default.nix
index 315d58403825..25aada6e3c44 100644
--- a/nixpkgs/pkgs/tools/networking/netifd/default.nix
+++ b/nixpkgs/pkgs/tools/networking/netifd/default.nix
@@ -18,6 +18,6 @@ stdenv.mkDerivation {
     homepage = "https://git.openwrt.org/?p=project/netifd.git;a=summary";
     license = licenses.lgpl21Only;
     platforms = platforms.linux;
-    maintainers = with maintainers; [ ];
+    maintainers = with maintainers; [ mkg20001 ];
   };
 }
diff --git a/nixpkgs/pkgs/tools/networking/ngrep/default.nix b/nixpkgs/pkgs/tools/networking/ngrep/default.nix
index bee8678d1c93..c44f6e1eb832 100644
--- a/nixpkgs/pkgs/tools/networking/ngrep/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ngrep/default.nix
@@ -44,10 +44,12 @@ stdenv.mkDerivation rec {
       more common packet sniffing tools, such as tcpdump and snoop.
     '';
     homepage = "https://github.com/jpr5/ngrep/";
-    # <ngrep>/doc/README.txt says that ngrep itself is licensed under a
-    # 'BSD-like' license but that the 'regex' library (in the ngrep tarball) is
-    # GPLv2.
-    license = "ngrep";  # Some custom BSD-style, see LICENSE.txt
+    license = {
+      shortName = "ngrep";  # BSD-style, see README.md and LICENSE
+      url = "https://github.com/jpr5/ngrep/blob/master/LICENSE";
+      free = true;
+      redistributable = true;
+    };
     platforms = with platforms; linux ++ darwin;
     maintainers = [ maintainers.bjornfor ];
   };
diff --git a/nixpkgs/pkgs/tools/networking/ockam/default.nix b/nixpkgs/pkgs/tools/networking/ockam/default.nix
index fe5ba72caf68..fe0bbf374635 100644
--- a/nixpkgs/pkgs/tools/networking/ockam/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ockam/default.nix
@@ -12,7 +12,7 @@
 
 let
   pname = "ockam";
-  version = "0.90.0";
+  version = "0.105.0";
 in
 rustPlatform.buildRustPackage {
   inherit pname version;
@@ -21,10 +21,10 @@ rustPlatform.buildRustPackage {
     owner = "build-trust";
     repo = pname;
     rev = "ockam_v${version}";
-    sha256 = "sha256-IblL87YSSTew4UOZEkbPrQ1Zy9x33mfxGG1kg1atxrs=";
+    sha256 = "sha256-YS98elkf1iIslC1dAf+Os2VoA0pmHmkQN0//PtBRBcM=";
   };
 
-  cargoHash = "sha256-/fKqUOa1Dos01IKyIZIjWwpZNXKh+cVoq4s2TUFWkBw=";
+  cargoHash = "sha256-aW+Pc2C7vohUAByrzBiOaJlBPfSLAv0FrOxRiB1AM9k=";
   nativeBuildInputs = [ git pkg-config ];
   buildInputs = [ openssl dbus ]
     ++ lib.optionals stdenv.isDarwin [ Security ];
diff --git a/nixpkgs/pkgs/tools/networking/oha/default.nix b/nixpkgs/pkgs/tools/networking/oha/default.nix
index 3fd3bc49c916..03028ca580a1 100644
--- a/nixpkgs/pkgs/tools/networking/oha/default.nix
+++ b/nixpkgs/pkgs/tools/networking/oha/default.nix
@@ -9,16 +9,16 @@
 
 rustPlatform.buildRustPackage rec {
   pname = "oha";
-  version = "0.6.5";
+  version = "1.0.0";
 
   src = fetchFromGitHub {
     owner = "hatoo";
     repo = pname;
     rev = "refs/tags/v${version}";
-    sha256 = "sha256-eC0EiBD0FQ/Ucvjh5q1htZLVmpzzOzKAVmHW6/Krc0Q=";
+    sha256 = "sha256-QZEDp+XCc3ZWQ1UTlMUpdvJCbuO6VCYnJj1Jj9o+Ovs=";
   };
 
-  cargoSha256 = "sha256-AmFDi5l55tJ3yZwTH4DyxOsium8WoSW7JVmn1L+lRpU=";
+  cargoSha256 = "sha256-JEbsAJ9NbWw03qYUQqLx7sA04Xq990zdBuludVbxoIg=";
 
   nativeBuildInputs = lib.optionals stdenv.isLinux [
     pkg-config
diff --git a/nixpkgs/pkgs/tools/networking/ooniprobe-cli/default.nix b/nixpkgs/pkgs/tools/networking/ooniprobe-cli/default.nix
index baf0ba802c0f..b677b1d1ca01 100644
--- a/nixpkgs/pkgs/tools/networking/ooniprobe-cli/default.nix
+++ b/nixpkgs/pkgs/tools/networking/ooniprobe-cli/default.nix
@@ -5,16 +5,16 @@
 
 buildGoModule rec {
   pname = "ooniprobe-cli";
-  version = "3.19.0";
+  version = "3.19.1";
 
   src = fetchFromGitHub {
     owner = "ooni";
     repo = "probe-cli";
     rev = "v${version}";
-    hash = "sha256-W3C4KbZnOdljofnlYZk/F6E77/AXjdNTRoWrtoEVfqg=";
+    hash = "sha256-sYIp5zl49waERfTYPfNjbyzep7p4sRlweDVcuTtWB28=";
   };
 
-  vendorHash = "sha256-wEhh0nMdFH9wLfNSxYvbkbtu69cNEmVpQDk57/gdnw8=";
+  vendorHash = "sha256-6RyK0oy9Lcuh2TXpQqAqmrA+bS9hug6+il7L1z+kYvs=";
 
   subPackages = [ "cmd/ooniprobe" ];
 
diff --git a/nixpkgs/pkgs/tools/networking/opendrop/default.nix b/nixpkgs/pkgs/tools/networking/opendrop/default.nix
index 6a8937215105..a617eadfc410 100644
--- a/nixpkgs/pkgs/tools/networking/opendrop/default.nix
+++ b/nixpkgs/pkgs/tools/networking/opendrop/default.nix
@@ -1,24 +1,37 @@
 { lib
 , buildPythonApplication
-, fetchPypi
+, fetchFromGitHub
 , fleep
+, ifaddr
 , libarchive-c
 , pillow
 , requests-toolbelt
 , setuptools
-, zeroconf }:
+, zeroconf
+, pytestCheckHook
+, openssl
+}:
 
 buildPythonApplication rec {
   pname = "opendrop";
   version = "0.13.0";
+  format = "setuptools";
 
-  src = fetchPypi {
-    inherit version pname;
-    sha256 = "sha256-FE1oGpL6C9iBhI8Zj71Pm9qkObJvSeU2gaBZwK1bTQc=";
+  src = fetchFromGitHub {
+    owner = "seemoo-lab";
+    repo = "opendrop";
+    rev = "v${version}";
+    hash = "sha256-4FeVQO7Z6t9mjIgesdjKx4Mi+Ro5EVGJpEFjCvB2SlA=";
   };
 
+  nativeBuildInputs = [
+    # Tests fail if I put it on buildInputs
+    openssl
+  ];
+
   propagatedBuildInputs = [
     fleep
+    ifaddr
     libarchive-c
     pillow
     requests-toolbelt
@@ -26,16 +39,26 @@ buildPythonApplication rec {
     zeroconf
   ];
 
-  # There are tests, but getting the following error:
-  # nix_run_setup: error: argument action: invalid choice: 'test' (choose from 'receive', 'find', 'send')
-  # Opendrop works as intended though
-  doCheck = false;
+  makeWrapperArgs = [
+    "--prefix PATH : ${lib.makeBinPath nativeBuildInputs}"
+  ];
+
+  checkInputs = [
+    pytestCheckHook
+  ];
+
+  preCheck = ''
+    # Solves PermissionError: [Errno 13] Permission denied: '/homeless-shelter'
+    export HOME=$(mktemp -d)
+  '';
 
   meta = with lib; {
     description = "An open Apple AirDrop implementation written in Python";
     homepage = "https://owlink.org/";
+    changelog = "https://github.com/seemoo-lab/opendrop/releases/tag/${src.rev}";
     license = licenses.gpl3Only;
     maintainers = with maintainers; [ wolfangaukang ];
+    mainProgram = "opendrop";
     platforms = [ "x86_64-linux" ];
   };
 }
diff --git a/nixpkgs/pkgs/tools/networking/opensnitch/daemon.nix b/nixpkgs/pkgs/tools/networking/opensnitch/daemon.nix
index 98c7f51ba71e..9825d25bbc5a 100644
--- a/nixpkgs/pkgs/tools/networking/opensnitch/daemon.nix
+++ b/nixpkgs/pkgs/tools/networking/opensnitch/daemon.nix
@@ -18,13 +18,13 @@
 
 buildGoModule rec {
   pname = "opensnitch";
-  version = "1.6.3";
+  version = "1.6.4";
 
   src = fetchFromGitHub {
     owner = "evilsocket";
     repo = "opensnitch";
     rev = "v${version}";
-    hash = "sha256-C8Uuz2FC7Zu07ZmFpp+ejpNxkyC3/mM9J2dc5FUKx64=";
+    hash = "sha256-fkRykhcjWZ4MDl2HZ1ZFaQmEeRYhiCBeUxG/Eu7D8NA=";
   };
 
   postPatch = ''
diff --git a/nixpkgs/pkgs/tools/networking/opensnitch/ui.nix b/nixpkgs/pkgs/tools/networking/opensnitch/ui.nix
index 86ceeb281cea..9e7903149070 100644
--- a/nixpkgs/pkgs/tools/networking/opensnitch/ui.nix
+++ b/nixpkgs/pkgs/tools/networking/opensnitch/ui.nix
@@ -7,13 +7,13 @@
 
 python3Packages.buildPythonApplication rec {
   pname = "opensnitch-ui";
-  version = "1.6.2";
+  version = "1.6.4";
 
   src = fetchFromGitHub {
     owner = "evilsocket";
     repo = "opensnitch";
     rev = "refs/tags/v${version}";
-    hash = "sha256-1ArwbewgZuoDF2lxY720yFQSsTuLR0WkS8vsTCr2FL4=";
+    hash = "sha256-fkRykhcjWZ4MDl2HZ1ZFaQmEeRYhiCBeUxG/Eu7D8NA=";
   };
 
   postPatch = ''
diff --git a/nixpkgs/pkgs/tools/networking/pgrok/build-deps/package.json b/nixpkgs/pkgs/tools/networking/pgrok/build-deps/package.json
index 3ace3f15e44c..b40bf794c6de 100644
--- a/nixpkgs/pkgs/tools/networking/pgrok/build-deps/package.json
+++ b/nixpkgs/pkgs/tools/networking/pgrok/build-deps/package.json
@@ -5,7 +5,7 @@
     "build": "tsc && vite build --outDir=dist --emptyOutDir",
     "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0"
   },
-  "version": "1.4.0",
+  "version": "1.4.1",
   "dependencies": {
     "axios": "~1.4.0",
     "react": "~18.2.0",
diff --git a/nixpkgs/pkgs/tools/networking/pgrok/default.nix b/nixpkgs/pkgs/tools/networking/pgrok/default.nix
index 21a62ba8ccd6..ab1c6d9f0a61 100644
--- a/nixpkgs/pkgs/tools/networking/pgrok/default.nix
+++ b/nixpkgs/pkgs/tools/networking/pgrok/default.nix
@@ -5,16 +5,16 @@
 }:
 buildGoModule rec {
   pname = "pgrok";
-  version = "1.4.0";
+  version = "1.4.1";
 
   src = fetchFromGitHub {
     owner = "pgrok";
     repo = "pgrok";
     rev = "v${version}";
-    hash = "sha256-2k3XLXmf1Xnx4HvS7sD/aq+78Z4I7uY4djV958n5TX4=";
+    hash = "sha256-P36rpFi5J+dF6FrVaPhqupG00h4kwr0qumt4ehL/7vU=";
   };
 
-  vendorHash = "sha256-M0xVHRh9NKPxmUEmx1dDQUZc8aXcdAfHisQAnt72RdY=";
+  vendorHash = "sha256-X5FjzliIJdfJnNaUXBjv1uq5tyjMVjBbnLCBH/P0LFM=";
 
   outputs = [ "out" "server" ];
 
diff --git a/nixpkgs/pkgs/tools/networking/q/default.nix b/nixpkgs/pkgs/tools/networking/q/default.nix
index 40d61afd65d8..3bf04806233c 100644
--- a/nixpkgs/pkgs/tools/networking/q/default.nix
+++ b/nixpkgs/pkgs/tools/networking/q/default.nix
@@ -2,16 +2,16 @@
 
 buildGoModule rec {
   pname = "q";
-  version = "0.13.5";
+  version = "0.15.1";
 
   src = fetchFromGitHub {
     owner = "natesales";
     repo = "q";
     rev = "v${version}";
-    sha256 = "sha256-3T72841HoZTjyzebSL7oWWwbvxBMKSX98usCrkZ4QuI=";
+    sha256 = "sha256-yItgytsPR/FkiERHhLTq1vNJbZ204DckEc3xK3PaPKM=";
   };
 
-  vendorHash = "sha256-VjwlNCmq5yAYlQRg+rKsN6EPDeb0FcnK5Y4MzBNO0Kg=";
+  vendorHash = "sha256-xLv2F/rOSjMTnTrLck/1E8Y0fTbpUutQIJGmqetqYjg=";
 
   doCheck = false; # tries to resolve DNS
 
diff --git a/nixpkgs/pkgs/tools/networking/requestly/default.nix b/nixpkgs/pkgs/tools/networking/requestly/default.nix
index 3a4128c0806d..b23336e6d0e9 100644
--- a/nixpkgs/pkgs/tools/networking/requestly/default.nix
+++ b/nixpkgs/pkgs/tools/networking/requestly/default.nix
@@ -5,11 +5,11 @@
 
 let
   pname = "requestly";
-  version = "1.5.12";
+  version = "1.5.13";
 
   src = fetchurl {
     url = "https://github.com/requestly/requestly-desktop-app/releases/download/v${version}/Requestly-${version}.AppImage";
-    hash = "sha256-HM3+j9E67J1bAklnDtSN5/rOK9Wn7N7h+qlPKR/E8Ns=";
+    hash = "sha256-DSOZBVBjIYO8BG3o7AUsH7h2KvSPlp9Lj9d3OwvBhfQ=";
   };
 
   appimageContents = appimageTools.extractType2 { inherit pname version src; };
diff --git a/nixpkgs/pkgs/tools/networking/sing-box/default.nix b/nixpkgs/pkgs/tools/networking/sing-box/default.nix
index 0d75f874a198..d29bbe1292db 100644
--- a/nixpkgs/pkgs/tools/networking/sing-box/default.nix
+++ b/nixpkgs/pkgs/tools/networking/sing-box/default.nix
@@ -11,16 +11,16 @@
 
 buildGoModule rec {
   pname = "sing-box";
-  version = "1.6.5";
+  version = "1.7.0";
 
   src = fetchFromGitHub {
     owner = "SagerNet";
     repo = pname;
     rev = "v${version}";
-    hash = "sha256-djbRt4VdrZ2a0yLbNaFNhKIN0AwuCCJATIcwFhnw5aM=";
+    hash = "sha256-XD4xWOQumqbXMBbzHgCIgFIegUqJnFZsAvk1VZXX5rc=";
   };
 
-  vendorHash = "sha256-qoW9+t427k5Ea9BhAdWIh+utD7EnIU1OLKJfsmYlEt8=";
+  vendorHash = "sha256-U70FjJ0HO5dyFj50qpyjy+k2r7IR/6gOLDi2LM3M3No=";
 
   tags = [
     "with_quic"
diff --git a/nixpkgs/pkgs/tools/networking/tridactyl-native/default.nix b/nixpkgs/pkgs/tools/networking/tridactyl-native/default.nix
deleted file mode 100644
index 91043caa4354..000000000000
--- a/nixpkgs/pkgs/tools/networking/tridactyl-native/default.nix
+++ /dev/null
@@ -1,29 +0,0 @@
-{ lib, nimPackages, fetchFromGitHub }:
-
-nimPackages.buildNimPackage rec {
-  pname = "tridactyl-native";
-  version = "0.3.7";
-
-  src = fetchFromGitHub {
-    owner = "tridactyl";
-    repo = "native_messenger";
-    rev = "62f19dba573b924703829847feb1bfee68885514";
-    sha256 = "sha256-YGDVcfFcI9cRCCZ4BrO5xTuI9mrGq1lfbEITB7o3vQQ=";
-  };
-  buildInputs = with nimPackages; [ tempfile ];
-
-  installPhase = ''
-    mkdir -p "$out/lib/mozilla/native-messaging-hosts"
-    sed -i -e "s|REPLACE_ME_WITH_SED|$out/bin/native_main|" "tridactyl.json"
-    cp tridactyl.json "$out/lib/mozilla/native-messaging-hosts/"
-  '';
-
-  meta = with lib; {
-    description =
-      "Native messenger for Tridactyl, a vim-like Firefox webextension";
-    homepage = "https://github.com/tridactyl/native_messenger";
-    license = licenses.bsd2;
-    platforms = platforms.all;
-    maintainers = with maintainers; [ timokau dit7ya ];
-  };
-}
diff --git a/nixpkgs/pkgs/tools/networking/uqmi/default.nix b/nixpkgs/pkgs/tools/networking/uqmi/default.nix
index 31c004986355..8050909487da 100644
--- a/nixpkgs/pkgs/tools/networking/uqmi/default.nix
+++ b/nixpkgs/pkgs/tools/networking/uqmi/default.nix
@@ -28,6 +28,6 @@ stdenv.mkDerivation {
     homepage = "https://git.openwrt.org/?p=project/uqmi.git;a=summary";
     license = licenses.gpl2Plus;
     platforms = platforms.all;
-    maintainers = with maintainers; [ fpletz ];
+    maintainers = with maintainers; [ fpletz mkg20001 ];
   };
 }
diff --git a/nixpkgs/pkgs/tools/networking/v2raya/default.nix b/nixpkgs/pkgs/tools/networking/v2raya/default.nix
index c861fd68c8bd..02f348a2df9a 100644
--- a/nixpkgs/pkgs/tools/networking/v2raya/default.nix
+++ b/nixpkgs/pkgs/tools/networking/v2raya/default.nix
@@ -11,13 +11,13 @@
 }:
 let
   pname = "v2raya";
-  version = "2.2.4";
+  version = "2.2.4.3";
 
   src = fetchFromGitHub {
     owner = "v2rayA";
     repo = "v2rayA";
     rev = "v${version}";
-    hash = "sha256-X2fCp9uVdt7fIW1C/tdRK1Tmr8mq6VBk6UBnt99E+1c=";
+    hash = "sha256-6643sdKVHOHrGRocTm881GCHoON4tlrKcNfOFMHwnQY=";
     postFetch = "sed -i -e 's/npmmirror/yarnpkg/g' $out/gui/yarn.lock";
   };
   guiSrc = "${src}/gui";
@@ -30,7 +30,7 @@ let
 
     offlineCache = fetchYarnDeps {
       yarnLock = "${guiSrc}/yarn.lock";
-      sha256 = "sha256-pB0B5Iy6dLfU5CL2E9OBQGJKLJqYQRwPxx9aaCDg1Qk=";
+      sha256 = "sha256-rZIcVLolTMdtN27W6gCw9uk9m4N5v9SZn2563+aN/gs=";
     };
 
     buildPhase = ''
@@ -62,7 +62,7 @@ buildGoModule {
   inherit pname version;
 
   src = "${src}/service";
-  vendorHash = "sha256-lK6oTI9o8oLXPPMFO/Q97tIsdRd9smUk1v7GwwCFitg=";
+  vendorHash = "sha256-wwDv2ThHwtnUpAnQoc0Ms0mGC44jRvABcE4K5MrF8S4=";
 
   ldflags = [
     "-s"
diff --git a/nixpkgs/pkgs/tools/networking/v2raya/package.json b/nixpkgs/pkgs/tools/networking/v2raya/package.json
index 3886aaa1616c..531c64b76311 100644
--- a/nixpkgs/pkgs/tools/networking/v2raya/package.json
+++ b/nixpkgs/pkgs/tools/networking/v2raya/package.json
@@ -9,9 +9,10 @@
     "lint": "vue-cli-service lint"
   },
   "resolutions": {
-    "@achrinza/node-ipc": "^10.1.9"
+    "@achrinza/node-ipc": "^10.1.10"
   },
   "dependencies": {
+    "@achrinza/node-ipc": "^10.1.10",
     "@mdi/font": "^5.8.55",
     "@nuintun/qrcode": "^3.3.0",
     "@vue/babel-preset-app": "^4.2.2",
diff --git a/nixpkgs/pkgs/tools/networking/wg-friendly-peer-names/default.nix b/nixpkgs/pkgs/tools/networking/wg-friendly-peer-names/default.nix
index eaa8efbcebdb..ebbd898576d3 100644
--- a/nixpkgs/pkgs/tools/networking/wg-friendly-peer-names/default.nix
+++ b/nixpkgs/pkgs/tools/networking/wg-friendly-peer-names/default.nix
@@ -6,13 +6,13 @@
 
 stdenv.mkDerivation {
   pname = "wg-friendly-peer-names";
-  version = "unstable-2021-11-08";
+  version = "unstable-2021-12-10";
 
   src = fetchFromGitHub {
     owner = "FlyveHest";
     repo = "wg-friendly-peer-names";
-    rev = "66b9b6b74ec77b9fec69b2a58296635321d4f5f1";
-    sha256 = "pH/b5rCHIqLxz/Fnx+Dm0m005qAUWBsczSU9vGEQ2RQ=";
+    rev = "b0c3e1a95c843dc9c6432895105b839ef9b362fc";
+    hash = "sha256-aGxrABmR+aQO35RYo/zI2037clnGOW0Tr16p7M1fQqc=";
   };
 
   installPhase = ''
diff --git a/nixpkgs/pkgs/tools/networking/wol/default.nix b/nixpkgs/pkgs/tools/networking/wol/default.nix
index 114a8457d5b2..14cf48ae0dbd 100644
--- a/nixpkgs/pkgs/tools/networking/wol/default.nix
+++ b/nixpkgs/pkgs/tools/networking/wol/default.nix
@@ -19,6 +19,7 @@ stdenv.mkDerivation rec {
     homepage = "https://sourceforge.net/projects/wake-on-lan/";
     license = licenses.gpl2;
     maintainers = with maintainers; [ makefu ];
+    mainProgram = "wol";
     platforms = platforms.linux;
   };
 }