我正在使用vichuploadbundle在symfony中寻找多个上传。我也有工作上传者但仍然只有一个文件。我找不到解决问题的答案。我也尝试了许多教程,但没有任何方法可以帮助我。在他们的文档中,我无法找到答案。我该怎么办?
错误:
Expected argument of type "Symfony\Component\HttpFoundation\File\File", "array" given
我的实体:
/**
* @ORM\Entity
* @Vich\Uploadable
*/
class Product
{
/**
* @ORM\Id
* @ORM\Column(type="integer")
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @ORM\Column(type="string", length=50, nullable=true)
* @Assert\NotBlank()
* @Assert\Length(
* min=5,
* minMessage="Title is too short!",
* max=50,
* maxMessage="Title is too long!"
* )
*/
private $title;
/**
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\User")
* @ORM\JoinColumn(nullable=false)
*/
private $author;
/**
* @ORM\Column(type="string", length=150, nullable=true)
* @Assert\NotBlank()
* @Assert\Length(
* min=5,
* minMessage="Perex is too short!",
* max=100,
* maxMessage="Perex is too long!"
* )
*/
private $perex;
/**
* @ORM\Column(type="text", length=500, nullable=true)
* @Assert\NotBlank()
*/
private $text;
/**
* @var ArrayCollection
* @ORM\OneToMany(targetEntity="AppBundle\Entity\ProductPicture", mappedBy="product", cascade={"all"}, orphanRemoval=true)
*/
private $pictures;
public function __construct()
{
$this->pictures = new ArrayCollection();
}
/**
* @return ArrayCollection
*/
public function getPictures()
{
return $this->pictures;
}
/**
* @param ArrayCollection $pictures
*/
public function setPictures($pictures)
{
$this->pictures = $pictures;
}
public function getAttachPictures()
{
return null;
}
public function setAttachPictures(array $files=array())
{
if (!$files) return [];
foreach ($files as $file) {
if (!$file) return [];
$this->attachPicture($file);
}
return [];
}
public function attachPicture(UploadedFile $file=null)
{
if (!$file) {
return;
}
$picture = new ProductPicture();
$picture->setImageFile($file);
$this->addPicture($picture);
}
public function addPicture(ProductPicture $picture)
{
$picture->setProduct($this);
$this->pictures->add($picture);
}
public function removePicture(ProductPicture $picture)
{
$picture->setProduct(null);
$this->pictures->removeElement($picture);
}
}
ProductPicture:
/**
* @ORM\Entity
* @Vich\Uploadable
*/
class ProductPicture
{
/**
* @ORM\Id
* @ORM\Column(type="integer")
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @var Product
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Product", inversedBy="pictures")
*/
private $product;
/**
*
* @Vich\UploadableField(mapping="product_image", fileNameProperty="imageName", size="imageSize")
* @Assert\File(
* maxSize = "1024k",
* mimeTypes = {"image/png", "image/jpeg", "image/jpg"},
* mimeTypesMessage = "Please upload a valid valid IMAGE"
* )
*
* @var File
*/
private $imageFile;
/**
* @ORM\Column(type="string", length=255, nullable=true)
*
* @var array
*/
private $imageName;
/**
*
* @param File|\Symfony\Component\HttpFoundation\File\UploadedFile $image
*
* @return Product
*/
public function setImageFile(File $image = null)
{
$this->imageFile = $image;
}
public function getImageFile()
{
return $this->imageFile;
}
public function setProduct(Product $product)
{
$this->product = $product;
}
public function getProduct()
{
return $this->product;
}
/**
* @return mixed
*/
public function getId()
{
return $this->id;
}
/**
* @param mixed $id
*/
public function setId($id)
{
$this->id = $id;
}
/**
* @return array
*/
public function getImageName()
{
return $this->imageName;
}
/**
* @param array $imageName
*/
public function setImageName($imageName)
{
$this->imageName = $imageName;
}
}
形式:
class ProductType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('title')
->add('perex')
->add('text')
->add('attachPictures', FileType::class, ['multiple'=>true, 'required'=>false])
;
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'data_class' => Product::class,
]);
}
}
答案 0 :(得分:0)
我无法帮助您使用此上传工具包,但我可以用更简单的方式向您展示它在我的案例中的工作方式(使用简单的请求,而不是一些花哨的捆绑包)
这里 https://gist.github.com/poznet/e3955a48fea01d8640dafbd966c53a83
你有
这个特性有点乱(没有附带大小/类型检查等),但它有效。
如果您有任何问题可以随意提出。
PS在你的情况下,如果你上传多个文件你得到数组,而不是文件类:D
答案 1 :(得分:0)
您应该将文件部件构建为实体
balance > amount
在您的产品实体中......
/**
* @ORM\Entity
* @Vich\Uploadable
*/
class ProductPicture
{
/**
* @ORM\Id
* @ORM\Column(type="integer")
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @var Product
* @ORM\ManyToOne(targetEntity="path\to\your\entity\Product", inversedBy="pictures")
*/
private $product;
/**
*
* @Vich\UploadableField(mapping="product_image", fileNameProperty="imageName", size="imageSize")
* @Assert\File(
* maxSize = "1024k",
* mimeTypes = {"image/png", "image/jpeg", "image/jpg"},
* mimeTypesMessage = "Please upload a valid valid IMAGE"
* )
*
* @var File
*/
private $imageFile;
/**
* @ORM\Column(type="string", length=255, nullable=true)
*
* @var array
*/
private $imageName;
/**
*
* @param File|\Symfony\Component\HttpFoundation\File\UploadedFile $image
*
* @return Product
*/
public function setImageFile(File $image = null)
{
$this->imageFile = $image;
}
public function getImageFile()
{
return $this->imageFile;
}
public function setProduct(Product $product)
{
$this->product = $product;
}
public function getProduct()
{
return $this->product;
}
}
最后以表格形式使用......
/**
* @var ArrayCollection
* @ORM\OneToMany(targetEntity="path\to\your\entity\ProductPicture", mappedBy="product", cascade={"all"}, orphanRemoval=true)
*/
private $pictures;
public function __construct()
{
$this->pictures = new ArrayCollection();
}
/**
* @return ArrayCollection
*/
public function getPictures()
{
return $this->pictures;
}
/**
* @param ArrayCollection $pictures
*/
public function setPictures($pictures)
{
$this->pictures = $pictures;
}
public function getAttachPictures()
{
return null;
}
public function setAttachPictures(array $files=array())
{
if (!$files) return [];
foreach ($files as $file) {
if (!$file) return [];
$this->attachPicture($file);
}
return [];
}
public function attachPicture(UploadedFile $file=null)
{
if (!$file) {
return;
}
$picture = new ProductPicture();
$picture->setImageFile($file);
$this->addPicture($picture);
}
public function addPicture(ProductPicture $picture)
{
$picture->setProduct($this);
$this->pictures->add($picture);
}
public function removePicture(ProductPicture $picture)
{
$picture->setProduct(null);
$this->pictures->removeElement($picture);
}
答案 2 :(得分:0)
Symfony 4 工作解决方案。
非常简单。整理您的实体,创建表单并form transformer
// src/Entity/Product.php
/**
* @ORM\Entity
* @Vich\Uploadable
*/
class Product
{
...
/**
* @var Collection|ProductPicture[]
* @ORM\OneToMany(targetEntity="AppBundle\Entity\ProductPicture", mappedBy="product", cascade={"persist", "remove"}, orphanRemoval=true)
*/
private $pictures;
public function __construct()
{
$this->pictures = new ArrayCollection();
}
/**
* @return Collection|ProductPicture[]
*/
public function getPictures(): Collection
{
return $this->pictures;
}
public function addPicture(ProductPicture $picture): self
{
if (!$this->pictures->contains($picture) {
$this->pictures->add($picture);
$picture->setProduct($this);
}
return $this;
}
public function removePicture(ProductPicture $picture): self
{
if ($this->pictures->contains($picture) {
$this->pictures->removeElement($picture);
if ($picture->getProduct() === $this) {
$picture->setProduct(null);
}
}
return $this;
}
...
}
// src/Entity/ProductPicture.php
/**
* @ORM\Entity
* @Vich\Uploadable
*/
class ProductPicture
{
...
/**
* @var Product
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Product", inversedBy="pictures")
* @ORM\JoinColumn(nullable=false)
*/
private $product;
/**
*
* @Vich\UploadableField(mapping="product_image", fileNameProperty="imageName", size="imageSize")
* @Assert\File(
* maxSize = "1024k",
* mimeTypes = {"image/png", "image/jpeg", "image/jpg"},
* mimeTypesMessage = "Please upload a valid valid IMAGE"
* )
*
* @var File
*/
private $imageFile;
...
/**
* @param File|\Symfony\Component\HttpFoundation\File\UploadedFile $image
*
* @return Product
*/
public function setImageFile(?File $image = null)
{
$this->imageFile = $image;
if (null !== $image) {
// It is required that at least one field changes if you are using doctrine
// otherwise the event listeners won't be called and the file is lost
$this->updatedAt = new DateTimeImmutable();
}
}
public function getImageFile()
{
return $this->imageFile;
}
public function setProduct(Product $product)
{
$this->product = $product;
}
public function getProduct()
{
return $this->product;
}
...
}
然后您需要创建简单的ProductType表单:
// src/Form/ProductForm.php
class PictureType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options): void
{
$builder
->add($builder->create(
'pictures',
FileType::class,
[
'required' => false,
'multiple' => true,
]
)->addModelTransformer(new FilesToPicturesTransformer()))
->add(...);
}
public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([
'data_class' => Product::class,
]);
}
和FilesToPicturesTransformer(数据转换器):
// src/Form/FilesToPicturesTransformer.php
class FilesToPicturesTransformer implements DataTransformerInterface
{
/**
* {@inheritdoc}
*/
public function transform($value): void
{
// don't need this if you build API
}
/**
* {@inheritdoc}
*/
public function reverseTransform($value): ArrayCollection
{
$pictures = new ArrayCollection();
foreach ($value as $file) {
$picture = (new ProductPicture())
->setImageFile($file);
if (!$pictures->contains($picture)) {
$pictures->add($picture);
}
}
return $pictures;
}
}