Portal    Foro    Buscar    FAQ    Registrarse    Conectarse


Publicar nuevo tema  Responder al tema 
Página 1 de 1
 
 
Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL
Autor Mensaje
Responder citando   Descargar mensaje  
Mensaje Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
Uno de los servidores de Internet en los que residen las bases de datos que manejo tiene configurado un time-out muy pequeño para cortar la conexión, de manera que el usuario no puede entretenerse ni cinco minutos en rellenar la pantalla o se queda desconectado del servidor.
Para evitar esto, hay que comprobar si la conexión sigue abierta antes de intentar efectuar cualquier consulta. En estos casos la propiedad "Opened" del objeto Connection no sirve, pues seguirá siendo true.
Lo que estoy utilizando ahora es la famosa tabla ficticia "dual".
Esta tabla (ignoro si es un estándar SQL o no) es una tabla ficticia que se usaba en Oracle para devolver valores que no existen en las tablas. Por ejemplo, si queremos que una consulta devuelva "LITERAL" haríamos la consulta: SELECT "LITERAL" FROM DUAL.
El otro día se me ocurrió probarlo con MySQL 5.0 y resulta que también funciona. Por tanto el código para soslayar el corte de conexión queda así:

PUBLIC PROCEDURE conectar()

  DIM ckey, pass AS String
  'Consulta ping
  TRY hconn.Exec("SELECT \"1\" from dual")
  IF ERROR THEN
    'No hay conexión a la Base de datos
    hConn = NEW Connection  
    WITH hConn
      .Type =  Settings["Base/Tipo"]
      .Host = Settings["Base/Host"]
      .Login = Settings["Base/Usuario"]
      .Password = Settings["Base/Password"]
      .Name = Settings["Base/Nombre"]
    END WITH
    TRY hConn.Open
    IF ERROR THEN
      Message.Error("Imposible conectar a la base de datos. Error: " & Error.Text)
      QUIT
    END IF
  ENDIF
  RETURN

END

 
Espero que os sirva.
 




===================
No podemos regresar
 
shordi - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Responder citando   Descargar mensaje  
Mensaje Re: Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
No entiendo esto.

