SSD Nodes Learn 8GB RAM — $66/jaar
Gidsen Matt ConnorDoor Matt Connor · Bijgewerkt 2026-08-02

Open Connector zelf hosten voor AI-agents

Draai de Open Connector-authgateway op uw eigen VPS. Gebruik een vastgezette image, TLS-origin, OAuth-callbacks en back-ups, zonder SaaS-token in uw agent.

Wat Open Connector doet voor een AI-agent

Met self-hosting van Open Connector plaatst u één authenticatiegateway tussen uw AI-agents en elke software-as-a-service (SaaS)-API die zij aanroepen. De agent bevat daardoor nooit een token van de provider. Het is een opensourcegateway van OOMOL Lab met de Apache 2.0-licentie. De gateway draait als één container, slaat de status op in één SQLite-bestand en stelt provideracties beschikbaar via HTTP en MCP (model context protocol).

Het probleem begint bij de tweede integratie. Elke provider heeft een eigen OAuth-flow (open authorization), een eigen levensduur voor refresh tokens en eigen scopenamen. Vijf providers handmatig in een agent integreren betekent vijf redirect-handlers, vijf credential-opslagen en vijf refresh-loops die moeten worden uitgevoerd voordat een token verloopt. Bijna niemand schrijft die code. In plaats daarvan maken zij per service één lang geldige persoonlijke access token aan en plakken die in de agentconfiguratie, een omgevingsbestand of de prompt zelf. Elke tool die de agent uitvoert, kan die token vervolgens lezen. De token komt ook in het transcript terecht. Dat is de fout die wordt beschreven in geheimen uit AI-agents houden.

Een authenticatiegateway splitst de credential in twee delen. De gateway slaat de credential van de provider op en voert de OAuth-flow uit. De agent krijgt een runtime-token die alleen geldig is voor de gateway. Wanneer de agent een actie aanroept, laadt de gateway de opgeslagen credential, voegt deze server-side toe aan het uitgaande verzoek en retourneert alleen de response body. De agent ontvangt de access token van de provider nooit. Als het agenttranscript uitlekt, kost dat u dus één intrekbare runtime-token in plaats van uw GitHub-account.

De catalogus vermeldt meer dan 1,000 providers en 10,000 vooraf gebouwde acties. Dat is het eigen cijfer van het project en niet iets wat u van buitenaf kunt verifiëren. Wat u wel kunt verifiëren, is de structuur: één HTTP-endpoint per actie, één opgeslagen verbinding per provider en één token per agent.

Waarom u Open Connector zelf host in plaats van een gehoste connectorservice te gebruiken

Een gehoste connectorservice doet hetzelfde werk en bewaart de refresh tokens voor elke provider die u eraan koppelt. Een refresh token voor Google of GitHub is een lang geldige cryptografische sleutel tot uw e-mail en repositories. Deze blijft meestal geldig nadat u uw wachtwoord hebt gewijzigd. Als die service wordt gehackt, wordt uw omgeving ook getroffen. Met self-hosting verplaatst u deze gegevens naar SQLite op een machine die u huurt en beheert. Ze worden daar beveiligd met een sleutel die uw server nooit verlaat.

Benoem de kosten voordat u begint. Deze VPS wordt de waardevolste server die u beheert. In één bestand staan werkende aanmeldgegevens voor een tiental services. Daarom moet u deze server behandelen als een host voor een wachtwoordbeheerder: een firewall die alleen 443 toegankelijk maakt, geen gedeelde aanmeldingen, een back-up die u daadwerkelijk eenmaal hebt teruggezet en een waarschuwing wanneer de server niet meer reageert. Als u uw wachtwoordkluis niet op deze server zou plaatsen, plaats de connector er dan ook niet op.

Zet een versie vast voordat u iets installeert

