systemprompt_runtime/managed/
inventory.rs1use super::OrchestrationError;
8use crate::AppContext;
9use systemprompt_identifiers::UserId;
10use systemprompt_marketplace::inventory::{BaselineScope, InventoryService, InventoryStatus};
11pub use systemprompt_marketplace::inventory::{LatestPublication, LatestPublicationStatus};
12
13pub async fn refresh(
14 ctx: &AppContext,
15 owner: &UserId,
16) -> Result<InventoryStatus, OrchestrationError> {
17 let services = load_services(ctx, owner).await?;
18 Ok(
19 InventoryService::new(ctx.managed_repository().as_ref().clone())
20 .refresh(owner, ctx.app_paths().system().services(), &services)
21 .await?,
22 )
23}
24
25pub async fn publish_latest(
26 ctx: &AppContext,
27 owner: &UserId,
28 actor: &UserId,
29) -> Result<Vec<LatestPublication>, OrchestrationError> {
30 let services = load_services(ctx, owner).await?;
31 let service = InventoryService::new(ctx.managed_repository().as_ref().clone());
32 service
33 .refresh(owner, ctx.app_paths().system().services(), &services)
34 .await?;
35 let mut guard = ctx.publish_guard().lock().await;
36 Ok(service
37 .publish_latest(
38 &BaselineScope {
39 owner,
40 actor,
41 root: ctx.app_paths().system().services(),
42 services: &services,
43 },
44 &mut guard,
45 )
46 .await?)
47}
48
49async fn load_services(
50 ctx: &AppContext,
51 owner: &UserId,
52) -> Result<systemprompt_manifest::services::ServicesConfig, OrchestrationError> {
53 match systemprompt_loader::ConfigLoader::load() {
54 Ok(services) => Ok(services),
55 Err(error) => {
56 tracing::warn!(%error, "Configured inventory could not be loaded; previous inventory retained");
57 ctx.managed_repository()
58 .record_inventory_failure(owner)
59 .await?;
60 Err(OrchestrationError::InventoryLoad(error))
61 },
62 }
63}