Partager via


Déploiement AOT natif sur iOS et Mac Catalyst

Le déploiement AOT natif produit une application d’interface utilisateur d’application multiplateforme .NET (.NET MAUI) sur iOS et Mac Catalyst compilée à l’avance (AOT) en code natif. Native AOT effectue une analyse de programme statique, le découpage complet de votre application, qui est agressif dans la suppression du code qui n’est pas référencé statiquement et la génération de code à l’avance.

La publication et le déploiement d’une application AOT native produisent les avantages suivants :

  • Taille réduite du package d’application.
  • Temps de démarrage plus rapide.
  • Temps de génération plus rapide.

L’AOT natif introduit des limitations sur l’utilisation de certains aspects du runtime .NET et ne doit être utilisée que dans les scénarios où la taille et les performances de l’application sont importantes. Il vous faudra adapter vos applications aux exigences AOT natives, ce qui signifie qu’elles sont entièrement rognantes et compatibles avec AOT. Pour plus d’informations sur les limitations AOT natives, consultez limitations DOT natives.

Lorsque le déploiement AOT natif est activé, le système de génération analyse votre code et toutes ses dépendances, pour vérifier s’il convient pour le découpage complet et la compilation AOT. Si des incompatibilités sont détectées, le découpage et les avertissements AOT sont générés. Un avertissement de découpage unique ou AOT signifie que l’application n’est pas compatible avec le déploiement AOT natif et qu’elle peut ne pas fonctionner correctement. Par conséquent, lors de la création d’une application pour le déploiement AOT natif, vous devez passer en revue et corriger tous les avertissements de découpage et AOT. L’échec de cette opération peut entraîner des exceptions au moment de l’exécution, car le code nécessaire a pu être supprimé. Si vous supprimez les avertissements que l’application déployée AOT doit être soigneusement testée pour vérifier que la fonctionnalité n’a pas changé de l’application nontrimmée. Pour plus d’informations, consultez Présentation des avertissements de suppression et Introduction aux avertissements AOT.

Remarque

Il peut y avoir des cas où la correction de la suppression et des avertissements AOT n’est pas possible, par exemple lorsqu’elles se produisent pour les bibliothèques tierces. Dans ce cas, les bibliothèques tierces doivent être mises à jour pour devenir entièrement compatibles.

Avantages en matière de performances AOT natifs

La publication et le déploiement d’une application AOT native produisent une application qui est généralement jusqu’à 2,5x plus petite, et une application qui démarre généralement jusqu’à 2 fois plus rapidement. Toutefois, les avantages exacts en matière de performances dépendent de plusieurs facteurs qui incluent la plateforme utilisée, l’appareil sur lequel l’application est en cours d’exécution et l’application elle-même.

Important

Les graphiques suivants présentent des avantages de performances typiques du déploiement AOT natif pour une dotnet new maui application sur iOS et Mac Catalyst. Toutefois, les données exactes dépendent du matériel et peuvent changer dans les versions ultérieures.

Le graphique suivant montre la taille du package d’application pour une dotnet new maui application sur iOS et Mac Catalyst sur différents modèles de déploiement :

Graphique montrant la taille du package d’application sur différents modèles de déploiement.

Le graphique précédent montre que, généralement, Native AOT produit plus de 2x applications plus petites pour iOS et Mac Catalyst par rapport au modèle de déploiement par défaut.

Le graphique suivant montre le temps de démarrage moyen, sur un matériel spécifique, pour une dotnet new maui application sur iOS et Mac Catalyst sur un déploiement Mono et AOT natif :

Graphique montrant le temps de démarrage moyen de l’application sur Mono et AOT natif.

Le graphique précédent montre que L’AOT natif a généralement jusqu’à 2 fois plus de temps de démarrage plus rapides sur les appareils iOS et une durée de démarrage 1,2 fois plus rapide sur Mac Catalyst, par rapport au déploiement Mono.

Le graphique suivant montre le temps de génération moyen, sur un matériel spécifique, pour une dotnet new maui application sur iOS et Mac Catalyst sur différents modèles de déploiement :

Graphique montrant le temps de génération moyen de l’application sur Mono et AOT natif.

Le graphique précédent montre que l’AOT natif a jusqu’à 2,8 fois de build plus rapides sur les appareils iOS par rapport au modèle de déploiement par défaut. Pour Mac Catalyst, les temps de génération sont comparables pour les applications RID uniques arm64, mais sont légèrement plus lents pour les applications universelles par rapport au déploiement Mono.

Important

Dans de nombreux scénarios, L’AOT natif génère des applications plus petites et plus rapides. Toutefois, dans certains scénarios, L’AOT natif peut ne pas produire d’applications plus petites et plus rapides. Par conséquent, il est important de tester et de profiler votre application pour déterminer le résultat de l’activation du déploiement AOT natif.

Publier à l’aide d’AOT natif

