systemprompt_runtime/
context_traits.rs1use std::sync::Arc;
10
11use systemprompt_analytics::{AnalyticsService, FingerprintRepository};
12use systemprompt_extension::{
13 Extension, ExtensionContext, HasAnalytics, HasFingerprint, HasRouteClassifier, HasUserService,
14};
15use systemprompt_models::RouteClassifier;
16use systemprompt_traits::{
17 AnalyticsProvider, AppContext as AppContextTrait, ConfigProvider, DatabaseHandle,
18 FingerprintProvider, UserProvider,
19};
20use systemprompt_users::UserService;
21
22use crate::AppContext;
23
24impl AppContextTrait for AppContext {
25 fn config(&self) -> Arc<dyn ConfigProvider> {
26 let concrete = Arc::clone(&self.cfg.config);
27 let provider: Arc<dyn ConfigProvider> = concrete;
28 provider
29 }
30
31 fn database_handle(&self) -> Arc<dyn DatabaseHandle> {
32 let concrete = Arc::clone(&self.data.database);
33 let handle: Arc<dyn DatabaseHandle> = concrete;
34 handle
35 }
36
37 fn session_provider(&self) -> Option<Arc<dyn systemprompt_traits::SessionProvider>> {
38 Some(self.session_store())
39 }
40
41 fn analytics_provider(&self) -> Option<Arc<dyn AnalyticsProvider>> {
42 let concrete = Arc::clone(&self.data.analytics_service);
43 let provider: Arc<dyn AnalyticsProvider> = concrete;
44 Some(provider)
45 }
46
47 fn fingerprint_provider(&self) -> Option<Arc<dyn FingerprintProvider>> {
48 let concrete = Arc::clone(self.data.fingerprint_repo.as_ref()?);
49 let provider: Arc<dyn FingerprintProvider> = concrete;
50 Some(provider)
51 }
52
53 fn user_provider(&self) -> Option<Arc<dyn UserProvider>> {
54 let concrete = Arc::clone(self.data.user_service.as_ref()?);
55 let provider: Arc<dyn UserProvider> = concrete;
56 Some(provider)
57 }
58}
59
60impl ExtensionContext for AppContext {
61 fn system_owner_id(&self) -> systemprompt_identifiers::UserId {
62 self.system_admin().id().clone()
63 }
64
65 fn config(&self) -> Arc<dyn ConfigProvider> {
66 let concrete = Arc::clone(&self.cfg.config);
67 let provider: Arc<dyn ConfigProvider> = concrete;
68 provider
69 }
70
71 fn database(&self) -> Arc<dyn DatabaseHandle> {
72 let concrete = Arc::clone(&self.data.database);
73 let handle: Arc<dyn DatabaseHandle> = concrete;
74 handle
75 }
76
77 fn file_storage(&self) -> Arc<dyn systemprompt_traits::FileStorage> {
78 Arc::clone(Self::file_storage(self))
79 }
80
81 fn instance_id(&self) -> systemprompt_identifiers::InstanceId {
82 self.config().instance_id.clone()
83 }
84
85 fn instances(&self) -> systemprompt_traits::DynInstanceRegistry {
86 let concrete = Arc::clone(self.service_repository());
87 let registry: systemprompt_traits::DynInstanceRegistry = concrete;
88 registry
89 }
90
91 fn leases(&self) -> systemprompt_traits::DynLeaseRepository {
92 let concrete = Arc::clone(&self.coordination_repositories().leases);
93 let leases: systemprompt_traits::DynLeaseRepository = concrete;
94 leases
95 }
96
97 fn advisory_locks(&self) -> systemprompt_traits::DynAdvisoryLocks {
98 let concrete = Arc::clone(&self.coordination_repositories().locks);
99 let locks: systemprompt_traits::DynAdvisoryLocks = concrete;
100 locks
101 }
102
103 fn secret(&self, name: &str) -> Option<systemprompt_traits::ExtensionSecret> {
104 let secrets = match systemprompt_config::SecretsBootstrap::get() {
105 Ok(secrets) => secrets,
106 Err(error) => {
107 tracing::warn!(%error, secret = name, "extension secret requested before secrets loaded");
108 return None;
109 },
110 };
111 secrets
112 .custom_secret(name)
113 .map(|value| systemprompt_traits::ExtensionSecret::new(value.clone()))
114 }
115
116 fn get_extension(&self, id: &str) -> Option<Arc<dyn Extension>> {
117 self.plugins.extension_registry.get(id).cloned()
118 }
119
120 fn config_planes(
121 &self,
122 ) -> systemprompt_provider_contracts::ConfigPlaneResult<crate::ConfigPlaneSet> {
123 Self::config_planes(self)
124 }
125}
126
127impl HasAnalytics for AppContext {
128 type Analytics = Arc<AnalyticsService>;
129
130 fn analytics(&self) -> &Self::Analytics {
131 &self.data.analytics_service
132 }
133}
134
135impl HasFingerprint for AppContext {
136 type Fingerprint = Arc<FingerprintRepository>;
137
138 fn fingerprint(&self) -> Option<&Self::Fingerprint> {
139 self.data.fingerprint_repo.as_ref()
140 }
141}
142
143impl HasUserService for AppContext {
144 type UserService = Arc<UserService>;
145
146 fn user_service(&self) -> Option<&Self::UserService> {
147 self.data.user_service.as_ref()
148 }
149}
150
151impl HasRouteClassifier for AppContext {
152 type RouteClassifier = Arc<RouteClassifier>;
153
154 fn route_classifier(&self) -> &Self::RouteClassifier {
155 &self.cfg.route_classifier
156 }
157}