Skip to main content

CompletedResults

Struct CompletedResults 

Source
pub struct CompletedResults<T> { /* private fields */ }
Expand description

The transition table, with no lock and no I/O.

§What &mut self guarantees and what it does not

It guarantees the transitions are consistent within one caller. It does not make claim atomic against another thread, because a &mut self method only excludes callers that share the borrow. An adapter holds this behind a Mutex — one acquisition per operation, and the lock is released across the execution rather than held across it, so a slow tool does not block every other key. That is the same division as the registry’s compare-and-swap publish: the state machine is domain, the atomicity is the adapter’s, and neither is asked to do the other’s job.

Implementations§

Source§

impl<T> CompletedResults<T>

Source

pub fn with_capacity(capacity: NonZeroUsize) -> Self

A store holding at most capacity keys.

Bounded because a client chooses the keys: an unbounded map keyed by a peer-supplied id is a memory exhaustion primitive, and the wire offers nothing that would stop a client from minting a fresh id per request.

A capacity of zero is refused at the type level — such a store could never complete anything, so every call would fail for a reason that has nothing to do with the work itself.

Source

pub fn len(&self) -> usize

How many keys are held.

Source

pub fn is_empty(&self) -> bool

Whether nothing is held.

Source

pub const fn capacity(&self) -> usize

The ceiling, in keys.

Source

pub fn claim( &mut self, key: &IdempotencyKey, ) -> Result<Claim<T>, IdempotencyError>
where T: Clone,

Takes ownership of key, or reports why it could not.

§Errors

IdempotencyError::StoreFull when the store is at capacity, key is not already present, and every slot is held by a request still running. That is genuine overload, and refusing the new request is visible where discarding a live claim would let two callers run one request.

§Retention

When the store is full and key is new, the oldest completed result is dropped to make room. A retry replays its recorded result for as long as it is among the last capacity completed requests; a retry of something older than that runs again. The alternative, refusing every new key once the store has filled with finished work, turns a long-lived session into one that fails every call after the first capacity, which is the common case and not an edge. A dropped connection is retried in seconds, so the window is far longer than any retry needs.

T: Clone because handing a recorded result to the retrying caller leaves the recorded copy in place — a claim that consumed it would break the second retry, which is the case the store exists for.

Source

pub fn complete( &mut self, token: &ClaimToken, result: T, ) -> Result<(), StaleClaim>

Records the result of a claim.

§Errors

StaleClaim when the token is not the current holder of the key — because the claim was abandoned and re-taken, or because it was never valid. A stale completion is refused rather than applied: the attempt that replaced it is the one whose result the retrying client is entitled to, and writing over it would give two callers two different answers for one request id.

Source

pub fn abandon(&mut self, token: &ClaimToken) -> Result<(), StaleClaim>

Releases a claim so a later retry can execute.

§Errors

StaleClaim when the token is not the current holder. Releasing a claim another attempt now owns would hand the same key to a third caller while the second is still running it.

Source

pub fn completed(&self, key: &IdempotencyKey) -> Option<&T>

Whether a key has completed, without claiming it.

Source

pub fn is_in_flight(&self, key: &IdempotencyKey) -> bool

Whether a key is held by a live claim.

Trait Implementations§

Source§

impl<T: Debug> Debug for CompletedResults<T>

Source§

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

Formats the value using the given formatter. Read more

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<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
where ST: ?Sized, DT: ?Sized,

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<A, B, T> HttpServerConnExec<A, B> for T
where B: Body,

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> PolicyExt for T
where T: ?Sized,

Source§

fn and<P, B, E>(self, other: P) -> And<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow only if self and other return Action::Follow. Read more
Source§

fn or<P, B, E>(self, other: P) -> Or<T, P>
where T: Sized + Policy<B, E>, P: Policy<B, E>,

Create a new Policy that returns Action::Follow if either self or other returns Action::Follow. Read more
Source§

impl<T> Read<Exclusive, BecauseExclusive> for T
where T: ?Sized,

Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

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

Source§

type Error = !

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

fn try_from(value: U) -> Result<T, !>

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