Skip to content

Commit

Permalink
Merge pull request #250 from symfony-cmf/acrobat-symfony5-support-2
Browse files Browse the repository at this point in the history
Symfony 5 support
  • Loading branch information
dbu authored Apr 21, 2020
2 parents d9450c6 + c969140 commit 4f21849
Show file tree
Hide file tree
Showing 15 changed files with 292 additions and 41 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
phpunit.xml
composer.lock
/vendor/
.phpunit.result.cache
9 changes: 4 additions & 5 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@
language: php

php:
- 7.1
- 7.2
- 7.3

Expand All @@ -36,12 +35,12 @@ env:

matrix:
include:
- php: 7.1
env: COMPOSER_FLAGS="--prefer-lowest" SYMFONY_REQUIRE=3.4.* SYMFONY_DEPRECATIONS_HELPER=weak
- php: 7.4
env: SYMFONY_REQUIRE=4.3.*
- php: 7.2
env: COMPOSER_FLAGS="--prefer-lowest" SYMFONY_REQUIRE=4.4.* SYMFONY_DEPRECATIONS_HELPER=weak
- php: 7.4
env: SYMFONY_REQUIRE=4.4.*
- php: 7.4
env: SYMFONY_REQUIRE=5.0.*
fast_finish: true
allow_failures:

Expand Down
23 changes: 22 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,27 @@
Changelog
=========

2.3.0
-----

* Dropped support for PHP 7.1 and Symfony 3.4 and 4.3.
* Added support for Symfony 5.
* Deprecated passing a route object (or anything else that is not a string) as
the `$name` parameter in the `generate` method of the ChainRouter and the
DynamicRouter. Symfony 5 enforces the `$name` parameter to be a string with
static type declaration.
The future proof way to generate a route from an object is to use the route
name `RouteObjectInterface::OBJECT_BASED_ROUTE_NAME` (`cmf_routing_object`)
and pass the route object in the parameters with key
`RouteObjectInterface::ROUTE_OBJECT` (`_route_object`).
* The VersatileGeneratorInterface::supports method is deprecated as it was used
to avoid errors with routers not supporting objects in `$name`.

2.2.0
-----

* Avoid Symfony 4.3 event dispatcher deprecation warnings.

2.1.1
-----

Expand Down Expand Up @@ -36,7 +57,7 @@ Released.
---------

* **2016-11-30**: Changed file structure to have all php code in src/

1.4.0
-----