Open Connector is nieuw. De repository verscheen voor het eerst op 29 juni 2026. Op 1 augustus 2026 is de nieuwste release met tag v1.3.3, gepubliceerd op 30 juli 2026 en eveneens voorzien van de tag latest. De registry publiceert ook een tag tip, die is gebouwd vanaf de nieuwste commit op main.

Bij een project dat zo nieuw is, veranderen de bewegende tags vaak. Een docker compose pull die twee releases overslaat, kan een endpoint wijzigen waarvan uw agent afhankelijk is. U bent dan mogelijk de hele avond bezig om een agentprobleem te debuggen. Zet de image vast op een releasetag. Voer een upgrade uit wanneer u dat zelf besluit, nadat u de release notes hebt gelezen.

Open Connector achter TLS op uw eigen VPS implementeren

Voordat de container start, hebt u het volgende nodig:

  • Docker met de Compose-plugin, op Ubuntu 24.04 of een vergelijkbare distributie
  • een hostnaam waarvan het A-record naar deze VPS verwijst, bijvoorbeeld connect.example.com
  • een reverse proxy die TLS (transport layer security) voor deze hostnaam al beëindigt
  • twee willekeurige secrets, die u hieronder genereert

De handleiding Traefik reverse proxy voor meerdere Docker Compose-applicaties behandelt de proxyconfiguratie. Dezelfde certificaatconfiguratie, van begin tot eind voor één applicatie, staat in de handleiding n8n op een VPS met Docker en HTTPS.

Genereer eerst de secrets. De encryption key versleutelt de opgeslagen credentials. De admin token beschermt de webconsole en het volledige /api-oppervlak. Geen van beide heeft een standaardwaarde, en de runtime start zonder deze waarden probleemloos.

mkdir -p ~/open-connector && cd ~/open-connector
umask 077
printf 'OOMOL_CONNECT_ENCRYPTION_KEY=%s\n' "$(openssl rand -base64 32)" > .env
printf 'OOMOL_CONNECT_ADMIN_TOKEN=%s\n' "$(openssl rand -base64 32)" >> .env
chmod 600 .env

Kopieer beide waarden nu naar uw wachtwoordmanager, voordat u de applicatie voor het eerst start. Voor de encryption key bestaat geen herstelmethode. De reden daarvoor staat verderop in de lijst met fouten.

Maak nu compose.yaml. Dit verschilt op twee plaatsen van het upstream-voorbeeld. Beide verschillen zijn belangrijk.

services:
  connector:
    image: ghcr.io/oomol-lab/open-connector:v1.3.3
    restart: unless-stopped
    ports:
      - "127.0.0.1:3000:3000"
    volumes:
      - connector-data:/app/data
    environment:
      OOMOL_CONNECT_DATA_DIR: /app/data
      OOMOL_CONNECT_ORIGIN: "https://connect.example.com"
      OOMOL_CONNECT_ENCRYPTION_KEY: "${OOMOL_CONNECT_ENCRYPTION_KEY:?set this in .env}"
      OOMOL_CONNECT_ADMIN_TOKEN: "${OOMOL_CONNECT_ADMIN_TOKEN:?set this in .env}"

volumes:
  connector-data:

De eerste wijziging is de vastgezette tag in plaats van latest. De tweede wijziging is de poort. Het upstream-bestand publiceert 3000:3000, waardoor deze op elke interface van de host wordt gebonden. Docker schrijft de gepubliceerde poorten naar de NAT-tabel (network address translation) voordat het ufw-filterchain het pakket ziet. Daarom sluit ufw deny 3000 die poort niet. Dit is de valkuil die wordt beschreven in waarom Docker-poorten ufw omzeilen. Met 127.0.0.1:3000:3000 wordt de poort alleen op de loopback-interface gepubliceerd. Uw reverse proxy maakt dan vanaf dezelfde host verbinding.

