如何最好地编写一个位于通用 SQL 数据库(SQL Server、MySQL、Oracle 等)前面并侦听 SQL 查询的应用程序?
应用程序需要能够根据特定的查询类型拦截(防止传递到 SQL 数据库)或传递(发送到 SQL 数据库)查询。
有没有一种方法可以通用地做到这一点,以便它不绑定到特定的数据库后端?
基本系统不是特别容易,但也不是非常困难。您创建一个在一个端口(或一组端口)上侦听连接尝试的守护程序。它接受这些连接,然后建立自己与 DBMS 的连接,形成中间人中继/拦截点。主要问题在于如何配置事物,以便:
不过,您仍然可能会遇到问题。最值得注意的是,如果 GSL 与 DBMS 侦听器位于同一台机器上,那么当 GSL 连接到 DBMS 时,它会将 DBMS 视为本地连接而不是远程连接。如果 GSL 在另一台机器上,那么看起来所有连接都来自运行 GSL 的机器。
此外,如果信息是以加密方式发送的,那么您的 GSL 只能拦截加密通信。如果加密很好,您将无法记录它。您可能能够处理 Diffie-Hellman 交换,但您需要知道您到底在做什么,以及您正在拦截的 DBMS 是什么——您可能需要从客户那里获得支持他们会通过你的中间人系统。当然,如果“客户端”是您控制的 Web 服务器,您可以处理所有这些。
只要您的代码只是传输和记录查询,连接的详细信息往往就足够直截了当。每个 DBMS 都有自己的 SQL 请求处理协议,拦截、修改或拒绝操作需要了解每个 DBMS 的协议。
有做这种事情的商业产品。我在 IBM 工作,并且知道 IBM 的 Guardium 产品包含许多 DBMS 的这些功能(我相信,包括上面提到的所有这些功能——如果有问题,很可能是支持最少的 MySQL)。处理加密通信仍然很棘手,即使对于像 Guardium 这样的系统也是如此。
我有一个在 Unix 上运行的守护进程,它适用于一个特定的 DBMS。它处理了大部分——但不会试图干扰加密通信;它只是记录了两端方彼此所说的话。如果您需要代码,请与我联系 - 请参阅我的个人资料。许多部分可能可以与其他 DBMS 重用;其他部分完全是为其设计的特定 DBMS 所特有的。