Le modèle de déploiement AOT natif est activé avec la $(PublishAot) propriété de build et la dotnet publish commande. L’exemple suivant montre comment modifier un fichier projet pour activer le déploiement AOT natif sur iOS et Mac Catalyst :

<PropertyGroup>
  <!-- enable trimming and AOT analyzers on all platforms -->
  <IsAotCompatible>true</IsAotCompatible>

  <!-- select platforms to use with NativeAOT -->
  <PublishAot Condition="$([MSBuild]::GetTargetPlatformIdentifier('$(TargetFramework)')) == 'ios'">true</PublishAot>
  <PublishAot Condition="$([MSBuild]::GetTargetPlatformIdentifier('$(TargetFramework)')) == 'maccatalyst'">true</PublishAot>
</PropertyGroup>

La définition de la $(IsAotCompatible) propriété truede build sur , pour toutes les plateformes, active le découpage et les analyseurs AOT. Ces analyseurs vous aident à identifier le code qui n’est pas compatible avec le découpage ou LOT.

La définition $(PublishAot) trueconditionnelle sur , pour iOS et Mac Catalyst, active l’analyse dynamique de l’utilisation du code lors de la compilation de build et d’AOT native lors de la publication. L’analyse AOT native inclut tout le code de l’application et toutes les bibliothèques dont dépend l’application.

Avertissement

La $(PublishAot) propriété de build ne doit pas être conditionnée par la configuration de build. Cela est dû au fait que les commutateurs de fonctionnalités de découpage sont activés ou désactivés en fonction de la valeur de la $(PublishAot) propriété de build, et que les mêmes fonctionnalités doivent être activées ou désactivées dans toutes les configurations de build afin que votre code se comporte de manière identique. Pour plus d’informations sur le découpage des commutateurs de fonctionnalités, consultez Découpage des commutateurs de fonctionnalités.

La seule façon de vérifier qu’une application AOT native fonctionne correctement consiste à la publier à l’aide dotnet publish et à vérifier qu’il n’y a pas de découpage ou d’avertissements AOT générés par votre code et ses dépendances. En particulier, dotnet build -t:Publish n’est pas équivalent à dotnet publish.

Utilisez la commande suivante dotnet publish pour publier votre application sur iOS et Mac Catalyst à l’aide du déploiement AOT natif :

# iOS
dotnet publish -f net9.0-ios -r ios-arm64

# Mac Catalyst
dotnet publish -f net9.0-maccatalyst -r maccatalyst-arm64
dotnet publish -f net9.0-maccatalyst -r maccatalyst-x64

# Universal Mac Catalyst apps
# (when <RuntimeIdentifiers>maccatalyst-x64;maccatalyst-arm64</RuntimeIdentifiers> is set in the project file)
dotnet publish -f net9.0-maccatalyst

Conseil

Publiez fréquemment des applications pour découvrir les problèmes de découpage ou DOT au début du cycle de vie du développement.

Limitations D’AOT natives

L’AOT natif introduit des limitations sur l’utilisation de certains aspects du runtime .NET et ne doit être utilisée que dans les scénarios où la taille et les performances de l’application sont importantes. Il vous faudra adapter vos applications aux exigences AOT natives, ce qui signifie qu’elles sont entièrement rognantes et compatibles avec AOT, et cela peut nécessiter beaucoup de travail. Outre les limitations .NET du déploiement AOT natif, le déploiement AOT natif pour .NET MAUI présente des limitations supplémentaires.

Les bibliothèques tierces dont dépendent vos applications peuvent ne pas être compatibles avec AOT. La seule façon de s’assurer qu’une bibliothèque est rognante et compatible avec AOT consiste à publier votre application à l’aide du déploiement AOT natif et de la dotnet publish commande, et à voir si le compilateur AOT natif génère des avertissements pour la bibliothèque. Pour plus d’informations sur la compatibilité de vos propres bibliothèques AOT, consultez Comment rendre les bibliothèques compatibles avec AOT natif.

Réflexion et code dynamique

Le déploiement AOT natif limite l’utilisation de la réflexion dans votre code et ses dépendances, et il peut devenir nécessaire d’utiliser des annotations pour aider le compilateur AOT natif à comprendre les modèles de réflexion. Lorsque le compilateur rencontre un modèle de réflexion, il ne peut pas analyser statiquement et ne peut donc pas générer l’application, il génère des avertissements de découpage. L’AOT natif vous empêche également d’utiliser du code dynamique dans votre application. Par exemple, la System.Linq.Expressions compilation ne fonctionnera pas comme prévu, et il n’est pas possible de charger et d’exécuter des assemblys au moment de l’exécution. Lorsque le compilateur rencontre un modèle dynamique qu’il ne peut pas compiler à l’avance, il génère un avertissement AOT.

