Search by

roundly-consulting / imports-for-laravel

mihaliak

Import CSV and XLSX files into Eloquent models: templates, column mapping, validated preview, duplicate handling, background batches and undo.

Package info

github.com/roundly-consulting/imports-for-laravel

Homepage

Documentation

pkg:composer/roundly-consulting/imports-for-laravel

Fund package maintenance!

Patreon

Statistics

Installs: 4

Dependents: 0

Suggesters: 0

Stars: 1

Open Issues: 0

1.0.1 2026-11-08 18:37 UTC

This package is auto-updated.

Last update: 2026-11-08 18:43:05 UTC


README

Imports for Laravel — Roundly open source

Latest release Tests Code style Donate Patreon Crypto

Imports for Laravel

CSV and XLSX imports into your Eloquent models: one importer class per record type, downloadable templates, column mapping, a validated preview, duplicate handling, background batches and undo. Nothing is saved until the user commits, and invalid rows never are.

Installation

Requires PHP 8.4 (with the zip, xmlreader, xmlwriter and mbstring extensions) and Laravel 13.

composer require roundly-consulting/imports-for-laravel
php artisan vendor:publish --tag="options-migrations"   # saved column mappings live in options-for-laravel
php artisan vendor:publish --tag="imports-migrations"
php artisan make:queue-batches-table   # Laravel's job_batches table, if you do not have it yet
php artisan migrate

Schedule imports:sweep (every five minutes) and imports:prune (daily) so stuck imports are released and old files deleted.

Usage

Describe one record type in an importer and list it in config('imports.importers'):

use App\Models\Asset;
use App\Models\Vendor;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Database\Eloquent\Model;
use RoundlyConsulting\Imports\Definition\{Field, NaturalKey, Ownership};
use RoundlyConsulting\Imports\Enums\ImportOperation;
use RoundlyConsulting\Imports\Importer;
use RoundlyConsulting\Imports\Rows\{ImportContext, ImportRow};

final class AssetsImporter extends Importer   // key `assets`, label `Assets`
{
    public function model(): string { return Asset::class; }
    public function ownership(): Ownership { return Ownership::column('team_id'); }
    public function naturalKey(): NaturalKey { return NaturalKey::by('asset_tag')->then('serial_number'); }

    public function fields(): array
    {
        return [
            Field::text('asset_tag')->aliases('tag', 'inventory no'),
            Field::text('serial_number'),
            Field::text('name')->required()->max(120),
            Field::date('purchased_on'),
            Field::reference('vendor')->to(Vendor::class)->by('vat_id', 'name')->storeAs('vendor_id'),
        ];
    }

    public function authorize(?Authenticatable $user, Model $owner, ImportOperation $operation): bool
    {
        return $user?->can('manage-assets', $owner) ?? false;
    }

    public function create(ImportRow $row, ImportContext $context): Model
    {
        return Asset::create([...$row->attributes(), ...$context->ownerAttributes()]);
    }

    public function update(Model $asset, ImportRow $row, ImportContext $context): Model
    {
        return tap($asset)->update($row->changes());   // blank cells keep the stored value
    }
}

Then upload, preview, commit — and undo if needed:

use RoundlyConsulting\Imports\Enums\DuplicateMode;
use RoundlyConsulting\Imports\Facades\Imports;

$import = Imports::for($team)->by($user)
    ->upload('assets', $request->file('file'))   // CSV or XLSX; columns map from the headers
    ->mode(DuplicateMode::Update)
    ->preview();   // ≤ 500 rows: checked now; larger files validate on the queue — poll isPreviewed()

$import->counts();                               // valid 47 · invalid 2 · duplicates 1
$batch = $import->commit();                      // a background job batch
$batch->rollback();                              // later: removes the rows it created, unless edited since

Documentation

The full documentation — configuration, every feature and its API, and testing — lives on our website: roundly-consulting.com/open-source/docs/imports-for-laravel

Release notes are in CHANGELOG.md. To contribute, see the contributing guide.

Support our work

This package is free and open source, built and maintained by Roundly Consulting. If it saves you time, please consider supporting our open-source work — a one-time donation, a monthly pledge on Patreon or a crypto donation helps fund maintenance, new features and new packages.

Donate to Roundly open source Become a patron on Patreon Donate crypto: BTC, ETH, BNB or SOL

License

The MIT License (MIT). See LICENSE.md.