2009-11-09 3 views
2

J'essaye d'exécuter des tests automatisés sur un produit particulier. Le test consiste à installer le produit à différents emplacements sur le disque dur, puis à effectuer certaines opérations sur celui-ci, puis à fermer l'application.Comment décharger les assemblages du GAC?

Le code qui lance le processus ressemble à ceci:

using (Process process = new Process()) 
      { 
       process.StartInfo.FileName = "C:\mylocation\myapp.exe"; 
       process.Start(); 
      } 

Lors de l'exécution des tests en continu, lorsque l'emplacement d'installation des changements d'application, je reçois une exception du code ci-dessus qui dit:

Restriction de l'API: L'assembly 'file: /// C: \ alternate_location \ myapp.exe' a déjà été chargé à partir d'un autre emplacement . Il ne peut pas être chargé à partir d'un nouvel emplacement dans le même domaine d'application .

Les tests ne peuvent pas être exécutés en continu à cause de cela.

Que peut-on faire pour surmonter cela? Y at-il de toute façon que je peux décharger les assemblées du GAC? Est-ce que je peux faire quelque chose dans mon application de test pour remédier à cela OU faut-il changer quelque chose dans l'application que je suis en train de tester?

+0

Si vous ne chargez pas de contenu dans le GAC, vous l'enregistrez ou l'ajoutez. Par conséquent, vous ne «déchargez» pas, vous «supprimez» (d'où la confusion dans la réponse de Konamiman) –

+0

Ok. Merci pour la correction. – Poulo

+0

Quel cadre de test utilisez-vous? – serialhobbyist

Répondre

1

Vous ne pouvez pas décharger les assemblys d'un domaine d'application une fois chargé. Mais vous pouvez créer un nouveau domaine d'application (AppDomain class), charger les assemblages en son sein, les utiliser, puis décharger le domaine. Voir ici: Good example of use of AppDomain

+1

Cela n'a rien à voir avec AppDomains. Elle fait référence au GAC –

+0

Est-ce que le + 1er peut expliquer la pertinence de la réponse? (Je vais supprimer mes commentaires et/ou -1 s'il y a une bonne raison ...) –

+0

Relisez la question, elle a tout à voir avec AppDomains et peu de choses à voir avec le GAC. Malheureusement trop tard pour défaire mon -1 ...Quelqu'un peut-il jeter un +1 pour annuler s'il vous plaît: P –

1

Ajouter quelque chose au GAC ne fait pas partie intégrante de la définition du composant - il est généralement effectué par un installateur, etc.

L'outil gacutil peut être utilisé pour retirer votre outil du GAC. Dans 1.1, c'était dans le répertoire Framework. Dans les versions plus récentes, c'est dans le SDK, par exemple, C:\Program Files (x86)\Microsoft Visual Studio 8\SDK\v2.0\Bin

+0

Mais, je désinstalle l'application après chaque cas de test. (sinon je ne serais pas autorisé à installer une autre copie de celui-ci) Donc, ne devrait pas la désinstallation prendre soin de l'enlever aussi, si l'installation ajouté l'assemblée au GAC? En outre, je ne semble pas être en mesure de reproduire le problème en effectuant les tests manuellement. Cela semble donc être un problème de synchronisation. Alors suggérez-vous d'utiliser l'outil pour retirer l'assemblage du GAC après chaque test? Cela peut ne pas être viable pour moi, car j'exécute les tests sur des machines sur lesquelles seul le framework .NET est installé. (Pas de VS et SDK) Y a-t-il une autre issue? – Poulo

+0

On dirait qu'il y a beaucoup de confusion ici. Vous êtes sûr de mettre des choses dans le GAC? L'exception que vous obtenez est liée à la tentative de chargement de la même DLL deux fois à partir de différents emplacements dans le même AppDomain, ce qui peut être dû à plusieurs tests exécutés dans le même contexte [AppDomain]. La réponse de Konamiman est correcte. Vous devriez développer votre question pour expliquer quel cadre/mécanisme vous utilisez pour exécuter les tests - Ce sera la clé pour trouver la meilleure façon d'isoler les exions les uns des autres de manière appropriée. Quand vous dites 'installation', que voulez-vous dire, installutil? MSI? –

+0

Désolé. Voici ce qui se passe. J'ai une application de test qui exécute les cas de test les uns après les autres. Les cas de test sont essentiellement des méthodes d'une classe. Les tests visent à tester un installateur d'un produit. Ainsi, chaque cas de test installe le produit en utilisant un programme d'installation InstallShield, puis pour vérifier, je lance l'application (qui a été installée) en utilisant la méthode que j'ai décrite dans la question. Je fais quelques opérations de base, puis ferme l'application et la désinstalle. Le cas de test suivant répète la même chose, sauf que l'application est installée dans un autre emplacement. ... suite – Poulo

0

Pourriez-vous nous fournir plus d'informations? Je n'ai pas été capable de reproduire cette erreur. Process.Start devrait créer un nouveau processus avec son propre AppDomain.

Sur ma machine j'ai créé un projet Harness qui a une référence de projet à DoNothing qui est un assemblage fortement signé et une référence de projet à LaodDoNothing qui fait référence à c: \ DoNothing.exe. J'ai collé le code ci-dessous de Harness.Main avec les sorties de débogage comme commentaires en ligne. Les exes suffixés avec unsigned ne sont pas signés.

//debug outputs when Main is jitted:'Harness.vshost.exe' (Managed): Loaded 'c:\project\DoNothing\Harness\bin\Debug\DoNothing.exe', Symbols loaded. 
//debug outputs when Main is jitted:'Harness.vshost.exe' (Managed): Loaded 'c:\project\DoNothing\Harness\bin\Debug\LoadDoNothing.exe', Symbols loaded. 

ZaZaZa.Main(); 
LoadDoNothing.Program.Main(); 
using (Process process = new Process()) 
{ 
    process.StartInfo.FileName = @"C:\donothingunsigned.exe"; 
    process.Start(); //debug outputs The thread 0x17f0 has exited with code 0 (0x0). No assemblies loads are logged to debug because this is a separate process. 


} 

using (Process process = new Process()) 
{ 
    process.StartInfo.FileName = @"C:\3\donothingunsigned2.exe"; 
    process.Start(); //Debug outputs The thread 0x1014 has exited with code 0 (0x0). No assemblies loads are logged to debug because this is a separate process. 
} 
AppDomain.CurrentDomain.ExecuteAssembly(@"C:\donothingunsigned.exe"); //debug outputs 'Harness.vshost.exe' (Managed): Loaded 'C:\donothingunsigned.exe' 
AppDomain.CurrentDomain.ExecuteAssembly(@"C:\3\donothingunsigned2.exe"); //no debug output because the loader realizes this assembly has already been loaded and uses that. 
+0

Je n'ai pas vraiment compris ce que vous essayez de transmettre. Mais j'ai remarqué que vous avez démarré deux exécutables différents 'donothingunsigned.exe' et 'donothingunsigned2.exe'. Mon problème est associé à essayer de démarrer le même exécutable à partir de différents endroits. C'est ce qui me donne l'exception dans les circonstances que j'ai mentionnées dans la question ainsi que dans les commentaires ultérieurs. – Poulo

+0

Je n'ai pas pu reproduire l'erreur en utilisant les méthodes ci-dessus. Les processus ne partagent pas les domaines d'application, donc je ne vois pas comment Process.Start() pourrait causer votre erreur. –

Questions connexes