Подтвердить что ты не робот

Плюсы и минусы подключения нескольких баз данных в одном script

Скажем, у пользователя есть две базы данных, размещенные на одном хосте, и мне нужно подключиться к обоим из них, чтобы я мог использовать любую таблицу в любое время без добавления кода подключения несколько раз.

Я реализовал это в CodeIgniter с добавлением данных авторизации обеих баз данных в файле database.php и для загрузки необходимой базы данных с помощью $this->load->database('dbname'); в script.

Теперь, для основного PHP, мы можем сделать это следующим образом:

mysql_connect ('host','user','password','port','dbname'); // connection with one database.   

Это связано с моей первой базой данных.

Теперь я хочу подключиться ко второй базе данных:

1) Я не закрыл выше соединение и связан со вторым с

mysql_connect ('host','user','password','port','dbname1');.

2) Будет ли это плохой практикой? Будет ли он потреблять больше объектов? Должна ли мы быть обязательной для закрытия первой?)

4b9b3361

Ответ 1

Не нужно открывать 2 соединения, чтобы использовать таблицы из 2 баз данных на одном сервере. Вам просто нужно использовать ноту database.table. Это означает, что вы можете даже присоединить таблицы из разных баз данных в том же запросе

SELECT t1.col1, t1.col2, t2.col2, t2.col2
FROM db1.table1 AS t1 JOIN db2.table1 AS t2 ON t1.col1 = t2.col3

Итак, если вы сначала подключились к db1, вы можете использовать таблицы db2 и то же самое, если вы подключились к db2, вы можете использовать таблицы db1.

Ответ 2

Вы пробовали это?

$mysqli1 = new mysqli("example.com", "user", "password", "database1");

$mysqli2 = new mysqli("example.com", "user", "password", "database2");

Ответ 3

Вы можете сделать это, следуя объектно-ориентированному подходу

Прежде всего создайте соединение с двумя базами данных:

$Db1 = new mysqli('localhost','root','','database1'); // this is object of database 1
$Db2 = new mysqli('localhost','root','','database2'); // this is object of database 2

$query1 = 'select * from `table_name_of_database1`';  // Query to be run on DB1
$query2 = 'select * from `table_name_of_database2`';   // Query to be run on DB2

$result1 = $Db1->query($query1); // Executing query on database1 by using $Db1
$result2 = $Db2->query($query2); // Executing query on database2 by using $Db2

echo "<pre>";

/* Print result of $query1 */

if ($result1->num_rows > 0) {
    while($row = $result1->fetch_assoc()) {
        print_r($row);
    }
} else {
    echo "0 results";
}


/*========================================================*/


/* Print result of $query2 */

if ($result2->num_rows > 0) {
    while($row = $result2->fetch_assoc()) {
         print_r($row);
    }
} else {
    echo "0 results";
}

Вывод: Если вы хотите использовать database1 использовать объект $Db1, и если вы хотите использовать database2, используйте $DB2.

Ответ 4

Зачем вам два подключения? Преимущества/преимущества двух баз данных в основном являются проблемами производительности. Но если вы на той же машине, на самом деле, единственным преимуществом, которое у вас есть, было бы более чистое разделение. Поэтому было бы лучше использовать одну БД с двумя разными префиксами для таблицы. Таким образом, вы разделяете данные с помощью префикса, а не DB.

Ответ 5

Я не думаю, что одновременное подключение к двум БД - это проблема, так как вы успешно сделали это (или знаете, как это сделать). Я могу это понять из вашего вопроса. Поэтому я не буду показывать, как это сделать. Если вам нужно, обратитесь к другим ответам.

Но для непосредственного решения ваших проблем:

  • Будет ли это плохой практикой? Как правило, вам следует избегать двух одновременных ручек подключения к БД. Если вам нужно только получить данные из одной базы данных и использовать их для выполнения чего-то другого, лучше всего поставить данные из DB1 в соответствующие переменные PHP, закрыть соединение; затем выполните второе соединение. Это было бы дешевле, чем одновременное открытие двух соединений DB. Однако, если вы делаете что-то вроде INSERT INTO db1.table SELECT FROM db2.table И ТАКЖЕ НЕОБХОДИМО СОБИРАТЬ ИЛИ ROLLBACK в зависимости от успеха или неудачи некоторых запросов, тогда AFAIK, вы должны держать оба соединения открытыми до тех пор, пока ваши процессы не закончатся. Видите ли, всегда есть компромиссы. Таким образом, вы решаете на основе потребности своего приложения и нести расходы.

