android_manifest/
service.rs

1use crate::VarOrBool;
2
3use super::intent_filter::IntentFilter;
4use super::meta_data::MetaData;
5use super::resources::{
6    MipmapOrDrawableResource, Resource, StringResource, StringResourceOrString,
7};
8use serde::{Deserialize, Serialize};
9
10/// Declares a service (a [`Service`] subclass) as one of the application's components.
11///
12/// Unlike activities, services lack a visual user interface. They're used to implement
13/// long-running background operations or a rich communications API that can be called by
14/// other applications. All services must be represented by `<service>` elements in the
15/// manifest file. Any that are not declared there will not be seen by the system and will
16/// never be run.
17///
18/// ## Note
19/// On Android 8.0 (API level 26) and higher, the system places limitations on what your
20/// app can do while it's running in the background. For more information, see the guides
21/// that discuss [`background execution limits`] and [`background location limits`].
22///
23/// ## XML Syntax
24/// ```xml
25/// <service android:description="string resource"
26///          android:directBootAware=["true" | "false"]
27///          android:enabled=["true" | "false"]
28///          android:exported=["true" | "false"]
29///          android:foregroundServiceType=["camera" | "connectedDevice" |
30///                                        "dataSync" | "location" | "mediaPlayback" |
31///                                        "mediaProjection" | "microphone" | "phoneCall"]
32///          android:icon="drawable resource"
33///          android:isolatedProcess=["true" | "false"]
34///          android:label="string resource"
35///          android:name="string"
36///          android:permission="string"
37///          android:process="string" >
38///             ...
39/// </service>
40/// ```
41///
42/// ## Contained in
43/// * [`<application>`]
44///
45/// ## Can contain
46/// * [`<intent-filter>`]
47/// * [`<meta-data>`]
48///
49/// ## introduced in
50/// API Level 1
51///
52/// [`Service`]: https://developer.android.com/reference/android/app/Service
53/// [`background execution limits`]: https://developer.android.com/about/versions/oreo/background
54/// [`background location limits`]: https://developer.android.com/about/versions/oreo/background-location-limits
55/// [`<application>`]: crate::Application
56/// [`<intent-filter>`]: crate::IntentFilter
57/// [`<meta-data>`]: crate::MetaData
58#[derive(
59    Debug, Deserialize, Serialize, YaSerialize, YaDeserialize, PartialEq, Eq, Default, Clone,
60)]
61pub struct Service {
62    /// A string that describes the service to users. The label should be set as a
63    /// reference to a string resource, so that it can be localized like other strings
64    /// in the user interface.
65    #[yaserde(attribute, prefix = "android")]
66    pub description: Option<Resource<StringResource>>,
67    /// Whether or not the service is direct-boot aware; that is, whether or not it can
68    /// run before the user unlocks the device.
69    ///
70    /// ## Note
71    /// During [`Direct Boot`], a service in your application can only access the data
72    /// that is stored in device protected storage.
73    ///
74    /// The default value is `"false"`.
75    ///
76    /// [`Direct Boot`]: https://developer.android.com/training/articles/direct-boot
77    #[yaserde(attribute, prefix = "android", rename = "directBootAware")]
78    pub direct_boot_aware: Option<VarOrBool>,
79    /// Whether or not the service can be instantiated by the system — `"true"` if it can
80    /// be, and `"false"` if not. The default value is `"true"`.
81    ///
82    /// The [`<application>`] element has its own [`enabled`] attribute that applies to
83    /// all application components, including services. The [`<application>`] and
84    /// <service> attributes must both be `"true"` (as they both are by default) for
85    /// the service to be enabled. If either is `"false"`, the service is disabled; it
86    /// cannot be instantiated.
87    ///
88    /// [`<application>`]: crate::Application
89    /// [`enabled`]: crate::Application#structfield.enabled
90    #[yaserde(attribute, prefix = "android")]
91    pub enabled: Option<VarOrBool>,
92    /// Whether or not components of other applications can invoke the service or interact
93    /// with it — `"true"` if they can, and `"false"` if not. When the value is
94    /// `"false"`, only components of the same application or applications with the
95    /// same user ID can start the service or bind to it.
96    ///
97    /// The default value depends on
98    /// whether the service contains intent filters. The absence of any filters means
99    /// that it can be invoked only by specifying its exact class name. This implies
100    /// that the service is intended only for application-internal use (since others
101    /// would not know the class name).So in this case, the default value is
102    /// `"false"`. On the other hand, the presence of at least one filter implies that
103    /// the service is intended for external use, so the default value is `"true"`.
104    ///
105    /// This attribute is not the only way to limit the exposure of a service to
106    /// other applications. You can also use a permission to limit the
107    /// external entities that can interact with the service (see the
108    /// [`permission`] attribute).
109    ///
110    /// [`permission`]: crate::Service#structfield.enabled
111    #[yaserde(attribute, prefix = "android")]
112    pub exported: Option<VarOrBool>,
113    /// Specify that the service is a [`foreground service`] that satisfies a particular
114    /// use case. For example, a foreground service type of `"location"` indicates
115    /// that an app is getting the device's current location, usually to [`continue a
116    /// user-initiated action`] related to device location.
117    ///
118    /// You can assign multiple foreground service types to a particular service.
119    ///
120    /// [`foreground service`]: https://developer.android.com/guide/components/services
121    /// [`continue a user-initiated action`]: https://developer.android.com/training/location/background#continue-user-initiated-action
122    #[yaserde(attribute, prefix = "android", rename = "foregroundServiceType")]
123    pub foreground_service_type: Option<ForegroundServiceType>,
124    /// An icon representing the service. This attribute must be set as a reference to a
125    /// drawable resource containing the image definition. If it is not set, the icon
126    /// specified for the application as a whole is used instead (see the
127    /// [`<application>`] element's [`icon`](crate::Application#structfield.icon)
128    /// attribute).
129    ///
130    /// The service's icon — whether set here or by the [`<application>`] element — is
131    /// also the default icon for all the service's intent filters (see the
132    /// [`<intent-filter>`] element's [`icon`](crate::IntentFilter#structfield.icon)
133    /// attribute).
134    ///
135    /// [`<application>`]: crate::Application
136    /// [`<intent-filter>`]: crate::IntentFilter
137    #[yaserde(attribute, prefix = "android")]
138    pub icon: Option<MipmapOrDrawableResource>,
139    /// If set to true, this service will run under a special process that is isolated
140    /// from the rest of the system and has no permissions of its own.
141    /// The only communication with it is through the Service API (binding and
142    /// starting).
143    #[yaserde(attribute, prefix = "android", rename = "isolatedProcess")]
144    pub isolated_process: Option<VarOrBool>,
145    /// A name for the service that can be displayed to users. If this attribute is not
146    /// set, the label set for the application as a whole is used instead
147    /// (see the [`<application>`] element's
148    /// [`label`](crate::Application#structfield.label) attribute).
149    ///
150    /// The service's label — whether set here or by the [`<application>`] element — is
151    /// also the default label for all the service's intent filters (see the
152    /// [`<intent-filter>`] element's [`label`](crate::IntentFilter#structfield.label)
153    /// attribute).
154    ///
155    /// The label should be set as a reference to a string resource, so that it can be
156    /// localized like other strings in the user interface. However, as a convenience
157    /// while you're developing the application, it can also be set as a raw string.
158    ///
159    /// [`<application>`]: crate::Application
160    /// [`<intent-filter>`]: crate::IntentFilter
161    #[yaserde(attribute, prefix = "android")]
162    pub label: Option<StringResourceOrString>,
163    /// The name of the [`Service`] subclass that implements the service. This should be a
164    /// fully qualified class name (such as, `"com.example.project.RoomService"`).
165    /// However, as a shorthand, if the first character of the name is a period (for
166    /// example, `".RoomService"`), it is appended to the package name specified in
167    /// the [`<manifest>`] element.
168    ///
169    /// Once you publish your application, you [`should not change this name`] (unless
170    /// you've set [`android:exported="false"`]).
171    ///
172    /// There is no default. The name must be specified.
173    ///
174    /// [`Service`]: https://developer.android.com/reference/android/app/Service
175    /// [`<manifest>`]: crate::AndroidManifest
176    /// [`should not change this name`]: https://android-developers.googleblog.com/2011/06/things-that-cannot-change.html
177    /// [`android:exported="false"`]: crate::Service#structfield.exported
178    #[yaserde(attribute, prefix = "android")]
179    pub name: String,
180    /// The name of a permission that an entity must have in order to launch the service
181    /// or bind to it. If a caller of [`startService()`], [`bindService()`],
182    /// or [`stopService()`] has not been granted this permission, the method
183    /// will not work and the Intent object will not be delivered to the
184    /// service.
185    ///
186    /// If this attribute is not set, the permission set by the [`<application>`]
187    /// element's [`permission`] attribute applies to the service. If neither
188    /// attribute is set, the service is not protected by a permission.
189    ///
190    /// For more information on permissions, see the [`Permissions`] section in the
191    /// introduction and a separate document, [`Security and Permissions`].
192    ///
193    /// [`startService()`]: https://developer.android.com/reference/android/content/Context#startService(android.content.Intent)
194    /// [`bindService()`]: https://developer.android.com/reference/android/content/Context#bindService(android.content.Intent,%20android.content.ServiceConnection,%20int)
195    /// [`stopService()`]: https://developer.android.com/reference/android/content/Context#stopService(android.content.Intent)
196    /// [`<application>`]: crate::Application
197    /// [`Security and Permissions`]: https://developer.android.com/training/articles/security-tips
198    /// [`permission`]: crate::Application#structfield.permission
199    /// [`Permissions`]: https://developer.android.com/guide/topics/manifest/manifest-intro#perms
200    #[yaserde(attribute, prefix = "android")]
201    pub permission: Option<String>,
202    /// The name of the process where the service is to run. Normally, all components of
203    /// an application run in the default process created for the application. It has
204    /// the same name as the application package. The [`<application>`] element's
205    /// [`process`] attribute can set a different default for all components. But
206    /// component can override the default with its own process attribute, allowing
207    /// you to spread your application across multiple processes.
208    ///
209    /// If the name assigned to this attribute begins with a colon `(':')`, a new process,
210    /// private to the application, is created when it's needed and the service runs
211    /// in that process. If the process name begins with a lowercase character, the
212    /// service will run in a global process of that name, provided that it has
213    /// permission to do so. This allows components in different applications to share
214    /// a process, reducing resource usage.
215    ///
216    /// [`<application>`]: crate::Application
217    /// [`process`]: crate::Application#structfield.process
218    #[yaserde(attribute, prefix = "android")]
219    pub process: Option<String>,
220    #[yaserde(rename = "intent-filter")]
221    #[serde(default, skip_serializing_if = "Vec::is_empty")]
222    pub intent_filter: Vec<IntentFilter>,
223    #[yaserde(rename = "meta-data")]
224    #[serde(default, skip_serializing_if = "Vec::is_empty")]
225    pub meta_data: Vec<MetaData>,
226}
227
228#[derive(Debug, Deserialize, Serialize, YaSerialize, YaDeserialize, PartialEq, Eq, Clone)]
229#[serde(rename_all = "camelCase")]
230#[derive(Default)]
231pub enum ForegroundServiceType {
232    #[yaserde(rename = "camera")]
233    #[default]
234    Camera,
235    #[yaserde(rename = "connectedDevice")]
236    ConnectedDevice,
237    #[yaserde(rename = "dataSync")]
238    DataSync,
239    #[yaserde(rename = "location")]
240    Location,
241    #[yaserde(rename = "mediaPlayback")]
242    MediaPlayback,
243    #[yaserde(rename = "mediaProjection")]
244    MediaProjection,
245    #[yaserde(rename = "microphone")]
246    Microphone,
247    #[yaserde(rename = "phoneCall")]
248    PhoneCall,
249}