Club Delphi  
    FTP   CCD     Buscar   Trucos   Trabajo   Foros

Retroceder   Foros Club Delphi > Principal > Conexión con bases de datos
Registrarse FAQ Miembros Calendario Guía de estilo Temas de Hoy

Conexión con bases de datos

Respuesta
 
Herramientas Buscar en Tema Desplegado
  #1  
Antiguo 07-05-2008
JMGR JMGR is offline
Miembro
 
Registrado: jun 2003
Ubicación: Santa Cruz de Tenerife
Posts: 46
Poder: 0
JMGR Va por buen camino
Comprobar en evento OnExit si valor de campo ya existe

Buenas!!!

Despues de mucho tiempo desconectado de las bases de datos ahora tengo que volver a "entretenerme" con ellas y estoy calentando con un programa sencillito de prueba pero mis conocimientos estan un poco oxidados...Seguramente esto es algo que habran preguntado miles de veces pero he estado buscando por el foro y googleando y no lo he encontrado...o no he sabido buscar...

Trabajo con Delphi5 y Access a traves de ADO, tengo una tabla con dos campos: Codigo y Cliente. Los registros se añaden a traves de un form con dos DBEdit y la idea es que cuando se añada un nuevo registro, al terminar de escribir el Codigo, es decir, en el evento OnExit del correspondiente DBEdit se compruebe si ese codigo de cliente ya existe en la base de datos para evitar duplicados. Para hacer esto creo recordar que usaba algo parecido al siguiente codigo (despues de, evidentemente, llamar al metodo Insert):

Código Delphi [-]
procedure TClientes.DBEdit1Exit(Sender: TObject);
begin
if DataModule3.TablaClientes.Locate('Codigo',dbedit1.text,[]) then
 begin
   if MessageDlg('Este codigo ya existe, ¿ desea modificar el cliente al que corresponde?', mtWarning, [mbYes,mbNo], 0) = mryes then
     DataModule3.TablaClientes.edit;
   Dbedit1.SetFocus;
 end;
end;

pero me da un error que dice algo asi como:

Cita:
"Los cambios solicitados en la tabla no se realizaron correctamente porque crearian valores duplicados en el indice, clave principal o relacion...y bla, bla, bla"
He estado mirando el codigo de antiguos programas y basicamente hago lo mismo solo que en aquellos funciona...

Es muy probable que este cometiendo un error evidente pero como ya dije llevo bastante tiempo desconectado de las bases de datos y no lo encuentro...

Mi duda es si el metodo LOCATE implica un POST cuando es llamado porque si no, no entiendo que "cambios" son los "solicitados" aludidos en el error...

Un poco de luz por favor...

Gracias y un saludo!
JMGR
Responder Con Cita
  #2  
Antiguo 07-05-2008
Avatar de BlueSteel
[BlueSteel] BlueSteel is offline
Miembro Premium
 
Registrado: may 2003
Ubicación: Concepción - Chile
Posts: 2.310
Poder: 23
BlueSteel Va por buen camino
Cool

Hola...

y para ingresar los datos utilizas DBEdit o Edit ???

yo utilizo Edit.. y en el evento onExit pongo lo sgte (Estoy utilizando SQL Server - Delphi 7 y ADO para el SQL )
Código Delphi [-]
             AQ_Consulta.Close;
             AQ_Consulta.SQL.Clear;
             AQ_Consulta.SQL.Add('Select 1 From CCosto');
             AQ_Consulta.SQL.Add('Where Ccto_Cod =:Var1');
             AQ_Consulta.Parameters[0].Value := vCod.Text;
             AQ_Consulta.Open;
             If AQ_Consulta.Eof Then vDet.SetFocus
             Else
                 Begin
                      ShowMessage('Ya fue registrado un Centro de Costo con ese Codigo...');
                      vCod.Clear;
                      vCod.SetFocus;
                 End;

AQ_Consulta es un ADOQuery en donde pregunta si existe el codigo.. si es EOF (Fin de Archivo)...no existe y me pasa el sgte campo (vDet.Setfocus), de lo contrario existe y envio mensajes ... limpio variables


Salu2
__________________
BlueSteel
Responder Con Cita
  #3  
Antiguo 08-05-2008
[coso] coso is offline
Miembro Premium
 
Registrado: may 2008
Ubicación: Girona
Posts: 1.678
Poder: 0
coso Va por buen camino
Si. El metodo locate implica un post.

