pub struct Viewer {
pub stream_id: StreamId,
pub viewer_id: String,
pub name: String,
pub color: String,
pub identity_issuer: Option<String>,
pub identity_subject: Option<String>,
pub avatar_url: Option<String>,
pub cursor: Option<(f32, f32)>,
pub client_id: Option<ClientId>,
pub id: ViewerId,
}Expand description
Ephemeral presence: one row per viewer per stream. As a child of the
framework Client, it is cascade-deleted when the browser tab disconnects,
so presence auto-clears with no timers.
Fields§
§stream_id: StreamId§viewer_id: String§name: String§color: String§identity_issuer: Option<String>Optional OIDC issuer for display identity enrichment. Presence and control remain available when this is absent.
identity_subject: Option<String>Optional OIDC subject. Client-asserted display data only; never used as authorization or as the control-lock owner key.
avatar_url: Option<String>Optional profile image URL from the identity provider.
cursor: Option<(f32, f32)>§client_id: Option<ClientId>§id: ViewerIdImplementations§
Source§impl Viewer
impl Viewer
Sourcepub fn row_id(stream_id: &StreamId, conn: &str) -> ViewerId
pub fn row_id(stream_id: &StreamId, conn: &str) -> ViewerId
One row per connection (conn = the WebSocket client id), not per
viewer_id. A browser’s tabs share the persisted viewer_id but are distinct
connections, so each gets its own presence row — independently cascade-cleaned
on disconnect — and only the connection holding the lock drives. Closing the
driving tab therefore frees its row and the survivor is reconciled the wheel.
Trait Implementations§
Source§impl AnyItem for Viewer
impl AnyItem for Viewer
Source§fn entity_type(&self) -> &'static str
fn entity_type(&self) -> &'static str
Source§fn server_owner(&self) -> Option<&str>
fn server_owner(&self) -> Option<&str>
#[server_owned] field value, if this item has one.Source§impl<'de> Deserialize<'de> for Viewer
impl<'de> Deserialize<'de> for Viewer
Source§fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
Source§impl Eventable for Viewer
impl Eventable for Viewer
Source§const ENTITY_NAME_STATIC: &'static str = "Viewer"
const ENTITY_NAME_STATIC: &'static str = "Viewer"
entity_type() from AnyItem for instance access).Source§fn entity_name_static() -> &'static str
fn entity_name_static() -> &'static str
Source§fn ingest_buffer_policy() -> IngestBufferPolicy
fn ingest_buffer_policy() -> IngestBufferPolicy
Source§impl TS for Viewer
impl TS for Viewer
Source§type WithoutGenerics = Viewer
type WithoutGenerics = Viewer
WithoutGenerics should just be Self.
If the type does have generic parameters, then all generic parameters must be replaced with
a dummy type, e.g ts_rs::Dummy or (). The only requirement for these dummy types is that
EXPORT_TO must be None. Read moreSource§type OptionInnerType = Viewer
type OptionInnerType = Viewer
std::option::Option<T>, then this associated type is set to T.
All other implementations of TS should set this type to Self instead.Source§fn docs() -> Option<String>
fn docs() -> Option<String>
TS is derived, docs are
automatically read from your doc comments or #[doc = ".."] attributesSource§fn decl_concrete(cfg: &Config) -> String
fn decl_concrete(cfg: &Config) -> String
TS::decl().
If this type is not generic, then this function is equivalent to TS::decl().Source§fn decl(cfg: &Config) -> String
fn decl(cfg: &Config) -> String
type User = { user_id: number, ... }.
This function will panic if the type has no declaration. Read moreSource§fn inline(cfg: &Config) -> String
fn inline(cfg: &Config) -> String
{ user_id: number }.
This function will panic if the type cannot be inlined.Source§fn inline_flattened(cfg: &Config) -> String
fn inline_flattened(cfg: &Config) -> String
Source§fn visit_generics(v: &mut impl TypeVisitor)where
Self: 'static,
fn visit_generics(v: &mut impl TypeVisitor)where
Self: 'static,
Source§fn output_path() -> Option<PathBuf>
fn output_path() -> Option<PathBuf>
T should be exported, relative to the output directory.
The returned path does not include any base directory. Read moreSource§fn visit_dependencies(v: &mut impl TypeVisitor)where
Self: 'static,
fn visit_dependencies(v: &mut impl TypeVisitor)where
Self: 'static,
Source§fn dependencies(cfg: &Config) -> Vec<Dependency>where
Self: 'static,
fn dependencies(cfg: &Config) -> Vec<Dependency>where
Self: 'static,
Source§fn export(cfg: &Config) -> Result<(), ExportError>where
Self: 'static,
fn export(cfg: &Config) -> Result<(), ExportError>where
Self: 'static,
TS::export_all. Read moreSource§fn export_all(cfg: &Config) -> Result<(), ExportError>where
Self: 'static,
fn export_all(cfg: &Config) -> Result<(), ExportError>where
Self: 'static,
TS::export. Read moreSource§fn export_to_string(cfg: &Config) -> Result<String, ExportError>where
Self: 'static,
fn export_to_string(cfg: &Config) -> Result<String, ExportError>where
Self: 'static,
Auto Trait Implementations§
impl Freeze for Viewer
impl RefUnwindSafe for Viewer
impl Send for Viewer
impl Sync for Viewer
impl Unpin for Viewer
impl UnsafeUnpin for Viewer
impl UnwindSafe for Viewer
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
impl<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
impl<T> CellValue for T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> DeserializeOwned for Twhere
T: for<'de> Deserialize<'de>,
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more