2012-10-18 2 views
2

기본적으로 서버에 실행중인 Java, Python 또는 C++ 스크립트를 사용하여 플레이어 인스턴스를 수신하여 참여, 통화, 내기, 접기, 카드 그리기 등의 작업을 수행하고 시간 제한을 설정합니다. 선수가 떠나거나 연결이 끊어 질 때.RPC를 사용하는 서버의 멀티 플레이어 카드 게임

기본적으로 나는 플레이어가 게임 서버와 통신하는 동일한 컴퓨터 또는 네트워크를 통해 연결된 컴퓨터에서 처리 할 수 ​​있도록 이러한 각 작업을 작은 요청으로하고 싶습니다.

메시징 보안은 문제가되지 않습니다. 이는 학습/연구/재미를위한 것입니다.

내 우선 순위 :

  1. 플레이어가 연결을 끊을 때 검출하기위한 좋은 계획을 가지고뿐만 아니라, 네트워크 대기 시간 등을 설명 할 수있을 손을 잃게하는 원인/부팅 전에.
  2. 속도. 내가 할 수있는 한 빨리 수백만 개의 손을 연주 할거야. 포트 또는 사용 소켓 또는 HTTP 포트 80 아파치 듣기 듣기

    1. : 공유 서버 인스턴스에
    2. 실행

    내 질문 (I 포트 또는 루트가 필요 것들에 제한적으로 액세스 할 수 있습니다) 스크립트? (나는 이것들 사이의 차이에 대해 약간 흐리다).

  3. 좋은 프레임 워크를 사용하려면 어떻게해야합니까?
  4. 메시지 유형? 나는 JSON 또는 프로토콜 버퍼를 생각하고있다.
  5. 빨리 만드는 방법?

감사합니다. 몇 가지 제안과 제안을 찾고 있습니다. 나는 그것을하는 것을 배울 그것 청초한 많은 것을 가진 차가운 문제다고 생각한다.

+0

가장 중요한 결정은 사용할 프레임 워크입니다. 학습 경험이 있다면 가장 중요한 질문은 배우고 싶은 것입니다. REST 서비스 또는 인터넷 프로토콜을 디자인하는 데 관심이 있습니까? Twisted 또는 asio와 같은 중간 수준의 프레임 워크 또는 Tomcat 또는 JBoss와 같은 상위 컨테이너를 학습 하시겠습니까? (일반적으로 컨테이너는 코드가 훨씬 적지 만 관리가 조금 더 쉬워 질 것입니다.) 3 가지 언어 중 어떤 것을 선호합니까? 그러나 그 외에도 다음과 같은 질문이 있습니다. 클라이언트 세션간에 얼마나 많은 데이터를 공유해야합니까? – abarnert

+0

좋은 질문입니다.내 궁극적 인 목표는 게임을하기 위해 다양한 인공 지능과 기계 학습 기술을 테스트하는 "테스트 놀이터"입니다. 클라이언트는 아무 것도 공유 할 필요가 없으며 서버를 게임 키퍼로 사용하여 서로 놀고 배우는 것입니다. – lollercoaster

+1

모든 플레이어가 사람이 아니라는 말로 시작해야합니다. 그런데 왜 네트워크가 필요합니까? 인공 지능이 동일한 머신에서 게임을하고있는 것을 인스턴스화하고 메모리를 통해 상태를 교환하게하십시오. 자신의 컴퓨터에서 각 AI를 실행하여 얻는 계산상의 이점보다 네트워크를 제거하여 훨씬 더 뛰어난 성능을 얻을 수 있습니다. AI 계산은 병렬 일 필요가 없습니다. –

답변

3

프레임 워크에 관한 한 Ginkgo은 네트워크 서비스를 구축하는 데 유망 해 보입니다. 파이썬은 매우 간단하며 비동기 성을 gevent으로 설정하면 일반적으로 콜백을 걱정할 필요없이 비동기식 작업을 수행 할 수 있습니다. gevent 코어는 또한 lot of building blocks에 대한 액세스를 제공합니다.

오히려 포트를 통해 통신 서비스를 많이하는 것보다, 당신은 Zookeeper 같은 RabbitMQ 또는 0mq, 또는 2) 분산 조정 서버처럼 하나 1)에 좋은 메시지 큐를 볼 수 있습니다.

당신이하고자하는 것은 어렵습니다. 특히 기본에 익숙하지 않은 경우 특히 그렇습니다. 이러한 기본 사항을 배우는 것은 가치있는 일입니다.

처음에는 속도에 대해 걱정하지 마십시오. 그것을 작동 시키십시오, 그리고 그것을 확장하십시오. 물론 미래에 확장하기 쉽도록 할 수있는 지침이 있습니다. 특히 Zookeeper은 수평 적으로 스케일링하기위한 구현하기 쉬운 기본 요소 (즉, 부하를 공유하는 여러 작업자)를 제공합니다. 특히 Zookeeper recipe book 및 그에 해당하는 python implementations을 참조하십시오 (gevent 기반 클라이언트 라이브러리 kazoo의 호의).