El problema q tienes es q el DBEdit es q ya actualiza la base de datos (hace un 'post') al salir, por lo que si el 'codigo' ya existe, te genera el error de 'valores duplicados' antes de llegar a tu codigo para encontrar el error. En otras palabras, el error q estas intentando 'pillar' lo detecta el servidor de base de datos antes. Deberias colocar el mensaje de error en el evento onPostError de la tabla, olvidandote de comprobar si ya existe ese codigo o no. Si lo que quieres es algo mas concreto, deberias buscar para 'cazar' excepciones.

Un par de cosas que he visto q tambien son extrañas:

- Si haces un locate, estas reposicionando el cursor en la base de datos por lo que si tienes la opcion UpdateWhereAll activada (que me parece q es por defecto), en el momento de salir estas cambiando el valor del dbedit antes que se actualizen los cambios.

- Veo un Table.Edit pero no veo ningun post. Parece q dejas abierta la tabla en modo edicion. Lo correcto (para q no te pasen errores como este, pues si la dejas en Table.State = dsEdit te puede pasar de todo) es hacer

Table.Edit;
Table.FieldValues['NOMBRE'] := 'nombre de ejemplo';
Table.FieldValues['TEL'] := '9355555555';
...
Table.Post;

Al entrar a los dbedits, estos automaticamente abren la tabla en modo edicion, y al salir postean, por lo que es innecesario incluir ese edit aqui.

La mejor manera de hacer estas cosas es no usar los dbedits, y si usar el evento onexit de un edit normal y corriente, editando como te ponia antes. Si te empeñas con los dbedit, no uses el locate o filtros o nada parecido dentro de ellos (ni el next, prior, ni indexfieldnames...) pues si mueves el cursor de la base de datos ya la pifiaste

PD: borland dejo de desarrollar sobre las TTable porque tenian (y provocaban) infinidad de bugs, te recomiendo q uses SQL, es mucho mas sencillo trabajar con ello


Venga, espero haberte servido de ayuda

Última edición por coso fecha: 08-05-2008 a las 00:47:04.
Responder Con Cita
  #4  
Antiguo 08-05-2008
Avatar de Lepe
[Lepe] Lepe is offline
Miembro Premium
 
Registrado: may 2003
Posts: 7.424
Poder: 29
Lepe Va por buen camino
En lugar de Locate puedes usar LookUp para ver si el código ya existe sin cambiar el cursor del registro.

Saludos
__________________
Si usted entendió mi comentario, contácteme y gustosamente,
se lo volveré a explicar hasta que no lo entienda, Gracias.
Responder Con Cita
  #5  
Antiguo 09-05-2008
Delfino Delfino is offline
Miembro
 
Registrado: jul 2003
Ubicación: Madrid
Posts: 974
Poder: 21
Delfino Va por buen camino
Cita:
Si. El metodo locate implica un post.
Quien ha dicho esto?
Cita:
En lugar de Locate puedes usar LookUp para ver si el código ya existe sin cambiar el cursor del registro.
O mejor dejar q el manejador de BD lo compruebe (lo haria mucho mas rapido) y tratar el error en el evento OnPostError del Dataset..
__________________
¿Microsoft? No, gracias..
Responder Con Cita
  #6  
Antiguo 09-05-2008
[coso] coso is offline
Miembro Premium
 
Registrado: may 2008
Ubicación: Girona
Posts: 1.678
Poder: 0
coso Va por buen camino
Cuando llamas a edit, la TTable.State esta en dsEdit. Cuando llamas a locate, la TTable.State pasa a dsBrowse. Si tienes activado UpdateWhereAll en la tabla, que es por defecto, se hace un post automatico. Compruebalo con algun programilla o el debbuger...

Saludos

Última edición por coso fecha: 09-05-2008 a las 12:53:43.
Responder Con Cita
Respuesta



Normas de Publicación
no Puedes crear nuevos temas
no Puedes responder a temas
no Puedes adjuntar archivos
no Puedes editar tus mensajes

El código vB está habilitado
Las caritas están habilitado
Código [IMG] está habilitado
Código HTML está deshabilitado
Saltar a Foro

Temas Similares
Tema Autor Foro Respuestas Último mensaje
Cancelar accion de un evento OnExit FGarcia Varios 5 11-05-2007 13:38:18
Evento 'OnExit' del Form Wellnic OOP 3 10-04-2007 19:08:51
Error en evento OnExit en TDBEdit halcon_rojo Varios 1 27-04-2006 23:17:19
Problemas con evento OnExit santi33a Varios 4 15-04-2006 13:30:50
Evento OnExit de un Edit Caro OOP 1 03-02-2006 17:57:01


La franja horaria es GMT +2. Ahora son las 21:16:35.


Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi
Copyright 1996-2007 Club Delphi