PHPackages                             yanah/laravel-kwik-crud - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Framework](/categories/framework)
4. /
5. yanah/laravel-kwik-crud

ActiveLibrary[Framework](/categories/framework)

yanah/laravel-kwik-crud
=======================

A Laravel package designed to streamline and accelerate development. Let's make it 'kwik' (quick)

v1.5.6(2mo ago)082MITPHPPHP &gt;=7.4CI passing

Since Dec 10Pushed 2mo ago1 watchersCompare

[ Source](https://github.com/smzapp/yanah-laravel-kwik-crud)[ Packagist](https://packagist.org/packages/yanah/laravel-kwik-crud)[ RSS](/packages/yanah-laravel-kwik-crud/feed)WikiDiscussions main Synced 1mo ago

READMEChangelog (2)Dependencies (2)Versions (31)Used By (0)

Yanah Laravel "Kwik" CRUD Package
=================================

[](#yanah-laravel-kwik-crud-package)

Description
-----------

[](#description)

This package is built to ease the work developers do by streamlining the process of scaffolding CRUD operations. It integrates seamlessly with Laravel, Inertia, and Vue.js 3, reducing boilerplate and simplifying the creation of CRUD functionality.

Discord
=======

[](#discord)

To collaborate, please join here:

Overview
--------

[](#overview)

- Stack Used
- Installation &amp; Configurations
- Run the application
- Package Command/s
- CRUD Implementation

> I. CRUD (Create)
> II. CRUD (LIST)
> III. CRUD (EDIT/UPDATE)
> IV. CRUD (SHOW)

- Customize Pages (CRUD)

> Insert Components before / after CRUD Pages (List, Edit, Create)
> Customize Form fields (Create/Edit)

- Additional Security
- CRUD Lifecycle
- Overriding CRUD controller method
- Before &amp; After Create (CRUD)
- Before &amp; After Update (CRUD)

Stack Used
----------

[](#stack-used)

- [Inertia 2.0](https://inertiajs.com/)
- [Vue 3](https://vuejs.org/)
- [Prime Vue 4](https://primevue.org/vite/)
- Reactjs (Coming soon)

Installation &amp; Configurations
---------------------------------

[](#installation--configurations)

To install the package, follow these steps:

```
$ composer require yanah/laravel-kwik-crud
```

```
$ php artisan kwik:install
```

- The default scafold is vuejs. We'll use reactjs soon.
- `kwik:install --client=reactjs`, Install for reactjs (SOON)

Add `KwikServiceProvider` to the providers array in your `config/app.php`:

```
'providers' => [
    // Other providers...
    Yanah\LaravelKwik\KwikServiceProvider::class,
]
```

In `app/Http/Kernel.php`, ensure that the `HandleInertiaRequests` middleware is added under web middleware groups.

```
protected $middlewareGroups = [
    'web' => [
        \App\Http\Middleware\HandleInertiaRequests::class,
        // other middlewares...
    ],
];
```

Publish kwik configurations

`$ php artisan vendor:publish --tag=kwikconfig`

After this, new files will be added in `config`

Install Front-end dependencies:

`$ npm install vue@latest @fortawesome/fontawesome-free primevue @primevue/themes primeicons @primevue/forms`

In `vite.config.js` alias, add `@kwik`

```
resolve: {
    alias: {
        '@kwik': path.resolve(__dirname, 'vendor/yanah/laravel-kwik-crud/src/client/vuejs'), // use reactjs for react
    },
},
```

In `tailwind.config.js` alias, add this line.

```
content: [
    // More contents here
    'vendor/yanah/laravel-kwik-crud/src/client/vuejs/**/*.vue',
],
```

Run the application
-------------------

[](#run-the-application)

Check `tailwind.config.js` configuration

> Make sure to implement or use `primevue` in `app.ts`[![Frontend Configurations](https://camo.githubusercontent.com/b30ef310ecc2975da2d19e2dbaef71655607d6abc91e9ec5b5e638d47774b2aa/68747470733a2f2f692e696d6775722e636f6d2f714b6a616c586b2e706e67)](https://camo.githubusercontent.com/b30ef310ecc2975da2d19e2dbaef71655607d6abc91e9ec5b5e638d47774b2aa/68747470733a2f2f692e696d6775722e636f6d2f714b6a616c586b2e706e67)

`$ npm run dev`

`$ php artisan serve`

Package Commands
----------------

[](#package-commands)

Execute CRUD automatically

```
$ php artisan kwik:crud {name} {--only=}
```

Check the flags below:

`name` - refers to your model name. It should be capitalized &amp; in singular form.

`--only=`:

- `crudfiles` - Only the ModelList.php, ModelCreate.php, ModelEdit.php will be generated
- `controller` - Only the {Model}Controller will be generated
- `model` - Only the Model will be generate

Example:

```
$ php artisan kwik:crud Post --only=crudfiles
```

I. CRUD (Create)
----------------

[](#i-crud-create)

Populate form with fields inside `prepareCreateForm()`:

Example:

```
$this->formgroup->addGroup('users', [
    'tab' => true,
    'label' => 'Users',
]);

$this->formgroup->addField('first_name', [
    'label' => 'Samuel',
    'type' => 'text'
]);
```

---

In creating of a form, configure `Crud\\{Model}Create.php` ### First, in prepareCreateForm(), Add group

[](#first-in-preparecreateform-add-group)

Use the following syntax to add a group:

```
$this->formgroup->addGroup('GROUP_NAME_UNIQUE', [
    'tab' => boolean,
    'label' => string,
]);
```

### Second, Add field. Here is the syntax:

[](#second-add-field-here-is-the-syntax)

```
$this->formgroup->addField('FIELD_NAME', $attributes);
```

**Note:** The `type` attribute serves as the key to determine what input type we'll implement.

$attributes (Properties)
------------------------

[](#attributes-properties)

 Types:
--------

[](#-types-)

- text
- input Group
- textarea
- switch
- checkbox
- radio
- select
- select\_group
- calendar: date &amp; time
- autocomplete
- custom\_file
- custom\_html

```
**Text** $attributes example:
[
    'label' => 'Post Title',
    'type' => 'text'
]

**Input Group** $attributes example:
[
    'type' => 'input_group',
    'label' => 'Address',
    'placeholder' => 'Type your address',
    'group_icon' => 'pi pi-address-book'
]

- group_icon is referred here: https://primevue.org/icons/

**Textarea** $attributes example:
[
    'label' => 'Post Body',
    'type' => 'textarea',
    'rows' => 4
]
**Switch** $attributes example:
[
    'label' => 'Billing details',
    'type' => 'switch'
]

**Checkbox**  $attributes example:
[
    'type' => 'checkbox',
    'is_boolean' => true, // if you need to return the checkbox as boolean, else string.
    'value' => old('CHECKBOX_ITEM', false),
    'label' => 'Your label',
    'class_item' => 'mb-5'
]

**Radio** $attributes example:
[
    'label' => 'Business Options',
    'type' => 'radio',
    'options' => [
        ['label' => 'Option 1', 'value' => 'option1'],
        ['label' => 'Option 2', 'value' => 'option2'],
        ['label' => 'Option 3', 'value' => 'option3'],
    ]
]

**Select** $attributes example:
[
    'label' => 'Business category',
    'type' => 'select',
    'options' => [
        ['label' => 'Option 1', 'optionValue' => 'option1'], // note: optionValue should be string
        ['label' => 'Option 2', 'optionValue' => 'option2'],
        ['label' => 'Option 3', 'optionValue' => 'option3'],
    ]
]

**Select Group** $attributes example:
[
    'type' => 'select_group',
    'label' => 'Service Group',
    'placeholder' => 'List of Services',
    'required' => true,
    'options' => [
        [
            'label' => 'First group',
            'items' => [
                [ 'label' => 'First1', 'optionValue' => 'first1'],  // note: optionValue should be string
                [ 'label' => 'First2', 'optionValue' => 'first2'],
                [ 'label' => 'First3', 'optionValue' => 'first3'],
            ],
        ],
    ]
];

**Calendar** $attributes example:
[
    'label' => 'business Calendar',
    'type' => 'calendar'
]

To set time only, configure inputProps:
[
    'type' => 'calendar',
    'label' => 'Time only',
    'inputProps' => [
        'timeOnly' => true,
        'hourFormat' => '12'
    ]
]

See more attributes here: https://primevue.org/datepicker/#time

**Custom html**
- If you wan to add a custom html:
[
    'type' => 'custom_html',
    'value' => function() {
        return 'Read here.';
    }
]
```

Autocomplete input
------------------

[](#autocomplete-input)

Example:

```
[
    'type'    => 'autocomplete',
    'required' => true,
    'label'   => 'Search me',
    'default_query_results' => [
        ['label' => 'test', 'value' => 'this'],
        ['label' => 'test2', 'value' => 'this2'],
    ],
    'api_endpoint' => '/post/search'
]
```

PropertyTypeDescription`default_query_results``array`Automatically populates values to be searched if an API fetch is not required.`api_endpoint``string | null`Defines the API endpoint. You should have a `/post/search` route to handle the request and then the response must match the data structure of `default_query_results`.Creating custom vue file
------------------------

[](#creating-custom-vue-file)

Add custom vue file into the field.

```
[
    'type'  => 'custom_file',
    'source' => '@/Components/CustomVueFile.vue' // This is relative to resources/js/Components directory
]
```

- `source` - All fileds should be saved inside `Components` folder.

Props:

`attributes` - All of the array values above will serve as attributes.

Emit

`@updateFieldValue` - This will update the value and be passed as payload.

Example:

```

    Input Something

const props = defineProps({
    attributes: Object,
    fieldName: String
})
const emit = defineEmits(['updateFieldValue']);
function updateInput(event) {
    emit('updateFieldValue', props.fieldName, event.target.value);
}

```

**More Attributes:**

```
[
    'helper_text' => 'Sample text',

    'value' => 'ANY', // we attached this for every field for edit page purposes.

    'wrapperProps' => [
        // We may add bind to the wrapper of label & input
        // example: 'class' => 'bg-danger flex-row'
    ],

    'labelProps' => [
        // Cutomize or add styles on label
        // example: 'class' => 'text-sm'
    ],

    'inputProps' => [
        // Cutomize or add styles on Input Fields
        // example: 'class' => 'bg-danger w-full'
    ],

    'tooltip_label' => 'You may want to add tooltip for label. Icon is question mark.'
]
```

(To customize fields proceed to the bottom.)

\*\*\* Validations \*\*\*

Validations are defined in `$validationRules`.

```
protected $validationRules = [
    // Add validations here.
];
```

II. CRUD (LIST)
---------------

[](#ii-crud-list)

CRUD List is configured in `Crud\{Model}List.php`

### A. Two options how we display the table

[](#a-two-options-how-we-display-the-table)

**First**, Through Pagination.

Use `BodyPaginatorInterface` as interface, then add the `responseBodyPaginator()`.
It should look like this:

```
class {Model}List implements ControlCrudInterface, BodyPaginatorInterface
{
    public function responseBodyPaginator(Builder $query) : LengthAwarePaginator
    {
        // you may customize the query here.
        return $query->paginate($this->perPage);
    }
}
```

**Second**, We may want to display all response data.

Use `BodyCollectionInterface` as interface, then add the `responseBodyCollection()`
It should look like this:

```
class {Model}List implements ControlCrudInterface, BodyCollectionInterface
{
    public function responseBodyCollection(Builder $query) : Collection
    {
        return $query->get()->map(function($item) {
            $item->primary = $item->title;  // customized main text
            $item->secondary = $item->body; // description
            return $item;
        });
    }
}
```

or, you may customize the row using html codes by adding `rawHtml`.

```
public function responseBodyCollection(Builder $query) : Collection
{
    return $query->get()->map(function($item) {
        $item->rawHtml = 'Custom html here'; // Add this property
        return $item;
    });
}
```

### B. Define View

[](#b-define-view)

We have two options of how our list should look like:

`ListTemplateViewEnum::TABLELIST` or `ListTemplateViewEnum::LISTITEM`

- First, `TABLELIST` view contains pagination which requires `BodyPaginatorInterface` interface.
- Second, `LISTITEM` view displays all list it is attached to `BodyCollectionInterface`.

### C. Toggle Visibility

[](#c-toggle-visibility)

In your `\App\CrudKwik\DIR\{Model}List.php` file, insert `toggleVisibility` method

```
use Yanah\LaravelKwik\Crud\CrudListControl;

public function toggleVisibility(CrudListControl $control) : array
{
    $control->set('showSearch', true); // add more below

    return $control->get()->toArray();
}
```

To toggle action buttons:

```
$control->set('showSearchBar', false);
$control->updateAction('edit', true);
$control->updateAction('delete', true);
```

APIs:

- `showSearchBar`: boolean - wrapper of add button, search and summary
- `showSearch`: boolean - toggle display search input
- `showPrintPdf`: boolean - toggle pdf print button (WIP)
- `showAddButton`: boolean - toggle Add button
- `showListSummary`: boolean - This shows the summary list of records in table list
- `actions`: array - toggle action buttons (preview, edit, delet).

Available toggle controls:

```
'showSearchBar' => true,
'showSearch'    => true,
'showPrintPdf'  => false,
'showAddButton' => true,
'showListSummary' => true,
'actions' => [
    'preview' => true,
    'edit' => true,
    'delete' => true,
]
```

### D. Handle Search functionality

[](#d-handle-search-functionality)

Search functionality is visible only on pagination list and `$control->set('showSearch', true);`

```
public function search(Builder $query, string $q) : Builder
{
    return $query->where('FIELD', $q);
}
```

III. CRUD (EDIT/UPDATE)
-----------------------

[](#iii-crud-editupdate)

We'll reuse the fields we defined in `prepareCreateForm()`.

We update those in `prepareEditForm()`.

```
$this->formgroup->editField('GROUP_NAME', 'FIELD_NAME', $attributes); // pattern
```

For `$attributes`, refer to **$attributes (Properties)** above.

Example: ```
$this->formgroup->editField('details', 'post_title', [
    'label' => 'Post Title (Edited)',
    'value' => old('post_title', $post->title)
]);
```

Or the details:

```
$this->formgroup->editDetails(string $groupName, array $details);
```

(To customize fields proceed to the bottom.)

\*\*\* Validations \*\*\*

Check method `getValidationRules` to modify validations added in `{Model}Create.php`

```
public function getValidationRules() {}
```

IV. CRUD (SHOW)
---------------

[](#iv-crud-show)

From your controller, customize the display based on the data.

Expected return:

```
[
    'data' => $data, // This will be shown on the table
    'except' => [] // list down the fields you don't want to display.
];
```

Customization:

You may add vue files before or after the table:

```
public function getShowItem(Builder $query, $fields = ['*'], $id)
{
    $this->setPageWrapperItems([
        'prepend' => '@/Components/SampleLorem.vue', // Before the table
        'append'  => '@/Components/SampleLorem.vue', // This will be shown after the table
    ]);
    // More codes below
}
```

```

const emit = defineEmits(['toggleShowTable']); // add this

```

Customize Pages (CRUD)
----------------------

[](#customize-pages-crud)

### Insert Components before / after CRUD Pages (List, Edit, Create)

[](#insert-components-before--after-crud-pages-list-edit-create)

Implement `PageAffixInterface` in `Crud\{Model}Create.php`, `Crud\{Model}Edit.php`, `Crud\{Model}List.php`and define the components to be inserted (prepend / append).

```
use Yanah\LaravelKwik\App\Contracts\PageAffixInterface;

class {CrudClass} extends KwikForm implements PageAffixInterface
{
    public function defineAttributes(): array
    {
        return [
            'prepend' => '@/Components/YOUR_FILE_HERE.vue',
            'append'  => '@/Components/YOUR_FILE_HERE.vue'
        ];
    }
}
```

`prepend` &amp; `append` have available api:

```
import { usePage } from '@inertiajs/vue3';
const { props: pageProps } = usePage();
console.log(pageProps.pageWrapper);
```

Example:

```
//@/Components/YOUR_FILE_HERE.vue
const emit = defineEmits(['updateCrudList']); // Make sure to define updateCrudList.

const ChangeListItems = () => {
  router.visit(`URL`, {
    method: 'get',
    preserveState: true,
    replace: true,
    onSuccess: (response) => {
      emit('updateCrudList', response.props.crud)
    },
  });
}
```

Customize Form fields (Create/Edit)
-----------------------------------

[](#customize-form-fields-createedit)

You may want to wrap fields.

Example:

```
$this->formgroup->beginWrap('INDEX_KEY', $atributes, $headings);

// Add Fields here

$this->formgroup->endWrap();
```

See `$attributes` below:

```
[
    'class' => 'gap-4 xs:grid-cols-1 sm:grid-cols-1', // cuztomize the cols number as desired
    'style' => 'background:red;'
]
```

See `$headings` (optional) below:

```
[
    'heading' => string,
    'paragraph' => string,
]
```

Additional Security
-------------------

[](#additional-security)

Notice that in `show` &amp; `edit` pages, routes are accessible via id.

You may want to append `uuid` instead.

First, make sure to add `uuid` field in your model and migration.

Next, use the `UuidRestrictionTrait` trait in your controller.
Example:

```
use Yanah\LaravelKwik\Traits\UuidRestrictionTrait;

class {Your}Controller extends KwikController implements PageControlInterface
{
    use UuidRestrictionTrait; // Attach this
}
```

CRUD Persist Lifecycle
----------------------

[](#crud-persist-lifecycle)

`Store`

1. PageControl - Serves as middleware.
2. `beforeStore` - prepare method before storing.
3. Validations - handle validations.
4. Insert Model - updateOrCreate or create
5. `afterStore` - Handle . We may trigger an event after store.

`Update`

1. PageControl - Serves as middleware.
2. `beforeUpdate` - prepare method before storing.
3. Validations - handle validations.
4. Update model
5. `afterUpdate` - Handle . We may trigger an event after store.

Overriding CRUD controller method
---------------------------------

[](#overriding-crud-controller-method)

You may want to override Crud Controller methods and use Laravel CRUD methods:

```
class YourController extends KwikController  implements PageControlInterface
{
    public function create()
    {
        // do something here.

        return parent::create();
    }
}
```

Before &amp; After Create (CRUD)
--------------------------------

[](#before--after-create-crud)

In some cases, you may want to execute something or trigger an event before and after creating of new record. To do this, you have to override `beforeStore()` and `afterStore()` methods.

In your `\App\CrudKwik\DIR\{Model}Create.php` file, insert these lines:

```
use Yanah\LaravelKwik\Services\CrudService;

public function beforeStore(CrudService $crudService) : void
{
    // Change to false if you want to insert validated payloads only.
    $crudService->setShouldIncludeFillable(true);

    $crudService->setIndexOfUpdateCreate([
        // You may want to use updateCreate.
        // Add here the index, example:
        'user_id' => 1 // this will updateCreate based on user_id
    ]);
}

public function afterStore($response)
{
    // Add stuffs

    // response
    return response()->json(['success' => true], 201);
}
```

Before &amp; After Update (CRUD)
--------------------------------

[](#before--after-update-crud)

In your `\App\CrudKwik\DIR\{Model}Edit.php` file, insert these lines:

```
use Yanah\LaravelKwik\Services\CrudService;

public function beforeUpdate(CrudService $crudService) : void
{
    $crudService->setShouldIncludeFillable(true);
    $crudService->setIndexOfUpdateCreate([
        // You may want to use updateCreate.
        // Add here the index
    ]);
}

public function afterUpdate($id)
{
    // trigger event after update

    return response()->json(['success' => true], 201);
}
```

---

**Todo list:**

- Add Test
- Responsiveness
- Validate frontend

That's all. Please feel free to send PR when you found a bug. Hope this package will help you "kwik"en your development. Appreciated!

###  Health Score

41

—

FairBetter than 89% of packages

Maintenance88

Actively maintained with recent releases

Popularity12

Limited adoption so far

Community7

Small or concentrated contributor base

Maturity49

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~22 days

Recently: every ~8 days

Total

21

Last Release

62d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/2d2f4de67557ede589c1eb9427797b268e002b14aed9a36f9167fe5ba2809d8b?d=identicon)[smzapp](/maintainers/smzapp)

---

Top Contributors

[![smzapp](https://avatars.githubusercontent.com/u/11945208?v=4)](https://github.com/smzapp "smzapp (132 commits)")

### Embed Badge

![Health badge](/badges/yanah-laravel-kwik-crud/health.svg)

```
[![Health](https://phpackages.com/badges/yanah-laravel-kwik-crud/health.svg)](https://phpackages.com/packages/yanah-laravel-kwik-crud)
```

###  Alternatives

[codewithdennis/larament

Larament is a time-saving starter kit to quickly launch Laravel 13.x projects. It includes FilamentPHP 5.x pre-installed and configured, along with additional tools and features to streamline your development workflow.

3691.5k](/packages/codewithdennis-larament)[ecotone/laravel

Laravel integration for Ecotone

21307.6k3](/packages/ecotone-laravel)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
