lol

chatgpt-retrieval-plugin: init module

authored by

happysalada and committed by
Yt
5ba4f429 2a9cc485

+117 -2
+1
nixos/modules/module-list.nix
··· 1138 1138 ./services/web-apps/calibre-web.nix 1139 1139 ./services/web-apps/coder.nix 1140 1140 ./services/web-apps/changedetection-io.nix 1141 + ./services/web-apps/chatgpt-retrieval-plugin.nix 1141 1142 ./services/web-apps/cloudlog.nix 1142 1143 ./services/web-apps/code-server.nix 1143 1144 ./services/web-apps/convos.nix
+106
nixos/modules/services/web-apps/chatgpt-retrieval-plugin.nix
··· 1 + { config, pkgs, lib, ... }: 2 + 3 + with lib; 4 + 5 + let 6 + cfg = config.services.chatgpt-retrieval-plugin; 7 + in 8 + { 9 + options.services.chatgpt-retrieval-plugin = { 10 + enable = mkEnableOption (lib.mdDoc "chatgpt-retrieval-plugin service"); 11 + 12 + port = mkOption { 13 + type = types.port; 14 + default = 8080; 15 + description = lib.mdDoc "Port the chatgpt-retrieval-plugin service listens on."; 16 + }; 17 + 18 + host = mkOption { 19 + type = types.str; 20 + default = "127.0.0.1"; 21 + example = "0.0.0.0"; 22 + description = lib.mdDoc "The hostname or IP address for chatgpt-retrieval-plugin to bind to."; 23 + }; 24 + 25 + bearerTokenPath = mkOption { 26 + type = types.path; 27 + description = lib.mdDoc '' 28 + Path to the secret bearer token used for the http api authentication. 29 + ''; 30 + default = ""; 31 + example = "config.age.secrets.CHATGPT_RETRIEVAL_PLUGIN_BEARER_TOKEN.path"; 32 + }; 33 + 34 + openaiApiKeyPath = mkOption { 35 + type = types.path; 36 + description = lib.mdDoc '' 37 + Path to the secret openai api key used for embeddings. 38 + ''; 39 + default = ""; 40 + example = "config.age.secrets.CHATGPT_RETRIEVAL_PLUGIN_OPENAI_API_KEY.path"; 41 + }; 42 + 43 + datastore = mkOption { 44 + type = types.enum [ "pinecone" "weaviate" "zilliz" "milvus" "qdrant" "redis" ]; 45 + default = "qdrant"; 46 + description = lib.mdDoc "This specifies the vector database provider you want to use to store and query embeddings."; 47 + }; 48 + 49 + qdrantCollection = mkOption { 50 + type = types.str; 51 + description = lib.mdDoc '' 52 + name of the qdrant collection used to store documents. 53 + ''; 54 + default = "document_chunks"; 55 + }; 56 + }; 57 + 58 + config = mkIf cfg.enable { 59 + 60 + assertions = [ 61 + { 62 + assertion = cfg.bearerTokenPath != ""; 63 + message = "services.chatgpt-retrieval-plugin.bearerTokenPath should not be an empty string."; 64 + } 65 + { 66 + assertion = cfg.openaiApiKeyPath != ""; 67 + message = "services.chatgpt-retrieval-plugin.openaiApiKeyPath should not be an empty string."; 68 + } 69 + ]; 70 + 71 + systemd.services.chatgpt-retrieval-plugin = { 72 + description = "ChatGPT Retrieval Plugin"; 73 + after = [ "network.target" ]; 74 + wantedBy = [ "multi-user.target" ]; 75 + 76 + serviceConfig = { 77 + DynamicUser = true; 78 + Restart = "always"; 79 + LoadCredential = [ 80 + "BEARER_TOKEN:${cfg.bearerTokenPath}" 81 + "OPENAI_API_KEY:${cfg.openaiApiKeyPath}" 82 + ]; 83 + StateDirectory = "chatgpt-retrieval-plugin"; 84 + StateDirectoryMode = "0755"; 85 + }; 86 + 87 + # it doesn't make sense to pass secrets as env vars, this is a hack until 88 + # upstream has proper secret management. 89 + script = '' 90 + export BEARER_TOKEN=$(${pkgs.systemd}/bin/systemd-creds cat BEARER_TOKEN) 91 + export OPENAI_API_KEY=$(${pkgs.systemd}/bin/systemd-creds cat OPENAI_API_KEY) 92 + exec ${pkgs.chatgpt-retrieval-plugin}/bin/start --host ${cfg.host} --port ${toString cfg.port} 93 + ''; 94 + 95 + environment = { 96 + DATASTORE = cfg.datastore; 97 + QDRANT_COLLECTION = mkIf (cfg.datastore == "qdrant") cfg.qdrantCollection; 98 + }; 99 + }; 100 + 101 + systemd.tmpfiles.rules = [ 102 + # create the directory for static files for fastapi 103 + "C /var/lib/chatgpt-retrieval-plugin/.well-known - - - - ${pkgs.chatgpt-retrieval-plugin}/${pkgs.python3Packages.python.sitePackages}/.well-known" 104 + ]; 105 + }; 106 + }
+10 -2
pkgs/servers/chatgpt-retrieval-plugin/default.nix
··· 3 3 , fetchFromGitHub 4 4 , python3 5 5 , nix-update-script 6 + , dasel 6 7 }: 7 8 8 9 python3Packages.buildPythonApplication { ··· 22 23 substituteInPlace pyproject.toml \ 23 24 --replace 'python-dotenv = "^0.21.1"' 'python-dotenv = "*"' \ 24 25 --replace 'python-multipart = "^0.0.6"' 'python-multipart = "^0.0.5"' \ 25 - --replace 'tiktoken = "^0.2.0"' 'tiktoken = "^0.3.0"' 26 + --replace 'tiktoken = "^0.2.0"' 'tiktoken = "^0.3.0"' \ 27 + --replace 'packages = [{include = "server"}]' 'packages = [{include = "server"}, {include = "models"}, {include = "datastore"}, {include = "services"}]' 28 + 29 + substituteInPlace server/main.py \ 30 + --replace 'directory=".well-known"' 'directory="/var/lib/chatgpt-retrieval-plugin/.well-known"' \ 31 + --replace '0.0.0.0' '127.0.0.1' \ 32 + --replace '8000' '8080' 33 + 34 + ${dasel}/bin/dasel put -t string -f pyproject.toml -v '.well-known/*' '.tool.poetry.include.[]' 26 35 ''; 27 36 28 37 nativeBuildInputs = with python3Packages; [ 29 38 poetry-core 30 39 ]; 31 - 32 40 33 41 propagatedBuildInputs = with python3.pkgs; [ 34 42 fastapi