Build future-proof AI apps

The config-first web stack for
AI and humans

Build apps that AI can generate, humans can review, and teams can maintain. Config that works between code and natural language.

$npx lowdefy@latest dev
2.6k+stars
4years open source
3K+weekly npm downloads
lowdefy.yaml
lowdefy: '4.5.2' pages:  - id: welcome  type: PageHeaderMenu  blocks:  - id: card  type: Card  blocks:  - id: name  type: TextInput  properties:  label: What's your name?  - id: greeting  type: Alert  properties:  type: success  message:  _js: |  const n = state('name');  return n ? `Hello, ${n}!` : 'Type your name';  - id: submit  type: Button  properties:  title: Save  events:  onClick:  - id: validate  type: Validate

Powering enterprise apps in production

AvisLexusBarloworldCourierITFlavaRTT

AI writes code fast but the maintenance doesn't scale

Vibe-coding produces working prototypes. But production needs maintainability, security, and consistency.

AI generates 5000 lines of code that you can't review

Every prompt produces a wall of code. No one has time to audit it all, so bugs and vulnerabilities slip through.

Every AI session creates new standards, destroying quality

There's no consistency between sessions. Each generation is a unique snowflake of dependencies and patterns.

Security vulnerabilities are often an afterthought

SQL injection, XSS, broken auth. LLMs don't audit their output. Neither do most teams.

Dependency updates break everything, across every project

When Next.js ships a breaking change, you have to fix every AI-generated codebase individually.

The Solution

Config-first: the abstraction layer AI needs

A declarative config that sits between JavaScript and natural language. Constrained enough for guarantees, expressive enough for real apps.

50 lines of config vs 500 lines of code

Declarative YAML replaces thousands of lines of boilerplate. Review entire apps at a glance.

Schema-validated. No arbitrary code paths

Every config property is validated against a schema. No room for hidden logic or unexpected behavior.

One framework update upgrades all your apps

Config is stable. Update Lowdefy once, and every app benefits. No migration scripts needed.

Config is interpreted, not executed. Secure by design

No code injection possible. Auth, permissions, and data validation are built into the runtime.

Code generators vs Lowdefy

Lovable, v0, and other code generators produce raw React. Lowdefy produces reviewable, schema-validated config.

Code Generators
~150
import { useState, useEffect } from 'react'; import { useQuery, useMutation } from '@tanstack/react-query'; import { Table, Card, Button, Modal, Form, Input, Select, message, Popconfirm, Space, Tag } from 'antd'; import { EditOutlined, DeleteOutlined, PlusOutlined } from '@ant-design/icons'; interface User { id: string; name: string; email: string; role: 'admin' | 'user' | 'editor'; status: 'active' | 'inactive'; createdAt: Date; } const fetchUsers = async (): Promise<User[]> => { const res = await fetch('/api/users'); if (!res.ok) throw new Error('Failed to fetch users'); return res.json(); }; const updateUser = async (user: Partial<User> & { id: string }) => { const res = await fetch(`/api/users/${user.id}`, { method: 'PUT', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(user), }); if (!res.ok) throw new Error('Failed to update user'); return res.json(); }; const deleteUser = async (id: string) => { const res = await fetch(`/api/users/${id}`, { method: 'DELETE' }); if (!res.ok) throw new Error('Failed to delete user'); }; const createUser = async (user: Omit<User, 'id' | 'createdAt'>) => { const res = await fetch('/api/users', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(user), }); if (!res.ok) throw new Error('Failed to create user'); return res.json(); }; export function UserDashboard() { const [isModalOpen, setIsModalOpen] = useState(false); const [editingUser, setEditingUser] = useState<User | null>(null); const [form] = Form.useForm(); const { data: users, isLoading, error, refetch } = useQuery({ queryKey: ['users'], queryFn: fetchUsers, }); const updateMutation = useMutation({ mutationFn: updateUser, onSuccess: () => { message.success('User updated successfully'); refetch(); handleCloseModal(); }, onError: () => message.error('Failed to update user'), }); const deleteMutation = useMutation({ mutationFn: deleteUser, onSuccess: () => { message.success('User deleted successfully'); refetch(); }, onError: () => message.error('Failed to delete user'), }); const createMutation = useMutation({ mutationFn: createUser, onSuccess: () => { message.success('User created successfully'); refetch(); handleCloseModal(); }, onError: () => message.error('Failed to create user'), }); const handleEdit = (user: User) => { setEditingUser(user); form.setFieldsValue(user); setIsModalOpen(true); }; const handleCloseModal = () => { setIsModalOpen(false); setEditingUser(null); form.resetFields(); }; const handleSubmit = async (values: Partial<User>) => { if (editingUser) { await updateMutation.mutateAsync({ ...values, id: editingUser.id }); } else { await createMutation.mutateAsync(values as Omit<User, 'id' | 'createdAt'>); } }; if (error) return <div>Error loading users</div>; const columns = [ { title: 'Name', dataIndex: 'name', key: 'name', sorter: true }, { title: 'Email', dataIndex: 'email', key: 'email' }, { title: 'Role', dataIndex: 'role', key: 'role', render: (role: string) => ( <Tag color={role === 'admin' ? 'red' : role === 'editor' ? 'blue' : 'default'}> {role.toUpperCase()} </Tag> ), }, { title: 'Status', dataIndex: 'status', key: 'status', render: (status: string) => ( <Tag color={status === 'active' ? 'green' : 'default'}>{status}</Tag> ), }, { title: 'Actions', key: 'actions', render: (_: unknown, record: User) => ( <Space> <Button icon={<EditOutlined />} onClick={() => handleEdit(record)} /> <Popconfirm title="Delete user?" onConfirm={() => deleteMutation.mutate(record.id)}> <Button icon={<DeleteOutlined />} danger /> </Popconfirm> </Space> ), }, ]; return ( <Card title="User Management" extra={ <Button type="primary" icon={<PlusOutlined />} onClick={() => setIsModalOpen(true)}> Add User </Button> } > <Table columns={columns} dataSource={users} loading={isLoading} rowKey="id" /> <Modal title={editingUser ? 'Edit User' : 'Create User'} open={isModalOpen} onCancel={handleCloseModal} onOk={() => form.submit()} confirmLoading={updateMutation.isPending || createMutation.isPending} > <Form form={form} layout="vertical" onFinish={handleSubmit}> <Form.Item name="name" label="Name" rules={[{ required: true }]}> <Input /> </Form.Item> <Form.Item name="email" label="Email" rules={[{ required: true, type: 'email' }]}> <Input /> </Form.Item> <Form.Item name="role" label="Role" rules={[{ required: true }]}> <Select options={[ { value: 'admin', label: 'Admin' }, { value: 'editor', label: 'Editor' }, { value: 'user', label: 'User' }, ]} /> </Form.Item> <Form.Item name="status" label="Status" rules={[{ required: true }]}> <Select options={[ { value: 'active', label: 'Active' }, { value: 'inactive', label: 'Inactive' }, ]} /> </Form.Item> </Form> </Modal> </Card> ); }
  • • Hard to review - need to understand React patterns
  • • Security depends on implementation quality
  • • Every change can introduce bugs
  • • Dependency on specific package versions