"빠름"은 개발 시간을 최적화하여 반복 작업을 줄이고 개발 환경을 저주하는 시간을 단축한다는 것을 의미합니다. 파이썬을 사용하면 빨리 시작하고 실행할 수 있으며 나중에 CPU 시간이나 메모리 사용에 정말로 바인딩하기 시작하면 나중에 최적화 할 수 있습니다. 이 특정 응용 프로그램을 사용하면 네트워크 IO에 바인딩 할 확률이 훨씬 높아집니다.

+0

+1. 수평 확장 및 신속한 개발에 대한 좋은 설명은 서버 측 성능의 열쇠입니다. 좀 더 성숙한 것 대신에 Gingko를 사용할 지 확신하지 못합니다. 그러나 gevent 위에 구축 된 완벽한 프레임 워크에 대한 아이디어는 상당히 멋집니다. 배울 것이별로 없을 때 콜백을 연결하는 방법을 배우는 데 80 %의 시간을 소비하지 않아도됩니다. – abarnert

+0

감사합니다. 은행 나무 *는 내가 원했던 것보다 성숙하지 못하지만, 내가 아는 바로는 평범한 문서 (즉, 문서가있다)를 가지고 있고 내 경험에 의하면 최소한의 상용구. 필자는 문서화 된 다른 gevent 기반 서비스 프레임 워크에 대해 자세히 알아보기를 원합니다. :) –

+0

요점은 제가 은행 나무보다 나은 다른 gevent 기반 프레임 워크를 모른다는 것입니다. 그래서 저는 은행 나무를 내가 원하는 것만 큼 성숙하지 않고 여전히 조심해야한다고 생각합니다. 어쨌든, 당신은 내가 그걸 가지고 노는 것을 확신했습니다. 당신의 대답은 "유망 해 보입니다"라고 말하는 것 이상을 말하지 않으므로, 당신의 대답은 분명히 내가 준 +1입니다. – abarnert

2

다른 건 없나요? 어쩌면 당신의 질문에 함께 갈 커피 한 잔 :

질문을 기초로하면 기본 TCP/IP 네트워킹에서부터 확장 가능한 아키텍처에 이르기까지 다양한 주제의 텍스트가 필요할 것입니다. 그럼에도 불구하고 어떤 방향을 제시하십시오.

질문 :

  1. 포트 또는 사용 소켓 또는 HTTP 포트 80 아파치 듣기 스크립트에 들어? (나는 이것들 사이의 차이에 대해 약간 흐리다).
난 당신이 어쩌면이 "빨리 내가 ​​할 수있는 이러한 손의 수백만 연주"될 서비스를 구현 설계 이들 각각의 정의에 명확하지 않은 경우 조금 흠 것을 감행 할

, 과도한 도달? 그러나 그들이 "무지가 행복하다"고 말하면서 당신을 멈추게하지 마십시오.

  1. 좋은 프레임 워크는 무엇입니까?

나는 귀하의 프로젝트가 Node.js의 좋은 후보라고 생각합니다. 주된 이유는 Node.js가 상대적으로 확장 가능하고 확장성에 필요한 복잡성을 숨기는 데 좋은 점입니다. Node.js에는 단점이 있으며, 단지 Google에서 'Node.js 확장 성 비평'을 검색합니다. 노드에 대한 주요 포인트입니다.js는 일반적인 목적의 프레임 워크를 사용하는 것과는 달리 확장 성이 어렵고 그 주위에 방법이 없으며 Node.js가 너무 높고 특정 적이기 때문에 문제를 해결할 수있는 옵션이 적습니다. 다른 단점은 Node.js가 Java 또는 Phyton이 아닌 Javascript를 선호한다는 것입니다.

  1. 메시지 유형? 나는 JSON 또는 프로토콜 버퍼를 생각하고있다.

클라이언트와 서버 사이에 많은 트래픽이 발생하지 않는다고 생각합니다. JSON이 더 널리 퍼져 있기 때문에 별 문제가되지 않습니다.

  1. 빨리 만드는 방법?

진짜 질문은 확장 성을 만드는 방법입니다. 인간 대 인간 카드 게임을 실행하는 것은 계산 집약적이지 않으므로 계산 한계에 도달하기 전에 I/O 용량이 부족할 것입니다. 이러한 한계를 극복하기 위해서는 부하를 시스템에 분산시켜야합니다. 멀티 플레이어 게임에서 일반적인 방법은 플레이어가 사용할 수있는 미리 정의 된 슬롯 수가있는 각 서버와 동일한 게임 서버에 대한 링크를 제공하는 목록 서버를 갖추는 것입니다. 이것은 중개인 기계가 얼마나 바쁜지에 따라 클라이언트에게 작업자 시스템을 할당하는 브로커 - 근로자 아키텍처의 변형입니다. 게임 사용자는 친구와 게임을 할 수 있도록 서버를 선택할 수 있어야합니다.

