laravel-addresses/docs/customization.md

189 lines
4.6 KiB
Markdown
Raw Permalink Normal View History

2026-04-14 08:20:42 +00:00
# Customization
## Custom Model Classes
You can extend any of the three package models with your own. This is useful for adding custom methods, relationships, accessors or validation logic.
### 1. Create your custom model
```php
// app/Models/CustomAddress.php
namespace App\Models;
use Blax\Addresses\Models\Address as BaseAddress;
class CustomAddress extends BaseAddress
{
public function getFullAddressAttribute(): string
{
return "{$this->street}, {$this->postal_code} {$this->city}, {$this->country_code}";
}
public function geocode(): self
{
// your geocoding logic
return $this;
}
}
```
### 2. Update the config
```php
// config/addresses.php
'models' => [
'address' => \App\Models\CustomAddress::class,
'address_link' => \Blax\Addresses\Models\AddressLink::class,
'address_assignment' => \Blax\Addresses\Models\AddressAssignment::class,
],
```
The package resolves all model classes through `config('addresses.models.…')`, so your custom class will be used everywhere — in relationships, service methods, and traits.
### Example: Custom AddressLink
```php
namespace App\Models;
use Blax\Addresses\Models\AddressLink as BaseAddressLink;
class CustomAddressLink extends BaseAddressLink
{
protected static function booted()
{
static::creating(function (self $link) {
// Auto-set label from type if not provided
if (! $link->label) {
$link->label = $link->type->label();
}
});
}
}
```
```php
'models' => [
'address_link' => \App\Models\CustomAddressLink::class,
],
```
---
## Custom Table Names
Change the table names if they collide with existing tables in your application:
```php
// config/addresses.php
'table_names' => [
'addresses' => 'company_addresses',
'address_links' => 'company_address_links',
'address_assignments' => 'company_address_assignments',
],
```
**Important:** Update the published migration to match these names before running `php artisan migrate`. The migration stub reads from the config, so if you publish the config first and then the migration, the table names will be picked up automatically.
---
## Custom Default Link Type
Change the default `AddressLinkType` applied when adding an address without specifying a type:
```php
// config/addresses.php
'default_link_type' => \Blax\Addresses\Enums\AddressLinkType::Home,
```
Now `$user->addAddress(['city' => 'Vienna'])` will use `Home` instead of `Other`.
---
## Using the Meta Column
All three models (`Address`, `AddressLink`, `AddressAssignment`) include a `meta` JSON column for storing arbitrary data. The column is cast to `object`.
```php
// On addresses — store extra data
$link = $user->addAddress([
'street' => 'Main Street 1',
'city' => 'Vienna',
'meta' => [
'plus_code' => '8FWR4HCJ+XX',
'what3words' => 'index.home.raft',
'timezone' => 'Europe/Vienna',
],
]);
// On address links — store context about the relationship
$link = $user->addAddress(['city' => 'Vienna'], AddressLinkType::Office, [
'meta' => [
'department' => 'Engineering',
'access_code' => '4521',
],
]);
// On address assignments — store context about the assignment
$job->assignAddressLink($link, 'delivery', [
'meta' => [
'time_window' => '09:00-12:00',
'priority' => 'express',
],
]);
// Reading meta
$address->meta->plus_code; // "8FWR4HCJ+XX"
$link->meta->department; // "Engineering"
$assignment->meta->time_window; // "09:00-12:00"
```
---
## Model Bindings
The service provider registers model bindings so that resolving a package model through the container returns the configured (possibly customised) class:
```php
// Always resolves to your custom class if configured
$address = app(\Blax\Addresses\Models\Address::class);
```
This means type-hinting the base class in dependency injection will automatically resolve to your custom model.
---
## Extending the AddressService
The `AddressService` is registered as a singleton. To add custom methods, extend it and rebind:
```php
namespace App\Services;
use Blax\Addresses\Services\AddressService;
use Blax\Addresses\Models\Address;
class CustomAddressService extends AddressService
{
public function geocode(Address $address): Address
{
// your geocoding implementation
return $address;
}
}
```
In a service provider:
```php
$this->app->singleton(
\Blax\Addresses\Services\AddressService::class,
\App\Services\CustomAddressService::class
);
```
The `address()` helper and all DI injection will now resolve your custom service.