В качестве практического примера этого сценария я когда-то работал над проектом, где мне нужно было выбрать SELECT table1, INSERT INTO table2, если INSERT преуспеет, я удаляю все строки из таблицы1, если DELETE терпит неудачу, я откатываюсь операция INSERT, потому что данные не могут жить в двух таблицах одновременно.

Конечно, мой собственный случай включал только одну БД, поэтому нет необходимости в втором соединении. Но предполагая, что две таблицы были в разных БД, тогда это может быть похоже на вашу ситуацию.

  1. Будет ли он потреблять больше объектов? Никаких других объектов, кроме тех, которые указаны в 1 выше, а именно, соединения DB подключаются в соответствии с вашим вопросом.

  2. Должны ли мы обязательным требовать закрытия первого? Еще раз, в зависимости от вашего приложения.

Ответ 6

Вместо mysql_connect используйте mysqli_connect.

mysqli предоставляет функциональность для подключения нескольких баз данных за раз.

Ответ 7

1) Можно ли подключиться к нескольким базам данных в одном script?

Да, мы можем создать несколько идентификаторов ссылок MySQL в одном и том же script.

2) Не должно быть похоже на закрытие одного соединения с mysql_close и открытие нового, но оба соединения должны открываться одновременно, и пользователь может использовать любую таблицу из любой базы данных?

Использовать постоянные подключения к базе данных, такие как mysql_pconnect

3) Если это возможно, что может быть недостатком этого? Будет ли создан два объекта, и это создаст проблему?

Я не думаю, что он создает какие-то проблемы, кроме увеличения загрузки на сервере.

Ответ 8

Вы можете использовать это как

$db1 = mysql_connect($hostname, $username, $password); 
$db2 = mysql_connect($hostname, $username, $password, true); 

mysql_select_db('abc', $db1);
mysql_select_db('def', $db2);

Для базы данных 1

mysql_query('select * from table1', $db1);

Для базы данных 2

mysql_query('select * from table2', $db2);

Ответ 9

В: Какие минусы существуют для подключения к другой базе данных без закрытия предыдущей базы данных?

A: Когда вы подключаетесь к серверу базы данных, физически назначаете ресурсы для взаимодействия с вами, если две базы данных находятся на одном сервере, вы без необходимости использовали ресурсы, которые могли бы использоваться для решения других подключений или других действий. Поэтому вы должны быть правильными близкими соединениями, которые не нужно продолжать использовать.

В: Является ли это подходящей практикой? Каков наилучший способ сделать это, не открывая это соединение в каждом script несколько раз? Я хочу, чтобы это выполнялось в основном php только в том случае, если я уже знаю это в codeigniter.

Односторонние СЕЗОНЫ, но вы не можете хранить контуры базы данных в сеансах. Прочитайте в PHP.net это предупреждение: "Некоторые типы данных не могут быть сериализованы таким образом, хранятся в сеансах. Они включают переменные ресурсов или объекты с круговыми ссылки (т.е. объекты, которые передают ссылку на себя другому объекту)". Соединения MySQL - один из таких ресурсов.

Вам нужно подключиться к каждой странице.

Это не так плохо, как кажется, если вы можете положиться на объединение пулов через mysql_pconnect(). При подключении функция сначала попытается найти (постоянную) ссылку, которая уже открыта с тем же хостом, именем пользователя и паролем. Если он найден, идентификатор для него будет возвращен вместо открытия нового соединения. Соединение с SQL-сервером не будет закрыто при завершении выполнения script. Вместо этого ссылка останется открытой для будущего использования (mysql_close() не будет закрывать ссылки, установленные mysql_pconnect()).

Ссылка:

http://php.net/manual/en/function.mysql-pconnect.php

http://www.php.net/manual/en/intro.session.php

Не удается передать соединение mysqli в сеансе в php

Ответ 10

Лучший способ использования нескольких баз данных - использовать функции PDO

Пример

