Mise à niveau des projets

Les modifications apportées au modèle de projet d’une version de Visual Studio à la suivante peuvent nécessiter la mise à niveau de projets et de solutions afin qu’elles puissent s’exécuter sur la version la plus récente. Le Kit de développement logiciel (SDK) Visual Studio fournit des interfaces qui peuvent être utilisées pour implémenter la prise en charge de la mise à niveau dans vos propres projets.

Stratégies de mise à niveau

Pour prendre en charge une mise à niveau, l’implémentation de votre système de projet doit définir et implémenter une stratégie de mise à niveau. Pour déterminer votre stratégie, vous pouvez choisir de prendre en charge la sauvegarde côte à côte (SxS), la sauvegarde de copie ou les deux.

  • La sauvegarde SxS signifie qu’un projet copie uniquement les fichiers qui ont besoin d’une mise à niveau en place, en ajoutant un suffixe de nom de fichier approprié, par exemple . old ».

  • La sauvegarde de copie signifie qu’un projet copie tous les éléments de projet vers un emplacement de sauvegarde fourni par l’utilisateur. Les fichiers pertinents à l’emplacement du projet d’origine sont ensuite mis à niveau.

Fonctionnement de la mise à niveau

Lorsqu’une solution créée dans une version antérieure de Visual Studio est ouverte dans une version plus récente, l’IDE case activée le fichier de solution pour déterminer s’il doit être mis à niveau. Si la mise à niveau est nécessaire, l’Assistant Mise à niveau est automatiquement lancé pour guider l’utilisateur dans le processus de mise à niveau.

Lorsqu’une solution a besoin d’une mise à niveau, elle interroge chaque fabrique de projets pour sa stratégie de mise à niveau. La stratégie détermine si la fabrique de projets prend en charge la sauvegarde de copie ou la sauvegarde SxS. Les informations sont envoyées à l’Assistant Mise à niveau, qui collecte les informations requises pour la sauvegarde et présente les options applicables à l’utilisateur.

Solutions multi-projets

Si une solution contient plusieurs projets et que les stratégies de mise à niveau diffèrent, par exemple lorsqu’un projet C++ qui prend uniquement en charge la sauvegarde SxS et un projet Web qui prend uniquement en charge la sauvegarde de copie, les fabriques de projets doivent négocier la stratégie de mise à niveau.

La solution interroge chaque fabrique de projet pour IVsProjectUpgradeViaFactory. Il appelle UpgradeProject_CheckOnly ensuite pour voir si les fichiers projet globaux doivent être mis à niveau et déterminer les stratégies de mise à niveau prises en charge. L’Assistant Mise à niveau est ensuite appelé.

Une fois que l’utilisateur a terminé l’Assistant, UpgradeProject il est appelé sur chaque fabrique de projet pour effectuer la mise à niveau réelle. Pour faciliter la sauvegarde, les méthodes IVsProjectUpgradeViaFactory fournissent au SVsUpgradeLogger service de journaliser les détails du processus de mise à niveau. Ce service ne peut pas être mis en cache.

Après avoir mis à jour tous les fichiers globaux pertinents, chaque fabrique de projet peut choisir d’instancier un projet. L’implémentation du projet doit prendre en charge IVsProjectUpgrade. La UpgradeProject méthode est ensuite appelée pour mettre à niveau tous les éléments de projet pertinents.

Remarque

La UpgradeProject méthode ne fournit pas le service SVsUpgradeLogger. Ce service peut être obtenu en appelant QueryService.

Meilleures pratiques

Utilisez le SVsQueryEditQuerySave service pour case activée si vous pouvez modifier un fichier avant de le modifier et l’enregistrer avant de l’enregistrer. Cela aidera vos implémentations de sauvegarde et de mise à niveau à gérer les fichiers projet sous contrôle de code source, les fichiers avec des autorisations insuffisantes, etc.

Utilisez le SVsUpgradeLogger service pendant toutes les phases de sauvegarde et de mise à niveau pour fournir des informations sur la réussite ou l’échec du processus de mise à niveau.

Pour plus d’informations sur la sauvegarde et la mise à niveau de projets, consultez les commentaires pour IVsProjectUpgrade dans vsshell2.idl.

Mise à niveau de projets personnalisés

