{"id":16423597,"url":"https://github.com/rougin/basilisk","last_synced_at":"2025-10-26T22:31:42.164Z","repository":{"id":57047494,"uuid":"48939921","full_name":"rougin/basilisk","owner":"rougin","description":"Simple project skeleton for Slytherin.","archived":false,"fork":false,"pushed_at":"2024-11-29T06:10:07.000Z","size":290,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-02-01T00:51:05.675Z","etag":null,"topics":["mini-app","php-app","php-mvc"],"latest_commit_sha":null,"homepage":"https://roug.in/basilisk/","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/rougin.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE.md","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}},"created_at":"2016-01-03T09:01:38.000Z","updated_at":"2024-11-29T06:10:11.000Z","dependencies_parsed_at":"2024-09-09T09:03:29.020Z","dependency_job_id":null,"html_url":"https://github.com/rougin/basilisk","commit_stats":{"total_commits":214,"total_committers":1,"mean_commits":214.0,"dds":0.0,"last_synced_commit":"a7172907eb16f091918c39e235a4c21deb4767b0"},"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rougin%2Fbasilisk","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rougin%2Fbasilisk/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rougin%2Fbasilisk/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rougin%2Fbasilisk/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/rougin","download_url":"https://codeload.github.com/rougin/basilisk/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":238408488,"owners_count":19467099,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","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":["mini-app","php-app","php-mvc"],"created_at":"2024-10-11T07:40:22.915Z","updated_at":"2025-10-26T22:31:41.818Z","avatar_url":"https://github.com/rougin.png","language":"PHP","readme":"# Basilisk\n\n[![Latest Version on Packagist][ico-version]][link-packagist]\n[![Software License][ico-license]][link-license]\n[![Build Status][ico-build]][link-build]\n[![Coverage Status][ico-coverage]][link-coverage]\n[![Total Downloads][ico-downloads]][link-downloads]\n\n`Basilisk` is a project skeleton specifically for the [Slytherin](https://roug.in/slytherin/) PHP micro-framework which contains an opinionated code structure based on [my experiences](https://roug.in/) creating projects using `Slytherin` as its foundation. The code structure should be easy to understand and be under [SOLID](https://en.wikipedia.org/wiki/SOLID) principles.\n\n## Installation\n\nCreate a new `Basilisk` project via [Composer](https://getcomposer.org/):\n\n``` bash\n$ composer create-project rougin/basilisk \"hogwarts\"\n```\n\nOnce created, kindly execute the one-time setup to the project:\n\n``` bash\n$ cd hogwarts\n$ php setup.php\n```\n\n## Running the project\n\nTo run `Basilisk` in a web browser, the [PHP's built-in web server](https://www.php.net/manual/en/features.commandline.webserver.php) can be used:\n\n``` bash\n$ php -S localhost:80 -t app/public\n```\n\nAfter running, open a web browser then proceed to http://localhost in a new tab.\n\n\u003e [!WARNING]\n\u003e This command should only be used for development purposes. It is recommended to use [Apache](https://httpd.apache.org/) or [Nginx](https://nginx.org/en/) in running this project.\n\n## What's inside?\n\nA `Basilisk` project contains a configuration of the following packages:\n\n### Slytherin\n\n[Slytherin](https://github.com/rougin/slytherin) is a simple and extensible PHP micro-framework that tries to achieve a [SOLID-based design](https://en.wikipedia.org/wiki/SOLID) for creating web applications. As `Slytherin` is the core foundation of `Basilisk`, the following packages of `Slytherin` has already been configured out of the box:\n\n* [HttpIntegration](https://github.com/rougin/slytherin/wiki/Http) allows to use PHP's superglobals (e.g., `$_GET`, `$_POST`, etc.);\n* [ConfigurationIntegration](https://github.com/rougin/slytherin/wiki/IntegrationInterface-Implementation) allows to use the `Configuration` class in any part of the code structure through dependency injection;\n* [MiddlewareIntegration](https://github.com/rougin/slytherin/wiki/Middleware) provides a simple way in integrating [PSR-15](https://www.php-fig.org/psr/psr-15/) middlewares to HTTP requests and HTTP responses;\n* [RoutingIntegration](https://github.com/rougin/slytherin/wiki/Routing) adds a systematic way of configuring HTTP routes and its routers; and\n* [RendererIntegration](https://github.com/rougin/slytherin/wiki/Template) provides a simple logic for loading PHP templates.\n\n\u003e [!NOTE]\n\u003e Kindly see the [Slytherin's documentation](https://github.com/rougin/slytherin/wiki) on how to use the above-mentioned packages.\n\n### Dotenv\n\n[Dotenv](https://github.com/vlucas/phpdotenv) is a simple PHP package that loads environment variables from `.env` files to `getenv()`, `$_ENV` and `$_SERVER` automagically. This is one of the core packages of `Basilisk` as it uses environment variables in most of its configuration in the `app/config` directory:\n\n```\n# .env.example\n\n#######################\n# Application Settings\n#######################\nAPP_NAME=\"Basilisk\"\nAPP_VERSION=\"0.1.0\"\n\n# ...\n```\n\n``` php\n// app/config/app.php\n\nreturn array(\n\n    // ...\n\n    'name' =\u003e getenv('APP_NAME'), // returns \"Basilisk\"\n\n    // ...\n\n    'version' =\u003e getenv('APP_VERSION'), // returns \"0.1.0\"\n\n    // ...\n\n);\n```\n\n### Phinx\n\n[Phinx](https://phinx.org/) is a tool made for PHP in performing database migrations. Being a framework-agnostic package, `Phinx` can create, write and perform database migrations easily. To use this package, kindly install it first using `Composer`:\n\n``` bash\n$ composer require robmorgan/phinx\n```\n\nOnce installed, kindly check the `app/config/phinx.php` file on the variables that requires an update:\n\n``` php\n// app/config/phinx.php\n\nreturn array(\n\n    /**\n     * Paths to be used for database migration.\n     *\n     * @var array\u003cstring, string[]\u003e\n     */\n    'paths' =\u003e array(\n\n        /**\n         * @var array\n         */\n        'migrations' =\u003e array(\n            $root . '/src/Phinx/Scripts',\n        ),\n\n        /**\n         * @var array\n         */\n        'seeds' =\u003e array(\n            $root . '/src/Phinx/Seeders',\n        ),\n\n    ),\n\n    // ...\n\n);\n```\n\nWhen creating or performing database migrations using `Phinx`, always use the configuration file provided by `Basilisk`:\n\n``` bash\n$ vendor/bin/phinx create CreateUsersTable -c app/config/phinx.php\n```\n\n### Weasley\n\n[Weasley](https://github.com/rougin/weasley) is a utility package in PHP that provides generators, helpers, and utilities for Slytherin. The following packages are also configured within `Basilisk`:\n\n* `Laravel\\Eloquent` enables the usage of [Eloquent](https://laravel.com/docs/eloquent) to `Basilisk` which is an [Object-relational mapper (ORM)](https://en.wikipedia.org/wiki/Object%E2%80%93relational_mapping) from [Laravel](https://laravel.com). To use this package, kindly install its required package first in `Composer`:\n\n  ``` bash\n  $ composer require illuminate/database\n  ```\n\n* `Laravel\\Blade` allows `Basilisk` to use [Blade](https://laravel.com/docs/blade) from `Laravel` for creating PHP templates using the `Blade` templating engine. To use this package, kindly uncomment its related code first in the `app/config/app.php` file:\n\n  ``` php\n  // app/config/app.php\n\n  // ...\n\n  /**\n   * This section specifies the core integrations that are\n   * required to run in Slytherin. The following will use\n   * the defined HTTP variables, available HTTP routes, and\n   * the specified HTTP middlewares (if they're available).\n   */\n  'Rougin\\Slytherin\\Http\\HttpIntegration',\n  'Rougin\\Slytherin\\Integration\\ConfigurationIntegration',\n  'Rougin\\Slytherin\\Middleware\\MiddlewareIntegration',\n  'Rougin\\Slytherin\\Routing\\RoutingIntegration',\n  // 'Rougin\\Slytherin\\Template\\RendererIntegration', // comment this line\n\n  /**\n   * This section specifies the packages came from Weasley.\n   * Please see Weasley's documentation for all of its\n   * available packages and integrations that can be used.\n   *\n   * @link https://roug.in/weasley/\n   */\n  'Rougin\\Weasley\\Packages\\Laravel\\Eloquent',\n  'Rougin\\Weasley\\Packages\\Laravel\\Blade', // uncomment this line\n  ```\n\n  Then proceed to install its required package from `Composer`:\n\n  ``` bash\n  $ composer require illuminate/view\n  ```\n\n  Once installed, the `Blade` templates can now be added in the `app/blades` directory:\n\n  ``` php\n  // app/blades/index.blade.php\n\n  @extends('main')\n\n  @section('content')\n    \u003cdiv class=\"container\"\u003e\n      \u003cdiv class=\"p-5\"\u003e\n        \u003ch1 class=\"text-center\"\u003eHello, Muggle!\u003c/h1\u003e\n      \u003c/div\u003e\n    \u003c/div\u003e\n  @endsection\n  ```\n\n## Directory structure\n\nThe following directory names below are only the preferred names [based on my experience](https://roug.in/work/) building projects using `Slytherin`. However, they can be easily be extended or removed as `Slytherin` not does not conform to any of the specified preferences:\n\n```\nsrc/\n├─ Checks/\n├─ Depots/\n├─ Models/\n├─ Phinx/\n│  ├─ Scripts/\n│  ├─ Seeders/\n├─ Routes/\n├─ Scripts/\n```\n\n### `Checks`\n\nThis directory contains PHP classes that are used specifically for validation. The said PHP classes may be extended to the `Check` class of [Weasley](https://roug.in/weasley/):\n\n``` php\nnamespace App\\Checks;\n\nuse Rougin\\Weasley\\Check;\n\nclass UserCheck extends Check\n{\n    /**\n     * @var array\u003cstring, string\u003e\n     */\n    protected $labels =\n    [\n        'name' =\u003e 'Name',\n        'email' =\u003e 'Email',\n    ];\n\n    /**\n     * @var array\u003cstring, string\u003e\n     */\n    protected $rules =\n    [\n        'name' =\u003e 'required',\n        'email' =\u003e 'required|email',\n    ];\n}\n```\n\n\u003e [!NOTE]\n\u003e For more information on how to create a validation class, please see the [Validation section](https://github.com/rougin/weasley?tab=readme-ov-file#validation) of the `Weasley` documentation.\n\n### `Depots`\n\nThis is the main directory that should contain the business logic of `Basilisk`:\n\n``` php\nnamespace App\\Depots;\n\nuse App\\Models\\User;\n\nclass UserDepot\n{\n    /**\n     * @var \\App\\Models\\User\n     */\n    protected $user;\n\n    /**\n     * @param \\App\\Models\\User $user\n     */\n    public function __construct(User $user)\n    {\n        $this-\u003euser = $user;\n    }\n\n    /**\n     * @return array\u003cstring, mixed\u003e[]\n     */\n    public function all()\n    {\n        $result = $this-\u003euser-\u003eall();\n\n        $items = array();\n\n        // ...\n\n        return $items;\n    }\n}\n```\n\nPrior in using depots, I implemented most of the logic in the `Routes` or `Models` directories. However, it presents a challenge to me in organizing code when implementing new features. In using depots, I can reuse the same logic in to either `Routes` (for receiving user request) or in `Scripts` directory (for handling terminal-based actions).\n\n\u003e [!NOTE]\n\u003e In other PHP frameworks and other guides, `Depot` is also known as the [Repository pattern](https://designpatternsphp.readthedocs.io/en/latest/More/Repository/README.html).\n\n### `Models`\n\nThis is the directory where for storing the models (if using [`Eloquent`](https://laravel.com/docs/eloquent)) or entities (if using [`Doctrine`](https://www.doctrine-project.org/index.html)). In my experience, my best practice is that the class names added in this directory should represent a database table (e.g., if having a `users` table from the database, it should be represented in `Basilisk` as `User` class):\n\n``` php\n\u003c?php\n\nnamespace App\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass User extends Model\n{\n    /**\n     * @var string[]\n     */\n    protected $fillable =\n    [\n        'name',\n        'password',\n        'email',\n    ];\n\n    /**\n     * @var string[]\n     */\n    protected $hidden =\n    [\n        'password'\n    ];\n\n    /**\n     * @var string\n     */\n    protected $table = 'users';\n}\n\n```\n\n\u003e [!NOTE]\n\u003e As `Basilisk` provided a `User` model based on `Eloquent`, kindly see its [official discussion](https://laravel.com/docs/eloquent) for its usage and configuration.\n\n### `Phinx`\n\nThis is the directory for the storage of related files to the [Phinx](https://phinx.org/) package. The `Scripts` directory must contain the generated database migrations while the `Seeders` directory must contain the custom database seeders:\n\n``` php\n// src/Phinx/Scripts/20171012020230_create_users_table.php\n\nuse Phinx\\Migration\\AbstractMigration;\n\nclass CreateUsersTable extends AbstractMigration\n{\n    public function change(): void\n    {\n        $properties = ['id' =\u003e false, 'primary_key' =\u003e ['id']];\n\n        $table = $this-\u003etable('users', $properties);\n\n        $table-\u003eaddColumn('id', 'integer', ['limit' =\u003e 10, 'identity' =\u003e true]);\n        $table-\u003eaddColumn('name', 'string', ['limit' =\u003e 200]);\n        $table-\u003eaddColumn('email', 'string', ['limit' =\u003e 200]);\n        $table-\u003eaddColumn('password', 'string', ['limit' =\u003e 500]);\n        $table-\u003eaddColumn('created_at', 'datetime');\n        $table-\u003eaddColumn('updated_at', 'datetime', ['null' =\u003e true]);\n\n        $table-\u003ecreate();\n    }\n}\n```\n\n``` php\n// src/Phinx/Seeders/UserSeeder.php\n\nuse Phinx\\Seed\\AbstractSeed;\n\nclass UserSeeder extends AbstractSeed\n{\n    protected $items =\n    [\n        ['name' =\u003e 'Harry Jonathans Potter', 'email' =\u003e 'hjpotter@hogwarts.co.uk'],\n        ['name' =\u003e 'Hermione Jane Granger', 'email' =\u003e 'hjgranger@hogwarts.co.uk'],\n        ['name' =\u003e 'Ronald Bilius Weasley', 'email' =\u003e 'rbweasley@hogwarts.co.uk'],\n    ];\n\n    public function run(): void\n    {\n        $data = array();\n\n        foreach ($this-\u003eitems as $item)\n        {\n            $item['created_at'] = date('Y-m-d H:i:s');\n\n            $data[] = $item;\n        }\n\n        $this-\u003etable('users')-\u003einsert($data)-\u003esave();\n    }\n}\n```\n\nThis directory will also be used for performing database migrations and its seeders. To perform a database migration, kindly run the `migrate` command:\n\n``` bash\n$ vendor/bin/phinx migrate -c app/config/phinx.php\n```\n\nThe `seed:run` command can be used for populating data in a database:\n\n``` bash\n$ vendor/bin/phinx seed:run -c app/config/phinx.php\n```\n\nWhen executed, the command above will perform the database seeders in **alphabetical** order.\n\n\u003e [!NOTE]\n\u003e Before performing any database migrations from `Phinx`, kindly update the database credentials first in `.env`:\n\u003e\n\u003e ``` bash\n\u003e $ cp .env.example .env\n\u003e ```\n\n### `Routes`\n\nThis is the gateway of `Basilisk` wherein the [HTTP routes](https://github.com/rougin/slytherin/wiki/Defining-HTTP-Routes) are stored and configured as a PHP class. The PHP class can call or instantiate the classes found from the previously mentioned directories:\n\n``` php\nnamespace App\\Routes;\n\nuse Rougin\\Slytherin\\Template\\RendererInterface;\n\nclass Hello\n{\n    /**\n     * Returns the \"Hello, Muggle!\" text.\n     *\n     * @return string\n     */\n    public function index(RendererInterface $renderer)\n    {\n        return $renderer-\u003erender('index');\n    }\n}\n```\n\nOnce a HTTP route was created to the directory, it should be added to the `Router` for it to be recognized by `Slytherin`:\n\n``` php\nnamespace App;\n\nuse Rougin\\Slytherin\\Routing\\Router as Slytherin;\n\nclass Router extends Slytherin\n{\n    /**\n     * @var string\n     */\n    protected $namespace = 'App\\Routes';\n\n    /**\n     * @var string\n     */\n    protected $prefix = '/';\n\n    /**\n     * @return \\Rougin\\Slytherin\\Routing\\RouteInterface[]\n     */\n    public function routes()\n    {\n        $this-\u003eget('/', 'Hello@index');\n\n        // ...\n\n        return $this-\u003eroutes;\n    }\n}\n```\n\n\u003e [!NOTE]\n\u003e In other PHP frameworks, `Routes` is commonly known as `Controllers`.\n\n### `Scripts`\n\nThis is the directory to store commands or scripts. These scripts can be executed directly using the `php` command in the terminal:\n\n``` php\n// src/Scripts/HelloWorld.php\n\necho 'Hello world!';\n```\n\n``` bash\n$ php src/Scripts/HelloWorld.php\n\nHello world!\n```\n\n## Development workflow\n\n`Basilisk` also provides unit testing and static code analysis out of the box when implementing new features to minimize the introduction of errors during development. It also has an opinionated coding style which can be configured after the installation.\n\n### Unit testing\n\nThe sample unit tests provided in `Basilisk` were written in [PHPUnit](https://phpunit.de/index.html):\n\n``` bash\n$ composer test\n```\n\nIt is recommended to run the above command to always check if the updated code introduces errors when creating fixes or implementing new features.\n\n\u003e [!NOTE]\n\u003e Please see the [official documentation](https://phpunit.de/documentation.html) of `PHPUnit` on how to write unit tests to the specified testing framework.\n\n### Code quality\n\nTo retain the code quality of `Basilisk`, a static code analysis code tool named [PHPStan](https://phpstan.org/) can be used during development. To start, kindly install the specified package in the global environment of `Composer`:\n\n``` bash\n$ composer global require phpstan/phpstan --dev\n```\n\nOnce installed, `PHPStan` can now be run using its namesake command:\n\n``` bash\n$ phpstan\n```\n\n\u003e [!NOTE]\n\u003e When running `phpstan`, it will use the `phpstan.neon` file which is already provided by `Basilisk`.\n\n### Coding style\n\nAside from code quality, `Basilisk` also uses a tool named [PHP Coding Standards Fixer](https://cs.symfony.com/) for maintaining an opinionated style guide. To use this tooling, it needs also to be installed in the `Composer`'s global environment first:\n\n``` bash\n$ composer global require friendsofphp/php-cs-fixer --dev\n```\n\nAfter its installation, kindly use the `php-cs-fixer` command in the same `Authsum` directory:\n\n``` bash\n$ php-cs-fixer fix --config=phpstyle.php\n```\n\nThe `phpstyle.php` file provided by `Basilisk` currently follows the [PSR-12](https://www.php-fig.org/psr/psr-12/) standard as its baseline for the coding style and uses [Allman](https://en.wikipedia.org/wiki/Indentation_style#Allman_style) as its indentation style.\n\n\u003e [!NOTE]\n\u003e Installing both `PHPStan` and `PHP Coding Standards Fixer` requires a minimum version of PHP at least `7.4`.\n\n## Changelog\n\nPlease see [CHANGELOG][link-changelog] for more information what has changed recently.\n\n## License\n\nThe MIT License (MIT). Please see [LICENSE][link-license] for more information.\n\n[ico-build]: https://img.shields.io/github/actions/workflow/status/rougin/basilisk/build.yml?style=flat-square\n[ico-coverage]: https://img.shields.io/codecov/c/github/rougin/basilisk?style=flat-square\n[ico-downloads]: https://img.shields.io/packagist/dt/rougin/basilisk.svg?style=flat-square\n[ico-license]: https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square\n[ico-version]: https://img.shields.io/packagist/v/rougin/basilisk.svg?style=flat-square\n\n[link-build]: https://github.com/rougin/basilisk/actions\n[link-changelog]: https://github.com/rougin/basilisk/blob/master/CHANGELOG.md\n[link-contributors]: https://github.com/rougin/basilisk/contributors\n[link-coverage]: https://app.codecov.io/gh/rougin/basilisk\n[link-downloads]: https://packagist.org/packages/rougin/basilisk\n[link-license]: https://github.com/rougin/basilisk/blob/master/LICENSE.md\n[link-packagist]: https://packagist.org/packages/rougin/basilisk\n[link-upgrading]: https://github.com/rougin/basilisk/blob/master/UPGRADING.md\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frougin%2Fbasilisk","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frougin%2Fbasilisk","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frougin%2Fbasilisk/lists"}