Может кому-то пригодится, а может кто-то что-то и посоветует
Что умеет класс:
- убирает дубли вида index.php/controller/action (если showScriptName => false)
- Если у вас есть rules для метода, то стандартный url будет редиректиться(301) на "правильный url"
- если withoutWww =>true то будет редирект(301) с www на без www
- если SlashTheEnd => true то редирект(301) на url со слешем в конце, если не определен suffix для роута
Код: Выделить всё
<?php
namespace app\components;
use Yii;
use yii\web\UrlManager;
use yii\helpers\Url;
use yii\caching\Cache;
class MyUrlManager extends UrlManager {
/**
* @var boolean когда true redirect с www на без www
*/
public $withoutWww = false;
/**
* @var boolean когда true redirect с без / в конце на /
*/
public $SlashTheEnd = true;
public function parseRequest($request) {
if ($this->suffix == '' && $this->SlashTheEnd == true)
$this->suffix = '/';
$this->indexFix();
if ($this->enablePrettyUrl) {
$pathInfo = $request->getPathInfo();
/* @var $rule UrlRule */
foreach ($this->rules as $rule) {
if (($result = $rule->parseRequest($this, $request)) !== false) {
$this->doubleUrlFix($result);
$url = $this->wwwFix();
return $result;
}
}
if ($this->enableStrictParsing) {
return false;
}
Yii::trace('No matching URL rules. Using default URL parsing logic.', __METHOD__);
$suffix = (string) $this->suffix;
if ($suffix !== '' && $pathInfo !== '') {
$n = strlen($this->suffix);
if (substr_compare($pathInfo, $this->suffix, -$n, $n) === 0) {
$pathInfo = substr($pathInfo, 0, -$n);
if ($pathInfo === '') {
// suffix alone is not allowed
return false;
}
} else {
// suffix doesn't match
$this->doubleUrlFix([$pathInfo, []]);
return false;
}
}
$url = [$pathInfo, []];
$this->doubleUrlFix($url);
$url = $this->wwwFix();
return $url;
} else {
Yii::trace('Pretty URL not enabled. Using default URL parsing logic.', __METHOD__);
$route = $request->getQueryParam($this->routeParam, '');
if (is_array($route)) {
$route = '';
}
return [(string) $route, []];
}
}
/**
* Редирект на без www
* @param string $url
* @return string|bool $url|redirect
*/
public function wwwFix($url = false) {
if (strpos(Yii::$app->request->hostInfo, 'www.') !== false && $this->withoutWww == true) {
if ($url) {
return str_replace('www.', '', Yii::$app->request->hostInfo) . $url;
} else {
$url = str_replace('www.', '', Yii::$app->request->hostInfo) . Yii::$app->request->url;
Yii::$app->getResponse()->redirect($url, 301);
header('HTTP/1.1 301 Moved Permanently');
header('Location: ' . $url);
Yii::$app->end();
}
} else {
return $url;
}
}
/**
* Убирает дубли страниц
* @param type $url
* @param type $r
*/
private function doubleUrlFix($url) {
$url[0] = trim($url[0], '/');
$url = Url::to(array_merge(['/' . $url[0]], array_merge($url[1], Yii::$app->request->get())));
if ($url != Url::to()) {
$url = $this->wwwFix($url);
Yii::$app->getResponse()->redirect($url, 301);
header('HTTP/1.1 301 Moved Permanently');
header('Location: ' . $url);
Yii::$app->end();
}
}
/**
* убирает дубли через index.php
*/
public function indexFix() {
if (strpos(Yii::$app->request->url, Yii::$app->request->scriptUrl) !== FALSE && $this->showScriptName == false) {
$url = str_replace(Yii::$app->request->scriptUrl, '', Yii::$app->request->url);
if (strpos($url, '/') !== 0) {
$url = '/' . $url;
}
$this->doubleUrlFix([$url, []]);
$url = $this->wwwFix($url);
Yii::$app->getResponse()->redirect($url, 301);
header('HTTP/1.1 301 Moved Permanently');
header('Location: ' . $url);
Yii::$app->end();
}
}
}