:? markeert elke variabele als verplicht. Daardoor weigert de stack te starten wanneer .env ontbreekt, in plaats van te starten met onversleutelde credentials. Door de waarden in .env te bewaren, en niet in het Compose-bestand, volgt u het patroon uit env-bestanden en secrets voor Docker Compose.

docker compose up -d
docker compose logs -n 30 connector
curl -s http://127.0.0.1:3000/health
sudo ss -tlnp | grep 3000

/health geeft { "ok": true } terug zodra de runtime actief is. ss moet 127.0.0.1:3000 afdrukken. Een regel met 0.0.0.0:3000 betekent dat de poorttoewijzing nog steeds die van upstream is. De gateway beantwoordt dan rechtstreeks het volledige internet. Als de healthcheck de melding connection refused geeft, luistert de container nog niet. Lees dan eerst de logs voordat u de proxy aanpast.

Traefik-labels voor dezelfde service
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.connector.rule=Host(`connect.example.com`)"
      - "traefik.http.routers.connector.entrypoints=websecure"
      - "traefik.http.routers.connector.tls.certresolver=le"
      - "traefik.http.services.connector.loadbalancer.server.port=3000"

Wanneer Traefik op dezelfde host in Docker draait, koppelt u deze service aan het Traefik-netwerk en verwijdert u het blok ports:. Traefik bereikt de container dan via het interne netwerk en er hoeft helemaal geen poort naar de host te worden gepubliceerd. certresolver=le moet overeenkomen met de resolvernaam in uw statische Traefic-configuratie. Anders wordt de router gestart zonder certificaat.

Waarom OAuth een echte hostnaam vereist

OOMOL_CONNECT_ORIGIN is de instelling die mensen overslaan. Daardoor mislukt OAuth op een manier die op een fout bij de provider lijkt. De runtime bouwt de omleidings-URI op basis van die origin, in de vorm <origin>/oauth/callback. Als de origin niet is ingesteld, is de standaardwaarde http://localhost:3000. De runtime stuurt de provider dan een omleidings-URI van http://localhost:3000/oauth/callback, terwijl uw OAuth-app https://connect.example.com/oauth/callback heeft geregistreerd. De twee tekenreeksen verschillen. GitHub antwoordt dan:

The redirect_uri MUST match the registered callback URL for this application.

Een OAuth-provider leidt een browser terug naar die URI. Daarom moet dit een adres zijn dat vanaf internet bereikbaar is. Providers weigeren gewone http:// voor alles behalve localhost. Daarom heeft deze implementatie een hostnaam en een certificaat nodig. Stel de origin in voordat u de applicatie voor het eerst start. De waarde wordt bij het opstarten ingelezen. Voer na het aanpassen van .env of compose.yaml opnieuw docker compose up -d uit om de wijziging toe te passen.

Uw eerste provider via OAuth verbinden

Maak eerst de OAuth-app aan bij de provider. Op GitHub is het pad Settings, vervolgens Developer settings, vervolgens OAuth Apps en daarna New OAuth App. Stel de autorisatie-callback-URL in op https://connect.example.com/oauth/callback. Bewaar de client-ID en het clientgeheim.

Elke aanroep van /api bevat het beheertoken. Exporteer dit daarom eenmaal voor de shellsessie.

export ADMIN_TOKEN='paste-the-admin-token'
curl -s https://connect.example.com/api/oauth/configs \
  -H "authorization: Bearer $ADMIN_TOKEN"

In deze lijst ziet u de redirect-URI die de runtime voor elke provider verwacht. Daarmee controleert u het snelst of uw origin actief is. Als er nog steeds localhost staat, draait de container met de oude waarde. De OAuth-flow mislukt dan bij de laatste stap.

Sla de clientgegevens op en start vervolgens een autorisatie.

curl -s -X PUT https://connect.example.com/api/oauth/configs/github \
  -H "authorization: Bearer $ADMIN_TOKEN" \
  -H 'content-type: application/json' \
  -d '{"clientId":"...","clientSecret":"..."}'

