- every revision bump (API writes and /bmadmin saves) enqueues
updated.jz.bm.material with {material_id, revision} in a savepoint
- the materials namespace authorizer allows a subscribe only to a
visible material the user may manage
- api.ManagesMaterials and api.CanWatchMaterial
56 lines
2.0 KiB
Go
56 lines
2.0 KiB
Go
package bm
|
|
|
|
import (
|
|
"context"
|
|
"errors"
|
|
|
|
usermodels "git.golem15.com/golem15/sm-user-plugin/models"
|
|
"git.golem15.com/golem15/summercms/modules/backpack"
|
|
"git.golem15.com/golem15/summercms/modules/lighthouse"
|
|
"git.golem15.com/jakub/sm-bm-plugin/classes"
|
|
"git.golem15.com/jakub/sm-bm-plugin/controllers"
|
|
"gorm.io/gorm"
|
|
|
|
// The app always ships the Centrifugo driver; config/realtime.yaml
|
|
// keeps the null driver until rome's .env selects centrifugo.
|
|
_ "git.golem15.com/golem15/summercms/modules/lighthouse/centrifugo"
|
|
)
|
|
|
|
// errDatabaseUnavailable is the user lookup's answer before serve has
|
|
// published the database.
|
|
var errDatabaseUnavailable = errors.New("jz.bm: database unavailable")
|
|
|
|
// wireRealtime binds the app to the framework realtime service: it builds
|
|
// the service selected by realtime.driver, installs the user lookup the
|
|
// connection token reads its display name from and the notifier the
|
|
// materials admin announces revisions with, and registers the authorizer of
|
|
// the materials namespace. Channel authorizers belong to the plugins that
|
|
// own the channels: jz.bm owns materials (classes.MaterialsNamespace),
|
|
// golem15.presentations its own.
|
|
func (p *Plugin) wireRealtime(app *backpack.App) error {
|
|
svc, err := lighthouse.From(app)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
p.realtime = svc
|
|
controllers.UseMaterialRevisionNotifier(&classes.MaterialRevisionNotifier{Realtime: svc})
|
|
svc.SetUserLookup(func(ctx context.Context, id uint) (lighthouse.User, bool, error) {
|
|
// Boot runs before serve publishes the database, so the handle is
|
|
// resolved per call.
|
|
gdb, ok := app.Lookup[*gorm.DB]()
|
|
if !ok || gdb == nil {
|
|
return lighthouse.User{}, false, errDatabaseUnavailable
|
|
}
|
|
var u usermodels.User
|
|
err := gdb.WithContext(ctx).Select("id", "name").Where("id = ?", id).Take(&u).Error
|
|
if errors.Is(err, gorm.ErrRecordNotFound) {
|
|
return lighthouse.User{}, false, nil
|
|
}
|
|
if err != nil {
|
|
return lighthouse.User{}, false, err
|
|
}
|
|
return lighthouse.User{ID: u.ID, Name: u.Name}, true, nil
|
|
})
|
|
return p.registerMaterialsRealtime(svc)
|
|
}
|