Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Parabol Files Upload Bundle Laravel Package

parabol/parabol-files-upload-bundle

A Laravel/PHP bundle from Parabol for handling file uploads, packaging the upload workflow into a reusable component for your applications. Integrates with your Laravel project to simplify accepting, validating, and storing uploaded files.

View on GitHub
Deep Wiki
Context7

Getting Started

The first thing to establish before anything else: despite the "upload" naming, parabol/files-upload-bundle is a Symfony bundle, not a Laravel package. It declares a Bundle class, registers via config/bundles.php, and wires itself through Symfony's DI container. If you are working inside a Laravel application you cannot composer require this and expect it to work — you would be pulling a package that depends on symfony/http-kernel, symfony/form, and doctrine ORM conventions that Laravel does not provide. Treat this assessment as relevant only to a Symfony project.

With that caveat in place, the minimal path looks like a standard third-party Symfony bundle:

  1. composer require parabol/files-upload-bundle
  2. Register the bundle in config/bundles.php:
    Parabol\FilesUploadBundle\ParabolFilesUploadBundle::class => ['all' => true],
    
  3. Import the bundle's routing (needed if it ships upload/download controllers) and configure storage/upload directories in config/packages/parabol_files_upload.yaml (the exact key names are undocumented — see Gotchas).
  4. Look first at the entity mapping the bundle expects. Bundles in this style usually ship a File entity or a FileInterface + trait (FileTrait) you apply to your own entity so it can own uploaded files. That mapping is the thing you will touch on day one.

Your first real use case will almost certainly be: attach a single uploaded file to an existing Doctrine entity, persist it, and render/delete it later. Start by wiring one entity with the bundle's trait/interface, submit one file through a form, and confirm the file lands in the configured storage directory and a row appears in the file table. Everything else — galleries, multiple files, ordering — builds on that single working slice.

Given the package has zero stars, zero dependents, and no visible documentation beyond the repo README, plan to spend the first hour reading the bundle source (DependencyInjection/Configuration.php and the entity directory) rather than reading docs. The configuration tree in that one file tells you more about valid config keys than any README will.

Implementation Patterns

Because the bundle is undocumented and unused in the wild, the only reliable implementation patterns are the ones you establish by reading its source. Expect the usual shape for a Symfony file-upload bundle and adapt:

Trait-on-your-entity pattern. Most bundles of this genre ship an interface plus a trait so your domain entity stays yours. The pattern is:

use Parabol\FilesUploadBundle\Entity\FileTrait;

class Article
{
    use FileTrait; // adds $file / $files, getters, setters
}

Apply it to a single throwaway entity first and let Doctrine run a schema diff (bin/console doctrine:schema:update --dump-sql) to see exactly what columns the trait expects. That diff output effectively is your integration documentation.

Form-integration pattern. File entities typically attach through a FileType or an EntityType mapped to the file entity. If the bundle exposes a form type, embed it:

$builder->add('file', FileType::class, ['required' => false]);

If it does not, you will be mapping an EntityType to the file entity yourself and handling the VichUploader-style file move in a form event or controller. Verify which by grepping the package source for AbstractType subclasses.

Lifecycle / controller pattern. Wire persistence and file movement inside a Doctrine lifecycle callback or a controller action. Two safe workflows:

  • Upload-then-persist: move the uploaded file to its final path, create the File entity, set the entity relation, flush. Simple, but leaves orphaned files on error.
  • Persist-then-move: store the entity, flush, move the file in a postPersist/postFlush listener, flush again. Safer for transactional consistency, but more moving parts.

Start with upload-then-persist; graduate to lifecycle listeners only once the happy path works.

Serving files. If the bundle ships a download controller, you get a route like /file/{id} for free and should configure access control around it. If it does not, you are responsible for streaming through BinaryFileResponse — do not serve uploads directly from the public web root unless you've thought about filename collisions and content-type sniffing.

Integration tip: Because the bundle is essentially unmaintained, isolate its surface area. Wrap its file operations behind a small FileStorage service in your own code so that if you have to replace the bundle later (and you likely will), the blast radius is one class rather than every controller that touches an upload.

Gotchas and Tips

Unmaintained / zero-traction risk is the headline gotcha. Zero stars, zero dependents means no community to fall back on: no Stack Overflow answers, no fork with your bug already fixed, no release notes telling you what changed. Pin the exact version in composer.json, vendor the source if necessary, and budget for eventual replacement. Do not build a core product feature on it without a fallback plan.

The Laravel/Symfony mismatch. If you arrived here assuming this is a Laravel package — it isn't. There is no ServiceProvider, no config/parabol.php, no facade. Attempting to install it in Laravel will pull Symfony transitive dependencies and fail on kernel/form coupling. For Laravel, look at Spatie Media Library or Laravel's own filesystem/HasMedia patterns instead.

Configuration quirks are likely. The config key names are not documented. Open DependencyInjection/Configuration.php first and trace every node through the Extension and into the service definitions in Resources/config/services.yml. Half the "it doesn't work" cases with bundles like this come down to a config key that silently defaults to something you didn't intend — Symfony's config tree will often accept an unused key without error depending on how it's declared.

Debugging strategy. When uploads vanish, check in this order:

  1. The configured upload_dir — does it exist and is it writable by your web user? (ls -la on the parent.)
  2. The Doctrine mapping — is the File table actually created and is the relation correctly mapped? (doctrine:schema:validate.)
  3. The form — is the file field actually bound and is the mapped entity receiving the value? (dump($form->getData()) in the controller.)
  4. The lifecycle — is the file move actually firing? (Add a LoggerInterface call inside the relevant listener.)

Extension points are limited. Without maintained docs, your extension points are whatever was declared public in the service definitions. Expect to override via a compiler pass or by redeclaring services rather than through any documented plugin system. Do not rely on protected/private internals — a future (unlikely) release will break them, and so will any fork you make.

Version and PHP compatibility. Check the composer.json require block for the Symfony version constraint before you assume it's compatible with your project. Bundles with no releases often target Symfony 2.x/3.x, which will not install against Symfony 6/7. This is the most common hard blocker with dormant bundles.

Fork before you fix. If you hit a bug, the practical move is to fork the repo locally, patch it, and point composer at your fork via a vcs repository or path repository. You will almost certainly not get a PR merged upstream.

Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
coleus/frame
thtg88/journalism
filagora/filagora-ai-forums
rlacerda83/query-parser
socialdept/atp-orm
cboxdk/laravel-assistant-client
socialdept/atp-resolver
socialdept/tenant-domains
tautvydasr/blade-class-names
socialdept/color-scales
maherelgamil/controller
coleus/widgets
coleus/table
coleus/users
coleus/music
coleus/health
coleus/calendar
coleus/notes
coleus/support
coleus/settings