[RESUELTO] Manejo de errores SQL

Discute sobre las herramientas de la base de datos
Responder
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

[RESUELTO] Manejo de errores SQL

Mensaje por JoseJuan »

Hola a todos/as, este es mi primer mensaje, soy novato total en Base, os ruego un poco de paciencia conmigo.
Al tema, se trata de un procedimiento para eliminar un registro usando una sentencia SQL.
En condiciones normales el código realiza su función correctamente.
Cuando intento eliminar un registro que tiene relacionados en otra tabla y uso la orden "On Error ... ", da el mensaje "Error de ejecución de BASIC." "Variable de objeto no establecida", el código Err=1 no me sirve.

Si suprimo "On Error ..." el mensajes es:
"Se ha producido una excepción
Type: com.sun.star.sdbc.SQLException
Message: El registro no se puede eliminar o cambiar porque la tabla 'Tabla2' incluye registros relacionados.."

Pero en este caso no puedo interceptar el error para mostrar solo el texto de 'Message'

Este es el código resumido:

Código: Seleccionar todo

On Error GoTo Err_BorrarRegistro
.....			
Conexion = ThisDatabaseDocument.CurrentController.ActiveConnection
Sentencia = Conexion.CreateStatement
TexSQL =  '"DELETE Tabla1.*  FROM Tabla1 WHERE CodigoPrincipal = 22"
Sentencia.ExecuteUpdate(TexSQL)
Tampoco puedo comprobar previamente la existencia de registros relacionados por que el código debe ser llamado desde varios formularios, tomando los datos para el borrado de forma dinámica, en cada caso las tablas relacionadas son diferentes y obligaría a retocar el código para cada nuevo formulario.
Las tablas se encuentran en un archivo .mdb de ms-access.

Como puedo interceptar los errores de SQL y conocer su código de error para editar el mensaje y poder realizar las acciones necesarias?

Saludos.
Última edición por mauricio el Mar Abr 10, 2018 5:39 pm, editado 2 veces en total.
Razón: Marcar icono de resuelto
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Longi
Mensajes: 804
Registrado: Dom Ene 20, 2013 9:05 pm
Ubicación: Ourense, Galicia, España

Re: Manejo de errores SQL

Mensaje por Longi »

Creo que no es necesario lo que planteas.
Si en la relación entre tablas escoges la opción 'Eliminación en cascada'.
Con esta opción te elimina el registro que estás intentando eliminar y todos aquellos que están, no solo relacionados, sino subordinados a aquel que eliminas.
No te dará error, pero te quedas sin todos los registros que cuelgan del que eliminas (que por otra parte es lógico).

Un saludo!
Openoffice 4.1.7, en Windows 10
Libreoffice 6.4.2, en Windows 10
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

Re: Manejo de errores SQL

Mensaje por JoseJuan »

Ante todo, gracias por la sugerencia.
Conozco bien el método que propones, pero no puedo aplicarlo, no se trata lineas de facturas o similar.
La Tabla1, sobre la que se intenta realiza el borrado, contiene información de empresas y la Tabla2 relacionada, contiene datos de expedientes, no interesa borrar nada cuando hayan registros relacionados. Puede darse el caso que hayan empresas sin expedientes asociados y esas si quisiera poder borrarlas.
Simplemente quiero manejar el texto que se muestra, pero la orden 'On Error' no me funciona.
¿Pudiera ser un problema general con la orden 'On Error' y no solo con la SQL? Siempre muestra el mismo mensaje "Error de ejecución de BASIC."
Saludos.
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Longi
Mensajes: 804
Registrado: Dom Ene 20, 2013 9:05 pm
Ubicación: Ourense, Galicia, España

Re: Manejo de errores SQL

Mensaje por Longi »

