I'm asking if it's possible to pass an array as value for some elements? For example in my case I'm trying to set roles for a FOSUserBundle User
entity that takes roles
as an array of values and not plain values. I have this in my fixture:
UserBundle\Entity\User:
User0:
username: admin
email: [email protected]
enabled: 1
plainPassword: admin
roles: [ROLE_ADMIN]
groups: @Group0
User{1..10}:
username: <firstNameMale>
email: <companyEmail>
enabled: <boolean(35)>
plainPassword: <lexify>
roles: 35%? [ROLE_ADMIN, ROLE_USER, ROLE_PROFILE_ONE, ROLE_PROFILE_TWO]
groups: @Group*
But it's not working and I'm getting this error:
[Symfony\Component\Debug\Exception\ContextErrorException] Catchable Fatal Error: Argument 1 passed to FOS\UserBundle\Model\User::setRoles() must be of the type array, string given, called in /var/www/html/vendor/nelmio/alice/src/Nelmio/Alice/Loader/Base.php on line 483 and defined in /var/www/html/vendor/friendsofsymfony/user-bundle/FOS/UserBundle/Model/User.php line 530
Any advice around this?
Update answer
Using first approach with plain array in YAML file:
After made some changes as @frumious suggested the fixture now has this content:
UserBundle\Entity\User:
User0:
username: admin
email: [email protected]
enabled: 1
plainPassword: admin
roles: [ROLE_ADMIN]
groups: @Group0
User{1..10}:
username: <firstNameMale>
email: <companyEmail>
enabled: <boolean(35)>
plainPassword: <lexify>
roles: [ROLE_PROFILE_ONE, ROLE_PROFILE_TWO]
groups: @Group*
In this way I will assign always the two roles for each test User but I'm having some problems trying to get where the Faker
should be placed and which code to write inside it.
But any time I try to execute the set by calling:
h4cc_alice_fixtures:load:sets ./src/CommonBundle/DataFixtures/TananeSet.php
I got this error:
[ErrorException] Catchable Fatal Error: Argument 1 passed to Doctrine\Common\Collections\ArrayCollection::__construct() must be of the type array, object given, called in /var/www/html/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php o
n line 555 and defined in /var/www/html/vendor/doctrine/collections/lib/Doctrine/Common/Collections/ArrayCollection.php line 47
Which makes me think the problem here is related to $groups
variable in User
entity. This is a piece of code on that entity:
/**
* @ORM\Entity
* @ORM\Table(name="fos_user")
* @Gedmo\SoftDeleteable(fieldName="deletedAt", timeAware=false)
* @ORM\Entity(repositoryClass="UserBundle\Entity\Repository\UserRepository")
*/
class User extends BaseUser {
/**
* Hook timestampable behavior
* updates createdAt, updatedAt fields
*/
use TimestampableEntity;
/**
* @ORM\Id
* @ORM\Column(type="integer")
* @ORM\GeneratedValue(strategy="AUTO")
*/
protected $id;
/**
* @ORM\ManyToMany(targetEntity="Group")
* @ORM\JoinTable(name="fos_user_user_group",
* joinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="id")},
* inverseJoinColumns={@ORM\JoinColumn(name="group_id", referencedColumnName="id")}
* )
*/
protected $groups;
/**
* @ORM\Column(name="deletedAt", type="datetime", nullable=true)
*/
protected $deletedAt;
}
How I can fix that error? What I should pass as parameter for groups
?
Using second approach: defining a service
Following the other suggestion by @frumious I define a service as follow:
services:
roles.faker.provider:
class: CommonBundle\Tools\RolesFakerProvider
tags:
- { name: h4cc_alice_fixtures.provider }
And this is the method:
namespace CommonBundle\Tools;
class RolesFakerProvider {
public function randomRoles()
{
$names = ['ROLE_USER', 'ROLE_PROFILE_ONE', 'ROLE_PROFILE_TWO'];
return [$names[array_rand($names)]];
}
}
Then I made this changes:
UserBundle\Entity\User:
User0:
username: admin
email: [email protected]
enabled: 1
plainPassword: admin
roles: [ROLE_ADMIN]
groups: @Group0
User{1..10}:
username: <firstNameMale>
email: <companyEmail>
enabled: <boolean(35)>
plainPassword: <lexify>
# BEFORE
#roles: [ROLE_PROFILE_ONE, ROLE_PROFILE_TWO]
# AFTER
roles: <randomRoles>
groups: @Group*
And this one is returning this error instead:
[Symfony\Component\Debug\Exception\ContextErrorException] Catchable Fatal Error: Argument 1 passed to FOS\UserBundle\Model\User::setRoles() must be of the type array, string given, called in /var/www/html/vendor/nelmio/alice/src/Nelmio/Alice/Loader/Base.php on line 483 and defin ed in /var/www/html/vendor/friendsofsymfony/user-bundle/FOS/UserBundle/Model/User.php line 530
Which makes me think the function isn't returning an array
or something else is getting wrong, any advice around this one too?
groups: [@Group*]
? Approach 2: that looks like it should work to me, if your service is getting injected properly, and the method is actually being called (the method, as defined, clearly returns an array!). I'd try it in-line in the YAML (roles: <?php ?>
etc), and also with [] (roles: [<?php ?>]
). If that works and the service doesn't, I'd debug/log/die()
to try to work out what's actually happening! – frumiousroles: [<randomRole>]
) or returning the [] from the method (return '['.$names[array_rand($names)].']';
) – frumious