Dans l’application .NET MAUI, cela signifie que :

  • Tous les xamls doivent être compilés à l’avance. Par conséquent, vérifiez que vous n’avez pas désactivé la compilation XAML et que toutes les liaisons sont compilées. Pour plus d’informations, consultez compilation XAML et liaisons compilées.
  • Toutes les expressions de liaison doivent utiliser des liaisons compilées, plutôt qu’un chemin d’accès de liaison défini sur une chaîne. Pour plus d’informations, consultez Liaisons compilées.
  • Les opérateurs de conversion implicite peuvent ne pas être appelés lors de l’affectation d’une valeur d’un type incompatible à une propriété en XAML, ou lorsque deux propriétés de types différents utilisent une liaison de données. Au lieu de cela, vous devez définir un TypeConverter type pour votre type et l’attacher au type à l’aide du TypeConverterAttribute. Pour plus d’informations, consultez Définir un TypeConverter pour remplacer un opérateur de conversion implicite.
  • Il n’est pas possible d’analyser XAML au moment de l’exécution avec la LoadFromXaml méthode. Bien que cela puisse être rendu sécurisé en annotant tous les types qui peuvent être chargés lors de l’exécution avec l’attribut DynamicallyAccessedMembers ou l’attribut DynamicDependency , il est très sujette à des erreurs et n’est pas recommandé.
  • La réception de données de navigation à l’aide du QueryPropertyAttribute fichier ne fonctionnera pas. Au lieu de cela, vous devez implémenter l’interface IQueryAttributable sur les types qui doivent accepter les paramètres de requête. Pour plus d’informations, consultez Traiter les données de navigation à l’aide d’une méthode unique.
  • La SearchHandler.DisplayMemberName propriété peut ne pas fonctionner. Au lieu de cela, vous devez fournir un ItemTemplate pour définir l’apparence des résultats SearchHandler. Pour plus d’informations, consultez Définir l’apparence de l’élément de résultats de recherche.

Important

L’interpréteur Mono n’est pas compatible avec le déploiement AOT natif. Par conséquent, les propriétés MSBuild et $(MtouchInterpreter) MSBuild n’ont aucun effet lors de l’utilisation $(UseInterpreter) d’AOT natif. Pour plus d’informations sur l’interpréteur Mono, consultez l’interpréteur Mono sur iOS et Mac Catalyst.

Pour plus d’informations sur les avertissements de découpage, consultez Présentation des avertissements de suppression. Pour plus d’informations sur les avertissements AOT, consultez Introduction aux avertissements AOT.

Adapter une application au déploiement AOT natif

Utilisez la liste de contrôle suivante pour vous aider à adapter votre application aux exigences de déploiement AOT natives :

  • Vérifiez que tous les xamls sont compilés :
    • Supprimez toute [XamlCompilation(XamlCompilationOptions.Skip)] l’utilisation.
    • Supprimez toute <?xaml-comp compile="false" ?> l’utilisation.
  • Supprimez tous les appels à la LoadFromXaml méthode.
  • Vérifiez que toutes les liaisons de données sont compilées. Pour plus d’informations, consultez Liaisons compilées.
    • Vérifiez que toutes les liaisons de données XAML sont annotées avec x:DataType.
    • Vérifiez que toutes les liaisons de données de code remplacent toutes les liaisons basées sur des chaînes par des liaisons lambda.
  • Remplacez toute [QueryProperty(...)] l’utilisation par une implémentation de l’interface IQueryAttributable . Pour plus d’informations, consultez Traiter les données de navigation à l’aide d’une méthode unique.
  • Remplacez toute SearchHandler.DisplayMemberName l’utilisation par un ItemTemplate. Pour plus d’informations, consultez Définir l’apparence de l’élément de résultats de recherche.
  • Remplacez tous les opérateurs de conversion implicite pour les types utilisés en XAML par un TypeConverter, et attachez-le à votre type à l’aide du TypeConverterAttributefichier . Pour plus d’informations, consultez Définir un TypeConverter pour remplacer un opérateur de conversion implicite.
    • Lors de la conversion d’un type en type A B, la ConvertTo méthode sur un convertisseur de type associé A sera utilisée ou la ConvertFrom méthode sur un convertisseur de type associé B sera utilisée.
    • Lorsque les types source et cible ont un convertisseur de type associé, l’un d’eux peut être utilisé.
  • Compilez toutes les expressions régulières à l’aide de générateurs sources. Pour plus d’informations, consultez Générateurs de sources d’expressions régulières .NET.
  • Vérifiez que la sérialisation et la désérialisation JSON utilisent un contexte généré par la source. Pour plus d’informations, consultez Les API minimales et les charges utiles JSON.
  • Passez en revue et corrigez les avertissements AOT ou de découpage. Pour plus d’informations, consultez Présentation des avertissements de suppression et Introduction aux avertissements AOT.
  • Testez soigneusement votre application.

Voir aussi