我正在调试一个在显示博客帖子列表时间歇性崩溃(500错误)的codeigniter应用程序。
崩溃发生了20-30%的页面重新加载 - 似乎与服务器配置错误的内存问题有关。
首先 我通过在发送到视图页面的每个阵列下方执行print_r($array); exit;
来关闭控制器。如果你只是输出数组没有问题(没有通过视图) - 从来没有超时。
所以我不认为查询逻辑有问题。此外,当页面正确加载时,CI的分析器显示查询时间<.001(当它崩溃时我得到500错误并且无法读取探查器的信息)。
下一步 我转到print_r
视图的HTML,其中包含控制器发送的数组的循环。这就是存在瓶颈的地方,偶尔会导致500错误。
应用程序的设计方式使得单个视图处理控制器发送的所有数组,并使用最终输出构建HTML页面。
因此,该视图有很多PHP逻辑。在运行foreach循环之前插入广告单元的几个数组拆分,测试post参数的条件,嵌套的foreach循环等。
它非常复杂但完全可读。但是我想知道它是否有太多的逻辑,如果这个逻辑的负载应该分成更小的片段(多个视图),然后合并到一个最终的HTML字符串中。
视图有
if / elseif
,有些嵌套foreach
,一些嵌套array_splice
多个empty
和isset
您对此问题有何看法?你通常会避免逻辑沉重的观点吗?有什么建议吗?
请注意,我不会像其他SO讨论那样询问网页设计师等的“清理”视图。我的观点是,如果这种结构可能导致我的超时以及可能的解决方案。
答案 0 :(得分:1)
你对这个问题有什么看法?
这是你确定它的瓶颈。现在,如果视图性能为500(超时),则视图性能是不可接受的。如果它可以使用它需要修复。
你通常会避免逻辑沉重的观点
始终。这就是MVC模式的目的。保持尽可能多的逻辑控制器,视图应该只是演示文稿。
似乎太多试图被置于一个视图中。如果您想发布一些代码,那么就更容易就需要查看的内容提出建议。对我来说,最大的罪犯是conditionals testing for post parameters
。我认为这几乎肯定属于你的控制器。这些post params用于什么?
如果post params指示输出类型,则分离到不同的视图会更清晰,而不是在一个超级视图中处理多种不同的输出类型。
答案 1 :(得分:1)
首先,我首先检查php设置中的执行时间限制。您描述的情况看起来非常像这个问题:有时脚本会设法及时到达那里,有时候不会。 )关于here的更多信息。
第二,是的,你应该避免逻辑沉重的观点。老实说,我不知道如何在CodeIgniter中做到这一点,但在Zend Framework中有所谓的视图助手,可用于将视图相关(但重)逻辑与模板分开。
最后,您是否已使用XDebug或其他类似工具分析了您的脚本?
更新:“视频参数的条件测试”在视图中坐满(并且只是阻止所有尝试移动到控制器中)的情况是......有趣,至少可以说。对不起,那么使用MVC框架有什么意义呢?
答案 2 :(得分:1)
首先,这不是模板代码可读性的问题 - 复杂性与错误的存在之间存在很强的相关性。 Cyclomatic complexity是衡量复杂性的一种方法;根据您发布的内容,此模板的圈复杂度至少为60.在我们的所有项目中,我的目标都是&lt; 8,当我们到达12时会感到恐慌。
如果您的视图代码包含错误,我不会感到惊讶 - 不仅仅是一个超时的事情,而是通过逻辑树的一些奇怪的路径,通过查看代码您无法想象。
Williams模板库为您提供了几个工具 - 例如,您可以定义备用视图来处理“如果问题,像这样渲染,如果像这样渲染渲染”逻辑。您也可以在此处使用区域。
有一种假设认为,因为视图处理用户界面,所以它们不那么重要 - 但事实并非如此。
因此,我们假设您将视图重构为更简单的结构。这会影响处理器负载吗?嗯 - 取决于。
通常,“可维护性”和“性能”必须相互交换。经典的例子是汇编代码与解释语言 - 对于大多数人来说,汇编程序很难维护,而解释的脚本语言则更容易处理;另一方面,毫无疑问哪个更快。
在你的情况下,我认为代码的总量会增加 - 例如,“提取方法”作为重构会增加代码量几行 - 但它应该更容易缓存。还应该更容易确定错误发生的确切位置。