diff --git a/docs/apple-privacy-manifest.md b/docs/apple-privacy-manifest.md new file mode 100644 index 000000000000..b0d7ab53910c --- /dev/null +++ b/docs/apple-privacy-manifest.md @@ -0,0 +1,263 @@ +# Apple’s privacy manifest policy requirements +Apple is introducing new privacy policies that affect .NET applications targeting macOS, Mac Catalyst, iOS, iPadOS, and tvOS platforms on the App Stores. The policies affect how app developers are expected to disclose how they use any data collected from a users device and why certain APIs are being used. Developers will provide the details for these in a [privacy manifest file][PrivacyManifestFiles] that is included in the application bundle. + +The [data collection](https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_data_use_in_privacy_manifests) policies require you to declare the types of data that you collect and describe the data in a [privacy manifest files][PrivacyManifestFiles]. Apart from how to properly include the [privacy manifest files][PrivacyManifestFiles] in your .NET project, this document does not go into any detail on the data collection settings. The Apple documentation should be sufficient for declaring how your App or framework uses data it collects from users. + +The [Required Reason APIs][RequiredReasonAPI] policy forces app developers to identify certain categories of APIs that their app, or frameworks use and to provide a reason for their use. This information is provided in a [privacy manifest files][PrivacyManifestFiles] along with the data collection information. This document will provide .NET application developers the information needed to provide a `PrivacyInfo.xcprivacy` file with thier .NET applications with the proper policy settings to pass the [Required Reason APIs][RequiredReasonAPI] checks when submitting to the Apple App Stores. + +The privacy manifest file (`PrivacyInfo.xcprivacy`) lists the [types of data](https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_data_use_in_privacy_manifests) your .NET MAUI application, or any third-party SDKs and packages collect, and the reasons for using certain [Required Reason APIs][RequiredReasonAPI] categories. + +**Important:** If the use of the [Required Reason APIs][RequiredReasonAPI] by you or third-party SDKs isn’t declared in the privacy manifest, your application might be rejected by the App Store. For more information, visit Apple’s documentation on [Required Reasons APIs][RequiredReasonAPI]. + +## Prepare your .NET MAUI applications for Apple’s privacy manifest policy +You must review your native code, C# code, and data collection and tracking practices to understand if Apple’s privacy manifest policy applies to you. Follow these guidelines to decide if you need to include a privacy manifest file in your product: + +* If your application includes any third-party SDKs or packages, then these third-party components (if applicable) must provision their own privacy manifest files separately. **Note:** It’s your responsibility however, to make sure that the owners of these third-party components include privacy manifest files. Microsoft isn’t responsible for any third-party privacy manifest, and their data collection and tracking practices. + +* If your application includes the [.NET APIs][C#NETAPIs] that call certain native APIs listed in the Apple’s [Required Reason API][RequiredReasonAPI] categories, then you must assess your product for the API usage. For assessing what constitutes as part of data collection and tracking practices, refer to Apple’s documentation on [privacy manifest files][PrivacyManifestFiles]. **Note:** It’s your responsibility to assess your use of each of these APIs and declare the applicable reasons for using them. + +Depending on whether you’re using [.NET for iOS or .NET MAUI to develop an application](#privacy-manifest-for-net-maui-and-net-for-ios-or-tvos-applications) or providing [ObjectiveC or Swift Binding packages](#privacy-manifest-for-binding-projects) to use with .NET MAUI applications, the requirement for providing a privacy manifest file might differ. + +**Note:** The above guidelines are provided for your convenience. It’s important that you review Apple’s documentation on [privacy manifest files][PrivacyManifestFiles] before creating a privacy manifest for your project. + +**Important:** +The following information is provided based on Apple's documentation as of March 2024. It is recommended that you review Apple’s documentation on [privacy manifest files][PrivacyManifestFiles] when creating a privacy manifest for your project to ensure you are using the most recent guidelines. If you find any discrepancies in the information below, please [file a bug](https://github.com/dotnet/maui/issues) and include the API in question. + +## Privacy manifest for .NET MAUI and .NET for iOS or tvOS applications +If you’re developing an application using .NET MAUI, consider the following steps: + +1. Assess if your native application code uses any of the following APIs: + * APIs listed under the [Required Reason API][RequiredReasonAPI] category. + * The [C# .NET APIs][C#NETAPIs] in .NET MAUI framework. +1. If you meet one or both of the conditions from step 1, or if you have disabled [linking](https://learn.microsoft.com/xamarin/ios/deploy-test/linker?tabs=macos), which will retain all of the [C# .NET APIs][C#NETAPIs], then [create a privacy manifest file](https://developer.apple.com/documentation/bundleresources/privacy_manifest_files#4284009) following the [example](#example) to add a `PrivacyInfo.xcprivacy` file to your project. + +1. In the privacy manifest file, declare the approved reasons for using the [Required Reasons APIs][RequiredReasonAPI] or [C# .NET APIs][C#NETAPIs], as applicable. + +**Important:** If you don’t declare the reasons for the use of APIs, your application might be rejected by the App Store. + +Verify if your native application code collects any type of data [categorized by Apple](https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_data_use_in_privacy_manifests#4250555) and declare those data types in the privacy manifest file as applicable. Any third-party SDKs or packages used in your application must include their own separate manifest files to declare data collection and the use of any [Required Reasons APIs][RequiredReasonAPI] with approved reasons. + +### Notes: + +* It’s your responsibility to check the accuracy of the privacy manifest within the .NET MAUI app and if any third-party components included in your .NET MAUI project require any declarations in you privacy manifest. It’s recommended that you search these third-party components for any references to a privacy manifest declaration. + +* If you’re developing an application using .NET MAUI as a library, check if your native application code collects any of the following information outside of the .NET MAUI project: + * [Data collection](https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_data_use_in_privacy_manifests) + * [Required Reasons APIs][RequiredReasonAPI] + + If it does, then you must declare their usage in the privacy manifest file. + +## Privacy manifest for Binding projects +If you are Binding project owner, and you are binding a xcframework, then the xcframework provider will need to include the `PrivacyInfo.xcprivacy` file as part of the xcframework. Otherwise, there are two options, provide documentation for package consumers to create the `PrivacyInfo.xcprivacy` file properly or change the bindings to bind an xcframework that has the `PrivacyInfo.xcprivacy` file included. It is currently not possible for Binding project authors to include a `PrivacyInfo.xcprivacy` file outside an xcframework that will be recognized by Apple when submitting an app. + +## C# .NET APIs in .NET MAUI +.NET for iOS, tvOS and .NET MAUI build on top of the .NET runtime and BCL. Each SDK's API usages are detailed in the links below. + +* [.NET Runtime and BCL API usages]() +* [.NET for iOS, tvOS and Xamarin.iOS API Usages]() +* [.NET MAUI and Xamarin.Forms API Usages]() + +All .NET Apps that target devices running iOS, iPadOS, or tvOS will require a `PrivacyInfo.xcprivacy` file in the app bundle. This is due to the .NET Runtime and BCL using [Required Reasons APIs][RequiredReasonAPI] that are not removed regardless of the [linking](https://learn.microsoft.com/xamarin/ios/deploy-test/linker?tabs=macos) setting. The following three API categories and their associated reasons must be in the `PrivacyInfo.xcprivacy`. +* NSPrivacyAccessedAPICategoryFileTimestamp - C617.1 +* NSPrivacyAccessedAPICategorySystemBootTime - 35F9.1 +* NSPrivacyAccessedAPICategoryDiskSpace - E174.1 + +Additionally, if you use the `NSUserDefaults` APIs in your app, you will need to add the `NSPrivacyAccessedAPICategoryUserDefaults` API category, with a reason code of `CAS92.1`. + +See the example below for detailed instructions on how to add a `PrivacyInfo.xcprivacy` file to your App. + +# Example +Let's look at how you would add a Privacy Manifest file to an application that uses the following APIs: + +* [NSUserDefaults](https://learn.microsoft.com/dotnet/api/foundation.nsuserdefaults) +* [NSProcessInfo.SystemUptime](https://learn.microsoft.com/dotnet/api/foundation.nsprocessinfo.systemuptime) +* [NSFileManager.ModificationDate](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.modificationdate) + +How they are used is not that important for this example, but the `why` will determine the reason code needed for the privacy manifest. + +## Adding the `PrivacyInfo.xcprivacy` file to your project + +The `PrivacyInfo.xcprivacy` is consider a resource when it is time to build the bundle. In accordance with [Placing Content in a Bundle](https://developer.apple.com/documentation/bundleresources/placing_content_in_a_bundle) the file is placed in the root of the Bundle. Use the proper set of instructions below for your project type: + +### .NET MAUI +1. Creat a new blank file named `PrivacyInfo.xcprivacy` in the `Platforms/iOS` folder in your .NET MAUI project. +1. In your favorite text editor, edit the .NET MAUI csproj project file. +1. Add the following elements to the bottom of the root `` element: + ```xml + + + + ``` + This will package the file into the iOS app at the root of the bundle. + +### .NET for iOS (net?-ios) +1. Creat a new blank file named `PrivacyInfo.xcprivacy` in the `Resources` folder in your .NET for iOS project. This is all that is needed to package the file into the iOS app at the root of the bundle. + +### .NET for tvOS (net?-tvos) +1. Creat a new blank file named `PrivacyInfo.xcprivacy` in the root folder in your .NET for tvOS project. +1. In your favorite text editor, edit the .NET for tvOS csproj project file. +1. Add the following elements to the bottom of the root `` element: + ```xml + + + + ``` + This will package the file into the tvOS app at the root of the bundle. + +### Xamarin.iOS including Xamarin.Forms +1. Creat a new blank file named `PrivacyInfo.xcprivacy` in the root folder of your Xamarin.iOS project. +1. In your favorite text editor, edit the Xamarin.iOS csproj project file. +1. Locate the `` that contains other `` elements and add the following element: + ```xml + + ``` + This will package the file into the iOS app at the root of the bundle. + +Now that the file has been created in the proper location your project, it needs to be ppopulated with the correct settings for your app or framework. + +## Creating the `PrivacyInfo.xcprivacy` file + +We will start by building the contents of the `PrivacyInfo.xcprivacy` file, and then go through each supported platform and how to properly configure your project so the file is included in the bundle properly. + +Since the application is based on .NET, a privacy manifest is required. Let's walkthrough the steps needed to add a privacy manifest that declares our usages of the above three API's. + +1. Open Xcode and either create new `App` project, or open an existing one. +1. In Xcode use the File->New->File menu to open the `Choose a new template for your file:` dialog box. +1. Scroll down until you find the `App Privacy` template. +1. Select the `App Privacy` template and then click `Next` +1. In the `Save As` dialog, leave the filename as `PrivacyInfo` as that is the required name for the file. +1. Click `Create` and close Xcode. +1. Use Finder to copy the `PrivacyInfo.xcprivacy` file from the Xcode project to your documents folder for now. +1. The Xcode project is no longer needed and can be deleted. + +You should now have a file named `PrivacyInfo.xcprivacy` under your documents folder with contents similar to: + +```xml + + + + + + +``` +Use your favorite text editor, like [Visual Studio Code](https://aka.ms/vscode), to open the file for editing. + +You can add the entries for the APIs usage to the `PrivacyInfo.xcproject` as follows: + +1. Edit the `PrivacyInfo.xcprivacy` file to appear as follows: + ```xml + + + + + + NSPrivacyAccessedAPITypes + + + + + ``` + This adds the `NSPrivacyAccessAPITypes` key where each category usage will be added. +1. Since the .NET runtime and BCL include APIs from the [File timestamp][FileTimestampAPIs], [System boot time][SystemBootTimeAPIs], [Disk space][DiskSpaceAPIs] API categories, add the following to the `NSPrivacyAccessedAPITypes` array: + ```xml + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryFileTimestamp + NSPrivacyAccessedAPITypeReasons + + C617.1 + + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategorySystemBootTime + NSPrivacyAccessedAPITypeReasons + + 35F9.1 + + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryDiskSpace + NSPrivacyAccessedAPITypeReasons + + E174.1 + + + ``` +1. For the [NSProcessInfo.SystemUptime](https://learn.microsoft.com/dotnet/api/foundation.nsprocessinfo.systemuptime), a reason code of `35F9.1` is needed since that is the only reason code available. But since the .NET runtime and BCL already included that category and reason, there is nothing additional to add. + +1. For the [NSFileManager.ModificationDate](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.modificationdate), a reason code of `C617.1` is needed since the modification dates are stored as a hash using [NSUserDefaults](https://learn.microsoft.com/dotnet/api/foundation.nsuserdefaults) but not displayed to the user. Again, the .NET runtime and BCL requirements have already satisfied this category and reason so no additional changes are needed. + +1. For the [NSUserDefaults](https://learn.microsoft.com/dotnet/api/foundation.nsuserdefaults), a reason code of `CA92.1` is provided since the data accessed is only accessible to the app itself. Add the following element to the `NSPrivacyAccessedAPITypes` array: + ```xml + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryUserDefaults + NSPrivacyAccessedAPITypeReasons + + CA92.1 + + + ``` + +The complete `PrivacyInfo.xcprivacy` should now look similar to: +```xml + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryFileTimestamp + NSPrivacyAccessedAPITypeReasons + + C617.1 + + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategorySystemBootTime + NSPrivacyAccessedAPITypeReasons + + 35F9.1 + + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryDiskSpace + NSPrivacyAccessedAPITypeReasons + + E174.1 + + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryUserDefaults + NSPrivacyAccessedAPITypeReasons + + CA92.1 + + + + + +``` + +Once added to your project, the `PrivacyInfo.xcprivacy` file will need to be updated if there are any additional API usages from additional categories or additional reasons for usage. This will include adding a NuGet package or Binding project that calls into any of Apple’s [Required Reason APIs][RequiredReasonAPI]. It is ultimately your responsibility to provide an accurate `PrivacyInfo.xcprivacy` file, failing to do so may result in the App Store rejecting your submission. + +[RequiredReasonAPI]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api +[PrivacyManifestFiles]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files +[C#NETAPIs]: #c-net-apis-in-net-maui +[FileTimestampAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278393 +[SystemBootTimeAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278394 +[DiskSpaceAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278397 +[ActiveKeyboardAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278400 +[UserDefaultsAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278401 \ No newline at end of file diff --git a/docs/required-reasons-bcl.md b/docs/required-reasons-bcl.md new file mode 100644 index 000000000000..471d457db14a --- /dev/null +++ b/docs/required-reasons-bcl.md @@ -0,0 +1,213 @@ +# Required Reasons API usage in .NET, Mono and the BCL + +The tables provide lists of C# .NET APIs that call the [Required Reasons APIs][RequiredReasonAPI] organized by category. These API usages are present in your app even if you do not explicitly call them. Therefore, you will be required to provide the API categories and reasons provided below in your apps `PrivacyInfo.xcprivacy` file. You may have to provide additional reason codes if you use the APIs directly, see [Required Reasons APIs][RequiredReasonAPI] for more information on the reason codes. + +**Note:** The following lists are verified only for .NET versions 8.0.0 and later. + +### [File timestamp APIs][FileTimestampAPIs] + +The following APIs either directly or indirectly access file timestamps and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryFileTimestamp` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. Refer to [File timestamp APIs][FileTimestampAPIs] for any additional relevant values to add to the `NSPrivacyAccessedAPITypeReasons` array. +| .NET API | Internal Usages | CoreClr Usages | Mono Usages +| - | - | - | - | +| [System.Diagnostics.FileVersionInfo](https://learn.microsoft.com/dotnet/api/System.Diagnostics.FileVersionInfo) | [Interop.Sys.LStat](https://source.dot.net/#System.Private.CoreLib/src/libraries/Common/src/Interop/Unix/System.Native/Interop.Stat.cs,65) | SystemNative_LStat | g_file_test +| [System.IO.Compression.ZipFile.CreateFromDirectory](https://learn.microsoft.com/dotnet/api/System.IO.Compression.ZipFile.CreateFromDirectory) | [Interop.Sys.Stat](https://source.dot.net/#System.Private.CoreLib/src/libraries/Common/src/Interop/Unix/System.Native/Interop.Stat.cs,62) | SystemNative_Stat | mono_file_map_size +| [System.IO.Directory.CreateDirectory(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.CreateDirectory) | [Interop.Sys.FStat](https://source.dot.net/#System.Private.CoreLib/src/libraries/Common/src/Interop/Unix/System.Native/Interop.Stat.cs,59) | SystemNative_FStat | +| [System.IO.Directory.CreateDirectory(string, UnixFileMode)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.CreateDirectory) | [System.Runtime.Loader.AssemblyLoadContext.ResolveSatelliteAssembly](https://source.dot.net/#System.Private.CoreLib/src/libraries/System.Private.CoreLib/src/System/Runtime/Loader/AssemblyLoadContext.cs,763) +| [System.IO.Directory.Delete(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.Delete) +| [System.IO.Directory.Exists(string?)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.Exists) +| [System.IO.Directory.GetCreationTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetCreationTime) +| [System.IO.Directory.GetCreationTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetCreationTimeUtc) +| [System.IO.Directory.GetLastAccessTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetLastAccessTime) +| [System.IO.Directory.GetLastAccessTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetLastAccessTimeUtc) +| [System.IO.Directory.GetLastWriteTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetLastWriteTime) +| [System.IO.Directory.GetLastWriteTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.GetLastWriteTimeUtc) +| [System.IO.Directory.Move(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.Directory.Move) +| [System.IO.DirectoryInfo.Delete(string?)](https://learn.microsoft.com/dotnet/api/System.IO.DirectoryInfo.Delete) +| [System.IO.DirectoryInfo.MoveTo(string)](https://learn.microsoft.com/dotnet/api/System.IO.DirectoryInfo.MoveTo) +| [System.IO.Enumeration.FileSystemEntry.Attributes](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.Attributes) +| [System.IO.Enumeration.FileSystemEntry.CreationTime](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.CreationTime) +| [System.IO.Enumeration.FileSystemEntry.CreationTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.CreationTimeUtc) +| [System.IO.Enumeration.FileSystemEntry.IsHidden](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.IsHidden) +| [System.IO.Enumeration.FileSystemEntry.LastAccessTime](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.Attributes) +| [System.IO.Enumeration.FileSystemEntry.LastAccessTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.LastAccessTimeUtc) +| [System.IO.Enumeration.FileSystemEntry.LastWriteTime](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.LastWriteTime) +| [System.IO.Enumeration.FileSystemEntry.LastWriteTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.LastWriteTimeUtc) +| [System.IO.Enumeration.FileSystemEntry.Length](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.Length) +| [System.IO.Enumeration.FileSystemEntry.ToFileSystemInfo()](https://learn.microsoft.com/dotnet/api/System.IO.Enumeration.FileSystemEntry.ToFileSystemInfo) +| [System.IO.File.Copy(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.File.Copy) +| [System.IO.File.Copy(string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.File.Copy) +| [System.IO.File.Delete(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.Delete) +| [System.IO.File.Exists(string?)](https://learn.microsoft.com/dotnet/api/System.IO.File.Exists) +| [System.IO.File.GetAttributes(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetAttributes) +| [System.IO.File.GetAttributes(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetAttributes) +| [System.IO.File.GetCreationTime(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetCreationTime) +| [System.IO.File.GetCreationTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetCreationTime) +| [System.IO.File.GetCreationTimeUtc(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetCreationTimeUtc) +| [System.IO.File.GetCreationTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetCreationTimeUtc) +| [System.IO.File.GetLastAccessTime(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastAccessTime) +| [System.IO.File.GetLastAccessTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastAccessTime) +| [System.IO.File.GetLastAccessTimeUtc(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastAccessTimeUtc) +| [System.IO.File.GetLastAccessTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastAccessTimeUtc) +| [System.IO.File.GetLastWriteTime(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastWriteTime) +| [System.IO.File.GetLastWriteTime(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastWriteTime) +| [System.IO.File.GetLastWriteTimeUtc(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastWriteTimeUtc) +| [System.IO.File.GetLastWriteTimeUtc(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetLastWriteTimeUtc) +| [System.IO.File.GetUnixFileMode(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetUnixFileMode) +| [System.IO.File.GetUnixFileMode(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.GetUnixFileMode) +| [System.IO.File.Move(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.File.Move) +| [System.IO.File.Move(string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.File.Move) +| [System.IO.File.OpenHandle(string, FileMode, FileAccess, FileShare, FileOptions, long)](https://learn.microsoft.com/dotnet/api/System.IO.File.OpenHandle) +| [System.IO.File.Replace(string, string, string)](https://learn.microsoft.com/dotnet/api/System.IO.File.Replace) +| [System.IO.File.Replace(string, string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.File.Replace) +| [System.IO.File.ReadAllBytes(string)](https://learn.microsoft.com/dotnet/api/System.IO.File.ReadAllBytes) +| [System.IO.File.ReadAllBytesAsync(string, CancellationToken)](https://learn.microsoft.com/dotnet/api/System.IO.File.ReadAllBytesAsync) +| [System.IO.FileInfo.Delete()](https://learn.microsoft.com/dotnet/api/System.IO.FileInfo.Delete) +| [System.IO.FileInfo.MoveTo(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.FileInfo.MoveTo) +| [System.IO.FileInfo.MoveTo(string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.FileInfo.MoveTo) +| [System.IO.FileInfo.Replace(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.FileInfo.Replace) +| [System.IO.FileInfo.Replace(string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.FileInfo.Replace) +| [System.IO.FileSystemInfo.Attributes](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.Attributes) +| [System.IO.FileSystemInfo.CreationTime](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.CreationTime) +| [System.IO.FileSystemInfo.CreationTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.CreationTimeUtc) +| [System.IO.FileSystemInfo.LastAccessTime](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.Attributes) +| [System.IO.FileSystemInfo.LastAccessTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.LastAccessTimeUtc) +| [System.IO.FileSystemInfo.LastWriteTime](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.LastWriteTime) +| [System.IO.FileSystemInfo.LastWriteTimeUtc](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.LastWriteTimeUtc) +| [System.IO.FileSystemInfo.Length](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.Length) +| [System.IO.FileSystemInfo.Refresh()](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.Refresh) +| [System.IO.FileSystemInfo.UnixFileMode](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemInfo.UnixFileMode) +| [System.IO.FileSystemWatcher](https://learn.microsoft.com/dotnet/api/System.IO.FileSystemWatcher) +| [System.IO.IsolatedStorage.IsolatedStorageFile.MoveDirectory(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.IsolatedStorage.IsolatedStorageFile.MoveDirectory) +| [System.IO.IsolatedStorage.IsolatedStorageFile.MoveFile(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.IsolatedStorage.IsolatedStorageFile.MoveFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?, long)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?, long, MemoryMappedFileAccess)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.Path.Exists(string?)](https://learn.microsoft.com/dotnet/api/System.IO.Path.Exists) +| [System.IO.Pipes.AnonymousPipeClientStream](https://learn.microsoft.com/dotnet/api/System.IO.Pipes.AnonymousPipeClientStream) +| [System.IO.Pipes.AnonymousPipeServerStream](https://learn.microsoft.com/dotnet/api/System.IO.Pipes.AnonymousPipeServerStream) +| [System.IO.Pipes.NamedPipeClientStream](https://learn.microsoft.com/dotnet/api/System.IO.Pipes.NamedPipeClientStream) +| [System.IO.Pipes.NamedPipeServerStream](https://learn.microsoft.com/dotnet/api/System.IO.Pipes.NamedPipeServerStream) +| [System.IO.RandomAccess.GetLength(SafeFileHandle)](https://learn.microsoft.com/dotnet/api/System.IO.RandomAccess.GetLength) +| [System.Formats.Tar.TarWriter.WriteEntry(TarEntry)](https://learn.microsoft.com/dotnet/api/System.Formats.Tar.TarWriter.WriteEntry) +| [System.Formats.Tar.TarWriter.WriteEntry(string, string)](https://learn.microsoft.com/dotnet/api/System.Formats.Tar.TarWriter.WriteEntry) +| [System.Formats.Tar.TarWriter.WriteEntryAsync(TarEntry, CancellationToken)](https://learn.microsoft.com/dotnet/api/System.Formats.Tar.TarWriter.WriteEntryAsync) +| [System.Formats.Tar.TarWriter.WriteEntryAsync(string, string, CancellationToken)](https://learn.microsoft.com/dotnet/api/System.Formats.Tar.TarWriter.WriteEntryAsync) +| [System.Net.Sockets.Socket.SendPacketsAsync(SocketAsyncEventArgs)](https://learn.microsoft.com/dotnet/api/System.Net.Sockets.Socket.SendPacketsAsync) +| [System.TimeZoneInfo.Local](https://learn.microsoft.com/dotnet/api/System.TimeZoneInfo.Local) + + + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryFileTimestamp + NSPrivacyAccessedAPITypeReasons + + C617.1 + + + + + +``` + +Additional reason codes from [File timestamp APIs][FileTimestampAPIs] can be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + +### [System boot time APIs][SystemBootTimeAPIs] + +The following APIs either directly or indirectly access the system boot time and require reasons for use. Use the string `NSPrivacyAccessedAPICategorySystemBootTime` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you only access the system boot time from the list of APIs below, then use the `35F9.1` value in the `NSPrivacyAccessedAPITypeReasons` array. +| .NET API | Internal Usages | CoreClr Usages | Mono Usages +| - | - | - | - | +| [System.Environment.TickCount](https://learn.microsoft.com/dotnet/api/System.Environment.TickCount) | | | mono_msec_boottime +| [System.Environment.TickCount64](https://learn.microsoft.com/dotnet/api/System.Environment.TickCount64) | | | mono_domain_finalize +| | | | mono_join_uninterrupted +| | | | mono_msec_ticks +| | | | mono_100ns_ticks +| | | | threads_wait_pending_joinable_threads +| | | | current_time + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategorySystemBootTime + NSPrivacyAccessedAPITypeReasons + + 35F9.1 + + + + + +``` + +### [Disk space APIs][DiskSpaceAPIs] + +The following APIs either directly or indirectly access the available disk space and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryDiskSpace` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you access the available disk space from the list of APIs below, then use [Disk space APIs][DiskSpaceAPIs] to determine the correct values to place in the `NSPrivacyAccessedAPITypeReasons` array. +| .NET API | Internal Usages | CoreClr Usages | Mono Usages +| - | - | - | - | +| [System.IO.DriveInfo.AvailableFreeSpace](https://learn.microsoft.com/dotnet/api/System.IO.DriveInfo.AvailableFreeSpace) | [Interop.Sys.TryGetFileSystemType](https://source.dot.net/#System.Private.CoreLib/src/libraries/Common/src/Interop/Unix/System.Native/Interop.UnixFileSystemTypes.cs,155) | SystemNative_GetFileSystemType | | +| [System.IO.DriveInfo.DriveFormat](https://learn.microsoft.com/dotnet/api/System.IO.DriveInfo.DriveFormat) | [Interop.Sys.GetSpaceInfoForMountPoint](https://source.dot.net/#System.IO.FileSystem.DriveInfo/src/libraries/Common/src/Interop/Unix/System.Native/Interop.MountPoints.FormatInfo.cs,34) | SystemNative_GetSpaceInfoForMountPoint | | +| [System.IO.DriveInfo.DriveType](https://learn.microsoft.com/dotnet/api/System.IO.DriveInfo.DriveType) | [Interop.Sys.GetFormatInfoForMountPoint](https://source.dot.net/#System.IO.FileSystem.DriveInfo/src/libraries/Common/src/Interop/Unix/System.Native/Interop.MountPoints.FormatInfo.cs,37) | SystemNative_GetFormatInfoForMountPoint | +| [System.IO.DriveInfo.TotalFreeSpace](https://learn.microsoft.com/dotnet/api/System.IO.DriveInfo.TotalFreeSpace) +| [System.IO.DriveInfo.TotalSize](https://learn.microsoft.com/dotnet/api/System.IO.DriveInfo.TotalSize) +| [System.IO.File.Copy(string, string)](https://learn.microsoft.com/dotnet/api/System.IO.File.Copy) +| [System.IO.File.Copy(string, string, boolean)](https://learn.microsoft.com/dotnet/api/System.IO.File.Copy) +| [System.IO.File.OpenHandle(string, FileMode, FileAccess, FileShare, FileOptions, long)](https://learn.microsoft.com/dotnet/api/System.IO.File.OpenHandle) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?, long)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile(string, FileMode, string?, long, MemoryMappedFileAccess)](https://learn.microsoft.com/dotnet/api/System.IO.MemoryMappedFiles.MemoryMappedFile.CreateFromFile) +| [System.TimeZoneInfo.Local](https://learn.microsoft.com/dotnet/api/System.TimeZoneInfo.Local) +| [System.Net.Sockets.Socket.SendPacketsAsync(SocketAsyncEventArgs)](https://learn.microsoft.com/dotnet/api/System.Net.Sockets.Socket.SendPacketsAsync) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryDiskSpace + NSPrivacyAccessedAPITypeReasons + + E174.1 + + + + + +``` + +Reason codes from [Disk space APIs][DiskSpaceAPIs] can be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + + +[RequiredReasonAPI]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api +[PrivacyManifestFiles]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files +[C#NETAPIs]: #c-net-apis-in-net-maui +[FileTimestampAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278393 +[SystemBootTimeAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278394 +[DiskSpaceAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278397 +[ActiveKeyboardAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278400 +[UserDefaultsAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278401 diff --git a/docs/required-reasons-dotnet-maui.md b/docs/required-reasons-dotnet-maui.md new file mode 100644 index 000000000000..84ada8d4a04d --- /dev/null +++ b/docs/required-reasons-dotnet-maui.md @@ -0,0 +1,46 @@ +# Required Reasons API usage in .NET MAUI and Xamarin.Forms + +The tables provide lists of C# .NET APIs that call the [Required Reasons APIs][RequiredReasonAPI] organized by category. If your application, SDK or package code calls any of the APIs from these lists, declare the reasons for their use in your privacy manifest file following the guidelines specified in Apple’s documentation on [Required Reasons APIs][RequiredReasonAPI]. + + +**Note:** The following lists are verified only for .NET MAUI versions 8.0.0 and later. + +### [User defaults APIs][UserDefaultsAPIs] +The following APIs either directly or indirectly access user defaults and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryUserDefaults` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you only access the user defaults from the list of APIs below, then use the value `C56D.1` in the `NSPrivacyAccessedAPITypeReasons` array. Refer to [User defaults APIs][UserDefaultsAPIs] to determine the any additional relevant values to place in the `NSPrivacyAccessedAPITypeReasons` array. +| API usage | +| - | +| [NSUserDefaults](https://learn.microsoft.com/dotnet/api/foundation.nsuserdefaults) | + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryUserDefaults + NSPrivacyAccessedAPITypeReasons + + ... + + + + + +``` + +Reason codes from [User defaults APIs][UserDefaultsAPIs] need to be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + + +[RequiredReasonAPI]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api +[PrivacyManifestFiles]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files +[C#NETAPIs]: #c-net-apis-in-net-maui +[FileTimestampAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278393 +[SystemBootTimeAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278394 +[DiskSpaceAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278397 +[ActiveKeyboardAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278400 +[UserDefaultsAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278401 \ No newline at end of file diff --git a/docs/required-reasons-macios.md b/docs/required-reasons-macios.md new file mode 100644 index 000000000000..6efd612ae8e4 --- /dev/null +++ b/docs/required-reasons-macios.md @@ -0,0 +1,189 @@ +# Required Reasons API usage in .NET for iOS, tvOS, and Xamarin.iOS + +The tables provide lists of C# .NET APIs that call the [Required Reasons APIs][RequiredReasonAPI] organized by category. If your application, SDK or package code calls any of the APIs from these lists, declare the reasons for their use in your privacy manifest file following the guidelines specified in Apple’s documentation on [Required Reasons APIs][RequiredReasonAPI]. + +**Note:** The following lists are verified only for .NET for iOS, tvOS and Xamarin.iOS versions 8.0.4 and later. + +### [File timestamp APIs][FileTimestampAPIs] + +The following APIs either directly or indirectly access file timestamps and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryFileTimestamp` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. Refer to [File timestamp APIs][FileTimestampAPIs] for any additional relevent values to add to the `NSPrivacyAccessedAPITypeReasons` array. +| Foundation APIs | UIKit APIs | AppKit APIs | +| - | - | - | +| [NSFileManager.CreationDate](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.creationdate) | [UIDocument.FileModificationDate](https://learn.microsoft.com/dotnet/api/uikit.uidocument.filemodificationdate) | [NSDocument.FileModificationDate](https://learn.microsoft.com/dotnet/api/appkit.nsdocument.filemodificationdate) | +| [NSFileManager.ModificationDate](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.modificationdate) +| [NSFileManager.SetAttributes(NSDictionary, string, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.setattributes) +| [NSFileManager.SetAttributes(NSFileAttributes, string, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.setattributes) +| [NSFileManager.SetAttributes(NSFileAttributes, string)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.setattributes) +| [NSFileManager.CreateDirectory(string, bool, NSDictionary, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.createdictionary) +| [NSFileManager.CreateDirectory(string, bool, NSFileAttributes, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.createdictionary) +| [NSFileManager.CreateDirectory(string, bool, NSFileAttributes)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.createdictionary) +| [NSFileManager.CreateFile(string, NSData, NSDictionary)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.createfile) +| [NSFileManager.CreateFile(string, NSData, NSFileAttributes)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.createfile) +| [NSFileManager.GetAttributes(string, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.getattributes) +| [NSFileManager.GetAttributes(string)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.getattributes) +| [NSDictionary.ToFileAttributes()](https://learn.microsoft.com/dotnet/api/foundation.nsdictionary.tofileattributes) +| [NSUrl.ContentModificationDateKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.contentmodificationdatekey) +| [NSUrl.CreationDateKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.creationdatekey) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryFileTimestamp + NSPrivacyAccessedAPITypeReasons + + ... + + + + + +``` + +Additional reason codes from [File timestamp APIs][FileTimestampAPIs] can be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + +### [System boot time APIs][SystemBootTimeAPIs] + +The following APIs either directly or indirectly access the system boot time and require reasons for use. Use the string `NSPrivacyAccessedAPICategorySystemBootTime` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you only access the system boot time from the list of APIs below, then use the `35F9.1` value in the `NSPrivacyAccessedAPITypeReasons` array. +| Foundation APIs | UIKit APIs | AppKit APIs | +| - | - | - | +| [NSProcessInfo.SystemUptime](https://learn.microsoft.com/dotnet/api/foundation.nsprocessinfo.systemuptime) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategorySystemBootTime + NSPrivacyAccessedAPITypeReasons + + 35F9.1 + + + + + +``` + +### [Disk space APIs][DiskSpaceAPIs] + +The following APIs either directly or indirectly access the available disk space and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryDiskSpace` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you access the available disk space from the list of APIs below, then use [Disk space APIs][DiskSpaceAPIs] to determine the correct values to place in the `NSPrivacyAccessedAPITypeReasons` array. +| Foundation APIs | UIKit APIs | AppKit APIs | +| - | - | - | +| [NSUrl.VolumeAvailableCapacityKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.volumeavailablecapacitykey) +| [NSUrl.VolumeAvailableCapacityForImportantUsageKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.volumeavailablecapacityforimportantusagekey) +| [NSUrl.VolumeAvailableCapacityForOpportunisticUsageKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.volumeavailablecapacityforopportunisticusagekey) +| [NSUrl.VolumeTotalCapacityKey](https://learn.microsoft.com/dotnet/api/foundation.nsurl.volumetotalcapacity) +| [NSFileManager.SystemFreeSize](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.systemfreesize) +| [NSFileManager.SystemSize](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.systemsize) +| [NSFileManager.GetFileSystemAttributes(string, NSError)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.getfilesystemattributes) +| [NSFileManager.GetFileSystemAttributes(string)](https://learn.microsoft.com/dotnet/api/foundation.nsfilemanager.getfilesystemattributes) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryDiskSpace + NSPrivacyAccessedAPITypeReasons + + ... + + + + + +``` + +Reason codes from [Disk space APIs][DiskSpaceAPIs] need to be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + +### [Active keyboard APIs][ActiveKeyboardAPIs] + +The following APIs either directly or indirectly access the list of available keyboards and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryActiveKeyboards` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you access the list of available keyboards from the list of APIs below, then use [Active keyboard APIs][ActiveKeyboardAPIs] to determine the correct values to place in the `NSPrivacyAccessedAPITypeReasons` array. +| Foundation APIs | UIKit APIs | AppKit APIs | +| - | - | - | +| | [UITextInputMode.ActiveInputModes](https://learn.microsoft.com/dotnet/api/appkit.uitextinputmode.activeinputmodes) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryActiveKeyboards + NSPrivacyAccessedAPITypeReasons + + ... + + + + + +``` + +Reason codes from [Active keyboard APIs][ActiveKeyboardAPIs] need to be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + +### [User defaults APIs][UserDefaultsAPIs] +The following APIs either directly or indirectly access user defaults and require reasons for use. Use the string `NSPrivacyAccessedAPICategoryUserDefaults` as the value for the `NSPrivacyAccessedAPIType` key in your `NSPrivacyAccessedAPITypes` dictionary. If you only access the user defaults from the list of APIs below, then use the value `C56D.1` in the `NSPrivacyAccessedAPITypeReasons` array. Refer to [User defaults APIs][UserDefaultsAPIs] to determine the any additional relevant values to place in the `NSPrivacyAccessedAPITypeReasons` array. +| Foundation APIs | UIKit APIs | AppKit APIs | +| - | - | - | +| [NSUserDefaults](https://learn.microsoft.com/dotnet/api/foundation.nsuserdefaults) | | [NSUserDefaultsController.NSUserDefaultsController(NSUserDefaults, NSDictionary)](https://learn.microsoft.com/dotnet/api/appkit.nsuserdefaultscontroller.-ctor#appkit-nsuserdefaultscontroller-ctor(foundation-nsuserdefaults-foundation-nsdictionary)) +| | | [NSUserDefaultsController.Defaults](https://learn.microsoft.com/dotnet/api/appkit.nsuserdefaultscontroller.defaults) +| | | [NSUserDefaultsController.SharedUserDefaultsController](https://learn.microsoft.com/dotnet/api/appkit.nsuserdefaultscontroller.shareduserdefaultscontroller) + +For example, if you use any of the APIs listed above, your `PrivacyInfo.xcprivacy` would contain the `dict` element in the `NSPrivacyAccessedAPITypes` key's array as shown below: + +```xml + + + + + NSPrivacyAccessedAPITypes + + + NSPrivacyAccessedAPIType + NSPrivacyAccessedAPICategoryUserDefaults + NSPrivacyAccessedAPITypeReasons + + ... + + + + + +``` + +Reason codes from [User defaults APIs][UserDefaultsAPIs] need to be provided in the array following the `NSPrivacyAccessedAPITypeReasons` key. + + +[RequiredReasonAPI]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api +[PrivacyManifestFiles]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files +[C#NETAPIs]: #c-net-apis-in-net-maui +[FileTimestampAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278393 +[SystemBootTimeAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278394 +[DiskSpaceAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278397 +[ActiveKeyboardAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278400 +[UserDefaultsAPIs]: https://developer.apple.com/documentation/bundleresources/privacy_manifest_files/describing_use_of_required_reason_api#4278401 \ No newline at end of file