From c63120478bc7c85974f5c0959c84cedd9d287d4c Mon Sep 17 00:00:00 2001 From: Manuel Raynaud Date: Thu, 5 Sep 2013 12:25:27 +0200 Subject: [PATCH 1/5] start refactorin rewriting routing --- .../Controller/Front/UrlRewritingController.php | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/core/lib/Thelia/Controller/Front/UrlRewritingController.php b/core/lib/Thelia/Controller/Front/UrlRewritingController.php index 2e725aecd..a024cbaea 100755 --- a/core/lib/Thelia/Controller/Front/UrlRewritingController.php +++ b/core/lib/Thelia/Controller/Front/UrlRewritingController.php @@ -53,7 +53,7 @@ class UrlRewritingController extends BaseFrontController /* define GET arguments in request */ if(null !== $rewrittenUrlData->view) { - $request->query->set('view', $rewrittenUrlData->view); + $request->attributes->set('_view', $rewrittenUrlData->view); if(null !== $rewrittenUrlData->viewId) { $request->query->set($rewrittenUrlData->view . '_id', $rewrittenUrlData->viewId); } @@ -66,16 +66,6 @@ class UrlRewritingController extends BaseFrontController $request->query->set($parameter, $value); } } - - if (! $view = $request->query->get('view')) { - $view = "index"; - if ($request->request->has('view')) { - $view = $request->request->get('view'); - } - } - - $request->attributes->set('_view', $view); - } } From a0f894d70f9fbc274f9ef9c98b04bce36eb6710f Mon Sep 17 00:00:00 2001 From: Etienne Roudeix Date: Thu, 5 Sep 2013 17:54:04 +0200 Subject: [PATCH 2/5] customer substitutions --- .../Template/Smarty/Plugins/DataAccessFunctions.php | 12 ++++++------ templates/default/debug.html | 13 ++----------- 2 files changed, 8 insertions(+), 17 deletions(-) diff --git a/core/lib/Thelia/Core/Template/Smarty/Plugins/DataAccessFunctions.php b/core/lib/Thelia/Core/Template/Smarty/Plugins/DataAccessFunctions.php index ee65f34b3..a2fd10c15 100755 --- a/core/lib/Thelia/Core/Template/Smarty/Plugins/DataAccessFunctions.php +++ b/core/lib/Thelia/Core/Template/Smarty/Plugins/DataAccessFunctions.php @@ -68,14 +68,14 @@ class DataAccessFunctions extends AbstractSmartyPlugin } /** - * Provides access to user attributes using the accessors. + * @param $objectLabel + * @param $user + * @param $params * - * @param array $params - * @param unknown $smarty - * @return string the value of the requested attribute - * @throws InvalidArgumentException if the object does not have the requested attribute. + * @return string + * @throws \InvalidArgumentException */ - protected function userDataAccess($objectLabel, $user, $params) + protected function userDataAccess($objectLabel, $user, $params) { $attribute = $this->getNormalizedParam($params, array('attribute', 'attrib', 'attr')); diff --git a/templates/default/debug.html b/templates/default/debug.html index 461e8eed7..1c54c05a4 100755 --- a/templates/default/debug.html +++ b/templates/default/debug.html @@ -1,11 +1,2 @@ -

ALL ATTRIBUTES

- - \ No newline at end of file +::{customer attr="firstname"};; +::{customer attr="titleId"};; \ No newline at end of file From 00d7d9b29a9afbd152d3e096442e021d7544dedd Mon Sep 17 00:00:00 2001 From: Manuel Raynaud Date: Thu, 5 Sep 2013 20:46:46 +0200 Subject: [PATCH 3/5] create router for rewriting matching --- core/lib/Thelia/Config/Resources/routing.xml | 4 + .../Thelia/Config/Resources/routing/front.xml | 9 - .../Thelia/Core/Routing/RewritingRouter.php | 218 ++++++++++++++++++ 3 files changed, 222 insertions(+), 9 deletions(-) create mode 100644 core/lib/Thelia/Core/Routing/RewritingRouter.php diff --git a/core/lib/Thelia/Config/Resources/routing.xml b/core/lib/Thelia/Config/Resources/routing.xml index 5200aefc1..a8ad18abf 100755 --- a/core/lib/Thelia/Config/Resources/routing.xml +++ b/core/lib/Thelia/Config/Resources/routing.xml @@ -75,6 +75,10 @@ %kernel.debug% + + + + diff --git a/core/lib/Thelia/Config/Resources/routing/front.xml b/core/lib/Thelia/Config/Resources/routing/front.xml index 4cf2d710c..861ccb93e 100755 --- a/core/lib/Thelia/Config/Resources/routing/front.xml +++ b/core/lib/Thelia/Config/Resources/routing/front.xml @@ -60,13 +60,4 @@ cart - - diff --git a/core/lib/Thelia/Core/Routing/RewritingRouter.php b/core/lib/Thelia/Core/Routing/RewritingRouter.php new file mode 100644 index 000000000..570372f60 --- /dev/null +++ b/core/lib/Thelia/Core/Routing/RewritingRouter.php @@ -0,0 +1,218 @@ +. */ +/* */ +/*************************************************************************************/ + +namespace Thelia\Core\Routing; +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\Routing\Exception\InvalidParameterException; +use Symfony\Component\Routing\Exception\MethodNotAllowedException; +use Symfony\Component\Routing\Exception\MissingMandatoryParametersException; +use Symfony\Component\Routing\Exception\ResourceNotFoundException; +use Symfony\Component\Routing\Exception\RouteNotFoundException; +use Symfony\Component\Routing\Matcher\RequestMatcherInterface; +use Symfony\Component\Routing\RequestContext; +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Routing\RouterInterface; +use Thelia\Exception\RedirectException; +use Thelia\Exception\UrlRewritingException; +use Thelia\Model\ConfigQuery; +use Thelia\Tools\Redirect; +use Thelia\Tools\URL; + + +/** + * Class RewritingRouter + * @package Thelia\Core\Routing + * @author Manuel Raynaud + */ +class RewritingRouter implements RouterInterface, RequestMatcherInterface +{ + + /** + * @var RequestContext The context + */ + protected $context; + + /** + * @var options, don't use for now but mandatory + */ + protected $options; + + /** + * Sets the request context. + * + * @param RequestContext $context The context + * + * @api + */ + public function setContext(RequestContext $context) + { + // TODO: Implement setContext() method. + $this->context = $context; + } + + /** + * Gets the request context. + * + * @return RequestContext The context + * + * @api + */ + public function getContext() + { + // TODO: Implement getContext() method. + return $this->context; + } + + public function setOption($key, $value) + { + //NOTHING TO DO FOR NOW + } + + /** + * Gets the RouteCollection instance associated with this Router. + * + * @return RouteCollection A RouteCollection instance + */ + public function getRouteCollection() + { + return new RouteCollection(); + } + + /** + * Generates a URL or path for a specific route based on the given parameters. + * + * Parameters that reference placeholders in the route pattern will substitute them in the + * path or host. Extra params are added as query string to the URL. + * + * When the passed reference type cannot be generated for the route because it requires a different + * host or scheme than the current one, the method will return a more comprehensive reference + * that includes the required params. For example, when you call this method with $referenceType = ABSOLUTE_PATH + * but the route requires the https scheme whereas the current scheme is http, it will instead return an + * ABSOLUTE_URL with the https scheme and the current host. This makes sure the generated URL matches + * the route in any case. + * + * If there is no route with the given name, the generator must throw the RouteNotFoundException. + * + * @param string $name The name of the route + * @param mixed $parameters An array of parameters + * @param Boolean|string $referenceType The type of reference to be generated (one of the constants) + * + * @return string The generated URL + * + * @throws RouteNotFoundException If the named route doesn't exist + * @throws MissingMandatoryParametersException When some parameters are missing that are mandatory for the route + * @throws InvalidParameterException When a parameter value for a placeholder is not correct because + * it does not match the requirement + * + * @api + */ + public function generate($name, $parameters = array(), $referenceType = self::ABSOLUTE_PATH) + { + // TODO: Implement generate() method. + } + + /** + * Tries to match a URL path with a set of routes. + * + * If the matcher can not find information, it must throw one of the exceptions documented + * below. + * + * @param string $pathinfo The path info to be parsed (raw format, i.e. not urldecoded) + * + * @return array An array of parameters + * + * @throws ResourceNotFoundException If the resource could not be found + * @throws MethodNotAllowedException If the resource was found but the request method is not allowed + * + * @api + */ + public function match($pathinfo) + { + throw new ResourceNotFoundException("impossible to find route with this method, please use matchRequest method"); + } + + /** + * Tries to match a request with a set of routes. + * + * If the matcher can not find information, it must throw one of the exceptions documented + * below. + * + * @param Request $request The request to match + * + * @throws \Exception|\Thelia\Exception\UrlRewritingException + * @throws \Symfony\Component\Routing\Exception\ResourceNotFoundException + * @throws \Thelia\Exception\RedirectException + * @return array An array of parameters + * + */ + public function matchRequest(Request $request) + { + if(ConfigQuery::isRewritingEnable()) { + try { + $rewrittenUrlData = URL::getInstance()->resolve($request->getPathInfo()); + var_dump($rewrittenUrlData); exit; + } catch(UrlRewritingException $e) { + switch($e->getCode()) { + case UrlRewritingException::URL_NOT_FOUND : + throw new ResourceNotFoundException(); + break; + default: + throw $e; + } + } + + /* is the URL redirected ? */ + + if(null !== $rewrittenUrlData->redirectedToUrl) { + $this->redirect($rewrittenUrlData->redirectedToUrl, 301); + } + + /* define GET arguments in request */ + + if(null !== $rewrittenUrlData->view) { + $request->attributes->set('_view', $rewrittenUrlData->view); + if(null !== $rewrittenUrlData->viewId) { + $request->query->set($rewrittenUrlData->view . '_id', $rewrittenUrlData->viewId); + } + } + if(null !== $rewrittenUrlData->locale) { + $request->query->set('locale', $rewrittenUrlData->locale); + } + + foreach($rewrittenUrlData->otherParameters as $parameter => $value) { + $request->query->set($parameter, $value); + } + + return array ( + '_controller' => 'Thelia\\Controller\\Front\\DefaultController::noAction', + '_route' => 'rewrite' + ); + } + throw new ResourceNotFoundException(); + } + + protected function redirect($url, $code = 302) + { + Redirect::exec($url, $status); + } +} \ No newline at end of file From 89ad332d8895d2830b2a415408c387e7750f9eda Mon Sep 17 00:00:00 2001 From: Manuel Raynaud Date: Fri, 6 Sep 2013 08:24:03 +0200 Subject: [PATCH 4/5] use good Request object --- core/lib/Thelia/Tests/Controller/DefaultControllerTest.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/lib/Thelia/Tests/Controller/DefaultControllerTest.php b/core/lib/Thelia/Tests/Controller/DefaultControllerTest.php index 33ea807e3..177802078 100755 --- a/core/lib/Thelia/Tests/Controller/DefaultControllerTest.php +++ b/core/lib/Thelia/Tests/Controller/DefaultControllerTest.php @@ -23,7 +23,7 @@ namespace Thelia\Tests\Controller; -use Symfony\Component\HttpFoundation\Request; +use Thelia\Core\HttpFoundation\Request; use Thelia\Controller\Front\DefaultController; /** From b95218295db1283b18e8d4fa82c3ad39261efaa2 Mon Sep 17 00:00:00 2001 From: Etienne Roudeix Date: Fri, 6 Sep 2013 08:59:06 +0200 Subject: [PATCH 5/5] rewriting router --- .../Controller/Front/DefaultController.php | 20 +++++++++---------- .../Thelia/Core/Routing/RewritingRouter.php | 7 ++++--- .../Template/Smarty/Plugins/UrlGenerator.php | 2 +- .../Thelia/Rewriting/RewritingResolver.php | 2 ++ .../Thelia/Rewriting/RewritingRetriever.php | 2 ++ core/lib/Thelia/Tools/URL.php | 8 ++++---- 6 files changed, 23 insertions(+), 18 deletions(-) diff --git a/core/lib/Thelia/Controller/Front/DefaultController.php b/core/lib/Thelia/Controller/Front/DefaultController.php index 58501ebb0..fe7e1aede 100755 --- a/core/lib/Thelia/Controller/Front/DefaultController.php +++ b/core/lib/Thelia/Controller/Front/DefaultController.php @@ -46,16 +46,6 @@ class DefaultController extends BaseFrontController */ public function noAction(Request $request) { - if(ConfigQuery::isRewritingEnable()) { - - /* Does the query GET parameters match a rewritten URL ? */ - $rewrittenUrl = URL::getInstance()->retrieveCurrent($request); - if($rewrittenUrl->rewrittenUrl !== null) { - /* 301 redirection to rewritten URL */ - $this->redirect($rewrittenUrl->rewrittenUrl, 301); - } - } - $view = null; if (! $view = $request->query->get('view')) { @@ -71,5 +61,15 @@ class DefaultController extends BaseFrontController $request->attributes->set("_view", "index"); } + if(ConfigQuery::isRewritingEnable()) { + if($request->attributes->get('_rewritten', false) === false) { + /* Does the query GET parameters match a rewritten URL ? */ + $rewrittenUrl = URL::getInstance()->retrieveCurrent($request); + if($rewrittenUrl->rewrittenUrl !== null) { + /* 301 redirection to rewritten URL */ + $this->redirect($rewrittenUrl->rewrittenUrl, 301); + } + } + } } } diff --git a/core/lib/Thelia/Core/Routing/RewritingRouter.php b/core/lib/Thelia/Core/Routing/RewritingRouter.php index 570372f60..79d5dc80b 100644 --- a/core/lib/Thelia/Core/Routing/RewritingRouter.php +++ b/core/lib/Thelia/Core/Routing/RewritingRouter.php @@ -43,6 +43,7 @@ use Thelia\Tools\URL; * Class RewritingRouter * @package Thelia\Core\Routing * @author Manuel Raynaud + * @author Etienne Roudeix */ class RewritingRouter implements RouterInterface, RequestMatcherInterface { @@ -170,7 +171,6 @@ class RewritingRouter implements RouterInterface, RequestMatcherInterface if(ConfigQuery::isRewritingEnable()) { try { $rewrittenUrlData = URL::getInstance()->resolve($request->getPathInfo()); - var_dump($rewrittenUrlData); exit; } catch(UrlRewritingException $e) { switch($e->getCode()) { case UrlRewritingException::URL_NOT_FOUND : @@ -205,13 +205,14 @@ class RewritingRouter implements RouterInterface, RequestMatcherInterface return array ( '_controller' => 'Thelia\\Controller\\Front\\DefaultController::noAction', - '_route' => 'rewrite' + '_route' => 'rewrite', + '_rewritten' => true, ); } throw new ResourceNotFoundException(); } - protected function redirect($url, $code = 302) + protected function redirect($url, $status = 302) { Redirect::exec($url, $status); } diff --git a/core/lib/Thelia/Core/Template/Smarty/Plugins/UrlGenerator.php b/core/lib/Thelia/Core/Template/Smarty/Plugins/UrlGenerator.php index 72b3b88fb..f6c20ecfb 100755 --- a/core/lib/Thelia/Core/Template/Smarty/Plugins/UrlGenerator.php +++ b/core/lib/Thelia/Core/Template/Smarty/Plugins/UrlGenerator.php @@ -169,7 +169,7 @@ class UrlGenerator extends AbstractSmartyPlugin protected function getCurrentUrl() { - return URL::getInstance()->retrieveCurrent()->toString(); + return URL::getInstance()->retrieveCurrent($this->request)->toString(); } protected function getReturnToUrl() diff --git a/core/lib/Thelia/Rewriting/RewritingResolver.php b/core/lib/Thelia/Rewriting/RewritingResolver.php index 900442db9..4c8bcba40 100755 --- a/core/lib/Thelia/Rewriting/RewritingResolver.php +++ b/core/lib/Thelia/Rewriting/RewritingResolver.php @@ -58,6 +58,8 @@ class RewritingResolver public function load($rewrittenUrl) { + $rewrittenUrl = ltrim($rewrittenUrl, '/'); + $this->search = $this->rewritingUrlQuery->getResolverSearch($rewrittenUrl); if($this->search->count() == 0) { diff --git a/core/lib/Thelia/Rewriting/RewritingRetriever.php b/core/lib/Thelia/Rewriting/RewritingRetriever.php index dfbe63517..8289942f2 100755 --- a/core/lib/Thelia/Rewriting/RewritingRetriever.php +++ b/core/lib/Thelia/Rewriting/RewritingRetriever.php @@ -66,6 +66,7 @@ class RewritingRetriever $allParametersWithoutView[$view . '_id'] = $viewId; } + $this->rewrittenUrl = null; $this->url = URL::getInstance()->viewUrl($view, $allParametersWithoutView); if($this->search !== null) { $this->rewrittenUrl = $this->search->getUrl(); @@ -93,6 +94,7 @@ class RewritingRetriever $allParametersWithoutView[$view . '_id'] = $viewId; } + $this->rewrittenUrl = null; $this->url = URL::getInstance()->viewUrl($view, $allParametersWithoutView); if($this->search !== null) { $this->rewrittenUrl = $this->search->getUrl(); diff --git a/core/lib/Thelia/Tools/URL.php b/core/lib/Thelia/Tools/URL.php index 152f82895..161175bbf 100755 --- a/core/lib/Thelia/Tools/URL.php +++ b/core/lib/Thelia/Tools/URL.php @@ -204,20 +204,20 @@ class URL public function retrieveCurrent(Request $request) { if(ConfigQuery::isRewritingEnable()) { - $view = $request->query->get('view', null); + $view = $request->attributes->get('_view', null); $viewLocale = $request->query->get('locale', null); $viewId = $view === null ? null : $request->query->get($view . '_id', null); $allOtherParameters = $request->query->all(); if($view !== null) { unset($allOtherParameters['view']); + if($viewId !== null) { + unset($allOtherParameters[$view . '_id']); + } } if($viewLocale !== null) { unset($allOtherParameters['locale']); } - if($viewId !== null) { - unset($allOtherParameters[$view . '_id']); - } $this->retriever->loadSpecificUrl($view, $viewLocale, $viewId, $allOtherParameters); }