Skip to main content

systemprompt_models/bridge/manifest/
entries.rs

1//! Catalogue entries carried inside a [`super::SignedManifest`]: plugins,
2//! skills, rules, agents, hooks and library artifacts.
3//!
4//! Copyright (c) systemprompt.io — Business Source License 1.1.
5//! See <https://systemprompt.io> for licensing details.
6
7use serde::{Deserialize, Serialize};
8
9use crate::bridge::ids::{
10    LibraryArtifactId, PluginId, RuleId, RuleName, Sha256Digest, SkillId, SkillName,
11};
12use crate::services::hooks::{HookCategory, HookEvent};
13use crate::services::plugin::{PluginComponentRef, PluginHooksRef};
14use systemprompt_identifiers::{AgentId, AgentName, HookId, ModelId, ProviderId};
15
16#[derive(Debug, Clone, Serialize, Deserialize)]
17pub struct PluginEntry {
18    pub id: PluginId,
19    pub version: String,
20    pub sha256: Sha256Digest,
21    pub files: Vec<PluginFile>,
22    #[serde(default)]
23    pub hooks: PluginHooksRef,
24}
25
26#[derive(Debug, Clone, Serialize, Deserialize)]
27pub struct PluginFile {
28    pub path: String,
29    pub sha256: Sha256Digest,
30    pub size: u64,
31}
32
33/// A Cowork-native library document (raw HTML in the desktop app's Artifacts
34/// library) — not one of the in-chat MCP artifacts in [`crate::artifacts`].
35#[derive(Debug, Clone, Serialize, Deserialize)]
36pub struct ArtifactEntry {
37    pub id: LibraryArtifactId,
38    pub name: String,
39    pub description: String,
40    pub version: String,
41    pub mcp_tools: Vec<String>,
42    pub content: String,
43    pub starred: bool,
44    pub sha256: Sha256Digest,
45    #[serde(default, skip_serializing_if = "Vec::is_empty")]
46    pub plugins: Vec<PluginId>,
47}
48
49#[derive(Debug, Clone, Serialize, Deserialize)]
50pub struct SkillEntry {
51    #[serde(default, skip_serializing_if = "Option::is_none")]
52    pub publication: Option<SkillPublication>,
53    pub id: SkillId,
54    pub name: SkillName,
55    pub description: String,
56    pub file_path: String,
57    #[serde(default)]
58    pub tags: Vec<String>,
59    pub sha256: Sha256Digest,
60    pub instructions: String,
61    #[serde(default, skip_serializing_if = "Vec::is_empty")]
62    pub hosts: Vec<String>,
63    #[serde(default, skip_serializing_if = "Vec::is_empty")]
64    pub plugins: Vec<PluginId>,
65}
66
67/// Exact signed publication identity shared by every host projection. This is
68/// distribution evidence, not proof that a host installed or invoked the skill.
69#[derive(Debug, Clone, Serialize, Deserialize)]
70pub struct SkillPublication {
71    pub publication_id: systemprompt_identifiers::PublicationId,
72    pub resource_id: systemprompt_identifiers::ManagedResourceId,
73    pub revision_id: systemprompt_identifiers::ResourceRevisionId,
74    pub generation: i64,
75    pub bundle_digest: Sha256Digest,
76}
77
78#[derive(Debug, Clone, Serialize, Deserialize)]
79pub struct RuleEntry {
80    pub id: RuleId,
81    pub name: RuleName,
82    pub description: String,
83    pub file_path: String,
84    #[serde(default)]
85    pub tags: Vec<String>,
86    pub sha256: Sha256Digest,
87    pub instructions: String,
88    #[serde(default, skip_serializing_if = "Vec::is_empty")]
89    pub hosts: Vec<String>,
90    #[serde(default, skip_serializing_if = "Vec::is_empty")]
91    pub plugins: Vec<PluginId>,
92}
93
94#[derive(Debug, Clone, Serialize, Deserialize)]
95pub struct AgentEntry {
96    pub id: AgentId,
97    pub name: AgentName,
98    pub display_name: String,
99    pub description: String,
100    pub version: String,
101    pub endpoint: String,
102    pub enabled: bool,
103    pub is_default: bool,
104    pub is_primary: bool,
105    #[serde(default)]
106    pub provider: Option<ProviderId>,
107    #[serde(default)]
108    pub model: Option<ModelId>,
109    #[serde(default)]
110    pub mcp_servers: PluginComponentRef,
111    #[serde(default)]
112    pub skills: PluginComponentRef,
113    #[serde(default)]
114    pub tags: Vec<String>,
115    #[serde(default)]
116    pub system_prompt: Option<String>,
117}
118
119#[derive(Debug, Clone, Serialize, Deserialize)]
120pub struct HookEntry {
121    pub id: HookId,
122    pub name: String,
123    pub description: String,
124    pub version: String,
125    pub event: HookEvent,
126    pub matcher: String,
127    pub command: String,
128    #[serde(default)]
129    pub is_async: bool,
130    pub category: HookCategory,
131    #[serde(default)]
132    pub tags: Vec<String>,
133    pub sha256: Sha256Digest,
134}