symfonycontrib/imagefield-bundle
SymfonyContrib ImageFieldBundle provides a ready-made Symfony form type for image uploads, handling file selection, preview, and storage integration. It helps add image fields to forms quickly with less boilerplate and consistent, reusable behavior across your application.
This is a Symfony2-era bundle (PHP 5.3/5.4, Symfony 2.x) that provides an image-oriented form widget by extending symfonycontrib/filefield-bundle. Treat it as a legacy component: verify it installs on your PHP version, and expect to only realistically use it on an existing Symfony 2.x codebase. There are zero dependents and no stars — audit the source before adopting.
Install both bundles — this one depends on FileFieldBundle; you cannot use it standalone.
"require": {
"symfonycontrib/filefield-bundle": "dev-master",
"symfonycontrib/imagefield-bundle": "dev-master"
}
Pin to a commit SHA rather than dev-master; there are no tagged releases you can rely on.
Register in AppKernel in dependency order — ImageFieldBundle extends FileFieldBundle, so register the parent first:
new SymfonyContrib\Bundle\FileFieldBundle\FileFieldBundle(),
new SymfonyContrib\Bundle\ImageFieldBundle\ImageFieldBundle(),
Look first at Form/Type/ (the form type extending FileField's type), Resources/views/Form/ (the Twig form theme for the image widget), and DependencyInjection/ (service ID + any config knobs). The form type alias is what you'll reference in ->add().
First use case — add an image upload field backed by a nullable string property on an entity, render it with the bundle's form theme, and show the currently stored image next to the input. Confirm the type alias via app/console container:debug | grep -i image.
Persist the filename, not the file. The standard Symfony file pattern applies: store a relative path string on the entity, keep the physical file in web/uploads, write the bytes in a lifecycle callback. The bundle gives you the widget; upload/rename/delete logic stays in your entity or a small upload listener.
Entity shape
class Product
{
/** @var string|null */
private $image;
/** @var UploadedFile|null */
private $imageFile;
public function setImageFile(UploadedFile $file = null) { $this->imageFile = $file; }
public function getImageFile() { return $this->imageFile; }
// upload() / removeUpload() called from prePersist/preUpdate
}
Form type usage — add the field using the bundle's alias (confirm exact name in the README or Form/Type), e.g. ->add('imageFile', 'imagefield'). On Symfony 2.8+ prefer the FQCN if the type is resolvable, since string aliases are deprecated toward 3.0.
Register the form theme manually if it isn't auto-loaded. Symfony form themes are not injected by bundles automatically:
{% form_theme form 'ImageFieldBundle:Form:fields.html.twig' %}
or globally in config.yml under twig.form.resources.
Preview pattern — the point of using this over a plain file type is showing the current image in the widget. In your template, conditionally render the stored path:
{% if form.vars.value.image %}
<img src="{{ asset('uploads/' ~ form.vars.value.image) }}" alt="">
{% endif %}
{{ form_widget(form.imageFile) }}
Reuse across entities — factor the upload/rename/delete boilerplate into a trait or small service (ImageUploader with upload(UploadedFile, $dir)), and reuse a single base form type. You will otherwise copy the same prePersist/preUpdate code for every entity.
Always pair with validation. The bundle is a widget, not a validator. Add Symfony\Component\Validator\Constraints\Image (max dimensions, mime types) plus a NotBlank/NotNull on the file for creation, and validate on the entity, not the field.
Deletion and replacement — when a new file replaces an old one, unlink the old path in preUpdate; on entity delete, unlink in a preRemove callback or a Doctrine event subscriber. Orphaned uploads are the most common long-term mess with this pattern.
Extensions — resize/thumbnail/crop is not part of this bundle. Pair it with liip/imagine-bundle (Symfony 2 equivalent) for derived images, and keep the bundle solely as the input widget.
Symfony 2 only. The type naming, service conventions, and likely use of deprecated Symfony APIs mean it will not drop into Symfony 3+/4+ without edits (string type aliases removed, getRequest() deprecations, each(), etc.). Do not plan a greenfield project around it.
Bundle order is load-bearing. Forgetting to register FileFieldBundle first yields a "type not found" or a class-not-found during container compilation. If the form type is unresolved, run app/console container:debug | grep -i filefield to confirm the parent bundle's services are loaded.
Abandonment risk. No stars, no dependents, dev-master only. Treat the source as the documentation: read the form type, read the Twig template, and be prepared to fork or vendor it into src/ if you need fixes.
Upload directory permissions. The bundle's default target directory (usually web/uploads) must be writable by the web user; absolute paths should come from getUploadRootDir()/__DIR__, never the request. Check getUploadDir() vs getUploadRootDir() naming — it's easy to return a web-relative path where an absolute one is required.
Orphan files on validation failure. If the form fails validation after the file is uploaded, the prePersist hook never runs and the file is left behind. Either move the file only after $form->isValid(), or add a cleanup on postSubmit/kernel terminate.
Multiple images are not handled. This is a single-file widget; for galleries, use a collection of file fields or VichUploaderBundle. Don't try to bend it into a multi-upload.
Template overriding. To change the widget markup, override the namespaced Twig template (place your version under app/Resources/ImageFieldBundle/views/Form/) rather than editing vendor/. If the widget isn't picking up styling, confirm the theme is registered and that you're not rendering form_widget() outside the themed form.
Debugging checklist: container:debug for the form type service; twig:debug for the theme path; debug:config if the DI exposes config; and check php -l/error log for PHP 7 deprecation notices that turn into fatal errors under strict error handlers.
Extension points: override the form type service definition in config.yml, extend the bundle's type with your own getParent() returning the image type, or replace the Twig template. These are the cleanest ways to add behavior (e.g. add a "remove" checkbox or a resize call) without forking.
How can I help you explore Laravel packages today?