web-dev-qa-db-fra.com

Méthode non trouvée au moment de l'exécution

J'ai un projet ASP.Net C # essayant d'accéder aux méthodes d'une classe dans un autre projet. Cela fonctionne pour la première moitié des méthodes de la classe, mais pas pour l'autre moitié des méthodes de la classe que j'ai récemment ajoutées. Ils compilent, mais ils lancent une exception de méthode non trouvée au moment de l'exécution.

Est-ce que quelqu'un a des idées que je pourrais essayer? J'ai essayé:

  1. recréer le fichier .sln
  2. Subbing dans un autre projet de bibliothèque de classe, que je sais fonctionne. Il semble que l'erreur se trouve dans mon projet principal qui appelle la méthode dans l'autre projet.
24
Baconbeastnz

"Méthode non trouvée" est une erreur très spécifique, ce qui signifie une méthode elle attendue (c'est-à-dire qu'elle était au moment de la compilation) n'est tout simplement pas présente. Cela signifie généralement que les fichiers que vous êtes déploiement sont différents de ce que vous pensez qu'ils sont - spécifiquement, je parierais que vous déployez la version ancienne de la bibliothèque (qui manque de vos ajouts). ).

Vérifiez les dll déployées sur le serveur Web par rapport à ce que vous devriez être {pensez} _.

50
Marc Gravell

J'ai eu le même problème. Dans mon cas, cela a été causé par l’ajout d’un argument optionnel . Vous devez donc d’abord:

referenceencingAssembly:

referencedAssembly.DoStuff(firstArgument, secondArgument)

referenceAssembly:

public void DoStuff(string firstArgument, string secondArgument)
{
   //stuff to do
}

Ensuite, vous ajoutez un paramètre facultatif à la méthode, mais vous ne fournissez pas cet argument lors de son appel.

referenceencingAssembly:

referencedAssembly.DoStuff(firstArgument, secondArgument)//unchanged

referenceAssembly:

public void DoStuff(string firstArgument, string secondArgument, string thirdArgument = "default value")
{
   //stuff to do
}

