Symfony 5.4 introduced support for Enums in forms November 2021. Later, in Symfony 6.2, we improved enums support to allow using them in YAML files, env vars, etc. In Symfony 6.3 we're improving enums support again.
Enums in Expressions
The ExpressionLanguage component now includes a function called enum()
to get the case of an enumeration inside expressions:
1 2 3 4 5 6 7 8 9 10 11 12
namespace App\Config\Order;
enum OrderStatus
{
case Paid = 'paid';
case Pending = 'pending';
case Refunded = 'refunded';
case Deleted = 'deleted';
}
// inside expressions, namespace separators must be escaped with 3 backslashes
$expressionLanguage->evaluate('order.status == enum("App\\\Config\\\Order\\\OrderStatus::Paid")')
Enums Support in EnumNode Config
When using the Config component, you can now use enum values as part of the
allowed values of enum nodes defined with the enumNode()
method:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
enum OrderDelivery: string
{
case Standard = 'standard';
case Expedited = 'expedited';
case Priority = 'priority';
}
$rootNode
->children()
->enumNode('delivery')
// You can provide all values of the enum...
->values(OrderDelivery::cases())
// ... or you can pass only some values next to other scalar values
->values([OrderDelivery::Priority, OrderDelivery::Standard, 'other', false])
->end()
->end()
;
Enums as Default Values of Route Parameters
In Symfony 6.2 we added support for using the value of backed enums as route arguments so Symfony would transform them automatically into their associated enum case. In Symfony 6.3 we're improving this feature by allowing to use enum cases as the default value of route arguments:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
// src/Controller/OrderController.php
namespace App\Controller;
use App\Config\Order\OrderStatus;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Annotation\Route;
class OrderController extends AbstractController
{
#[Route('/orders/list/{status}', name: 'list_orders_by_status')]
public function list(OrderStatus $status = OrderStatus::Paid): Response
{
// ...
}
}
Related to this, we've also improved the parameter bag used to get values from
the Request to add a getEnum()
method. This converts e.g. the values from a
query string into backed enum cases:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
// src/Controller/OrderController.php
namespace App\Controller;
// ...
use Symfony\Component\HttpFoundation\Request;
class OrderController extends AbstractController
{
#[Route('/orders/list/', name: 'list_orders')]
public function list(Request $request): Response
{
// the second argument is the FQCN of the backed enum to use when transforming the value
$status = $request->query->getEnum('status', OrderStatus::class);
// ...
}
}
shouldn't
enum("App\\Config\\OrderStatus::Paid")')
be
enum("App\\Config\\Order\\OrderStatus::Paid")')
Ditto for the route parameters example:
use App\Config\OrderStatus;
should be
use App\Config\Order\OrderStatus;
OrderStatusEnum $status = OrderStatus::Paid
Shouldn't that be: OrderStatus $status = OrderStatus::Paid ??
I've been using this for a long time in 6.2. It's not new to 6.3, or is it? What am I missing?
@Tac @Thomas I've updated the code examples to fix the errors that you reported. Thanks!
@Jan sorry for the confusion. I've reworded the original post to explain that 6.3 adds support for using enums as default values of route parameters.
Was there no blog post about "added support for using the value of backed enums as route arguments" ?
I like usage of controller as a route parameter, impatient to use that
Great !