Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@socialgorithm/game-server

Package Overview
Dependencies
Maintainers
2
Versions
40
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@socialgorithm/game-server - npm Package Compare versions

Comparing version 1.0.3 to 1.1.0

dist/Match.d.ts

22

dist/GameServer.d.ts

@@ -1,19 +0,19 @@

import { GameMessage } from "@socialgorithm/model";
import * as io from "socket.io";
import { NewGameFn } from "./Game";
/// <reference types="socket.io" />
import { Messages, Socket } from "@socialgorithm/model";
import { NewMatchFn } from "./Match";
import { ServerOptions } from "./ServerOptions";
export declare class GameServer {
private newGameFn;
private newMatchFn;
io: SocketIO.Server;
private games;
private playerToGameID;
private matches;
private playerToMatchID;
private playerToSocket;
constructor(gameInfo: GameMessage.GameInfoMessage, newGameFn: NewGameFn, serverOptions?: ServerOptions);
constructor(gameInfo: Messages.GameInfoMessage, newMatchFn: NewMatchFn, serverOptions?: ServerOptions);
sendGameMessageToPlayer: (player: string, payload: any) => void;
sendGameUpdated: (socket: io.Socket, gameID: string) => (payload: any) => void;
sendGameEnded: (socket: io.Socket, gameID: string) => (gameEndedMessage: GameMessage.GameEndedMessage) => void;
private createGame;
sendMatchEnded: (socket: Socket) => (matchEndedMessage: Messages.MatchEndedMessage) => void;
sendGameEnded: (socket: Socket) => (gameEndedMessage: import("@socialgorithm/model").Game) => void;
private createMatch;
private sendPlayerMessageToGame;
private generateGameTokens;
private generateMatchTokens;
private allPlayersReady;
}
"use strict";
var __assign = (this && this.__assign) || function () {
__assign = Object.assign || function(t) {
for (var s, i = 1, n = arguments.length; i < n; i++) {
s = arguments[i];
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
t[p] = s[p];
}
return t;
};
return __assign.apply(this, arguments);
};
exports.__esModule = true;

@@ -20,7 +9,7 @@ var model_1 = require("@socialgorithm/model");

