Skip to content

Commit 6b7d307

Browse files
committed
Merge branch '2.4'
2 parents 6bdcdb1 + 479ec86 commit 6b7d307

File tree

9 files changed

+141
-37
lines changed

9 files changed

+141
-37
lines changed

book/forms.rst

+4-9
Original file line numberDiff line numberDiff line change
@@ -477,14 +477,10 @@ Disabling Validation
477477
~~~~~~~~~~~~~~~~~~~~
478478

479479
.. versionadded:: 2.3
480-
The ability to set ``validation_groups`` to false was added in Symfony 2.3,
481-
although setting it to an empty array achieved the same result in previous
482-
versions.
480+
The ability to set ``validation_groups`` to false was added in Symfony 2.3.
483481

484482
Sometimes it is useful to suppress the validation of a form altogether. For
485-
these cases, you can skip the call to :method:`Symfony\\Component\\Form\\FormInterface::isValid`
486-
in your controller. If this is not possible, you can alternatively set the
487-
``validation_groups`` option to ``false`` or an empty array::
483+
these cases you can set the ``validation_groups`` option to ``false``::
488484

489485
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
490486

@@ -497,9 +493,8 @@ in your controller. If this is not possible, you can alternatively set the
497493

498494
Note that when you do that, the form will still run basic integrity checks,
499495
for example whether an uploaded file was too large or whether non-existing
500-
fields were submitted. If you want to suppress validation completely, remove
501-
the :method:`Symfony\\Component\\Form\\FormInterface::isValid` call from your
502-
controller.
496+
fields were submitted. If you want to suppress validation, you can use the
497+
:ref:`POST_SUBMIT event <cookbook-dynamic-form-modification-suppressing-form-validation>`
503498

504499
.. index::
505500
single: Forms; Validation groups based on submitted data

book/http_cache.rst

+24-21
Original file line numberDiff line numberDiff line change
@@ -301,9 +301,11 @@ The ``Cache-Control`` header is unique in that it contains not one, but various
301301
pieces of information about the cacheability of a response. Each piece of
302302
information is separated by a comma:
303303

304-
Cache-Control: private, max-age=0, must-revalidate
304+
.. code-block:: text
305+
306+
Cache-Control: private, max-age=0, must-revalidate
305307
306-
Cache-Control: max-age=3600, must-revalidate
308+
Cache-Control: max-age=3600, must-revalidate
307309
308310
Symfony provides an abstraction around the ``Cache-Control`` header to make
309311
its creation more manageable::
@@ -385,7 +387,7 @@ header when none is set by the developer by following these rules:
385387
* If ``Cache-Control`` is empty (but one of the other cache headers is present),
386388
its value is set to ``private, must-revalidate``;
387389

388-
* But if at least one ``Cache-Control`` directive is set, and no 'public' or
390+
* But if at least one ``Cache-Control`` directive is set, and no ``public`` or
389391
``private`` directives have been explicitly added, Symfony2 adds the
390392
``private`` directive automatically (except when ``s-maxage`` is set).
391393

@@ -667,7 +669,7 @@ exposing a simple and efficient pattern::
667669
// a database or a key-value store for instance)
668670
$article = ...;
669671

670-
// create a Response with a ETag and/or a Last-Modified header
672+
// create a Response with an ETag and/or a Last-Modified header
671673
$response = new Response();
672674
$response->setETag($article->computeETag());
673675
$response->setLastModified($article->getPublishedAt());
@@ -679,17 +681,17 @@ exposing a simple and efficient pattern::
679681
if ($response->isNotModified($request)) {
680682
// return the 304 Response immediately
681683
return $response;
682-
} else {
683-
// do more work here - like retrieving more data
684-
$comments = ...;
685-
686-
// or render a template with the $response you've already started
687-
return $this->render(
688-
'MyBundle:MyController:article.html.twig',
689-
array('article' => $article, 'comments' => $comments),
690-
$response
691-
);
692684
}
685+
686+
// do more work here - like retrieving more data
687+
$comments = ...;
688+
689+
// or render a template with the $response you've already started
690+
return $this->render(
691+
'MyBundle:MyController:article.html.twig',
692+
array('article' => $article, 'comments' => $comments),
693+
$response
694+
);
693695
}
694696

695697
When the ``Response`` is not modified, the ``isNotModified()`` automatically sets
@@ -956,8 +958,9 @@ component cache will only last for 60 seconds.
956958
When using a controller reference, the ESI tag should reference the embedded
957959
action as an accessible URL so the gateway cache can fetch it independently of
958960
the rest of the page. Symfony2 takes care of generating a unique URL for any
959-
controller reference and it is able to route them properly thanks to a
960-
listener that must be enabled in your configuration:
961+
controller reference and it is able to route them properly thanks to the
962+
:class:`Symfony\\Component\\HttpKernel\\EventListener\\FragmentListener`
963+
that must be enabled in your configuration:
961964

