lengthofrope / treehouse
TreeHouse - Modern PHP Framework with Zero Dependencies
Requires
- php: ^8.4
- ext-fileinfo: *
- ext-filter: *
- ext-json: *
- ext-mbstring: *
- ext-openssl: *
- ext-pdo: *
Requires (Dev)
- phpunit/phpunit: ^11.0
This package is auto-updated.
Last update: 2025-06-28 20:21:19 UTC
README
A modern, lightweight PHP framework built from scratch with zero external dependencies.
WORK IN PROGRESS
Please note that this framework is in WIP state. It is nowhere near production ready.
Features
- Zero Dependencies: Pure PHP implementation with no external libraries
- Modern PHP 8.4+: Built for the latest PHP features
- MVC Architecture: Clean separation of concerns
- Dependency Injection: Built-in container with automatic resolution
- Routing: Flexible HTTP routing with middleware support
- Template Engine: ThymeLeaf-inspired template engine with components and layouts
- Database ORM: Active Record pattern with relationships
- Console Commands: CLI interface for development and maintenance
- Caching: Multi-driver caching system
- Validation: Comprehensive form and data validation
- Security: Built-in CSRF protection, encryption, and sanitization
Installation
Create a New Project
composer create-project lengthofrope/treehouse my-app
cd my-app
composer install
./bin/th serve
Or Install via Composer
composer require lengthofrope/treehouse
Using the CLI Tool
Create a new project:
# Install TreeHouse globally composer global require lengthofrope/treehouse # Create new project ./bin/treehouse new my-app cd my-app composer install ./bin/treehouse serve
Quick Start
1. Create a Controller
<?php namespace App\Controllers; use LengthOfRope\TreeHouse\Http\Request; use LengthOfRope\TreeHouse\Http\Response; class HomeController { public function index(): string { return view('home', [ 'title' => 'Welcome to TreeHouse', 'message' => 'Your application is running!' ]); } }
2. Define Routes
In config/routes/web.php
:
<?php use App\Controllers\HomeController; $router->get('/', [HomeController::class, 'index']); $router->get('/users/{id}', [UserController::class, 'show']) ->where('id', '\d+'); $router->group(['middleware' => 'auth'], function($router) { $router->get('/dashboard', [DashboardController::class, 'index']); });
3. Create Models
<?php namespace App\Models; use LengthOfRope\TreeHouse\Database\ActiveRecord; class User extends ActiveRecord { protected array $fillable = ['name', 'email']; protected array $hidden = ['password']; public function posts() { return $this->hasMany(Post::class); } }
4. Use the Database
// Create $user = User::create([ 'name' => 'John Doe', 'email' => 'john@example.com' ]); // Query $users = User::query() ->where('active', true) ->orderBy('name') ->get(); // Relations $posts = $user->posts()->where('published', true)->get();
Directory Structure
my-app/
├── src/App/ # Application code
│ ├── Controllers/ # HTTP controllers
│ ├── Models/ # Database models
│ ├── Services/ # Business logic
│ └── Middleware/ # HTTP middleware
├── config/ # Configuration files
├── public/ # Web root
├── resources/views/ # Templates
├── storage/ # Cache, logs, compiled views
├── tests/ # Test files
├── database/migrations/ # Database migrations
└── bin/th # CLI command
CLI Commands
TreeHouse includes a comprehensive CLI tool:
# Development server ./bin/th serve --port=8000 # Cache management ./bin/th cache:clear ./bin/th cache:stats # Database ./bin/th migrate:run # Testing ./bin/th test:run # Create new project ./bin/treehouse new my-app
Configuration
Configuration files are stored in the config/
directory:
app.php
- Application settingsdatabase.php
- Database connectionscache.php
- Cache configurationroutes/web.php
- Web route definitionsroutes/api.php
- API route definitions
Template Engine
TreeHouse includes a powerful ThymeLeaf-inspired template engine:
Layout Template (layouts/app.th.html
):
<!DOCTYPE html> <html> <head> <title th:text="${title}">Default Title</title> </head> <body> <main th:fragment="content"> <!-- Content will be inserted here --> </main> </body> </html>
Page Template (home.th.html
):
<div th:extends="layouts/app" th:fragment="content"> <h1 th:text="${title}">Welcome</h1> <p th:text="${message}">Default message</p> <div th:if="${user}"> <p>Welcome, <span th:text="${user.name}">User</span>!</p> </div> <div th:each="post : ${posts}"> <article> <h2 th:text="${post.title}">Post Title</h2> <p th:text="${post.excerpt}">Post excerpt</p> </article> </div> </div>
Template Features:
th:text
- Set element text contentth:if
- Conditional renderingth:each
- Loop over collectionsth:extends
- Extend layout templatesth:fragment
- Define reusable fragments${variable}
- Variable interpolation
Middleware
Create and register middleware for request processing:
<?php namespace App\Middleware; use LengthOfRope\TreeHouse\Router\Middleware\MiddlewareInterface; use LengthOfRope\TreeHouse\Http\Request; use LengthOfRope\TreeHouse\Http\Response; class AuthMiddleware implements MiddlewareInterface { public function handle(Request $request, callable $next): Response { if (!auth()->check()) { return redirect('/login'); } return $next($request); } }
Testing
TreeHouse applications come with PHPUnit configured:
<?php namespace Tests\Unit; use Tests\TestCase; use App\Models\User; class UserTest extends TestCase { public function test_user_creation() { $user = User::create([ 'name' => 'Test User', 'email' => 'test@example.com' ]); $this->assertEquals('Test User', $user->name); $this->assertTrue($user->exists); } }
Run tests:
./bin/th test:run
composer test
Contributing
- Fork the repository
- Create your feature branch (
git checkout -b feature/amazing-feature
) - Commit your changes (
git commit -m 'Add some amazing feature'
) - Push to the branch (
git push origin feature/amazing-feature
) - Open a Pull Request
License
The TreeHouse framework is open-sourced software licensed under the MIT license.
Author
Bas de Kort
Email: bdekort@proton.me
GitHub: @lengthofrope
Support
- Documentation: https://treehouse-framework.dev
- Issues: GitHub Issues
- Discussions: GitHub Discussions