Skip to main content

ObsEvent

Struct ObsEvent 

Source
pub struct ObsEvent {
    pub pc_id: String,
    pub at: DateTime<Utc>,
    pub kind: String,
    pub source: String,
    pub event_record_id: Option<String>,
    pub payload: Value,
}
Expand description

One observability event published to obs.<pc_id>.

The kind field is a free-form string — vocabulary lives at the consumer (backend projector decides filtering / coloring; SPA decides chip labels). Established kinds at #246 land:

  • logon / logoff — Security log 4624 / 4634
  • boot / shutdown — System log 12 / 13 (kernel-general)
  • unexpected_shutdown — System log 41
  • sleep / resume — System log 42 / 107
  • agent_started / agent_self_update — agent-emitted (later)
  • diagnostic — kanade logs collect bundles (#219)

New kinds can be added without a wire change; the backend projector stores whatever string the agent sends and the SPA surfaces it.

Fields§

§pc_id: String

PC reporting the event. Routing key on the subject side (obs.<pc_id>) and primary scope of the SPA timeline view.

§at: DateTime<Utc>

Wall-clock instant of the event as known to the SOURCE (e.g. Windows Event Log’s TimeCreated), NOT the moment the agent published it. The timeline must reflect when things happened on the box, not when the projector heard about them — the two can differ by minutes when the agent is catching up from outbox after a broker outage.

§kind: String

What kind of event this is — the SPA’s filter chip and the backend projector’s coloring key. See the doc comment on this struct for the vocabulary at landing.

§source: String

Where this event came from. Format <scheme>:<detail> (e.g. winlog:System, winlog:Security, agent:internal, kanade:logs_collect). Two roles:

  • Distinguishes events from different sources that might share an event_record_id namespace.
  • Lets the SPA filter “show me only winlog events” without needing a separate enum.
§event_record_id: Option<String>

Stable per-source unique identifier — e.g. EventRecordID from the Windows Event Log. Combined with pc_id and source it forms the dedup key, so agent re-sends (under watermark drift, outbox replay, etc.) are harmless.

None for sources that have no natural unique id (e.g. agent-emitted milestones where the only candidate is the at timestamp + kind, which the backend can synthesize from those fields if needed).

#[serde(default)] so an agent publisher that has no id to emit can omit the field entirely; serde fills None rather than refusing the message. Without this, agent versions that always send the field can deserialize but future ones that drop it on null cases would silently land in the warn-log → projector drop path.

§payload: Value

Free-form per-kind details. The wire stays narrow (pc_id, at, kind, source, event_record_id) and the per-kind shape lives here:

  • logon: { "user": "...", "logon_type": 2 }
  • boot: typically null or {} — the bare presence is the event
  • diagnostic: { "bucket": "OBJECT_DIAGNOSTICS", "key": "..." } — pointer to the actual log blob

Backend projector stores this as TEXT (the JSON representation); SPA renders it kind-aware.

#[serde(default)] so a publisher emitting a bare-presence event can omit the field entirely (serde fills Value::Null) rather than being forced to write "payload": null on every line.

Trait Implementations§

Source§

impl Clone for ObsEvent

Source§

fn clone(&self) -> ObsEvent

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for ObsEvent

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<'de> Deserialize<'de> for ObsEvent

Source§

fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>
where __D: Deserializer<'de>,

Deserialize this value from the given Serde deserializer. Read more
Source§

impl PartialEq for ObsEvent

Source§

fn eq(&self, other: &ObsEvent) -> bool

Tests for self and other values to be equal, and is used by ==.
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Tests for !=. The default implementation is almost always sufficient, and should not be overridden without very good reason.
Source§

impl Serialize for ObsEvent

Source§

fn serialize<__S>(&self, __serializer: __S) -> Result<__S::Ok, __S::Error>
where __S: Serializer,

Serialize this value into the given Serde serializer. Read more
Source§

impl Eq for ObsEvent

Source§

impl StructuralPartialEq for ObsEvent

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> DynClone for T
where T: Clone,

Source§

fn __clone_box(&self, _: Private) -> *mut ()

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> Pointable for T

Source§

const ALIGN: usize

The alignment of pointer.
Source§

type Init = T

The type for initializers.
Source§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
Source§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
Source§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
Source§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V

Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

impl<T> DeserializeOwned for T
where T: for<'de> Deserialize<'de>,