Des messages d’exception en anglais?

Nous enregistrons toutes les exceptions qui se produisent dans notre système en écrivant le message Exception.Message dans un fichier. Cependant, ils sont écrits dans la culture du client. Et les erreurs turques ne signifient pas grand chose pour moi.

Alors, comment pouvons-nous enregistrer des messages d’erreur en anglais sans changer la culture des utilisateurs?

Ce problème peut être partiellement résolu. Le code d’exception Framework charge les messages d’erreur à partir de ses ressources, en fonction des parameters régionaux du thread en cours. Dans le cas de certaines exceptions, cela se produit lors de l’access à la propriété Message.

Pour ces exceptions, vous pouvez obtenir la version complète en anglais américain du message en basculant brièvement les parameters régionaux du thread vers en-US tout en le connectant (en enregistrant au préalable les parameters régionaux de l’utilisateur d’origine et en les restaurant immédiatement après).

Faire ceci sur un thread séparé est encore mieux: cela garantit qu’il n’y aura pas d’effets secondaires. Par exemple:

try { System.IO.StreamReader sr=new System.IO.StreamReader(@"c:\does-not-exist"); } catch(Exception ex) { Console.WriteLine(ex.ToSsortingng()); //Will display localized message ExceptionLogger el = new ExceptionLogger(ex); System.Threading.Thread t = new System.Threading.Thread(el.DoLog); t.CurrentUICulture = new System.Globalization.CultureInfo("en-US"); t.Start(); } 

Où la classe ExceptionLogger ressemble à quelque chose comme:

 class ExceptionLogger { Exception _ex; public ExceptionLogger(Exception ex) { _ex = ex; } public void DoLog() { Console.WriteLine(_ex.ToSsortingng()); //Will display en-US message } } 

Cependant, comme Joe le souligne correctement dans un commentaire sur une révision antérieure de cette réponse, certains messages sont déjà (partiellement) chargés à partir des ressources linguistiques au moment où l’exception est générée.

Cela s’applique à la partie “paramètre ne peut pas être nulle” du message généré lorsqu’une exception ArgumentNullException (“foo”) est émise, par exemple. Dans ces cas, le message apparaîtra toujours (partiellement) localisé, même si vous utilisez le code ci-dessus.

En dehors de l’utilisation de hacks peu pratiques, comme exécuter tout votre code non-interface utilisateur sur un thread avec des parameters régionaux en-US pour commencer, il ne semble pas y avoir beaucoup à faire: le code d’exception .NET Framework n’a pas installations pour remplacer les parameters régionaux de message d’erreur.

Vous pouvez rechercher le message d’exception d’origine sur unlocalize.com

Un point litigieux peut-être, mais au lieu de définir la culture en-US , vous pouvez la définir sur Invariant . Dans la culture Invariant , les messages d’erreur sont en anglais.

 Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture; Thread.CurrentThread.CurrentUICulture = CultureInfo.InvariantCulture; 

Il a l’avantage de ne pas avoir l’air biaisé, en particulier pour les pays anglophones non américains. (aka évite les remarques sournoises de collègues)

Windows doit avoir la langue de l’interface utilisateur que vous souhaitez utiliser installée. Si ce n’est pas le cas, il n’a aucun moyen de savoir comme par magie le message traduit.

Dans Windows 7 ultime, avec pt-PT, le code suivant:

 Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("pt-PT"); ssortingng msg1 = new DirectoryNotFoundException().Message; Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("en-US"); ssortingng msg2 = new FileNotFoundException().Message; Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo("fr-FR"); ssortingng msg3 = new FileNotFoundException().Message; 

Produit des messages en pt-PT, en-US et en-US. Comme il n’y a pas de fichier de culture français installé, la langue par défaut de Windows (installée?) Est utilisée.

Voici une solution qui ne nécessite aucun codage et fonctionne même pour des textes d’exceptions qui sont chargés trop tôt pour que nous puissions changer par code (par exemple, ceux de mscorlib).

Cela peut ne pas être toujours applicable dans tous les cas (cela dépend de votre configuration car vous devez être capable de créer un fichier .config en plus du fichier principal .exe), mais cela fonctionne pour moi. Donc, il suffit de créer un app.config dans dev, (ou un [myapp].exe.config ou web.config en production) contenant par exemple les lignes suivantes:

  ...             ...  

Qu’est-ce que cela fait est d’indiquer à la structure de redirect les liaisons d’assemblage pour les ressources de mscorlib et les ressources de System.Xml, pour les versions entre 1 et 999, en français (culture est définie sur “fr”) à un assembly qui n’existe pas version arbitraire 999).

Ainsi, lorsque le CLR recherchera des ressources françaises pour ces deux assemblages (mscorlib et System.xml), il ne les trouvera pas et utilisera l’anglais avec aisance. Selon votre contexte et vos tests, vous souhaiterez peut-être append d’autres assemblys à ces redirections (assemblages contenant des ressources localisées).

Bien sûr, je ne pense pas que cela soit pris en charge par Microsoft, donc utilisez-le à vos risques et périls. Eh bien, si vous détectez un problème, vous pouvez simplement supprimer cette configuration et vérifier qu’elle n’est pas liée.

Je sais que c’est un vieux sujet, mais je pense que ma solution peut être tout à fait pertinente pour quiconque le rencontre dans une recherche sur le Web:

Dans le journal des exceptions, vous pouvez enregistrer ex.GetType.ToSsortingng, ce qui enregistre le nom de la classe d’exception. Je m’attendrais à ce que le nom d’une classe soit indépendant du langage et serait donc toujours représenté en anglais (par exemple, “System.FileNotFoundException”), bien qu’à l’heure actuelle je n’ai pas access à un système de langue étrangère pour tester le idée.

Si vous voulez vraiment le texte du message d’erreur, vous pouvez créer un dictionnaire de tous les noms de classe d’exception possibles et leurs messages équivalents dans la langue de votre choix, mais pour l’anglais, je pense que le nom de la classe est parfaitement adapté.

Paramétrer Thread.CurrentThread.CurrentUICulture sera utilisé pour localiser les exceptions. Si vous avez besoin de deux types d’exceptions (une pour l’utilisateur et une pour vous), vous pouvez utiliser la fonction suivante pour traduire le message d’exception. Il cherche dans les ressources .NET-Libraries le texte original pour obtenir la clé de ressource, puis retourne la valeur traduite. Mais il y a une faiblesse que je n’ai pas encore trouvé de bonne solution: les messages, qui contiennent {0} dans les ressources, ne seront pas trouvés. Si quelqu’un a une bonne solution, je vous en serais reconnaissant.

 public static ssortingng TranslateExceptionMessage(Exception E, CultureInfo targetCulture) { try { Assembly a = E.GetType().Assembly; ResourceManager rm = new ResourceManager(a.GetName().Name, a); ResourceSet rsOriginal = rm.GetResourceSet(Thread.CurrentThread.CurrentUICulture, true, true); ResourceSet rsTranslated = rm.GetResourceSet(targetCulture, true, true); foreach (DictionaryEntry item in rsOriginal) if (item.Value.ToSsortingng() == E.Message.ToSsortingng()) return rsTranslated.GetSsortingng(item.Key.ToSsortingng(), false); // success } catch { } return E.Message; // failed (error or cause it's not intelligent enough to locale '{0}'-patterns } 

J’imagine l’une de ces approches:

1) Les exceptions ne sont lues que par vous, c’est-à-dire qu’elles ne sont pas une fonctionnalité client, vous pouvez donc utiliser des chaînes non localisées et câblées qui ne changeront pas lorsque vous exécuterez en mode turc.

2) Inclure un code d’erreur, par exemple. 0X00000001 avec chaque erreur afin que vous puissiez facilement le chercher dans un tableau anglais.

 CultureInfo oldCI = Thread.CurrentThread.CurrentCulture; Thread.CurrentThread.CurrentCulture = CultureInfo.CreateSpecificCulture ("en-US"); Thread.CurrentThread.CurrentUICulture=new CultureInfo("en-US"); try { System.IO.StreamReader sr=new System.IO.StreamReader(@"c:\does-not-exist"); } catch(Exception ex) { Console.WriteLine(ex.ToSsortingng()) } Thread.CurrentThread.CurrentCulture = oldCI; Thread.CurrentThread.CurrentUICulture = oldCI; 

Sans WORKAROUNDS.

Tks 🙂

Le framework .NET se compose de deux parties:

  1. Le framework .NET lui-même
  2. Les modules linguistiques du framework .NET

Tous les textes (ex. Messages d’exception, étiquettes de boutons sur un MessageBox, etc.) sont en anglais dans le framework .NET lui-même. Les packs de langue ont les textes localisés.

Selon votre situation exacte, une solution consisterait à désinstaller les modules linguistiques (c.-à-d., Demander au client de le faire). Dans ce cas, les textes d’exception seront en anglais. Notez toutefois que tous les autres textes fournis par le framework seront également en anglais (par exemple, les étiquettes des boutons sur un MessageBox, les raccourcis clavier pour les commandes ApplicationCommands).

J’ai eu la même situation et toutes les réponses que j’ai trouvées ici et ailleurs n’ont pas aidé ou n’étaient pas satisfaisantes:
Forcer la langue des exceptions en anglais
C # – Obtenir des messages d’exception en anglais lorsque l’application est dans une autre langue?
Comment changer la langue du message d’exception Visual Studio en anglais pendant le débogage
Comment gérer la traduction du message d’exception?
Comment éviter complètement les messages d’exception localisés .NET

Le Thread.CurrentUICulture modifie la langue des exceptions .net, mais pas pour Win32Exception , qui utilise des ressources Windows dans la langue de l’interface utilisateur Windows elle-même. Donc, je n’ai jamais réussi à imprimer les messages de Win32Exception en anglais au lieu de l’allemand, même en utilisant FormatMessage() comme décrit dans
Comment obtenir Win32Exception en anglais?

J’ai donc créé ma propre solution, qui stocke la majorité des messages d’exception existants pour différentes langues dans des fichiers externes. Vous n’obtiendrez pas le message très précis dans la langue de votre choix, mais vous recevrez un message dans cette langue, ce qui est beaucoup plus que ce que vous obtenez actuellement (un message dans une langue que vous ne comprenez probablement pas).

Les fonctions statiques de cette classe peuvent être exécutées sur des installations Windows avec des langages différents: CreateMessages() crée les textes spécifiques à la culture
SaveMessagesToXML() enregistre dans autant de fichiers XML que les langues créées ou chargées
LoadMessagesFromXML() charge tous les fichiers XML avec des messages spécifiques à la langue

Lors de la création des fichiers XML sur différentes installations Windows avec des langages différents, vous aurez bientôt toutes les langues dont vous avez besoin.
Vous pouvez peut-être créer les textes pour différentes langues sur 1 Windows lorsque vous avez installé plusieurs packs de langue MUI, mais je ne l’ai pas encore testé.

Testé avec VS2008, prêt à l’emploi. Les commentaires et suggestions sont les bienvenus!

 using System; using System.Collections.Generic; using System.ComponentModel; using System.Globalization; using System.Reflection; using System.Threading; using System.Xml; public struct CException { //---------------------------------------------------------------------------- public CException(Exception i_oException) { m_oException = i_oException; m_oCultureInfo = null; m_sMessage = null; } //---------------------------------------------------------------------------- public CException(Exception i_oException, ssortingng i_sCulture) { m_oException = i_oException; try { m_oCultureInfo = new CultureInfo(i_sCulture); } catch { m_oCultureInfo = CultureInfo.InvariantCulture; } m_sMessage = null; } //---------------------------------------------------------------------------- public CException(Exception i_oException, CultureInfo i_oCultureInfo) { m_oException = i_oException; m_oCultureInfo = i_oCultureInfo == null ? CultureInfo.InvariantCulture : i_oCultureInfo; m_sMessage = null; } //---------------------------------------------------------------------------- // GetMessage //---------------------------------------------------------------------------- public ssortingng GetMessage() { return GetMessage(m_oException, m_oCultureInfo); } public ssortingng GetMessage(Ssortingng i_sCulture) { return GetMessage(m_oException, i_sCulture); } public ssortingng GetMessage(CultureInfo i_oCultureInfo) { return GetMessage(m_oException, i_oCultureInfo); } public static ssortingng GetMessage(Exception i_oException) { return GetMessage(i_oException, CultureInfo.InvariantCulture); } public static ssortingng GetMessage(Exception i_oException, ssortingng i_sCulture) { CultureInfo oCultureInfo = null; try { oCultureInfo = new CultureInfo(i_sCulture); } catch { oCultureInfo = CultureInfo.InvariantCulture; } return GetMessage(i_oException, oCultureInfo); } public static ssortingng GetMessage(Exception i_oException, CultureInfo i_oCultureInfo) { if (i_oException == null) return null; if (i_oCultureInfo == null) i_oCultureInfo = CultureInfo.InvariantCulture; if (ms_dictCultureExceptionMessages == null) return null; if (!ms_dictCultureExceptionMessages.ContainsKey(i_oCultureInfo)) return CreateMessage(i_oException, i_oCultureInfo); Dictionary dictExceptionMessage = ms_dictCultureExceptionMessages[i_oCultureInfo]; ssortingng sExceptionName = i_oException.GetType().FullName; sExceptionName = MakeXMLCompliant(sExceptionName); Win32Exception oWin32Exception = (Win32Exception)i_oException; if (oWin32Exception != null) sExceptionName += "_" + oWin32Exception.NativeErrorCode; if (dictExceptionMessage.ContainsKey(sExceptionName)) return dictExceptionMessage[sExceptionName]; else return CreateMessage(i_oException, i_oCultureInfo); } //---------------------------------------------------------------------------- // CreateMessages //---------------------------------------------------------------------------- public static void CreateMessages(CultureInfo i_oCultureInfo) { Thread oTH = new Thread(new ThreadStart(CreateMessagesInThread)); if (i_oCultureInfo != null) { oTH.CurrentCulture = i_oCultureInfo; oTH.CurrentUICulture = i_oCultureInfo; } oTH.Start(); while (oTH.IsAlive) { Thread.Sleep(10); } } //---------------------------------------------------------------------------- // LoadMessagesFromXML //---------------------------------------------------------------------------- public static void LoadMessagesFromXML(ssortingng i_sPath, ssortingng i_sBaseFilename) { if (i_sBaseFilename == null) i_sBaseFilename = msc_sBaseFilename; ssortingng[] asFiles = null; try { asFiles = System.IO.Directory.GetFiles(i_sPath, i_sBaseFilename + "_*.xml"); } catch { return; } ms_dictCultureExceptionMessages.Clear(); for (int ixFile = 0; ixFile < asFiles.Length; ixFile++) { string sXmlPathFilename = asFiles[ixFile]; XmlDocument xmldoc = new XmlDocument(); try { xmldoc.Load(sXmlPathFilename); XmlNode xmlnodeRoot = xmldoc.SelectSingleNode("/" + msc_sXmlGroup_Root); string sCulture = xmlnodeRoot.SelectSingleNode(msc_sXmlGroup_Info + "/" + msc_sXmlData_Culture).Value; CultureInfo oCultureInfo = new CultureInfo(sCulture); XmlNode xmlnodeMessages = xmlnodeRoot.SelectSingleNode(msc_sXmlGroup_Messages); XmlNodeList xmlnodelistMessage = xmlnodeMessages.ChildNodes; Dictionary dictExceptionMessage = new Dictionary(xmlnodelistMessage.Count + 10); for (int ixNode = 0; ixNode < xmlnodelistMessage.Count; ixNode++) dictExceptionMessage.Add(xmlnodelistMessage[ixNode].Name, xmlnodelistMessage[ixNode].InnerText); ms_dictCultureExceptionMessages.Add(oCultureInfo, dictExceptionMessage); } catch { return; } } } //---------------------------------------------------------------------------- // SaveMessagesToXML //---------------------------------------------------------------------------- public static void SaveMessagesToXML(string i_sPath, string i_sBaseFilename) { if (i_sBaseFilename == null) i_sBaseFilename = msc_sBaseFilename; foreach (KeyValuePair> kvpCultureExceptionMessages in ms_dictCultureExceptionMessages) { ssortingng sXmlPathFilename = i_sPath + i_sBaseFilename + "_" + kvpCultureExceptionMessages.Key.TwoLetterISOLanguageName + ".xml"; Dictionary dictExceptionMessage = kvpCultureExceptionMessages.Value; XmlDocument xmldoc = new XmlDocument(); XmlWriter xmlwriter = null; XmlWriterSettings writerSettings = new XmlWriterSettings(); writerSettings.Indent = true; try { XmlNode xmlnodeRoot = xmldoc.CreateElement(msc_sXmlGroup_Root); xmldoc.AppendChild(xmlnodeRoot); XmlNode xmlnodeInfo = xmldoc.CreateElement(msc_sXmlGroup_Info); XmlNode xmlnodeMessages = xmldoc.CreateElement(msc_sXmlGroup_Messages); xmlnodeRoot.AppendChild(xmlnodeInfo); xmlnodeRoot.AppendChild(xmlnodeMessages); XmlNode xmlnodeCulture = xmldoc.CreateElement(msc_sXmlData_Culture); xmlnodeCulture.InnerText = kvpCultureExceptionMessages.Key.Name; xmlnodeInfo.AppendChild(xmlnodeCulture); foreach (KeyValuePair kvpExceptionMessage in dictExceptionMessage) { XmlNode xmlnodeMsg = xmldoc.CreateElement(kvpExceptionMessage.Key); xmlnodeMsg.InnerText = kvpExceptionMessage.Value; xmlnodeMessages.AppendChild(xmlnodeMsg); } xmlwriter = XmlWriter.Create(sXmlPathFilename, writerSettings); xmldoc.WriteTo(xmlwriter); } catch (Exception e) { return; } finally { if (xmlwriter != null) xmlwriter.Close(); } } } //---------------------------------------------------------------------------- // CreateMessagesInThread //---------------------------------------------------------------------------- private static void CreateMessagesInThread() { Thread.CurrentThread.Name = "CException.CreateMessagesInThread"; Dictionary dictExceptionMessage = new Dictionary(0x1000); GetExceptionMessages(dictExceptionMessage); GetExceptionMessagesWin32(dictExceptionMessage); ms_dictCultureExceptionMessages.Add(Thread.CurrentThread.CurrentUICulture, dictExceptionMessage); } //---------------------------------------------------------------------------- // GetExceptionTypes //---------------------------------------------------------------------------- private static List GetExceptionTypes() { Assembly[] aoAssembly = AppDomain.CurrentDomain.GetAssemblies(); List listoExceptionType = new List(); Type oExceptionType = typeof(Exception); for (int ixAssm = 0; ixAssm < aoAssembly.Length; ixAssm++) { if (!aoAssembly[ixAssm].GlobalAssemblyCache) continue; Type[] aoType = aoAssembly[ixAssm].GetTypes(); for (int ixType = 0; ixType < aoType.Length; ixType++) { if (aoType[ixType].IsSubclassOf(oExceptionType)) listoExceptionType.Add(aoType[ixType]); } } return listoExceptionType; } //---------------------------------------------------------------------------- // GetExceptionMessages //---------------------------------------------------------------------------- private static void GetExceptionMessages(Dictionary i_dictExceptionMessage) { List listoExceptionType = GetExceptionTypes(); for (int ixException = 0; ixException < listoExceptionType.Count; ixException++) { Type oExceptionType = listoExceptionType[ixException]; string sExceptionName = MakeXMLCompliant(oExceptionType.FullName); try { if (i_dictExceptionMessage.ContainsKey(sExceptionName)) continue; Exception e = (Exception)(Activator.CreateInstance(oExceptionType)); i_dictExceptionMessage.Add(sExceptionName, e.Message); } catch (Exception) { i_dictExceptionMessage.Add(sExceptionName, null); } } } //---------------------------------------------------------------------------- // GetExceptionMessagesWin32 //---------------------------------------------------------------------------- private static void GetExceptionMessagesWin32(Dictionary i_dictExceptionMessage) { ssortingng sTypeName = MakeXMLCompliant(typeof(Win32Exception).FullName) + "_"; for (int iError = 0; iError < 0x4000; iError++) // Win32 errors may range from 0 to 0xFFFF { Exception e = new Win32Exception(iError); if (!e.Message.StartsWith("Unknown error (", StringComparison.OrdinalIgnoreCase)) i_dictExceptionMessage.Add(sTypeName + iError, e.Message); } } //---------------------------------------------------------------------------- // CreateMessage //---------------------------------------------------------------------------- private static string CreateMessage(Exception i_oException, CultureInfo i_oCultureInfo) { CException oEx = new CException(i_oException, i_oCultureInfo); Thread oTH = new Thread(new ParameterizedThreadStart(CreateMessageInThread)); oTH.Start(oEx); while (oTH.IsAlive) { Thread.Sleep(10); } return oEx.m_sMessage; } //---------------------------------------------------------------------------- // CreateMessageInThread //---------------------------------------------------------------------------- private static void CreateMessageInThread(Object i_oData) { if (i_oData == null) return; CException oEx = (CException)i_oData; if (oEx.m_oException == null) return; Thread.CurrentThread.CurrentUICulture = oEx.m_oCultureInfo == null ? CultureInfo.InvariantCulture : oEx.m_oCultureInfo; // create new exception in desired culture Exception e = null; Win32Exception oWin32Exception = (Win32Exception)(oEx.m_oException); if (oWin32Exception != null) e = new Win32Exception(oWin32Exception.NativeErrorCode); else { try { e = (Exception)(Activator.CreateInstance(oEx.m_oException.GetType())); } catch { } } if (e != null) oEx.m_sMessage = e.Message; } //---------------------------------------------------------------------------- // MakeXMLCompliant // from https://www.w3.org/TR/xml/ //---------------------------------------------------------------------------- private static string MakeXMLCompliant(string i_sName) { if (string.IsNullOrEmpty(i_sName)) return "_"; System.Text.StringBuilder oSB = new System.Text.StringBuilder(); for (int ixChar = 0; ixChar < (i_sName == null ? 0 : i_sName.Length); ixChar++) { char character = i_sName[ixChar]; if (IsXmlNodeNameCharacterValid(ixChar, character)) oSB.Append(character); } if (oSB.Length <= 0) oSB.Append("_"); return oSB.ToString(); } //---------------------------------------------------------------------------- private static bool IsXmlNodeNameCharacterValid(int i_ixPos, char i_character) { if (i_character == ':') return true; if (i_character == '_') return true; if (i_character >= 'A' && i_character <= 'Z') return true; if (i_character >= 'a' && i_character <= 'z') return true; if (i_character >= 0x00C0 && i_character <= 0x00D6) return true; if (i_character >= 0x00D8 && i_character <= 0x00F6) return true; if (i_character >= 0x00F8 && i_character <= 0x02FF) return true; if (i_character >= 0x0370 && i_character <= 0x037D) return true; if (i_character >= 0x037F && i_character <= 0x1FFF) return true; if (i_character >= 0x200C && i_character <= 0x200D) return true; if (i_character >= 0x2070 && i_character <= 0x218F) return true; if (i_character >= 0x2C00 && i_character <= 0x2FEF) return true; if (i_character >= 0x3001 && i_character <= 0xD7FF) return true; if (i_character >= 0xF900 && i_character <= 0xFDCF) return true; if (i_character >= 0xFDF0 && i_character <= 0xFFFD) return true; // if (i_character >= 0x10000 && i_character <= 0xEFFFF) return true; if (i_ixPos > 0) { if (i_character == '-') return true; if (i_character == '.') return true; if (i_character >= '0' && i_character <= '9') return true; if (i_character == 0xB7) return true; if (i_character >= 0x0300 && i_character <= 0x036F) return true; if (i_character >= 0x203F && i_character <= 0x2040) return true; } return false; } private static string msc_sBaseFilename = "exception_messages"; private static string msc_sXmlGroup_Root = "exception_messages"; private static string msc_sXmlGroup_Info = "info"; private static string msc_sXmlGroup_Messages = "messages"; private static string msc_sXmlData_Culture = "culture"; private Exception m_oException; private CultureInfo m_oCultureInfo; private string m_sMessage; static Dictionary> ms_dictCultureExceptionMessages = new Dictionary>(); } internal class Program { public static void Main() { CException.CreateMessages(null); CException.SaveMessagesToXML(@"d:\temp\", "emsg"); CException.LoadMessagesFromXML(@"d:\temp\", "emsg"); } } 

Vous devez vous connecter à la stack d’appels au lieu de simplement un message d’erreur (IIRC, simple exception.ToSsortingng () devrait le faire pour vous). À partir de là, vous pouvez déterminer exactement l’origine de l’exception et en déduire habituellement quelle exception.

Remplacer le message d’exception dans le bloc catch à l’aide de la méthode d’extension

  public static ssortingng GetEnglishMessageAndStackTrace(this Exception ex) { CultureInfo currentCulture = Thread.CurrentThread.CurrentUICulture; try { dynamic exceptionInstanceLocal = System.Activator.CreateInstance(ex.GetType()); ssortingng str; Thread.CurrentThread.CurrentUICulture = new CultureInfo("en-US"); if (ex.Message == exceptionInstanceLocal.Message) { dynamic exceptionInstanceENG = System.Activator.CreateInstance(ex.GetType()); str = exceptionInstanceENG.ToSsortingng() + ex.StackTrace; } else { str = ex.ToSsortingng(); } Thread.CurrentThread.CurrentUICulture = currentCulture; return str; } catch (Exception) { Thread.CurrentThread.CurrentUICulture = currentCulture; return ex.ToSsortingng(); } 

Pour les besoins de la journalisation, certaines applications devront peut-être récupérer le message d’exception en anglais (en plus de l’afficher dans l’UICulture du client habituel).

Pour cela, le code suivant

  1. change le UICulture actuel
  2. recrée l’object exception levée à l’aide de “GetType ()” & “Activator.CreateInstance (t)”
  3. affiche le nouveau message de l’object Exception dans le nouvel UICuture
  4. et enfin change l’UICulture actuelle en UICulture antérieure.

      try { int[] a = { 3, 6 }; Console.WriteLine(a[3]); //Throws index out of bounds exception System.IO.StreamReader sr = new System.IO.StreamReader(@"c:\does-not-exist"); // throws file not found exception throw new System.IO.IOException(); } catch (Exception ex) { Console.WriteLine(ex.Message); Type t = ex.GetType(); CultureInfo CurrentUICulture = System.Threading.Thread.CurrentThread.CurrentUICulture; System.Threading.Thread.CurrentThread.CurrentUICulture = new System.Globalization.CultureInfo("en-US"); object o = Activator.CreateInstance(t); System.Threading.Thread.CurrentThread.CurrentUICulture = CurrentUICulture; // Changing the UICulture back to earlier culture Console.WriteLine(((Exception)o).Message.ToSsortingng()); Console.ReadLine(); }