laravel-model-tools maintained by malsanyang
Laravel Model Tools
Laravel model utilities for applications that expose UUID references while keeping internal database IDs private.
Features
- Automatic UUID reference generation on model creation and update
reference()andreferenceOrFail()query helpers- Optional reference-based route model binding
- Migration generator for adding a reference column
- Optional
BaseModelwith soft deletes and datetime casts - Laravel package auto-discovery
Requirements
- PHP 8.3 or later
- Laravel 11, 12, or 13
Installation
Install the package with Composer:
composer require malsanyang/laravel-model-tools
Laravel discovers the package service provider automatically.
Publish the configuration file if you want to change the reference column or route model binding behaviour:
php artisan vendor:publish --tag=model-tools-config
Usage
Add the HasReference trait to an Eloquent model:
use Illuminate\Database\Eloquent\Model;
use MalSanyang\ModelTools\Concerns\HasReference;
class Page extends Model
{
use HasReference;
}
Generate and run a migration for the model's table:
php artisan model-tools:reference-migration pages
php artisan migrate
The generated migration adds the following column:
$table->uuid('reference')->nullable()->unique()->after('id');
When a model is created or updated without a reference, the trait assigns a UUID automatically:
$page = new Page;
$page->title = 'About us';
$page->save();
$page->reference;
The trait checks that the configured column exists before assigning a UUID.
Finding Models by Reference
Return the matching model or null:
$page = Page::reference($uuid);
Return the matching model or throw an Eloquent ModelNotFoundException:
$page = Page::referenceOrFail($uuid);
Configuration
The published config/model-tools.php file contains:
return [
'reference_column' => 'reference',
'use_reference_as_route_key' => true,
];
Custom Reference Column
Change reference_column to use a different column throughout the package:
'reference_column' => 'uuid',
The migration command uses the configured column by default. You can also override the generated migration's column explicitly:
php artisan model-tools:reference-migration pages --column=uuid
Ensure the generated column name matches the column resolved by the model.
For a model-specific column, override the trait methods on that model:
class Page extends Model
{
use HasReference;
public static function referenceColumn(): string
{
return 'uuid';
}
public function getRouteKeyName(): string
{
return config('model-tools.use_reference_as_route_key')
? static::referenceColumn()
: parent::getRouteKeyName();
}
}
Route Model Binding
Models using HasReference use the configured reference column for implicit
route model binding by default:
Route::get('/pages/{page}', function (Page $page) {
return $page;
});
Given the default configuration, Laravel resolves {page} using the model's
reference value instead of its internal ID.
Disable this globally if you want Laravel to use the model's normal route key:
'use_reference_as_route_key' => false,
Optional Base Model
Applications that want shared defaults can extend the package base model:
use MalSanyang\ModelTools\Models\BaseModel;
class Page extends BaseModel
{
// Includes HasReference, SoftDeletes, and datetime casts.
}
Using the trait directly is recommended when you want more control over your model's behaviour.
Development
Install the development dependencies:
composer install
Run formatting checks, static analysis, and tests:
composer check
Run the complete CI suite, including Composer validation and the dependency security audit:
composer ci:check
Individual checks are also available:
composer lint:check
composer analyse
composer test
composer audit
Security
Please report vulnerabilities privately by following the instructions in the security policy. Do not disclose security issues through public GitHub issues.
License
Laravel Model Tools is open-source software licensed under the MIT License.