mirror of
https://github.com/1f349/dendrite.git
synced 2024-11-25 21:21:35 +00:00
Reject make_join for empty rooms (#1439)
* Sanity-check room version on RS event input * Update gomatrixserverlib * Reject make_join when no room members are left * Revert some changes from wrong branch * Distinguish between room not existing and room being abandoned on this server * nolint
This commit is contained in:
parent
a6700331ce
commit
3013ade84f
@ -29,6 +29,7 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
// MakeJoin implements the /make_join API
|
// MakeJoin implements the /make_join API
|
||||||
|
// nolint:gocyclo
|
||||||
func MakeJoin(
|
func MakeJoin(
|
||||||
httpReq *http.Request,
|
httpReq *http.Request,
|
||||||
request *gomatrixserverlib.FederationRequest,
|
request *gomatrixserverlib.FederationRequest,
|
||||||
@ -79,6 +80,29 @@ func MakeJoin(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check if we think we are still joined to the room
|
||||||
|
inRoomReq := &api.QueryServerJoinedToRoomRequest{
|
||||||
|
ServerName: cfg.Matrix.ServerName,
|
||||||
|
RoomID: roomID,
|
||||||
|
}
|
||||||
|
inRoomRes := &api.QueryServerJoinedToRoomResponse{}
|
||||||
|
if err = rsAPI.QueryServerJoinedToRoom(httpReq.Context(), inRoomReq, inRoomRes); err != nil {
|
||||||
|
util.GetLogger(httpReq.Context()).WithError(err).Error("rsAPI.QueryServerJoinedToRoom failed")
|
||||||
|
return jsonerror.InternalServerError()
|
||||||
|
}
|
||||||
|
if !inRoomRes.RoomExists {
|
||||||
|
return util.JSONResponse{
|
||||||
|
Code: http.StatusNotFound,
|
||||||
|
JSON: jsonerror.NotFound(fmt.Sprintf("Room ID %q was not found on this server", roomID)),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if !inRoomRes.IsInRoom {
|
||||||
|
return util.JSONResponse{
|
||||||
|
Code: http.StatusNotFound,
|
||||||
|
JSON: jsonerror.NotFound(fmt.Sprintf("Room ID %q has no remaining users on this server", roomID)),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Try building an event for the server
|
// Try building an event for the server
|
||||||
builder := gomatrixserverlib.EventBuilder{
|
builder := gomatrixserverlib.EventBuilder{
|
||||||
Sender: userID,
|
Sender: userID,
|
||||||
|
@ -199,6 +199,15 @@ func (t *testRoomserverAPI) QueryMembershipsForRoom(
|
|||||||
return fmt.Errorf("not implemented")
|
return fmt.Errorf("not implemented")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Query if a server is joined to a room
|
||||||
|
func (t *testRoomserverAPI) QueryServerJoinedToRoom(
|
||||||
|
ctx context.Context,
|
||||||
|
request *api.QueryServerJoinedToRoomRequest,
|
||||||
|
response *api.QueryServerJoinedToRoomResponse,
|
||||||
|
) error {
|
||||||
|
return fmt.Errorf("not implemented")
|
||||||
|
}
|
||||||
|
|
||||||
// Query whether a server is allowed to see an event
|
// Query whether a server is allowed to see an event
|
||||||
func (t *testRoomserverAPI) QueryServerAllowedToSeeEvent(
|
func (t *testRoomserverAPI) QueryServerAllowedToSeeEvent(
|
||||||
ctx context.Context,
|
ctx context.Context,
|
||||||
|
@ -89,6 +89,13 @@ type RoomserverInternalAPI interface {
|
|||||||
response *QueryMembershipsForRoomResponse,
|
response *QueryMembershipsForRoomResponse,
|
||||||
) error
|
) error
|
||||||
|
|
||||||
|
// Query if we think we're still in a room.
|
||||||
|
QueryServerJoinedToRoom(
|
||||||
|
ctx context.Context,
|
||||||
|
request *QueryServerJoinedToRoomRequest,
|
||||||
|
response *QueryServerJoinedToRoomResponse,
|
||||||
|
) error
|
||||||
|
|
||||||
// Query whether a server is allowed to see an event
|
// Query whether a server is allowed to see an event
|
||||||
QueryServerAllowedToSeeEvent(
|
QueryServerAllowedToSeeEvent(
|
||||||
ctx context.Context,
|
ctx context.Context,
|
||||||
|
@ -134,6 +134,16 @@ func (t *RoomserverInternalAPITrace) QueryMembershipsForRoom(
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (t *RoomserverInternalAPITrace) QueryServerJoinedToRoom(
|
||||||
|
ctx context.Context,
|
||||||
|
req *QueryServerJoinedToRoomRequest,
|
||||||
|
res *QueryServerJoinedToRoomResponse,
|
||||||
|
) error {
|
||||||
|
err := t.Impl.QueryServerJoinedToRoom(ctx, req, res)
|
||||||
|
util.GetLogger(ctx).WithError(err).Infof("QueryServerJoinedToRoom req=%+v res=%+v", js(req), js(res))
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
func (t *RoomserverInternalAPITrace) QueryServerAllowedToSeeEvent(
|
func (t *RoomserverInternalAPITrace) QueryServerAllowedToSeeEvent(
|
||||||
ctx context.Context,
|
ctx context.Context,
|
||||||
req *QueryServerAllowedToSeeEventRequest,
|
req *QueryServerAllowedToSeeEventRequest,
|
||||||
|
@ -140,6 +140,22 @@ type QueryMembershipsForRoomResponse struct {
|
|||||||
HasBeenInRoom bool `json:"has_been_in_room"`
|
HasBeenInRoom bool `json:"has_been_in_room"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// QueryServerJoinedToRoomRequest is a request to QueryServerJoinedToRoom
|
||||||
|
type QueryServerJoinedToRoomRequest struct {
|
||||||
|
// Server name of the server to find
|
||||||
|
ServerName gomatrixserverlib.ServerName `json:"server_name"`
|
||||||
|
// ID of the room to see if we are still joined to
|
||||||
|
RoomID string `json:"room_id"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// QueryMembershipsForRoomResponse is a response to QueryServerJoinedToRoom
|
||||||
|
type QueryServerJoinedToRoomResponse struct {
|
||||||
|
// True if the room exists on the server
|
||||||
|
RoomExists bool `json:"room_exists"`
|
||||||
|
// True if we still believe that we are participating in the room
|
||||||
|
IsInRoom bool `json:"is_in_room"`
|
||||||
|
}
|
||||||
|
|
||||||
// QueryServerAllowedToSeeEventRequest is a request to QueryServerAllowedToSeeEvent
|
// QueryServerAllowedToSeeEventRequest is a request to QueryServerAllowedToSeeEvent
|
||||||
type QueryServerAllowedToSeeEventRequest struct {
|
type QueryServerAllowedToSeeEventRequest struct {
|
||||||
// The event ID to look up invites in.
|
// The event ID to look up invites in.
|
||||||
|
@ -227,6 +227,50 @@ func (r *Queryer) QueryMembershipsForRoom(
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// QueryServerJoinedToRoom implements api.RoomserverInternalAPI
|
||||||
|
func (r *Queryer) QueryServerJoinedToRoom(
|
||||||
|
ctx context.Context,
|
||||||
|
request *api.QueryServerJoinedToRoomRequest,
|
||||||
|
response *api.QueryServerJoinedToRoomResponse,
|
||||||
|
) error {
|
||||||
|
info, err := r.DB.RoomInfo(ctx, request.RoomID)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("r.DB.RoomInfo: %w", err)
|
||||||
|
}
|
||||||
|
if info == nil || info.IsStub {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
response.RoomExists = true
|
||||||
|
|
||||||
|
eventNIDs, err := r.DB.GetMembershipEventNIDsForRoom(ctx, info.RoomNID, true, false)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("r.DB.GetMembershipEventNIDsForRoom: %w", err)
|
||||||
|
}
|
||||||
|
if len(eventNIDs) == 0 {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
events, err := r.DB.Events(ctx, eventNIDs)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("r.DB.Events: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, e := range events {
|
||||||
|
if e.Type() == gomatrixserverlib.MRoomMember && e.StateKey() != nil {
|
||||||
|
_, serverName, err := gomatrixserverlib.SplitID('@', *e.StateKey())
|
||||||
|
if err != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if serverName == request.ServerName {
|
||||||
|
response.IsInRoom = true
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
// QueryServerAllowedToSeeEvent implements api.RoomserverInternalAPI
|
// QueryServerAllowedToSeeEvent implements api.RoomserverInternalAPI
|
||||||
func (r *Queryer) QueryServerAllowedToSeeEvent(
|
func (r *Queryer) QueryServerAllowedToSeeEvent(
|
||||||
ctx context.Context,
|
ctx context.Context,
|
||||||
|
@ -38,6 +38,7 @@ const (
|
|||||||
RoomserverQueryEventsByIDPath = "/roomserver/queryEventsByID"
|
RoomserverQueryEventsByIDPath = "/roomserver/queryEventsByID"
|
||||||
RoomserverQueryMembershipForUserPath = "/roomserver/queryMembershipForUser"
|
RoomserverQueryMembershipForUserPath = "/roomserver/queryMembershipForUser"
|
||||||
RoomserverQueryMembershipsForRoomPath = "/roomserver/queryMembershipsForRoom"
|
RoomserverQueryMembershipsForRoomPath = "/roomserver/queryMembershipsForRoom"
|
||||||
|
RoomserverQueryServerJoinedToRoomPath = "/roomserver/queryServerJoinedToRoomPath"
|
||||||
RoomserverQueryServerAllowedToSeeEventPath = "/roomserver/queryServerAllowedToSeeEvent"
|
RoomserverQueryServerAllowedToSeeEventPath = "/roomserver/queryServerAllowedToSeeEvent"
|
||||||
RoomserverQueryMissingEventsPath = "/roomserver/queryMissingEvents"
|
RoomserverQueryMissingEventsPath = "/roomserver/queryMissingEvents"
|
||||||
RoomserverQueryStateAndAuthChainPath = "/roomserver/queryStateAndAuthChain"
|
RoomserverQueryStateAndAuthChainPath = "/roomserver/queryStateAndAuthChain"
|
||||||
@ -312,6 +313,19 @@ func (h *httpRoomserverInternalAPI) QueryMembershipsForRoom(
|
|||||||
return httputil.PostJSON(ctx, span, h.httpClient, apiURL, request, response)
|
return httputil.PostJSON(ctx, span, h.httpClient, apiURL, request, response)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// QueryMembershipsForRoom implements RoomserverQueryAPI
|
||||||
|
func (h *httpRoomserverInternalAPI) QueryServerJoinedToRoom(
|
||||||
|
ctx context.Context,
|
||||||
|
request *api.QueryServerJoinedToRoomRequest,
|
||||||
|
response *api.QueryServerJoinedToRoomResponse,
|
||||||
|
) error {
|
||||||
|
span, ctx := opentracing.StartSpanFromContext(ctx, "QueryServerJoinedToRoom")
|
||||||
|
defer span.Finish()
|
||||||
|
|
||||||
|
apiURL := h.roomserverURL + RoomserverQueryServerJoinedToRoomPath
|
||||||
|
return httputil.PostJSON(ctx, span, h.httpClient, apiURL, request, response)
|
||||||
|
}
|
||||||
|
|
||||||
// QueryServerAllowedToSeeEvent implements RoomserverQueryAPI
|
// QueryServerAllowedToSeeEvent implements RoomserverQueryAPI
|
||||||
func (h *httpRoomserverInternalAPI) QueryServerAllowedToSeeEvent(
|
func (h *httpRoomserverInternalAPI) QueryServerAllowedToSeeEvent(
|
||||||
ctx context.Context,
|
ctx context.Context,
|
||||||
|
@ -167,6 +167,20 @@ func AddRoutes(r api.RoomserverInternalAPI, internalAPIMux *mux.Router) {
|
|||||||
return util.JSONResponse{Code: http.StatusOK, JSON: &response}
|
return util.JSONResponse{Code: http.StatusOK, JSON: &response}
|
||||||
}),
|
}),
|
||||||
)
|
)
|
||||||
|
internalAPIMux.Handle(
|
||||||
|
RoomserverQueryServerJoinedToRoomPath,
|
||||||
|
httputil.MakeInternalAPI("queryServerJoinedToRoom", func(req *http.Request) util.JSONResponse {
|
||||||
|
var request api.QueryServerJoinedToRoomRequest
|
||||||
|
var response api.QueryServerJoinedToRoomResponse
|
||||||
|
if err := json.NewDecoder(req.Body).Decode(&request); err != nil {
|
||||||
|
return util.ErrorResponse(err)
|
||||||
|
}
|
||||||
|
if err := r.QueryServerJoinedToRoom(req.Context(), &request, &response); err != nil {
|
||||||
|
return util.ErrorResponse(err)
|
||||||
|
}
|
||||||
|
return util.JSONResponse{Code: http.StatusOK, JSON: &response}
|
||||||
|
}),
|
||||||
|
)
|
||||||
internalAPIMux.Handle(
|
internalAPIMux.Handle(
|
||||||
RoomserverQueryServerAllowedToSeeEventPath,
|
RoomserverQueryServerAllowedToSeeEventPath,
|
||||||
httputil.MakeInternalAPI("queryServerAllowedToSeeEvent", func(req *http.Request) util.JSONResponse {
|
httputil.MakeInternalAPI("queryServerAllowedToSeeEvent", func(req *http.Request) util.JSONResponse {
|
||||||
|
@ -477,3 +477,4 @@ Inbound federation correctly soft fails events
|
|||||||
Inbound federation accepts a second soft-failed event
|
Inbound federation accepts a second soft-failed event
|
||||||
Federation key API can act as a notary server via a POST request
|
Federation key API can act as a notary server via a POST request
|
||||||
Federation key API can act as a notary server via a GET request
|
Federation key API can act as a notary server via a GET request
|
||||||
|
Inbound /make_join rejects attempts to join rooms where all users have left
|
||||||
|
Loading…
Reference in New Issue
Block a user