curl -s -X POST https://connect.example.com/api/oauth/authorizations \
  -H "authorization: Bearer $ADMIN_TOKEN" \
  -H 'content-type: application/json' \
  -d '{"service":"github"}'

De tweede aanroep retourneert een authorizationUrl. Open deze in een browser, keur de scopes goed en de provider stuurt de browser terug naar /oauth/callback. Daar wisselt de runtime de code om en slaat deze de referentie op. De webconsole op uw origin doorloopt met een formulier dezelfde stappen achter hetzelfde beheertoken. Providers die een gewone API-sleutel gebruiken, slaan dit allemaal over: met {"authType":"api_key","values":{"apiKey":"..."}} slaat PUT /api/connections/<service> de sleutel rechtstreeks op.

Geef elke agent een runtimetoken, nooit de referentie

De agent verifieert zich bij de gateway met een runtimetoken dat de admin-API uitgeeft.

curl -s -X POST https://connect.example.com/api/runtime-tokens \
  -H "authorization: Bearer $ADMIN_TOKEN" \
  -H 'content-type: application/json' \
  -d '{"name":"research-agent"}'

De respons bevat een token dat begint met oct_. Geef elke agent één token en noem het naar die agent. Als u een token niet kunt identificeren, moet u anders alle tokens intrekken. De agent roept vervolgens acties aan via gewone HTTP.

curl -s -X POST https://connect.example.com/v1/actions/github.get_current_user \
  -H "authorization: Bearer oct_..." \
  -H 'content-type: application/json' \
  -d '{"input":{}}'

Een geldig antwoord is een envelop waarvan het veld success de waarde true heeft, met de payload van de provider onder data. Het GitHub-token staat nergens in die respons. Richt een MCP-client op https://connect.example.com/mcp met dezelfde bearer-header. De gateway biedt dan discover-tools zoals search_actions en execute_action in plaats van één tool per API. Daardoor blijft de toolslijst van de agent klein. MCP-servers uitvoeren op een VPS behandelt het clientgedeelte van deze configuratie.

Voer nog één controle uit voordat u dit als voltooid beschouwt. Herhaal de actieaanroep nadat u de header authorization hebt verwijderd. De eigen quickstart van het project roept /v1 aan zonder bearer. Een installatie zonder geconfigureerde runtime-authenticatie voert daarom acties uit voor iedereen die de poort kan bereiken. Als uw aanroep zonder authenticatie slaagt, hebt u twee opties: configureer runtimetokens en controleer of de anonieme aanroep nu mislukt, of beperk /api, /v1 en /mcp op de reverse proxy tot de adressen waarvandaan uw agents verbinding maken. Alleen /oauth/callback moet voor de buitenwereld toegankelijk blijven, omdat dit het enige pad is dat de browserredirect van een provider nodig heeft.

Beperk de actielijst tot wat de agent nodig heeft

Een gateway met duizend providers erachter biedt een groot aanvalsoppervlak voor een taalmodel. Met twee instellingen beperkt u dit.

OOMOL_CONNECT_ALLOWED_ACTIONS accepteert een kommagescheiden allowlist en ondersteunt service.* en *. OOMOL_CONNECT_BLOCKED_ACTIONS is de denylist en heeft voorrang. Als u de allowlist instelt op github.get_current_user,github.list_issues, wordt elke andere actie geweigerd, ongeacht wat de agent aanvraagt. Dat maakt het verschil tussen een fout en een incident. Runtime-tokens hebben naast de globale regels hun eigen actieregels. Hun lijst allowedProxies is leeg, dus POST /v1/proxy/:service wordt geweigerd totdat u deze actie toestaat. Dat proxy-eindpunt stuurt een onbewerkte aanvraag door naar een provider met uw referentie eraan gekoppeld. Laat deze lijst daarom leeg, tenzij één specifieke agent deze nodig heeft.

