Итак, ваш вопрос заключается в том, как эффективно общаться между СЕРВЕРОМ и несколькими КЛИЕНТАМИ почти в реальном времени. У вас две проблемы, эффективная коммуникация с клиентом. И эффективная связь между «сеансами» на сервере.
HTTP-КЛИЕНТ НА СЕРВЕР
Протокол http не сохраняет состояние. Это означает, что вы отправляете запрос, сервер отвечает, а затем соединение закрывается. Это затрудняет двунаправленное общение или управление событиями, как того требует игра. Вот почему в большинстве сетевых игр используется протокол UDP, который имеет гораздо меньшие накладные расходы на отправку информации. Мы должны использовать TCP/IP, и мы должны использовать протокол HTTP в этом сценарии, так как мы можем сделать это эффективно?
Комета - это ответ. Сервер Comet — это просто «термин», означающий сервер, который держит соединение открытым в течение длительного времени для постоянной отправки данных клиенту. Серверы Comet используют асинхронные потоковые (ajax) соединения, которые позволяют клиенту «узнавать» о поступлении новой информации без необходимости чтения всего ответа. См. также: Долгий опрос PHP Comet Server
СЕССИЯ К СЕССИИ
Когда сервер получает запрос, ему нужно задать вопрос «Где все остальные», и он должен задавать этот вопрос часто и эффективно. Mysql не будет лучшим технологическим решением для чего-то подобного. Вы хотите ОЧЕНЬ ОЧЕНЬ быстро записывать и читать небольшие значения из нескольких процессов (каждого http-клиента)
Зачем отправлять данные через сетевое соединение, декодировать их из строки (sql), а затем ждать, пока сервер декодирует вставку или ответ и т. д. - все это звучит как много дополнительных накладных расходов.
Что вам нужно, так это настоящий IPC (межпроцессное взаимодействие). Этого трудно достичь в PHP, но это можно сделать. Использование общей памяти или даже запись в файл с отображением памяти было бы лучшим решением для обеспечения максимальной скорости чтения и записи обновлений GPS-координат. PHP IPC
Связываем вместе:
Клиент отправляет запрос на сервер и начинает его опрашивать. Сервер считывает общую память, чтобы узнать координаты других. Сервер записывает в открытое соединение строку, содержащую строку JSON, описывающую местонахождение всех игроков. В то же время, пока клиент опрашивает сервер, он также должен отправить запрос на сервер с описанием своего местоположения, и сервер должен записать это значение в разделяемую память. Программа остается в непрерывном цикле, пока клиент не закроет http-соединение.
Смотрите это:
Если общая память не подходит, я бы предложил использовать другую базу данных или что-то более простое, например хранилище ключей и значений (memcache) или даже mongodb. У них обоих будет меньше транзакционных издержек, и они смогут вставлять и опрашивать гораздо быстрее, чем MySQL.
Третий вариант — использование PostgreSQL в качестве механизма IPC. Вы можете использовать события LISTEN для этого, но это становится немного надуманным.
Примечания:
Это решение не очень хорошо масштабируется с PHP. Допустим, вы используете apache и у вас есть 20 воркеров в вашем пуле воркеров. Когда вы достигнете 20 подключений, все процессы php серверов будут поглощены другими запросами, поэтому 21-й запрос будет бесконечно ждать, пока рабочий станет доступным.
Лучшее решение — реализовать сервер Comet/long-polling в чем-то вроде Twisted или любого другого асинхронного фреймворка.
person
Ben DeMott
schedule
11.03.2011