관련 :

  1. 플레이어가 연결을 끊을 때 검출하기위한 좋은 계획을 가지고뿐만 아니라, 네트워크 대기 시간 등을 설명 할 수있을 손을 잃게하는 원인/부팅 전에.

이 시간은 사람의 시간 단위 (밀리 초가 아니라 초)이기 때문에 클라이언트는 30 초 세션 시간 초과와 함께 10 초마다 keepalives에 말을 보내야합니다. 킵 얼라이브 (Keepalives)는 프레임 워크가 하위 레벨이며 처리하는 HTTP가 아닌 애플리케이션 프로토콜에서 JSON 메시지입니다. 프레임 워크 자체는 여러 개의 HTTP 세션 (요청/응답)이 동일한 연결을 통과 할 수 있지만 클라이언트가 항상 연결될 필요가없는 HTTP 1.1 연결 관리/풀링을 제공해야합니다. 이것은 신뢰성과 속도 사이의 좋은 절충안이며 턴 기반 카드 게임에 충분히 적합해야합니다.

1

솔직히 고전 램프로 시작하겠습니다. 재고 Apache 서버 및 mysql 데이터베이스를 가져 와서 파이썬 스크립트를 cgi-bin 디렉토리에 넣으십시오. 그들이 HTTP 대신 JSON을 보내고 받는다는 사실은별로 다르지 않습니다.

물론 이것은 가장 유연하거나 확장 가능한 솔루션이 될 수는 없지만 가능한 한 빨리 실제 문제에 직면해야합니다.

첫 번째 문제는 게임 상태입니다. 당신은 공유 상태가 없다고 주장하지만, 그것은 옳지 않습니다. 갑판에있는 카드, 테이블 위에 놓여있는 베팅, 차례입니다. 그것은 모든 상태이며 여러 플레이어들 사이에서 공유되고 서버에서 관리됩니다. 그 명령들 중 어떤 것이 다른 방법으로 작용할 수 있습니까? 따라서 CGI 스크립트의 개별 인스턴스간에 상태를 공유하는 방법이 필요합니다. 고전적인 솔루션은 데이터베이스에 상태를 저장하는 것입니다.

물론 사용자 세션도 처리해야합니다. 세부 사항은 어떤 세션 관리 체계를 선택 하느냐에 달려 있지만 가장 큰 문제는 연결 해제/시간 초과를 하위 수준에서 응용 프로그램 수준까지 전파하는 방법입니다.누군가 20 달러를 테이블에 놓은 다음 연결을 끊으면 어떻게됩니까? 가능한 모든 유스 케이스를 생각해야합니다.

다음으로 확장성에 대해 생각해 봐야합니다. 수백만 게임을 원하십니까? 글쎄, 모든 게임 상태를 가진 단일 데이터베이스가 있다면 원하는만큼 많은 웹 서버를 가질 수 있습니다. John Doe는 server1에 있고 Joe Schmoe는 server2에 있지만 동일한 게임에있을 수 있습니다. 반면에 동일한 게임에서 사람들이 같은 서버에서 만날 수있는 방법이 있다면 각 서버에 대해 별도의 데이터베이스를 사용할 수 있습니다. 어느 것이 더 합리적입니까? 어느 쪽이든, 서버 간의로드 밸런스는 어떻게됩니까? (당신은 그들 모두를 바쁘게하고 싶을뿐만 아니라 4 명의 플레이어가 모두 갈 준비가되어있는 상황을 피하기를 원하지만 3 개의 다른 서버에 있기 때문에 서로 게임을 할 수 없습니다 ...).

이 프로세스의 최종 결과는 원하는 용량의 1 %로 실행되는 서버를 엄청나게 망가뜨릴 것이므로 유지 관리 방법을 모를 수 있습니다. 그러나 문제 공간을보다 자세히 생각해 보았을 것입니다. 또한 장기적으로 볼 때 서버 개발의 기본 사항을 배웠을 것입니다.

시간이 있다면, 다음에는 모든 것을 던져서 사용자 지정 TCP 프로토콜을 설계하고, Twisted와 같이 서버를 구현하고, 게임 상태를 메모리에 유지하면서 모든 것을 다시 작성합니다. 표준로드 밸런서 대신 간단한 사용자 정의 브로커 작성

+0

예, 현재 나의 계획은 django/python + mysql + json이며 HTTP를 통해 궁금해하고 있습니다. 멋지다. 고마워. 중개인이 뭐야? 구글/위키 백과는 그다지 도움이되지 못했습니다. 기본적으로 연결/세션이있는 클라이언트의 상태를 유지하는 웹 서비스 일뿐입니다. – lollercoaster

+1

죄송합니다. "브로커"는 매우 과부하 된 용어입니다. 내가 의미하는 바는 플레이어와 게임에 대한 충분한 정보를 가지고 간단한로드 밸런싱에서부터 게임에 다시 참여하거나, 친구 찾기 등을하거나, 게임 별로드 밸런싱 (예 : 3 플레이어는 서버 2에서 네 번째를 기다리고, 다음 연결은 서버 2로 넘어 가고 서버 1에서도 부하가 적습니다. – abarnert

관련 문제