diff --git a/internal/mscs/msc2836/msc2836.go b/internal/mscs/msc2836/msc2836.go index 3e3b59199..b0c17c3cf 100644 --- a/internal/mscs/msc2836/msc2836.go +++ b/internal/mscs/msc2836/msc2836.go @@ -374,7 +374,7 @@ func (rc *reqCtx) includeParent(childEvent *gomatrixserverlib.HeaderedEvent) (pa if parentID == "" { return nil } - return rc.lookForEvent(parentID, false) + return rc.lookForEvent(parentID) } // If include_children: true, lookup all events which have event_id as an m.relationship @@ -414,7 +414,7 @@ func (rc *reqCtx) includeChildren(db Database, parentID string, limit int, recen } var childEvents []*gomatrixserverlib.HeaderedEvent for _, child := range children { - childEvent := rc.lookForEvent(child.EventID, false) + childEvent := rc.lookForEvent(child.EventID) if childEvent != nil { childEvents = append(childEvents, childEvent) } @@ -452,7 +452,7 @@ func walkThread( // This will probably be easiest if the event relationships response is directly pumped into the database // so the next walk will do the right thing. This requires those events to be authed and likely injected as // outliers into the roomserver DB, which will de-dupe appropriately. - event := rc.lookForEvent(wi.EventID, true) + event := rc.lookForEvent(wi.EventID) if event != nil { result = append(result, event) } @@ -549,33 +549,6 @@ func (rc *reqCtx) getServersForEventID(eventID string) (string, gomatrixserverli return roomID, roomVer, serversToQuery } -// remoteEvent queries for the event ID given. -func (rc *reqCtx) remoteEvent(eventID string) *gomatrixserverlib.HeaderedEvent { - if rc.isFederatedRequest { - return nil // we don't query remote servers for remote requests - } - _, roomVer, serversToQuery := rc.getServersForEventID(eventID) - for _, s := range serversToQuery { - txn, err := rc.fsAPI.GetEvent(rc.ctx, s, eventID) - if err != nil { - util.GetLogger(rc.ctx).WithError(err).Warn("remoteEvent: failed to GetEvent") - continue - } - if len(txn.PDUs) != 1 { - continue - } - ev, err := gomatrixserverlib.NewEventFromUntrustedJSON(txn.PDUs[0], roomVer) - if err != nil { - util.GetLogger(rc.ctx).WithError(err).Warn("remoteEvent: failed to NewEventFromUntrustedJSON") - continue - } - // TODO: check sigs on event - // TODO: check auth events on event - return ev.Headered(roomVer) - } - return nil -} - func (rc *reqCtx) remoteEventRelationships(eventID string) *gomatrixserverlib.MSC2836EventRelationshipsResponse { if rc.isFederatedRequest { return nil // we don't query remote servers for remote requests @@ -594,34 +567,23 @@ func (rc *reqCtx) remoteEventRelationships(eventID string) *gomatrixserverlib.MS return res } -// lookForEvent returns the event for the event ID given, by trying to auto-join rooms if not authorised and by querying remote servers -// if the event ID is unknown. If `exploreThread` is true, remote requests will use /event_relationships instead of /event. This is -// desirable when walking the thread, but is not desirable when satisfying include_parent|children flags. +// lookForEvent returns the event for the event ID given, by trying to query remote servers +// if the event ID is unknown via /event_relationships. // nolint:gocyclo -func (rc *reqCtx) lookForEvent(eventID string, exploreThread bool) *gomatrixserverlib.HeaderedEvent { +func (rc *reqCtx) lookForEvent(eventID string) *gomatrixserverlib.HeaderedEvent { event := rc.getLocalEvent(eventID) if event == nil { - if exploreThread { - queryRes := rc.remoteEventRelationships(eventID) - if queryRes != nil { - // inject all the events into the roomserver then return the event in question - rc.injectResponseToRoomserver(queryRes) - for _, ev := range queryRes.Events { - if ev.EventID() == eventID { - return ev.Headered(ev.Version()) - } + queryRes := rc.remoteEventRelationships(eventID) + if queryRes != nil { + // inject all the events into the roomserver then return the event in question + rc.injectResponseToRoomserver(queryRes) + for _, ev := range queryRes.Events { + if ev.EventID() == eventID { + return ev.Headered(ev.Version()) } } - // if we fail to query /event_relationships or we don't have the event queried in the response, fallthrough - // to do a /event call. } - // this event may have occurred before we joined the room, so delegate to another server to see if they know anything. - // Only ask for this event though. - event = rc.remoteEvent(eventID) - if event == nil { - return nil - } - } else if exploreThread && rc.hasUnexploredChildren(eventID) { + } else if rc.hasUnexploredChildren(eventID) { // we have the local event but we may need to do a remote hit anyway if we are exploring the thread and have unknown children. // If we don't do this then we risk never fetching the children. queryRes := rc.remoteEventRelationships(eventID) @@ -683,7 +645,7 @@ func (rc *reqCtx) getLocalEvent(eventID string) *gomatrixserverlib.HeaderedEvent return nil } if len(queryEventsRes.Events) == 0 { - util.GetLogger(rc.ctx).Infof("getLocalEvent: event does not exist") + util.GetLogger(rc.ctx).WithField("event_id", eventID).Infof("getLocalEvent: event does not exist") return nil // event does not exist } return queryEventsRes.Events[0] diff --git a/internal/mscs/msc2836/storage.go b/internal/mscs/msc2836/storage.go index ab253b6e7..ef59086b3 100644 --- a/internal/mscs/msc2836/storage.go +++ b/internal/mscs/msc2836/storage.go @@ -10,6 +10,7 @@ import ( "github.com/matrix-org/dendrite/internal/config" "github.com/matrix-org/dendrite/internal/sqlutil" "github.com/matrix-org/gomatrixserverlib" + "github.com/matrix-org/util" ) type eventInfo struct { @@ -240,21 +241,23 @@ func (p *DB) StoreRelation(ctx context.Context, ev *gomatrixserverlib.HeaderedEv if err != nil { return err } + util.GetLogger(ctx).Infof("StoreRelation child=%s parent=%s rel_type=%s", child, parent, relType) _, err = txn.Stmt(p.insertNodeStmt).ExecContext(ctx, ev.EventID(), ev.OriginServerTS(), ev.RoomID(), count, base64.RawStdEncoding.EncodeToString(hash), 0) return err }) } func (p *DB) UpdateChildMetadata(ctx context.Context, ev *gomatrixserverlib.HeaderedEvent) error { + eventCount, eventHash := extractChildMetadata(ev) + if eventCount == 0 { + return nil // nothing to update with + } + // extract current children count/hash, if they are less than the current event then update the columns and set to unexplored count, hash, _, err := p.ChildMetadata(ctx, ev.EventID()) if err != nil { return err } - eventCount, eventHash := extractChildMetadata(ev) - if eventCount == 0 { - return nil // nothing to update with - } if eventCount > count || (eventCount == count && !bytes.Equal(hash, eventHash)) { _, err = p.updateChildMetadataStmt.ExecContext(ctx, eventCount, base64.RawStdEncoding.EncodeToString(eventHash), 0, ev.EventID()) return err @@ -266,6 +269,9 @@ func (p *DB) ChildMetadata(ctx context.Context, eventID string) (count int, hash var b64hash string var exploredInt int if err = p.selectChildMetadataStmt.QueryRowContext(ctx, eventID).Scan(&count, &b64hash, &exploredInt); err != nil { + if err == sql.ErrNoRows { + err = nil + } return } hash, err = base64.RawStdEncoding.DecodeString(b64hash)