var GameServer = (function () {
function GameServer(gameInfo, newGameFn, serverOptions) {
function GameServer(gameInfo, newMatchFn, serverOptions) {
var _this = this;
this.newGameFn = newGameFn;
this.games = new Map();
this.playerToGameID = new Map();
this.newMatchFn = newMatchFn;
this.matches = new Map();
this.playerToMatchID = new Map();
this.playerToSocket = new Map();

@@ -32,43 +21,38 @@ this.sendGameMessageToPlayer = function (player, payload) {

}
_this.playerToSocket.get(player).emit(model_1.GAME_SOCKET_MESSAGE.GAME__PLAYER, payload);
_this.playerToSocket.get(player).emit(new model_1.Events.GameToPlayerEvent(payload));
};
this.sendGameUpdated = function (socket, gameID) { return function (payload) {
var gameUpdatedMessage = {
payload: payload
};
socket.emit(model_1.GAME_SOCKET_MESSAGE.GAME_UPDATED, __assign({ gameID: gameID }, gameUpdatedMessage));
this.sendMatchEnded = function (socket) { return function (matchEndedMessage) {
socket.emit(new model_1.Events.MatchEndedEvent(matchEndedMessage));
}; };
this.sendGameEnded = function (socket, gameID) { return function (gameEndedMessage) {
socket.emit(model_1.GAME_SOCKET_MESSAGE.GAME_ENDED, __assign({ gameID: gameID }, gameEndedMessage));
this.sendGameEnded = function (socket) { return function (gameEndedMessage) {
socket.emit(new model_1.Events.GameEndedEvent(gameEndedMessage));
}; };
this.createGame = function (socket) { return function (createGameMessage) {
debug("Received create game message %O", createGameMessage);
var playerGameTokens = _this.generateGameTokens(createGameMessage.players);
createGameMessage.players = createGameMessage.players.map(function (player) { return playerGameTokens[player]; });
var gameOutputChannel = {
sendGameEnd: _this.sendGameEnded(socket, createGameMessage.gameID),
sendGameUpdate: _this.sendGameUpdated(socket, createGameMessage.gameID),
sendPlayerMessage: _this.sendGameMessageToPlayer
this.createMatch = function (socket) { return function (message) {
debug("Received create match message %O", message);
var playerTokens = _this.generateMatchTokens(message.players);
message.players = message.players.map(function (player) { return playerTokens[player]; });
var matchID = uuid_1.v4();
var matchOutputChannel = {
sendGameEnded: _this.sendGameEnded(socket),
sendMatchEnded: _this.sendMatchEnded(socket),
sendMessageToPlayer: _this.sendGameMessageToPlayer
};
_this.games.set(createGameMessage.gameID, {
game: _this.newGameFn(createGameMessage, gameOutputChannel),
players: createGameMessage.players
_this.matches.set(matchID, _this.newMatchFn(message, matchOutputChannel));
message.players.forEach(function (player) {
_this.playerToMatchID.set(player, matchID);
});
createGameMessage.players.forEach(function (player) {
_this.playerToGameID.set(player, createGameMessage.gameID);
});
socket.emit(model_1.GAME_SOCKET_MESSAGE.GAME_CREATED, { playerGameTokens: playerGameTokens });
socket.emit(new model_1.Events.MatchCreatedEvent({ playerTokens: playerTokens }));
}; };
this.sendPlayerMessageToGame = function (player) { return function (payload) {
if (!_this.playerToGameID.has(player)) {
this.sendPlayerMessageToGame = function (player) { return function (message) {
if (!_this.playerToMatchID.has(player)) {
debug("Player " + player + " does not have an associated game, cannot send player's message");
return;
}
var gameId = _this.playerToGameID.get(player);
if (!_this.games.has(gameId)) {
debug("Game " + gameId + " not found, cannot send player " + player + "'s message");
var matchId = _this.playerToMatchID.get(player);
if (!_this.matches.has(matchId)) {
debug("Match " + matchId + " not found, cannot send player " + player + "'s message");
}
_this.games.get(gameId).game.onPlayerMessage(player, payload);
_this.matches.get(matchId).onMessageFromPlayer(player, message);
}; };
this.generateGameTokens = function (players) {
this.generateMatchTokens = function (players) {
var gameTokens = {};

@@ -78,6 +62,6 @@ players.forEach(function (player) { gameTokens[player] = uuid_1.v4(); });

};
this.allPlayersReady = function (gameID) {
var requiredPlayers = _this.games.get(gameID).players;
var currentPlayers = Object.entries(_this.playerToGameID)
.filter(function (entry) { return entry[1] === gameID; })
this.allPlayersReady = function (matchID) {
var requiredPlayers = _this.matches.get(matchID).players;
var currentPlayers = Object.entries(_this.playerToMatchID)
.filter(function (entry) { return entry[1] === matchID; })
.map(function (entry) { return entry[0]; });

@@ -92,14 +76,17 @@ return requiredPlayers.every(function (requiredPlayer) { return currentPlayers.includes(requiredPlayer); });

debug("Started Socialgorithm Game Server on " + port);
this.io.on("connection", function (socket) {
socket.emit(model_1.GAME_SOCKET_MESSAGE.GAME_INFO, gameInfo);
if (socket.handshake.query && socket.handshake.query.token) {
var token = socket.handshake.query.token;
this.io.on("connection", function (rawSocket) {
var socket = new model_1.Socket(rawSocket);
socket.emit(new model_1.Events.GameInfoEvent(gameInfo));
if (socket.socket.handshake.query && socket.socket.handshake.query.token) {
var token = socket.socket.handshake.query.token;
_this.playerToSocket.set(token, socket);
socket.on(model_1.GAME_SOCKET_MESSAGE.GAME__PLAYER, _this.sendPlayerMessageToGame(token));
var playersGame = _this.playerToGameID.get(token);
if (playersGame && _this.allPlayersReady(playersGame)) {
_this.games.get(playersGame).game.start();
socket.addHandler(new model_1.Handlers.PlayerToGameEventHandler(_this.sendPlayerMessageToGame(token)));
var playersMatch = _this.playerToMatchID.get(token);
if (playersMatch && _this.allPlayersReady(playersMatch)) {
_this.matches.get(playersMatch).start();
}
}
socket.on(model_1.GAME_SOCKET_MESSAGE.CREATE_GAME, _this.createGame(socket));
else {
socket.addHandler(new model_1.Handlers.CreateMatchEventHandler(_this.createMatch(socket)));
}
});

@@ -106,0 +93,0 @@ }

@@ -1,5 +0,5 @@

import { GAME_SOCKET_MESSAGE, GameMessage, Player } from "@socialgorithm/model";
import { Game, GameOutputChannel, NewGameFn } from "./Game";
import { Messages, Player } from "@socialgorithm/model";
import { GameServer } from "./GameServer";
import { IMatch, MatchOutputChannel, NewMatchFn } from "./Match";
export default GameServer;
export { GAME_SOCKET_MESSAGE, Game, GameMessage, GameOutputChannel, NewGameFn, Player, };
export { Messages, IMatch, MatchOutputChannel, NewMatchFn, Player, };
"use strict";
exports.__esModule = true;
var model_1 = require("@socialgorithm/model");
exports.GAME_SOCKET_MESSAGE = model_1.GAME_SOCKET_MESSAGE;
exports.GameMessage = model_1.GameMessage;
exports.Messages = model_1.Messages;
var GameServer_1 = require("./GameServer");
exports["default"] = GameServer_1.GameServer;
//# sourceMappingURL=index.js.map
{
"name": "@socialgorithm/game-server",
"version": "1.0.3",
"version": "1.1.0",
"description": "JS Game Server library",

@@ -32,3 +32,3 @@ "main": "dist/index.js",

"dependencies": {
"@socialgorithm/model": "^0.0.13",
"@socialgorithm/model": "0.0.15",
"debug": "^4.1.1",

@@ -35,0 +35,0 @@ "socket.io": "^2.2.0",

@@ -1,6 +0,6 @@

import { GAME_SOCKET_MESSAGE, GameMessage, Player } from "@socialgorithm/model";
import { Events, Handlers, Messages, Player, Socket } from "@socialgorithm/model";
import * as http from "http";
import * as io from "socket.io";
import { v4 as uuid } from "uuid";
import { Game, GameAndPlayers, GameOutputChannel, NewGameFn } from "./Game";
import { IMatch, MatchOutputChannel, NewMatchFn } from "./Match";
import { ServerOptions } from "./ServerOptions";

@@ -12,7 +12,7 @@ // tslint:disable-next-line:no-var-requires

public io: SocketIO.Server;
private games: Map<string, GameAndPlayers> = new Map();
private playerToGameID: Map<Player, string> = new Map();
private playerToSocket: Map<Player, io.Socket> = new Map();
private matches: Map<string, IMatch> = new Map();
private playerToMatchID: Map<Player, string> = new Map();
private playerToSocket: Map<Player, Socket> = new Map();
constructor(gameInfo: GameMessage.GameInfoMessage, private newGameFn: NewGameFn, serverOptions?: ServerOptions) {
constructor(gameInfo: Messages.GameInfoMessage, private newMatchFn: NewMatchFn, serverOptions?: ServerOptions) {
const app = http.createServer();

@@ -27,19 +27,22 @@ this.io = io(app);

this.io.on("connection", (socket: io.Socket) => {
socket.emit(GAME_SOCKET_MESSAGE.GAME_INFO, gameInfo);
this.io.on("connection", (rawSocket: io.Socket) => {
// Use a wrapper for type-safety
const socket = new Socket(rawSocket);
socket.emit(new Events.GameInfoEvent(gameInfo));
if (socket.handshake.query && socket.handshake.query.token) {
if (socket.socket.handshake.query && socket.socket.handshake.query.token) {
// This is a uabc/player connection
const token = socket.handshake.query.token;
const token = socket.socket.handshake.query.token;
this.playerToSocket.set(token, socket);
socket.on(GAME_SOCKET_MESSAGE.GAME__PLAYER, this.sendPlayerMessageToGame(token));
socket.addHandler(new Handlers.PlayerToGameEventHandler(this.sendPlayerMessageToGame(token)));
// If all players in a game are connected, start the game
const playersGame = this.playerToGameID.get(token);
if (playersGame && this.allPlayersReady(playersGame)) {
this.games.get(playersGame).game.start();
// If all players in a match are connected, start the match
const playersMatch = this.playerToMatchID.get(token);
if (playersMatch && this.allPlayersReady(playersMatch)) {
this.matches.get(playersMatch).start();
}
} else {
// Otherwise, it's a tournament server connection
socket.addHandler(new Handlers.CreateMatchEventHandler(this.createMatch(socket)));
}
socket.on(GAME_SOCKET_MESSAGE.CREATE_GAME, this.createGame(socket));
});

@@ -54,59 +57,50 @@ }

this.playerToSocket.get(player).emit(GAME_SOCKET_MESSAGE.GAME__PLAYER, payload);
this.playerToSocket.get(player).emit(new Events.GameToPlayerEvent(payload));
}
public sendGameUpdated = (socket: io.Socket, gameID: string) => (payload: any) => {
const gameUpdatedMessage: GameMessage.GameUpdatedMessage = {
payload,
};
socket.emit(GAME_SOCKET_MESSAGE.GAME_UPDATED, { gameID, ...gameUpdatedMessage });
public sendMatchEnded = (socket: Socket) => (matchEndedMessage: Messages.MatchEndedMessage) => {
socket.emit(new Events.MatchEndedEvent(matchEndedMessage));
}
public sendGameEnded = (socket: io.Socket, gameID: string) => (gameEndedMessage: GameMessage.GameEndedMessage) => {
socket.emit(GAME_SOCKET_MESSAGE.GAME_ENDED, { gameID, ...gameEndedMessage });
public sendGameEnded = (socket: Socket) => (gameEndedMessage: Messages.GameEndedMessage) => {
socket.emit(new Events.GameEndedEvent(gameEndedMessage));
}
private createGame = (socket: io.Socket) => (createGameMessage: GameMessage.CreateGameMessage) => {
private createMatch = (socket: Socket) => (message: Messages.CreateMatchMessage) => {
debug("Received create match message %O", message);
const playerTokens = this.generateMatchTokens(message.players);
message.players = message.players.map(player => playerTokens[player]);
// Convert player names to tokens - will be replaced when tournament-server uses secret tokens instead
debug("Received create game message %O", createGameMessage);
const playerGameTokens = this.generateGameTokens(createGameMessage.players);
createGameMessage.players = createGameMessage.players.map(player => playerGameTokens[player]);
const gameOutputChannel: GameOutputChannel = {
sendGameEnd: this.sendGameEnded(socket, createGameMessage.gameID),
sendGameUpdate: this.sendGameUpdated(socket, createGameMessage.gameID),
sendPlayerMessage: this.sendGameMessageToPlayer,
const matchID = uuid();
const matchOutputChannel: MatchOutputChannel = {
sendGameEnded: this.sendGameEnded(socket),
sendMatchEnded: this.sendMatchEnded(socket),
sendMessageToPlayer: this.sendGameMessageToPlayer,
};
this.games.set(
createGameMessage.gameID,
{
game: this.newGameFn(createGameMessage, gameOutputChannel),
players: createGameMessage.players,
},
);
createGameMessage.players.forEach(player => {
this.playerToGameID.set(player, createGameMessage.gameID);
this.matches.set(matchID, this.newMatchFn(message, matchOutputChannel));
message.players.forEach(player => {
this.playerToMatchID.set(player, matchID);
});
socket.emit(GAME_SOCKET_MESSAGE.GAME_CREATED, { playerGameTokens });
socket.emit(new Events.MatchCreatedEvent({ playerTokens }));
}
private sendPlayerMessageToGame = (player: Player) => (payload: any) => {
private sendPlayerMessageToGame = (player: Player) => (message: Messages.PlayerToGameMessage) => {
// Find the game that the player is in, send message
if (!this.playerToGameID.has(player)) {
if (!this.playerToMatchID.has(player)) {
debug(`Player ${player} does not have an associated game, cannot send player's message`);
return;
}
const gameId = this.playerToGameID.get(player);
const matchId = this.playerToMatchID.get(player);
if (!this.games.has(gameId)) {
debug(`Game ${gameId} not found, cannot send player ${player}'s message`);
if (!this.matches.has(matchId)) {
debug(`Match ${matchId} not found, cannot send player ${player}'s message`);
}
this.games.get(gameId).game.onPlayerMessage(player, payload);
this.matches.get(matchId).onMessageFromPlayer(player, message);
}
private generateGameTokens = (players: Player[]) => {
private generateMatchTokens = (players: Player[]) => {
const gameTokens: { [key: string]: string } = {};

@@ -117,6 +111,6 @@ players.forEach(player => { gameTokens[player] = uuid(); });

private allPlayersReady = (gameID: string) => {
const requiredPlayers = this.games.get(gameID).players;
const currentPlayers: Player[] = Object.entries(this.playerToGameID)
.filter(entry => entry[1] === gameID)
private allPlayersReady = (matchID: string) => {
const requiredPlayers = this.matches.get(matchID).players;
const currentPlayers: Player[] = Object.entries(this.playerToMatchID)
.filter(entry => entry[1] === matchID)
.map(entry => entry[0]);

@@ -123,0 +117,0 @@

@@ -1,4 +0,4 @@

import { GAME_SOCKET_MESSAGE, GameMessage, Player } from "@socialgorithm/model";
import { Game, GameOutputChannel, NewGameFn } from "./Game";
import { Messages, Player } from "@socialgorithm/model";
import { GameServer } from "./GameServer";
import { IMatch, MatchOutputChannel, NewMatchFn } from "./Match";

@@ -8,8 +8,7 @@ export default GameServer;

export {
GAME_SOCKET_MESSAGE,
Game,
GameMessage,
GameOutputChannel,
NewGameFn,
Messages,
IMatch,
MatchOutputChannel,
NewMatchFn,
Player,
};

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc