как коректно подключиться / отключиться от базы?

alexhemp

Новичок
Фанат
icechel
pconnect работает примерно так

1. Смотрит нет ли свободного соединения в "пуле" с такими-же логином-паролем и хостом что переданы в параметрах
2. Если есть - использует его
3. Если нет - создает и помещает в "пул"
4. Помечает как "занятое"
5. Отдает ссылку на него в результате
6. При окончании работы скрипта при высвобождении ресурсов соединение созданное pconnect не закрывается, а помечается как "свободное"
7. Следующий pconnect - берет из пула уже открытое соединение.

Результаты:
плюсы - быстрее открывается соединение с сервером - не тратится время на авторизацию.
минусы - некоторые потери памяти на структуры данных соединения.

В плане too many connections - pconnect никак не влияет, ибо создает те-же соединения, просто не уничтожает а повторно использует.
Если намешать в одной системе connect и pconnect - то тогда могут быть проблемы, т.к. connect ВСЕГДА создает новое соединение, невзирая на то что в "пуле" уже есть такие-же открытые, поэтому при такой мешаниние быстрее будет достигаться заданный предел.
 

Фанат

oncle terrible
Команда форума
alexhemp
это ты все сам придумал, или тебе подсказал кто?

-~{}~ 10.12.04 17:10:

dusya
верно ли, что при mysql_pconnect() на 1 сайт приходиться 1 коннект для всех посетителей?
Нет, неверно.
 

alexhemp

Новичок
dusya

Оверхед тут - создание mysql link на каждый запуск скрипта (проверка авторизации и инициализация клиентских и серверных структур данных в таблицах соединений).

Чем меньше скрипт, чем меньше работа с базой - тем больше накладные расходы на установление соединения. pconnect делает это 1 раз для каждого соединения в "пуле" соединений.


верно ли, что при mysql_pconnect() на 1 сайт приходиться 1 коннект для всех посетителей?
Неверно. Соединений может быть много, они "занимаются" и "освобождаются" по мере работы скриптов и хранятся в "пуле".

В общем мой рецепт прост: всегда и везде использовать pconnect и смотреть чтобы не использовался просто connect. (мало ли какие скрипты ставить будешь).
 

icechel

Новичок
alexhemp
Могешь показать пример скриптов с пконнектом ? И применяешь ли ты это на колокейшене или на массовом хостинге ?
 

f1

formula 1
Автор оригинала: alexhemp
В общем мой рецепт прост: всегда и везде использовать pconnect и смотреть чтобы не использовался просто connect. (мало ли какие скрипты ставить будешь).
Рецепт не верен
Я бы сказал опасен
 

Фанат

oncle terrible
Команда форума
alexhemp
Мальчик мой.
Вот эти твои слова
Неверно. Соединений может быть много, они "занимаются" и "освобождаются" по мере работы скриптов и хранятся в "пуле".
противоречат тому, что ты пишешь ранее.
свободного соединения в "пуле" с такими-же логином-паролем и хостом что переданы в параметрах
Из твоих объяснений никак не следукет, что вывод dusya про одно и то же соединение не верен.
Наоборот - из твоих бессвязных рассказов именно такой вывод и делается.
 

alexhemp

Новичок
Автор оригинала: Фанат
alexhemp
это ты все сам придумал, или тебе подсказал кто?
Подсказало чтение исходников mysql extention
частности там есть интересная ф-ция php_mysql_do_connect
pconnect через нее определяется
php_mysql_do_connect(INTERNAL_FUNCTION_PARAM_PASSTHRU, 1);