// database cobfigurations
$config= array(
    // first database
    array(
        'type'=>'mysql',                    // DB type
        'host'=>'localhost',                // DB host
        'dbname'=>'database1',      // DB name
        'user'=>'root',                 // DB username
        'pass'=>'12345',                // DB password
    ),
    // second database
    array(
        'type'=>'mysql',                    // DB type
        'host'=>'localhost',                // DB host
        'dbname'=>'database2',      // DB name
        'user'=>'root',                 // DB username
        'pass'=>'987654',               // DB password
    ),
);
// database connections
$mysql=array();
foreach($config as $con)
{
    $con=(object)$con;
    $start= new PDO($con->type.':host='.$con->host.';dbname='.$con->dbname.'', $con->user, $con->pass, array(
            // pdo setup
            PDO::ATTR_PERSISTENT            => FALSE,
            PDO::ATTR_DEFAULT_FETCH_MODE    => PDO::FETCH_OBJ,
            PDO::ATTR_ERRMODE               => PDO::ERRMODE_EXCEPTION,
            PDO::MYSQL_ATTR_INIT_COMMAND    => 'SET NAMES UTF8'
    ));

    if ($start && !empty($start) && !is_resource($start))
        $mysql[]=$start;    // connection is OK prepare objects
    else
        $mysql[]=false; // connection is NOT OK, return false
}

/**********************
 ****  HOW TO USE ****
**********************/ 

// fetch data from database 1
$data1 = $mysql[0]->query("SELECT id, title, text FROM content1")->fetchAll();
if(count($data1)>0)
{
    foreach($data1 as $i=>$result)
    {
        echo $result->id.' '.$result->title.' '.$result->text.'<br>'
    }
}

// fetch data from database 2
$data2 = $mysql[1]->query("SELECT id, title, text FROM content2")->fetchAll();
if(count($data2)>0)
{
    foreach($data2 as $i=>$result)
    {
        echo $result->id.' '.$result->title.' '.$result->text.'<br>'
    }
}

Если вы раньше не использовали PDO, прочитайте этот короткий учебник:

http://www.mysqltutorial.org/php-querying-data-from-mysql-table/

Практически такой же, как соединения mysql и mysqli, но более продвинутый, быстрый и безопасный.

Прочитайте эту документацию: http://php.net/manual/en/book.pdo.php

И вы можете добавить более двух баз данных

Ответ 11

Использовать PDO, поддерживаемый версией php 5, вместо mysql connect

Ответ 12

Вот простой класс, который автоматически выбирает необходимую базу данных при необходимости.

class Database 
{
    private $host   = 'host';
    private $user   = 'root';
    private $pass   = 'pass';
    private $dbname = '';

    private $mysqli = null;

    function __construct() 
    {
        // dbname is not defined in constructor
        $this->mysqli = new mysqli( $this->host, $this->user, $this->pass );    
    }

    function __get( $dbname ) 
    {
        // if dbname is different, and select_db() is succesfull, save current dbname
        if ( $this->dbname !== $dbname && $this->mysqli->select_db( $dbname ) ) {
            $this->dbname = $dbname;
        }

        // return connection
        return $this->mysqli;
    }
}


// examples
$db = new Database();

$result = $db->db1->query( "SELECT DATABASE()" );
print_r( $result->fetch_row() );

$result = $db->db2->query( "SELECT DATABASE()" );
print_r( $result->fetch_row() );

$result = $db->{'dbname with spaces'}->query( "SELECT DATABASE()" );
print_r( $result->fetch_row() );

Ответ 13

$con1 = mysql_connect($hostname, $username, $password); 
$con2 = mysql_connect($hostname, $username, $password, true); 

mysql_select_db('database1', $con1);
mysql_select_db('database2', $con2);

Затем для запроса базы данных 1 передайте первый идентификатор ссылки:

mysql_query('select * from tablename', $con1);

а для базы данных 2 - второе:

mysql_query('select * from tablename', $con2);

Ответ 14

Если у пользователя mysql есть разрешение на две базы данных, вы можете присоединиться к двум таблицам из двух баз данных и т.д.

SELECT database1.table.title title1,database2.table.title title2 
FROM database1.table
INNER JOIN database2.table 
ON (database1.table.id=database2.table.id)