Citizen-developer app builder for Nextcloud — compose apps from registers, connectors, workflows, and documents without code.
OpenBuilt is a citizen-developer app builder for Nextcloud. It lets non-technical users compose apps from the Conduction ecosystem (OpenRegister schemas, OpenConnector APIs, Procest workflows, Docudesk documents, NL Design themes, MyDash dashboards) through a visual interface, without scaffolding PHP for each new app.
Per ADR-024 each built app is rendered at runtime by mounting CnAppRoot with the app's manifest, which lives as a JSON blob in OpenBuilt's own OpenRegister namespace. Per ADR-031 behaviour (state machines, aggregations, calculations, notifications) is declared as schema metadata in the register file instead of service code. Built apps are virtual at first (records in OpenBuilt's register, rendered inside the OpenBuilt shell at /apps/openbuilt/builder/{slug}); a Phase-2 export generates a real Nextcloud app from a virtual app.
Requires OpenRegister — all virtual-app data is stored as OpenRegister objects.
Add screenshots here once the shell + textarea editor + seeded hello-world virtual app are merged.
Features are defined in openspec/specs/ and tracked via the 9-spec chain that starts with bootstrap-openbuilt.
Application+BuiltAppRouteOR schemas with declarativedraft → published → archivedlifecycle (canonical ADR-031 example — no service class)- Manifest endpoint —
GET /index.php/apps/openbuilt/api/applications/{slug}/manifestreturns the stored manifest blob - Nested-
CnAppRootruntime —/builder/{slug}/*mounts a virtual app inside the OpenBuilt shell; path segments after the slug forward to the inner manifest's router - Textarea manifest editor — JSON-only for v1 (visual editor lives in chain spec #5)
- Seeded
hello-worldApplication exercisingindex,detail, andformpage types out of the box
nextcloud-vue-in-memory-manifest(innextcloud-vue/) —useAppManifestoverload accepting an in-memory manifest objectopenregister-runtime-schema-api(inopenregister/) — runtime schema-creation APIopenbuilt-schema-editor— visual schema designeropenbuilt-page-editor— visual manifest/page designeropenbuilt-versioning— draft / publish / rollbackopenbuilt-rbac— per-built-app permissionsopenbuilt-templates-marketplace— starter templatesopenbuilt-export-to-real-app— Phase-2 export to a real Nextcloud app
graph TD
A[OpenBuilt shell - Vue 2 / Pinia] -->|nested mount| B[CnAppRoot per virtual app]
A -->|CRUD via OR REST| C[OpenRegister API]
B -->|GET manifest| D[ApplicationsController]
D --> C
C --> E[(PostgreSQL JSON store)]
A --> F[Nextcloud Activity + Search]
| Schema | Description |
|---|---|
Application |
One row per virtual app. Holds slug, name, description, manifest (JSON blob), version, status (draft / published / archived). Declarative lifecycle via x-openregister-lifecycle. |
BuiltAppRoute |
Slug → applicationUuid index for fast runtime lookup; upkept by the Application lifecycle. |
hello-message |
Seed schema for the canonical hello-world virtual app (three sample objects). |
Data model is fully defined in lib/Settings/openbuilt_register.json. See openspec/changes/bootstrap-openbuilt/ for the foundational spec.
| Dependency | Version |
|---|---|
| Nextcloud | 28 – 33 |
| PHP | 8.1+ |
| Node.js | 20+ |
| OpenRegister | latest |
| @conduction/nextcloud-vue | latest |
- Go to Apps in your Nextcloud instance
- Search for OpenBuilt
- Click Download and enable
OpenRegister must be installed first. Install OpenRegister →
cd /var/www/html/custom_apps
git clone https://github.com/ConductionNL/openbuilt.git openbuilt
cd openbuilt
npm install && npm run build
php occ app:enable openbuiltnpm install
npm run dev # Watch mode
npm run build # Production build# PHP
composer check:strict # PHPCS + PHPMD + Psalm + PHPStan + tests
composer cs:fix # Auto-fix PHPCS
composer phpmd # Mess detection
# Frontend
npm run lint # ESLint
npm run stylelint # CSS lintingNote: The
js/build output is not committed. Build the frontend before enabling the app or the UI will be blank.
| Layer | Technology |
|---|---|
| Frontend | Vue 2.7, Pinia, @conduction/nextcloud-vue (CnAppRoot, CnPageRenderer, useAppManifest) |
| Build | Webpack 5, @nextcloud/webpack-vue-config |
| Backend | PHP 8.1+, Nextcloud App Framework (single controller method: manifest endpoint) |
| Data | OpenRegister (PostgreSQL JSON objects + x-openregister-lifecycle declarative state machines) |
| Quality | PHPCS, PHPMD, Psalm, PHPStan, ESLint, Stylelint |
| Branch | Purpose |
|---|---|
main |
Stable releases — triggers release workflow |
beta |
Beta / pre-release builds |
development |
Active development — merge target for feature branches |
| Resource | Description |
|---|---|
openspec/app-config.json |
App identity, dependencies, CI configuration |
openspec/changes/bootstrap-openbuilt/ |
Foundational spec (proposal, specs, design, tasks) |
openspec/specs/ |
Feature specs |
openspec/architecture/ |
App-specific Architectural Decision Records |
- Accessibility: WCAG AA (NL Design System guarantees, ADR-010)
- Authorization: RBAC via OpenRegister (ADR-022) — no app-local RBAC duplication
- Audit trail: Full lifecycle audit on every Application transition via OR's audit trail
- Localization: English and Dutch (ADR-007)
- OpenRegister — Object storage layer (required dependency)
- OpenConnector — API / iPaaS integration (consumed by built apps via manifest)
- Procest — Process / case management (consumed via workflow attachments)
- Docudesk — Document generation (consumed via template attachments)
- MyDash — Dashboards (consumed via widget embeds)
- NL Design — Government theming (CSS variable inheritance)
For support, contact support@conduction.nl.
For a Service Level Agreement (SLA), contact sales@conduction.nl.
This project is licensed under the EUPL-1.2.
Built by Conduction — open-source software for Dutch government and public sector organizations.