Si vous modifiez les informations persistantes dans le fichier projet entre des versions Visual Studio différentes de votre produit, vous devez prendre en charge la mise à niveau de votre fichier projet vers la version la plus récente. Pour prendre en charge la mise à niveau qui vous permet de participer à l’Assistant Conversion de Visual Studio, implémentez l’interfaceIVsProjectUpgradeViaFactory. Cette interface fournit le seul mécanisme disponible pour mettre à niveau une copie. La mise à niveau du projet est une étape du processus d’ouverture de la solution. L’interface IVsProjectUpgradeViaFactory est implémentée par la fabrique de projet. Sinon, elle doit pouvoir être obtenue à partir de la fabrique de projet.

L’ancien mécanisme qui utilise l’interface IVsProjectUpgrade est toujours pris en charge, mais il est conçu pour mettre à niveau le système de projet pendant le processus d’ouverture du projet. L’interface IVsProjectUpgrade est donc appelée par l’environnement Visual Studio, même si l’interface IVsProjectUpgradeViaFactory est appelée ou implémentée. Cette approche vous permet d’utiliser IVsProjectUpgradeViaFactory pour implémenter uniquement la mise à niveau du projet et de la copie, et de déléguer le reste du travail à effectuer sur place (éventuellement au nouvel emplacement) par l’interface IVsProjectUpgrade.

Pour obtenir un exemple d’implémentation, IVsProjectUpgradeconsultez les exemples VSSDK.

Scénarios possibles lors d’une mise à niveau de projet :

  • Si le fichier présente un format récent non pris en charge par le projet, il doit retourner une erreur indiquant ce problème. Cela suppose que l’ancienne version de votre produit inclut du code à case activée pour la version.

  • Si l’indicateur PUVFF_SXSBACKUP est spécifié dans la méthode UpgradeProject, la mise à niveau est implémentée en tant que mise à niveau sur place avant l’ouverture du projet.

  • Si l’indicateur PUVFF_COPYBACKUP est spécifié dans la méthode UpgradeProject, la mise à niveau est implémentée en tant que mise à niveau de la copie.

  • Si l’indicateur UPF_SILENTMIGRATE est spécifié dans l’appel à UpgradeProject, l’utilisateur est invité par l’environnement à mettre à niveau le fichier projet en tant que mise à niveau sur place, une fois le projet ouvert. Par exemple, l’environnement invite l’utilisateur à effectuer la mise à niveau quand celui-ci ouvre une version antérieure de la solution.

  • Si l’indicateur UPF_SILENTMIGRATE n’est pas spécifié dans l’appel à UpgradeProject, vous devez inviter l’utilisateur à mettre à niveau le fichier projet.

    Voici un exemple de message d’invite de mise à niveau :

    « Le projet '%1' a été créé avec une version antérieure de Visual Studio. Si vous l’ouvrez avec cette version de Visual Studio, vous ne pourrez peut-être plus l’ouvrir avec les versions antérieures de Visual Studio. Voulez-vous continuer et ouvrir ce projet ? »

Pour implémenter IVsProjectUpgradeViaFactory

  1. Implémentez la méthode de l’interface IVsProjectUpgradeViaFactory, à savoir la méthode UpgradeProject dans votre implémentation de la fabrique de projet, ou définissez les implémentations pour qu’elles puissent être appelées à partir de votre implémentation de la fabrique de projet.

  2. Si vous souhaitez effectuer une mise à niveau sur place à l’ouverture de la solution, spécifiez l’indicateur PUVFF_SXSBACKUP en tant que paramètre VSPUVF_FLAGS dans votre implémentation d’UpgradeProject.

  3. Si vous souhaitez effectuer une mise à niveau sur place à l’ouverture de la solution, spécifiez l’indicateur PUVFF_COPYBACKUP en tant que paramètre VSPUVF_FLAGS dans votre implémentation d’UpgradeProject.

  4. Pour les étapes 2 et 3, vous pouvez implémenter les étapes de mise à niveau du fichier, avec IVsQueryEditQuerySave2, comme décrit dans la section « Implémentation d’IVsProjectUpgade » ci-dessous, ou déléguer la mise à niveau du fichier à IVsProjectUpgrade.

  5. Utilisez les méthodes d’IVsUpgradeLogger pour publier les messages de mise à niveau à l’intention de l’utilisateur à l’aide de l’Assistant Migration de Visual Studio.

  6. L’interface IVsFileUpgrade permet d’implémenter tout type de mise à niveau de fichier devant être effectuée dans le cadre de la mise à niveau du projet. Cette interface n’est pas appelée à partir de l’interface IVsProjectUpgradeViaFactory. Elle fournit un mécanisme de mise à niveau de fichiers qui font partie du système de projet, mais dont celui-ci n’a pas directement connaissance. Par exemple, cette situation peut se produire si les fichiers et les propriétés liés au compilateur ne sont pas gérés par la même équipe de développement que celle qui gère le reste du système de projet.

