CodeIgniter URI 参数部分绕过 "if" 语句

CodeIgniter URI Parameter is partially bypassing an "if" statement

美好的一天,亲爱的人们。我是社区的新手,但在编程方面并不多。让我把小故事带来。

我正在创建一个基于 CodeIgniter Framework (v 2.1.4) 的小应用程序。我已经配置了整个代码,所以我不必在 URL 上编写 "index.php" 部分,而且我也将默认控制器配置为不在 URL 中编写。我还确保每个控制器的每个方法都被 linked 到一个视图,该视图具有 div 能够显示错误消息的功能,这要归功于 '$this->session->flashdata()' 方法。

那么,假设我的默认控制器名为 'inicio'。为了从我的本地服务器 运行 它,我转到浏览器并在地址栏中写入以下行:

URL: http://localhost/vga/

并配置了 application/config/routes.php 这样我就可以避免不必要的写入

$route['default_controller'] = 'inicio';
$route['404_override'] = '';
$route['inicio'] = '';

我设置了.htaccess

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule .* index.php/[=13=] [PT,L] 

仅此而已。这会将我带到默认控制器,该控制器由会话管理器控制,强制我填写登录表单,以便访问此页面的内部部分。

URL: http://localhost/vga/acceso

此登录有一个 link 基本注册表单,非常有用。

URL: http://localhost/vga/acceso/registro

甚至还有一个配置文件控制器,让我可以查看和编辑自己的配置文件。好东西,我什至不需要 URI 段参数,因为 ID 是由会话传递的。

除了默认控制器的配置之外,我没有触及 application/config/routes.php。到目前为止一切都很酷。

现在,我的头疼来了。

我创建了一个新控制器来控制此页面中的 'roles'。这个控制器有 3 个方法:

class Roles extends  CI_Controller {
    function index() {}
    function editar() {}
    function usuarios() {}
}

每种方法背后的基本思想都相当简单。

'index' 应该列出这个网络系统中存在的角色(例如管理员,用户等),并告诉我有多少用户,按角色分类。 'editar' 应该让我编辑每个角色的基本方面。 'usuarios' 应该会显示每个角色中存在的用户列表。

我对每种方法都进行了编程,它们工作得很好。该问题依赖于在奇怪的情况下显示的该死的 flashdata,特别是在 'editar' 和 'usuarios' 方法中。

它们为什么特别?好吧,与其他所有方法相比,它们拥有 3 个 URI 段:控制器、方法和一个参数。

场景是这样的:

'editar'和'usuarios'都有一些共同的代码行:

/*
    I'll be trying to edit a specific numeric entry,
    and force it to be zero in case of empty segment. 
    The page should be redirected in this case.
*/
$id = $this->uri->segment(3, 0); 
if( $id == 0 ){
    $this->session->set_flashdata('message', 'Error #X' ); /* Only these controllers have this Error Code */
    redirect( 'roles' , 'refresh');
}

看起来不错吧?好吧,问题是,当我在 'roles' 索引中并转到 'roles/usuario/1'(这是现有数据)或 'roles/editar/1'(这也是现有数据)时,这些页面显示正如预期的那样干净。当我在浏览器上按 'refresh' 或从此处转到任何页面时,问题就来了……因为在所有情况下,系统都会抛出一条 'Error #X' 消息……并且该页面是未重定向,正如我在 $id = 0 的情况下所期望的那样。因此,我假设流程绕过了 if 语句,足以设置 $this->session->flashdata('message') 变量,但不足以命令重定向方法。

这里头疼得要命。然后,我开始思考了一下,试图进一步利用 application/config/routes.php 特性,于是我设置了一些规则,文件变成了这样:

$route['default_controller'] = 'inicio';
$route['404_override'] = '';
$route['inicio'] = '';
$route['roles_usuarios/(:any)'] = 'roles/usuarios/';
$route['roles_editar/(:any)'] = 'roles/editar/';

瞧瞧,该死的消息在奇怪的情况下停止显示,并且只在我期望显示时显示(当 $this->uri->segment(3) 未插入 URL,或者当我的数据库中不存在它的值时,以防将其用作数据库查询的参数)。

$this->uri->segment(3) 是如何绕过 if 语句的?

我设法发现这可能是一个路由问题,因为替换

$route['roles_usuarios/(:any)'] = 'roles/usuarios/';
$route['roles_editar/(:any)'] = 'roles/editar/';

来自

$route['roles/usuarios/(:any)'] = 'roles/usuarios/';
$route['roles/editar/(:any)'] = 'roles/editar/';

再次触发异常,我真的不想在我的网址中使用下划线。

我很乐意感谢这里的任何帮助。


更新:已解决。让我分享我的知识。

使用@AdrienXL 的指南,我设法找到了一种让 htaccess 工作的方法,其中包括在 routes.php 中明确显示 3 段 uri 路由的代码行,并为角色控制器中之前的任何其他路由。

这些是现在的文件:

.htaccess

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/ [L]

routes.php

$route['default_controller'] = 'inicio';
$route['404_override'] = '';
$route['inicio'] = '';
$route['roles/editar/(:num)'] = 'roles/editar/';
$route['roles/usuarios/(:num)'] = 'roles/usuarios/';
$route['roles/(:any)'] = 'roles/index';

现在系统运行完美。谢谢!

更新:已解决。让我分享我的知识。

使用@AdrienXL 的指南,我设法找到了一种让 htaccess 工作的方法,其中包括在 routes.php 中明确显示 3 段 uri 路由的代码行,并为角色控制器中之前的任何其他路由。

这些是现在的文件:

.htaccess

RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/ [L]

routes.php

$route['default_controller'] = 'inicio';
$route['404_override'] = '';
$route['inicio'] = '';
$route['roles/editar/(:num)'] = 'roles/editar/';
$route['roles/usuarios/(:num)'] = 'roles/usuarios/';
$route['roles/(:any)'] = 'roles/index';

现在系统运行完美。谢谢!