我正在尝试在加载标记时设置友好网址的自定义路由,我的意思是我想将其转换为http://test.com/en/results?search_query=data&search=tag
到此http://test.com/en/tag/data
试图通过在我的routes.php中设置它来实现:
$route['^(en|es|ro)/tag/(:any)'] = "fetch/results?search_query=$1&search=tag";
但没有成功,我做错了吗?
我的routes.php:
$route['default_controller'] = "home";
// URI like '/en/about' -> use controller 'about'
$route['^(en|es|ro)/video/(.+)$'] = "video/id/$2";
$route['^(en|es|ro)/results$'] = "fetch/results$2";
$route['(en|es|ro)/tag/(:any)'] = "fetch/results?search_query=$2&search=tag";
$route['^(en|es|ro)/(.+)$'] = "$2";
// '/en', '/de', '/fr' and '/nl' URIs -> use default controller
$route['^(en|es|ro)$'] = $route['default_controller'];
$route['404_override'] = '';
答案 0 :(得分:3)
我很确定^
没有必要。试试没有它:
$route['(en|es|ro)/tag/(:any)'] = "fetch/results?search_query=$1&search=tag";
在该上下文中,^
将被视为文字字符串。如果你想顶级使用正则表达式,我相信你必须将正则表达式本身包含在括号中,如下所示:
$route['(^(en|es|ro))/tag/(:any)'] = "fetch/results?search_query=$1&search=tag";
我不是百分之百确定,但如果我是对的,两者都应该有效。但是,路由总是假设模式的第一部分是字符串应该从哪个开始,因此无论如何都不需要^
。
还有一件事:你没有使用第二场比赛,而是第一场比赛。我相信您希望在路线中将$1
替换为$2
。
$route['(en|es|ro)/tag/(:any)'] = "fetch/results?search_query=$2&search=tag";
// ^^^1^^^^ ^^^2^^ ^^
编辑:经过进一步调查和测试,似乎Codeigniter无法正确处理使用?key=value
等查询字符串的路由。如果在?
问号之前使用斜杠,则至少可以将其路由到正确的控制器和方法:
$route['(en|es|ro)/tag/(:any)'] = "fetch/results/?search_query=$2&search=tag";
这样的网址:
http://example.com/es/tag/Codeigniter's Router
...将以此字符串作为参数路由到results
方法,但$_GET
将为空:
?search_query=Codeigniter%27s%20Router&search=tag
所以,你可以用parse_str()
:
function results($request)
{
$request = ltrim($request, '?');
parse_str($request, $get);
// echo $get['search_query']
}
当然,你总是可以使用.htaccess
,但我理解将所有路由逻辑保存在一个地方的愿望。很抱歉,如果这不是您所希望的答案,但我担心如果不编写自定义路由器,则无法在Codeigniter中以明显的方式执行此操作。我的建议可能是找到另一种处理路由的方法以及从URL访问数据的方式。
答案 1 :(得分:1)
您可能需要在标记周围转义正斜杠。所以看起来应该是这样的:
$route['^(en|es|ro)\/tag\/(:any)']
答案 2 :(得分:0)
我有类似的东西,它看起来像
$route['(:any)/something/(:any)'] = "real/$2/path/$1";