Merge branch 'feat/96-add-getlobbystatus-command-on-server-side' into 'main'
Feat/96 add getlobbystatus command on server side Closes #96 See merge request cs108-fs26/Gruppe-13!103
This commit was merged in pull request #259.
This commit is contained in:
@@ -508,6 +508,67 @@ END
|
||||
|
||||
### Example Response (error)
|
||||
|
||||
```
|
||||
-ERR
|
||||
CODE=LOBBY_NOT_FOUND
|
||||
MESSAGE=Lobby not found
|
||||
END
|
||||
```
|
||||
|
||||
## GET_LOBBY_STATUS command
|
||||
|
||||
The `GET_LOBBY_STATUS` command requests the server to return the current state of a lobby, including the list of players and their ready state.
|
||||
|
||||
### Required pre-execution checks
|
||||
None.
|
||||
|
||||
### Request Parameters
|
||||
| Parameter Name | Type | Optional | Description |
|
||||
| :------------- | :--- | :------: | :---------- |
|
||||
| `ID` | `int` | no | Numeric id of the target lobby |
|
||||
|
||||
### Implementation notes
|
||||
|
||||
- Parser: `GetLobbyStatusParser` — reads the `ID` parameter and builds `GetLobbyStatusRequest`.
|
||||
- Handler: `GetLobbyStatusHandler` — queries `LobbyManager` for the lobby and builds a `GetLobbyStatusResponse` containing player entries.
|
||||
|
||||
### Success Response
|
||||
|
||||
The response contains a `LOBBY` collection with nested `PLAYERS` and one or more `PLAYER` entries. Each `PLAYER` entry contains `USERNAME` and `READY` fields.
|
||||
|
||||
Example response structure:
|
||||
|
||||
```
|
||||
+OK
|
||||
LOBBY
|
||||
ID=1
|
||||
PLAYERS
|
||||
PLAYER
|
||||
USERNAME=Lars_001
|
||||
READY=false
|
||||
END
|
||||
PLAYER
|
||||
USERNAME=Anna
|
||||
READY=true
|
||||
END
|
||||
END
|
||||
END
|
||||
END
|
||||
```
|
||||
|
||||
### Error Response
|
||||
| Code | Description |
|
||||
| :--- | :---------- |
|
||||
| `LOBBY_NOT_FOUND` | The specified lobby id does not exist |
|
||||
|
||||
### Example Request
|
||||
|
||||
```
|
||||
GET_LOBBY_STATUS ID=1
|
||||
```
|
||||
|
||||
### Example Response (error)
|
||||
|
||||
```
|
||||
-ERR
|
||||
CODE=LOBBY_NOT_FOUND
|
||||
|
||||
+62
@@ -0,0 +1,62 @@
|
||||
package ch.unibas.dmi.dbis.cs108.casono.server.app.commands.lobby.get_lobby_status;
|
||||
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.domain.lobby.LobbyId;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.domain.lobby.LobbyManager;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.domain.user.UserRegistry;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.command.execution.CommandHandler;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.response.ErrorResponse;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.response.dispatcher.ResponseDispatcher;
|
||||
import java.util.Optional;
|
||||
|
||||
/** Handler for GET_LOBBY_STATUS: returns lobby details and player list. */
|
||||
public class GetLobbyStatusHandler extends CommandHandler<GetLobbyStatusRequest> {
|
||||
private final LobbyManager lobbyManager;
|
||||
private final UserRegistry userRegistry;
|
||||
|
||||
public GetLobbyStatusHandler(
|
||||
ResponseDispatcher responseDispatcher,
|
||||
LobbyManager lobbyManager,
|
||||
UserRegistry userRegistry) {
|
||||
super(responseDispatcher);
|
||||
this.lobbyManager = lobbyManager;
|
||||
this.userRegistry = userRegistry;
|
||||
|
||||
// Only require logged-in session if the request does not provide an explicit ID
|
||||
// or USERNAME
|
||||
addCheck(
|
||||
request -> {
|
||||
if (!(request instanceof GetLobbyStatusRequest)) {
|
||||
return Optional.empty();
|
||||
}
|
||||
GetLobbyStatusRequest r = (GetLobbyStatusRequest) request;
|
||||
if (r.getId() != null || r.getUsername() != null) {
|
||||
return Optional.empty();
|
||||
}
|
||||
var maybeUser = userRegistry.getBySessionId(r.getSessionId());
|
||||
if (maybeUser.isPresent()) {
|
||||
return Optional.empty();
|
||||
}
|
||||
return Optional.of(
|
||||
new ErrorResponse(
|
||||
r.getContext(),
|
||||
"USER_NOT_LOGGED_IN",
|
||||
"Request requires an associated logged-in user"));
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(GetLobbyStatusRequest request) {
|
||||
var lobby =
|
||||
(request.getId() != null)
|
||||
? lobbyManager.getLobby(LobbyId.of(request.getId()))
|
||||
: lobbyManager.getLobbyByUsername(request.getUsername());
|
||||
|
||||
if (lobby == null) {
|
||||
responseDispatcher.dispatch(
|
||||
new ErrorResponse(request.getContext(), "LOBBY_NOT_FOUND", "Lobby not found"));
|
||||
return;
|
||||
}
|
||||
|
||||
responseDispatcher.dispatch(new GetLobbyStatusResponse(request.getContext(), lobby));
|
||||
}
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
package ch.unibas.dmi.dbis.cs108.casono.server.app.commands.lobby.get_lobby_status;
|
||||
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.command.parsing.CommandParser;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.request.PrimitiveRequest;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.request.accessor.RequestParameterAccessor;
|
||||
|
||||
public class GetLobbyStatusParser implements CommandParser<GetLobbyStatusRequest> {
|
||||
@Override
|
||||
public GetLobbyStatusRequest parse(PrimitiveRequest primitiveRequest) {
|
||||
RequestParameterAccessor accessor =
|
||||
new RequestParameterAccessor(primitiveRequest.parameters());
|
||||
Integer id = null;
|
||||
try {
|
||||
id = accessor.optional("ID", null, Integer::parseInt);
|
||||
} catch (Exception e) {
|
||||
// parse error handled elsewhere
|
||||
}
|
||||
String username = accessor.optional("USERNAME", null);
|
||||
return new GetLobbyStatusRequest(primitiveRequest.context(), id, username);
|
||||
}
|
||||
}
|
||||
+23
@@ -0,0 +1,23 @@
|
||||
package ch.unibas.dmi.dbis.cs108.casono.server.app.commands.lobby.get_lobby_status;
|
||||
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.request.Request;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.request.RequestContext;
|
||||
|
||||
public class GetLobbyStatusRequest extends Request {
|
||||
private final Integer id;
|
||||
private final String username;
|
||||
|
||||
public GetLobbyStatusRequest(RequestContext context, Integer id, String username) {
|
||||
super(context);
|
||||
this.id = id;
|
||||
this.username = username;
|
||||
}
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public String getUsername() {
|
||||
return username;
|
||||
}
|
||||
}
|
||||
+34
@@ -0,0 +1,34 @@
|
||||
package ch.unibas.dmi.dbis.cs108.casono.server.app.commands.lobby.get_lobby_status;
|
||||
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.domain.lobby.Lobby;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.request.RequestContext;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.response.SuccessResponse;
|
||||
import ch.unibas.dmi.dbis.cs108.casono.server.network.protocol.response.builder.ResponseBody;
|
||||
|
||||
/** Response with lobby player listing and simple READY placeholders. */
|
||||
public class GetLobbyStatusResponse extends SuccessResponse {
|
||||
public GetLobbyStatusResponse(RequestContext context, Lobby lobby) {
|
||||
super(
|
||||
context,
|
||||
ResponseBody.builder()
|
||||
.block(
|
||||
"LOBBY",
|
||||
lb -> {
|
||||
lb.param("ID", lobby.getId().value());
|
||||
lb.param("NAME", lobby.getName());
|
||||
lb.block(
|
||||
"PLAYERS",
|
||||
players -> {
|
||||
for (String p : lobby.getPlayerNames()) {
|
||||
players.block(
|
||||
"PLAYER",
|
||||
pb -> {
|
||||
pb.param("USERNAME", p);
|
||||
pb.param("READY", "false");
|
||||
});
|
||||
}
|
||||
});
|
||||
})
|
||||
.build());
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user