From aa6bbf484a7963a754d47ba04869c06b72d4ee49 Mon Sep 17 00:00:00 2001 From: Neil Alexander Date: Mon, 21 Feb 2022 16:22:29 +0000 Subject: [PATCH] Return `ErrRoomNoExists` if insufficient state is available for a `buildEvent` to succeed when joining a room (#2210) This may help cases like #2206, since it should prompt us to try a federated join again instead. --- roomserver/internal/perform/perform_join.go | 11 ++++++++++- roomserver/storage/postgres/state_snapshot_table.go | 2 +- roomserver/storage/sqlite3/state_snapshot_table.go | 2 +- roomserver/types/types.go | 6 ++++++ 4 files changed, 18 insertions(+), 3 deletions(-) diff --git a/roomserver/internal/perform/perform_join.go b/roomserver/internal/perform/perform_join.go index 9d2a66d4..a40f66d2 100644 --- a/roomserver/internal/perform/perform_join.go +++ b/roomserver/internal/perform/perform_join.go @@ -29,6 +29,7 @@ import ( "github.com/matrix-org/dendrite/roomserver/internal/input" "github.com/matrix-org/dendrite/roomserver/internal/query" "github.com/matrix-org/dendrite/roomserver/storage" + "github.com/matrix-org/dendrite/roomserver/types" "github.com/matrix-org/dendrite/setup/config" "github.com/matrix-org/gomatrixserverlib" "github.com/sirupsen/logrus" @@ -367,7 +368,15 @@ func buildEvent( StateToFetch: eventsNeeded.Tuples(), }, &queryRes) if err != nil { - return nil, nil, fmt.Errorf("QueryLatestEventsAndState: %w", err) + switch err.(type) { + case types.MissingStateError: + // We know something about the room but the state seems to be + // insufficient to actually build a new event, so in effect we + // had might as well treat the room as if it doesn't exist. + return nil, nil, eventutil.ErrRoomNoExists + default: + return nil, nil, fmt.Errorf("QueryLatestEventsAndState: %w", err) + } } ev, err := eventutil.BuildEvent(ctx, builder, cfg, time.Now(), &eventsNeeded, &queryRes) diff --git a/roomserver/storage/postgres/state_snapshot_table.go b/roomserver/storage/postgres/state_snapshot_table.go index ce9f2463..8ed88603 100644 --- a/roomserver/storage/postgres/state_snapshot_table.go +++ b/roomserver/storage/postgres/state_snapshot_table.go @@ -134,7 +134,7 @@ func (s *stateSnapshotStatements) BulkSelectStateBlockNIDs( return nil, err } if i != len(stateNIDs) { - return nil, fmt.Errorf("storage: state NIDs missing from the database (%d != %d)", i, len(stateNIDs)) + return nil, types.MissingStateError(fmt.Sprintf("storage: state NIDs missing from the database (%d != %d)", i, len(stateNIDs))) } return results, nil } diff --git a/roomserver/storage/sqlite3/state_snapshot_table.go b/roomserver/storage/sqlite3/state_snapshot_table.go index 3c4bde3f..01df31e9 100644 --- a/roomserver/storage/sqlite3/state_snapshot_table.go +++ b/roomserver/storage/sqlite3/state_snapshot_table.go @@ -137,7 +137,7 @@ func (s *stateSnapshotStatements) BulkSelectStateBlockNIDs( } } if i != len(stateNIDs) { - return nil, fmt.Errorf("storage: state NIDs missing from the database (%d != %d)", i, len(stateNIDs)) + return nil, types.MissingStateError(fmt.Sprintf("storage: state NIDs missing from the database (%d != %d)", i, len(stateNIDs))) } return results, nil } diff --git a/roomserver/types/types.go b/roomserver/types/types.go index 5d52ccfc..65fbee04 100644 --- a/roomserver/types/types.go +++ b/roomserver/types/types.go @@ -213,6 +213,12 @@ type MissingEventError string func (e MissingEventError) Error() string { return string(e) } +// A MissingStateError is an error that happened because the roomserver was +// missing requested state snapshots from its databases. +type MissingStateError string + +func (e MissingStateError) Error() string { return string(e) } + // A RejectedError is returned when an event is stored as rejected. The error // contains the reason why. type RejectedError string