dialloibrahima/laravel-model-media

A lightweight trait for managing media files directly on your Eloquent models, without additional tables. Perfect when you need to attach files to models by simply storing the path as an attribute.

Installs: 0

Dependents: 0

Suggesters: 0

Security: 0

Stars: 0

Watchers: 0

Forks: 0

Open Issues: 0

pkg:composer/dialloibrahima/laravel-model-media

v1.0.0 2026-02-02 23:42 UTC

This package is auto-updated.

Last update: 2026-02-03 00:41:04 UTC


README

Latest Version on Packagist GitHub Tests Action Status Total Downloads PHP Version Laravel Version

A lightweight, zero-boilerplate media management trait for Laravel Eloquent models. Attach files directly to your existing model attributes without adding any extra database tables or complex relationships.

๐Ÿ“‹ Table of Contents

๐Ÿ˜ฐ The Problem

Most media management packages for Laravel (like Spatie MediaLibrary) are powerful but "heavy". They often require:

  • A new media table in your database.
  • Complex Polymorphic relationships.
  • Manual cleanup of files when models are deleted.
  • Overkill for simple use cases where you just want to store a profile picture or a document path directly on a model.

โœจ The Solution

Laravel Model Media keeps it simple. It uses your existing database columns to store file names.

  • โœ… No Extra Tables: Uses the columns you already have.
  • โœ… Automatic Cleanup: Deletes old files when you re-upload or delete the model.
  • โœ… Smart Filenames: Use model attributes or dynamic Closures for naming.
  • โœ… Zero Config: Just add the trait and register your media.

โš–๏ธ Comparison: Spatie MediaLibrary vs. Laravel Model Media

Feature Spatie MediaLibrary Laravel Model Media
Philosophy "One table for everything" "Keep it on the model"
New Tables media (Polymorphic) None
Complexity High (Conversions, Collections) Low (Simple & Fast)
Performance Extra Join/Query for each model Zero extra queries
Setup Migrations + Trait + Interface Trait only
Ideal for Complex CMS, Multiple galleries Profile pics, Single documents, Simple uploads

๐Ÿ“ฆ Installation

composer require dialloibrahima/laravel-model-media

โšก Quick Start

1. Prepare your Model

Add the HasMedia trait and register which column should handle media.

namespace App\Models;

use DialloIbrahima\HasMedia\HasMedia;
use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    use HasMedia;

    protected static function booted()
    {
        self::registerMediaForColumn(
            column: 'profile_photo',    // Your DB column
            directory: 'avatars',       // Storage folder
            fileName: 'id',             // Name file after the user ID
            disk: 'public'              // Optional: storage disk (default is 'public')
        );
    }
}

2. Handle Uploads

Call attachMedia() in your controller.

public function update(Request $request, User $user)
{
    if ($request->hasFile('photo')) {
        $user->attachMedia($request->file('photo'), 'profile_photo');
    }

    return back();
}

3. Retrieve URLs

<img src="{{ $user->getMediaUrl('profile_photo') }}">

๐Ÿ”ง Advanced Usage

Dynamic Filenames via Closure

If you need complex naming logic (like adding a random string or using another attribute), use a Closure:

self::registerMediaForColumn(
    column: 'invoice_pdf',
    directory: 'invoices',
    fileName: fn ($model, $file) => "invoice-{$model->number}-" . Str::random(5)
);

Automatic Cleanup

You don't need to do anything! Laravel Model Media automatically:

  • Deletes the old file when you re-upload a new one to the same column.
  • Deletes all associated files when the model is deleted (via Model Observer).

๐Ÿ—๏ธ How It Works

graph TD
    subgraph Upload ["๐Ÿ“ค 1. ATTACH (Upload)"]
        A[File Uploaded] --> B[attachMedia Method]
        B --> C[Retrieve Mapping]
        C --> D[Generate Filename]
        D --> E[Store to Disk]
        E --> F[Update Model Attribute]
    end

    subgraph Update ["๐Ÿ”„ 2. UPDATE (Auto-Cleanup)"]
        G[Replace File] --> H[Identify Old File]
        H --> I[Delete Old File from Disk]
        I --> J[Proceed with New Upload]
    end

    subgraph Delete ["๐Ÿ—‘๏ธ 3. DELETE (Full Cleanup)"]
        K[Model Deleted] --> L[MediaObserver Triggers]
        L --> M[Fetch All Mappings]
        M --> N[Delete All Files from Disk]
    end

    F -.-> G
    J --> B
Loading

๐Ÿงช Testing

The package includes a robust test suite. You can run it via composer:

composer test

We test for:

  • โœ… Correct storage path and filename generation.
  • โœ… Automatic deletion of old media on update.
  • โœ… Garbage collection of files on model deletion.
  • โœ… Prediction and predictability using faked storage and string overrides.

๐Ÿค Contributing

Please see CONTRIBUTING for details.

๐Ÿ“„ License

The MIT License (MIT). Please see License File for more information.

๐Ÿ‘จโ€๐Ÿ’ป Credits