Au niveau local, cela fonctionnera bien car la nouvelle version de referencingAssembly.dll aura une référence à la méthode DoStuff (string, string, string). Mais lorsque vous ne déployez que le referenceAssembly modifié (en pensant que l'argument ajouté était facultatif et que referncingAssembly fonctionne toujours), l'ancienne version de referenceencingAssembly renvoie un MethodNotFound, car elle recherche une méthode portant la signature DoStuff (string, string), qui est n'est plus présent dans referenceAssembly car nous avons ajouté l'argument supplémentaire (facultatif).


Une solution possible pourrait être une surcharge:

referenceAssembly:

public void DoStuff(string firstArgument, string secondArgument)//original method
{
   DoStuff(firstArgument, secondArgument, "default value")
}
public void DoStuff(string firstArgument, string secondArgument, string thirdArgument)//new overload of the method
{
//stuff to do
}

Vous pouvez également déployer la nouvelle génération referencingAssembly (qui fera référence à la méthode avec la signature DoStuff (chaîne, chaîne, chaîne)).

13
nozem

j'ai eu le même problème. Dans mon cas, la définition de "optimCompilations" sur "false" dans la configuration Web a résolu le problème.

9
Sebastien H.

J'ai fait face à ce genre de problème mais j'ai pu le résoudre. J'ai vidé mon dossier bin et de débogage et essayé de reconstruire le projet. cela a fonctionné, au moins pour moi. Ou essayez de nettoyer la solution et essayez de la reconstruire. Mais bien sûr, publier une partie de votre code pourrait être plus utile.

7
Sandy

J'ai eu un problème très similaire et j'ai constaté qu'une version plus ancienne de l'Assemblée avait été installée sur le GAC. Après avoir désinstallé cette version, le projet a été compilé et exécuté correctement. Vérifiez donc le GAC (C:\Windows\Assembly) pour vous assurer qu'il ne figure pas dans cette liste. 

4
Peter Jacoby

J'ai rencontré cette même exception aussi, bien que mon problème était différent, j'avais une méthode dans une de mes bibliothèques qui ressemblait à ça:

public void WriteMessage(string msg) 
{
    ...
}

et il y avait une nouvelle demande de modification et il s'est transformé en ceci:

public void WriteMessage(string msg, int code = 100)
{
    ...
}

après cela, j'ai mis à jour le projet qui utilise cette bibliothèque avec un binaire récemment compilé, il a commencé à lancer cette exception.

Après de nombreuses tentatives, rien n'a fonctionné, même le projet est propre, reconstruit, supprimant et rajoutant la référence, puis j'ai essayé de modifier l'appel de méthode du projet à partir de:

...
library.WriteMessage('hello!');
...

à:

...
library.WriteMessage('hello!', 100);
...

et puis compilé le projet, il a résolu le problème, après que je l'ai changé de nouveau à:

...
library.WriteMessage('hello!');
...

et maintenant tout a été réglé comme par magie, peut-être y avait-il une sorte de métadonnées en cache laissées quelque part qui ne sont pas mises à jour, et en changeant le nom de la méthode, rappelez-lui clairement que sa signature est différente, mais pas si différente.

J'espère que cela pourra aider quelqu'un qui fait face au même problème que moi.

4
Roy Yin

Deux projets dans votre solution: projet A et projet B. Les deux projets utilisent le package de nuget "DoStuff", mais des versions différentes du package DoStuff:

  • projet Une référence à la version 1.1 de DoStuff.
  • le projet B fait référence à la version 1.0 de DoStuff.
  • projet B référence projet A.

la version 1.1 a une nouvelle méthode, utilisée dans le projet A. Lorsque le projet B utilise le projet A, vous obtenez cette exception MethodNotFoundException car la version de DoStuff du projet B ne sait pas de quoi le projet A parle.

Pour éviter cela, nous avons mis en place un test unitaire qui échoue si les projets utilisent des versions différentes du même package de nuget. Une butée de porte relativement simple qui nous a évité quelques maux de tête ces dernières années.

3
increddibelly

J'ai rencontré le même problème lorsque j'exécutais une application avec les dlls gérées par le paquet Nuget. Il s’avère que lorsque j’essaie de mettre à jour les dll du gestionnaire de paquets Nuget, il n’a pas mis à jour ma couche de test . Je vous suggère de vérifier la version de dll à laquelle vous faites référence . Allez à ObjectBrower in VS et vérifiez sur les DLL et vérifiez l'emplacement de renvoi: assurez-vous que vous faites référence à la dernière DLL.

2
Owen Wang

Écoutez, cela doit être la cause la plus étrange de tous les temps, mais après une matinée entière à tout essayer, à reconstruire le projet à partir de zéro, etc., j'ai remarqué que la seule chose qui éviterait le problème serait que ma bibliothèque ait un nom différent pour l'Assemblée. 

Au fond de moi, une idée effroyable me faisait penser que j'avais déjà installé les versions précédentes de la DLL dans le GAC, mais je l'avais déjà vérifiée et d'ailleurs, ce n'était jamais mon intention. Mais en suivant cette piste, j'ai découvert que cette dll (et toutes les autres du projet!) Était installée dans C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\IDE !!!!!!

Aaaargh! J'imagine que je suis le seul à avoir tout gâché, mais je ne sais pas du tout pourquoi, je pensais pouvoir épargner à quelqu'un d'autre cette frustration de la possibilité lointaine que quelqu'un soit si malchanceux!

2
andycted

L'erreur s'est également produite lorsque j'avais une action en paramètre. J'ai passé une méthode sans l'envelopper dans une nouvelle action (..). 

DLL avait ceci:

public bool ShowMyForm(bool showConnectionWindow, Action onCloseNotify) {...}

L'application de test appelée DLL ressemble à ceci:

private void onFormClose()
{
    MessageBox.Show("Form Closed");
}

private void ShowForm()
{
     mydll.ShowMyForm(true, onFormClose ); // bug here: wrap in Action
}

Quand j'ai changé l'appel à 

mydll.ShowMyForm(true, new Action(onFormClose) );

l'exception a disparu. Le texte de l'exception est simplement trompeur - la méthode est là, mais le type du paramètre donnait une exception d'exécution. Dommage qu'il ne soit pas récupéré au moment de la compilation.

1
Willem

Mon cas était une petite variation des autres ici; mais cela pourrait aider quelqu'un… Je viens d'ajouter un argument optionnel dans une bibliothèque et de recevoir ce message de l'interface graphique utilisant cette bibliothèque.

Le problème était dû à l'interface utilisateur graphique et à l'une de ses bibliothèques référençant la même bibliothèque, mais une autre n'était pas à jour.

J'ai 

  • GUI référençant LibA et LibZ
  • LibA référençant LibZ

Donc, je viens de supprimer tous les dossiers "bin" et "obj" de LibA et de GUI, en veillant à avoir la mise à jour DLL de LibZ dans les deux, et tout fonctionne à nouveau.

1
Mickael V.

J'ai eu le même problème, puis j'ai changé le nom de la méthode en un autre nom et changé les références. alors cela fonctionne très bien. Je ne sais pas quel était le problème, mais il semble qu'il y ait un bogue lors de la modification du nom d'une méthode. Dans certaines circonstances, il n'est pas appliqué à l'ensemble du système.

1
smoothumut

Cela peut être une réponse tardive: Mais une solution possible consiste à nettoyer le dossier des fichiers ASP.NET temporaires: C’est-à-dire C:\Windows\Microsoft.NET\Framework\vX.X.XXXXX\ASP temporaire. Fichiers NET 

Supprimez les dossiers liés à votre site Web et reconstruisez la solution.

0
Nirman

Je n'ai pas pu résoudre le problème avec aucune des réponses suggérées .. Je ne pouvais pas trouver d'anciennes versions de l'Assemblée personnalisée. J'ai littéralement cherché partout avec l'outil Tout. En mode débogage, la bonne version de l’Assembly était affichée, mais la méthode n’était toujours pas trouvée.

L'activation Liaison automatique dans le fichier .csproj l'a corrigé pour moi

<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>

Je visais un package de .NET Framework 4.5 dans mon projet. Le paramètre ci-dessus n'est pas nécessaire si tous les packages du projet cible .NET Framework 4.5.1 ou version ultérieure.

0
Rubanov

J'ai eu ce problème lorsque j'avais copié la solution vers un autre emplacement sur une autre machine. Le dossier de construction a juste besoin d'être changé. Ne me demandez pas pourquoi mais la solution a été construite dans le dossier de construction (nous appellerons ce dossier A), puis une ancienne copie a été copiée du dossier B vers le dossier C. Au moment de l'exécution, mon dernier code n'a pas été trouvé car il était En regardant une ancienne version dans le dossier C. Dans Propriétés pour la solution dans l'onglet Générer, j'ai modifié le chemin de sortie vers le dossier B. Il a ensuite créé la dernière version dans le dossier B, qu'elle a copiée dans le dossier C et tout a fonctionné à nouveau.

Le peu que je ne sais pas, c'est pourquoi nous avons le dossier C en premier lieu. J'ai une solution de test codedUI et le dossier C est "C:\Utilisateurs \\ Documents\MyCodedUISolution\TestResults\_ 2017-04-20 11_31_29\Out". Je ne sais pas à quoi cela sert et pourquoi il a été créé, mais si l'ancien code est copié ici parce que vous modifiez le chemin de sortie ou que vous déplacez la solution sans modifier le chemin de sortie en fonction de ce qui est nécessaire, vous avez un problème.

0
Ewan

Dans mon cas, j'avais changé le type de retour d'une méthode d'IQueryable à IEnumerable.

J'avais recompilé et téléchargé la DLL contenant la méthode, mais pas la DLL avec le code qui appelle la méthode. L'appel DLL attendait donc toujours la méthode avec le type de retour précédent et ne pouvait pas le trouver.

0
rdans

J'ai été confronté au même problème, même si j'ai nettoyé et reconstruit la solution pas aidé .. lorsque j'ai publié l'application, l'ancienne version de dll était dans le dossier bin. J'ai donc changé la version de Assembly dans le fichier assemblyinfo. enfin son fonctionnement . La nouvelle version est disponible dans le dossier bin.

0
King_Fisher

Dans mon cas, je me suis déployé sur un PC .NET 3.0 (Windows XP) alors que la cible de la compilation était .NET 3.5. Je me demande vraiment pourquoi il n'y a pas d'avertissement plus élémentaire ...

Le problème a été l'utilisation de DataContract à partir de System.Runtime.Serialisation.

0
Martin Meeser