Skip to content
Grigoriev Oleg edited this page Apr 23, 2012 · 2 revisions

Клонирование объектов баз

Объекты БД можно клонировать:

$db1 = go\DB\DB::create($params, 'mysql');

$db2 = clone $db1;

При этом $db2 наследует все параметры и настройки $db1 и разделяет вместе с ним одно подключение к базе.

Если подключение уже было установлено, оно разделяется между двумя объектами. Но даже если оно не было ещё установлено на момент клонирования, в момент, когда оно будет создано, оно будет разделено между объектами.

Пример

Создаём объект подключения и клонируем его:

$db1 = go\DB\DB::create($params, 'mysql');

$db2 = clone $db1;

Реального подключения ещё нет ни у одного из объектов (lazy):

$db1->isConnected(); // False
$db2->isConnected(); // False

При установлении подключения, оно разделяется всеми объектами:

$db1->forcedConnect(); 
$db1->isConnected();   // True
$db2->isConnected();   // True

Запрос через $db2 не вызовет отложенного подключения (так как уже подключились):

$db2->query($pattern, $data);

"Мягкое" отключение на самом деле не приведёт к фактическому разрыву связи. Подключение продолжает висеть за счёт $db2:

$db1->close(true); 
$db1->isConnected();   // True
$db1->forcedConnect(); // nothing - connection is opened

"Жёсткое" отключение приведёт к потери подключения текущим объектом:

$db1->close();
$db1->isConnected(); // False

Но $db2 продолжает его удерживать:

$db2->isConnected();

"Мягкое" отключение $db2: все ссылки на подключение разорваны, теперь оно фактически и закрывается.

$db2->close(true);
  • isConnected() возвращает факт наличия подключения, даже если оно установлено другим объектом.
  • close() вызовет фактический разрыв подключения, только если подключение будет закрыто у всех открывших его объектов (или эти объекты будут удалены).

Варианты использования

Клоны наследуют все параметры клонированных объектов, включая префиксы, отладчики и т.п. Но их можно впоследствии изменить.

Будем работать с этой же базой, но для таблиц используем другой префикс и, заодно, выводим все запросы на экран:

$db1 = go\DB\DB::create($params, 'mysql');

$db2 = clone $db1;

$db2->setPrefix('p_');
$db2->setDebug(true);
Clone this wiki locally