capturar exception en .net

Iniciado por d91, 5 Octubre 2015, 05:06 AM

0 Miembros y 1 Visitante están viendo este tema.

d91

hola a todos, solo quiero que me orienten de como capturar una excepcion que dispara oracle y que es una cadena, no las he podido controlar con el codigo de visual basic.net porque de la forma en que lo hago retornaria una cadena y la funcion donde tengo el try catch retorna un entero si la ejecucion es normal
Código (vbnet) [Seleccionar]

public function ejecutasql() as integer
try
'todo_bien en la consulta
return 1
Catch ex As OracleException
Return "Error al generar Consulta" & ex.ToString
End Try

tambien he probado con esta otra pero igual no me controla la excepcion sino que de una vez me detiene la ejecucion
Código (vbnet) [Seleccionar]

Catch ex As OracleException
            Throw New ArgumentException("Error al generar consulta " & ex.Message.ToString)
        End Try

Eleкtro

#1
Cita de: d91 en  5 Octubre 2015, 05:06 AMquiero que me orienten de como capturar una excepcion que dispara oracle y que es una cadena, no las he podido controlar con el codigo de visual basic.net porque de la forma en que lo hago retornaria una cadena y la funcion donde tengo el try catch retorna un entero si la ejecucion es normal
Código (vbnet) [Seleccionar]


public function ejecutasql() as integer

...
return 1

Catch...
Return "Error al generar Consulta" & ex.ToString

End Function

Si tienes una función cuyo valor de retorno es Integer, entonces pretender devolver un datatype distinto (String) es un error de concepto por parte del programador, y la solución más eficiente es tan sencilla como evitar querer hacer eso.

Explica detalladamente por que sientes la necesidad de devolver un string y un integer en una misma función, y así podré(mos) ofrecerte una solución apropiada a tus necesidades.

De todas formas... siempre puedes especificar un valor de retorno de tipo Object en lugar de Integer y hacer los castings necesarios al llamar a la función, pero esto lo considero malos hábitos de programación, no te recomiendo hacerlo.

Por último, decirte que considero que eso no debería ser una función, sino un método, ya que no necesitas devolver nada para evaluar un success/fail.

Saludos!








Lekim

#2
Prueba esto:

Código (vbnet) [Seleccionar]
       Try
           Dim Resultado As IntPtr 'O Integer o lo que sea
           ' Resultado = ...


           Dim win32Err As Integer = System.Runtime.InteropServices.Marshal.GetLastWin32Error



           If Resultado = IntPtr.Zero Then  'Si Resultado  es un Stream o String debes poner  'If Resultado.Length = IntPtr.Zero Then'
               Throw New System.ComponentModel.Win32Exception([error]:=win32Err)
           Else

               'Variable/Control/Propiedad = Resultado

           End If

       Catch ex As Exception
           Throw

       Finally
           'Lo que quieras que haga al termintar...

       End Try



Pero si lo único que quieres es obtener el mensaje error entonces:

Código (vbnet) [Seleccionar]
       Try

       Catch ex As Exception
           MessageBox.Show(ex.Message)
       End Try


ya que como dice Elektro devuelve un valor String

Eleкtro

#3
Lekim, la función GetLastWin32Error es para el P/Invoking, solo se debe utilizar despues de llamar a una función no administrada (Windows API) y siempre que dicha función devuelva un código de error (no todas lo hacen por defecto), su propio nombre y la descripción lo indican por si mismo:

Cita de: https://msdn.microsoft.com/en-us/library/system.runtime.interopservices.marshal.getlastwin32error%28v=vs.110%29.aspxReturns the error code returned by the last unmanaged function that was called using platform invoke that has the DllImportAttribute.SetLastError flag set

Aparte de eso, en las funciones de la WinAPI que devuelvan un valor numérico, un valor de retorno tanto de "0" como distinto a "0" puede significar tanto un success como un tipo de error específico, es algo que depende de la función ya que no hay ningún estándar en ese sentido, cada función de la WinAPI es un mundo.

Aparte también, y solo por informar del siguiente dato, cabe mencionar que no existe una sincronización perfecta, como el nombre de la función explica por si mismo, esta se limita a devolver el último error Win32 conocido, ya sea el código de error devuelto por tu llamada, o sea el de otra llamada más reciente realizada por la aplicación.

Despues de esta pequeña aclaración, solo quiero aclarar que para controlar errores de miembros administrados (es decir, puro código .Net) se utiliza un bloque Try/Catch/Finally/End, nada más, por lo tanto el segundo código que has mostrado sería lo correcto :).

Saludos!








d91

la razon de hacer una funcion que devuelva un entero es porque al hacer el excuteNonQuery me devuelve un 1 y entonces lo retorno hasta la pagina aspx para dar un mensaje de "Operacion exitosa", y segun la orientacion que me han dado esta funcion  hare  que retorne la cadena de  mensaje exitoso desde aqui para que tambien pueda devolver una cadena de error.

d91

un ultimo detalle encontre ahora que cambio el tipo de retorno, dentro  de la misma clase donde tengo la funcion de ejecutar sql, tengo una que devuelve un dataset para llenar un dropdownlist, en esta funcion creo que no puedo cambiar el tipo de retorno para enviar el mensaje de error

Eleкtro

#6
Cita de: d91 en  5 Octubre 2015, 13:43 PM
la razon de hacer una funcion que devuelva un entero es porque al hacer el excuteNonQuery me devuelve un 1 y entonces lo retorno hasta la pagina aspx para dar un mensaje de "Operacion exitosa", y segun la orientacion que me han dado esta funcion  hare  que retorne la cadena de  mensaje exitoso desde aqui para que tambien pueda devolver una cadena de error.

Entonces, ¿no sería más apropiado hacer una función que devuelva un string, para cambiar el "1" por un "Operacion exitosa"?.

Código (vbnet) [Seleccionar]
public function ejecutasql() as string

try
'todo bien en la consulta
return "Operación exitosa"

catch ex As OracleException
Return ("Error al generar Consulta: " & ex.Message)

end try

End Try


...De esa manera estarías haciendo las cosas mejor que devolver un integer y string.

Si necesitas rehutilizar ese código de error personalizado (1), entonces también podrías hacerlo de la siguiente manera:
Código (vbnet) [Seleccionar]
public function ejecutasql() as keyvaluepair(of integer, string)

try
'todo bien en la consulta
return new keyvaluepair(of integer, string)(1, "Operación exitosa")

catch ex As OracleException
return new keyvaluepair(of integer, string)(0, ("Error al generar Consulta: " & ex.Message))

end try

End Try


Saludos








d91

ya lo resolvi el problema es que solo habia trabajo con messageBox y ahora que requiere un mensaje sobre algun label de una aplicacion web no podia comprender lo del valor de retorno y la exception, gracias a todos