Aquí hay un escenario estándar:
if(string.IsNullOrEmpty(Configuration.AppSettings["foobar"]))
throw new SomeStandardException("Application not configured correctly, bozo.");
El problema es que no estoy completamente seguro de qué excepción SomeStandardException
debería ser.
Leí detenidamente el Marco 3.5 y encontré dos posibles candidatos: ConfigurationException
y ConfigurationErrorsException
.
System.Configuration.ConfigurationException
La excepción que se produce cuando se produce un error del sistema de configuración.
Observaciones
LaConfigurationException
excepción se produce si la aplicación intenta leer o escribir datos en el archivo de configuración pero no tiene éxito. Algunas posibles razones para esto pueden incluir XML con formato incorrecto en el archivo de configuración, problemas de permisos de archivo y propiedades de configuración con valores que no son válidos.Nota:
El
ConfigurationException
objeto se mantiene por compatibilidad con versiones anteriores. ElConfigurationErrorsException
objeto lo reemplaza por el sistema de configuración.
Esta excepción en realidad suena perfecta para lo que necesito, pero se ha marcado como obsoleta, por lo tanto, ixnay en atthay.
Esto nos lleva a lo completamente desconcertante ConfigurationErrorsException
:
System.Configuration.ConfigurationErrorsException
El valor actual no es uno de los valores de EnableSessionState.
Como puede ver, su documentación es completamente inútil. (Es así en la ayuda local y en línea.) Un examen de la clase en sí muestra que es una exageración drástica de lo que quiero.
En pocas palabras, necesito una excepción estándar que se debe lanzar cuando falta una configuración de la aplicación o contiene un valor no válido. Se podría pensar que el Framework tenía una excepción incorporada para que las aplicaciones lo usaran. (Aparentemente lo hizo, pero se marcó como obsoleto y fue reemplazado por algo mucho más amplio).
¿Qué soluciones, si hay alguna, están usando para esto? ¿Tendré que aguantar y rodar mi propia excepción para esto?
Editar apéndices
Algunos han preguntado si puedo proporcionar un valor predeterminado o no y continuar. En ciertos casos, sí, y en esos casos, no se lanzaría la excepción. Sin embargo, para ciertas configuraciones, esto no se aplicará. Por ejemplo: nombres y credenciales de servidores de bases de datos, servidores de autenticación y rutas a aplicaciones de terceros instaladas.
También vale la pena señalar que la aplicación en la que estoy trabajando principalmente es una aplicación de consola que se ejecuta en modo por lotes, y quiero que arroje una excepción que sea atrapada por el método principal y se registre adecuadamente si la cosa no está configurada adecuadamente. (Es un código heredado que heredé, y actualmente solo asume que todo es color de rosa).
fuente
System.Configuration.ConfigurationErrorsException
ha sido actualizada.Respuestas:
No está limitado en su lanzamiento de excepciones a las excepciones existentes en el Marco. Si decide usar excepciones existentes, no tiene que seguir la documentación al pie de la letra. La documentación describirá cómo el marco utiliza una excepción que se da, pero no implica ninguna limitación sobre la forma que elija para su uso / reutilización una excepción existente.
Es su aplicación: siempre que la documente e indique claramente la excepción que se lanzará en el caso específico de un valor de configuración faltante, puede usar cualquier excepción que desee. Si desea una indicación muy específica de un valor faltante , puede considerar escribir su propia excepción ConfigurationSettingMissing:
EDITAR: Escribir su propia excepción en este caso conlleva el beneficio adicional de garantizar que nunca habrá ninguna confusión sobre el origen de la excepción: el marco o su aplicación. El marco nunca arrojará sus excepciones personalizadas.
ACTUALIZACIÓN: estoy de acuerdo con los comentarios, por lo que he cambiado la subclase a Excepción de configuración de excepción de excepción. Creo que generalmente es una buena idea subclasificar las excepciones personalizadas de las excepciones existentes de Framework cuando sea posible, evitando la clase Exception a menos que necesite una excepción específica de la aplicación.
fuente
Personalmente, usaría InvalidOperationException , ya que es un problema con el estado del objeto, no con el sistema de configuración. Después de todo, ¿no debería permitir que esta configuración se establezca por código y no por configuración? La parte importante aquí no es que no haya una línea en app.config, sino que no haya una información requerida.
Para mí, ConfigurationException (y su reemplazo, ConfigurationErrorsException, a pesar de los documentos engañosos de MSDN) son por errores al guardar, leer, etc. de Configuration.
fuente
Como dijo Daniel Richardson, ConfigurationErrorsException es el que se debe usar. En general, solo se recomienda crear sus propios tipos de excepción personalizados si tiene un escenario para manejarlos. En el caso de los errores de configuración, que generalmente son fatales, rara vez es así, por lo que suele ser más apropiado reutilizar el tipo ConfigurationErrorsException existente.
Antes de .NET 2.0, la recomendación era usar System.Configuration.ConfigurationException . ConfigurationException se volvió obsoleto en .NET 2.0, por razones que nunca fueron claras para mí, y la recomendación cambió para usar ConfigurationErrorsException.
Utilizo un método auxiliar para lanzar la excepción para que sea fácil cambiar la excepción que se lanza en un lugar al migrar de .NET 1.xa 2.0, o si Microsoft decide cambiar la recomendación nuevamente:
fuente
¿Qué hay de
System.Configuration.SettingsPropertyNotFoundException
?fuente
ConfigurationErrorsException
es la excepción correcta para lanzar en la situación que describe. Una versión anterior de la documentación de MSDNConfigurationErrorsException
tiene más sentido.http://msdn.microsoft.com/en-us/library/system.configuration.configurationerrorsexception(VS.80).aspx
El resumen y las observaciones anteriores de MSDN son:
ConfigurationErrorsException
excepción se produce cuando se produce algún error mientras se lee o se escribe la información de configuración.fuente
La clase ConfigurationElement (que es la clase base de muchas clases relacionadas con la configuración, como ConfigurationSection) tiene un método llamado OnRequiredPropertyNotFound (también hay otros métodos auxiliares). Tal vez puedas llamar a esos.
OnRequiredPropertyNotFound se implementa de la siguiente manera:
fuente
Lo succionaría y rodaría el mío ... pero antes de hacerlo, ¿es posible que el sistema asuma un valor predeterminado para esta configuración? Por lo general, intento hacer eso para cada configuración que podría perderse bu Ops Management folk ... (o tal vez debería decir, para tantas configuraciones como sea posible; para algunos claramente no es apropiado que el sistema tome una decisión predeterminada. ..)
en general, una excepción personalizada no es mucho esfuerzo ... aquí hay un ejemplo ...
fuente
Un método alternativo que podría usar para sus archivos de configuración sería usar secciones de configuración personalizadas en lugar de
AppSettings
. De esa manera, puede especificar que una propiedadIsRequired
y el sistema de configuración se encargarán de esta comprobación por usted. Si falta la propiedad, arrojará un,ConfigurationErrorsException
así que supongo que respalda la respuesta de que debe usar esa excepción en su caso.fuente
Mi regla general sería:
Si el caso de la configuración que falta no es muy común y creo que nunca querría manejar este caso de manera diferente a otras excepciones, solo uso la clase básica "Excepción" con un mensaje apropiado:
lanzar una nueva excepción ("mi mensaje aquí")
Si quiero, o creo que hay una alta probabilidad de que quisiera manejar este caso de una manera diferente a la mayoría de las otras excepciones, rodaría mi propio tipo como la gente ya ha sugerido aquí.
fuente
Tiendo a estar en desacuerdo con la premisa de su pregunta:
De acuerdo con la documentación de MSDN en System.Exception ( clase de excepción , realmente no debería lanzar excepciones para errores de entrada del usuario, por razones de rendimiento (lo cual ha sido señalado por otros en Stack Overflow y en otros lugares). Esto parece tener sentido ya que bien, ¿por qué su función no puede devolver falso si la entrada del usuario se ingresa incorrectamente y luego la aplicación sale correctamente? Esto parece ser más un problema de diseño que un problema con el que lanzar la excepción.
Como otros han señalado, si realmente tiene que lanzar una excepción, por alguna razón, no hay ninguna razón por la que no pueda definir su tipo de Excepción al heredar de System.Exception.
fuente
Puede intentar heredar de la Excepción XML, o simplemente usarla.
fuente