diff --git a/client/src/components/GameControls.vue b/client/src/components/GameControls.vue index bafc736..04509ab 100644 --- a/client/src/components/GameControls.vue +++ b/client/src/components/GameControls.vue @@ -1,6 +1,7 @@ @@ -19,6 +20,9 @@ export default { startGame() { this.$engine.startGame() }, + resetGame() { + this.$engine.resetGame() + }, }, } diff --git a/client/src/plugins/engine/index.js b/client/src/plugins/engine/index.js index 470c6c1..5de64ad 100644 --- a/client/src/plugins/engine/index.js +++ b/client/src/plugins/engine/index.js @@ -4,6 +4,7 @@ import stop from './stop' import fetchUpdate from './fetchUpdate' import fetchUserInfo from './fetchUserInfo' import startGame from './startGame' +import resetGame from './resetGame' import parseSyncData from './parseSyncData' export default (context, inject) => { @@ -19,6 +20,7 @@ export default (context, inject) => { fetchUpdate, fetchUserInfo, startGame, + resetGame, parseSyncData, } diff --git a/client/src/plugins/engine/resetGame.js b/client/src/plugins/engine/resetGame.js new file mode 100644 index 0000000..ed49631 --- /dev/null +++ b/client/src/plugins/engine/resetGame.js @@ -0,0 +1,7 @@ +export default async function() { + const { store } = this.context + + await this.callApi('/api/resetGame', { + g: store.state.engine.user?.game, + }) +} diff --git a/server/src/application/resetGame.go b/server/src/application/resetGame.go new file mode 100644 index 0000000..f0a93c4 --- /dev/null +++ b/server/src/application/resetGame.go @@ -0,0 +1,25 @@ +package application + +import ( + "fmt" + "net/http" + "sirlab.de/go/knyt/user" +) + +func (app *Application) ResetGame(usr *user.User, w http.ResponseWriter, r *http.Request) { + gameRef := r.URL.Query().Get("g") + gm, err := app.GetGameById(gameRef) + if err != nil { + w.WriteHeader(http.StatusNotFound) + fmt.Fprintf(w, "game not found") + return + } + + if usr.GetGameId() != gameRef || !usr.IsGamemaster() { + w.WriteHeader(http.StatusForbidden) + fmt.Fprintf(w, "forbidden") + return + } + + gm.ResetGame() +} diff --git a/server/src/game/changeGameState.go b/server/src/game/changeGameState.go index b793f9b..264ad90 100644 --- a/server/src/game/changeGameState.go +++ b/server/src/game/changeGameState.go @@ -8,7 +8,7 @@ func (gm *Game) changeGameState(expectedState, newState, newPhase string) error gm.mu.Lock() defer gm.mu.Unlock() - if gm.state != expectedState { + if expectedState != STATE_ANY && gm.state != expectedState { return fmt.Errorf("game state \"%s\" != expected state \"%s\"", gm.state, expectedState) } gm.state = newState @@ -22,7 +22,7 @@ func (gm *Game) changeGamePhase(expectedState, expectedPhase, newPhase string) e gm.mu.Lock() defer gm.mu.Unlock() - if gm.state != expectedState { + if expectedState != STATE_ANY && gm.state != expectedState { return fmt.Errorf("game state \"%s\" != expected state \"%s\"", gm.state, expectedState) } if gm.phase != expectedPhase { diff --git a/server/src/game/startGame.go b/server/src/game/startGame.go index b71f56c..1fbb447 100644 --- a/server/src/game/startGame.go +++ b/server/src/game/startGame.go @@ -33,7 +33,15 @@ func (gm *Game) startGameSub() { } } time.Sleep(3 * time.Second) - err = gm.changeGameState(STATE_READY_SET, STATE_PLAY, "") + err = gm.changeGameState(STATE_READY_SET, STATE_PLAY, PHASE_NONE) + if err != nil { + fmt.Println(err) + return + } +} + +func (gm *Game) ResetGame() { + err := gm.changeGameState(STATE_ANY, STATE_IDLE, PHASE_NONE) if err != nil { fmt.Println(err) return diff --git a/server/src/game/struct.go b/server/src/game/struct.go index e263c73..9cb4462 100644 --- a/server/src/game/struct.go +++ b/server/src/game/struct.go @@ -7,12 +7,17 @@ import ( ) const ( + STATE_ANY = "*" STATE_IDLE = "idle" STATE_ENTER_STATEMENTS = "enter-quotes" STATE_READY_SET = "ready-set" STATE_PLAY = "play" ) +const ( + PHASE_NONE = "" +) + type playerInfo struct { id string name string diff --git a/server/src/knyt.go b/server/src/knyt.go index ca020ed..773a5ab 100644 --- a/server/src/knyt.go +++ b/server/src/knyt.go @@ -24,6 +24,7 @@ func main() { mux.PrivateHandleFunc("/api/userinfo", mux.GetUserInfo) mux.PrivateHandleFunc("/api/sync", app.SyncHandler) mux.PrivateHandleFunc("/api/startGame", app.StartGame) + mux.PrivateHandleFunc("/api/resetGame", app.ResetGame) // default handler fsHandler := http.FileServer(http.Dir("../../client/dist/"))