{"id":20059887,"url":"https://github.com/deiucanta/laravel-smart","last_synced_at":"2025-05-05T15:32:03.856Z","repository":{"id":56964920,"uuid":"135179205","full_name":"deiucanta/laravel-smart","owner":"deiucanta","description":"Automatic Migrations, Validation and More","archived":false,"fork":false,"pushed_at":"2018-12-21T12:09:43.000Z","size":63,"stargazers_count":48,"open_issues_count":9,"forks_count":7,"subscribers_count":7,"default_branch":"master","last_synced_at":"2024-04-17T05:45:48.353Z","etag":null,"topics":["fields","laravel","migrations","model","validation"],"latest_commit_sha":null,"homepage":"","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/deiucanta.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2018-05-28T15:30:43.000Z","updated_at":"2023-07-14T22:05:12.000Z","dependencies_parsed_at":"2022-08-21T09:20:34.957Z","dependency_job_id":null,"html_url":"https://github.com/deiucanta/laravel-smart","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/deiucanta%2Flaravel-smart","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/deiucanta%2Flaravel-smart/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/deiucanta%2Flaravel-smart/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/deiucanta%2Flaravel-smart/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/deiucanta","download_url":"https://codeload.github.com/deiucanta/laravel-smart/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":224452789,"owners_count":17313668,"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":["fields","laravel","migrations","model","validation"],"created_at":"2024-11-13T13:10:31.292Z","updated_at":"2024-11-13T13:10:31.998Z","avatar_url":"https://github.com/deiucanta.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Laravel Smart\n\n![Laravel Smart Demo](https://i.imgur.com/MTFSm9b.gif)\n\n**Do not use this package in production!**\n\n1. This is a proof of concept. (update: this package is used successfully in an app that has 25 models)\n2. The code is not unit tested. (update: thanks to @robsontenorio we have basic unit testing)\n3. The API is not stable.\n\nI release this alpha version to get feedback on the API and to make sure I'm not missing important use cases.\n\nAlso, I cannot build this alone! I'm more than happy to receive help from the community. Don't be shy!\n\n- join the discussions (even if it's not your issue)\n- improve the documentation (if you found something hard to understand, raise an issue, send a pull-request, etc)\n- contribute with code (I will guide you as much as needed)\n\n---\n\n## Idea\n\nIf you define the fields in the model, you can get:\n\n- **automatic migrations**\n- automatic validation on `save()`\n- grouped field definition (name, schema type, casting, fillable/guarded, validation rules, schema modifiers, schema indexes)\n\n```php\n\u003c?php\n\nnamespace App;\n\nuse Deiucanta\\Smart\\Field;\nuse Deiucanta\\Smart\\Model;\n\nclass Product extends Model\n{\n    public function fields()\n    {\n        return [\n            Field::make('id')-\u003eincrements(),\n            Field::make('sku')-\u003estring()-\u003efillable()-\u003erequired()-\u003eunique()-\u003elabel(\"Sku Number\"),\n            Field::make('name')-\u003estring()-\u003efillable()-\u003erequired(),\n            Field::make('price')-\u003edecimal(6, 2)-\u003efillable()-\u003erequired()-\u003emin(0),\n            Field::make('description')-\u003etext()-\u003efillable()-\u003enullable(),\n            Field::make('created_at')-\u003etimestamp()-\u003enullable()-\u003eindex(),\n            Field::make('updated_at')-\u003etimestamp()-\u003enullable()-\u003eindex(),\n        ];\n    }\n}\n```\n\n## Installation\n\nTo install the package, just run:\n\n```\ncomposer require deiucanta/smart\n```\n\n## Usage\n\nCreate a Smart model:\n\n```\nphp artisan smart:model Product\n```\n\nInclude the model in the configuration file (`config/smart.php`):\n\n\u003e Note: this is now done automatically when you create the model.\n\n```php\n\u003c?php\n\nreturn [\n    'models' =\u003e [\n        \\App\\Product::class,\n    ]\n];\n```\n\nCreate a Smart migration:\n\n```\nphp artisan smart:migration\n```\n\nYou should be able to see a new migration in your migration directory. To apply the migration, you just run `php artisan migrate` as usual.\n\nYou will find a new file called `smart.json` in the `database` directory of your app. That is where the package stores the current state of the database/models. If you delete that file and run `php artisan smart:migration`, it will create a new migration as if the schema was empty.\n\n## API\n\nThese are the primitives with which you should be able to create any kind of field. However, there are some smarter methods which you can use.\n\n### Base methods\n\n| Method | Description |\n| - | - |\n| `type($type, $args)` | Set the `type` to be used in migrations |\n| `cast($cast)` | Set the `cast` type |\n| `rule($rule)` | Add a validation rule (Laravel format) |\n| `guarded()` | Make the field guarded |\n| `fillable()` | Make the field fillable |\n| `index()` | Add a simple index on this field in migrations |\n| `unique($where_closure = null)` | Add a unique index in migrations and a smart validation rule that ignores the current model id |\n| `primary()` | Add a primary key on this field in migrations |\n| `default($default)` | Set the default value in migrations and set the model attribute when you instantiate the model |\n| `nullable()` | Make the field nullable in migrations and also add the `nullable` validation rule |\n| `unsigned()` | Add the `unsigned` modifier in migrations |\n| `label($value)` | Set the field label for validation errors bag |\n\n### Type Methods\n\nThese are Laravel types that are currently supported.\n\n| Method | Type | Cast | Rule |\n| - | - | - | - |\n| `bigIncrements()` | `bigIncrements` | `integer` | - |\n| `bigInteger()` | `bigInteger` | `integer` | `numeric` |\n| `binary()` | `binary` | - | - |\n| `boolean()` | `boolean` | `boolean` | `boolean` |\n| `char($size = null)` | `char` | - | - |\n| `date()` | `date` | `date` | - |\n| `dateTime()` | `dateTime` | `datetime` | - |\n| `dateTimeTz()` | `dateTimeTz` | `datetime` | - |\n| `decimal($total, $decimal)` | `decimal` | `double` | `numeric` |\n| `double($total, $decimal)` | `double` | `double` | `numeric` |\n| `enum($values)` | `enum` | - | `in:value1,value2,...` |\n| `float($total, $decimal)` | `float` | `float` | `numeric` |\n| `geometry()` | `geometry` | - | - |\n| `geometryCollection()` | `geometryCollection` | - | - |\n| `increments()` | `increments` | `integer` | - |\n| `integer()` | `integer` | `integer` | `numeric` |\n| `ipAddress()` | `ipAddress` | - | `ip` |\n| `json()` | `json` | `array` | `array` |\n| `jsonb()` | `jsonb` | `array` | `array` |\n| `lineString()` | `lineString` | - | - |\n| `longText()` | `longText` | - | - |\n| `macAddress()` | `macAddress` | - | - |\n| `mediumIncrements()` | `mediumIncrements` | `integer` | - |\n| `mediumInteger()` | `mediumInteger` | `integer` | `numeric` |\n| `mediumText()` | `mediumText` | - | - |\n| `multiLineString()` | `multiLineString` | - | - |\n| `multiPoint()` | `multiPoint` | - | - |\n| `multiPolygon()` | `multiPolygon` | - | - |\n| `point()` | `point` | - | - |\n| `polygon()` | `polygon` | - | - |\n| `smallIncrements()` | `smallIncrements` | `integer` | - |\n| `smallInteger()` | `smallInteger` | `integer` | `numeric` |\n| `softDeletes()` | `softDeletes` | `datetime` | - |\n| `softDeletesTz()` | `softDeletesTz` | `datetime` | - |\n| `string($size = null)` | `string` | - | - |\n| `text()` | `text` | - | - |\n| `time()` | `time` | - | - |\n| `timeTz()` | `timeTz` | - | - |\n| `timestamp()` | `timestamp` |  `datetime` | - |\n| `timestampTz()` | `timestampTz` | `datetime` | - |\n| `tinyIncrements()` | `tinyIncrements` | `integer` | - |\n| `tinyInteger()` | `tinyInteger` | `integer` | `numeric` |\n| `unsignedBigInteger()` | `unsignedBigInteger` | `integer` | `numeric` |\n| `unsignedDecimal($total, $decimal)` | `unsignedDecimal` | `double` | `numeric` |\n| `unsignedInteger()` | `unsignedInteger` | `integer` | `numeric` |\n| `unsignedMediumInteger()` | `unsignedMediumInteger` | `integer` | `numeric` |\n| `unsignedSmallInteger()` | `unsignedSmallInteger` | `integer` | `numeric` |\n| `unsignedTinyInteger()` | `unsignedTinyInteger` | `integer` | `numeric` |\n| `uuid()` | `uuid` | - | - |\n| `year()` | `year` | `integer` | `numeric` |\n\nHere are some custom types just as an example of what can be done.\n\n| Method | Type | Cast | Rule |\n| - | - | - | - |\n| `email()` | `string` | - | `email` |\n| `url()` | `string` | - | `url` |\n| `slug()` | `string` | - | `regex:/^[a-z0-9]+(?:-[a-z0-9]+)*$/` |\n\n### Rule Methods\n\n| Method | Type | Cast | Rule |\n| - | - | - | - |\n| `accepted()` | - | - | `accepted` |\n| `activeUrl()` | - | - | `active_url` |\n| `after($date)` | - | - | `after:$date` |\n| `afterOrEqual($date)` | - | - | `after_or_equal:$date` |\n| `alpha()` | - | - | `alpha` |\n| `alphaDash()` | - | - | `alpha_dash` |\n| `alphaNum()` | - | - | `alpha_num` |\n| `array()` | - | - | `array` |\n| `bail()` | - | - | `bail` |\n| `before($date)` | - | - | `before:$date` |\n| `beforeOrEqual($date)` | - | - | `before_or_equal:$date` |\n| `between($min, $max)` | - | - | `between:$min,$max` |\n| `confirmed()` | - | - | `confirmed` |\n| `dateEquals($date)` | - | - | `date_equals:$date` |\n| `dateFormat($format)` | - | - | `date_format:$format` |\n| `different($field)` | - | - | `different:$field` |\n| `digits($value)` | - | - | `digits:$value` |\n| `digitsBetween($min, $max)` | - | - | `digits_between:$min,$max` |\n| `exists($table [, $column [, $where_closure ]])` | - | - | `Rule::exists(...)` |\n| `filled()` | - | - | `filled` |\n| `gt($field)` | - | - | `gt:$field` |\n| `gte($field)` | - | - | `gte:$field` |\n| `in($values)` | - | - | `Rule::in($values)` |\n| `inArray($field)` | - | - | `in_array:$field` |\n| `ip()` | - | - | `ip` |\n| `ipv4()` | - | - | `ipv4` |\n| `ipv6()` | - | - | `ipv6` |\n| `lt($field)` | - | - | `lt:$field` |\n| `lte($field)` | - | - | `lte:$field` |\n| `max($value)` | - | - | `max:$value` |\n| `min($value)` | - | - | `min:$value` |\n| `notIn($values)` | - | - | `value` |\n| `notRegex($pattern)` | - | - | `not_regex:$pattern` |\n| `numeric()` | - | - | `numeric` |\n| `present()` | - | - | `present` |\n| `regex($pattern)` | - | - | `regex:$pattern` |\n| `required()` | - | - | `required` |\n| `requiredIf($field, $value)` | - | - | `required_if:$field,$value` |\n| `requiredUnless($field, $value)` | - | - | `required_unless:$field,$value` |\n| `requiredWith($fields)` | - | - | `required_with:$fields[0],$fields[1],...` |\n| `requiredWithAll($fields)` | - | - | `required_with_all:$fields[0],$fields[1],...` |\n| `requiredWithout($fields)` | - | - | `required_without:$fields[0],$fields[1],...` |\n| `requiredWithoutAll($fields)` | - | - | `required_without_all:$fields[0],$fields[1],...` |\n| `same($field)` | - | - | `same:$field` |\n| `timezone()` | - | - | `timezone` |\n\n## Extra\n\n- an article I wrote about this idea a couple of months ago (https://medium.com/@deiucanta/make-laravel-fluent-again-with-smartfields-7d543e725365)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdeiucanta%2Flaravel-smart","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdeiucanta%2Flaravel-smart","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdeiucanta%2Flaravel-smart/lists"}