OOMOL_CONNECT_ALLOW_PRIVATE_NETWORK staat standaard op false. Hierdoor kan een verbinding met een zelfgehoste provider niet verwijzen naar een privéadres, zoals de cloudmetadataservice op 169.254.169.254 of uw database op hetzelfde netwerk. Laat deze instelling uitgeschakeld. Schakel deze alleen in voor een provider die u zelf host.

Maak een back-up van de box die elk token bevat

Twee zaken zijn belangrijk, en elk ervan is zonder het andere onbruikbaar. De database op /app/data/connect.sqlite in het volume connector-data bevat de verzegelde referenties. De encryptiesleutel in .env maakt deze vrij. Een back-up van het volume zonder de sleutel kan niets herstellen, en de sleutel zonder het volume kan niets herstellen. Daarom hoort de sleutel in uw password manager en hoort het volume in uw normale back-upschema.

Stop de container terwijl u het SQLite-bestand kopieert. Een kopie die tijdens een schrijfbewerking wordt gemaakt, kan als een beschadigde database worden hersteld.

docker volume ls | grep connector-data
docker compose stop connector
docker run --rm -v open-connector_connector-data:/data -v "$PWD":/backup alpine \
  tar czf /backup/connector-data.tgz -C /data .
docker compose start connector

De volumenaam bestaat uit uw projectdirectory plus _connector-data. Daarom staat het eerste commando daar: plak de werkelijke naam in het derde commando. Stuur het archief van de VPS met restic-back-ups vanaf een VPS. Dit versleutelt het archief voordat het de VPS verlaat, omdat dat archief de opslagplaats van de referenties is.

De runtime bewaart recente actieruns als auditrecords, standaard 5,000. Daardoor kan de console aangeven welke agent wat en wanneer heeft uitgevoerd. Dit logbestand is het eerste dat u moet lezen wanneer een agent zich vreemd gedraagt. Laat een Uptime Kuma-statuspagina ook https://connect.example.com/health controleren. Wanneer de gateway niet meer antwoordt, falen agents op verwarrende manieren. Als u weet dat de gateway niet beschikbaar is, bespaart u een uur waarin u agentuitvoer moet lezen.

Wat er misgaat en welke melding u ziet

redirect_uri_mismatch bij de provider. De origin en de geregistreerde callback-URL verschillen. Vergelijk de exacte tekenreeks uit /api/oauth/configs met de app-instellingen van de provider. Controleer ook https tegen http en let op een eventuele afsluitende slash.

Elke aanroep van /api retourneert 401. De header met het admin-token ontbreekt of bevat een typfout. De header is Authorization: Bearer <token>. De webconsole vraagt om hetzelfde token.

De container draait en de referenties staan als leesbare tekst opgeslagen. Dit gebeurt wanneer OOMOL_CONNECT_ENCRYPTION_KEY de container nooit bereikt. De runtime slaat de referentierecords dan onversleuteld op in plaats van het opstarten te weigeren. Controleer dit op uw eigen installatie. Verbind een provider met een API-key die u kunt herkennen en zoek deze vervolgens op in de database.

docker compose cp connector:/app/data/connect.sqlite /tmp/connect.sqlite
grep -c 'github_pat_' /tmp/connect.sqlite
shred -u /tmp/connect.sqlite

Een waarde hoger dan 0 betekent dat de key niet actief is. Controleer daarom of .env in dezelfde directory staat als compose.yaml en of docker compose config de waarde weergeeft. Nadat u de key hebt ingesteld, retourneert dezelfde zoekopdracht 0. De record is dan verzegeld met AES-256-GCM (advanced encryption standard, 256-bit key, Galois/counter mode).

Niets kan na een restore worden ontsleuteld. De encryption key is gewijzigd of verloren gegaan. Deze wordt bewust nooit naast de data opgeslagen. Er is daarom geen herstelprocedure en een supportticket biedt geen oplossing. Verbind elke provider opnieuw. Rotatie wordt ondersteund via een afzonderlijke key-variabele en een dataopdracht in de runtime. Lees daarom de actuele release notes voordat u iets roteert.

