За последние 24 часа нас посетили 40035 программистов и 2468 роботов. Сейчас ищут 1148 программистов ...

long polling серверная часть

Тема в разделе "PHP для новичков", создана пользователем qwert_ukg, 30 май 2012.

  1. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    правильно ли я реализовал long polling?
    может что-то нужно сделать по другому?

    Код (Text):
    1. if(isset($_POST['last_id']) && $_POST['last_id'] != ""){
    2.     $link = mysql_connect("localhost","xxx","yyy");
    3.     mysql_select_db("zzz");
    4.     mysql_set_charset('utf8');
    5.     function get_reply(){
    6.         $query = 'SELECT `id`,`pid`,`text`,`name`,`lvl`,`date` FROM `comments` WHERE `id` >  '.$_POST['last_id'].' ORDER BY `id` DESC LIMIT 30';
    7.         $result = mysql_query($query);
    8.         if(mysql_num_rows($result) > 0){
    9.             $data = array();
    10.             while($row = mysql_fetch_assoc($result)){
    11.                 $data[$row['id']] = $row;
    12.             }
    13.             echo json_encode($data);
    14.         }else{
    15.             usleep(1000);
    16.             get_reply();
    17.         }
    18.     }
    19.     get_reply();
    20.     mysql_close($link);
    21. }
    Добавлено спустя 8 минут 44 секунды:
    в случае превышения таймлимита (либо другой ошибки) клиент отправляет аякс запрос заново
     
  2. sobachnik

    sobachnik Старожил

    С нами с:
    20 апр 2007
    Сообщения:
    3.380
    Симпатии:
    13
    Адрес:
    Дмитров, МО
    Сразу честно скажу, что я никогда не использовал эту технологию и совсем её не знаю. Но есть некоторое представление о том, зачем оно надо и как должно работать. Возможно, моё представление неверно.
    Во-первых, как я понимаю, это придумали для того, чтобы разгрузить сервер от лишних запросов, на которые пока нечего ответить. Во-вторых, чтобы пользователь получал новые данные не раз в заданный интервал времени, а мгновенно, как только они появились. Тот код, который показан выше - это ежесекундное дёргание б.д. и проверка, есть ли там что-то новое. По сути, это всё теже ежесекундные запросы и пользователь получит ответ не сразу, как он появился, а спустя какой-то интервал времени. Кроме того, если на сайте будет сидеть сотня пользователей, то это будет сотня потенциально ненужных запросов в секунду к базе. Я думаю, что серверная часть - это должно быть нечто "событийное". И написанное, скорее всего, не на PHP. Это вроде как onchange в JS :) Программа должна либо держать одновременно множество соединений и при наличии нового запроса на добавление данных - определять, кому их нужно показать и отправлять, либо это может быть несколько процессов, которые могут "общаться", но не через файл или базу, а "дёргать друг друга" напрямую. Но как это реализовать технически - на данный момент не знаю. Изучаю Си в свободное время, но пока как-то медленно...
     
  3. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    node.js???
     
  4. Easy

    Easy Активный пользователь

    С нами с:
    15 июл 2011
    Сообщения:
    286
    Симпатии:
    0
    Да, долно быть событийное. Но, событие всё равно что то да инициализирует.
    Что бы не делать кучу запросов в БД можно воспользоватся shared memory.
    Вот тут есть пример http://habrahabr.ru/post/128535/
     
  5. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    ой, ну ребят. если у вас так усё запущено, может сразу на яве или на сях писать сервер? Будет прям как пулемёт.
     
  6. Easy

    Easy Активный пользователь

    С нами с:
    15 июл 2011
    Сообщения:
    286
    Симпатии:
    0
    То есть делать каждую секунду запрос в бд от каждого юзера + я уверен что ещё само открытие страницы делает дапросы, это по вашему оптимально?)
    Ну давайте писать сайты для 100 юзеров максимум :)

    ps сервера на с++ и пишу всегда :) php на то и пхп что бы сайты писать)
     
  7. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    это уже второй топик, в котором автор планирует и проектирует, всё еще отказываясь назвать примерную нагрузку.

    1 запрос в секунду, даже если всю страницу перерисовывать заново, даже со всеми запросами - это херня =) если юзеров не много.

    я б не чесал репу и не тыкал бы пальцем в небо. надо прикинуть количество. от этого плясать. а так - гадание на кофейной гуще.
     
  8. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    да не стоит плясать от количества, если делать, то делать хорошо

    Добавлено спустя 1 минуту 31 секунду:
    а вот решение которое я использую http://pastebin.com/af8hF88J
     
  9. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
  10. MiksIr

    MiksIr Активный пользователь

    С нами с:
    29 ноя 2006
    Сообщения:
    2.339
    Симпатии:
    44
    Обращение к памяти нужно синхронизировать.
     
  11. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    если будут проблемы с этим, хотя маловероятно, есть вариант оправлять запросы в демона, а не на веб сервер, но не факт что демон на пхп "понравится" хостеру
     
  12. MiksIr

    MiksIr Активный пользователь

    С нами с:
    29 ноя 2006
    Сообщения:
    2.339
    Симпатии:
    44
    Понимаете, мало найти идею, нужно ее еще осмыслить. Вы хотите шаред память, что бы жить под нагрузками, но у вас fork модель (а какая еще на хостинге) и нелоченная память, которая под одновременной записью начнет давать мусор. Это маловероятно, да... если нет нагрузок. Но в общем можно было и базу спрашивать постоянно =)
    Что бы я предложил? Не поверите... файл ;) Файл можно читать в цикле (tail -f знаете?). Запись в файл в большинстве юникс-ос атомарна в пределах страницы памяти, т.е. около 4к, т.е. даже лочить ничего не нужно, если сообщения мелкие. Ну и не требуется поддержки работы с shmop, которую могут на хостинге и отключить.
     
  13. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    омг
    возьми впску и чо хошь делай с ней =)
     
  14. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    я с вами согласен, но моих нагрузок достаточно для того чтобы быть уверенным в том что вероятность возникновения двух событий одновременно настолько мала что учитывать ее не стоит
     
  15. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    ты следующим шагом в развитии попробуй java поковырять. похоже, тебе подойдет.
     
  16. qwert_ukg

    qwert_ukg Активный пользователь

    С нами с:
    20 июл 2010
    Сообщения:
    387
    Симпатии:
    0
    Адрес:
    Алмата
    проблема одновременной записи решилась загуглив по перво ссылке
    Код (Text):
    1. if($sem_id = sem_get(ftok(__FILE__, 'e'))){
    2.    if (sem_acquire($sem_id)){
    3.       ...
    4.    }else return;
    5. }
    а так как мой хостер обеспечивает поддержку семафоров первый же комент на офе дал результат
    Код (Text):
    1. if ( !function_exists('sem_get') ) {
    2.             function sem_get($key) { return fopen(__FILE__.'.sem.'.$key, 'w+'); }
    3.             function sem_acquire($sem_id) { return flock($sem_id, LOCK_EX); }
    4.             function sem_release($sem_id) { return flock($sem_id, LOCK_UN); }
    5. }