Skip to content

Commit 624b73b

Browse files
committed
Merge branch '7.3' into 7.4
* 7.3: (47 commits) [Bundle] Best Practice: Add link for create ux-bundle fix(typo): form --> from Reword Update import.rst Tweaks Fix a code sample with two PHP classes fix directive Tweaks and rewords [AssetMapper] Adding info that always *all* entrypoints are included… Replace get_class() calls by ::class [EventDispatcher] Document event name is optionnal [Serializer] Fix YAML normalizationContext and denormalizationContext names Removed an unneeded versionadded directive Minor tweaks [Cache][Lock] Add support for `Relay\Cluster` in docs [Security] Document the new `expose_security_errors` option [Security] Fixed a code example Fixed a minor RST syntax issue Fixed a minor RST syntax issue Tweaks and rewords ...
2 parents 2276ec1 + 8dbfce1 commit 624b73b

32 files changed

+1021
-226
lines changed

bundles/best_practices.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -559,6 +559,7 @@ Learn more
559559

560560
* :doc:`/bundles/extension`
561561
* :doc:`/bundles/configuration`
562+
* :doc:`/frontend/create_ux_bundle`
562563

563564
.. _`PSR-4`: https://www.php-fig.org/psr/psr-4/
564565
.. _`Symfony Flex recipe`: https://github.com/symfony/recipes

components/cache/adapters/redis_adapter.rst

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,9 +20,9 @@ to utilize a cluster of servers to provide redundancy and/or fail-over is also a
2020

2121
**Requirements:** At least one `Redis server`_ must be installed and running to use this
2222
adapter. Additionally, this adapter requires a compatible extension or library that implements
23-
``\Redis``, ``\RedisArray``, ``RedisCluster``, ``\Relay\Relay`` or ``\Predis``.
23+
``\Redis``, ``\RedisArray``, ``RedisCluster``, ``\Relay\Relay``, ``\Relay\Cluster`` or ``\Predis``.
2424

25-
This adapter expects a `Redis`_, `RedisArray`_, `RedisCluster`_, `Relay`_ or `Predis`_ instance to be
25+
This adapter expects a `Redis`_, `RedisArray`_, `RedisCluster`_, `Relay`_, `RelayCluster`_ or `Predis`_ instance to be
2626
passed as the first parameter. A namespace and default cache lifetime can optionally be passed
2727
as the second and third parameters::
2828

@@ -48,6 +48,10 @@ as the second and third parameters::
4848
?MarshallerInterface $marshaller = null
4949
);
5050

51+
.. versionadded:: 7.3
52+
53+
Support for ``Relay\Cluster`` was introduced in Symfony 7.3.
54+
5155
Configure the Connection
5256
------------------------
5357

@@ -226,11 +230,34 @@ Available Options
226230
``ssl`` (type: ``array``, default: ``null``)
227231
SSL context options. See `php.net/context.ssl`_ for more information.
228232

233+
``relay_cluster_context`` (type: ``array``, default: ``[]``)
234+
Defines configuration options specific to ``\Relay\Cluster``. For example, to
235+
user a self-signed certificate for testing in local environment::
236+
237+
$options = [
238+
// ...
239+
'relay_cluster_context' => [
240+
// ...
241+
'stream' => [
242+
'verify_peer' => false,
243+
'verify_peer_name' => false,
244+
'allow_self_signed' => true,
245+
'local_cert' => '/valkey.crt',
246+
'local_pk' => '/valkey.key',
247+
'cafile' => '/valkey.crt',
248+
],
249+
],
250+
];
251+
229252
.. versionadded:: 7.1
230253

231-
The option `sentinel_master` as an alias for `redis_sentinel` was introduced
254+
The option ``sentinel_master`` as an alias for ``redis_sentinel`` was introduced
232255
in Symfony 7.1.
233256

257+
.. versionadded:: 7.3
258+
259+
The ``relay_cluster_context`` option was introduced in Symfony 7.3.
260+
234261
.. note::
235262

236263
When using the `Predis`_ library some additional Predis-specific options are available.
@@ -359,6 +386,7 @@ Supports key rotation, ensuring secure decryption with both old and new keys::
359386
.. _`RedisArray`: https://github.com/phpredis/phpredis/blob/develop/arrays.md
360387
.. _`RedisCluster`: https://github.com/phpredis/phpredis/blob/develop/cluster.md
361388
.. _`Relay`: https://relay.so/
389+
.. _`RelayCluster`: https://relay.so/docs/1.x/connections#cluster
362390
.. _`Predis`: https://packagist.org/packages/predis/predis
363391
.. _`Predis Connection Parameters`: https://github.com/nrk/predis/wiki/Connection-Parameters#list-of-connection-parameters
364392
.. _`TCP-keepalive`: https://redis.io/topics/clients#tcp-keepalive

components/event_dispatcher.rst

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -277,8 +277,9 @@ Dispatch the Event
277277

278278
The :method:`Symfony\\Component\\EventDispatcher\\EventDispatcher::dispatch`
279279
method notifies all listeners of the given event. It takes two arguments:
280-
the ``Event`` instance to pass to each listener of that event and the name
281-
of the event to dispatch::
280+
the ``Event`` instance to pass to each listener of that event and optionally the
281+
name of the event to dispatch. If it's not defined, the class of the ``Event``
282+
instance will be used::
282283

283284
use Acme\Store\Event\OrderPlacedEvent;
284285
use Acme\Store\Order;

components/lock.rst

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -612,9 +612,9 @@ RedisStore
612612
~~~~~~~~~~
613613

614614
The RedisStore saves locks on a Redis server, it requires a Redis connection
615-
implementing the ``\Redis``, ``\RedisArray``, ``\RedisCluster``, ``\Relay\Relay`` or
616-
``\Predis`` classes. This store does not support blocking, and expects a TTL to
617-
avoid stalled locks::
615+
implementing the ``\Redis``, ``\RedisArray``, ``\RedisCluster``, ``\Relay\Relay``,
616+
``\Relay\Cluster`` or ``\Predis`` classes. This store does not support blocking,
617+
and expects a TTL to avoid stalled locks::
618618

619619
use Symfony\Component\Lock\Store\RedisStore;
620620

@@ -623,6 +623,10 @@ avoid stalled locks::
623623

624624
$store = new RedisStore($redis);
625625

626+
.. versionadded:: 7.3
627+
628+
Support for ``Relay\Cluster`` was introduced in Symfony 7.3.
629+
626630
.. _lock-store-semaphore:
627631

628632
SemaphoreStore

