diff options
author | Neil Alexander <neilalexander@users.noreply.github.com> | 2020-08-25 12:32:29 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-08-25 12:32:29 +0100 |
commit | c8b873abc8cb20227774c648b7a774214c8f3752 (patch) | |
tree | 78e7cf34b4fc8625cc6458fead0fd2adee5114a2 /roomserver/storage | |
parent | 05242096a17ab432878f777c64240c2a3d5b367c (diff) |
Roomserver NID caches (#1335)
* Initial work on roomserver NID caches
* Give caches to roomserver storage
* Populate caches
* Fix bugs
* Fix WASM build
* Don't hit cache twice in RoomNIDExcludingStubs
* Store reverse room ID-room NID mapping, consult caches when assigning NIDs
Diffstat (limited to 'roomserver/storage')
-rw-r--r-- | roomserver/storage/postgres/storage.go | 4 | ||||
-rw-r--r-- | roomserver/storage/shared/storage.go | 80 | ||||
-rw-r--r-- | roomserver/storage/sqlite3/storage.go | 4 | ||||
-rw-r--r-- | roomserver/storage/storage.go | 7 | ||||
-rw-r--r-- | roomserver/storage/storage_wasm.go | 5 |
5 files changed, 88 insertions, 12 deletions
diff --git a/roomserver/storage/postgres/storage.go b/roomserver/storage/postgres/storage.go index d217b5d2..02ff072d 100644 --- a/roomserver/storage/postgres/storage.go +++ b/roomserver/storage/postgres/storage.go @@ -18,6 +18,7 @@ package postgres import ( "database/sql" + "github.com/matrix-org/dendrite/internal/caching" "github.com/matrix-org/dendrite/internal/config" "github.com/matrix-org/dendrite/internal/sqlutil" @@ -33,7 +34,7 @@ type Database struct { // Open a postgres database. // nolint: gocyclo -func Open(dbProperties *config.DatabaseOptions) (*Database, error) { +func Open(dbProperties *config.DatabaseOptions, cache caching.RoomServerCaches) (*Database, error) { var d Database var db *sql.DB var err error @@ -98,6 +99,7 @@ func Open(dbProperties *config.DatabaseOptions) (*Database, error) { } d.Database = shared.Database{ DB: db, + Cache: cache, Writer: sqlutil.NewDummyWriter(), EventTypesTable: eventTypes, EventStateKeysTable: eventStateKeys, diff --git a/roomserver/storage/shared/storage.go b/roomserver/storage/shared/storage.go index 7101376a..0788f6cb 100644 --- a/roomserver/storage/shared/storage.go +++ b/roomserver/storage/shared/storage.go @@ -6,6 +6,7 @@ import ( "encoding/json" "fmt" + "github.com/matrix-org/dendrite/internal/caching" "github.com/matrix-org/dendrite/internal/sqlutil" "github.com/matrix-org/dendrite/roomserver/api" "github.com/matrix-org/dendrite/roomserver/storage/tables" @@ -27,6 +28,7 @@ const redactionsArePermanent = false type Database struct { DB *sql.DB + Cache caching.RoomServerCaches Writer sqlutil.Writer EventsTable tables.Events EventJSONTable tables.EventJSON @@ -51,7 +53,26 @@ func (d *Database) SupportsConcurrentRoomInputs() bool { func (d *Database) EventTypeNIDs( ctx context.Context, eventTypes []string, ) (map[string]types.EventTypeNID, error) { - return d.EventTypesTable.BulkSelectEventTypeNID(ctx, eventTypes) + result := make(map[string]types.EventTypeNID) + remaining := []string{} + for _, eventType := range eventTypes { + if nid, ok := d.Cache.GetRoomServerEventTypeNID(eventType); ok { + result[eventType] = nid + } else { + remaining = append(remaining, eventType) + } + } + if len(remaining) > 0 { + nids, err := d.EventTypesTable.BulkSelectEventTypeNID(ctx, remaining) + if err != nil { + return nil, err + } + for eventType, nid := range nids { + result[eventType] = nid + d.Cache.StoreRoomServerEventTypeNID(eventType, nid) + } + } + return result, nil } func (d *Database) EventStateKeys( @@ -63,7 +84,26 @@ func (d *Database) EventStateKeys( func (d *Database) EventStateKeyNIDs( ctx context.Context, eventStateKeys []string, ) (map[string]types.EventStateKeyNID, error) { - return d.EventStateKeysTable.BulkSelectEventStateKeyNID(ctx, eventStateKeys) + result := make(map[string]types.EventStateKeyNID) + remaining := []string{} + for _, eventStateKey := range eventStateKeys { + if nid, ok := d.Cache.GetRoomServerStateKeyNID(eventStateKey); ok { + result[eventStateKey] = nid + } else { + remaining = append(remaining, eventStateKey) + } + } + if len(remaining) > 0 { + nids, err := d.EventStateKeysTable.BulkSelectEventStateKeyNID(ctx, remaining) + if err != nil { + return nil, err + } + for eventStateKey, nid := range nids { + result[eventStateKey] = nid + d.Cache.StoreRoomServerStateKeyNID(eventStateKey, nid) + } + } + return result, nil } func (d *Database) StateEntriesForEventIDs( @@ -157,10 +197,14 @@ func (d *Database) EventsFromIDs(ctx context.Context, eventIDs []string) ([]type } func (d *Database) RoomNID(ctx context.Context, roomID string) (types.RoomNID, error) { + if nid, ok := d.Cache.GetRoomServerRoomNID(roomID); ok { + return nid, nil + } roomNID, err := d.RoomsTable.SelectRoomNID(ctx, nil, roomID) if err == sql.ErrNoRows { return 0, nil } + d.Cache.StoreRoomServerRoomNID(roomID, roomNID) return roomNID, err } @@ -214,6 +258,9 @@ func (d *Database) StateEntries( func (d *Database) GetRoomVersionForRoom( ctx context.Context, roomID string, ) (gomatrixserverlib.RoomVersion, error) { + if roomVersion, ok := d.Cache.GetRoomVersion(roomID); ok { + return roomVersion, nil + } return d.RoomsTable.SelectRoomVersionForRoomID( ctx, nil, roomID, ) @@ -222,6 +269,11 @@ func (d *Database) GetRoomVersionForRoom( func (d *Database) GetRoomVersionForRoomNID( ctx context.Context, roomNID types.RoomNID, ) (gomatrixserverlib.RoomVersion, error) { + if roomID, ok := d.Cache.GetRoomServerRoomID(roomNID); ok { + if roomVersion, ok := d.Cache.GetRoomVersion(roomID); ok { + return roomVersion, nil + } + } return d.RoomsTable.SelectRoomVersionForRoomNID( ctx, roomNID, ) @@ -488,6 +540,9 @@ func (d *Database) assignRoomNID( ctx context.Context, txn *sql.Tx, roomID string, roomVersion gomatrixserverlib.RoomVersion, ) (types.RoomNID, error) { + if roomNID, ok := d.Cache.GetRoomServerRoomNID(roomID); ok { + return roomNID, nil + } // Check if we already have a numeric ID in the database. roomNID, err := d.RoomsTable.SelectRoomNID(ctx, txn, roomID) if err == sql.ErrNoRows { @@ -498,14 +553,20 @@ func (d *Database) assignRoomNID( roomNID, err = d.RoomsTable.SelectRoomNID(ctx, txn, roomID) } } + if err == nil { + d.Cache.StoreRoomServerRoomNID(roomID, roomNID) + } return roomNID, err } func (d *Database) assignEventTypeNID( ctx context.Context, txn *sql.Tx, eventType string, -) (eventTypeNID types.EventTypeNID, err error) { +) (types.EventTypeNID, error) { + if eventTypeNID, ok := d.Cache.GetRoomServerEventTypeNID(eventType); ok { + return eventTypeNID, nil + } // Check if we already have a numeric ID in the database. - eventTypeNID, err = d.EventTypesTable.SelectEventTypeNID(ctx, txn, eventType) + eventTypeNID, err := d.EventTypesTable.SelectEventTypeNID(ctx, txn, eventType) if err == sql.ErrNoRows { // We don't have a numeric ID so insert one into the database. eventTypeNID, err = d.EventTypesTable.InsertEventTypeNID(ctx, txn, eventType) @@ -514,12 +575,18 @@ func (d *Database) assignEventTypeNID( eventTypeNID, err = d.EventTypesTable.SelectEventTypeNID(ctx, txn, eventType) } } - return + if err == nil { + d.Cache.StoreRoomServerEventTypeNID(eventType, eventTypeNID) + } + return eventTypeNID, err } func (d *Database) assignStateKeyNID( ctx context.Context, txn *sql.Tx, eventStateKey string, ) (types.EventStateKeyNID, error) { + if eventStateKeyNID, ok := d.Cache.GetRoomServerStateKeyNID(eventStateKey); ok { + return eventStateKeyNID, nil + } // Check if we already have a numeric ID in the database. eventStateKeyNID, err := d.EventStateKeysTable.SelectEventStateKeyNID(ctx, txn, eventStateKey) if err == sql.ErrNoRows { @@ -530,6 +597,9 @@ func (d *Database) assignStateKeyNID( eventStateKeyNID, err = d.EventStateKeysTable.SelectEventStateKeyNID(ctx, txn, eventStateKey) } } + if err == nil { + d.Cache.StoreRoomServerStateKeyNID(eventStateKey, eventStateKeyNID) + } return eventStateKeyNID, err } diff --git a/roomserver/storage/sqlite3/storage.go b/roomserver/storage/sqlite3/storage.go index d1738966..87dce6ad 100644 --- a/roomserver/storage/sqlite3/storage.go +++ b/roomserver/storage/sqlite3/storage.go @@ -19,6 +19,7 @@ import ( "context" "database/sql" + "github.com/matrix-org/dendrite/internal/caching" "github.com/matrix-org/dendrite/internal/config" "github.com/matrix-org/dendrite/internal/sqlutil" "github.com/matrix-org/dendrite/roomserver/storage/shared" @@ -46,7 +47,7 @@ type Database struct { // Open a sqlite database. // nolint: gocyclo -func Open(dbProperties *config.DatabaseOptions) (*Database, error) { +func Open(dbProperties *config.DatabaseOptions, cache caching.RoomServerCaches) (*Database, error) { var d Database var err error if d.db, err = sqlutil.Open(dbProperties); err != nil { @@ -120,6 +121,7 @@ func Open(dbProperties *config.DatabaseOptions) (*Database, error) { } d.Database = shared.Database{ DB: d.db, + Cache: cache, Writer: sqlutil.NewExclusiveWriter(), EventsTable: d.events, EventTypesTable: d.eventTypes, diff --git a/roomserver/storage/storage.go b/roomserver/storage/storage.go index c6561fdc..cfbb7b55 100644 --- a/roomserver/storage/storage.go +++ b/roomserver/storage/storage.go @@ -19,18 +19,19 @@ package storage import ( "fmt" + "github.com/matrix-org/dendrite/internal/caching" "github.com/matrix-org/dendrite/internal/config" "github.com/matrix-org/dendrite/roomserver/storage/postgres" "github.com/matrix-org/dendrite/roomserver/storage/sqlite3" ) // Open opens a database connection. -func Open(dbProperties *config.DatabaseOptions) (Database, error) { +func Open(dbProperties *config.DatabaseOptions, cache caching.RoomServerCaches) (Database, error) { switch { case dbProperties.ConnectionString.IsSQLite(): - return sqlite3.Open(dbProperties) + return sqlite3.Open(dbProperties, cache) case dbProperties.ConnectionString.IsPostgres(): - return postgres.Open(dbProperties) + return postgres.Open(dbProperties, cache) default: return nil, fmt.Errorf("unexpected database type") } diff --git a/roomserver/storage/storage_wasm.go b/roomserver/storage/storage_wasm.go index 43367f36..28e28546 100644 --- a/roomserver/storage/storage_wasm.go +++ b/roomserver/storage/storage_wasm.go @@ -17,15 +17,16 @@ package storage import ( "fmt" + "github.com/matrix-org/dendrite/internal/caching" "github.com/matrix-org/dendrite/internal/config" "github.com/matrix-org/dendrite/roomserver/storage/sqlite3" ) // NewPublicRoomsServerDatabase opens a database connection. -func Open(dbProperties *config.DatabaseOptions) (Database, error) { +func Open(dbProperties *config.DatabaseOptions, cache caching.RoomServerCaches) (Database, error) { switch { case dbProperties.ConnectionString.IsSQLite(): - return sqlite3.Open(dbProperties) + return sqlite3.Open(dbProperties, cache) case dbProperties.ConnectionString.IsPostgres(): return nil, fmt.Errorf("can't use Postgres implementation") default: |