De agent geeft een foutmelding met de naam van een actie die in de catalogus zichtbaar is. Discovery en uitvoering zijn afzonderlijke stappen. Een actie kan in search_actions staan en toch worden geweigerd door OOMOL_CONNECT_ALLOWED_ACTIONS, door de denylist of door de eigen regels van het runtime-token.

Upgrades. Maak een back-up van het volume, wijzig de image-tag naar de nieuwe release en voer vervolgens docker compose pull && docker compose up -d uit. Controleer docker compose logs -n 50 connector op een migratieregel. Voer daarna de health check en één echte actie opnieuw uit voordat u de installatie weer vertrouwt. Rollback betekent dat u de oude tag terugplaatst. Dit werkt alleen omdat u de tag hebt vastgezet.

FAQ

Heb ik een openbaar domein nodig om Open Connector zelf te hosten?

Voor providers die een API key gebruiken, nee: een gateway op 127.0.0.1 is voldoende. Voor OAuth is het in de praktijk wel nodig. De provider verwijst een browser door naar uw callback-URL. Die URL moet daarom vanaf het openbare internet bereikbaar zijn. Providers weigeren gewone http:// buiten localhost. Stel OOMOL_CONNECT_ORIGIN vóór de eerste start in op uw https://-hostnaam en registreer <origin>/oauth/callback in de OAuth-app van de provider.

Wat gebeurt er als ik de encryptiesleutel van Open Connector verlies?

De opgeslagen referenties kunnen niet worden ontsleuteld. Er is geen herstelmogelijkheid. De sleutel wordt bewust nooit samen met de gegevens opgeslagen. Daarom kan niemand die de database in handen krijgt deze gegevens lezen, ook u niet. U kunt alleen een nieuwe sleutel instellen en elke provider opnieuw verbinden. Bewaar de sleutel in een wachtwoordbeheerder en neem de database op in uw back-uproulatie, omdat voor herstel beide nodig zijn.

Kan mijn AI-agent het toegangstoken van de provider zien?

Niet wanneer de agent via de gateway aanroept. De agent authenticeert zich met een runtime-token dat begint met oct_. De gateway voegt de referentie van de provider op de server toe aan het uitgaande verzoek en retourneert alleen het antwoord. Twee zaken doorbreken deze eigenschap: het /v1/proxy/:service-endpoint, dat onbewerkte verzoeken doorstuurt met uw referentie eraan toegevoegd en waarvan de rechten bewust leeg beginnen, en het zelf plakken van een API key in de agent, waarmee de gateway volledig wordt overgeslagen.

Moet de gateway bereikbaar zijn vanaf het openbare internet?

Alleen /oauth/callback moet dat zijn. Publiceer de containerpoort op 127.0.0.1, zodat de NAT-regels van Docker deze niet buiten uw firewall kunnen blootstellen, en plaats de reverse proxy ervoor. Test daarna één actieaanroep zonder de header authorization. Als die slaagt, beperkt u /api, /v1 en /mcp bij de proxy tot de adressen die uw agents gebruiken, totdat alleen geauthenticeerde aanroepen werken.

Is Open Connector klaar voor productiegebruik?

Het is gelicentieerd onder Apache 2.0 en ontwikkelt zich snel: de repository verscheen op 29 June 2026 en v1.3.3 is uitgebracht op 30 July 2026. Beschouw daarom elk versienummer in deze handleiding als een momentopname van 1 August 2026. Voer het uit met een vastgezette release-tag, nooit op latest of tip. Lees vóór elke upgrade de release notes en houd een volumeback-up bij die u eenmaal hebt teruggezet. Het ontwerp is geschikt voor een systeem dat u beheert. Het risico zit in de snelle versiewijzigingen, niet in de architectuur.