In unserer letzten Folge (So erstellen Sie datenbankübergreifende Abfragen in MySQL) habe ich gelernt, wie man datenbankübergreifende Abfragen in MySQL erstellt. Das funktionierte großartig, aber als unser Held versuchte, dieses neu gewonnene Wissen in PHP zu nutzen, stellte er fest, dass sein bester Freund versagte.
Ich habe mir PHPs angesehen mysql_select_db
. Das scheint zu bedeuten, dass ich, wenn ich MySQL mit PHP verwenden möchte, ein paar Optionen habe:
Verwenden Sie mysql_select_db
, es kann jedoch jeweils nur eine Datenbank verwendet werden. Dies ist unser aktuelles Setup. Die Datenbank als Namespace-ID zu verwenden scheint nicht zu funktionieren (in der MySQL-Shell funktioniert es einwandfrei, daher weiß ich, dass es bei unserem MySQL-Server-Setup kein Problem darstellt).
Nicht verwenden mysql_select_db
。从我看到的一些示例来看,这似乎意味着我必须为我所做的每个查询指定数据库。这是有道理的,因为我没有使用 mysql_select_db
. Aus einigen Beispielen, die ich gesehen habe, scheint dies zu bedeuten, dass ich die Datenbank für jede Abfrage angeben muss, die ich mache. Das macht Sinn, da ich
Gibt es etwas Besseres als das? Gibt es eine Möglichkeit für mich, eine datenbankübergreifende MySQL-Abfrage in PHP durchzuführen, ohne etwas Verrücktes wie (2) tun zu müssen?
KlarstellungSELECTforeign_db.login.username,firstname,lastname fromforeign_db.login,user where...
: Mit keiner der vorgeschlagenen Antworten konnte ich tatsächlich datenbankübergreifende Abfragen durchführen. Stattdessen ermöglichen sie mir den separaten Zugriff auf zwei verschiedene Datenbanken. Ich möchte eine Lösung, die es mir ermöglicht, so etwas wie
阅读您的说明后,我的印象是您实际上想要查询驻留在两个单独的 MySQL 服务器实例中的表。至少,您的澄清文字:
建议您希望在以两个用户身份登录时运行一个查询(可能驻留在也可能不驻留在同一个 mysql 服务器实例上)。
在您的问题中,您说您想要从两个不同的数据库查询数据,但重要的是要认识到一个 MySQL 实例可以有很多很多数据库。对于由同一 mysql 实例管理的多个数据库,您链接到的问题中提出的解决方案很简单:只需在表名前添加数据库名称前缀,用点分隔数据库和表名称:
.
.但是,就像我指出的那样,这只在以下情况下有效:
场景1:同一主机上的数据库:授予适当的权限并限定表名称
因此,如果这些表实际上驻留在同一个 mysql 实例上,则无需第二次登录或连接 - 只需授予您用于连接到数据库的数据库用户适当的权限,即可从您需要的所有表中进行选择。您可以使用 GRANT 语法来做到这一点,记录如下:http://dev.mysql.com/doc/refman/5.1/en/grant.html
例如,
GRANT SELECT ON sakila.film TO 'test'@'%'
将允许用户test@%
从film 选择数据
表。完成此操作后,用户可以使用 sakila.film(所谓的限定表名)引用该表,或者如果当前数据库设置为 sakila,只需如下所示sakila
数据库中的电影
场景2:由不同MySQL实例管理的数据库:FEDERATED引擎
如果您要访问的表实际上由两个不同的 MySQL 实例管理,则有一个技巧可能有效,也可能无效,具体取决于您的配置。从MySQL 5.0开始,mysql支持
FEDERATED
存储引擎。这使您可以创建一个实际上不是表的表,而是远程服务器上表的窥视孔。该引擎记录在此处:http://dev. mysql.com/doc/refman/5.1/en/federated-storage-engine.html例如,如果您知道远程主机上的
misc
数据库中有此表:您可以使用以下命令创建指向该远程表的本地“指针”:
不幸的是,
FEDERATED
引擎并不总是可用,因此您必须首先检查是否可以使用它。但假设是这样,那么您可以在查询中简单地使用本地表 t,就像任何其他表一样,MySQL 将与远程服务器通信并对另一端的物理表执行适当的操作。警告:FEDERATED 表存在多个优化问题。您应该了解这些是否以及在多大程度上适用于您。例如,在许多情况下,将
WHERE
应用于联合表可能会导致整个表内容通过网络拉至本地服务器,在本地服务器上应用实际的过滤。另一个问题是表创建:您必须非常确定联合表及其指向的表的定义完全匹配,除了 ENGINE 子句(和 CONNECTION)。例如,如果您有不同的字符集,则数据在通过网络传输后可能会完全乱码。如果您想使用
FEDERATED
表,请阅读这篇文章http://oreilly.com/pub/a/databases/2006/08/10/mysql-federated-tables.html 来决定它是否适合您特定用例。如果您认为确实需要它,我有一个实用程序可以在此处创建联合表:http://forge.mysql.com/tools/tool.php?id=54
场景3:无法使用FEDERATED,但表位于不同的MySQL实例上
最后,如果您在不同的 MySQL 实例上有表,但由于某种原因无法使用联合表引擎,那么恐怕您就不走运了。您只需对两个 MySQL 实例执行查询、接收结果并在 PHP 中执行一些智能操作。根据您的具体要求,这可能是一个完全可行的解决方案
我想您需要自己决定我的答案的哪一部分最能解决您的问题,并添加评论以防您需要更多帮助。蒂亚·罗兰。
您将需要数据库在同一主机上运行。
如果是这样,您应该能够在您最喜欢的/默认数据库上使用 mysql_select_db 并手动指定外部数据库。
如果您的数据库运行在不同的主机上,您将无法直接加入。但随后您可以进行 2 个查询。