hoophq/hoop: a sidecar that filters what your agents do to databases
One gateway in front of every protocol. Same policy across MCP, LLMs, databases and containers. Wire-level enforcement at under 5ms.
At a glance
- What is it?
- hoop.dev's sidecar sits between an agent and a Postgres or MSSQL server, masking fields and refusing destructive statements at the wire. Here is how it installs, what the config controls, and where the documentation is still thin.
- Who is it for?
- Adopt hoophq/hoop if you already run an agent against a database and want a deny list and field masking that the agent cannot bypass by changing its prompt. Do not adopt it if you need a PAM, an MCP gateway, or a sandbox: the README states plainly that it is none of those, and the fleet features (token issuance, review queue, config push) are listed as not built.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository received new commits within the last day.
- What is it written in?
- Mainly Go, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 30, 2026, and from our analysis. They are not legal advice.
Editorial analysis
The problem: an agent with a live database connection and no referee
An agent that can run SQL will eventually run the wrong SQL. The README frames this as a speed problem rather than an intelligence problem: "An agent that drops a table is not smart. It is fast." Static rules cannot judge intent, and a human cannot review at machine speed, so the project's answer is to put another agent on the wire whose only job is to read each statement before it lands.
The target user is not the person building the agent. It is the person who has to let that agent touch a production database. The README is explicit that the agent never knows the sidecar exists: no SDK, no prompt changes, no agent-side config. You change one thing, the port in the connection string, and point it at 127.0.0.1:15432 instead of the database itself. That constraint shapes everything else about the design, including the fact that a refused statement comes back as a real pgwire error carrying the message you wrote in the config, so the agent reads why it was refused instead of guessing at a dropped connection.
How the sidecar inspects wire bytes instead of tool calls
The inspection core lives in sidecar/, described in the repository as "Wire bytes to statements, statements to verdicts." That ordering matters. Because the sidecar speaks the database protocol rather than a tool-calling interface, it sees the same bytes a client would send to Postgres or SQL Server, parses them into statements, and returns a verdict before the statement reaches the upstream.
Four controls sit on that path. Data Masking rewrites sensitive values in the response, in memory, before they reach the client; the README is careful to note that the request itself is never touched. Guardrails are an ordered deny list checked against every statement. The Session Analyzer scores each action's intent and syntax for risk before execution, and local rules run first, so a statement a guardrail already refuses never costs a model call. Reviews escalate risky operations to a human for one-off approval.
The protocol table in the README covers PostgreSQL, Microsoft SQL Server and HTTP. All three support masking and guardrails. The Session Analyzer runs on all three as well, but HTTP needs the http.capture_body setting, which is the one place where the HTTP path is visibly different from the database paths. Anything outside those three protocols is not covered by the table.
Installing hoop and standing up a first sidecar
The README gives a Homebrew tap as the install path. The tap is fetched from the hoophq/brew repository and the formula is simply named hoop.
brew tap hoophq/brew https://github.com/hoophq/brew.git
brew install hoopConfiguration is a single YAML file. The README's example enables email redaction and refuses destructive SQL. Note the admin block, which exposes /healthz, /stats, /config and /events on 127.0.0.1:19000, and the listeners block, which is where the port mapping happens: clients connect to listen, and upstream is your real resource.
log_level: info
admin:
listen: 127.0.0.1:19000
mask:
enabled: true
rules:
- {name: emails, entity: EMAIL_ADDRESS, strategy: redact}
policy:
enforce: true
rules:
- name: no-destructive-sql
type: operation
operations: [drop, delete, truncate]
listeners:
- name: localdb
protocol: postgres
listen: 127.0.0.1:15432
upstream: 127.0.0.1:5432
connection: localdbBefore starting it for real, the README documents a validate flag that checks the config and exits. Use it, because a malformed listener block fails at startup otherwise.
hoop start sidecar --config config.yaml --validate
hoop start sidecar --config config.yamlWhat you should see: with the sample config loaded, a query selecting an email column returns the value replaced by a redaction marker, and a DELETE returns a pgwire error reading "destructive statements are not permitted." The request for the SELECT is unchanged; only the response is rewritten.
The config example has a typo, and the control plane is half-built
Two things in the README deserve a direct warning. First, the sample config contains both a policy block and a guardails block (note the spelling) with the same rule name and a message field. The prose around the example says the file "redacts emails and refuses destructive SQL," but the example itself is inconsistent about which key carries the message. Treat the sample as illustrative, not copy-pasteable, and validate before you rely on it.
Second, the control plane's own status table is unusually honest and worth reading before you plan a rollout. Guardrails, Data Masking, Session Analyzer and Review rules are marked Built, with configuration living in the control plane. Slack for review delivery is Built. Administrators are Built. Sidecar fleet token issuance, resources and liveness are Not built. The review queue (approve, reject, retry) is Not built. Pushing configuration to the fleet is Not built, and the README states that each sidecar still reads its own file.
That last line is the real constraint. A fleet of sidecars today means a fleet of YAML files. The README also notes that routes with no backend behind them say so and name the work they wait on, rather than showing an empty table. That is a good sign for the UI, but it does not change the fact that central configuration distribution does not exist yet.
Where hoop is the wrong tool
The README spends a paragraph on what the project is not, and it is worth taking at face value. It is not a PAM: PAM decides who connects, and once a user is connected, PAM is done, whereas this controls what every statement does and what comes back. It is not an MCP gateway, because MCP gateways broker one interface while the sidecar sits on the wire underneath. It is not an agent sandbox, because sandboxes isolate the agent while the sidecar governs the connection between the agent and the resource. And it is not a platform you migrate to.
If your requirement is identity and access management for humans, or isolation of untrusted code, this project does not address it and does not claim to. The masking is response-side only, so it will not stop an agent from learning a schema, and it will not stop a read of a column you forgot to add a rule for. The guardrail is an operation deny list, which means anything not on the list passes. That is a deliberately narrow contract, and treating it as a general security boundary would be a misreading.
How this differs from Teleport and from MCP gateways
Teleport is the comparison people search for, and the README's own framing gives the cleanest distinction. Teleport is in the PAM family: it answers who may connect to a resource and issues short-lived credentials to that end. Once the session is open, the decision is over. hoop.dev answers a different question at a different layer: given that a connection exists, is this particular statement allowed, and what comes back to the caller.
The practical consequence is that the two are not substitutes. A Teleport deployment does not mask an email address in a result set, and hoop does not issue certificates or manage human identity. An MCP gateway is the other common comparison, and it is narrower in a different direction: it brokers tool calls over one interface, so anything your agent reaches without going through that interface is invisible to it. The sidecar's bet is that wire protocols outlive models, frameworks and MCP, so governing the connection covers the cases an MCP server never speaks. That bet is stated in the README as a design position, not demonstrated with a compatibility list beyond Postgres, MSSQL and HTTP.
Maintenance, licence and what a fleet actually costs you
The repository is not archived, and the last push was on 2026-09-10. Releases are frequent and granular: 1.163.0, 1.162.0 and 1.161.1 all landed on 2026-09-09, which suggests a rapid patch cadence rather than a slow release train. Frequent small releases are easier to bisect when something breaks, but they also mean you should pin a version rather than track main.
The licence is MIT, which permits commercial use and modification with minimal conditions; the repository carries a LICENSE file and a CLA.md for contributions. That is a permissive arrangement, but nothing here is legal advice, and if you redistribute the binary you should read the licence text and the CLA yourself.
The upgrade cost is where the honest answer is less comfortable. Because each sidecar reads its own config file, an upgrade is per-instance work: pull the new binary, re-run hoop start sidecar --config config.yaml --validate, and only then restart. There is no documented rollback path in the README, and the control plane cannot push configuration to the fleet yet, so a bad rule change has to be reverted file by file. Plan for that before you run more than a handful of sidecars.
Editorial conclusion
Adopt hoophq/hoop if you already run an agent against a database and want a deny list and field masking that the agent cannot bypass by changing its prompt. Do not adopt it if you need a PAM, an MCP gateway, or a sandbox: the README states plainly that it is none of those, and the fleet features (token issuance, review queue, config push) are listed as not built. Before you commit, run hoop start sidecar --config config.yaml --validate against your real config, confirm which of postgres, mssql or http your client actually speaks, and read the control plane section to see which surfaces are still marked Not built.
Frequently asked questions
What is hoop.dev and what does it do?
It is an open-source sidecar that sits between an agent and a database or HTTP resource, masking sensitive fields in responses and refusing statements that match a configured deny list. The README describes it as runtime control for agents, distributed as one binary and one config file under the MIT licence.
How do I install hoophq/hoop?
The README gives a Homebrew tap: brew tap hoophq/brew https://github.com/hoophq/brew.git followed by brew install hoop. The repository also contains Dockerfiles and a hoophq/hoop image on Docker Hub.
Which protocols does hoop.dev support?
The README's protocol table lists PostgreSQL, Microsoft SQL Server and HTTP, with masking and guardrails available on all three. The Session Analyzer also runs on all three, and the HTTP path requires the http.capture_body setting.
Does hoop.dev replace Teleport?
No. The README positions it as not a PAM: PAM decides who connects, and once a user is connected PAM is done, while the sidecar controls what each statement does and what comes back. The two operate at different layers rather than substituting for one another.
Can I manage many sidecars from one place?
Partly. The README's control plane status table marks Guardrails, Data Masking, Session Analyzer, Review rules, Slack delivery and Administrators as Built, but lists sidecar fleet token issuance, liveness, the review queue and pushing configuration to the fleet as Not built. Each sidecar still reads its own config file.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/hoophq-hoop)