Si la conexion se corta pues se corta. Normalmente uno se va al servidor y extrae los datos que necesita que son los que viajan por la red. En ocasiones (para esas cosas estamos los programadores9 nos traemos las tablas a casa y ahora consultamos sobre ellas. Este segundo método tiene sus ventajas e inconvenientes, pero es práctico porque globalmente reduce el tráfico de red. Todo es una cuestión de punteros pero nada de eso sirve para el caso en que la comunicacion se corte.

Tampoco he visto nunca eso que dices del literal en Oracle.

En tin, todo es aprender cosas nuevas pero la verdad es que no lo entiendo
 
 



 
soplo - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Responder citando   Descargar mensaje  
Mensaje Re: Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
Pues tal vez yo lo hago mal, pero el tema es así:

1.- Un usuario llama un formulario que contiene los datos de un menda. Ahí se abre la conexión y se reciben los datos de la consulta "Select"
2.- El usuario se dedica a rellenar el formulario modificando algunos campos mientras bromea con la de al lado, se funa un cigarro y habla por teléfono. Tiempo total 20 minutos.
3.- Mientras él hace tantas tareas simultáneas (multiproceso usuarial, se llama) El servidor le corta la conexión por time-out.
4.- El usuario pulsa grabar y recibe un mensaje de error.

¿Cómo evitar ese mensaje? No quiero abrir y cerrar conexiones en cada consulta, que eso es enlentecer la aplicación. Por tanto lo que queda (lo único que he encontrado) es hacer una consulta de prueba y al recibir el error reabrir la conexión. Se podría hacer la consulta real enviarla y repetirla si hay error, pero la solución que propongo no ocupa prácticamente tiempo ni datos y nos asegura que al enviar la consulta real la conexión está viva.

La tabla dual no sirve sólo para devolver literales. También puede devolver campos calculados, variables del sistema, etc. etc. Se ideó, según me enseñaron, para la realización de rutinas estándar que sirvan en cualquier base de datos y que no dependan del nombre de las tablas concretas de ninguna. Ahora veo que MySQL sí reconoce funciones de fecha solas sin cláusula FROM en la sentencia. Pero no siempre ha sido así en todos los entornos y en todas las versiones (al menos antes no era así). el manual de MySQL 5.0 dice, cuando habla de la sentencia SELECT :

" En MySQL 5.0, puede especificar DUAL como nombre de tabla falso en siguaciones donde no se referencian tablas:

mysql> SELECT 1 + 1 FROM DUAL;
-> 2

DUAL es una característica puramente de compatibilidad. Otros servidores requieren esta sintaxis. "

Como decía Bernard Shaw: "Si quieres aprender algo, escribe un libro sobre el tema". Escribiendo esta respuesta he aprendido que se pueden enviar sentencias sin FROM en mySQL, ("SELECT CURDATE();", por ejemplo) cosa que nunca me había fijado.
Eso convierte el código que os he puesto arriba en un tanto obsoleto. Puesto que en lugar de la consulta a "dual" se puede utilizar una consulta a cualquier función de fecha o matemática, pero no me resisto a dejarlo así, que me dio mucha alegría encontrar, aún vivo, al viejo y querido "dual"...

Por cierto, lo de "siguaciones" es cosa del manual de MySQL, es lo que tiene copiar y pegar...

Saludos
 




===================
No podemos regresar
 
shordi - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Responder citando   Descargar mensaje  
Mensaje Re: Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
Bueno, al menos ahora si entiendo lo que dices, pero no entiendo como funciona el DUAL ese que dices.

 
 



 
soplo - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Responder citando   Descargar mensaje  
Mensaje Re: Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
¿Y no sería más lógico comprobar si la conexión está abierta y si no, pues abrirla justo antes de guardar los datos?

Esta es una función genérica para obtener la conexión a una BD (en este caso sqlite)
que devuelve FALSE en caso de éxito,  

PUBLIC cnLog AS Connection

PUBLIC FUNCTION connDB(path AS String) AS Boolean
DIM myHost, myDBName AS String

    myHost = Left(path, RInStr(path, "/"))
    myDBName = Mid(path, Len(myHost) + 1, RInStr(path, "/"))
   'si ya está conectado, sale devolviendo FALSE
    IF cnLog <> NULL THEN RETURN FALSE
    
    cnLog = NEW Connection
    
    cnLog.Host = myHost
    cnLog.Name = myDBName
    cnLog.Type = "sqlite3"
    
    TRY cnLog.Open()
    
    IF ERROR THEN
        cnLog = NULL
        Message.Error(("Error connecting to database: ") & myDBName)
        RETURN TRUE
    ENDIF
    
    RETURN FALSE
  
END


De esta forma, podrías usarlo así:

PUBLIC SUB btnGuardar_Click()
    IF connDB(rutaSQLite) THEN RETURN 'si falla (devuelve TRUE) entonces sale del procedimiento
    'pero si tiene éxito, la conexión se abre ahora.
    
    guardarAlgo() 'si ha tenido éxito la conexión, ejecutas las rutinas necesarias para guardar
END


Ya no tienes que preocuparte de mantener viva la conexión, porque si se ha cerrado, se abrirá siempre que quieras guardar o recoger datos al pulsar el botón.
No te será difícil adaptarlo a mysql.

Saludos

P.D. Por la temática del hilo, voy a moverlo al foro de Bases de Datos
 




===================
Jesús Guardón

Por favor, usemos el corrector ortográfico antes de pulsar el botón "Enviar".

"uo ǝs ʇɐu pıɟıɔıן ɐdɹǝupǝɹ ɐ dɹoƃɹɐɯɐɹ, soןo ɥɐʎ bnǝ dɹodouǝɹsǝןo"
 
jguardon - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Responder citando   Descargar mensaje  
Mensaje Re: Evitando Que El Servidor Corte La Conexión A La Base De Datos MySQL 
 
Jesús, en el caso que estamos tratando eso no serviría porque cnLog, o sea, la conexión, no sería null, ya que tú ya la abriste e hiciste consultas a través de ella. Sería siempre un objeto tipo connection y el procedimiento te generaría un error.
El problema reside en que es el servidor el que corta la conexión sin que tú te enteres, es decir, sin que tu gambas se entere (para él aún sigue abierta). Por tanto la única manera de saber si la conexión sigue viva es hacer una petición de alguna clase al servidor.
Puedes hacer una consulta normal, pero eso puede consumir más tiempo y recursos... la solución es hacer lo que en algunos sitios se denomina "Consulta ping". Yo proponía el uso de la tabla ficticia "dual", pero veo que ahora hay otros métodos, como por ejemplo SELECT CURDATE(); que MySQL admite sin problemas.

Soplo: DUAL es símplemente una tabla ficticia que se usa para obtener el resultado de campos calculados o ficticios. Imaínate que tu servidor SQL no admite sintaxis de SELECT sin la cláusula FROM. ¿Cómo obtienes la hora, por ejemplo, del servidor? pues SELECT CURTIME() FROM DUAL; sería la solución (No es el caso de MySQL en concreto, que sí admite Select sin from, pero hay otras bases de datos en que no es así).

Sea como sea, no me hagáis mucho caso. A veces sale a pasear el dinosaurio que llevo dentro... Ésta técnica la aprendí allá por el año 89 en unos cursos en Oracle España... pos no ha llovido ni ná desde entonces...

Saludos
 




===================
No podemos regresar
 
shordi - Ver perfil del usuarioEnviar mensaje privado 
Volver arribaPágina inferior
Mostrar mensajes anteriores:    
 
OcultarTemas parecidos
Tema Autor Foro Respuestas último mensaje
No hay nuevos mensajes Cerrar Una Conexión A La Base De Datos Co... bies88 Controles/Librerías/Componentes 3 Miercoles, 21 Julio 2010, 11:40 Ver último mensaje
bies88
No hay nuevos mensajes Error Con Conexión A MySQL En Servidor Web Cubel Bases de Datos 2 Miercoles, 24 Julio 2013, 11:25 Ver último mensaje
Cubel
No hay nuevos mensajes Servidor De Base De Datos. ¿KVM O LXC? tincho Bases de Datos 1 Lunes, 20 Marzo 2017, 22:06 Ver último mensaje
tincho
No hay nuevos mensajes Archivo Conexión A Base De Datos Shell Bases de Datos 2 Viernes, 20 Septiembre 2019, 15:57 Ver último mensaje
gambafeliz
 

Publicar nuevo tema  Responder al tema  Página 1 de 1
 

Usuarios navegando en este tema: 0 registrados, 0 ocultos y 1 invitado
Usuarios registrados conectados: Ninguno


 
Lista de permisos
No puede crear mensajes
No puede responder temas
No puede editar sus mensajes
No puede borrar sus mensajes
No puede votar en encuestas
No puede adjuntar archivos
Puede descargar archivos
No puede publicar eventos en el calendario



  

 

cron