Gardener: Mini Framework

In an era of massive bundles and deep abstractions, Gardener offers a breath of fresh air. Built on the reliable foundations of Express and EJS, Gardener is a lightweight web framework designed for developers who want to build modern web applications without the overhead of React or heavy frontend runtimes.
🌿 What is Gardener?
Gardener is a "DOM-first" framework. It allows you to build sophisticated UIs using the web's native languages—plain HTML, CSS, and JavaScript—while providing the modularity of reusable components.
Why it exists
Modern frameworks often introduce significant complexity. Gardener focuses on:
- Minimal Runtime: No heavy virtual DOM overhead.
- Direct Control: You stay close to the actual DOM elements.
- Simplicity: Avoiding unnecessary layers of abstraction.
🏗️ How it Works: Architecture
Gardener follows a clean Request → Render → Enhance lifecycle:
- Express: Handles your routing and backend logic.
- EJS: Renders server-side templates into standard HTML.
- Frontend Library: Enhances the DOM with a component system, state handling, and developer tooling.
Component Types
- Static Components: EJS partials that are perfect for content-heavy sections.
- Dynamic Components: Reusable, parameterized components generated from DOM-to-COMPONENT logic.
💻 Code Example: Creating a Component
With Gardener, you don't have to manage complex state trees. You define your structure, and Gardener handles the element creation.
import { gardener } from '/static/gardener.js';
export function myComponent(name) {
return gardener({
"t": "div",
"cn": ["flex", "justify-center", "items-center", "target"],
"children": [
{
"t": "span",
"cn": ["text-xl", "font-bold"],
"txt": `Hello ${name}`
},
{
"t": "button",
"txt": "click",
"events": {
"click": "() => console.log('button clicked')"
}
}
]
});
}
Pro Tip: You don't need to write this JSON manually! Write your standard HTML, select the element, and run the Gardener Parser to generate your reusable component automatically.
<script type="module">
import { parser } from '/static/gardener.js';
parser('.target');
//A popup appears on brow
Reusing Components
Integrating components into your pages is straightforward:
<script type="module">
import { fetchElement, appendElement, replaceElement } from '/static/gardener.js';
// Option 1: Append to a target
appendElement(fetchElement('.target'), myComponent('Gardener'));
// Option 2: Replace a target entirely (internal fetch)
replaceElement('.target', myComponent('Gardener'));
</script>
🚀 Key Features
| Feature | Description |
|---|---|
| Ultra Lightweight | Bundled with esbuild for maximum performance. |
| No Dependencies | Zero frontend framework dependencies; just pure JS. |
| Image Optimization | Powered by Sharp with automatic caching (.webp). |
| Hot Reloading | Instant feedback with backend file watching and frontend polling. |
| Static Support | Support for static builds and one-click page creation. |
🛠️ Tech Stack & Setup
Gardener leverages a robust, battle-tested stack:
- TypeScript for type safety.
- Express & EJS for the server and templating.
- esbuild for lightning-fast bundling.
- Sharp for high-performance image processing.
Getting Started
Ready to plant your first project? Run the following command in your terminal:
npm create gardener app
🎯 Positioning
Gardener isn't trying to be React. It’s designed for:
- Control Freaks: Developers who prefer granular control over abstraction.
- Performance Junkies: Building lightweight applications with minimal footprint.
- Learners: Anyone wanting to understand how frameworks actually work under the hood.


