{"id":35576417,"url":"https://github.com/mirko-pagliai/simple-view-controller","last_synced_at":"2026-01-11T08:44:00.767Z","repository":{"id":330567439,"uuid":"1123163374","full_name":"mirko-pagliai/simple-view-controller","owner":"mirko-pagliai","description":"A lightweight PHP framework focused exclusively on the Controller and View layers","archived":false,"fork":false,"pushed_at":"2026-01-03T09:19:31.000Z","size":112,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-01-08T08:32:23.081Z","etag":null,"topics":["framework","mvc-framework","mvc-pattern","php","php-framework","php8"],"latest_commit_sha":null,"homepage":"","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mirko-pagliai.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.txt","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-12-26T09:58:57.000Z","updated_at":"2026-01-03T09:19:34.000Z","dependencies_parsed_at":"2025-12-27T23:00:29.040Z","dependency_job_id":null,"html_url":"https://github.com/mirko-pagliai/simple-view-controller","commit_stats":null,"previous_names":["mirko-pagliai/simple-view-control","mirko-pagliai/simple-view-controller"],"tags_count":null,"template":false,"template_full_name":null,"purl":"pkg:github/mirko-pagliai/simple-view-controller","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirko-pagliai%2Fsimple-view-controller","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirko-pagliai%2Fsimple-view-controller/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirko-pagliai%2Fsimple-view-controller/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirko-pagliai%2Fsimple-view-controller/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mirko-pagliai","download_url":"https://codeload.github.com/mirko-pagliai/simple-view-controller/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mirko-pagliai%2Fsimple-view-controller/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28298863,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-11T08:21:30.231Z","status":"ssl_error","status_checked_at":"2026-01-11T08:21:26.882Z","response_time":60,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["framework","mvc-framework","mvc-pattern","php","php-framework","php8"],"created_at":"2026-01-04T19:53:21.921Z","updated_at":"2026-01-11T08:44:00.762Z","avatar_url":"https://github.com/mirko-pagliai.png","language":"PHP","readme":"# simple-view-controller\n[![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE.txt)\n[![CI](https://github.com/mirko-pagliai/simple-view-controller/actions/workflows/ci.yml/badge.svg)](https://github.com/mirko-pagliai/simple-view-controller/actions/workflows/ci.yml)\n[![codecov](https://codecov.io/gh/mirko-pagliai/simple-view-controller/graph/badge.svg?token=0mNM4qL98u)](https://codecov.io/gh/mirko-pagliai/simple-view-controller)\n[![CodeFactor](https://www.codefactor.io/repository/github/mirko-pagliai/simple-view-controller/badge)](https://www.codefactor.io/repository/github/mirko-pagliai/simple-view-controller)\n\n`simple-view-controller` is a lightweight PHP framework focused exclusively on the **Controller** and **View** layers.\n\nIt is designed as a library, not as a full-stack framework, and intentionally omits models, ORMs, template engines, and dependency injection containers.\n\nThe goal is to provide a minimal, explicit, and predictable runtime for small web applications.\n\n## Design goals\n\n- Explicit behavior over implicit conventions\n- Minimal and stable public API\n- No magic exposed to the user\n- Framework as a library, not as an application\n- Use Symfony components without adopting a full-stack approach\n\n## What the framework provides\n\n- An `Application` runtime to handle HTTP requests\n- Routing based on [Symfony Routing](https://symfony.com/doc/current/create_framework/routing.html)\n- A base `Controller` class\n- A minimal `View` abstraction\n- Automatic injection of the current `Request` into the `View`\n- Automatic template resolution and rendering\n- Centralized error handling (404 and 500)\n- PSR-3 compatible logging\n- Environment variable loading via dotenv\n\n## What the framework does NOT provide\n\nBy design, the framework does not include:\n\n- Models or a data layer\n- ORMs or database abstractions\n- A dependency injection container\n- A templating engine\n- HTML helpers\n- CLI tooling\n- Code generation\n- An application entry point (`index.php`)\n- A global debug switch\n\nAll of these are application-level concerns.\n\n## Routing\n\nRouting is based on [Symfony Routing](https://symfony.com/doc/current/create_framework/routing.html).\n\nRoutes can be defined in two supported ways.\n\n### Option 1: defining routes in `config/routes.php` (best way)\n\nBy default, the application will try to load routes from `config/routes.php`\n\nThe file must return a `RouteCollection`:\n\n```php\n\u003c?php\ndeclare(strict_types=1);\n\nuse Symfony\\Component\\Routing\\Route;\nuse Symfony\\Component\\Routing\\RouteCollection;\n\nuse App\\Controller\\HomeController;\n\n$routes = new RouteCollection();\n$routes-\u003eadd('home', new Route(path: '/', defaults: [\n    '_controller' =\u003e ['\\App\\Controller\\HomeController', 'index'],\n]));\n\nreturn $routes;\n```\n\n### Option 2: passing routes directly to the `Application`\n\nAlternatively, you can pass a `RouteCollection` instance as an application argument:\n```php\n\u003c?php\ndeclare(strict_types=1);\n\nuse SimpleVC\\Application;\nuse Symfony\\Component\\Routing\\Route;\nuse Symfony\\Component\\Routing\\RouteCollection;\n\n$routes = new RouteCollection();\n$routes-\u003eadd('home', new Route(path: '/', defaults: [\n    '_controller' =\u003e ['\\App\\Controller\\HomeController', 'index'],\n]));\n\n$app = new Application($routes);\n\n$response = $app-\u003ehandle();\n$response-\u003esend();\n```\n\n## Controllers\n\nControllers must extend `SimpleVC\\Controller`:\n```php\n\u003c?php\ndeclare(strict_types=1);\n\nnamespace App\\Controller;\n\nuse SimpleVC\\Controller;\nuse Symfony\\Component\\HttpFoundation\\Response;\n\nclass HomeController extends Controller\n{\n    public function index(): Response\n    {\n        //Here's something...\n    }\n}\n```\n\nThe runtime invokes controller methods.\nWhat they return is interpreted by the runtime, which is responsible for producing the final `Response`.\n\nThe framework explicitly supports multiple controller styles.\n\n### Example 1: controller preparing the `View` (implicit rendering)\n\n```php\npublic function index(): void\n{\n    $this-\u003eset('title', 'Home');\n    $this-\u003eset('message', 'Hello world');\n}\n```\nIn this case:\n\n- the controller does not return anything\n- the controller does not implicity call `render()`\n- the runtime resolves the template automatically\n- the runtime renders the template and produces the `Response`\n\nThe runtime will automatically resolve the template as `templates/{ControllerName}/{methodName}.php`.  \nSo in this example case it would be `templates/Home/index.php`.  \nInside this template file there will be the variables `$title` and `$text`.\n\n### Example 2: controller explicitly calls the `render()` method (returns a `Response`)\n\n```php\npublic function index(): Response\n{\n    $this-\u003eset('title', 'Home');\n    $this-\u003eset('message', 'Hello world');\n    \n    return $this-\u003erender('Custom/stuff.php');\n}\n```\nThe result is like the previous case, but in this one it will use the `templates/Custom/stuff.php` file.\n\n### Example 3: controller directly returns a `Response`\n\n```php\npublic function index(): Response\n{\n    return new Response('\u003cstrong\u003eHello world\u003c/strong\u003e');\n}\n```\n\nIn this case, the returned `Response` is used directly by the runtime.\n\n## Views\n\nThe `View` abstraction is intentionally minimal.\n\n- Variables are assigned by the controller  \n- The current `Request` is injected automatically\n- By default, the template is resolved and rendered by the runtime\n\nTemplates are plain PHP files.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmirko-pagliai%2Fsimple-view-controller","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmirko-pagliai%2Fsimple-view-controller","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmirko-pagliai%2Fsimple-view-controller/lists"}