# OpnForm: an AGPLv3 form builder you can self-host with Docker

> OpnForm is a Laravel and Nuxt form builder that ships a managed cloud and a self-hosted Docker path. The interesting part is not the builder UI, it is how the project splits its licence and what the self-hosted compose stack actually asks of you.

**OpnForm/OpnForm** — Beautiful Open-Source Form Builder

- Repository: https://github.com/OpnForm/OpnForm
- Website: https://opnform.com
- Stars: 3,757 · Forks: 546
- Language: PHP
- License: NOASSERTION
- Published: 2026-09-23 · Updated: 2026-09-23 · Language: en
- Canonical page: https://hysenlabs.com/projects/opnform-opnform

## What OpnForm is for, and who ends up running it

OpnForm is a form builder: you assemble a form from input types such as text, date, URL and file uploads, embed it, and collect submissions. The README lists no-code building with unlimited forms and submissions, form logic, captcha protection, email notifications, analytics, and integrations with Slack, Webhooks and Discord. That is a familiar feature set. The decision that matters is not which input types exist, it is where the data and the runtime live.

The README is explicit that the easiest path is the managed cloud service, which comes with support, backups and upgrades. Self-hosting is documented separately, through the deployment guides at docs.opnform.com. So OpnForm is aimed at two different readers at once: someone who wants a hosted form tool and never wants to see a container, and someone who wants the whole stack on their own infrastructure. The repository is built for the second reader, but the README leads with the first. That ordering is honest about where the project's revenue comes from, and it also means the self-hosting documentation is the part you have to read carefully before you commit.

## The architecture: Laravel API, Nuxt client, and a queue you have to run

The repository splits into api/ and client/, with PHP as the primary language and Laravel and Nuxt listed as topics. The API is the application: it owns forms, submissions, notifications and integrations. The client is the builder and the public form renderer.

What the compose file reveals is that the API is not a single process. There are three services sharing the same image and environment: api, which serves requests; api-worker, which runs php artisan queue:work; and api-scheduler, which runs php artisan schedule:work. Each has its own healthcheck. The worker is checked by looking for a running queue:work process, and the scheduler is checked by running php artisan app:scheduler-status --mode=check --max-minutes=3. If you deploy the API container alone, forms may still render, but anything that depends on queued jobs or scheduled tasks will not happen. That is the single most common way a self-hosted form tool quietly stops working: the web container is healthy, the worker is dead, and nobody notices until notifications go missing.

The stack also expects PostgreSQL and Redis, declared as db and redis services with health conditions, and the compose file defaults DB_CONNECTION to pgsql. The API image is jhumanj/opnform-api:latest and it mounts a named volume at /usr/share/nginx/html/storage, so uploads and generated files persist outside the container. PHP limits are set in the environment: a 1G memory limit, a 600 second max execution time, and 64M for upload and post sizes. Those numbers are the project's own defaults, not suggestions you can ignore if you accept large file uploads.

## Installing OpnForm with Docker Compose and getting a first form

The README points self-hosters at the deployment guides rather than giving a one-line install. The repository does ship a docker-compose.yml at the top level, and that is the concrete starting point. The compose file reads environment variables from ./api/.env via env_file, so that file has to exist before the stack will start in a useful state.

Start by cloning the repository and creating the environment file the compose stack expects:

```bash
git clone https://github.com/OpnForm/OpnForm.git
cd OpnForm
cp api/.env.example api/.env
```

The compose file references ./api/.env directly, so the copy is what makes DB_DATABASE, DB_USERNAME and DB_PASSWORD resolvable. Those three default to forge in the compose environment block, and DB_CONNECTION defaults to pgsql.

Then bring the stack up. This starts the API, the queue worker and the scheduler together, which is what you want in a self-hosted install:

```bash
docker compose up -d
docker compose ps
```

The second command is the one to actually read. The api healthcheck runs php artisan about, the worker healthcheck looks for a queue:work process, and the scheduler healthcheck runs app:scheduler-status. A container that is up but unhealthy is the failure mode to watch for, not a container that is down.

For local development the README points to a separate Docker development guide, and the repository carries docker-compose.dev.yml and docker-compose.e2e.yml alongside the production file. If you are evaluating OpnForm rather than deploying it, the development compose file is the safer place to start, because it does not assume production credentials. The README does not document a rollback procedure for a failed upgrade, so plan your database backups before you pull a new image tag.

## Where the documentation is thin, and where OpnForm is the wrong tool

The README is a landing page, not an operations manual. It states that self-hosted deployment is covered by the deployment guides and that local development has its own Docker guide, but the README itself gives no migration steps, no upgrade path and no rollback instructions. The compose file pins the API image to latest. Running latest in production means an unattended pull can change your application between restarts, and nothing in the repository describes how to go back.

There is a second boundary that is easy to miss. The README describes a dual-licence model: the core is AGPLv3, and advanced features under api/app/Enterprise/ are proprietary, governed by a separate Enterprise License and Enterprise Terms. If you self-host the core and never touch those directories, you are running AGPLv3 code. If a feature you need lives under api/app/Enterprise/, the AGPLv3 grant does not cover it. The README does not enumerate which features are in that directory, so you have to check the tree yourself before you promise a capability to anyone.

