Pregunta

Tengo una operación de servicio web simple como esta:

    [WebMethod]
    public string HelloWorld()
    {
        throw new Exception("HelloWorldException");
        return "Hello World";
    }

Y luego tengo una aplicación cliente que consume el servicio web y luego llama a la operación.Obviamente arrojará una excepción :-)

    try
    {
        hwservicens.Service1 service1 = new hwservicens.Service1();
        service1.HelloWorld();
    }
    catch(Exception e)
    {
        Console.WriteLine(e.ToString());
    }

En mi bloque catch, lo que me gustaría hacer es extraer el mensaje de la excepción real para usarlo en mi código.La excepción detectada es una SoapException, lo cual está bien, pero es Message la propiedad es así...

System.Web.Services.Protocols.SoapException: Server was unable to process request. ---> System.Exception: HelloWorldException
   at WebService1.Service1.HelloWorld() in C:\svnroot\Vordur\WebService1\Service1.asmx.cs:line 27
   --- End of inner exception stack trace ---

...y el InnerException es null.

Lo que me gustaría hacer es extraer el Message propiedad de la InnerException (el HelloWorldException texto en mi muestra), ¿alguien puede ayudar con eso?Si puede evitarlo, no sugiera analizar el Message propiedad de la SoapException.

¿Fue útil?

Solución

Lamentablemente no creo que esto sea posible.

La excepción que está generando en el código de su servicio web está codificada en una falla de jabón, que luego se pasa como una cadena a su código de cliente.

Lo que está viendo en el mensaje SoapException es simplemente el texto de la falla de Soap, que no se convierte nuevamente en una excepción, sino que simplemente se almacena como texto.

Si desea devolver información útil en condiciones de error, le recomiendo devolver una clase personalizada de su servicio web que puede tener una propiedad "Error" que contiene su información.

[WebMethod]
public ResponseClass HelloWorld()
{
  ResponseClass c = new ResponseClass();
  try 
  {
    throw new Exception("Exception Text");
    // The following would be returned on a success
    c.WasError = false;
    c.ReturnValue = "Hello World";
  }
  catch(Exception e)
  {
    c.WasError = true;
    c.ErrorMessage = e.Message;
    return c;
  }
}

Otros consejos

Él ES ¡posible!

Ejemplo de operación de servicio:

try
{
   // do something good for humanity
}
catch (Exception e)
{
   throw new SoapException(e.InnerException.Message,
                           SoapException.ServerFaultCode);
}

Cliente que consume el servicio:

try
{
   // save humanity
}
catch (Exception e)
{
   Console.WriteLine(e.Message);    
}

Sólo una cosa: debe configurar el modo customErrors = 'RemoteOnly' o 'Activado' en su web.config (del proyecto de servicio).

créditos sobre el descubrimiento de errores personalizados - http://forums.asp.net/t/236665.aspx/1

Me encontré con algo similar hace un tiempo y blogueó sobre esto.No estoy seguro de si es exactamente aplicable, pero podría serlo.El código es bastante simple una vez que te das cuenta de que tienes que pasar por un objeto MessageFault.En mi caso, sabía que el detalle contenía un GUID que podía usar para volver a consultar el servicio SOAP para obtener más detalles.El código se ve así:

catch (FaultException soapEx)
{
    MessageFault mf = soapEx.CreateMessageFault();
    if (mf.HasDetail)
    {
        XmlDictionaryReader reader = mf.GetReaderAtDetailContents();
        Guid g = reader.ReadContentAsGuid();
    }
}
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top