tauri_plugin_android_fs/
models.rs

1use std::time::SystemTime;
2use serde::{Deserialize, Serialize};
3
4
5/// Path to represent a file or directory.
6/// 
7/// # Note
8/// For compatibility, an interconversion to [`tauri_plugin_fs::FilePath`] is implemented, such as follwing. 
9/// This may be lossy and also not guaranteed to work properly with other plugins. 
10/// But at least, it can be used with [`convertFileSrc`](https://v2.tauri.app/reference/javascript/api/namespacecore/#convertfilesrc).
11/// ```no_run
12/// use tauri_plugin_android_fs::FileUri;
13/// use tauri_plugin_fs::FilePath;
14/// 
15/// let uri: FileUri = unimplemented!();
16/// 
17/// // this can use with convertFileSrc on frontend
18/// let path: FilePath = uri.into();
19/// 
20/// let uri: FileUri = path.into();
21/// ```
22/// 
23/// # Typescript type
24/// You should use the following type because it might change in the future, and the inner value should not be used directly.  
25/// ```typescript
26/// type FileUri = any
27/// type FileUri = string
28/// ```
29#[derive(Debug, Clone, Hash, PartialEq, Eq, Deserialize, Serialize)]
30#[serde(rename_all = "camelCase")]
31pub struct FileUri {
32    pub(crate) uri: String,
33    pub(crate) document_top_tree_uri: Option<String>,
34}
35
36impl From<tauri_plugin_fs::FilePath> for FileUri {
37
38    fn from(value: tauri_plugin_fs::FilePath) -> Self {
39        let uri = match value {
40            tauri_plugin_fs::FilePath::Url(url) => url.to_string(),
41            tauri_plugin_fs::FilePath::Path(path_buf) => format!("file://{}", path_buf.to_string_lossy()),
42        };
43
44        Self { uri, document_top_tree_uri: None }
45    }
46}
47
48impl From<FileUri> for tauri_plugin_fs::FilePath {
49
50    fn from(value: FileUri) -> Self {
51        let result: std::result::Result<_, std::convert::Infallible> = value.uri.parse();
52
53        // This will not cause panic. Because result err is infallible.
54        result.unwrap()
55    }
56}
57
58#[derive(Debug, Clone, Hash, PartialEq, Eq, Deserialize, Serialize)]
59#[serde(rename_all = "camelCase")]
60pub enum Entry {
61
62    #[non_exhaustive]
63    File {
64        name: String,
65        uri: FileUri,
66        last_modified: SystemTime,
67        byte_size: u64,
68        mime_type: String,
69    },
70
71    #[non_exhaustive]
72    Dir {
73        name: String,
74        uri: FileUri,
75        last_modified: SystemTime,
76    }
77}
78
79/// Access mode
80#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
81pub enum PersistableAccessMode {
82
83    /// Read-only access.
84    ReadOnly,
85
86    /// Write-only access.
87    WriteOnly,
88
89    /// Read-write access.
90    ReadAndWrite,
91}
92
93/// Access mode
94#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
95#[non_exhaustive]
96pub enum FileAccessMode {
97
98    /// Opens the file in read-only mode.
99    /// 
100    /// FileDescriptor mode: "r"
101    Read,
102
103    /// Opens the file in write-only mode.
104    /// **This may or may not truncate.**
105    /// So please use `WriteTruncate` or `WriteAppend` instead.
106    ///
107    /// FileDescriptor mode: "w"
108    Write,
109
110    /// Opens the file in write-only mode.
111    /// The existing content is truncated (deleted), and new data is written from the beginning.
112    /// Creates a new file if it does not exist.
113    ///
114    /// FileDescriptor mode: "wt"
115    WriteTruncate,
116
117    /// Opens the file in write-only mode.
118    /// The existing content is preserved, and new data is appended to the end of the file.
119    /// Creates a new file if it does not exist.
120    /// 
121    /// FileDescriptor mode: "wa"
122    WriteAppend,
123
124    /// Opens the file in read-write mode.  
125    /// 
126    /// FileDescriptor mode: "rw"
127    ReadWrite,
128
129    /// Opens the file in read-write mode.
130    /// The existing content is truncated (deleted), and new data is written from the beginning.
131    /// Creates a new file if it does not exist.
132    ///
133    /// FileDescriptor mode: "rwt"
134    ReadWriteTruncate,
135}
136
137/// Filters for VisualMediaPicker.
138#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
139pub enum VisualMediaTarget {
140
141    /// Allow only images to be selected.  
142    ImageOnly,
143
144    /// Allow only videos to be selected.  
145    VideoOnly,
146
147    /// Allow only images and videos to be selected.  
148    ImageAndVideo
149}
150
151/// The application specific directory.  
152#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
153#[non_exhaustive]
154pub enum PrivateDir {
155
156    /// The application specific persistent-data directory.  
157    /// 
158    /// The system prevents other apps from accessing these locations, and on Android 10 (API level 29) and higher, these locations are encrypted.  
159    ///  
160    /// These files will be deleted when the app is uninstalled and may also be deleted at the user’s request.  
161    /// 
162    /// ex: `/data/user/0/{app-package-name}/files`
163    Data,
164
165    /// The application specific cache directory.  
166    /// 
167    /// The system prevents other apps from accessing these locations, and on Android 10 (API level 29) and higher, these locations are encrypted.  
168    /// 
169    /// These files will be deleted when the app is uninstalled and may also be deleted at the user’s request. 
170    /// In addition, the system will automatically delete files in this directory as disk space is needed elsewhere on the device.  
171    /// 
172    /// ex: `/data/user/0/{app-package-name}/cache`
173    Cache,
174}
175
176#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
177#[non_exhaustive]
178pub enum PublicDir {
179    
180    #[serde(untagged)]
181    Image(PublicImageDir),
182
183    #[serde(untagged)]
184    Video(PublicVideoDir),
185
186    #[serde(untagged)]
187    Audio(PublicAudioDir),
188
189    #[serde(untagged)]
190    GeneralPurpose(PublicGeneralPurposeDir),
191}
192
193/// Directory in which to place images that are available to other applications and users.  
194#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
195#[non_exhaustive]
196pub enum PublicImageDir {
197
198    /// Standard directory in which to place pictures that are available to the user.  
199    /// 
200    /// ex: `~/Pictures/{app_name}`
201    Pictures,
202
203    /// The traditional location for pictures and videos when mounting the device as a camera.  
204    /// 
205    /// ex: `~/DCIM/{app_name}`
206    DCIM,
207}
208
209/// Directory in which to place videos that are available to other applications and users.  
210#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
211#[non_exhaustive]
212pub enum PublicVideoDir {
213
214	/// Standard directory in which to place movies that are available to the user.  
215	/// 
216	/// ex: `~/Movies/{app_name}`
217	Movies,
218
219	/// The traditional location for pictures and videos when mounting the device as a camera.  
220	/// 
221	/// ex: `~/DCIM/{app_name}`
222	DCIM,
223}
224
225/// Directory in which to place audios that are available to other applications and users.  
226#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
227#[non_exhaustive]
228pub enum PublicAudioDir {
229
230    /// Standard directory in which to place movies that are available to the user.  
231    /// 
232    /// ex: `~/Music/{app_name}`
233    Music,
234
235    /// Standard directory in which to place any audio files that should be in the list of alarms that the user can select (not as regular music).  
236    /// 
237    /// ex: `~/Alarms/{app_name}`
238    Alarms,
239
240    /// Standard directory in which to place any audio files that should be in the list of audiobooks that the user can select (not as regular music).  
241    /// 
242    /// This is not available on Android 9 (API level 28) and lower.  
243    /// 
244    /// ex: `~/Audiobooks/{app_name}`  
245    Audiobooks,
246
247    /// Standard directory in which to place any audio files that should be in the list of notifications that the user can select (not as regular music).  
248    /// 
249    /// ex: `~/Notifications/{app_name}`
250    Notifications,
251
252    /// Standard directory in which to place any audio files that should be in the list of podcasts that the user can select (not as regular music).  
253    /// 
254    /// ex: `~/Podcasts/{app_name}`
255    Podcasts,
256
257    /// Standard directory in which to place any audio files that should be in the list of ringtones that the user can select (not as regular music).  
258    /// 
259    /// ex: `~/Ringtones/{app_name}`
260    Ringtones,
261
262    /// Standard directory in which to place any audio files that should be in the list of voice recordings recorded by voice recorder apps that the user can select (not as regular music).   
263    /// 
264    /// This is not available on Android 11 (API level 30) and lower.  
265    /// 
266    /// ex: `~/Recordings/{app_name}`
267    Recordings,
268}
269
270/// Directory in which to place files that are available to other applications and users.  
271#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq, Deserialize, Serialize)]
272#[non_exhaustive]
273pub enum PublicGeneralPurposeDir {
274
275    /// Standard directory in which to place documents that have been created by the user.  
276    /// 
277    /// ex: `~/Documents/{app_name}`
278    Documents,
279
280    /// Standard directory in which to place files that have been downloaded by the user.  
281    /// 
282    /// ex: `~/Download/{app_name}`  
283    Download,
284}
285
286
287macro_rules! impl_into_pubdir {
288    ($target: ident, $wrapper: ident) => {
289        impl From<$target> for PublicDir {
290            fn from(value: $target) -> Self {
291                Self::$wrapper(value)
292            }
293        }
294    };
295}
296impl_into_pubdir!(PublicImageDir, Image);
297impl_into_pubdir!(PublicVideoDir, Video);
298impl_into_pubdir!(PublicAudioDir, Audio);
299impl_into_pubdir!(PublicGeneralPurposeDir, GeneralPurpose);