CodeIgniter HMVC框架下如何从uploads/images加载图片至视图
在CodeIgniter HMVC中加载独立uploads目录下的图片
我明白你的问题——当前的Assets库只能处理模块内的资源,但你想把uploads目录独立出来,在视图里直接调用里面的图片。其实只需要对现有的Assets控制器做一点扩展,就能实现这个需求,下面是具体的解决方案:
方案一:扩展Assets控制器,支持uploads目录
当前你的Assets控制器的index方法只从APPPATH/modules/路径下读取文件,我们可以添加一个分支判断,当请求的资源路径包含uploads前缀时,就从APPPATH/uploads/目录下去查找文件。
修改application/libraries/Assets.php中的index方法:
<?php if (!defined('BASEPATH')) exit('No direct script access allowed'); class Assets extends MX_Controller { function __construct() { parent::__construct(); } function index(){ //$this->user->authorize(); $segments = $this->uri->segments; // 移除第一个segments(也就是'assets') array_shift($segments); // 判断是否是uploads资源 if($segments[0] === 'uploads'){ // 移除uploads前缀,拼接uploads目录路径 array_shift($segments); $file = APPPATH . 'uploads/' . implode('/', $segments); } else { // 原来的模块资源逻辑 $file = APPPATH. 'modules/' . implode('/', $segments); } //----get path parts form extension $path_parts = pathinfo( $file); //---set the type for the headers $file_type= strtolower($path_parts['extension']); if (is_file($file)) { //----write propper headers switch ($file_type) { case 'css': header('Content-type: text/css'); break; case 'js': header('Content-type: text/javascript'); break; case 'json': header('Content-type: application/json;charset=UTF-8'); break; case 'xml': header('Content-type: text/xml'); break; case 'pdf': header('Content-type: application/pdf'); break; case 'svg': header('Content-type: image/svg+xml;charset=UTF-8'); break; case 'jpg': case 'jpeg': case 'png': case 'gif': header('Content-type: image/'.$file_type); break; } readfile($file); } else { show_error("Asset not found: $file"); } exit; } }
关键修改点:
- 先移除URI中的第一个分段(也就是
assets,因为你的控制器是Assets.php,路由会映射到assets/xxx) - 判断剩余分段的第一个是否是
uploads,如果是,就切换到APPPATH/uploads/路径下查找文件 - 修复了原来switch语句中的逻辑错误:
case 'jpg' || 'jpeg' || 'png' || 'gif':这种写法是无效的,改为逐个声明case
视图中调用uploads图片
修改完成后,你就可以在视图里用和模块资源一样的方式调用uploads里的图片了:
<img src="<?php echo site_url('assets/uploads/images/your-image.jpg'); ?>" alt="示例图片">
方案二:新增专门的uploads处理方法(更优雅)
如果不想把uploads逻辑和模块资源逻辑混在一起,可以在Assets控制器里新增一个uploads方法,专门处理uploads目录的资源:
function uploads(){ $segments = $this->uri->segments; // 移除前两个分段:'assets'和'uploads' array_shift($segments); array_shift($segments); $file = APPPATH . 'uploads/' . implode('/', $segments); // 复用文件类型判断和输出逻辑 $path_parts = pathinfo( $file); $file_type= strtolower($path_parts['extension']); if (is_file($file)) { switch ($file_type) { case 'jpg': case 'jpeg': case 'png': case 'gif': header('Content-type: image/'.$file_type); break; // 如需处理uploads里的其他文件类型,可添加对应case } readfile($file); } else { show_error("Upload asset not found: $file"); } exit; }
这种方式下,视图里的调用路径和方案一完全一致,CI路由会自动匹配到Assets控制器的uploads方法。
注意事项
- 确保
application/uploads/和application/uploads/images/目录有可读权限(通常设置为755) - 生产环境中,建议给uploads目录添加安全限制,比如通过
.htaccess禁止执行目录内的脚本文件
内容的提问来源于stack exchange,提问作者Fer
相关产品推荐
相关产品推荐