Implémentation d’IVsProjectUpgrade

Si votre système de projet implémente IVsProjectUpgrade uniquement, il ne peut pas participer à l’Assistant Conversion de Visual Studio. Toutefois, même si vous implémentez l’interface IVsProjectUpgradeViaFactory, vous pouvez déléguer la mise à niveau du fichier à l’implémentation d’IVsProjectUpgrade.

Pour implémenter IVsProjectUpgrade

  1. Quand un utilisateur tente d’ouvrir un projet, la méthode UpgradeProject est appelée par l’environnement après l’ouverture du projet et avant toute autre action de l’utilisateur sur le projet. Si l’utilisateur a déjà été invité à mettre à niveau la solution, l’indicateur UPF_SILENTMIGRATE est passé au paramètre grfUpgradeFlags. Si l’utilisateur ouvre directement un projet, par exemple à l’aide de la commande Ajouter un projet existant , l’indicateur UPF_SILENTMIGRATE n’est pas passé et le projet doit inviter l’utilisateur à effectuer la mise à niveau.

  2. En réponse à l’appel à UpgradeProject, le projet doit évaluer si le fichier projet a été mis à niveau. Si le projet n’a pas besoin de mettre à niveau le type de projet vers une nouvelle version, il peut simplement retourner l’indicateur S_OK.

  3. Si le projet doit mettre à niveau le type de projet vers une nouvelle version, il doit déterminer si le fichier projet peut être modifié en appelant la méthode QueryEditFiles et en passant une valeur de tagVSQueryEditFlags pour le paramètre rgfQueryEdit. Ensuite, le projet doit effectuer les opérations suivantes :

  4. Si l’appel à QueryEditFiles sur le fichier projet entraîne l’extraction du fichier et la récupération de la version la plus récente, le projet est déchargé et rechargé. La méthode UpgradeProject est rappelée après la création d’une autre instance du projet. À ce deuxième appel, le fichier projet peut être écrit sur le disque. Il est recommandé que le projet enregistre une copie du fichier projet dans le format antérieur avec l’extension de fichier .OLD, qu’il apporte les modifications nécessaires pour la mise à niveau, puis qu’il enregistre le fichier projet dans le nouveau format. Là encore, si une étape de la mise à niveau échoue, la méthode doit indiquer une erreur en retournant VS_E_PROJECTMIGRATIONFAILED. Le projet est alors déchargé dans l’Explorateur de solutions.

    Il est important de bien comprendre le déroulement du processus exécuté dans l’environnement quand l’appel à la méthode QueryEditFiles (en spécifiant une valeur pour ReportOnly) retourne les indicateurs QER_EditNotOK et QER_ReadOnlyUnderScc.

  5. L’utilisateur tente d’ouvrir le fichier projet.

  6. L’environnement appelle votre implémentation de CanCreateProject.

  7. Si CanCreateProject retourne true, l’environnement appelle votre implémentation de CanCreateProject.

  8. L’environnement appelle votre implémentation de Load pour ouvrir le fichier et initialiser l’objet projet, par exemple, Projet1.

  9. L’environnement appelle votre implémentation d’ IVsProjectUpgrade::UpgradeProject pour déterminer si le fichier projet doit être mis à niveau.

  10. Vous appelez QueryEditFiles et passez une valeur de QEF_ReportOnly pour le paramètre rgfQueryEdit.

  11. L’environnement retourne QER_EditNotOK pour VSQueryEditResult et le bit QER_ReadOnlyUnderScc est défini dans VSQueryEditResultFlags.

  12. Votre implémentation d’IVsProjectUpgrade appelle IVsQueryEditQuerySave::QueryEditFiles (QEF_ForceEdit_NoPrompting, QEF_DisallowInMemoryEdits).

