diff --git a/app.js b/app.js
index e4614fab940b64093697c895737c8fa350cf20dd..7674a025f9b79d2d841ce0d30d975a6b6268a9f4 100644
--- a/app.js
+++ b/app.js
@@ -1,28 +1,5 @@
 const express = require("express");
-const { WebSocketServer } = require("ws");
-const gameModule = require("./src/game/game.js");
-
-// Maintain a list of connections
-// This will eventually map connections to lobby or game instances
-let connections = [];
-
-let games = {};
-
-// TO BE REWRITTEN
-games["game1"] = {
-  gameBoard: gameModule.createGameBoard(10, 10),
-  players: [],
-};
-
-games["game2"] = {
-  gameBoard: gameModule.createGameBoard(10, 10),
-  players: [],
-};
-
-games["game3"] = {
-  gameBoard: gameModule.createGameBoard(10, 10),
-  players: [],
-};
+const sockServer = require("./src/models/WebSocketModel.js");
 
 let webserver = express();
 
@@ -33,13 +10,25 @@ webserver.get("/", (_, res) => {
 });
 
 webserver.get("/public_games", (_, res) => {
-  let ids = Object.keys(games);
+  let ids = sockServer.getGameIds();
   res.json({ ids: ids });
 });
 
-webserver.get("/join_game/:gameId", (req, res) => {
-  let { gameId } = req.params;
-  if (!games.hasOwnProperty(gameId)) {
+webserver.get("/join_game/:gameId/:gameType", (req, res) => {
+  let { gameId, gameType } = req.params;
+  if (gameType === "private") {
+    if (!sockServer.hasGame(gameId)) {
+      sockServer.createGame(gameId, gameType);
+    } else {
+      console.log("Game already exists");
+      if (sockServer.games[gameId].type === "public") {
+        // TODO: THIS IS A HACK
+        return res.sendFile("public/index.html", { root: __dirname });
+      }
+    }
+    return res.sendFile("public/game.html", { root: __dirname });
+  }
+  if (!sockServer.hasGame(gameId)) {
     return res.status(404).send();
   }
   console.log("Sending room", gameId);
@@ -51,118 +40,16 @@ webserver.get("/join_game/:gameId", (req, res) => {
   res.sendFile("public/game.html", { root: __dirname });
 });
 
-webserver.listen(3000, () => console.log("Web server started."));
-
-const sockserver = new WebSocketServer({ port: 3001 });
-
-let gameBoard = [
-  [0, 0, 0, 0, 0, 0, 0, 0, 0],
-  [0, 1, 0, 0, 0, 0, 0, 0, 0],
-  [0, 0, 0, 0, 0, 0, 2, 0, 0],
-  [0, 0, 0, 0, 0, 0, 0, 0, 0],
-  [0, 0, 0, 0, 0, 0, 0, 0, 0],
-];
-
-let moveHandler = (connection, message) => {
-  console.log("Received move: " + message.data);
-  let movement = message.data;
-  let pid = message.pid;
-  let gameBoard = games[connection.protocol].gameBoard;
-  console.log("pid: ", pid);
-
-  for (var i = 0; i < gameBoard.length; i++) {
-    for (var j = 0; j < gameBoard[0].length; j++) {
-      if (gameBoard[i][j].type === 1 && gameBoard[i][j].pid === pid) {
-		console.log("Updating direction to: " + movement);
-        switch (movement) {
-          case "up":
-            gameBoard[i][j].direction = 0;
-            break;
-          case "right":
-		    console.log("1");
-			console.log(gameBoard[i][j]);
-            gameBoard[i][j].direction = 1;
-			cell.direction = 1;
-            break;
-          case "down":
-            gameBoard[i][j].direction = 2;
-            break;
-          case "left":
-            gameBoard[i][j].direction = 3;
-            break;
-        }
-		 console.log("New direction set to: " + gameBoard[i][j].direction);
-        return;
-      }
-    }
-  }
-};
-
-sockserver.on("connection", (connection) => {
-  console.log("New client connected!");
-
-  console.log(connection.protocol);
-
-  let roomId = connection.protocol;
-
-  games[roomId].players.push(connection);
-  games[roomId].gameBoard = gameModule.addPlayer(
-    games[roomId].gameBoard,
-    games[roomId].players.length,
-  );
-
-  connection.send(
-    JSON.stringify({ type: "newUser", data: games[roomId].players.length }),
-  );
-
-  connection.on("close", () => {
-    games[roomId].players = games[roomId].players.filter(
-      (curr) => curr !== games[roomId].players,
-    );
-    console.log("Client has disconnected!");
-  });
-
-  connection.on("message", (event) => {
-    try {
-      let message = JSON.parse(event);
-      // All messages are expected to have a type
-      if (message.type === "move") {
-        console.log("Received move: " + message.data);
-		moveHandler(connection, message);
-      } else if (message.type === "chat") {
-        console.log("Received chat: " + message.data);
-      } else if (message.type === "join") {
-        console.log("Received join: " + message.data);
-      } else if (message.type === "leave") {
-        console.log("Received leave: " + message.data);
-      } else {
-        console.log("Received: " + message);
-      }
-    } catch (e) {
-      console.log("Error parsing JSON: " + e.message);
-    }
-  });
-
-  connection.onerror = function () {
-    console.log("websocket error");
-  };
+webserver.get("/public/gameClient.js", (_, res) => {
+  res.sendFile("gameClient.js", { root: `${__dirname}/public` });
 });
 
+webserver.listen(3000, () => console.log("Web server started."));
+
 console.log("Server started.");
 
 // Game loop
 
-for (let game in games) {
-  setInterval(() => {
-    games[game].gameBoard = gameModule.moveOneStep(games[game].gameBoard);
-    for (let conn of games[game].players) {
-      conn.send(
-        JSON.stringify({ type: "gameBoard", data: games[game].gameBoard }),
-      );
-    }
-  }, 1000);
-}
-
 //setInterval(() => {
 //	console.log('Broadcasting message to clients, connections.length: ', connections.length);
 //	connections.forEach(connection => {
diff --git a/public/game.html b/public/game.html
index 80e94909daa1c6ed8265db5c03645fb382ff4436..c156280708127f100ac9a64e6eddc9e24599a067 100644
--- a/public/game.html
+++ b/public/game.html
@@ -1,151 +1,30 @@
 <!doctype html>
 <html lang="en">
   <head>
-    <title>WebSocket Example</title>
+    <title>GBS</title>
   </head>
 
-  <body>
-    <h1>WebSocket Client</h1>
-    <input type="text" id="messageInput" placeholder="Type a message..." />
-    <button id="sendButton">Send</button>
-    <div id="messages"></div>
+  <style>
+    #chatOutput {
+      height: 200px;
+      overflow-y: scroll;
+      border: 1px solid black;
+    }
+  </style>
 
-    <div id="game">
-      <canvas id="gameCanvas" width="800" height="600"></canvas>
+  <body>
+    <div id="game"></div>
+    <div id="Chat">
+      <div id="chatOutput"></div>
+      <input type="text" id="chatInput" />
+      <button id="chatSend">Send</button>
+    </div>
+    <div id="start">
+      <div id="numPlayers">Number of Players: 0</div>
+      <div id="playersStarted">Players Started: 0</div>
+      <button id="startButton">Ready</button>
     </div>
 
-    <script>
-      let pathParts = window.location.pathname.split("/");
-      let roomId = pathParts[pathParts.length - 1];
-
-      const joinMessage = { type: "join", data: `${roomId}` };
-      let moveMessage = { type: "move", data: "up", pid: 0 };
-
-      const socket = new WebSocket("ws://127.0.0.1:3001", `${roomId}`);
-
-      const canvas = document.getElementById("gameCanvas");
-      const width = canvas.width;
-      const height = canvas.height;
-
-      let gameBoardHandler = (event) => {
-        let ctx = canvas.getContext("2d");
-        ctx.clearRect(0, 0, width, height);
-        ctx.fillStyle = "black";
-        ctx.fillRect(0, 0, width, height);
-        ctx.fillStyle = "white";
-
-        let board = event.data;
-        console.log(board);
-
-        widthStep = width / board[0].length;
-        heightStep = height / board.length;
-
-        for (let i = 0; i < board.length; i++) {
-          for (let j = 0; j < board[i].length; j++) {
-            if (board[i][j].type === 0) {
-              ctx.fillRect(
-                j * widthStep + 1,
-                i * heightStep + 1,
-                widthStep - 2,
-                heightStep - 2,
-              );
-            }
-            if (board[i][j].type === 1) {
-              ctx.fillStyle = "red";
-              ctx.fillRect(
-                j * widthStep + 1,
-                i * heightStep + 1,
-                widthStep - 2,
-                heightStep - 2,
-              );
-              ctx.fillStyle = "white";
-            }
-            if (board[i][j].type === 2) {
-              ctx.fillStyle = "red";
-              ctx.fillRect(
-                j * widthStep + 1,
-                i * heightStep + 1,
-                widthStep - 2,
-                heightStep - 2,
-              );
-              ctx.fillStyle = "white";
-            }
-            if (board[i][j].type === 3) {
-              ctx.fillStyle = "blue";
-              ctx.fillRect(
-                j * widthStep + 1,
-                i * heightStep + 1,
-                widthStep - 2,
-                heightStep - 2,
-              );
-              ctx.fillStyle = "white";
-            }
-            if (board[i][j].type === 4) {
-              ctx.fillStyle = "yellow";
-              ctx.fillRect(
-                j * widthStep + 1,
-                i * heightStep + 1,
-                widthStep - 2,
-                heightStep - 2,
-              );
-              ctx.fillStyle = "white";
-            }
-          }
-        }
-      };
-
-      let newUserHandler = (event) => {
-        moveMessage.pid = event.data;
-      };
-
-      socket.addEventListener("open", () => {
-        console.log("Connected to server");
-        socket.send(JSON.stringify(joinMessage));
-      });
-
-      socket.addEventListener("message", (event) => {
-        try {
-          let msg = JSON.parse(event.data);
-          if (msg.type === "gameBoard") {
-            gameBoardHandler(msg);
-          } else if (msg.type === "newUser") {
-            newUserHandler(msg);
-          } else {
-            const messages = document.getElementById("messages");
-            const messageElement = document.createElement("div");
-            messageElement.innerText = event.data;
-            messages.appendChild(messageElement);
-          }
-        } catch {
-          console.log(event.data);
-        }
-      });
-
-      document.addEventListener("keydown", (event) => {
-        if (event.key === "ArrowUp") {
-          moveMessage.data = "up";
-          socket.send(JSON.stringify(moveMessage));
-        }
-        if (event.key === "ArrowDown") {
-          moveMessage.data = "down";
-          socket.send(JSON.stringify(moveMessage));
-        }
-        if (event.key === "ArrowLeft") {
-          moveMessage.data = "left";
-          socket.send(JSON.stringify(moveMessage));
-        }
-        if (event.key === "ArrowRight") {
-          moveMessage.data = "right";
-          socket.send(JSON.stringify(moveMessage));
-        }
-      });
-
-      document.getElementById("sendButton").addEventListener("click", () => {
-        const messageInput = document.getElementById("messageInput");
-        const message = messageInput.value;
-        socket.send(message);
-        messageInput.value = "";
-      });
-    </script>
+    <script src="/public/gameClient.js"></script>
   </body>
 </html>
diff --git a/public/gameClient.js b/public/gameClient.js
new file mode 100644
index 0000000000000000000000000000000000000000..2f37c9492da3ed383aa303c638ba68281a587536
--- /dev/null
+++ b/public/gameClient.js
@@ -0,0 +1,195 @@
+let pathParts = window.location.pathname.split("/");
+let roomId = pathParts[pathParts.length - 2];
+
+const joinMessage = { type: "join", data: `${roomId}`, pid: 0 };
+let moveMessage = { type: "move", data: "up", pid: 0 };
+const startMessage = { type: "start", data: `${roomId}`, pid: 0 };
+const chatMessage = { type: "chat", data: "", pid: 0 };
+
+const socket = new WebSocket("ws://127.0.0.1:3001", `${roomId}`);
+
+let canvas = null;
+let width = 800;
+let height = 600;
+
+let gameStarted = false;
+
+let startButton = document.getElementById("startButton");
+let chatSend = document.getElementById("chatSend");
+let chatInput = document.getElementById("chatInput");
+
+let playersReady = 0;
+
+let gameBoardHandler = (event) => {
+  canvas = document.getElementById("gameCanvas");
+  let ctx = canvas.getContext("2d");
+  ctx.clearRect(0, 0, width, height);
+  ctx.fillStyle = "black";
+  ctx.fillRect(0, 0, width, height);
+  ctx.fillStyle = "white";
+
+  let board = event.data;
+  widthStep = width / board[0].length;
+  heightStep = height / board.length;
+
+  for (let i = 0; i < board.length; i++) {
+    for (let j = 0; j < board[i].length; j++) {
+      if (board[i][j].type === 0) {
+        ctx.fillRect(
+          j * widthStep + 1,
+          i * heightStep + 1,
+          widthStep - 2,
+          heightStep - 2,
+        );
+      }
+      if (board[i][j].type === 1) {
+        ctx.fillStyle = "red";
+        ctx.fillRect(
+          j * widthStep + 1,
+          i * heightStep + 1,
+          widthStep - 2,
+          heightStep - 2,
+        );
+        ctx.fillStyle = "white";
+      }
+      if (board[i][j].type === 2) {
+        ctx.fillStyle = "red";
+        ctx.fillRect(
+          j * widthStep + 1,
+          i * heightStep + 1,
+          widthStep - 2,
+          heightStep - 2,
+        );
+        ctx.fillStyle = "white";
+      }
+      if (board[i][j].type === 3) {
+        ctx.fillStyle = "blue";
+        ctx.fillRect(
+          j * widthStep + 1,
+          i * heightStep + 1,
+          widthStep - 2,
+          heightStep - 2,
+        );
+        ctx.fillStyle = "white";
+      }
+      if (board[i][j].type === 4) {
+        ctx.fillStyle = "yellow";
+        ctx.fillRect(
+          j * widthStep + 1,
+          i * heightStep + 1,
+          widthStep - 2,
+          heightStep - 2,
+        );
+        ctx.fillStyle = "white";
+      }
+    }
+  }
+};
+
+let newUserHandler = (event) => {
+  moveMessage.pid = event.data;
+  startMessage.pid = event.data;
+  chatMessage.pid = event.data;
+  joinMessage.pid = event.data;
+  socket.send(JSON.stringify(joinMessage));
+};
+
+socket.addEventListener("open", () => {
+  console.log("Connected to server");
+});
+
+socket.addEventListener("message", (event) => {
+  try {
+    let msg = JSON.parse(event.data);
+    if (msg.type === "gameBoard") {
+      gameBoardHandler(msg);
+    } else if (msg.type === "newUser") {
+      newUserHandler(msg);
+    } else if (msg.type === "chat") {
+      const messages = document.getElementById("chatOutput");
+      const messageElement = document.createElement("div");
+      messageElement.innerText = `${msg.pid}: ${msg.data}`;
+      messages.appendChild(messageElement);
+    } else if (msg.type === "start") {
+      gameStart();
+      gameStarted = true;
+    } else if (msg.type === "playerReady") {
+      const messages = document.getElementById("chatOutput");
+      const messageElement = document.createElement("div");
+      messageElement.innerText = `Player ${msg.pid} is ready!`;
+      messages.appendChild(messageElement);
+
+      updatePlayerCount(1);
+    } else if (msg.type === "playerJoined") {
+      const messages = document.getElementById("chatOutput");
+      const messageElement = document.createElement("div");
+      messageElement.innerText = `Player ${msg.pid} has joined the game!`;
+      messages.appendChild(messageElement);
+
+      updateNumberPlayers(msg.numPlayers);
+    }
+  } catch (e) {
+    console.log(e.message);
+  }
+});
+
+document.addEventListener("keydown", (event) => {
+  console.log(event.key);
+  if (event.key === "ArrowUp") {
+    moveMessage.data = "up";
+    socket.send(JSON.stringify(moveMessage));
+  }
+  if (event.key === "ArrowDown") {
+    moveMessage.data = "down";
+    socket.send(JSON.stringify(moveMessage));
+  }
+  if (event.key === "ArrowLeft") {
+    moveMessage.data = "left";
+    socket.send(JSON.stringify(moveMessage));
+  }
+  if (event.key === "ArrowRight") {
+    moveMessage.data = "right";
+    socket.send(JSON.stringify(moveMessage));
+  }
+  if (event.key === "Enter") {
+    if (!gameStarted) {
+      sendChat();
+    }
+  }
+});
+
+startButton.addEventListener("click", () => {
+  socket.send(JSON.stringify(startMessage));
+});
+
+chatSend.addEventListener("click", () => {
+  sendChat();
+});
+
+let sendChat = () => {
+  chatMessage.data = chatInput.value;
+  socket.send(JSON.stringify(chatMessage));
+  chatInput.value = "";
+};
+
+let gameStart = () => {
+  let gameDiv = document.getElementById("game");
+  canvas = document.createElement("canvas");
+  canvas.id = "gameCanvas";
+  canvas.width = width;
+  canvas.height = height;
+  gameDiv.appendChild(canvas);
+
+  document.getElementById("chatInput").disabled = false;
+};
+
+let updatePlayerCount = (count) => {
+  let playerCount = document.getElementById("playersStarted");
+  playersReady += count;
+  playerCount.innerText = `Players: ${playersReady}`;
+};
+
+let updateNumberPlayers = (count) => {
+  let countDiv = document.getElementById("numPlayers");
+  countDiv.innerText = `Number of players: ${count}`;
+};
diff --git a/public/index.html b/public/index.html
index 155b83b9fce20a8d6e729e89260099022a1926dd..44ee57eecb223edf4f42ae1f39af091862509668 100644
--- a/public/index.html
+++ b/public/index.html
@@ -75,7 +75,16 @@
           aria-labelledby="headingTwo"
           data-parent="#accordion"
         >
-          <div class="card-body">Test2</div>
+          <div class="card-body">
+            <input type="text" id="gameId" placeholder="Game ID" />
+            <button
+              id="privButton"
+              class="btn btn-primary"
+              onclick="window.location = `/join_game/${document.getElementById('gameId').value}/private`"
+            >
+              Join Game
+            </button>
+          </div>
         </div>
       </div>
     </div>
@@ -87,6 +96,12 @@
 
       publicBody.textContent = "Loading...";
 
+      let privButton = document.getElementById("privButton");
+      privButton.addEventListener("click", () => {
+        console.log("Joining game " + document.getElementById("gameId").value);
+        window.location = `/join_game/${document.getElementById("gameId").value}/private`;
+      });
+
       fetch("/public_games")
         .then((response) => {
           return response.json();
@@ -103,7 +118,7 @@
             button.addEventListener("click", () => {
               // will redirect to new chatroom immediately
               console.log("Joining game " + data.ids[i]);
-              window.location = `/join_game/${data.ids[i]}`;
+              window.location = `/join_game/${data.ids[i]}/public`;
             });
             publicBody.appendChild(button);
           }
diff --git a/src/game/game.js b/src/game/game.js
index 1087a46df079a33437644b2fbccf65e4c9ce60ce..7f7fb14b90aefcf375d810a01c65de91fdc2ebfd 100644
--- a/src/game/game.js
+++ b/src/game/game.js
@@ -3,7 +3,7 @@ const cellTypes = {
   PLAYERHEAD: 1,
   PLAYERBODY: 2,
   FOOD: 3,
-  BANANA: 4
+  BANANA: 4,
 };
 
 function createCell(x, y, type) {
@@ -32,7 +32,9 @@ function addFood(gameBoard) {
     }
   }
 
-  let bananaExists = gameBoard.some(row => row.some(cell => cell.type === cellTypes.BANANA)); 
+  let bananaExists = gameBoard.some((row) =>
+    row.some((cell) => cell.type === cellTypes.BANANA),
+  );
 
   //Create food cells randomly
   if (emptySpaces.length > 0) {
@@ -76,9 +78,9 @@ module.exports = {
       if (gameBoard[y][x].type === cellTypes.EMPTY) {
         gameBoard[y][x].type = cellTypes.PLAYERHEAD;
         gameBoard[y][x].pid = pid;
-		
-		let bodyPlaced = false;
-		
+
+        let bodyPlaced = false;
+
         if (y - 1 >= 0 && gameBoard[y - 1][x].type === cellTypes.EMPTY) {
           // Place body segment
           gameBoard[y - 1][x] = createCell(x, y - 1, cellTypes.PLAYERBODY);
@@ -86,20 +88,20 @@ module.exports = {
           gameBoard[y][x].next = gameBoard[y - 1][x];
           bodyPlaced = true;
         }
-		if (bodyPlaced) {
+        if (bodyPlaced) {
           placedCell = true;
-		} else {
+        } else {
           gameBoard[y][x] = createCell(x, y, cellTypes.EMPTY);
+        }
       }
     }
-	}
     //console.log(gameBoard);
     return gameBoard;
   },
 
   moveOneStep: (gameBoard) => {
     // Save board state to allow multiple snake movements
-    let updatedBoard = gameBoard.map(row => row.map(cell => ({ ...cell })));
+    let updatedBoard = gameBoard.map((row) => row.map((cell) => ({ ...cell })));
 
     // Loop through board until we find a PLAYERHEAD
     for (var i = 0; i < gameBoard.length; i++) {
@@ -137,8 +139,10 @@ module.exports = {
           ) {
             console.log(`Player ${cell.pid} has collided with the wall!`);
             // Remove the player from the game (indicating death)
-            updatedBoard = updatedBoard.map(row =>
-              row.map(c => (c.pid === cell.pid ? createCell(c.x, c.y, cellTypes.EMPTY) : c))
+            updatedBoard = updatedBoard.map((row) =>
+              row.map((c) =>
+                c.pid === cell.pid ? createCell(c.x, c.y, cellTypes.EMPTY) : c,
+              ),
             );
             continue;
           }
@@ -157,14 +161,16 @@ module.exports = {
 
           // Handle collision with banana
           if (gameBoard[newY][newX].type == cellTypes.BANANA) {
-			      console.log('Slip');
-			      updatedBoard[newY][newX] = createCell(newX, newY, cellTypes.EMPTY);
-			      updatedBoard = updatedBoard.map(row =>
-			        row.map(c => (c.pid === cell.pid ? createCell(c.x, c.y, cellTypes.EMPTY) : c))
+            console.log("Slip");
+            updatedBoard[newY][newX] = createCell(newX, newY, cellTypes.EMPTY);
+            updatedBoard = updatedBoard.map((row) =>
+              row.map((c) =>
+                c.pid === cell.pid ? createCell(c.x, c.y, cellTypes.EMPTY) : c,
+              ),
             );
-		        updatedBoard = addFood(updatedBoard);
-		        continue;
-	      	}
+            updatedBoard = addFood(updatedBoard);
+            continue;
+          }
 
           // Snake head to new position by updating cell object
           let newHeadCell = createCell(newX, newY, cellTypes.PLAYERHEAD);
diff --git a/src/models/WebSocketModel.js b/src/models/WebSocketModel.js
new file mode 100644
index 0000000000000000000000000000000000000000..348144b15315e2c7307b30f214f5130452b81c31
--- /dev/null
+++ b/src/models/WebSocketModel.js
@@ -0,0 +1,207 @@
+const { WebSocketServer } = require("ws");
+const gameModule = require("../game/game.js");
+
+class WebSocketModel {
+  constructor() {
+    this.connections = [];
+    this.games = {};
+    this.games["game1"] = {
+      gameBoard: gameModule.createGameBoard(10, 10),
+      players: [],
+      type: "public",
+      started: false,
+      readyPlayers: 0,
+    };
+    this.games["game2"] = {
+      gameBoard: gameModule.createGameBoard(10, 10),
+      players: [],
+      type: "public",
+      started: false,
+      readyPlayers: 0,
+    };
+    this.games["game3"] = {
+      gameBoard: gameModule.createGameBoard(10, 10),
+      players: [],
+      type: "public",
+      started: false,
+      readyPlayers: 0,
+    };
+    this.sockserver = new WebSocketServer({ port: 3001 });
+
+    this.onConnection();
+
+    for (let game in this.games) {
+      setInterval(() => {
+        if (!this.games[game].started) return;
+
+        this.games[game].gameBoard = gameModule.moveOneStep(
+          this.games[game].gameBoard,
+        );
+        for (let conn of this.games[game].players) {
+          conn.send(
+            JSON.stringify({
+              type: "gameBoard",
+              data: this.games[game].gameBoard,
+            }),
+          );
+        }
+      }, 1000);
+    }
+  }
+
+  hasGame(gameId) {
+    return this.games.hasOwnProperty(gameId);
+  }
+
+  getGameIds() {
+    let publicGames = [];
+    publicGames = Object.keys(this.games).filter(
+      (game) => this.games[game].type === "public",
+    );
+    return publicGames;
+  }
+
+  createGame(gameId, gameType) {
+    this.games[gameId] = {
+      gameBoard: gameModule.createGameBoard(10, 10),
+      players: [],
+      type: gameType,
+      started: false,
+      readyPlayers: 0,
+    };
+  }
+
+  moveHandler(connection, message) {
+    console.log("Received move: " + message.data);
+    let movement = message.data;
+    let pid = message.pid;
+    let gameBoard = this.games[connection.protocol].gameBoard;
+    console.log("pid: ", pid);
+
+    for (var i = 0; i < gameBoard.length; i++) {
+      for (var j = 0; j < gameBoard[0].length; j++) {
+        if (gameBoard[i][j].type === 1 && gameBoard[i][j].pid === pid) {
+          console.log("Updating direction to: " + movement);
+          switch (movement) {
+            case "up":
+              gameBoard[i][j].direction = 0;
+              break;
+            case "right":
+              gameBoard[i][j].direction = 1;
+              cell.direction = 1;
+              break;
+            case "down":
+              gameBoard[i][j].direction = 2;
+              break;
+            case "left":
+              gameBoard[i][j].direction = 3;
+              break;
+          }
+          console.log("New direction set to: " + gameBoard[i][j].direction);
+          return;
+        }
+      }
+    }
+  }
+
+  onConnection() {
+    this.sockserver.on("connection", (connection) => {
+      console.log("New client connected!");
+
+      console.log(connection.protocol);
+
+      let roomId = connection.protocol;
+
+      if (!this.games[roomId].started) {
+        this.games[roomId].players.push(connection);
+        this.games[roomId].gameBoard = gameModule.addPlayer(
+          this.games[roomId].gameBoard,
+          this.games[roomId].players.length,
+        );
+      } else {
+        this.games[roomId].players.push(connection);
+      }
+
+      connection.send(
+        JSON.stringify({
+          type: "newUser",
+          data: this.games[roomId].players.length,
+        }),
+      );
+
+      connection.on("close", () => {
+        this.games[roomId].players = this.games[roomId].players.filter(
+          (curr) => curr !== this.games[roomId].players,
+        );
+        console.log("Client has disconnected!");
+      });
+
+      connection.on("message", (event) => {
+        try {
+          let message = JSON.parse(event);
+          console.log("Received message: " + message);
+          // All messages are expected to have a type
+          if (message.type === "move") {
+            console.log("Received move: " + message.data);
+            this.moveHandler(connection, message);
+          } else if (message.type === "chat") {
+            console.log("Received chat: " + message.data);
+            for (let conn of this.games[roomId].players) {
+              conn.send(
+                JSON.stringify({
+                  type: "chat",
+                  data: message.data,
+                  pid: message.pid,
+                }),
+              );
+            }
+          } else if (message.type === "join") {
+            console.log("Received join: " + message.data);
+            for (let conn of this.games[roomId].players) {
+              conn.send(
+                JSON.stringify({
+                  type: "playerJoined",
+                  data: message.data,
+                  numPlayers: this.games[roomId].players.length,
+                  pid: message.pid,
+                }),
+              );
+            }
+          } else if (message.type === "leave") {
+            console.log("Received leave: " + message.data);
+          } else if (message.type === "start") {
+            console.log("Received start: " + message.data);
+            for (let conn of this.games[roomId].players) {
+              if (conn !== connection)
+                conn.send(
+                  JSON.stringify({ type: "playerReady", data: message.data }),
+                );
+            }
+            this.games[roomId].readyPlayers++;
+            if (
+              this.games[roomId].players.length ===
+              this.games[roomId].readyPlayers
+            ) {
+              for (let conn of this.games[roomId].players) {
+                conn.send(
+                  JSON.stringify({ type: "start", data: message.data }),
+                );
+              }
+              this.games[roomId].started = true;
+            }
+          } else {
+            console.log("Received: " + message);
+          }
+        } catch (e) {
+          console.log("Error parsing JSON: " + e.message);
+        }
+      });
+
+      connection.onerror = function () {
+        console.log("websocket error");
+      };
+    });
+  }
+}
+
+module.exports = new WebSocketModel();
diff --git a/tests/TEMPFILE b/tests/TEMPFILE
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/tests/websocket.test.js b/tests/websocket.test.js
deleted file mode 100644
index 1dfa7434ee9075b61494750f740bb01ec536ade9..0000000000000000000000000000000000000000
--- a/tests/websocket.test.js
+++ /dev/null
@@ -1,50 +0,0 @@
-let WebSocketClient = require("websocket").client;
-
-let createClient = (port, hostname, protocol) => {
-  let WebSocketClient = require("websocket").client;
-  let client = new WebSocketClient();
-
-  client.on("connectFailed", (error) => {
-    console.log("Connect Error: " + error.toString());
-  });
-
-  client.on("connect", (connection) => {
-    console.log("WebSocket Client Connected");
-    connection.on("error", (error) => {
-      console.log("Connection Error: " + error.toString());
-    });
-
-    connection.on("close", () => {
-      console.log(`${protocol} Connection Closed`);
-    });
-
-    connection.on("message", (message) => {
-      if (message.type === "utf8") {
-        console.log("Received: '" + message.utf8Data + "'");
-      }
-    });
-  });
-
-  client.connect(`ws://${hostname}:${port}/`, protocol);
-};
-
-test("start websocket server", () => {
-  let ConnectionController = require("../src/route/connectionController");
-  let wsServer = ConnectionController.startServer(8080, "localhost");
-  expect(wsServer).toBeDefined();
-  expect(wsServer.server).toBeDefined();
-  expect(wsServer.app).toBeDefined();
-  expect(wsServer.connections).toBeDefined();
-
-  console.log(wsServer.server);
-
-  let shutdown = () => {
-    wsServer.server.closeAllConnections();
-    wsServer.server.shutDown();
-    wsServer.app.close();
-  };
-
-  let client = createClient(8080, "localhost", "echo-protocol");
-
-  shutdown();
-});