components/options_resolver.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -936,7 +936,7 @@ can change your code to do the configuration only once per class::
936936
public function __construct(array $options = [])
937937
{
938938
// What type of Mailer is this, a Mailer, a GoogleMailer, ... ?
939-
$class = get_class($this);
939+
$class = $this::class;
940940

941941
// Was configureOptions() executed before for this class?
942942
if (!isset(self::$resolversByClass[$class])) {

components/property_info.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -131,7 +131,7 @@ class exposes public methods to extract several types of information:
131131
$propertyInfo->getProperties($awesomeObject);
132132

133133
// Good!
134-
$propertyInfo->getProperties(get_class($awesomeObject));
134+
$propertyInfo->getProperties($awesomeObject::class);
135135
$propertyInfo->getProperties('Example\Namespace\YourAwesomeClass');
136136
$propertyInfo->getProperties(YourAwesomeClass::class);
137137

components/runtime.rst

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,9 @@ So how does this front-controller work? At first, the special
3636
the component. This file runs the following logic:
3737

3838
#. It instantiates a :class:`Symfony\\Component\\Runtime\\RuntimeInterface`;
39+
#. The front-controller script (e.g. ``public/index.php``) is included by the
40+
runtime, making it run again. Ensure this doesn't produce any side effects
41+
in your code;
3942
#. The callable (returned by ``public/index.php``) is passed to the Runtime, whose job
4043
is to resolve the arguments (in this example: ``array $context``);
4144
#. Then, this callable is called to get the application (``App\Kernel``);

components/uid.rst

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -369,6 +369,7 @@ entity primary keys::
369369
namespace App\Entity;
370370

371371
use Doctrine\ORM\Mapping as ORM;
372+
use Symfony\Bridge\Doctrine\IdGenerator\UuidGenerator;
372373
use Symfony\Bridge\Doctrine\Types\UuidType;
373374
use Symfony\Component\Uid\Uuid;
374375

@@ -377,7 +378,7 @@ entity primary keys::
377378
#[ORM\Id]
378379
#[ORM\Column(type: UuidType::NAME, unique: true)]
379380
#[ORM\GeneratedValue(strategy: 'CUSTOM')]
380-
#[ORM\CustomIdGenerator(class: 'doctrine.uuid_generator')]
381+
#[ORM\CustomIdGenerator(class: UuidGenerator::class)]
381382
private ?Uuid $id;
382383

383384
public function getId(): ?Uuid
@@ -557,6 +558,7 @@ entity primary keys::
557558
namespace App\Entity;
558559

559560
use Doctrine\ORM\Mapping as ORM;
561+
use Symfony\Bridge\Doctrine\IdGenerator\UlidGenerator;
560562
use Symfony\Bridge\Doctrine\Types\UlidType;
561563
use Symfony\Component\Uid\Ulid;
562564

@@ -565,7 +567,7 @@ entity primary keys::
565567
#[ORM\Id]
566568
#[ORM\Column(type: UlidType::NAME, unique: true)]
567569
#[ORM\GeneratedValue(strategy: 'CUSTOM')]
568-
#[ORM\CustomIdGenerator(class: 'doctrine.ulid_generator')]
570+
#[ORM\CustomIdGenerator(class: UlidGenerator::class)]
569571
private ?Ulid $id;
570572

571573
public function getId(): ?Ulid

components/yaml.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -298,7 +298,7 @@ You can make it convert to a ``DateTime`` instance by using the ``PARSE_DATETIME
298298
flag::
299299

300300
$date = Yaml::parse('2016-05-27', Yaml::PARSE_DATETIME);
301-
var_dump(get_class($date)); // DateTime
301+
var_dump($date::class); // DateTime
302302

303303
Dumping Multi-line Literal Blocks
304304
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

console/verbosity.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ level. For example::
6868

6969
// available methods: ->isSilent(), ->isQuiet(), ->isVerbose(), ->isVeryVerbose(), ->isDebug()
7070
if ($output->isVerbose()) {
71-
$output->writeln('User class: '.get_class($user));
71+
$output->writeln('User class: '.$user::class);
7272
}
7373

7474
// alternatively you can pass the verbosity level PHP constant to writeln()

controller/service.rst

Lines changed: 59 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -7,11 +7,65 @@ and your controllers extend the `AbstractController`_ class, they *are* automati
77
registered as services. This means you can use dependency injection like any
88
other normal service.
99

10-
If your controllers don't extend the `AbstractController`_ class, you must
11-
explicitly mark your controller services as ``public``. Alternatively, you can
12-
apply the ``controller.service_arguments`` tag to your controller services. This
13-
will make the tagged services ``public`` and will allow you to inject services
14-
in method parameters:
10+
If you prefer to not extend the ``AbstractController`` class, you can register
11+
your controllers as services in several ways:
12+
13+
#. Using the ``#[Route]`` attribute;
14+
#. Using the ``#[AsController]`` attribute;
15+
#. Using the ``controller.service_arguments`` service tag.
16+
17+
Using the ``#[Route]`` Attribute
18+
--------------------------------
19+
20+
When using :ref:`the #[Route] attribute <routing-route-attributes>` to define
21+
routes on any PHP class, Symfony treats that class as a controller. It registers
22+
it as a public, non-lazy service and enables service argument injection in all
23+
its methods.
24+
25+
This is the simplest and recommended way to register controllers as services
26+
when not extending the base controller class.
27+
28+
.. versionadded:: 7.3
29+
30+
The feature to register controllers as services when using the ``#[Route]``
31+
attribute was introduced in Symfony 7.3.
32+
33+
Using the ``#[AsController]`` Attribute
34+
---------------------------------------
35+
36+
If you prefer, you can use the ``#[AsController]`` PHP attribute to automatically
37+
apply the ``controller.service_arguments`` tag to your controller services::
38+
39+
// src/Controller/HelloController.php
40+
namespace App\Controller;
41+
42+
use Symfony\Component\HttpFoundation\Response;
43+
use Symfony\Component\HttpKernel\Attribute\AsController;
44+
use Symfony\Component\Routing\Attribute\Route;
45+
46+
#[AsController]
47+
class HelloController
48+
{
49+
#[Route('/hello', name: 'hello', methods: ['GET'])]
50+
public function index(): Response
51+
{
52+
// ...
53+
}
54+
}
55+
56+
.. tip::
57+
58+
When using the ``#[Route]`` attribute, Symfony already registers the controller
59+
class as a service, so using the ``#[AsController]`` attribute is redundant.
60+
61+
Using the ``controller.service_arguments`` Service Tag
62+
------------------------------------------------------
63+
64+
If your controllers don't extend the `AbstractController`_ class and you don't
65+
use the ``#[AsController]`` or ``#[Route]`` attributes, you must register the
66+
controllers as public services manually and apply the ``controller.service_arguments``
67+
:doc:`service tag </service_container/tags>` to enable service injection in
68+
controller actions:
1569

1670
.. configuration-block::
1771

@@ -58,26 +112,6 @@ in method parameters:
58112
calls:
59113
- [setContainer, ['@abstract_controller.locator']]
60114
61-
If you prefer, you can use the ``#[AsController]`` PHP attribute to automatically
62-
apply the ``controller.service_arguments`` tag to your controller services::
63-
64-
// src/Controller/HelloController.php
65-
namespace App\Controller;
66-
67-
use Symfony\Component\HttpFoundation\Response;
68-
use Symfony\Component\HttpKernel\Attribute\AsController;
69-
use Symfony\Component\Routing\Attribute\Route;
70-
71-
#[AsController]
72-
class HelloController
73-
{
74-
#[Route('/hello', name: 'hello', methods: ['GET'])]
75-
public function index(): Response
76-
{
77-
// ...
78-
}
79-
}
80-
81115
Registering your controller as a service is the first step, but you also need to
82116
update your routing config to reference the service properly, so that Symfony
83117
knows to use it.

doctrine.rst

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -783,6 +783,32 @@ variable. Let's say you want the first or the last comment of a product dependin
783783
Comment $comment
784784
): Response {
785785
}
786+
787+
.. _doctrine-entity-value-resolver-resolve-target-entities:
788+
789+
Fetch via Interfaces
790+
~~~~~~~~~~~~~~~~~~~~
791+
792+
Suppose your ``Product`` class implements an interface called ``ProductInterface``.
793+
If you want to decouple your controllers from the concrete entity implementation,
794+
you can reference the entity by its interface instead.
795+
796+
To enable this, first configure the
797+
:doc:`resolve_target_entities option </doctrine/resolve_target_entity>`.
798+
Then, your controller can type-hint the interface, and the entity will be
799+
resolved automatically::
800+
801+
public function show(
802+
#[MapEntity]
803+
ProductInterface $product
804+
): Response {
805+
// ...
806+
}
807+
808+
.. versionadded:: 7.3
809+
810+
Support for target entity resolution in the ``EntityValueResolver`` was
811+
introduced Symfony 7.3
786812

787813
MapEntity Options
788814
~~~~~~~~~~~~~~~~~

doctrine/associations.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -447,7 +447,7 @@ by adding JOINs.
447447
$category = $product->getCategory();
448448

449449
// prints "Proxies\AppEntityCategoryProxy"
450-
dump(get_class($category));
450+
dump($category::class);
451451
die();
452452

453453
This proxy object extends the true ``Category`` object, and looks and

0 commit comments

Comments
 (0)