FTP | CCD | Buscar | Trucos | Trabajo | Foros |
|
Registrarse | FAQ | Miembros | Calendario | Guía de estilo | Temas de Hoy |
|
Herramientas | Buscar en Tema | Desplegado |
|
#1
|
||||
|
||||
Combinación fallida de Filter, RevertRecord y UpdateStatus
Hola a todos.
Hace tiempo que no escribía sobre TClientDataSet, una clase nativa sobre la que he trabajado considerablemente y que aún sigue dándome una que otra sorpresa (la mayoría buenas). Hoy encontré una posible falla en la versión de Delphi 7 de ese componente, la cual me gustaría compartir aquí. Primero que nada para advertir sobre su existencia y proponer un sencillo remedio (work around), pero también para saber si se trata de un defecto conocido y si éste persiste en las nuevas versiones de Delphi. Con un objeto TClientDataSet nativo que ya se encuentre abierto y ordenado por su campo llave (ID en este ejemplo), hagamos lo siguiente:
El remedio que encontré fue casi obvio: usar Delete en lugar de RevertRecord. La ayuda de Delphi no especifica si el método RevertRecord es aplicable solamente a registros que tienen el estado usModified, o si también puede ser utilizado con los que tienen el estado usInserted. No obstante, parece funcionar muy bien en el segundo caso mientras el conjunto de datos no tenga un filtro activo. Así pues, mi recomendación sería que se utilice el método Delete en lugar de RevertRecord si se desea eliminar de la lista de cambios a algún registro nuevo (al menos mientras exista el problema planteado). Por otra parte, con los registros traídos de la base de datos y modificados en memoria (estado usModified), no parece haber problema al usar RevertRecord para deshacer sus cambios aunque haya un filtro presente. Espero sea de ayuda lo anterior, y de antemano gracias por cualquier información relacionada que puedan proporcionar. Un abrazo irreversible. Al González. Última edición por Al González fecha: 30-07-2010 a las 00:55:15. |
#2
|
||||
|
||||
Volviendo a este tema. ¿Alguien podría hacer la misma prueba en una versión superior a Delphi 7?
Se los agradezco. ¡Saludos! |
#3
|
||||
|
||||
Hola de nuevo.
Esto puede ser de alguna utilidad. Haciendo más pruebas encontré que este defecto tiene cierto patrón. Ocurre solamente con registros nuevos (creados en memoria y aún no aplicados al servidor), que pueden o no tener modificaciones tras haber sido guardados en memoria (con o sin ediciones tras el primer Post). Pero NO ocurre si el registro en cuestión es el último en la lista de cambios (change log) del conjunto de datos. Es decir, aparentemente, si el nuevo registro es la última operación realizada entre todas las altas, bajas y cambios que están pendientes de ser aplicados al servidor, RevertRecord funcionará sin conflicto alguno con el filtraje usado, eliminando el nuevo registro de la memoria del conjunto de datos y de su lista de cambios. Los siguientes son cinco ejemplos de listas de cambios en el orden en el que son hechas las operaciones. Ejemplo 1: Alta A Alta B (puede ser revertido B, pero no A) Ejemplo 2: Alta A Alta B Baja C (no puede ser revertido ni A ni B) Ejemplo 3: Alta A Alta B Cambio B (puede ser revertido B, pero no A) Ejemplo 4: Alta A Alta B Cambio C (no puede ser revertido ni A ni B) Ejemplo 5: Alta A Alta B Baja C Cambio A (puede ser revertido A, pero no B) El remedio de llamar al método Delete con los registros nuevos para evitar el problema, si bien puede resultar una solución práctica, tiene el inconveniente de que mantiene el registro invisible ocupando memoria en la lista de cambios, sin hablar de los eventos y otras acciones llevadas a cabo por el método Delete. Se me ha ocurrido que puede reemplazarse el método RevertRecord nativo por uno que haga lo mismo, pero que, cuando el registro sea nuevo, revise si éste se encuentra hasta el final de la lista de cambios (para ello puede utilizarse un cursor clonado con la propiedad StatusFilter llena), y, en caso de no ser así, lo modifique silenciosamente (sin disparar eventos), forzándolo a quedar al final de la lista de cambios antes de ejecutar la reversión. Grosso modo, algo como:
Lo sé, después de ver todo esto, la solución de usar un simple Delete no parece tan mala, pero lo aquí planteado puede llegar a servirle a alguien. Finalmente agradecería cualquier prueba que puedan hacer en Delphi 2009 o 20010. Por cierto, tengo entendido que ésta última trae el código fuente de la unidad MidasLib. En ella podría estar la clave de este defecto del método RevertRecord de la interfaz IDSCursor. ¿Alguien se anima a participar en esta investigación? Yo la dejaré hasta aquí por ahora. Saludos. Al González. |
#4
|
||||
|
||||
Amigo Al, yo puedo probarlo en delphi 2007, no sé si te puede servir ya que especificas 2009 y 2010.
|
#5
|
|||
|
|||
Probaré con Delphi 2010 y te diré Al go.
Saludos
__________________
Guía de Estilo |
#6
|
||||
|
||||
Cita:
Andrés, si tienes el archivo MidasLib.pas en tu Delphi 2010, ¿podrías echar una mirada a la clase que implementa los métodos de la interfaz IDSCursor, especialmente a los que intervienen en el change log? (y ya de paso corregir este problema y enviarle la solución a Embarcadero ). Lo que daría por estar viendo ese código ahora. Tendré que esperar hasta estar frente a una computadora con Delphi 2010. Última edición por Al González fecha: 15-08-2010 a las 02:32:28. |
#7
|
||||
|
||||
¿No te sirve la versión trial?
|
|
|
Temas Similares | ||||
Tema | Autor | Foro | Respuestas | Último mensaje |
Connection fallida | el-mono | Firebird e Interbase | 1 | 30-12-2008 22:24:14 |
Migración Fallida | Shadowless | Windows | 2 | 29-10-2008 10:53:12 |
Prueba turbo Delphi Net Fallida | ASAPLTDA | Varios | 0 | 08-05-2007 18:54:39 |
Conexion fallida con FireBird | mvelgar | Conexión con bases de datos | 3 | 05-05-2007 02:59:27 |
Combinación de teclas | Jose_Pérez | API de Windows | 2 | 17-06-2003 11:57:30 |
|