Skip to main content

Workspace

Struct Workspace 

Source
pub struct Workspace { /* private fields */ }
Expand description

One workspace, resolved: the runtime it borrows, the model, and everything discovered on disk, ready to mint runs from.

Held by reference by every run it mints, so a host keeps one per repository for as long as it wants to send prompts at it. Dropping it does not end the runs already minted — a PreparedRun owns its session — but the MCP connections go with it, and so does the runtime when this held the last Arc.

Send and Sync: the runtime is shared through Arcs and creates sessions from &self, so concurrent minting from one workspace needs no lock of basis’s own.

Implementations§

Source§

impl Workspace

Source

pub async fn open(path: impl Into<PathBuf>) -> Result<Self, RunError>

Opens path with basis’s defaults: a private runtime with the provider auto-detected from the environment, the newest model it offers, and every convention discovered where convention says to look.

builder is the same call with the knobs exposed — including with_runtime, for the host that opens many workspaces on one Runtime.

Source

pub fn builder(path: impl Into<PathBuf>) -> WorkspaceBuilder

Configures a workspace before opening it.

Source

pub fn prepare(&self, spec: impl Into<RunSpec>) -> Result<PreparedRun, RunError>

Mints a run: a fresh conversation against this workspace.

Synchronous, and deliberately so — everything expensive already happened. What this does is spawn a session on the existing runtime and hand back the PreparedRun that drives it.

The spec’s prompt may be empty. Once a session outlives a turn, a conversation with nothing said yet is a real state — it is what ACP’s session/new opens — so the emptiness check belongs where a prompt is actually sent, which is PreparedRun::execute and PreparedRun::send. (The free prepare keeps its own up-front check, because a one-shot caller that passed nothing wants to hear about it before a session exists.)

Source

pub fn resume( &self, agent_id: &str, spec: impl Into<RunSpec>, ) -> Result<PreparedRun, RunError>

Picks up a conversation a previous process left behind.

agent_id is PreparedRun::agent_id, not the session id: mentra persists agents, and a session is one process’s view of one. Resuming replays the transcript from the store, so the first turn after this already knows everything the last one did.

The workspace has to be the one the conversation belongs to. Nothing here checks that — mentra’s store is keyed by agent, not by path — so resuming an agent under a workspace it never ran in gives it that workspace’s context and tools alongside its own history.

Source

pub fn fingerprint(&self) -> Snapshot

A cheap stand-in for everything in this workspace a run could see.

The utility ADR-0014 kept when watch was deleted, on the type its ledger row promised it to. The semantics are crate::fingerprint’s verbatim: a digest over git ls-files plus HEAD, stat only, and every uncertain answer resolving to changed rather than unchanged.

Fingerprints the workspace as it is now, not as it was when the workspace was opened — that is the whole point, since a caller’s loop asks it repeatedly against one long-lived workspace.

Blocking: it spawns git and stats files. An async caller belongs on a blocking thread — tokio::task::spawn_blocking, or the equivalent.

Source

pub fn path(&self) -> &Path

The path this workspace was opened with, which is what its runs are scoped to.

Source

pub fn root(&self) -> &Path

The same directory as discovery resolved it, symlinks followed. What the run header reports, and what fingerprint reads.

Source

pub fn model(&self) -> &str

The model every run from this workspace uses, resolved once.

Source

pub fn provider(&self) -> &str

Source

pub fn context(&self) -> &WorkspaceContext

The context documents discovered at open, weakest precedence first.

Source

pub fn skills(&self) -> &[LoadedSkill]

The skills this workspace registered on the runtime, after layering.

Only what this workspace registered. The registry itself is the runtime’s and additive, so on a shared runtime a run may also be able to load_skill what a sibling workspace registered — an accepted consequence of sharing (see WorkspaceBuilder::open).

Source

pub fn templates(&self) -> &[Template]

The prompt templates this workspace defines, after layering, name-ordered. Over ACP these become the client’s commands.

Source

pub fn mcp_servers(&self) -> &[String]

The MCP servers connected at open, by the names that took effect — which is the configured name unless another workspace on the shared runtime already held it, in which case it carries a deterministic suffix. Names only: nothing here echoes a command or a credential.

Source

pub fn mentra_runtime(&self) -> &Runtime

The mentra runtime the runs are minted on, for a host that wants mentra’s own surface — the task board, teams, the store — alongside basis’s.

The same bargain as PreparedRun::session: basis does not hide mentra, and reaching past basis’s surface is a supported thing to do rather than a workaround. Renamed from runtime() when ADR-0018 gave basis a Runtime of its own, so the name says whose surface comes back.

Trait Implementations§

Source§

impl Debug for Workspace

Hand-written because neither the runtime nor the registration is Debug material, and because the context documents hold whole files — a derived impl would dump them.

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<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, 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