962965
.. configuration-block::
963966

@@ -1063,10 +1066,10 @@ Here is how you can configure the Symfony2 reverse proxy to support the
10631066
}
10641067

10651068
$response = new Response();
1066-
if (!$this->getStore()->purge($request->getUri())) {
1067-
$response->setStatusCode(Response::HTTP_NOT_FOUND, 'Not purged');
1068-
} else {
1069+
if ($this->getStore()->purge($request->getUri())) {
10691070
$response->setStatusCode(Response::HTTP_OK, 'Purged');
1071+
} else {
1072+
$response->setStatusCode(Response::HTTP_NOT_FOUND, 'Not purged');
10701073
}
10711074

10721075
return $response;
@@ -1104,6 +1107,6 @@ Learn more from the Cookbook
11041107
.. _`validation model`: http://tools.ietf.org/html/rfc2616#section-13.3
11051108
.. _`RFC 2616`: http://tools.ietf.org/html/rfc2616
11061109
.. _`HTTP Bis`: http://tools.ietf.org/wg/httpbis/
1107-
.. _`P4 - Conditional Requests`: http://tools.ietf.org/html/draft-ietf-httpbis-p4-conditional-12
1108-
.. _`P6 - Caching: Browser and intermediary caches`: http://tools.ietf.org/html/draft-ietf-httpbis-p6-cache-12
1110+
.. _`P4 - Conditional Requests`: http://tools.ietf.org/html/draft-ietf-httpbis-p4-conditional
1111+
.. _`P6 - Caching: Browser and intermediary caches`: http://tools.ietf.org/html/draft-ietf-httpbis-p6-cache
11091112
.. _`ESI`: http://www.w3.org/TR/esi-lang

book/validation.rst

+1-1
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ The job of the ``validator`` is easy: to read the constraints (i.e. rules)
115115
of a class and verify whether or not the data on the object satisfies those
116116
constraints. If validation fails, a non-empty list of errors
117117
(class :class:`Symfony\\Component\\Validator\\ConstraintViolationList`) is
118-
returned. Take this simple example from inside a controller:
118+
returned. Take this simple example from inside a controller::
119119

120120
// ...
121121
use Symfony\Component\HttpFoundation\Response;

cookbook/form/dynamic_form_modification.rst

+32
Original file line numberDiff line numberDiff line change
@@ -583,3 +583,35 @@ after the sport is selected. This should be handled by making an AJAX call
583583
back to your application. In that controller, you can submit your form, but
584584
instead of processing it, simply use the submitted form to render the updated
585585
fields. The response from the AJAX call can then be used to update the view.
586+
587+
.. _cookbook-dynamic-form-modification-suppressing-form-validation:
588+
589+
Suppressing Form Validation
590+
---------------------------
591+
592+
To suppress form validation you can use the ``POST_SUBMIT`` event and prevent
593+
the :class:`Symfony\\Component\\Form\\Extension\\Validator\\EventListener\\ValidationListener`
594+
from being called.
595+
596+
The reason for needing to do this is that even if you set ``group_validation``
597+
to ``false`` there are still some integrity checks executed. For example
598+
an uploaded file will still be checked to see if it is too large and the form
599+
will still check to see if non-existing fields were submitted. To disable
600+
all of this, use a listener::
601+
602+
use Symfony\Component\Form\FormBuilderInterface;
603+
use Symfony\Component\Form\FormEvents;
604+
605+
public function buildForm(FormBuilderInterface $builder, array $options)
606+
{
607+
$builder->addEventListener(FormEvents::POST_SUBMIT, function($event) {
608+
$event->stopPropagation();
609+
}, 900); // Always set a higher priority than ValidationListener
610+
611+
// ...
612+
}
613+
614+
.. caution::
615+
616+
By doing this, you may accidentally disable something more than just form
617+
validation, since the ``POST_SUBMIT`` event may have other listeners.

cookbook/map.rst.inc

+1
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,7 @@
109109

110110
* :doc:`/cookbook/profiler/data_collector`
111111
* :doc:`/cookbook/profiler/matchers`
112+
* :doc:`/cookbook/profiler/storage`
112113

113114
* :doc:`/cookbook/request/index`
114115

cookbook/profiler/index.rst

+1
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,4 @@ Profiler
66

77
data_collector
88
matchers
9+
storage

cookbook/profiler/storage.rst

+69
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
.. index::
2+
single: Profiling; Storage Configuration
3+
4+
Switching the Profiler Storage
5+
==============================
6+
7+
By default the profile stores the collected data in files in the cache directory.
8+
You can control the storage being used through the ``dsn``, ``username``,
9+
``password`` and ``lifetime`` options. For example, the following configuration
10+
uses MySQL as the storage for the profiler with a lifetime of one hour:
11+
12+
.. configuration-block::
13+
14+
.. code-block:: yaml
15+
16+
# app/config/config.yml
17+
framework:
18+
profiler:
19+
dsn: "mysql:host=localhost;dbname=%database_name%"
20+
username: "%database_user%"
21+
password: "%database_password%"
22+
lifetime: 3600
23+
24+
.. code-block:: xml
25+
26+
<!-- app/config/config.xml -->
27+
<?xml version="1.0" encoding="UTF-8" ?>
28+
<container xmlns="http://symfony.com/schema/dic/services"
29+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
30+
xmlns:framework="http://symfony.com/schema/dic/symfony"
31+
xsi:schemaLocation="http://symfony.com/schema/dic/services
32+
http://symfony.com/schema/dic/services/services-1.0.xsd
33+
http://symfony.com/schema/dic/symfony
34+
http://symfony.com/schema/dic/symfony/symfony-1.0.xsd"
35+
>
36+
<framework:config>
37+
<framework:profiler
38+
dsn="mysql:host=localhost;dbname=%database_name%"
39+
username="%database_user%"
40+
password="%database_password%"
41+
lifetime="3600"
42+
/>
43+
</framework:config>
44+
</container>
45+
46+
.. code-block:: php
47+
48+
// app/config/config.php
49+
50+
// ...
51+
$container->loadFromExtension('framework', array(
52+
'profiler' => array(
53+
'dsn' => 'mysql:host=localhost;dbname=%database_name%',
54+
'username' => '%database_user',
55+
'password' => '%database_password%',
56+
'lifetime' => 3600,
57+
),
58+
));
59+
60+
The :doc:`HttpKernel component </components/http_kernel/introduction>` currently
61+
supports the following profiler storage implementations:
62+
63+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\FileProfilerStorage`
64+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\MemcachedProfilerStorage`
65+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\MemcacheProfilerStorage`
66+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\MongoDbProfilerStorage`
67+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\MysqlProfilerStorage`
68+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\RedisProfilerStorage`
69+
* :class:`Symfony\\Component\\HttpKernel\\Profiler\\SqliteProfilerStorage`

cookbook/security/entity_provider.rst

+3-3
Original file line numberDiff line numberDiff line change
@@ -226,7 +226,7 @@ user records and encode their password, see :ref:`book-security-encoding-user-pa
226226

227227
.. code-block:: bash
228228
229-
$ mysql> select * from acme_users;
229+
$ mysql> SELECT * FROM acme_users;
230230
+----+----------+------+------------------------------------------+--------------------+-----------+
231231
| id | username | salt | password | email | is_active |
232232
+----+----------+------+------------------------------------------+--------------------+-----------+
@@ -682,14 +682,14 @@ this:
682682

683683
.. code-block:: bash
684684
685-
$ mysql> select * from acme_role;
685+
$ mysql> SELECT * FROM acme_role;
686686
+----+-------+------------+
687687
| id | name | role |
688688
+----+-------+------------+
689689
| 1 | admin | ROLE_ADMIN |
690690
+----+-------+------------+
691691
692-
$ mysql> select * from user_role;
692+
$ mysql> SELECT * FROM user_role;
693693
+---------+---------+
694694
| user_id | role_id |
695695
+---------+---------+

cookbook/service_container/scopes.rst

+6-3
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,7 @@ marked as ``synchronized``:
134134
class: Acme\HelloBundle\Client\ClientConfiguration
135135
scope: client
136136
synchronized: true
137+
synthetic: true
137138
# ...
138139
139140
.. code-block:: xml
@@ -151,6 +152,7 @@ marked as ``synchronized``:
151152
id="client_configuration"
152153
scope="client"
153154
synchronized="true"
155+
synthetic="true"
154156
class="Acme\HelloBundle\Client\ClientConfiguration"
155157
/>
156158
</services>
@@ -167,6 +169,7 @@ marked as ``synchronized``:
167169
);
168170
$definition->setScope('client');
169171
$definition->setSynchronized(true);
172+
$definition->setSynthetic(true);
170173
$container->setDefinition('client_configuration', $definition);
171174
172175
Now, if you inject this service using setter injection, there are no drawbacks
@@ -196,9 +199,9 @@ and everything works without any special code in your service or in your definit
196199
}
197200
}
198201

199-
Whenever the ``client`` scope is entered or left, the service container will
200-
automatically call the ``setClientConfiguration()`` method with the current
201-
``client_configuration`` instance.
202+
Whenever the ``client`` scope is active, the service container will
203+
automatically call the ``setClientConfiguration()`` method when the
204+
``client_configuration`` service is set in the container.
202205

203206
You might have noticed that the ``setClientConfiguration()`` method accepts
204207
``null`` as a valid value for the ``client_configuration`` argument. That's

0 commit comments

Comments
 (0)