Si he entendido bien (cosa poco usual por otra parte), lo que quieres es eliminar registros de una tabla y mantener los de la otra.....En este caso, a riesgo de equivocarme, creo que lo que tendrías que tener son tablas sin relación entre ellas.
No puedes pretender talar un manzano y que las manzanas queden en el aire. Si que puedes quitar las manzanas y dejar el árbol, pero no al revés.
Quizá debas replantear el diseño, o hacer que las manzanas pasen a cajas de fruta, en un almacén, y después te dediques a talar el manzano.
El ejemplo es muy tonto, pero creo que bastante gráfico: Antes del borrado, tendrías que hacer copia del registro que tiene asociado en otra tabla.
Algo así hago en una base que tengo de trabajadores en empresas. Primero cambio el trabajador a una empresa ficticia llamada 'bajas', con NIF=0 (pasó de trabajar en la empresa 'A' a trabajar en la empresa 'bajas'. Después doy de baja la empresa 'A'.
Si no fuese así y no tengo la opción en cascada, no me dejaría borrar (en realidad la paso al listado de empresas de baja) la empresa 'A' mientras tenga empleados dentro.
Espero no haberte liado más en vez de aclarar algo!

Un saludo! ;)
Openoffice 4.1.7, en Windows 10
Libreoffice 6.4.2, en Windows 10
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

Re: Manejo de errores SQL

Mensaje por JoseJuan »

Gracias por tu respuesta, aunque me pierdo un poco con tu metáfora de las manzanas.
Para no irnos del tema, déjame que repita unas frases:
"no interesa borrar nada cuando hayan registros relacionados"
"Simplemente quiero manejar el texto que se muestra, pero la orden 'On Error' no me funciona."

Aunque te parezca una situación extraña, a veces el nivel de los usuarios nos obliga a prever todas las situaciones.
Intentare explicarlo de otra forma, si un usuario intenta borrar un cliente que tiene facturas relacionadas, tu me dices que fuerce el borrado de la factura.
Yo lo quiero hacer es enviar un mensaje amable avisándole que no lo puede hacer.
Si permito que el mensaje comience "Se ha producido una excepción" "Type: com.sun.star.sdbc.SQLException", el usuario probablemente no llegará al leer el final, la parte "Message:", que es donde está la información que me interesa que lea.

Otra posible solución seria reconfigurar la salida de los mensajes, al inicio del tiempo de ejecución, para que solo mostrara esa última parte, pero esto lo veo mucho más complicado.

Saludos.
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Longi
Mensajes: 804
Registrado: Dom Ene 20, 2013 9:05 pm
Ubicación: Ourense, Galicia, España

Re: Manejo de errores SQL

Mensaje por Longi »

Buenas otra vez!
Evidentemente no te había entendido del todo.
También es evidente que el control de errores no lo manejo en absoluto.
Por otra parte, supongo que es posible que, en el momento de ir a hacer un borrado, se pueda hacer un ResultSet sobre el registro en el que se está, de tal manera que podemos saber cuantos registros cuelgan de él, y si es superior a 0, entonces podremos sacar el mensaje por un msgbox, explicando que para este registro no es posible hacer el borrado, ya que existen registros en otras tablas que están relacionados con él.
Si esto lo hacemos antes de la ejecución del SQL que elimina, y hacemos un exit sub, entonces no llegamos al mensaje de error que ofrece el propio sitema.
Si no tiene registros colgando, entonces le permitimos seguir el camino de la eliminación, y no tendría que salir ningún mensaje extraño.
Esto sería 'sencillo' si el borrado se hace desde botón, y algo más difícil (o eso me parece a mi) si el borrado se hace desde los botones de las barras del propio formulario.

(A ver si esta vez acierto!!)

Ya nos cuentas!
Openoffice 4.1.7, en Windows 10
Libreoffice 6.4.2, en Windows 10
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

Re: Manejo de errores SQL

Mensaje por JoseJuan »

Hola,
Todavía no conozco el ResultSet, parece una buena idea si estubiéramos en una situación sencilla y muy controlada.
No parece un problema controlar el origen de la acción: barra de navegación o botón en formulario. Creo que esta lucha la tengo superada.

Por seguir con el ejemplo anterior, piensa que aparte de la tabla de Facturas, hubieran otras también relacionadas como podrían ser Envíos, Bancos, Cobros, etc. debería preguntar por cada tabla y conocer de antemano los nombres de los campos vinculados. En resumen, sería hacer a mano parte del trabajo del gestor de datos.

Yo solo quiero interceptar el error, chequear el código de error que se ha generado al ejecutar la SQL y mostrar un mensaje comprensible cuando sea el código esperado.
Algo similar a lo que nos propone Mauricio en su magnífico libro "Aprendiendo LibreOffice Basic", pág 99 :

Código: Seleccionar todo

