mirror of
https://github.com/matrix-org/dendrite.git
synced 2026-01-16 10:33:11 -06:00
Remove PerformError from peeking and joining endpoints
This commit is contained in:
parent
e3f1456517
commit
4b7875fb27
|
|
@ -15,14 +15,18 @@
|
|||
package routing
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"net/http"
|
||||
"time"
|
||||
|
||||
appserviceAPI "github.com/matrix-org/dendrite/appservice/api"
|
||||
"github.com/matrix-org/dendrite/clientapi/httputil"
|
||||
"github.com/matrix-org/dendrite/clientapi/jsonerror"
|
||||
"github.com/matrix-org/dendrite/internal/eventutil"
|
||||
roomserverAPI "github.com/matrix-org/dendrite/roomserver/api"
|
||||
"github.com/matrix-org/dendrite/userapi/api"
|
||||
"github.com/matrix-org/gomatrix"
|
||||
"github.com/matrix-org/gomatrixserverlib/spec"
|
||||
"github.com/matrix-org/util"
|
||||
)
|
||||
|
|
@ -41,7 +45,6 @@ func JoinRoomByIDOrAlias(
|
|||
IsGuest: device.AccountType == api.AccountTypeGuest,
|
||||
Content: map[string]interface{}{},
|
||||
}
|
||||
joinRes := roomserverAPI.PerformJoinResponse{}
|
||||
|
||||
// Check to see if any ?server_name= query parameters were
|
||||
// given in the request.
|
||||
|
|
@ -81,37 +84,66 @@ func JoinRoomByIDOrAlias(
|
|||
done := make(chan util.JSONResponse, 1)
|
||||
go func() {
|
||||
defer close(done)
|
||||
if err := rsAPI.PerformJoin(req.Context(), &joinReq, &joinRes); err != nil {
|
||||
done <- jsonerror.InternalAPIError(req.Context(), err)
|
||||
} else if joinRes.Error != nil {
|
||||
if joinRes.Error.Code == roomserverAPI.PerformErrorNotAllowed && device.AccountType == api.AccountTypeGuest {
|
||||
done <- util.JSONResponse{
|
||||
Code: http.StatusForbidden,
|
||||
JSON: jsonerror.GuestAccessForbidden(joinRes.Error.Msg),
|
||||
}
|
||||
} else {
|
||||
done <- joinRes.Error.JSONResponse()
|
||||
}
|
||||
} else {
|
||||
done <- util.JSONResponse{
|
||||
roomID, _, err := rsAPI.PerformJoin(req.Context(), &joinReq)
|
||||
var response util.JSONResponse
|
||||
|
||||
switch e := err.(type) {
|
||||
case nil: // success case
|
||||
response = util.JSONResponse{
|
||||
Code: http.StatusOK,
|
||||
// TODO: Put the response struct somewhere internal.
|
||||
JSON: struct {
|
||||
RoomID string `json:"room_id"`
|
||||
}{joinRes.RoomID},
|
||||
}{roomID},
|
||||
}
|
||||
case roomserverAPI.ErrInvalidID:
|
||||
response = util.JSONResponse{
|
||||
Code: http.StatusBadRequest,
|
||||
JSON: jsonerror.Unknown(e.Error()),
|
||||
}
|
||||
case roomserverAPI.ErrNotAllowed:
|
||||
jsonErr := jsonerror.Forbidden(e.Error())
|
||||
if device.AccountType == api.AccountTypeGuest {
|
||||
jsonErr = jsonerror.GuestAccessForbidden(e.Error())
|
||||
}
|
||||
response = util.JSONResponse{
|
||||
Code: http.StatusForbidden,
|
||||
JSON: jsonErr,
|
||||
}
|
||||
case *gomatrix.HTTPError: // this ensures we proxy responses over federation to the client
|
||||
response = util.JSONResponse{
|
||||
Code: e.Code,
|
||||
JSON: json.RawMessage(e.Message),
|
||||
}
|
||||
default:
|
||||
response = util.JSONResponse{
|
||||
Code: http.StatusInternalServerError,
|
||||
JSON: jsonerror.InternalServerError(),
|
||||
}
|
||||
if errors.Is(err, eventutil.ErrRoomNoExists) {
|
||||
response = util.JSONResponse{
|
||||
Code: http.StatusNotFound,
|
||||
JSON: jsonerror.NotFound(e.Error()),
|
||||
}
|
||||
}
|
||||
}
|
||||
done <- response
|
||||
}()
|
||||
|
||||
// Wait either for the join to finish, or for us to hit a reasonable
|
||||
// timeout, at which point we'll just return a 200 to placate clients.
|
||||
timer := time.NewTimer(time.Second * 20)
|
||||
select {
|
||||
case <-time.After(time.Second * 20):
|
||||
case <-timer.C:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusAccepted,
|
||||
JSON: jsonerror.Unknown("The room join will continue in the background."),
|
||||
}
|
||||
case result := <-done:
|
||||
// Stop and drain the timer
|
||||
if !timer.Stop() {
|
||||
<-timer.C
|
||||
}
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,13 +15,16 @@
|
|||
package routing
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"net/http"
|
||||
|
||||
"github.com/matrix-org/dendrite/clientapi/jsonerror"
|
||||
roomserverAPI "github.com/matrix-org/dendrite/roomserver/api"
|
||||
"github.com/matrix-org/dendrite/userapi/api"
|
||||
"github.com/matrix-org/gomatrix"
|
||||
"github.com/matrix-org/gomatrixserverlib/spec"
|
||||
"github.com/matrix-org/util"
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
func PeekRoomByIDOrAlias(
|
||||
|
|
@ -41,8 +44,6 @@ func PeekRoomByIDOrAlias(
|
|||
UserID: device.UserID,
|
||||
DeviceID: device.ID,
|
||||
}
|
||||
peekRes := roomserverAPI.PerformPeekResponse{}
|
||||
|
||||
// Check to see if any ?server_name= query parameters were
|
||||
// given in the request.
|
||||
if serverNames, ok := req.URL.Query()["server_name"]; ok {
|
||||
|
|
@ -55,11 +56,27 @@ func PeekRoomByIDOrAlias(
|
|||
}
|
||||
|
||||
// Ask the roomserver to perform the peek.
|
||||
if err := rsAPI.PerformPeek(req.Context(), &peekReq, &peekRes); err != nil {
|
||||
return util.ErrorResponse(err)
|
||||
}
|
||||
if peekRes.Error != nil {
|
||||
return peekRes.Error.JSONResponse()
|
||||
roomID, err := rsAPI.PerformPeek(req.Context(), &peekReq)
|
||||
switch e := err.(type) {
|
||||
case roomserverAPI.ErrInvalidID:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusBadRequest,
|
||||
JSON: jsonerror.Unknown(e.Error()),
|
||||
}
|
||||
case roomserverAPI.ErrNotAllowed:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusForbidden,
|
||||
JSON: jsonerror.Forbidden(e.Error()),
|
||||
}
|
||||
case *gomatrix.HTTPError:
|
||||
return util.JSONResponse{
|
||||
Code: e.Code,
|
||||
JSON: json.RawMessage(e.Message),
|
||||
}
|
||||
case nil:
|
||||
default:
|
||||
logrus.WithError(err).WithField("roomID", roomIDOrAlias).Errorf("Failed to peek room")
|
||||
return jsonerror.InternalServerError()
|
||||
}
|
||||
|
||||
// if this user is already joined to the room, we let them peek anyway
|
||||
|
|
@ -75,7 +92,7 @@ func PeekRoomByIDOrAlias(
|
|||
// TODO: Put the response struct somewhere internal.
|
||||
JSON: struct {
|
||||
RoomID string `json:"room_id"`
|
||||
}{peekRes.RoomID},
|
||||
}{roomID},
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -85,18 +102,17 @@ func UnpeekRoomByID(
|
|||
rsAPI roomserverAPI.ClientRoomserverAPI,
|
||||
roomID string,
|
||||
) util.JSONResponse {
|
||||
unpeekReq := roomserverAPI.PerformUnpeekRequest{
|
||||
RoomID: roomID,
|
||||
UserID: device.UserID,
|
||||
DeviceID: device.ID,
|
||||
}
|
||||
unpeekRes := roomserverAPI.PerformUnpeekResponse{}
|
||||
|
||||
if err := rsAPI.PerformUnpeek(req.Context(), &unpeekReq, &unpeekRes); err != nil {
|
||||
return jsonerror.InternalAPIError(req.Context(), err)
|
||||
}
|
||||
if unpeekRes.Error != nil {
|
||||
return unpeekRes.Error.JSONResponse()
|
||||
err := rsAPI.PerformUnpeek(req.Context(), roomID, device.UserID, device.ID)
|
||||
switch e := err.(type) {
|
||||
case roomserverAPI.ErrInvalidID:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusBadRequest,
|
||||
JSON: jsonerror.Unknown(e.Error()),
|
||||
}
|
||||
case nil:
|
||||
default:
|
||||
logrus.WithError(err).WithField("roomID", roomID).Errorf("Failed to un-peek room")
|
||||
return jsonerror.InternalServerError()
|
||||
}
|
||||
|
||||
return util.JSONResponse{
|
||||
|
|
|
|||
|
|
@ -174,10 +174,10 @@ type ClientRoomserverAPI interface {
|
|||
PerformAdminEvacuateUser(ctx context.Context, userID string) (affected []string, err error)
|
||||
PerformAdminPurgeRoom(ctx context.Context, roomID string) error
|
||||
PerformAdminDownloadState(ctx context.Context, roomID, userID string, serverName spec.ServerName) error
|
||||
PerformPeek(ctx context.Context, req *PerformPeekRequest, res *PerformPeekResponse) error
|
||||
PerformUnpeek(ctx context.Context, req *PerformUnpeekRequest, res *PerformUnpeekResponse) error
|
||||
PerformPeek(ctx context.Context, req *PerformPeekRequest) (roomID string, err error)
|
||||
PerformUnpeek(ctx context.Context, roomID, userID, deviceID string) error
|
||||
PerformInvite(ctx context.Context, req *PerformInviteRequest) error
|
||||
PerformJoin(ctx context.Context, req *PerformJoinRequest, res *PerformJoinResponse) error
|
||||
PerformJoin(ctx context.Context, req *PerformJoinRequest) (roomID string, joinedVia spec.ServerName, err error)
|
||||
PerformLeave(ctx context.Context, req *PerformLeaveRequest, res *PerformLeaveResponse) error
|
||||
PerformPublish(ctx context.Context, req *PerformPublishRequest, res *PerformPublishResponse) error
|
||||
// PerformForget forgets a rooms history for a specific user
|
||||
|
|
@ -192,7 +192,7 @@ type UserRoomserverAPI interface {
|
|||
QueryCurrentState(ctx context.Context, req *QueryCurrentStateRequest, res *QueryCurrentStateResponse) error
|
||||
QueryMembershipsForRoom(ctx context.Context, req *QueryMembershipsForRoomRequest, res *QueryMembershipsForRoomResponse) error
|
||||
PerformAdminEvacuateUser(ctx context.Context, userID string) (affected []string, err error)
|
||||
PerformJoin(ctx context.Context, req *PerformJoinRequest, res *PerformJoinResponse) error
|
||||
PerformJoin(ctx context.Context, req *PerformJoinRequest) (roomID string, joinedVia spec.ServerName, err error)
|
||||
}
|
||||
|
||||
type FederationRoomserverAPI interface {
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
package api
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/http"
|
||||
|
||||
|
|
@ -28,11 +27,6 @@ func (p *PerformError) Error() string {
|
|||
// JSONResponse maps error codes to suitable HTTP error codes, defaulting to 500.
|
||||
func (p *PerformError) JSONResponse() util.JSONResponse {
|
||||
switch p.Code {
|
||||
case PerformErrorBadRequest:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusBadRequest,
|
||||
JSON: jsonerror.Unknown(p.Msg),
|
||||
}
|
||||
case PerformErrorNoRoom:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusNotFound,
|
||||
|
|
@ -43,22 +37,6 @@ func (p *PerformError) JSONResponse() util.JSONResponse {
|
|||
Code: http.StatusForbidden,
|
||||
JSON: jsonerror.Forbidden(p.Msg),
|
||||
}
|
||||
case PerformErrorNoOperation:
|
||||
return util.JSONResponse{
|
||||
Code: http.StatusForbidden,
|
||||
JSON: jsonerror.Forbidden(p.Msg),
|
||||
}
|
||||
case PerformErrRemote:
|
||||
// if the code is 0 then something bad happened and it isn't
|
||||
// a remote HTTP error being encapsulated, e.g network error to remote.
|
||||
if p.RemoteCode == 0 {
|
||||
return util.ErrorResponse(fmt.Errorf("%s", p.Msg))
|
||||
}
|
||||
return util.JSONResponse{
|
||||
Code: p.RemoteCode,
|
||||
// TODO: Should we assert this is in fact JSON? E.g gjson parse?
|
||||
JSON: json.RawMessage(p.Msg),
|
||||
}
|
||||
default:
|
||||
return util.ErrorResponse(p)
|
||||
}
|
||||
|
|
@ -67,14 +45,8 @@ func (p *PerformError) JSONResponse() util.JSONResponse {
|
|||
const (
|
||||
// PerformErrorNotAllowed means the user is not allowed to invite/join/etc this room (e.g join_rule:invite or banned)
|
||||
PerformErrorNotAllowed PerformErrorCode = 1
|
||||
// PerformErrorBadRequest means the request was wrong in some way (invalid user ID, wrong server, etc)
|
||||
PerformErrorBadRequest PerformErrorCode = 2
|
||||
// PerformErrorNoRoom means that the room being joined doesn't exist.
|
||||
PerformErrorNoRoom PerformErrorCode = 3
|
||||
// PerformErrorNoOperation means that the request resulted in nothing happening e.g invite->invite or leave->leave.
|
||||
PerformErrorNoOperation PerformErrorCode = 4
|
||||
// PerformErrRemote means that the request failed and the PerformError.Msg is the raw remote JSON error response
|
||||
PerformErrRemote PerformErrorCode = 5
|
||||
)
|
||||
|
||||
type PerformJoinRequest struct {
|
||||
|
|
@ -86,14 +58,6 @@ type PerformJoinRequest struct {
|
|||
Unsigned map[string]interface{} `json:"unsigned"`
|
||||
}
|
||||
|
||||
type PerformJoinResponse struct {
|
||||
// The room ID, populated on success.
|
||||
RoomID string `json:"room_id"`
|
||||
JoinedVia spec.ServerName
|
||||
// If non-nil, the join request failed. Contains more information why it failed.
|
||||
Error *PerformError
|
||||
}
|
||||
|
||||
type PerformLeaveRequest struct {
|
||||
RoomID string `json:"room_id"`
|
||||
UserID string `json:"user_id"`
|
||||
|
|
@ -119,24 +83,6 @@ type PerformPeekRequest struct {
|
|||
ServerNames []spec.ServerName `json:"server_names"`
|
||||
}
|
||||
|
||||
type PerformPeekResponse struct {
|
||||
// The room ID, populated on success.
|
||||
RoomID string `json:"room_id"`
|
||||
// If non-nil, the join request failed. Contains more information why it failed.
|
||||
Error *PerformError
|
||||
}
|
||||
|
||||
type PerformUnpeekRequest struct {
|
||||
RoomID string `json:"room_id"`
|
||||
UserID string `json:"user_id"`
|
||||
DeviceID string `json:"device_id"`
|
||||
}
|
||||
|
||||
type PerformUnpeekResponse struct {
|
||||
// If non-nil, the join request failed. Contains more information why it failed.
|
||||
Error *PerformError
|
||||
}
|
||||
|
||||
// PerformBackfillRequest is a request to PerformBackfill.
|
||||
type PerformBackfillRequest struct {
|
||||
// The room to backfill
|
||||
|
|
|
|||
|
|
@ -53,32 +53,22 @@ type Joiner struct {
|
|||
func (r *Joiner) PerformJoin(
|
||||
ctx context.Context,
|
||||
req *rsAPI.PerformJoinRequest,
|
||||
res *rsAPI.PerformJoinResponse,
|
||||
) error {
|
||||
) (roomID string, joinedVia spec.ServerName, err error) {
|
||||
logger := logrus.WithContext(ctx).WithFields(logrus.Fields{
|
||||
"room_id": req.RoomIDOrAlias,
|
||||
"user_id": req.UserID,
|
||||
"servers": req.ServerNames,
|
||||
})
|
||||
logger.Info("User requested to room join")
|
||||
roomID, joinedVia, err := r.performJoin(context.Background(), req)
|
||||
roomID, joinedVia, err = r.performJoin(context.Background(), req)
|
||||
if err != nil {
|
||||
logger.WithError(err).Error("Failed to join room")
|
||||
sentry.CaptureException(err)
|
||||
perr, ok := err.(*rsAPI.PerformError)
|
||||
if ok {
|
||||
res.Error = perr
|
||||
} else {
|
||||
res.Error = &rsAPI.PerformError{
|
||||
Msg: err.Error(),
|
||||
}
|
||||
}
|
||||
return nil
|
||||
return "", "", err
|
||||
}
|
||||
logger.Info("User joined room successfully")
|
||||
res.RoomID = roomID
|
||||
res.JoinedVia = joinedVia
|
||||
return nil
|
||||
|
||||
return roomID, joinedVia, nil
|
||||
}
|
||||
|
||||
func (r *Joiner) performJoin(
|
||||
|
|
@ -87,16 +77,10 @@ func (r *Joiner) performJoin(
|
|||
) (string, spec.ServerName, error) {
|
||||
_, domain, err := gomatrixserverlib.SplitID('@', req.UserID)
|
||||
if err != nil {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Supplied user ID %q in incorrect format", req.UserID),
|
||||
}
|
||||
return "", "", rsAPI.ErrInvalidID{Err: fmt.Errorf("supplied user ID %q in incorrect format", req.UserID)}
|
||||
}
|
||||
if !r.Cfg.Matrix.IsLocalServerName(domain) {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("User %q does not belong to this homeserver", req.UserID),
|
||||
}
|
||||
return "", "", rsAPI.ErrInvalidID{Err: fmt.Errorf("user %q does not belong to this homeserver", req.UserID)}
|
||||
}
|
||||
if strings.HasPrefix(req.RoomIDOrAlias, "!") {
|
||||
return r.performJoinRoomByID(ctx, req)
|
||||
|
|
@ -104,10 +88,7 @@ func (r *Joiner) performJoin(
|
|||
if strings.HasPrefix(req.RoomIDOrAlias, "#") {
|
||||
return r.performJoinRoomByAlias(ctx, req)
|
||||
}
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID or alias %q is invalid", req.RoomIDOrAlias),
|
||||
}
|
||||
return "", "", rsAPI.ErrInvalidID{Err: fmt.Errorf("room ID or alias %q is invalid", req.RoomIDOrAlias)}
|
||||
}
|
||||
|
||||
func (r *Joiner) performJoinRoomByAlias(
|
||||
|
|
@ -182,10 +163,7 @@ func (r *Joiner) performJoinRoomByID(
|
|||
// Get the domain part of the room ID.
|
||||
_, domain, err := gomatrixserverlib.SplitID('!', req.RoomIDOrAlias)
|
||||
if err != nil {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID %q is invalid: %s", req.RoomIDOrAlias, err),
|
||||
}
|
||||
return "", "", rsAPI.ErrInvalidID{Err: fmt.Errorf("room ID %q is invalid: %w", req.RoomIDOrAlias, err)}
|
||||
}
|
||||
|
||||
// If the server name in the room ID isn't ours then it's a
|
||||
|
|
@ -199,10 +177,7 @@ func (r *Joiner) performJoinRoomByID(
|
|||
userID := req.UserID
|
||||
_, userDomain, err := r.Cfg.Matrix.SplitLocalID('@', userID)
|
||||
if err != nil {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("User ID %q is invalid: %s", userID, err),
|
||||
}
|
||||
return "", "", rsAPI.ErrInvalidID{Err: fmt.Errorf("user ID %q is invalid: %w", userID, err)}
|
||||
}
|
||||
eb := gomatrixserverlib.EventBuilder{
|
||||
Type: spec.MRoomMember,
|
||||
|
|
@ -286,10 +261,7 @@ func (r *Joiner) performJoinRoomByID(
|
|||
// Servers MUST only allow guest users to join rooms if the m.room.guest_access state event
|
||||
// is present on the room and has the guest_access value can_join.
|
||||
if guestAccess != "can_join" {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorNotAllowed,
|
||||
Msg: "Guest access is forbidden",
|
||||
}
|
||||
return "", "", rsAPI.ErrNotAllowed{Err: fmt.Errorf("guest access is forbidden")}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -341,16 +313,10 @@ func (r *Joiner) performJoinRoomByID(
|
|||
}
|
||||
inputRes := rsAPI.InputRoomEventsResponse{}
|
||||
if err = r.Inputer.InputRoomEvents(ctx, &inputReq, &inputRes); err != nil {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorNoOperation,
|
||||
Msg: fmt.Sprintf("InputRoomEvents failed: %s", err),
|
||||
}
|
||||
return "", "", rsAPI.ErrNotAllowed{Err: err}
|
||||
}
|
||||
if err = inputRes.Err(); err != nil {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorNotAllowed,
|
||||
Msg: fmt.Sprintf("InputRoomEvents auth failed: %s", err),
|
||||
}
|
||||
return "", "", rsAPI.ErrNotAllowed{Err: err}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -363,10 +329,7 @@ func (r *Joiner) performJoinRoomByID(
|
|||
// Otherwise we'll try a federated join as normal, since it's quite
|
||||
// possible that the room still exists on other servers.
|
||||
if len(req.ServerNames) == 0 {
|
||||
return "", "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorNoRoom,
|
||||
Msg: fmt.Sprintf("room ID %q does not exist", req.RoomIDOrAlias),
|
||||
}
|
||||
return "", "", eventutil.ErrRoomNoExists
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -401,11 +364,7 @@ func (r *Joiner) performFederatedJoinRoomByID(
|
|||
fedRes := fsAPI.PerformJoinResponse{}
|
||||
r.FSAPI.PerformJoin(ctx, &fedReq, &fedRes)
|
||||
if fedRes.LastError != nil {
|
||||
return "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrRemote,
|
||||
Msg: fedRes.LastError.Message,
|
||||
RemoteCode: fedRes.LastError.Code,
|
||||
}
|
||||
return "", fedRes.LastError
|
||||
}
|
||||
return fedRes.JoinedVia, nil
|
||||
}
|
||||
|
|
@ -429,10 +388,7 @@ func (r *Joiner) populateAuthorisedViaUserForRestrictedJoin(
|
|||
return "", nil
|
||||
}
|
||||
if !res.Allowed {
|
||||
return "", &rsAPI.PerformError{
|
||||
Code: rsAPI.PerformErrorNotAllowed,
|
||||
Msg: fmt.Sprintf("The join to room %s was not allowed.", joinReq.RoomIDOrAlias),
|
||||
}
|
||||
return "", rsAPI.ErrNotAllowed{Err: fmt.Errorf("the join to room %s was not allowed", joinReq.RoomIDOrAlias)}
|
||||
}
|
||||
return res.AuthorisedVia, nil
|
||||
}
|
||||
|
|
|
|||
|
|
@ -44,21 +44,8 @@ type Peeker struct {
|
|||
func (r *Peeker) PerformPeek(
|
||||
ctx context.Context,
|
||||
req *api.PerformPeekRequest,
|
||||
res *api.PerformPeekResponse,
|
||||
) error {
|
||||
roomID, err := r.performPeek(ctx, req)
|
||||
if err != nil {
|
||||
perr, ok := err.(*api.PerformError)
|
||||
if ok {
|
||||
res.Error = perr
|
||||
} else {
|
||||
res.Error = &api.PerformError{
|
||||
Msg: err.Error(),
|
||||
}
|
||||
}
|
||||
}
|
||||
res.RoomID = roomID
|
||||
return nil
|
||||
) (roomID string, err error) {
|
||||
return r.performPeek(ctx, req)
|
||||
}
|
||||
|
||||
func (r *Peeker) performPeek(
|
||||
|
|
@ -68,16 +55,10 @@ func (r *Peeker) performPeek(
|
|||
// FIXME: there's way too much duplication with performJoin
|
||||
_, domain, err := gomatrixserverlib.SplitID('@', req.UserID)
|
||||
if err != nil {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Supplied user ID %q in incorrect format", req.UserID),
|
||||
}
|
||||
return "", api.ErrInvalidID{Err: fmt.Errorf("supplied user ID %q in incorrect format", req.UserID)}
|
||||
}
|
||||
if !r.Cfg.Matrix.IsLocalServerName(domain) {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("User %q does not belong to this homeserver", req.UserID),
|
||||
}
|
||||
return "", api.ErrInvalidID{Err: fmt.Errorf("user %q does not belong to this homeserver", req.UserID)}
|
||||
}
|
||||
if strings.HasPrefix(req.RoomIDOrAlias, "!") {
|
||||
return r.performPeekRoomByID(ctx, req)
|
||||
|
|
@ -85,10 +66,7 @@ func (r *Peeker) performPeek(
|
|||
if strings.HasPrefix(req.RoomIDOrAlias, "#") {
|
||||
return r.performPeekRoomByAlias(ctx, req)
|
||||
}
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID or alias %q is invalid", req.RoomIDOrAlias),
|
||||
}
|
||||
return "", api.ErrInvalidID{Err: fmt.Errorf("room ID or alias %q is invalid", req.RoomIDOrAlias)}
|
||||
}
|
||||
|
||||
func (r *Peeker) performPeekRoomByAlias(
|
||||
|
|
@ -98,7 +76,7 @@ func (r *Peeker) performPeekRoomByAlias(
|
|||
// Get the domain part of the room alias.
|
||||
_, domain, err := gomatrixserverlib.SplitID('#', req.RoomIDOrAlias)
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("alias %q is not in the correct format", req.RoomIDOrAlias)
|
||||
return "", api.ErrInvalidID{Err: fmt.Errorf("alias %q is not in the correct format", req.RoomIDOrAlias)}
|
||||
}
|
||||
req.ServerNames = append(req.ServerNames, domain)
|
||||
|
||||
|
|
@ -147,10 +125,7 @@ func (r *Peeker) performPeekRoomByID(
|
|||
// Get the domain part of the room ID.
|
||||
_, domain, err := gomatrixserverlib.SplitID('!', roomID)
|
||||
if err != nil {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID %q is invalid: %s", roomID, err),
|
||||
}
|
||||
return "", api.ErrInvalidID{Err: fmt.Errorf("room ID %q is invalid: %w", roomID, err)}
|
||||
}
|
||||
|
||||
// handle federated peeks
|
||||
|
|
@ -169,11 +144,7 @@ func (r *Peeker) performPeekRoomByID(
|
|||
fedRes := fsAPI.PerformOutboundPeekResponse{}
|
||||
_ = r.FSAPI.PerformOutboundPeek(ctx, &fedReq, &fedRes)
|
||||
if fedRes.LastError != nil {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrRemote,
|
||||
Msg: fedRes.LastError.Message,
|
||||
RemoteCode: fedRes.LastError.Code,
|
||||
}
|
||||
return "", fedRes.LastError
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -194,17 +165,11 @@ func (r *Peeker) performPeekRoomByID(
|
|||
}
|
||||
|
||||
if !worldReadable {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorNotAllowed,
|
||||
Msg: "Room is not world-readable",
|
||||
}
|
||||
return "", api.ErrNotAllowed{Err: fmt.Errorf("room is not world-readable")}
|
||||
}
|
||||
|
||||
if ev, _ := r.DB.GetStateEvent(ctx, roomID, "m.room.encryption", ""); ev != nil {
|
||||
return "", &api.PerformError{
|
||||
Code: api.PerformErrorNotAllowed,
|
||||
Msg: "Cannot peek into an encrypted room",
|
||||
}
|
||||
return "", api.ErrNotAllowed{Err: fmt.Errorf("Cannot peek into an encrypted room")}
|
||||
}
|
||||
|
||||
// TODO: handle federated peeks
|
||||
|
|
|
|||
|
|
@ -34,84 +34,48 @@ type Unpeeker struct {
|
|||
Inputer *input.Inputer
|
||||
}
|
||||
|
||||
// PerformPeek handles peeking into matrix rooms, including over federation by talking to the federationapi.
|
||||
// PerformUnpeek handles un-peeking matrix rooms, including over federation by talking to the federationapi.
|
||||
func (r *Unpeeker) PerformUnpeek(
|
||||
ctx context.Context,
|
||||
req *api.PerformUnpeekRequest,
|
||||
res *api.PerformUnpeekResponse,
|
||||
) error {
|
||||
if err := r.performUnpeek(ctx, req); err != nil {
|
||||
perr, ok := err.(*api.PerformError)
|
||||
if ok {
|
||||
res.Error = perr
|
||||
} else {
|
||||
res.Error = &api.PerformError{
|
||||
Msg: err.Error(),
|
||||
}
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (r *Unpeeker) performUnpeek(
|
||||
ctx context.Context,
|
||||
req *api.PerformUnpeekRequest,
|
||||
roomID, userID, deviceID string,
|
||||
) error {
|
||||
// FIXME: there's way too much duplication with performJoin
|
||||
_, domain, err := gomatrixserverlib.SplitID('@', req.UserID)
|
||||
_, domain, err := gomatrixserverlib.SplitID('@', userID)
|
||||
if err != nil {
|
||||
return &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Supplied user ID %q in incorrect format", req.UserID),
|
||||
}
|
||||
return api.ErrInvalidID{Err: fmt.Errorf("supplied user ID %q in incorrect format", userID)}
|
||||
}
|
||||
if !r.Cfg.Matrix.IsLocalServerName(domain) {
|
||||
return &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("User %q does not belong to this homeserver", req.UserID),
|
||||
}
|
||||
return api.ErrInvalidID{Err: fmt.Errorf("user %q does not belong to this homeserver", userID)}
|
||||
}
|
||||
if strings.HasPrefix(req.RoomID, "!") {
|
||||
return r.performUnpeekRoomByID(ctx, req)
|
||||
}
|
||||
return &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID %q is invalid", req.RoomID),
|
||||
if strings.HasPrefix(roomID, "!") {
|
||||
return r.performUnpeekRoomByID(ctx, roomID, userID, deviceID)
|
||||
}
|
||||
return api.ErrInvalidID{Err: fmt.Errorf("room ID %q is invalid", roomID)}
|
||||
}
|
||||
|
||||
func (r *Unpeeker) performUnpeekRoomByID(
|
||||
_ context.Context,
|
||||
req *api.PerformUnpeekRequest,
|
||||
roomID, userID, deviceID string,
|
||||
) (err error) {
|
||||
// Get the domain part of the room ID.
|
||||
_, _, err = gomatrixserverlib.SplitID('!', req.RoomID)
|
||||
_, _, err = gomatrixserverlib.SplitID('!', roomID)
|
||||
if err != nil {
|
||||
return &api.PerformError{
|
||||
Code: api.PerformErrorBadRequest,
|
||||
Msg: fmt.Sprintf("Room ID %q is invalid: %s", req.RoomID, err),
|
||||
}
|
||||
return api.ErrInvalidID{Err: fmt.Errorf("room ID %q is invalid: %w", roomID, err)}
|
||||
}
|
||||
|
||||
// TODO: handle federated peeks
|
||||
|
||||
err = r.Inputer.OutputProducer.ProduceRoomEvents(req.RoomID, []api.OutputEvent{
|
||||
{
|
||||
Type: api.OutputTypeRetirePeek,
|
||||
RetirePeek: &api.OutputRetirePeek{
|
||||
RoomID: req.RoomID,
|
||||
UserID: req.UserID,
|
||||
DeviceID: req.DeviceID,
|
||||
},
|
||||
},
|
||||
})
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
// By this point, if req.RoomIDOrAlias contained an alias, then
|
||||
// it will have been overwritten with a room ID by performPeekRoomByAlias.
|
||||
// We should now include this in the response so that the CS API can
|
||||
// return the right room ID.
|
||||
return nil
|
||||
return r.Inputer.OutputProducer.ProduceRoomEvents(roomID, []api.OutputEvent{
|
||||
{
|
||||
Type: api.OutputTypeRetirePeek,
|
||||
RetirePeek: &api.OutputRetirePeek{
|
||||
RoomID: roomID,
|
||||
UserID: userID,
|
||||
DeviceID: deviceID,
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
|
|
|||
|
|
@ -172,8 +172,8 @@ func addUserToRoom(
|
|||
UserID: userID,
|
||||
Content: addGroupContent,
|
||||
}
|
||||
joinRes := rsapi.PerformJoinResponse{}
|
||||
return rsAPI.PerformJoin(ctx, &joinReq, &joinRes)
|
||||
_, _, err := rsAPI.PerformJoin(ctx, &joinReq)
|
||||
return err
|
||||
}
|
||||
|
||||
func (a *UserInternalAPI) PerformAccountCreation(ctx context.Context, req *api.PerformAccountCreationRequest, res *api.PerformAccountCreationResponse) error {
|
||||
|
|
|
|||
Loading…
Reference in a new issue