This is a Rails Application that uses WebSockets and the react-crossword component to create multiplayer crosswords. You can read a blog post about why I built it and how it works.
You can see a demo at multicrosser.chriszetter.com.
To run this project:
- Install Redis and make sure the server is running
- Run
./bin/setupto install dependencies - Run
./bin/rails crosswords:load_from_feedto load the latest crosswords to display on the homepage - Run
./bin/rails serverto start the project
Here's what happens when a player types a character:
- Client:
react-crosswordcallssetCellValueto update the grid
setCellValuecalls theonMovecallback with cell location and valueonMovecallback calls themovefunction in the action cable subscription- The
movefunction sends the move to the server
- Server:
MovesChannel#moveis run
- The move is recorded in Redis
- The move is rebroadcast to others in the channel
- On all clients:
- The
receivedfunction runs in the Action Cable subscriptions which calls theonReceiveMovecallback onReceiveMovecallssetCellValuewith thetriggerOnMoveCallbackoption set tofalsesoonMoveisn't called againsetCellValueupdates the crossword gird
If the move can't be broadcast with Action Cable it's stored in the MoveBuffer. On reconnection:
- The remote state of the grid will be received from the server and updated
- The moves in the moves buffer will be replayed
When the move MoveBuffer is replayed, moves will only apply if the cell they change still has the same character in it when the move was made. For example, if you change an 'A' to a 'B' while offline this move will be discarded if someone has since changed the 'A' to a 'C' and broadcast it to the server before you.
The MoveBuffer uses local storage so will persist if the page is refreshed or the browser is closed.
Crosswords are scraped from the Guardian Crossword pages which contain a JSON representation of each crossword. The crosswords are re-used following their Open Licence Terms.