Як отримати доступ до констант класу в Twig?


133

У мене в класі сутності є кілька констант, наприклад:

class Entity {
    const TYPE_PERSON = 0;
    const TYPE_COMPANY = 1;
}

У звичайному PHP я часто це роблю, if($var == Entity::TYPE_PERSON)і мені хотілося б робити такі речі в Twig. Це можливо?

Відповіді:


185
{% if var == constant('Namespace\\Entity::TYPE_PERSON') %}
{# or #}
{% if var is constant('Namespace\\Entity::TYPE_PERSON') %}

Дивіться документацію щодо constantфункції та constantтесту .


3
Ви повинні додати тестуючі контакти з екземпляром об’єкта до свого вітника{% if var is constant('TYPE_PERSON', object) %}
ioleo

1
Працював, коли я набирав простір імен, як-от повідомлення @ message.
крафтер

232

Просто, щоб заощадити свій час. Якщо вам потрібно отримати доступ до констант класу в просторі імен, використовуйте

{{ constant('Acme\\DemoBundle\\Entity\\Demo::MY_CONSTANT') }}

22
Важливо зазначити, що подвійні косі риски є важливими. Я витратив кілька хвилин, тому що не ставлю подвійних нахилів.
Ден Морфіс

Дякую! ти економиш мій час! :)
sintetico82

7
Нічого, це некрасиво :-) Було б добре, якби Twig міг зробити константи схожими на інші властивості / змінні. наприклад{% if var == object.MY_CONSTANT %}
Рік Хейвуд

27

З 1.12.1 ви також можете зчитувати константи від екземплярів об'єкта:

{% if var == constant('TYPE_PERSON', entity)

Це працює лише в тому випадку, якщо сутність є екземпляром Entity, я думаю, що питання стосується доступу до константи без визначеного об'єкта в шаблоні.
Сергі

У цьому випадку ви просто пишете {{ constant('Namespace\\Classname::CONSTANT_NAME') }}( doc )
Олександр Федоров

Що в цьому добре, це те, що він дозволяє легко використовувати змінну Twig замість рядкового літералу як постійного імені.
CJ Dennis

Просто для наочності. Якщо ви хочете передати константи в класі як гілочку змінної та використовувати її так {{ constant('TYPE_PERSON', entity) }}, можна зробити наступне (інстанціювати клас сутності)$this->render('index.html.twig', ['entity' => new Entity()]);
Олександр Циганок,

13

Редагувати: Я знайшов краще рішення, читайте про це тут.



Скажімо, у вас клас:

namespace MyNamespace;
class MyClass
{
    const MY_CONSTANT = 'my_constant';
    const MY_CONSTANT2 = 'const2';
}

Створіть та зареєструйте розширення Twig:

class MyClassExtension extends \Twig_Extension
{
    public function getName()
    { 
        return 'my_class_extension'; 
    }

    public function getGlobals()
    {
        $class = new \ReflectionClass('MyNamespace\MyClass');
        $constants = $class->getConstants();

        return array(
            'MyClass' => $constants
        );
    }
}

Тепер ви можете використовувати константи в Twig, наприклад:

{{ MyClass.MY_CONSTANT }}

12
Отже, визначити ціле розширення гілочок для кожного класу менш "некрасиво", ніж використовувати {{постійний ('Acme \\ DemoBundle \\ Entity \\ Demo :: MY_CONSTANT')}}? А що ви робите, коли назви класів перекриваються? Ви втрачаєте всю користь просторів імен тут
0x1gene

1
У мене є подібне рішення, я можу витягнути це в пакет. Проблема цього рішення полягає в тому, що у вас є роздуми над головою. У symfony ви можете написати пропуск компілятора для вирішення цього питання, коли контейнер компілюється.
Будь-хто

@ 0x1gene Ви праві, імена класів можуть перетинатися. Я мовчки припускав, що MyClass - це не просто будь-який клас, а клас, який дуже важливий в рамках проекту. І використовується досить часто, тому використання constant()FQN було б нудно.
Даміян Полак

@DamianPolac Чи знаєте ви, що PHPStorm підкаже вибір змін у файлі twig?
Кодіум

12

Якщо ви використовуєте простори імен

{{ constant('Namespace\\Entity::TYPE_COMPANY') }}

Важливо! Використовуйте подвійні нахили, а не одинарні


9

У книзі кращих практик Symfony є розділ з цим питанням:

Константи можна використовувати, наприклад, у ваших шаблонах Twig завдяки функції постійного ():

// src/AppBundle/Entity/Post.php
namespace AppBundle\Entity;

class Post
{
    const NUM_ITEMS = 10;

   // ...
}

І використовуйте цю константу в гілочці шаблону:

<p>
    Displaying the {{ constant('NUM_ITEMS', post) }} most recent results.
</p>

Тут посилання: http://symfony.com/doc/current/best_practices/configuration.html#constants-vs-configuration-options


4

Через кілька років я зрозумів, що моя попередня відповідь не дуже хороша. Я створив розширення, яке краще вирішує проблему. Він публікується як відкритий код.

https://github.com/dpolac/twig-const

Він визначає нового оператора Twig, #який дозволяє вам отримувати доступ до константи класу через будь-який об’єкт цього класу.

Використовуйте його так:

{% if entity.type == entity#TYPE_PERSON %}


Дякую за ідею, я ніколи про це не думав! Якщо ви хочете використовувати імена класів сутностей без примірників об'єктів, наприклад User#TYPE_PERSON, то NodeExpressionклас може бути змінений на що - щось на зразок цього, який працював для мене ->raw('(constant(\'App\\Entity\\' . $this->getNode('left')->getAttribute('name') . '::' . $this->getNode('right')->getAttribute('name') . '\'))'). Звичайно, це обмежує ваші класи App\Entityпростором імен, але я думаю, що це стосується найбільш поширеного випадку використання.
майбутні
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.