diff --git a/src/modals/ForceUpdateModal.js b/src/modals/ForceUpdateModal.js new file mode 100644 index 0000000..7edf7bc --- /dev/null +++ b/src/modals/ForceUpdateModal.js @@ -0,0 +1,23 @@ +import React from "react"; +import { Box, Label, Text } from "theme-ui"; + +import Modal from "../components/Modal"; + +function ForceUpdateModal({ isOpen }) { + return ( + + + + + Please refresh your browser to update to the latest version. + + + + ); +} + +export default ForceUpdateModal; diff --git a/src/network/Session.js b/src/network/Session.js index 88d4671..b2973cc 100644 --- a/src/network/Session.js +++ b/src/network/Session.js @@ -26,7 +26,7 @@ import { logError } from "../helpers/logging"; * Session Status Event - Status of the session has changed * * @event Session#status - * @property {"ready"|"joining"|"joined"|"offline"|"reconnecting"|"auth"} status + * @property {"ready"|"joining"|"joined"|"offline"|"reconnecting"|"auth"|"needs_update"} status */ /** @@ -101,6 +101,7 @@ class Session extends EventEmitter { this.socket.on("game_expired", this._handleGameExpired.bind(this)); this.socket.on("disconnect", this._handleSocketDisconnect.bind(this)); this.socket.io.on("reconnect", this._handleSocketReconnect.bind(this)); + this.socket.on("force_update", this._handleForceUpdate.bind(this)); this.emit("status", "ready"); } catch (error) { @@ -197,7 +198,7 @@ class Session extends EventEmitter { this._gameId = gameId; this._password = password; - this.socket.emit("join_game", gameId, password); + this.socket.emit("join_game", gameId, password, process.env.REACT_APP_VERSION); this.emit("status", "joining"); } @@ -418,6 +419,16 @@ class Session extends EventEmitter { this.joinGame(this._gameId, this._password); } } + + _handleForceUpdate() { + /** + * Force Update Event - An update has been released + * + * @event Session#forceUpdate + */ + this.socket.disconnect(); + this.emit("status", "needs_update"); + } } export default Session; diff --git a/src/routes/Game.js b/src/routes/Game.js index 7610850..190fb86 100644 --- a/src/routes/Game.js +++ b/src/routes/Game.js @@ -11,6 +11,7 @@ import MapLoadingOverlay from "../components/map/MapLoadingOverlay"; import AuthModal from "../modals/AuthModal"; import GameExpiredModal from "../modals/GameExpiredModal"; +import ForceUpdateModal from "../modals/ForceUpdateModal"; import { useAuth } from "../contexts/AuthContext"; import { MapStageProvider } from "../contexts/MapStageContext"; @@ -83,6 +84,7 @@ function Game() { }; }, [session]); + // Join game useEffect(() => { if (sessionStatus === "ready" && databaseStatus !== "loading") { @@ -137,6 +139,9 @@ function Game() { isOpen={gameExpired} onRequestClose={() => setGameExpired(false)} /> + {!sessionStatus && }