fission_core/
platform_clipboard.rs1use crate::capability::{CapabilityType, OperationCapability};
4use serde::{Deserialize, Serialize};
5
6#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
7pub struct ClipboardText {
8 pub text: Option<String>,
9}
10
11#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
12pub struct ClipboardWriteTextRequest {
13 pub text: String,
14}
15
16#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
17pub struct ClipboardItem {
18 pub content_type: String,
19 pub bytes: Vec<u8>,
20 pub suggested_name: Option<String>,
21}
22
23#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
24pub struct ClipboardContent {
25 pub items: Vec<ClipboardItem>,
26}
27
28#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
29pub struct ClipboardError {
30 pub code: String,
31 pub message: String,
32}
33
34impl ClipboardError {
35 pub fn new(code: impl Into<String>, message: impl Into<String>) -> Self {
42 Self {
43 code: code.into(),
44 message: message.into(),
45 }
46 }
47
48 pub fn unsupported(operation: impl Into<String>) -> Self {
54 Self::new(
55 "unsupported",
56 format!(
57 "clipboard operation `{}` is not supported by this host",
58 operation.into()
59 ),
60 )
61 }
62}
63
64pub struct ReadClipboardTextCapability;
65impl OperationCapability for ReadClipboardTextCapability {
66 type Request = ();
67 type Ok = ClipboardText;
68 type Err = ClipboardError;
69}
70
71pub struct WriteClipboardTextCapability;
72impl OperationCapability for WriteClipboardTextCapability {
73 type Request = ClipboardWriteTextRequest;
74 type Ok = ();
75 type Err = ClipboardError;
76}
77
78pub struct ReadClipboardContentCapability;
79impl OperationCapability for ReadClipboardContentCapability {
80 type Request = ();
81 type Ok = ClipboardContent;
82 type Err = ClipboardError;
83}
84
85pub struct WriteClipboardContentCapability;
86impl OperationCapability for WriteClipboardContentCapability {
87 type Request = ClipboardContent;
88 type Ok = ();
89 type Err = ClipboardError;
90}
91
92pub struct ClearClipboardCapability;
93impl OperationCapability for ClearClipboardCapability {
94 type Request = ();
95 type Ok = ();
96 type Err = ClipboardError;
97}
98
99pub const READ_CLIPBOARD_TEXT: CapabilityType<ReadClipboardTextCapability> =
100 CapabilityType::new("fission.clipboard.read_text");
101pub const WRITE_CLIPBOARD_TEXT: CapabilityType<WriteClipboardTextCapability> =
102 CapabilityType::new("fission.clipboard.write_text");
103pub const READ_CLIPBOARD_CONTENT: CapabilityType<ReadClipboardContentCapability> =
104 CapabilityType::new("fission.clipboard.read_content");
105pub const WRITE_CLIPBOARD_CONTENT: CapabilityType<WriteClipboardContentCapability> =
106 CapabilityType::new("fission.clipboard.write_content");
107pub const CLEAR_CLIPBOARD: CapabilityType<ClearClipboardCapability> =
108 CapabilityType::new("fission.clipboard.clear");
109
110#[cfg(test)]
111mod tests {
112 use super::*;
113
114 #[test]
115 fn clipboard_text_round_trips() {
116 let request = ClipboardWriteTextRequest {
117 text: "copy me".into(),
118 };
119 let bytes = serde_json::to_vec(&request).unwrap();
120 let decoded: ClipboardWriteTextRequest = serde_json::from_slice(&bytes).unwrap();
121 assert_eq!(decoded, request);
122 }
123
124 #[test]
125 fn clipboard_content_round_trips() {
126 let content = ClipboardContent {
127 items: vec![ClipboardItem {
128 content_type: "text/plain".into(),
129 bytes: b"copy me".to_vec(),
130 suggested_name: None,
131 }],
132 };
133 let bytes = serde_json::to_vec(&content).unwrap();
134 let decoded: ClipboardContent = serde_json::from_slice(&bytes).unwrap();
135 assert_eq!(decoded, content);
136 }
137}