Dávky súborov
FileImporter zmení každý nahratý súbor — alebo každú položku ZIP-u — na jeden záznam, napríklad dokument:
use RoundlyConsulting\Imports\Definition\{FileRules, Ownership};
use RoundlyConsulting\Imports\FileImporter;
use RoundlyConsulting\Imports\Rows\{ImportContext, ImportFile};
final class DocumentsImporter extends FileImporter
{
public function key(): string { return 'documents'; }
public function label(): string { return 'Documents'; }
public function ownership(): Ownership { return Ownership::column('team_id'); }
public function accepts(): FileRules { return FileRules::extensions('pdf', 'docx')->maxSize(20_480); }
public function authorize(?Authenticatable $user, Model $owner, ImportOperation $operation): bool
{
return $user?->can('manage-documents', $owner) ?? false;
}
public function create(ImportFile $file, ImportContext $context): Model
{
return Document::create(['team_id' => $context->owner->getKey(), 'name' => $file->name, 'path' => $file->storeOn('documents')]);
}
}
Imports::for($team)->by($user)->uploadFiles('documents', $request->file('files'))->preview()->commit();Metódy
| Metóda | Povinná | Predvolené |
|---|---|---|
key() · label() | nie | z názvu triedy, ako pri Importer |
ownership(): Ownership · authorize(?Authenticatable, Model $owner, ImportOperation): bool | áno | — (bezpečné odmietnutie) |
accepts(): FileRules | áno | — |
create(ImportFile $file, ImportContext $context): Model | áno | — |
duplicateCheck(): FileDuplicates | nie | FileDuplicates::ledger() |
rollback() · changeDetection() · checksumAttributes() | nie | ako pri Importer |
FileRules::extensions('pdf', 'docx') (porovnanie malými písmenami) alebo FileRules::any(), potom ->maxSize(int $kilobytes) (predvolene imports.files.max_file_size); allows() a maxBytes() ho spätne prečítajú. Importér súborov nemá polia, mapovanie ani režimy — Imports::importer('documents')->modes() je [] a jeho popis uvádza extensions.
Náhľad a duplicity
- Vstup: jedno alebo viac nahratí a/alebo archívov ZIP (názov .zip s obsahom ZIP); každý súbor alebo položka je jeden riadok, najviac files.max_files. Každá položka je vo výsledkoch riadkov (názov, veľkosť, SHA-256, stav).
- Pre každý súbor: platný, neplatný (extension_not_allowed, file_too_large, empty_file), duplicitný v dávke (duplicate_file) alebo v skoršom importe tohto vlastníka a importéra, ktorého záznam stále existuje (file_imported_earlier).
- Súbor, ktorého záznam vrátenie ponechalo, sa stále ráta ako importovaný; súbor sa dá znova importovať, len ak vrátenie záznam odstránilo (deleted, handled, missing).
- Hashe sa pri importe overia znova. Import a vrátenie fungujú ako pri riadkoch — číslo riadka je index položky a evidencia si uchová hash obsahu.
- errorReport() vypíše odmietnuté súbory: stĺpce File a Errors, jeden riadok na súbor.
use RoundlyConsulting\Imports\Definition\FileDuplicates;
public function duplicateCheck(): FileDuplicates
{
return FileDuplicates::using(
fn (string $sha256, Model $owner) => Document::whereBelongsTo($owner, 'team')->where('sha256', $sha256)->first(),
); // or FileDuplicates::ledger() (the default), FileDuplicates::none()
}ImportFile
$file->index; // the entry index (the row number)
$file->name; // sanitised, metadata only
$file->extension; $file->size; $file->sha256;
$file->readStream(); // a resource
$file->contents(); // small files only
$file->storeOn('s3', 'documents'); // copies under a generated ULID name + extension, returns the pathKópie vytvorené cez storeOn() sú mimo transakcie importu: vrátená časť po sebe môže jednu nechať, preto ich spárujte s háčikom rollback() alebo upratovaním, ak na tom záleží.
Bezpečnosť ZIP
- Kontroluje sa pred akýmkoľvek rozbalením: otvorenie len na čítanie s kontrolou konzistencie; archív do files.max_archive_size; položky do files.max_files; deklarovaný celkový objem do files.max_uncompressed; každá položka do limitu veľkosti importéra.
- Kompresný pomer do files.max_ratio, pre každú položku aj celkovo, pri všetkom nad files.ratio_min_size.
- Názvy: žiadne absolútne cesty, žiadne .. (ani so spätnými lomkami), žiadne riadiace znaky, najviac 255 bajtov; žiadne symbolické odkazy; žiadne šifrované položky. Adresáre a položky z files.ignore sa preskočia; vnorené archívy sú obyčajné súbory.
- Pri rozbaľovaní sa skutočne rozbalené bajty rátajú pre každú položku aj celkovo — nepravdivá hlavička sa zastaví uprostred streamu.
- Položky sa ukladajú pod generovanými názvami; žiadna cesta z archívu sa nikdy nedostane na disk. Akékoľvek porušenie odmietne celé nahratie a zmaže, čo sa už pripravilo.
Prejavte lásku k open source
Tento balík je zadarmo pod licenciou MIT. Ak vám šetrí čas, jednorazový príspevok alebo členstvo na Patreone nám pomôže ho ďalej udržiavať, testovať a dokumentovať.
Ďalšie spôsoby podpory vrátane kryptomienOdoslaním daru súhlasíte s našimi podmienkami prijímania darov.
Chcete to zabudovať do svojho produktu?
Naše balíky integrujeme do zákazkových Laravel a AI riešení. Napíšte nám, na čom pracujete, a ozveme sa do 48 hodín.