Cet appel peut entraîner l’extraction d’une nouvelle copie de votre fichier projet et la récupération de la version la plus récente, ainsi que la nécessité de recharger votre fichier projet. À ce stade, il y a deux cas de figure possibles :

  • Si vous gérez votre propre rechargement du projet, l’environnement appelle votre implémentation de ReloadItem (VSITEMID_ROOT). Quand vous recevez cet appel, rechargez la première instance de votre projet (Projet1) et continuez la mise à niveau de votre fichier projet. L’environnement sait que vous gérez votre propre rechargement du projet si vous retournez true pour GetProperty (VSHPROPID_HandlesOwnReload).

  • Si vous ne gérez pas votre propre rechargement du projet, retournez false pour GetProperty (VSHPROPID_HandlesOwnReload). Dans ce cas, avant QueryEditFiles(QEF_ForceEdit_NoPrompting, QEF_DisallowInMemoryEdits) retourne, l’environnement crée une autre instance de votre projet, par exemple Project2, comme suit :

    1. L’environnement appelle Close sur le premier objet projet (Projet1), ce qui fait passer cet objet à l’état inactif.

    2. L’environnement appelle votre implémentation d’ IVsProjectFactory::CreateProject pour créer une deuxième instance de votre projet (Projet2).

    3. L’environnement appelle votre implémentation d’ IPersistFileFormat::Load pour ouvrir le fichier et initialiser le deuxième objet projet (Projet2).

    4. L’environnement appelle IVsProjectUpgrade::UpgradeProject une deuxième fois pour déterminer si l’objet projet doit être mis à niveau. Toutefois, cet appel est effectué sur la nouvelle instance (la deuxième) du projet, Projet2. Il s’agit du projet qui est ouvert dans la solution.

      Remarque

      Dans l’instance de votre premier projet, Projet1, qui est à l’état inactif, vous devez retourner S_OK à partir du premier appel à votre implémentation d’UpgradeProject.

    5. Vous appelez QueryEditFiles et passez une valeur de QEF_ReportOnly pour le paramètre rgfQueryEdit.

    6. L’environnement retourne QER_EditOK. La mise à niveau peut continuer, car le fichier projet peut être modifié.

Si la mise à niveau échoue, retournez VS_E_PROJECTMIGRATIONFAILED à partir d’IVsProjectUpgrade::UpgradeProject. Si aucune mise à niveau n’est nécessaire ou si vous choisissez de ne pas faire la mise à niveau, gérez l’appel IVsProjectUpgrade::UpgradeProject comme une absence d’opération. Si vous retournez VS_E_PROJECTMIGRATIONFAILED, un nœud d’espace réservé est ajouté à la solution pour votre projet.

Mise à niveau d’éléments de projet

Si vous ajoutez ou gérez des éléments à l’intérieur des systèmes de projet que vous n’implémentez pas, vous devrez peut-être participer au processus de mise à niveau du projet. Crystal Reports est un exemple d’élément qui peut être ajouté au système de projet.

En règle générale, les implémenteurs d’éléments de projet souhaitent tirer parti d’un projet déjà instancié et mis à niveau, car ils doivent savoir quels sont les références du projet et quelles autres propriétés de projet sont là pour prendre une décision de mise à niveau.

Pour obtenir la notification de mise à niveau du projet

  1. Définissez l’indicateur SolutionOrProjectUpgrading (défini dans vsshell80.idl) dans l’implémentation de votre élément de projet. Cela entraîne le chargement automatique de l’élément de projet VSPackage lorsque l’interpréteur de commandes Visual Studio détermine qu’un système de projet est en cours de mise à niveau.

  2. Conseiller l’interface IVsSolutionEventsProjectUpgrade via la AdviseSolutionEvents méthode.

  3. L’interface IVsSolutionEventsProjectUpgrade est déclenchée une fois que l’implémentation du système de projet a terminé ses opérations de mise à niveau et que le nouveau projet mis à niveau est créé. Selon le scénario, l’interface IVsSolutionEventsProjectUpgrade est déclenchée après le OnAfterOpenSolution, le OnAfterOpenProjectou les OnAfterLoadProject méthodes.

Pour mettre à niveau les fichiers d’élément de projet

  1. Vous devez gérer soigneusement le processus de sauvegarde de fichiers dans l’implémentation de l’élément de projet. Cela s’applique en particulier à une sauvegarde côte à côte, où le fUpgradeFlag paramètre de la UpgradeProject méthode est défini PUVFF_SXSBACKUPsur , où les fichiers qui ont été sauvegardés sont placés le long des fichiers côte à côte désignés en tant que . old ». Les fichiers sauvegardés antérieurs à l’heure système pendant laquelle le projet a été mis à niveau peuvent être désignés comme obsolètes. En outre, elles peuvent être remplacées, sauf si vous prenez des mesures spécifiques pour éviter cela.

  2. Au moment où votre élément de projet reçoit une notification de la mise à niveau du projet, l’Assistant Conversion de Visual Studio s’affiche toujours. Par conséquent, vous devez utiliser les méthodes de l’interface IVsUpgradeLogger pour fournir des messages de mise à niveau vers l’interface utilisateur de l’Assistant.