|
因為 Codeigniter 預設的 Filter 能處理字串保持網址安全。
不過我又希望能夠傳入中文字串。
所以用了下面的處理方法。
不知道這樣是否安全……
(台灣的中文論壇討論不怎麼熱烈,上中國的開發者社區……)
MY_Router.php
PHP复制代码
<?php if( ! defined('BASEPATH') ) exit('No direct script access allowed');
/*
* Codeigniter Router Extend
* @package CI-Dev
* @author 蒼時弦や
*/
class MY_Router extends CI_Router
{
static private $pages;
function __construct ()
{
parent ::CI_Router();
}
function _validate_request ($segments)
{
// Does the requested controller exist in the root folder?
if (file_exists(APPPATH .'controllers/'.$segments[0].EXT ))
{
return $segments;
}
// Is the controller in a sub-folder?
if (is_dir(APPPATH .'controllers/'.$segments[0]))
{
// Set the directory and remove it from the segment array
$this->set_directory($segments[0]);
$segments = array_slice($segments, 1);
if (count($segments) > 0)
{
// Does the requested controller exist in the sub-folder?
if ( ! file_exists(APPPATH .'controllers/'.$this->fetch_directory().$segments[0].EXT ))
{
show_404 ($this->fetch_directory().$segments[0]);
}
}
else
{
$this->set_class($this->default_controller);
$this->set_method('index');
// Does the default controller exist in the sub-folder?
if ( ! file_exists(APPPATH .'controllers/'.$this->fetch_directory().$this->default_controller.EXT ))
{
$this->directory = '';
return array();
}
}
return $segments;
}
// Can't find the requested controller...
//Routing to Manager
if($segments[0] == 'index')
return array('manager', 'index', array_slice($segments, 1));
else
return array('manager', 'index', $segments);
}
}
复制代码
其實也就只是在找不到時轉到 manager 這個 Controller 去控管。
(參考之前的貼子改良的)
MY_URI.php
PHP复制代码
<?php if( ! defined('BASEPATH') ) exit('No direct script access allowed');
/*
* Codeigniter URI Extend
* @package CI-Dev
* @author 蒼時弦や
*/
class MY_URI extends CI_URI
{
function __construct ()
{
parent ::CI_URI();
}
/**
*
* Filter URI (Chinese Support)
*
* @access private
* @prama string
* @return string
*/
function _filter_uri ($str)
{
if ($str != '' && $this->config->item('permitted_uri_chars') != '' && $this->config->item('enable_query_strings') == FALSE)
{
// preg_quote() in PHP 5.3 escapes -, so the str_replace() and addition of - to preg_quote() is to maintain backwards
// compatibility as many are unaware of how characters in the permitted_uri_chars will be parsed as a regex pattern
if ( ! preg_match("|^[".str_replace(array('\\-', '\-'), '-', preg_quote($this->config->item('permitted_uri_chars'), '-'))."]+$|i", $str))
{
//show_error('The URI you submitted has disallowed characters.', 400);
//Urlencode Fix
$str = urlencode($str);
return array(1, $str);
}
}
// Convert programatic characters to entities
$bad = array('$', '(', ')', '%28', '%29');
$good = array('$', '(', ')', '(', ')');
return str_replace($bad, $good, $str);
}
/**
* Explode the URI Segments. The individual segments will
* be stored in the $this->segments array.
* Fix for Chinese (change to prama)
*
* @access private
* @return void
*/
function _explode_segments ()
{
foreach(explode("/", preg_replace("|/*(.+?)/*$|", "\\1", $this->uri_string)) as $key => $val)
{
// Filter segments for security
$val = $this->_filter_uri ($val);
if ($val != '' && !is_array($val))
{
$this->segments[] = trim($val);
}else{
if($key >= 2)
$this->segments[] = $val[1];
else{
$this->segments[] = 'index';
$this->segments[] = $val[1];
}
}
}
}
}
复制代码
因為 URI 比 Router 被 Load, 所以不能在 Load 上另外處理。
(在Router做_filter_uri之前會先做一次確保網址安全。)
進行分段的時候檢查是否被urlencode過,如果是則會強制推到傳入的值。
(避開Controller和Method)
不過 deurlencode 之後的事就不知道是不是安全了……
(雖然只是要弄類似 slug 那樣查詢,不會去 deurlencode ...) |
|