@@ -467,3 +467,70 @@ The following example shows these functions in action:
467467 {% if 'waiting_some_approval' in workflow_marked_places(post) %}
468468 <span class="label">PENDING</span>
469469 {% endif %}
470+
471+ Transition Blockers
472+ -------------------
473+
474+ .. versionadded :: 4.1
475+
476+ Transition Blockers were introduced in Symfony 4.1.
477+
478+ Transition Blockers provide a way to return a human-readable message for why a
479+ transition was blocked::
480+
481+ use Symfony\Component\Workflow\Event\GuardEvent;
482+ use Symfony\Component\EventDispatcher\EventSubscriberInterface;
483+
484+ class BlogPostPublishListener implements EventSubscriberInterface
485+ {
486+ public function guardPublish(GuardEvent $event)
487+ {
488+ /** @var \App\Entity\BlogPost $post */
489+ $post = $event->getSubject();
490+
491+ // If it's after 9pm, prevent publication
492+ if (date('H') > 21) {
493+ $event->addTransitionBlocker(
494+ new TransitionBlocker(
495+ "You can not publish this blog post because it's too late. Try again tomorrow morning."
496+ )
497+ );
498+ }
499+ }
500+
501+ public static function getSubscribedEvents()
502+ {
503+ return [
504+ 'workflow.blogpost.guard.publish' => ['guardPublish'],
505+ ];
506+ }
507+ }
508+
509+ You can access the message from a Twig template as follows:
510+
511+ .. code-block :: html+twig
512+
513+ <h2>Publication was blocked because:</h2>
514+ <ul>
515+ {% for transition in workflow_all_transitions(article) %}
516+ {% if not workflow_can(article, transition.name) %}
517+ <li>
518+ <strong>{{ transition.name }}</strong>:
519+ <ul>
520+ {% for blocker in workflow_build_transition_blocker_list(article, transition.name) %}
521+ <li>
522+ {{ blocker.message }}
523+ {% if blocker.parameters.expression is defined %}
524+ <code>{{ blocker.parameters.expression }}</code>
525+ {% endif %}
526+ </li>
527+ {% endfor %}
528+ </ul>
529+ </li>
530+ {% endif %}
531+ {% endfor %}
532+ </ul>
533+
534+ Don't need a human-readable message? You can still use::
535+
536+ $event->setBlocked('true');
0 commit comments