mssf_core/client/
notification.rs1use mssf_com::FabricClient::{
7 IFabricServiceEndpointsVersion, IFabricServiceNotification,
8 IFabricServiceNotificationEventHandler, IFabricServiceNotificationEventHandler_Impl,
9};
10
11use crate::types::{ServicePartitionInformation, Uri};
12
13use super::svc_mgmt_client::ResolvedServiceEndpoint;
14
15pub trait ServiceNotificationEventHandler: 'static {
18 fn on_notification(&self, notification: ServiceNotification) -> crate::Result<()>;
19}
20
21#[derive(Debug, Clone)]
25pub struct ServiceNotification {
26 pub service_name: Uri,
27 pub partition_info: Option<ServicePartitionInformation>,
28 pub partition_id: crate::GUID,
29 pub endpoints: Vec<ResolvedServiceEndpoint>,
30 pub version: Option<ServiceEndpointsVersion>,
31}
32
33impl From<&IFabricServiceNotification> for ServiceNotification {
34 fn from(com: &IFabricServiceNotification) -> Self {
35 let raw = unsafe { com.get_Notification().as_ref().unwrap() };
37 let endpoints = crate::iter::vec_from_raw_com(raw.EndpointCount as usize, raw.Endpoints);
38 let version = unsafe { com.GetVersion() }
39 .ok()
40 .map(ServiceEndpointsVersion::from);
41 Self {
42 service_name: Uri::from(raw.ServiceName),
43 partition_info: unsafe {
44 raw.PartitionInfo
48 .as_ref()
49 .map(ServicePartitionInformation::from)
50 },
51 partition_id: raw.PartitionId,
52 endpoints,
53 version,
54 }
55 }
56}
57
58#[derive(Debug, Clone)]
60pub struct ServiceEndpointsVersion {
61 com: IFabricServiceEndpointsVersion,
62}
63
64impl From<IFabricServiceEndpointsVersion> for ServiceEndpointsVersion {
65 fn from(com: IFabricServiceEndpointsVersion) -> Self {
66 Self { com }
67 }
68}
69
70impl From<ServiceEndpointsVersion> for IFabricServiceEndpointsVersion {
71 fn from(value: ServiceEndpointsVersion) -> Self {
72 value.com
73 }
74}
75
76impl ServiceEndpointsVersion {
77 pub fn compare(&self, other: &ServiceEndpointsVersion) -> crate::Result<i32> {
84 unsafe { self.com.Compare(&other.com) }.map_err(crate::Error::from)
85 }
86}
87
88impl PartialEq for ServiceEndpointsVersion {
89 fn eq(&self, other: &Self) -> bool {
90 match self.compare(other) {
91 Ok(i) => i == 0,
92 Err(_) => false, }
94 }
95}
96
97impl PartialOrd for ServiceEndpointsVersion {
98 fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering> {
102 match self.compare(other) {
103 Ok(i) => Some(i.cmp(&0)),
104 Err(_) => None,
106 }
107 }
108}
109
110#[windows_core::implement(IFabricServiceNotificationEventHandler)]
112#[allow(non_camel_case_types)] pub struct ServiceNotificationEventHandlerBridge<T>
114where
115 T: ServiceNotificationEventHandler,
116{
117 inner: T,
118}
119
120impl<T> ServiceNotificationEventHandlerBridge<T>
121where
122 T: ServiceNotificationEventHandler,
123{
124 pub fn new(inner: T) -> Self {
125 Self { inner }
126 }
127
128 pub fn new_com(inner: T) -> IFabricServiceNotificationEventHandler {
129 Self::new(inner).into()
130 }
131}
132
133impl<T> IFabricServiceNotificationEventHandler_Impl
134 for ServiceNotificationEventHandlerBridge_Impl<T>
135where
136 T: ServiceNotificationEventHandler,
137{
138 fn OnNotification(
139 &self,
140 notification: windows_core::Ref<IFabricServiceNotification>,
141 ) -> crate::WinResult<()> {
142 let com = notification.unwrap();
143 let msg = ServiceNotification::from(com);
144 self.inner
145 .on_notification(msg)
146 .map_err(crate::WinError::from)
147 }
148}
149
150pub struct LambdaServiceNotificationHandler<T>
155where
156 T: Fn(ServiceNotification) -> crate::Result<()> + 'static,
157{
158 f: T,
159}
160
161impl<T> LambdaServiceNotificationHandler<T>
162where
163 T: Fn(ServiceNotification) -> crate::Result<()> + 'static,
164{
165 pub fn new(f: T) -> Self {
166 Self { f }
167 }
168}
169
170impl<T> ServiceNotificationEventHandler for LambdaServiceNotificationHandler<T>
171where
172 T: Fn(ServiceNotification) -> crate::Result<()> + 'static,
173{
174 fn on_notification(&self, notification: ServiceNotification) -> crate::Result<()> {
175 (self.f)(notification)
176 }
177}