OpnForm is also the wrong tool if your organisation cannot accept AGPLv3 at all. The licence reaches users who interact with the software over a network, which is exactly the situation for a hosted form. If you are embedding a form builder inside a closed-source product and cannot meet those obligations, this is not a licensing problem you can configure away. And if you want a form tool with no server, no database and no queue worker, the self-hosted path is more infrastructure than the job requires.

## OpnForm compared with Formbricks

Formbricks is the comparison people search for, and the difference is in what the tool is for. OpnForm is a general form builder: you design a form, embed it, and route submissions through email notifications, webhooks, Slack or Discord. The README frames it around forms and submissions, with analytics on top.

Formbricks is positioned around survey and experience management, where the unit of work is a campaign shown to a user at a moment you choose, with targeting and follow-up logic. If your requirement is a contact form, a registration form or an intake form that writes to a webhook, OpnForm's model is the direct fit. If your requirement is measuring sentiment across a user base and acting on the results, a survey platform is built around that question in a way a form builder is not. Both are open source and both can be self-hosted, so the licence and hosting questions are similar; the difference that actually decides the choice is forms versus surveys, not the deployment story.

OpnForm's own repository also carries an MCP server, described in the README as letting AI agents create and preview a private form draft without a login, with OAuth adding workspace-aware management and read-only submission search, statistics and exports. The installable plugin package lives in plugins/opnform/. That is a differentiator against form builders that have no agent-facing interface at all, and it is worth checking the MCP integration guide before assuming it covers your use case.

## Maintenance, upgrades and what the AGPLv3 core means for you

The repository is not archived, and the last push was on 2026-09-22. Releases are frequent: v2.5.0 on 2026-09-02, v2.4.0 on 2026-08-20, and v2.3.0 on 2026-08-11. A project shipping three minor releases in a month is moving, and that cuts both ways. You get fixes quickly. You also get schema and API changes quickly, and the README does not describe a supported upgrade procedure for self-hosted installs.

The compose file gives one hint about upgrade cost. The API image tag is latest, and migrations run through Laravel. The README notes that the form statistics index migration runs outside a transaction and uses CREATE INDEX CONCURRENTLY on PostgreSQL, that it recovers an invalid index left by an interrupted build, and that it must be run through Laravel normally rather than wrapped in an external transaction. On a large form_statistics table, that migration will take time and will leave an invalid index behind if it is interrupted. Budget for it rather than treating an upgrade as a container restart.

On licensing, the core is AGPLv3 or any later version, and the Enterprise features under api/app/Enterprise/ are under a proprietary Enterprise License and Enterprise Terms. The README states the dual-licence model exists to fund development. What that means in practice is that the free part is genuinely free and the paid part is not open source. Whether AGPLv3 fits your distribution model is a question for your own legal review; the repository does not answer it for you.

## Conclusion

Adopt OpnForm if you want a form builder you can run on your own PostgreSQL and Redis, and if AGPLv3 obligations are acceptable for your deployment. Do not adopt it if you need a permissive licence for a closed product, or if you expect the README alone to be enough to operate it. Before committing, read the cloud-vs-self-hosting page, confirm which features live under api/app/Enterprise/, and run the compose stack with your own ./api/.env to see what the api, api-worker and api-scheduler containers report in their healthchecks.

## FAQ

### Can I self-host OpnForm instead of using the cloud service?

Yes. The README points self-hosted installations to the deployment guides at docs.opnform.com/deployment, and the repository ships a top-level docker-compose.yml with api, api-worker and api-scheduler services. The README frames the managed cloud as the easiest way to get started, with support, backups and upgrades included.

### How do I install OpnForm with Docker?

The compose file reads ./api/.env via env_file, so create that file first, then run docker compose up -d and check the result with docker compose ps. The API image is jhumanj/opnform-api:latest and the stack expects PostgreSQL and Redis services alongside it.

### Is OpnForm open source?

The core is open source under the GNU Affero General Public License Version 3 or any later version. Advanced features under api/app/Enterprise/ are proprietary, covered by a separate Enterprise License and Enterprise Terms.

### Does OpnForm have an API?

The repository is split into api/ and client/, with PHP as the primary language and Laravel as a topic. The compose file defines the API image and environment, and the README describes a remote MCP server with OAuth for workspace-aware form management and read-only submission search, statistics and exports.

### Can I embed an OpnForm form on my own site?

The README lists embed anywhere as a key feature, and the client build checks the public form bundle size and eager dependencies by reading .nuxt/dist/client/_nuxt. The README does not give a specific embed snippet, so the embed instructions themselves are in the technical documentation.

## Sources

- [Issues](https://github.com/OpnForm/OpnForm/issues)
- [OpnForm/OpnForm on GitHub](https://github.com/OpnForm/OpnForm)
- [Project website](https://opnform.com)
- [README](https://github.com/OpnForm/OpnForm/blob/main/README.md)
- [Releases](https://github.com/OpnForm/OpnForm/releases)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/opnform-opnform
