【问题标题】:Improving SQL Queries改进 SQL 查询
【发布时间】:2015-06-23 10:56:03
【问题描述】:

我最近设计了一个使用大量查询的网站。在我开发网站的过程中,我遇到了一个非常耗时且令人沮丧的问题。

所以问题是,在某个时候,我想向网站添加一个附加功能,它会对我的查询影响最大,我需要更改其中的大部分以使该功能正常工作。所以让我举个例子:假设我有一个用户表,我没有添加一列来检查用户是否被禁止。现在我添加了“禁止”列,现在的问题是,我需要安排所有其他查询来检查用户是否被禁止。我希望这是有道理的。

所以我的问题是,有没有一种方法可以最小化这项工作,而不是遍历所有查询并修改它们(添加被用户禁止),我可以添加一次该功能并且查询会起作用?基本上我该如何改进?

我希望这是有道理的,如果没有,我会尽力进一步解释。

如果能帮助我提高编码知识,我们将不胜感激。

PS。 我正在使用 SQL 和 PHP。如果有比 SQL 更好的方法可以解决此问题,请提出建议。

谢谢

【问题讨论】:

  • 你能不能只做一些条件语句,指检查被禁止的表,如果为真则传递给其他查询?
  • 添加新列并将其添加为其他查询的一部分需要您更改其他查询,您别无选择,只能手动进行。即使您使用一些 MVC 结构,您也需要实现新增功能。一个好方法是为您的查询和系统中的每个实体都有一个抽象层,每个实体都有自己的对象进行查询,这将使查询更改更容易。
  • 勾选使用ORM的php框架的选项
  • 如果这是一个通用的东西,对于某些提取必须忽略所有新状态,您可以添加一个计算列,其中包含与其他字段组合的 0/1,告诉该用户是否可以执行某事

标签: php mysql sql-server


【解决方案1】:

我了解您的问题。你有一些列规则。在所有应用程序中全局使用。例如,在我的情况下,有“状态”列,并且有一些称为“重要”的逻辑含义,如果列具有集合中的某些值之一,则该列有效。

所以,在任何地方,要检查状态是否“重要”,我需要写:

WHERE `status` IN('INCIDENT', 'ERROR')

如果我需要在重要状态列表中添加例如“FLAGGED”,我需要重写所有 SQL 查询:

WHERE `status` IN('INCIDENT', 'ERROR', 'FLAGGED')

一旦我厌倦了这个。我决定编写一个 MySQL 函数来完成这项工作。称之为 IS_STATUS_IMPORTANT(状态)。 但是这个解决方案没有通过测试,因为它降低了性能——它不允许 MySQL 正确使用索引。

我终于通过创建一些应用程序全局条件解决了这个问题,比如说:

class DbHelper {
    public static function importanceCondition($column_name) {
        return $column_name . " IN('INCIDENT', 'ERROR') ";
    }
}

现在我写的整个应用程序:

$sql = 'SELECT * FROM blah .... WHERE ...  AND ' .  DbHelper::importanceCondition('x.status');

如果我需要更改一些逻辑条件,我会在一个地方进行,它适用于整个应用程序。

在你的情况下,你可以添加一些功能

class DbHelper {
    ...
    public static function validUserCondition($user_alias) {
        return " ({$user_alias}.deleted = 0 AND {$user_alias}.banned = 0) ";
    }
}

【讨论】:

  • 感谢您的帮助。这就是我试图解释的。谢谢
【解决方案2】:

为什么不在用户登录的时候检查一下呢?如果他被禁止,则登录失败,并且所有进一步的查询都无法首先执行。

一般来说,您永远不应该将相同的逻辑分散到多个代码位置,因为无论何时您想要调整某些东西,都会导致这种多重努力。

在您可以重用的地方创建重用方法。这甚至可以重用,以使用另一个 WHERE 条件或执行 SQL 请求本身的方法来增强给定的 SQL(准备好的)语句。

【讨论】:

    【解决方案3】:

    我了解您的问题,有一些简单的解决方案可以使用 ORM(对象关系映射)查询支持多个数据库,例如(SQL、mysql、Oracle DB、NoSql...)

    PHP ORM 之类的 - DoctrinePropel

    • ORM 更好地支持大多数 PHP 框架
    • 哪种方式更好地处理查询
    • 将功能拆分为类的编码不太复杂
    • 易于管理表中的关系

    我希望这将帮助您以更少的时间和更好的性能修改查询

    【讨论】:

      【解决方案4】:

      我假设您在每个页面中都包含代码,以确保用户已成功登录。

      如果是这种情况,那么您需要做的就是更改登录脚本以拒绝被禁止的用户,因此所有其他页面都将按原样工作并拒绝任何未登录的用户,并且不会对这些用户进行任何查询其他页面需要更改。

      【讨论】:

        猜你喜欢
        • 2021-09-02
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-11-04
        • 2015-05-27
        相关资源
        最近更新 更多