Expand Down
18 changes: 9 additions & 9 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,20 @@
}
],
"require": {
"php": "^7.1",
"symfony/routing": "^3.4 || ^4.3",
"symfony/http-kernel": "^3.4 || ^4.3",
"php": "^7.2",
"symfony/routing": "^4.4 || ^5.0",
"symfony/http-kernel": "^4.4 || ^5.0",
"psr/log": "^1.0"
},
"require-dev": {
"symfony/phpunit-bridge": "^4.2.2",
"symfony/dependency-injection": "^3.4 || ^4.3",
"symfony/config": "^3.4 || ^4.3",
"symfony/event-dispatcher": "^3.4 || ^4.3",
"symfony/phpunit-bridge": "^5.0",
"symfony/dependency-injection": "^4.4 || ^5.0",
"symfony/config": "^4.4 || ^5.0",
"symfony/event-dispatcher": "^4.4 || ^5.0",
"symfony-cmf/testing": "^3@dev"
},
"suggest": {
"symfony/event-dispatcher": "DynamicRouter can optionally trigger an event at the start of matching. Minimal version (^3.4 || ^4.3)"
"symfony/event-dispatcher": "DynamicRouter can optionally trigger an event at the start of matching. Minimal version (^4.4 || ^5.0)"
},
"autoload": {
"psr-4": {
Expand All @@ -42,7 +42,7 @@
},
"extra": {
"branch-alias": {
"dev-master": "2.2-dev"
"dev-master": "2.x-dev"
}
}
}
4 changes: 4 additions & 0 deletions src/ChainRouter.php
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,10 @@ private function doMatch($pathinfo, Request $request = null)
*/
public function generate($name, $parameters = [], $absolute = UrlGeneratorInterface::ABSOLUTE_PATH)
{
if (is_object($name)) {
@trigger_error('Passing an object as route name is deprecated since version 2.3 and will not work in Symfony 5.0. Pass the `RouteObjectInterface::OBJECT_BASED_ROUTE_NAME` as route name and the object in the parameters with key `RouteObjectInterface::ROUTE_OBJECT`.', E_USER_DEPRECATED);
}

$debug = [];

foreach ($this->all() as $router) {
Expand Down
27 changes: 26 additions & 1 deletion src/ContentAwareGenerator.php
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,15 @@ public function setContentRepository(ContentRepositoryInterface $contentReposito
public function generate($name, $parameters = [], $absolute = UrlGeneratorInterface::ABSOLUTE_PATH)
{
if ($name instanceof SymfonyRoute) {
@trigger_error('Passing an object as route name is deprecated since version 2.3 and will not work in Symfony 5.0. Pass the `RouteObjectInterface::OBJECT_BASED_ROUTE_NAME` as route name and the object in the parameters with key `RouteObjectInterface::ROUTE_OBJECT`.', E_USER_DEPRECATED);

$route = $this->getBestLocaleRoute($name, $parameters);
} elseif (RouteObjectInterface::OBJECT_BASED_ROUTE_NAME === $name) {
if (array_key_exists(RouteObjectInterface::ROUTE_OBJECT, $parameters) && $parameters[RouteObjectInterface::ROUTE_OBJECT] instanceof SymfonyRoute) {
$route = $this->getBestLocaleRoute($parameters[RouteObjectInterface::ROUTE_OBJECT], $parameters);
} else {
$route = $this->getRouteByContent($name, $parameters);
}
} elseif (is_string($name) && $name) {
$route = $this->getRouteByName($name, $parameters);
} else {
Expand Down Expand Up @@ -164,7 +172,14 @@ protected function getBestLocaleRoute(SymfonyRoute $route, $parameters)
protected function getRouteByContent($name, &$parameters)
{
if ($name instanceof RouteReferrersReadInterface) {
@trigger_error('Passing an object as route name is deprecated since version 2.3 and will not work in Symfony 5.0. Pass the `RouteObjectInterface::OBJECT_BASED_ROUTE_NAME` as route name and the object in the parameters with key `RouteObjectInterface::ROUTE_OBJECT`.', E_USER_DEPRECATED);

$content = $name;
} elseif (RouteObjectInterface::OBJECT_BASED_ROUTE_NAME === $name
&& array_key_exists(RouteObjectInterface::ROUTE_OBJECT, $parameters)
&& $parameters[RouteObjectInterface::ROUTE_OBJECT] instanceof RouteReferrersReadInterface
) {
$content = $parameters[RouteObjectInterface::ROUTE_OBJECT];
} elseif (array_key_exists('content_id', $parameters)
&& null !== $this->contentRepository
) {
Expand Down Expand Up @@ -290,10 +305,20 @@ public function supports($name)
*/
public function getRouteDebugMessage($name, array $parameters = [])
{
if (!$name && array_key_exists('content_id', $parameters)) {
if ((!$name || RouteObjectInterface::OBJECT_BASED_ROUTE_NAME === $name)
&& array_key_exists('content_id', $parameters)
) {
return 'Content id '.$parameters['content_id'];
}

if (RouteObjectInterface::OBJECT_BASED_ROUTE_NAME === $name
&& array_key_exists(RouteObjectInterface::ROUTE_OBJECT, $parameters)
&& $parameters[RouteObjectInterface::ROUTE_OBJECT] instanceof RouteReferrersReadInterface
) {
return 'Route aware content '.parent::getRouteDebugMessage($name, $parameters);
}

// legacy
if ($name instanceof RouteReferrersReadInterface) {
return 'Route aware content '.parent::getRouteDebugMessage($name, $parameters);
}
Expand Down
10 changes: 7 additions & 3 deletions src/DynamicRouter.php
Original file line number Diff line number Diff line change
Expand Up @@ -174,9 +174,13 @@ public function getGenerator()
*/
public function generate($name, $parameters = [], $referenceType = UrlGeneratorInterface::ABSOLUTE_PATH)
{
if (is_object($name)) {
@trigger_error('Passing an object as route name is deprecated since version 2.3 and will not work in Symfony 5.0. Pass the `RouteObjectInterface::OBJECT_BASED_ROUTE_NAME` as route name and the object in the parameters with key `RouteObjectInterface::ROUTE_OBJECT', E_USER_DEPRECATED);
}

if ($this->eventDispatcher) {
$event = new RouterGenerateEvent($name, $parameters, $referenceType);
$this->eventDispatcher->dispatch(Events::PRE_DYNAMIC_GENERATE, $event);
$this->eventDispatcher->dispatch($event, Events::PRE_DYNAMIC_GENERATE);
$name = $event->getRoute();
$parameters = $event->getParameters();
$referenceType = $event->getReferenceType();
Expand Down Expand Up @@ -225,7 +229,7 @@ public function match($pathinfo)
$request = Request::create($pathinfo);
if ($this->eventDispatcher) {
$event = new RouterMatchEvent();
$this->eventDispatcher->dispatch(Events::PRE_DYNAMIC_MATCH, $event);
$this->eventDispatcher->dispatch($event, Events::PRE_DYNAMIC_MATCH);
}

if (!empty($this->uriFilterRegexp) && !preg_match($this->uriFilterRegexp, $pathinfo)) {
Expand Down Expand Up @@ -261,7 +265,7 @@ public function matchRequest(Request $request)
{
if ($this->eventDispatcher) {
$event = new RouterMatchEvent($request);
$this->eventDispatcher->dispatch(Events::PRE_DYNAMIC_MATCH_REQUEST, $event);
$this->eventDispatcher->dispatch($event, Events::PRE_DYNAMIC_MATCH_REQUEST);
}

if ($this->uriFilterRegexp
Expand Down
2 changes: 1 addition & 1 deletion src/Event/RouterGenerateEvent.php
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@

namespace Symfony\Cmf\Component\Routing\Event;

use Symfony\Component\EventDispatcher\Event;
use Symfony\Component\Routing\Route;
use Symfony\Contracts\EventDispatcher\Event;

/**
* Event fired before the dynamic router generates a url for a route.
Expand Down
2 changes: 1 addition & 1 deletion src/Event/RouterMatchEvent.php
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@

namespace Symfony\Cmf\Component\Routing\Event;

use Symfony\Component\EventDispatcher\Event;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Contracts\EventDispatcher\Event;

class RouterMatchEvent extends Event
{
Expand Down
20 changes: 20 additions & 0 deletions src/ProviderBasedGenerator.php
Original file line number Diff line number Diff line change
Expand Up @@ -77,10 +77,30 @@ public function supports($name)
*/
public function getRouteDebugMessage($name, array $parameters = [])
{
if (RouteObjectInterface::OBJECT_BASED_ROUTE_NAME === $name
&& array_key_exists(RouteObjectInterface::ROUTE_OBJECT, $parameters)
) {
$routeObject = $parameters[RouteObjectInterface::ROUTE_OBJECT];
if ($routeObject instanceof RouteObjectInterface) {
return 'Route with key '.$routeObject->getRouteKey();
}

if ($routeObject instanceof SymfonyRoute) {
return 'Route with path '.$routeObject->getPath();
}

if (is_object($routeObject)) {
return get_class($routeObject);
}

return 'Null route';
}

if (is_scalar($name)) {
return $name;
}

// legacy
if (is_array($name)) {
return serialize($name);
}
Expand Down
5 changes: 5 additions & 0 deletions src/RouteObjectInterface.php
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,11 @@ interface RouteObjectInterface
*/
const CONTENT_ID = '_content_id';

/**
* Route name used when passing a route object to the generator in $parameters[RouteObjectInterface::ROUTE_OBJECT].
*/
const OBJECT_BASED_ROUTE_NAME = 'cmf_routing_object';

/**
* Get the content document this route entry stands for. If non-null,
* the ControllerClassMapper uses it to identify a controller and
Expand Down
15 changes: 10 additions & 5 deletions src/VersatileGeneratorInterface.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,7 @@
use Symfony\Component\Routing\Generator\UrlGeneratorInterface;

/**
* This generator is able to handle more than string route names as symfony
* core supports them.
* This generator can provide additional information about the route that we wanted to generate.
*/
interface VersatileGeneratorInterface extends UrlGeneratorInterface
{
Expand All @@ -26,6 +25,13 @@ interface VersatileGeneratorInterface extends UrlGeneratorInterface
* resolved to a route, only whether the router can generate routes from
* objects of this class.
*
* @deprecated This method is deprecated since version 2.3 and will be
* removed in version 3.O.
*
* This method was used to not call generators that can not handle objects
* in $name. With Symfony 5, this becomes obsolete as the strict type
* declaration prevents passing anything else than a string as $name.
*
* @param mixed $name The route "name" which may also be an object or anything
*
* @return bool
Expand All @@ -36,9 +42,8 @@ public function supports($name);
* Convert a route identifier (name, content object etc) into a string
* usable for logging and other debug/error messages.
*
* @param mixed $name
* @param array $parameters which should contain a content field containing
* a RouteReferrersReadInterface object
* @param mixed $name In Symfony 5, the name can only be a string
* @param array $parameters Which might hold a route object or content id or similar to include in the debug message
*
* @return string
*/
Expand Down
Loading

0 comments on commit 4f21849

Please sign in to comment.