Symfony: How to use translation component in entity __toString?

1.6k views Asked by At

Yes, I know this has been asked before and discouraged, but I have a good use case for that. I am interested in learning the view-oriented supplementary approach.

The use case:

I have an entity, say Venue (id, name, capacity) which I use as collection in EasyAdmin. To render choices, I require this entity to have string representation.

I want the display to say %name% (%capacity% places).

As you've correctly guessed, I require the word "places" translated.

I could want to do it

  1. directly in the entity's __toString() method
  2. in form view by properly rendering __toString() output

I have no idea how to implement either but I agree that the first approach violates the MVC pattern.

Please advise.

2

There are 2 answers

1
baikho On BEST ANSWER

Displaying it as %name% (%capacity% places) is just a "possible" representation in your form view so I would shift this very specific representation to your Form Type.

What can belong in the __toString() method of your Venue entity:

class Venue 
{
    private $name;

    ... setter & getter method

    public function __toString()
    {
        return $this->getName();
    }
}

messages.en.yml:

my_translation: %name% (%capacity% places)

Next your Form Type using choice_label (also worth knowing: choice_translation_domain) :

use Symfony\Component\Translation\TranslatorInterface;

class YourFormType extends AbstractType
{
    private $translator;

    public function __construct(TranslatorInterface $translator)
    {
        $this->translator = $translator;
    }

    /**
     * @param FormBuilderInterface $builder
     * @param array $options
     */
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ->add(
                'venue',
                EntityType::class,
                array(
                    'choice_label' => function (Venue $venue, $key, $index) {
                        // Translatable choice labels
                        return $this->translator->trans('my_translation', array(
                            '%name%' => $venue->getName(),
                            '%capacity%' => $venue->getCapacity(),
                        ));
                    }
                )
            );
    }

}

& also register your form type as a service in services.yml:

your_form_type:
  class: Your\Bundle\Namespace\Form\YourFormType
  arguments: ["@translator"]
  tags:
    - { name: form.type }
0
spackmat On

I implemented a more or less complex solution for that problem, see my answer on this related question: https://stackoverflow.com/a/54038948/2564552