Код:
static void php_mysql_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent)
// пропущу проверки чтобы не утомлять (тут кстати и проверяются too many connections :-)
if (persistent) {
      list_entry *le;

// ищем соединение в списке постоянных 
/* try to find if we already have this link in our persistent list */
		if (zend_hash_find(&EG(persistent_list), hashed_details, hashed_details_length+1, (void **) &le)==FAILURE) {  
			/* we don't */

//не нашли - создаем

//
...			list_entry new_le;
// проверки пропускаем						/* create the link */
		mysql = (php_mysql_conn *) malloc(sizeof(php_mysql_conn));
		mysql->active_result_id = 0;
#if MYSQL_VERSION_ID > 32199 /* this lets us set the port number */
		mysql_init(&mysql->conn);
		if (connect_timeout != -1)
				mysql_options(&mysql->conn, MYSQL_OPT_CONNECT_TIMEOUT, (const char *)&connect_timeout);

			if (mysql_real_connect(&mysql->conn, host, user, passwd, NULL, port, socket, client_flags)==NULL) {
#else
			if (mysql_connect(&mysql->conn, host, user, passwd)==NULL) {
#endif
//
...
// пропускаем неважное для понимания

			/* hash it up */
// записываем в пул
			Z_TYPE(new_le) = le_plink;
			new_le.ptr = mysql;
			if (zend_hash_update(&EG(persistent_list), hashed_details, hashed_details_length+1, (void *) &new_le, sizeof(list_entry), NULL)==FAILURE) {
				free(mysql);
				efree(hashed_details);
				MYSQL_DO_CONNECT_RETURN_FALSE();
			}
			MySG(num_persistent)++;
			MySG(num_links)++;
// ну и тут дальше ничего полезного тоже нет для понимания процесса
По моему все очевидно, читайте исходники php для понимания, я в трудных случаях всегда так делаю.
 

Фанат

oncle terrible
Команда форума
Чем меньше скрипт, чем меньше работа с базой - тем больше накладные расходы на установление соединения.
Да-да!
50% от двух копеек - это, НЕСОМНЕННО в сто раз больше, чем полпроцента от двух рублей. Надо срочно попу рвать, чтобы сэкономить.
Смотрит нет ли свободного соединения в "пуле"
Вот именно в этом и состоит проблема пконнекта. На которую наткнулся icechel, к примеру. Висящие в воздухе открытые соединения.

В плане too many connections - pconnect никак не влияет
У тебя с арифметикой, я смотрю, совсем плохо.
 

alexhemp

Новичок
f1
Аргументируй? Проблем не наблюдал никогда, по крайней мере под средними нагрузками (10000 человек в день примерно).

Фанат
я давно уже не мальчик. Не придирайся к словам, глянь в исходники mysql ext для точного выяснения.
 

Фанат

oncle terrible
Команда форума
Подсказало чтение исходников mysql extention
молодец, исходники читать умеем.
а теперь вдумчиво читаем следующую фразу:
ПХП работает как модуль апача.
И пытаемся применить к ней ум, если имеется в наличии.
 

alexhemp

Новичок
Фанат
А почему это они висящие?

Если они на один хост с одним логином-паролем (99% нормальных скриптов и всяческих форумов-CMS). То следующее выполнение скрипта заюзает это-же соединение.

Давай поговорим не о моих проблемах а о реальной реализации. Перестань переходить на личности.
 

alexhemp

Новичок
Фанат
И что? если маленький предел pconnect-ов - это проблема хостинга, а не механизма в целом.
 

Profic

just Profic (PHP5 BetaTeam)
это проблема хостинга, а не механизма в целом
а вот тут я с тобой категорически не соглашусь.
начнем хотябы с того, что при использовании cgi/cli он впух и прах разбивается о shutdown процесса. и никаких хешей после себя естественно не оставляет. ибо физически не может
продолжим с того, что СВОЙ ОТДЕЛЬНЫЙ пул имеется для КАЖДОГО чайлда апача. а это значит кол-во открытых соединений = кол-во чайлдов апача * на кол-во пользователей хостинга (они же все используют pconnect, сам сказал). Причем имеются они всегда, даже тогда на сайт Васи Пупкина никто не заходит. Даже если счиать, что на одной машине хостятся 50 человек, которым отданы на растерзание 100 чайлдов апача, то рано или поздно количество открытых и висящих впустую соединений будет равно 5000 (пять тысяч!). муське плохо не станет?
вот и с спрашивается нафига козе такой баян?
 

alexhemp

Новичок
icechel
И на массовом и на коллокейшене.

Посмотрите в phpBB к примеру используется pconnect

Я бы сделал так если сомневаетесь

Вынес бы работу с клиентской библиотекой на уровень выше. и там бы использьзовал бы pconnect. Во всех скриптах использовал бы этот уровень абстракции с базой.
Если что - можно поменять на connect ;-)

Реально конечно если не стоит акселлератор (типа Zend Accelerator или Truck-MMCache) и скрипты маленькие (фронт-енд обычно проще чем бэк-энд) то компиляция PHP скрипта занимает намного больше времени чем вся работа с базой...
Экономия действительно копеечная, но 20 старушек - рупь ;-)

-~{}~ 10.12.04 17:59:

Profic

Дык сам механизм только в модуле и работает. Если не в модуле - то просто как обычный connect отрабатывает.
Но тогда проблема повисших коннектов - мне странна, ибо php при выгрузке должен прибрать за собой - закрыть ВСЕ соединения и т.п.
Опять-же в CGI никто теоретически не мешает использовать pconnect - мало-ли ты делаешь 100 раз соединение.

У меня есть на одном хостинге CGI вариант - но и там проблем с pconnect-ами не обнаружено никаких. Но и нагрузка там небольшая.
 

icechel

Новичок
alexhemp
Ты мне свои покажи где у тебя pconnect стоит. В PHPBB используется pconnect. Но в массе народ меняет его на просто коннект.

В целом ситуация понятна. Висячие процессы от пконнекта опять таки жрут память. Целесообразности пконнекта нет. Действительно об этом в мануале написано.
 

alexhemp

Новичок
Profic

насчет рассуждений по child-ы апача - не все так просто

Zend использует для выделения места под хэши _eamalloc

Там код очень заморочный, но упоминание кэширования тоже присутствует. Не удивлюсь увидев использованиe Shared Memory для хэш-таблиц, именно из соображений архитектуры Unix с постоянными fork-ами.

Проблема в том, что код весьма сложный, а времени особо сегодня нет. Я лично доверяю разработчикам PHP - не такие они идиоты, чтобы очевидные проблемы с pconnect не представлять.

-~{}~ 10.12.04 18:18:

icechel

Ну каждому свое... кто-то память экономит, кто-то время выполнения. Думаю рисков в pconnect нет никаких, всегда к тому-же можно поменять на connect.

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

icechel

Новичок
Вообще проверил сейчас на разных хостингах. Вроде работает и с пконнектом и процессы не размножаются.

На локальной машине процессы висят и не убиваются. Странно все это.
 
Сверху