Sub Manejo_Errores3()
   Dim sRutaArchivo As String
   On Error Goto CONTROLAERRORES
   sRutaArchivo = Trim(InputBox("Escribe la ruta del archivo a borrar"))
   Kill sRutaArchivo
   MsgBox "El archivo " & sRutaArchivo & " se borró correctamente"
Exit Sub

CONTROLAERRORES:
   Select Case Err
   Case 0
   Case 53
      MsgBox "No se encontró la ruta especificada" & Chr(13) & Chr(13) & sRutaArchivo, 48
   Case Else
      MsgBox "Ocurrió el error número: " & Err & Chr(13) & Error & Chr(13) & "En la línea " & Erl
   End Select

   On Error Goto 0
End Sub
Quizás se trate de un bug.
Alguien puede confirmar que le funciona el control de errores con sentencias SQL?

Saludos a todos.
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Avatar de Usuario
mauricio
Mensajes: 6092
Registrado: Sab Nov 22, 2008 5:36 am
Ubicación: CDMX
Contactar:

Re: Manejo de errores SQL

Mensaje por mauricio »

Procura (siempre), agregar un archivo con el problema, así ayudas a quien quiera ayudarte a no partir de cero, como he tenido que hacerlo...

Como ya te comento nuestro compañero, es mejor que establezcas la relación entre las tablas para que hagan la eliminación es cascada, claro, si esto es realmente lo que quieres, con esto, como dictan las buenas practicas, solo le debes de preguntar al usuario (aunque a veces estos no los lean), si realmente quieren borrar el registro.

Ahora, si quieres seguir el camino actual (si te gusta sufrir :) ), el controlador de errores funciona correctamente como puedes ver en el archivo anexo. IMPORTANTE, use base de datos Firebird, si no lo tienes activado en tu LibreOffice, mira la imagen siguiente:
foro.png
Saludos
Adjuntos
Base de datos.7z
(4 KiB) Descargado 169 veces
______________________________________________
"Todo cuanto no podemos dar nos posee". - André Gide
LibreOffice 6.2 | ArchLinux | Gnome3
No respondo preguntas privadas, por favor, usa el foro
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

Re: Manejo de errores SQL

Mensaje por JoseJuan »

Muchas gracias Mauricio. Quizás resumí demasiado el código del primer mensaje.

Ya he localizado parte del problema, tenia un error el formato del texto para el MsgBox (Err.Description importado de ms-access), estaba en una línea que no publiqué. Se generaba un error BASIC al procesar el error en la SQL.
Veo que no compruebas el código de error generado con If-Then o Select-Case, como mi rutina contiene varias operaciones previas con otros objetos me interesa controlar este código.
Existe una lista de errores interceptables de SQL?

Saludos.
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Avatar de Usuario
mauricio
Mensajes: 6092
Registrado: Sab Nov 22, 2008 5:36 am
Ubicación: CDMX
Contactar:

Re: [RESUELTO] Manejo de errores SQL

Mensaje por mauricio »

En mi ejemplo, la única línea que puede causar un error es la 10, no requiero comprobar otra, en tu caso tienes la variable global Err que te da el número de error con el que tienes que trabajar de acuerdo a tus necesidades.

Saludos
______________________________________________
"Todo cuanto no podemos dar nos posee". - André Gide
LibreOffice 6.2 | ArchLinux | Gnome3
No respondo preguntas privadas, por favor, usa el foro
Avatar de Usuario
JoseJuan
Mensajes: 34
Registrado: Mié Abr 04, 2018 10:41 pm
Ubicación: Valencia (España)

Re: [RESUELTO] Manejo de errores SQL

Mensaje por JoseJuan »

En este caso, con el mensaje "El registro no se puede eliminar o cambiar porque la tabla 'Tabla2' incluye registros relacionados.." devuelve un valor 1 en la variable Err.
La lista de valores de error, según la ayuda ("errores al tiempo de ejecución en Basic"), el 1 debería corresponder con el texto: "Interrupción de usuario".
Sospecho que debe existir otra lista de valores para los errores SQL pero no se como acceder a ella. Quizás dependa del gestor de datos, una base .mdb en este caso.
De momento pregunto por el texto del mensaje para establecer los detalles del msgbox. No es muy elegante pero funciona mientras no cambien el texto en una futura versión de LibO.
Gracias por tus inestimables aportaciones, son todo un lujo.
libreoffice 5.3.7.2 (x64) en Windows 7 / Libreoffice 6.4.2.2 en Windows 10
Responder