{"id":20499841,"url":"https://github.com/sherlockode/crudbundle","last_synced_at":"2026-06-30T22:01:22.700Z","repository":{"id":171569329,"uuid":"647331200","full_name":"sherlockode/CrudBundle","owner":"sherlockode","description":null,"archived":false,"fork":false,"pushed_at":"2026-03-23T22:25:13.000Z","size":104,"stargazers_count":1,"open_issues_count":0,"forks_count":1,"subscribers_count":5,"default_branch":"main","last_synced_at":"2026-03-24T18:17:33.631Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"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/sherlockode.png","metadata":{"files":{"readme":"README.md","changelog":null,"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-05-30T14:47:30.000Z","updated_at":"2024-04-13T12:47:48.000Z","dependencies_parsed_at":null,"dependency_job_id":"38d9ab15-12d3-4e59-a049-aa516375c11d","html_url":"https://github.com/sherlockode/CrudBundle","commit_stats":null,"previous_names":["sherlockode/crudbundle"],"tags_count":3,"template":false,"template_full_name":null,"purl":"pkg:github/sherlockode/CrudBundle","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sherlockode%2FCrudBundle","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sherlockode%2FCrudBundle/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sherlockode%2FCrudBundle/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sherlockode%2FCrudBundle/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sherlockode","download_url":"https://codeload.github.com/sherlockode/CrudBundle/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sherlockode%2FCrudBundle/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34984784,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-30T02:00:05.919Z","response_time":92,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"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":[],"created_at":"2024-11-15T18:18:47.901Z","updated_at":"2026-06-30T22:01:22.675Z","avatar_url":"https://github.com/sherlockode.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# SherlockodeCrud Bundle\n\n----\n\n[ ![](https://img.shields.io/packagist/l/sherlockode/crud-bundle)](https://packagist.org/packages/sherlockode/crud-bundle \"License\")\n[ ![](https://img.shields.io/packagist/v/sherlockode/crud-bundle)](https://packagist.org/packages/sherlockode/crud-bundle \"Version\")\n[ ![](https://poser.pugx.org/sherlockode/crud-bundle/downloads)](https://packagist.org/packages/sherlockode/crud-bundle \"Total Downloads\")\n\n---\n\n## Overview\n\n----\nThis bundle generate basic crud.\n\n----\n\n## Installation\n\n----\nInstall the bundle with composer:\n\n```bash\n$ composer require sherlockode/crud-bundle\n```\n\nGenerate a basic grid view:\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            config:\n                class: App\\Entity\\User\n                form: App\\Form\\Type\\UserType\n            grid:\n                fields:\n                    name:\n                        label: crud.user.name #translation key\n                    surname:\n                        label: crud.user.surname\n                    is_active:\n                        label: crud.user.active\n                        type: boolean # you can define a specific type if you need. See the section bellow \n                    created_at:\n                        label: crud.user.created_at\n                        type: date\n                        options:\n                            format: d-m-Y # you can customise the date format\n                actions: \n                    update: ~\n                    delete: ~\n                settings: \n                    page_size: 20 #the number of elements by page, 20 by default\n```\n\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user \n    type: sherlockode_crud.resource\n    prefix: /admin\n```\n\n---\n## Customisation \n\n#### You need custom action or custom field? You can easily define your own\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    templates:\n        action:\n            up_and_down: '@SherlockodeCrud/common/grid/action/up_and_down.html.twig'\n        field:\n            custom_field: '@SherlockodeCrud/common/grid/field/custom_field.html.twig'\n\n    # now, you can use them like this :\n    crud: \n        user:\n            # ...\n            grid:\n                fields:\n                    surname:\n                        label: crud.user.email\n                        type: custom_field\n                actions:\n                    up_and_down: ~\n```\n\n#### You need the object instead of a property value in the grid?  \n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud: \n        user:\n            # ...\n            grid:\n                fields:\n                    surname:\n                        label: crud.user.email\n                        path: . #use '.' to send the object instead of the property value\n```\n\n#### You need to add filters on your grid?\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            # ...\n            grid:\n                filters:\n                    name:\n                        type: string\n                        label: Label or custom translation key\n```\n\n#### You need to create a custom query for the grid?\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            # ...\n            grid:\n                repository:\n                    method: yourQueryBuilder\n```\n\n- In this example, in the UserRepository, you need to have a function named `yourQueryBuilder`\n- The `yourQueryBuilder` function need to return a `QueryBuilder` object\n\n#### You need filters?\nThe bundle has basic filters\n- String\n- Boolean\n- Float\n- Money\n- Date\n- DateRange\n- Entity\n\nEntity filter need more configuration:\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            # ...\n            grid:\n                filters:\n                    category:\n                        type: entity\n                        options:\n                            class: App\\Entity\\Category\n                            choice_label: name\n```\n\nTo add some filters: \n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            # ...\n            grid:\n                filters:\n                    name:\n                        type: string #the filter name\n                    createdAt:\n                        type: date_range\n```\n\n#### You need custom filter?\nIf you need a filter that does not exist, create it !\n\nCreate your own filter class and your own filter type class, in this example `MyCustomFilter`.\n`MyCustomFilter` need to implements `FilterInterface`\n\nNow you need to set the template for your new filter:\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    templates:\n        filter:\n            my_custom_filter: 'Grid\\Filter\\my_custom_filter.html.twig'\n    crud:\n        user:\n            # ...\n            grid:\n                filters:\n                    name:\n                        type: my_custom_filter\n```\n\n#### You need to sort your grid?\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            # ...\n            grid:\n                sorting:\n                    name: asc\n                    surname: desc\n```\n\n\n#### You need to let the user choose the order?\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            grid:\n                fields:\n                    name:\n                        label: crud.user.email\n                        sortable: ~ #set the column sortable\n```\n\n#### You need to change the redirection a resource creation or edition?\n\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        redirect_after_create: index \n        redirect_after_update: update \n        base_name: sherlockode_crud\n        resource_name: user \n    type: sherlockode_crud.resource\n    prefix: /admin\n```\nBy default, after a resource creation or edition, you will be redirected to the update action\n\n#### You need a custom template for a route?\n\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        templates: \"User\"\n    type: sherlockode_crud.resource\n    prefix: /admin\n```\n- In your templates project folder, be sure you have the `User` directory. \n- If you need a custom template only for the index action, name it `index.html.twig`, other routes will be rendered with the defaults templates \n\n\n#### You only want to create the index route, not all of them?\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        only: [index]\n    type: sherlockode_crud.resource\n    prefix: /admin\n```\n\n#### You want to create all routes excepted delete?\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        except: [delete]\n    type: sherlockode_crud.resource\n    prefix: /admin\n```\n\n#### You need to check permission before action?\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        permission: true\n    type: sherlockode_crud.resource\n    prefix: /admin\n```\n\nNow make your own voter for each action\n- index\n- create\n- edit\n- delete\n\nThe attribute is prefixed by the `resource_name`. In this example, it's `user_index` \n\n#### You want to send some variable?\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        vars: \n            global:\n                icon: bi bi-person-fill\n```\n\nIn this example, we send an icon to all paths.\n\nIf you want to do this only for a specific path:\n\n```yaml\n# sherlockode_crud_routing.yaml\n\napp_admin_user:\n    resource: |\n        base_name: sherlockode_crud\n        resource_name: user\n        vars: \n            index:\n                icon: bi bi-person-fill\n```\n\n#### You need to remove the delete confirmation page?\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            config:\n                delete_confirmation: false\n```\n\nYou need to add some information in the show view?\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            show:\n                name:\n                    type: string\n                is_active:\n                    type: boolean\n                category.name:\n                    type: string\n                created_at:\n                    type: date\n                    options:\n                        format: d-m-Y\n```\n\nYou need to change the translation domain?\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    translation_domain: yourDomain\n```\n\n\nYou need to disable the translation domain?\n\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    translation_domain: false\n    crud:\n        user:\n            # ...\n            grid:\n                fields:\n                    name:\n                        label: My Name #you can use a translation key or the label value if translation domain is false\n```\n\nIf you need to be more specific, you can disable translation or set a custom for some grids\n```yaml\n# config/packages/sherlockode_crud.yaml\n\nsherlockode_crud:\n    crud:\n        user:\n            config:\n                translation_domain: false #or yourDomain\n```\nIf you set a translation_domain for a grid, the value will replace the global one\n\n#### You need to send data to the views?\nIn ResourceControllerDataEvent, you have several actions : \n- ResourceControllerDataEvent::SHOW\n- ResourceControllerDataEvent::CREATE\n- ResourceControllerDataEvent::UPDATE\n- ResourceControllerDataEvent::DELETE_CONFIRMATION\n\nIn ResourceController, in show, create, update and delete confirmation actions, an even is dispatched before the page is rendered.\n\nIf you need to send data to the view, you can create a listener.\n```php\n# src/EventListener/ResourceListener.php\n\nclass ResourceListener implements EventSubscriberInterface\n{\n    public static function getSubscribedEvents(): array\n    {\n        return [\n            ResourceControllerDataEvent::UPDATE =\u003e 'update',\n        ];\n    }\n\n    public function update(ResourceControllerDataEvent $event): void\n    {\n        // send custom data to the view\n        $event-\u003esetData([]);\n    }\n}\n```\n\nIn the view, the data variable will contain your data sent in the example above.\n\n#### You need to prevent flush?\nIn ResourceControllerEvent, you have several actions :\n- ResourceControllerEvent::BEFORE_CREATE\n- ResourceControllerEvent::BEFORE_UPDATE\n- ResourceControllerEvent::BEFORE_DELETE\n\nIn ResourceController, in create, update and delete actions, an even is dispatched before flush is performed.\n\nIf you need to cancel the flush, you can create a listener\n```php\n# src/EventListener/ResourceListener.php\n\nclass ResourceListener implements EventSubscriberInterface\n{\n    public static function getSubscribedEvents(): array\n    {\n        return [\n            ResourceControllerEvent::BEFORE_UPDATE =\u003e 'update',\n        ];\n    }\n\n    public function update(ResourceControllerDataEvent $event): void\n    {\n        $event-\u003esetCancelProcess(true);\n        \n        // optional message, by default, a translation key is generated \n        // sherlockode_crud.crud_name.update.cancel\n        $event-\u003esetMessage('your message');\n    }\n}\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsherlockode%2Fcrudbundle","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsherlockode%2Fcrudbundle","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsherlockode%2Fcrudbundle/lists"}