var actionReceivers = {
'move': function (data) {
},
'buffer': function (data) {
},
'chat': function (data) {
}
};
socket.on('message', function(obj) {
for each (action in obj) { if (action in actionReceivers) {
actionReceivers[action](obj[action]);
} }
};
É importante ter uma "camada" intermediária como receiver pra
evitar que algum player possa achar uma falha no seu protocolo de
transmissão e ordenar a execução de comandos arbitrários no computador
dos outros jogadores. Com essa "camada de tradução", você limita os
comandos apenas a um subset dos disponíveis, diferente do que
aconteceria se você checasse diretamente a existência dos métodos na
classe do usuário ou algo assim. Obviamente ela não precisa funcionar
dessa forma (pode ser um dict com a lista de métodos disponíveis, por
exemplo), mas lembre-se sempre de não deixar que uma mensagem do
server execute algo que não seja explicitamente autorizado no cliente.
Amplexos.
--
diego nunes
http://dnun.es
--
William Régis Drawanz Dias
Aluno de Ciência da Computação - UFPel
Grupo de Aplicações de Inteligência Artificial
Essas são só sugestões e existem diversas técnicas diferentes. Eu
fiz um jogo isométrico multiplayer com chat de load mediano (60
usuários simultâneos por sala), mapas de 120x120 quadrantes (mais ou
menos 64 megapixels quadrados) com movimentação pelo teclado e usei
essa última técnica com grande sucesso. Há muita documentação por aí,
inclusive papers de algumas grandes empresas (a Bungie, por exemplo,
tem artigos periódicos sobre game development, cobrindo de uso de
memória a eficiência de protocolo, passando por infraestrutura e
técnicas de rede--recomendo muito que dê uma olhada).
> Provavelmente terei que fazer o mesmo cálculo de caminho do lado do
> server e sempre verificar se as 2 coordenadas estão sincronizadas...
A regra de ouro dos jogos que rodam no cliente (flash e js) é
lembrar que a não ser que a informação seja validada no servidor, ela
é intrinsecamente insegura e deve ser verificada de alguma forma.
> Outra coisa seria o cara enviar para o server uma socket de
> movimentação contendo uma coordenada do outro extremo do mapa do jogo,
> algo que ele ainda não teria acesso, pra isso eu teria tratar toda
> hora do lado do server se aquela coordenada que ele passou está ao seu
> alcance.
Só agora li aqui embaixo, isso, hahaha. É exatamente o que falei
lá em cima. Nesse caso, você só o deixa andar o quanto pode. No
próximo update ele vai enviar de novo uma posição impossível, mas você
só anda o quanto dá. E assim pro diante. Se for obviamente abusivo,
você pode pensar em auto-moderação do sistema e kickar o usuário.
> Tem várias paradas caóticas pra se pensar nesse projeto.
Nem vou falar das opções de melhoria de eficiência no lado do
servidor com cache de posicionamento e envio periódico em lote pra não
adicionar mais loucura :P Mas considere isso, futuramente. Em vez de
enviar os updates imediatamente, pense em um timer periódico pra
enviar em lote. Vai aumentar o número máximo de pessoas simultâneas na
sala enormemente.
Pense que a meta é que nenhum usuário receba mais do que 20
updates (mensagens no socket) por segundo--idealmente não mais do que
10.
2011/5/28 Ricardo Tomasi <ricar...@gmail.com>:
> A versão 0.7 do socket.io tem uma solução pra isso, custom events.
Só lembrando que o que está acontecendo é que o Socket.IO está
implementando um protocolo próprio pra isso: é mais um overhead na
comunicação. Toda "facilidade" pro desenvolvimento traz consigo o peso
da _genericidade_ da implementação, já que ela é voltada a um público
muito amplo e precisa atender a necessidades diversas.
Se não for muito dispendioso e sua aplicação precisar de um
desempenho excelente, recomendo que você implemente seu próprio
protocolo mínimo.
--
Se o cara quiser cheatar e enviar as sockets com um valor diferente do
que deveria, o servidor vai ver que os valores não estão batendo e vai
enviar uma socket pro client avisando algo do tipo "cara sua posição
atual não pode ser X é Y" e colocaria o player no seu devido lugar Y,
e se o cara editasse essa parte do código por exemplo e insistisse no
envio de sockets mal intencionadas levaria um kick.
A questão é, conseguir avaliar o que é lag e o que é cheat, isso eu
não consegui formar uma idéia aceitável. :/
Abraços.
Nesse caso a gente pode ter mais problema com o acúmulo de
comandos por causa de lag. Pra evitar isso, às vezes o desenvolvedor
decide que o fluxo é:
1) o usuário aperta a tecla;
2) a tecla apertada é enviada para o servidor;
3) o servidor recebe o comando e responde dizendo a posição atual do
usuário e a próxima posição;
4) ao receber a mensagem de movimentação do servidor, o personagem
finalmente se move nessa tela.
Esse fluxo é absolutamente à prova de hacks e, inclusive, ele é
auto-corretivo (auto-manutenção) no caso de hacks locais (que só
influenciariam a posição do usuário na tela dele mesmo). O problema é
que nesse caso temos o pior tipo de lag: o "input lag", que é o tempo
entre a ação do usuário e uma reação do aplicativo. Esse input lag
varia de acordo com a conexão do usuário e pode chegar a mais de meio
segundo, o que é pouco razoável. A vantagem é que todos os usuários
ficam mais sincronizados e as diferenças de posicionamento no mundo
virtual ficam quase irrisórias. De qualquer forma é uma abordagem que
funciona para poucos casos.
Temo que estejamos fugindo um bocado do escopo da lista. Querem
falar a respeito em private?
William, vou responder ao seu último email diretamente, pra não
poluir a lista de Node com assuntos de desenvolvimento de jogos.
Amplexos.
Muito obrigado a todos que estão me ajudando nesta discussão.
--
2011/6/1 William Dias <diasfo...@gmail.com>:
Renato Elias
Tel: +55 (011) 7694-3872
2011/6/1 Renato Elias <renato...@gmail.com>:
Essa é a versão ainda sem as optimizações debatidas aqui no tópico
(até pq quero que o código seja útil para quem está começando e ainda
não tem uma idéia clara de como node e socket.io funcionam). Por
enquanto nessa versão, os usuários podem apenas caminhar pelo mapinha
e conversar entre si. Se souberem de alguém que está começando e quer
ter um exemplo de um código que não seja de chat para aprender,
repassem o link (eu sei que algumas coisas podem estar feias ou
erradas no código pois afinal é o primeiro projeto em node que eu
trabalho, por isso estou completamente disponível para ouvir suas
críticas e sugestões). E me desculpem também pela falta de testes no
código, estou lendo sobre node-unit no momento e pretendo incorporá-lo
ao projeto em breve.
Estou fazendo uma baita refatoração no projeto, cuidando a prevenção
de cheats, broadcast seletivo e outras melhorias que foram descritas
aqui, principalmente pelo amigo Diego. Ah eu testei no ipod 4 aqui e
rodou, só quando vc der zoom vai perceber um baita lag na
movimentação, estou fazendo novos testes de performance pra melhorar
isso também.
Abraços pessoal! Qualquer coisa é só me chamar aqui ou no twitter @diaswrd
--