Lowdefy Config
~25
id: user_dashboard type: PageHeaderMenu  requests:  - id: get_users  type: MongoDBFind  connectionId: users  blocks:  - id: users_card  type: Card  properties:  title: User Management  blocks:  - id: users_table  type: AgGridAlpine  properties:  rowData:  _request: get_users  columnDefs:  - field: name  - field: email  - field: role 
  • • Scan and review in seconds
  • • Schema-validated, secure by default
  • • Framework handles all the complexity
  • • Upgrade framework without changing config

Full-stack, production-ready

Everything you need to build, connect, and deploy data-driven business apps.

Build

Internal Tools & Admin Panels
Customer Portals
Multi-step Forms & Intake
BI Dashboards & Reporting
Approval Workflows
Inventory & Asset Management

Too many apps?

Most teams run 10+ business apps that don't talk to each other. Resonancy builds one purpose-built solution that replaces them all, built on Lowdefy, delivered in weeks.

Sound familiar?

  • Teams losing time to clunky or disconnected systems
  • Key workflow dependencies limit business growth
  • Lost revenue because of mismanaged data
  • Falling behind competitors with more efficient operations

Consolidate Your Stack

Replace 10+ disconnected apps with one purpose-built solution.

Streamline Workflows

Seamlessly integrated systems that free up your team.

Ship in Weeks

Custom apps built fast with Lowdefy, not months.

Connect Everything

Real-time data across your business for reliable insights.

Talk to Resonancy
Services byResonancy
10+
Years building business apps
50+
Internal tools deployed

Built on open source

We build on Lowdefy, our own open source stack. Quick starter modules get you live fast, then we customize for your exact workflows.

What we deliver:

  • One unified app replacing your SaaS dependency
  • A custom solution tailored to your business
  • AI, data science & integrations included
  • Ongoing support & managed hosting

“When people, processes, and technology resonate together, magic happens.”

Gerrie van Wyk
Gerrie van Wyk
Co-founder, Resonancy & Lowdefy

Loved by developers

Teams around the world are building faster with Lowdefy.

“Lowdefy has allowed me to quickly test new product ideas without having to write any code. I have even recreated older PHP tools which are now easier to maintain and update.”

Jon Bennetts
Jon Bennetts
86-88 Solutions

“As a project manager with limited coding knowledge, I've been able to create various financial tracking and academic documentation apps effortlessly. The best part is the supportive community.”

Mahdy Arief
Mahdy Arief
Product Manager at Feedloop

“Lowdefy is the ideal solution for anyone looking to build a web application. Its simplicity allowed me to create a functional CRUD app in just a few hours.”

Ehan Groenewald
Ehan Groenewald
Data Scientist

Ready to build faster?

Get started with Lowdefy in minutes. No signup required, just run one command.

Open source • Apache 2.0