{"id":20684418,"url":"https://github.com/spiral-packages/livewire","last_synced_at":"2026-04-02T01:33:53.323Z","repository":{"id":146343609,"uuid":"618095837","full_name":"spiral-packages/livewire","owner":"spiral-packages","description":"Livewire integration bridge for Spiral Framework","archived":false,"fork":false,"pushed_at":"2024-04-16T17:09:44.000Z","size":337,"stargazers_count":2,"open_issues_count":6,"forks_count":1,"subscribers_count":2,"default_branch":"1.x","last_synced_at":"2025-06-20T06:38:11.396Z","etag":null,"topics":["livewire","php","spiral","spiral-framework"],"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/spiral-packages.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","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":"2023-03-23T18:39:01.000Z","updated_at":"2024-07-17T06:37:59.000Z","dependencies_parsed_at":null,"dependency_job_id":"62cacdcb-eddd-447e-b7dc-271227157e2c","html_url":"https://github.com/spiral-packages/livewire","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/spiral-packages/livewire","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/spiral-packages%2Flivewire","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/spiral-packages%2Flivewire/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/spiral-packages%2Flivewire/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/spiral-packages%2Flivewire/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/spiral-packages","download_url":"https://codeload.github.com/spiral-packages/livewire/tar.gz/refs/heads/1.x","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/spiral-packages%2Flivewire/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31293938,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-02T01:05:07.454Z","status":"ssl_error","status_checked_at":"2026-04-02T00:56:46.496Z","response_time":53,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: 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":["livewire","php","spiral","spiral-framework"],"created_at":"2024-11-16T22:21:39.603Z","updated_at":"2026-04-02T01:33:53.307Z","avatar_url":"https://github.com/spiral-packages.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Livewire integration bridge for Spiral Framework\n\n[![PHP Version Require](https://poser.pugx.org/spiral-packages/livewire/require/php)](https://packagist.org/packages/spiral-packages/livewire)\n[![Latest Stable Version](https://poser.pugx.org/spiral-packages/livewire/v/stable)](https://packagist.org/packages/spiral-packages/livewire)\n[![phpunit](https://github.com/spiral-packages/livewire/actions/workflows/phpunit.yml/badge.svg)](https://github.com/spiral-packages/livewire/actions)\n[![psalm](https://github.com/spiral-packages/livewire/actions/workflows/psalm.yml/badge.svg)](https://github.com/spiral-packages/livewire/actions)\n[![Codecov](https://codecov.io/gh/spiral-packages/livewire/branch/1.x/graph/badge.svg)](https://codecov.io/gh/spiral-packages/livewire)\n[![Total Downloads](https://poser.pugx.org/spiral-packages/livewire/downloads)](https://packagist.org/packages/spiral-packages/livewire)\n[![type-coverage](https://shepherd.dev/github/spiral-packages/livewire/coverage.svg)](https://shepherd.dev/github/spiral-packages/livewire)\n[![psalm-level](https://shepherd.dev/github/spiral-packages/livewire/level.svg)](https://shepherd.dev/github/spiral-packages/livewire)\n\n\n## WARNING!\nThis package is currently under active development. It is not recommended for use in production environments due to potential instability.\n\n## Requirements\n\nMake sure that your server is configured with following PHP version and extensions:\n\n- PHP 8.1+\n- Spiral framework 3.7+\n\n## Installation\n\nYou can install the package via composer:\n\n```bash\ncomposer require spiral-packages/livewire\n```\n\nTo enable the package in your Spiral Framework application, you will need to add\nthe `Spiral\\Livewire\\Bootloader\\LivewireBootloader` class to the list of bootloaders in your application:\n\n```php\nprotected const LOAD = [\n    // ...\n    \\Spiral\\Livewire\\Bootloader\\LivewireBootloader::class,\n];\n```\n\n\u003e **Note**\n\u003e If you are using [`spiral-packages/discoverer`](https://github.com/spiral-packages/discoverer),\n\u003e you don't need to register bootloader by yourself.\n\n\n### Template engines\n\n#### Twig\n\nTo get started with **Livewire** and **Twig** in Spiral Framework application, need to add the\n`Spiral\\Livewire\\Bootloader\\TwigBootloader` class to the list of bootloaders in your application.\n\nHere's an example of how to do that:\n\n```php\n    // ...\n    \\Spiral\\Livewire\\Bootloader\\TwigBootloader::class,\n```\n\nWhen the **TwigBootloader** is registered, it provides the `Spiral\\Livewire\\Twig\\Extension\\LivewireExtension` extension\nthat allows to use the **livewire_styles**, **livewire_scripts**, **livewire** Twig functions.\n- **livewire_styles** and **livewire_scripts** - These functions are used to include the required Livewire CSS and JavaScript code.\n- **livewire** - This function takes the `name` of the component as the first parameter and renders the\n  initial state of the component. Subsequent parameters will be passed to the component's **mount** method.\n\n#### Stempler\n\nTo get started with **Livewire** and **Stempler** in Spiral Framework application, need to add the\n`Spiral\\Livewire\\Bootloader\\StemplerBootloader` class to the list of bootloaders in your application.\n\nHere's an example of how to do that:\n\n```php\n    // ...\n    \\Spiral\\Livewire\\Bootloader\\StemplerBootloader::class,\n```\n\nWhen the **StemplerBootloader** is registered, it provides the `Spiral\\Livewire\\Template\\Stempler\\LivewireDirective`\ndirective that allows to use the **livewireStyles**, **livewireScripts** directives and\n`Spiral\\Livewire\\Template\\Stempler\\NodeVisitor` that can render a Livewire component on a page using the\n**\u003clivewire:name /\u003e** tag syntax.\n- **livewireStyles** and **livewireScripts** - These functions are used to include the required Livewire CSS and JavaScript code.\n\n## Configuration\n\nThe configuration file should be located at **app/config/livewire.php**, and it allows you to set options.\nHere is an example of how the configuration file might look:\n\n```php\nuse Spiral\\Events\\Config\\EventListener;\nuse Spiral\\Livewire\\Component\\Registry\\Processor\\AttributeProcessor;\nuse Spiral\\Livewire\\Event\\Component\\ComponentHydrateSubsequent;\nuse Spiral\\Livewire\\Listener\\Component\\SupportChildren;\nuse Spiral\\Livewire\\Listener\\Component\\SupportLocales;\nuse Spiral\\Livewire\\Middleware\\Component\\CallHydrationHooks;\nuse Spiral\\Livewire\\Middleware\\Component\\CallPropertyHydrationHooks;\nuse Spiral\\Livewire\\Middleware\\Component\\HydrateModelProperties;\nuse Spiral\\Livewire\\Interceptor\\Mount\\CycleInterceptor;\nuse Spiral\\Livewire\\Interceptor\\Mount\\TypecasterInterceptor;\n\nreturn [\n    'listeners' =\u003e [\n        // ...\n        ComponentHydrateSubsequent::class =\u003e [\n            new EventListener(\n                listener: SupportLocales::class,\n                method: 'onComponentHydrateSubsequent',\n                priority: 10\n            ),\n            new EventListener(\n                listener: SupportChildren::class,\n                method: 'onComponentHydrateSubsequent',\n                priority: 20\n            ),\n        ],\n        // ...\n    ],\n    'interceptors' =\u003e [\n        'mount' =\u003e [\n            CycleInterceptor::class,\n            TypecasterInterceptor::class,\n        ],\n        'boot' =\u003e []\n    ],\n    'initial_hydration_middleware' =\u003e [\n        // ...\n        CallHydrationHooks::class,\n        // ...\n    ],\n    'hydration_middleware' =\u003e [\n        // ...\n        HydrateModelProperties::class,\n        // ...\n    ],\n    'initial_dehydration_middleware' =\u003e [\n        // ...\n        CallPropertyHydrationHooks::class,\n        // ...\n    ],\n    'dehydration_middleware' =\u003e [\n        // ...\n        CallPropertyHydrationHooks::class,\n        // ...\n    ],\n    'processors' =\u003e [\n        // ...\n        AttributeProcessor::class,\n        // ...\n    ],\n    'disable_browser_cache' =\u003e true,\n];\n```\n\n\u003e **Notice**\n\u003e The package is configured by default and does not require any additional configuration.\n\u003e Use the config file only if you need to change the default configuration.\n\n\u003e **Warning**\n\u003e The order of all middleware is important! The correct order can be viewed in the default configuration here:\n\u003e **src/Bootloader/ConfigBootloader.php**\n\n## Usage\n\nAdd the required Livewire CSS and JavaScript code:\n\n### Twig\n\n```html\n\u003c!DOCTYPE html\u003e\n\u003chtml lang=\"@{locale}\"\u003e\n    \u003chead\u003e\n        // ...\n        {{ livewire_styles() }}\n    \u003c/head\u003e\n    \u003cbody\u003e\n        {% block body %}{% endblock %}\n        {{ livewire_scripts() }}\n    \u003c/body\u003e\n\u003c/html\u003e\n```\n\n### Stempler\n\n```html\n\u003c!DOCTYPE html\u003e\n\u003chtml lang=\"@{locale}\"\u003e\n\u003chead\u003e\n    // ...\n    @livewireStyles\n\u003c/head\u003e\n\u003cbody\u003e\n    // ...\n    @livewireScripts\n\u003c/body\u003e\n\u003c/html\u003e\n```\n\nLets create a simple Livewire component **Counter**:\n\n```php\nnamespace App\\Endpoint\\Web\\Livewire\\Component;\n\nuse Spiral\\Livewire\\Attribute\\Component;\nuse Spiral\\Livewire\\Attribute\\Model;\nuse Spiral\\Livewire\\Component\\LivewireComponent;\n\n#[Component(name: 'counter', template: 'components/counter')]\nfinal class Counter extends LivewireComponent\n{\n    #[Model]\n    public int $count = 0;\n\n    public function increment(): void\n    {\n        $this-\u003ecount++;\n    }\n}\n```\n\nCreate a template:\n\n```html\n\u003cdiv style=\"text-align: center\"\u003e\n    \u003cbutton wire:click=\"increment\"\u003e+\u003c/button\u003e\n    \u003ch1\u003e{{ count }}\u003c/h1\u003e\n\u003c/div\u003e\n```\n\nCall the Livewire component anywhere in your template.\n\n### Twig\n\n```html\n{{ livewire('counter') }}\n```\n\n### Stempler\n\n```html\n\u003clivewire:counter /\u003e\n```\n\nNow reload the page in the browser, you should see the counter component rendered.\nIf you click the \"+\" button, the page should automatically update without a page reload.\n\n### Validation\n\nThe first step in enabling validation in your Livewire components is to make sure that `spiral\\validator` or\n`spiral-packages/laravel-validator` packages are installed and properly configured in your application.\nOnce you have ensured that the validator package is installed, you will need to add the\n`Spiral\\Livewire\\Bootloader\\ValidationBootloader` class to the list of bootloaders in your application:\n\n```php\nprotected const LOAD = [\n    // ...\n    \\Spiral\\Livewire\\Bootloader\\ValidationBootloader::class,\n];\n```\n\nAfter adding the ValidationBootloader class, you must implement the `Spiral\\Livewire\\Validation\\ShouldBeValidated`\ninterface in your Livewire component and define the `validationRules` method to specify your validation rules.\nThis method should return an array of validation rules for each property that requires validation.\n**Validation rules must be in the format supported by the validator you are using.**\n\n\u003e **Notice**\n\u003e Validation rules are described in the [Spiral Validator](https://spiral.dev/docs/validation-spiral/3.6/en#validation-dsl),\n\u003e [Laravel Validator](https://laravel.com/docs/10.x/validation#available-validation-rules) documentation.\n\nFor example, if you want to validate the **name** and **email** fields of a ContactForm component,\nyou could define the component like this.\n\n#### Spiral Validator\n\n```php\nnamespace App\\Endpoint\\Web\\Livewire\\Component;\n\nuse Spiral\\Livewire\\Attribute\\Component;\nuse Spiral\\Livewire\\Attribute\\Model;\nuse Spiral\\Livewire\\Component\\LivewireComponent;\nuse Spiral\\Livewire\\Validation\\ShouldBeValidated;\n\n#[Component(name: 'contact-form', template: 'components/contact-form.twig')]\nfinal class ContactForm extends LivewireComponent implements ShouldBeValidated\n{\n    #[Model]\n    public string $name;\n\n    #[Model]\n    public string $email;\n\n    public function submit(): void\n    {\n        // This method will only be called if all the data is valid\n    }\n\n    public function validationRules(): array\n    {\n        return [\n            'name' =\u003e ['required'],\n            'email' =\u003e ['required', 'email']\n        ];\n    }\n```\n\n#### Laravel Validator\n\n```php\nnamespace App\\Endpoint\\Web\\Livewire\\Component;\n\nuse Spiral\\Livewire\\Attribute\\Component;\nuse Spiral\\Livewire\\Attribute\\Model;\nuse Spiral\\Livewire\\Component\\LivewireComponent;\nuse Spiral\\Livewire\\Validation\\ShouldBeValidated;\n\n#[Component(name: 'contact-form', template: 'components/contact-form.twig')]\nfinal class ContactForm extends LivewireComponent implements ShouldBeValidated\n{\n    #[Model]\n    public string $name;\n\n    #[Model]\n    public string $email;\n\n    public function submit(): void\n    {\n        // This method will only be called if all the data is valid\n    }\n\n    public function validationRules(): array\n    {\n        return [\n            'name' =\u003e 'required',\n            'email' =\u003e 'required|email'\n        ];\n    }\n```\n\nIn this examples, the validationRules method returns an array of rules that specify that both name and email are\nrequired fields, and that the email field must be a valid email address.\n\n- Validator can validate only single property when the property is updated. If the component is configured to update\n  the data when the field changes. For example, a validator might validate an Email and display an error **before**\n  the user clicks the Submit button.\n- Before calling the component method, the validator will check all the data and only call the method if all data is valid.\n\n### Interceptors\n\nSpiral provides a way for developers to customize the behavior of their executing `boot` and `mount` methods through\ninterceptors. An interceptor is a piece of code that is executed before or after a mount or boot method is called.\n\nSome interceptors are provided by the package and enabled by default.\n- **Spiral\\Livewire\\Interceptor\\Mount\\CycleInterceptor** - This is `mount` interceptor.\n  Automatically resolves Cycle entities based on given parameter.\n- **Spiral\\Livewire\\Interceptor\\Mount\\TypecasterInterceptor** - This is `mount` interceptor.\n  Automatically converts the parameters passed to the mount method to the required type\n  (**bool**, **int**, **float**, **array**).\n\n\u003e **Notice**\n\u003e The `CycleInterceptor` requires [Cycle ORM Bridge](https://github.com/spiral/cycle-bridge).\n\u003e If you don't use it, the interceptor will not be activated.\n\nYou can create an interceptor yourself and register it in the config file.\n\n```php\nnamespace App\\Interceptor;\n\nuse Spiral\\Core\\CoreInterceptorInterface;\nuse Spiral\\Core\\CoreInterface;\nuse Spiral\\Livewire\\Component\\LivewireComponent;\n\nclass SomeInterceptor implements CoreInterceptorInterface\n{\n    /**\n     * @param class-string $controller Component class name\n     * @param string $action method (boot or mount)\n     * @param array{\n     *     component: LivewireComponent,\n     *     reflection: \\ReflectionMethod,\n     *     parameters: array\n     * } $parameters Array with additional parameters.\n     *  For the mount method, contains an array with the parameters that were passed to it.\n     */\n    public function process(string $controller, string $action, array $parameters, CoreInterface $core): mixed\n    {\n        // Some code before calling method mount or boot\n\n        $core-\u003ecallAction($controller, $action, $parameters);\n\n        // Some code after calling method mount or boot\n\n        return null;\n    }\n}\n```\n\n```php\n// file app/config/livewire.php\nuse App\\Interceptor\\SomeInterceptor;\nuse Spiral\\Livewire\\Interceptor\\Mount\\CycleInterceptor;\nuse Spiral\\Livewire\\Interceptor\\Mount\\TypecasterInterceptor;\n\nreturn [\n    'interceptors' =\u003e [\n        'mount' =\u003e [\n            SomeInterceptor::class,\n            CycleInterceptor::class,\n            TypecasterInterceptor::class,\n        ],\n        'boot' =\u003e [\n            SomeInterceptor::class,\n        ]\n    ],\n];\n```\n\n## Testing\n\n```bash\ncomposer test\n```\n\n```bash\ncomposer psalm\n```\n\n```bash\ncomposer cs\n```\n\n## Changelog\n\nPlease see [CHANGELOG](CHANGELOG.md) for more information on what has changed recently.\n\n## License\n\nThe MIT License (MIT). Please see [License File](LICENSE) for more information.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fspiral-packages%2Flivewire","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fspiral-packages%2Flivewire","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fspiral-packages%2Flivewire/lists"}