Buffering, El Vampiro Asesino, la historia continua
J. Booth
Traducción
de Pablo Roca / Danny Castelo
En el artículo
hemos visto la tecnología de almacenamiento en buferes con Visual
FoxPro. Fueron revisados los diversos modos de bufer, y fue presentada
una comparación respecto a las ediciones directas de FoxPro 2.x
contra el almacenamiento en bufer de VisualFoxPro. En este artículo
veremos como se trabaja con las funciones TableUpdate y TableRevert y
entenderemos como son usadas con el sistema de almacenamiento en bufer.
Así
que... ¿Donde estan los datos realmente?
Con el
bufer activado, VisualFoxpro mantiene tres versiones de los datos. La
primera son los datos que existen en el archivo del disco, la segunda
son los datos que existen en tu bufer de datos, y la última son
los datos tal y como estaban cuando empezamos a modificar nuestro bufer.
Cualquiera de estas versiones de los datos las tenemos disponibles mediante
programación/código. Mas adelante veremos como podemos acceder
a ellas.
En el artículo anterior se
pudo ver que con el bufer de datos activado, la modificación se
realiza en una copia de los datos. La cuestión obvia es ¿Cómo
hacer que dicha copia se actualice en la tabla?. Con la función
TableUpdate.
Una definición ayudará
con la discusión, bufer sucio. Un bufer sucio es un bufer de datos
que contiene cambios pendientes que no han sido actualizados en la tabla.
Actualizar
o no actualizar
TableUpdate
es la función que provoca que los datos de un bufer se escriban
sobre una tabla. Esta función tiene (4) argumentos, la sintaxis
es,
TABLEUPDATE( [nFilas|lFilas> [, lForzar]] [, cAliasTabla | nÁreaTrabajo] [, cMatrizErrores])
Como
se puede ver, todos los argumentos de esta función son opcionales.
Realizando un TableUpdate sin argumentos actualizará el registro
actual de la área de trabajo activa y no avisará de un conflicto
de actualización. Vamos a ver los argumentos en detalle.
nFilas
| lFilas
En
Visual Foxpro 3.0 el primer argumento era lógico y .T. significaba
que se debían actualizar todos los registros cambiados, mientras
que .F. solo significaba que se actualizará el registro actual.
Este argumento lógico todavía funciona en Visual FoxPro
6.0, pero la alternativa numérica nos da un mayor control sobre
esto.
El
argumento numérico puede ser 0, 1 o 2 y controla como se actualizan
los registros. Un argumento de 0 (el valor por defecto) solo actualizará
el registro actual. Usando 1 o 2 actualizará todos los registros
modificados. La diferencia entre 1 y 2 tiene que ver en que sucede si
uno o más de los registros modificados no pueden ser actualizados.
Poniendo 1originará que el
tableupdate falle si cualquiera de los registros no puede ser actualizado.
Mientras que con 2 forzará a que Visual FoxPro actualice todos
los registros que pueda y que guarde una lista de los registros que no
pueden ser actualizados (esta lista es almacenada en la matriz pasada
como cuarto argumento).
lForzar
Este
argumento, de tipo lógico, controla si Visual FoxPro dará
un fallo en el TableUpdate si el registro que está siendo actualizado
ha sido cambiado por otro usuario mientras estabamos realizando las modificaciones.
Un valor de .T. fuerza la actualización aunque haya un conflicto,
mientras que .F. provocará que la actualización falle si
el registro del disco no está igual que como estaba al principio
de las modificaciones.
Recomiendo
encarecidamente que este argumento esté siempre a .F.. La razón
es que si no lo haces, tu código puede reemplazar las modificaciones
de otros usuarios indiscriminadamente. Lo que realmente debes hacer es
controlar el valor de retorno del TableUpdate para ver si se ha realizado
correctamente o no, y responder en este caso.
cAliasTabla
| nÁreaTrabajo
Este
argumento es el nombre del área de trabajo al cual le afecta el
tableupdate. Puede ser o bien el alias ó el número del área
de trabajo (¿Sigue alguien usando números de áreas
de trabajo en su código?).
Este
es otro de los argumentos opcionales que es recomendado usar siempre.
Si se omite este argumento entonces el TableUpdate afectará solo
al área de trabajo activa. Como podemos controlar esta situación,
es recomendable que le digamos al TableUpdate a que área de trabajo
debe afectar y no depender que el área de trabajo haya sido correctamente
seleccionada. La razón es que Visual FoxPro está orientado
a eventos y puede llegar a suceder que no seas capaz de saber cual es
el área de trabajo activa debido a que diversos eventos pueden
cambiar el área de trabajo activa. Poniendo el alias en la función
TableUpdate eliminarás cualquier posible efecto de equivocarte
en el área de trabajo a actualizar.
cMatrizErrores
Este
último argumento solo es válido si el primer argumento es
2. Con el primer argumento puesto a 2, la función TableUpdate intentará
actualizar todos los registros modificados y si alguno falla se pondrá
el número de registro que ha fallado en la matriz cMatrizErrores.
Un ejemplo de valores 1 y 2 como primer
argumento pueden ayudar a saber que significa todo esto. Vamos a suponer
que los registros 1, 3, 5, 6 y 9 han sido modificados en un bufer por
tablas. Realizamos un TableUpdate con 1 ó 2 como primer argumento
y hay un conflicto de actualización en los registros 3 y 6.
Con un valor de 1 en el primer argumento,
la función TableUpdate actualizará el registro 1 y entonces
cuando no pueda actualizar el registro 3 parará de intentar actualizar
registros y devolverá un .F. indicando un fallo de la operación
de actualización. Usar el valor 2 como primer argumento, provocará
que la función TableUpdate continúe intentando actualizar
el resto de los registros después de que fallara el registro 3.
La matriz definida en el cuarto argumento mantendrá la lista de
registros que no han podido ser actualizados (3 y 6), el TableUpdate de
todos modos devolverá .F. indicando un fallo en la actualización
debido a que no se ha completado dicha actualización.
…No Actualizar
Utilizar
el almacenamiento de datos en bufer no solo nos permite guardar las modificaciones
que ha realizado un usuario, también ofrece un método para
descartar las modificaciones. La función TableRevert restaurará
un bufer sucio poniendo los valores como estaban almacenados anteriormente
en el disco, la sintaxis es la siguiente;
TABLEREVERT([lTodasFilas [, cAliasTabla | nÁreaTrabajo]])
Los dos argumentos de esta función
son descritos en las siguientes secciones.
lTodasFilas
Este
argumento, de tipo lógico, controla que registros serán
restaurados, si es .T. entonces todos los registros sucios serán
restaurados en el alias seleccionado, un valor de .F., solo restaurará
el registro actual. Si no se especifica este argumento solo afectará
al registro actual.
cAliasTabla
| nÁreaTrabajo
Es el nombre de alias o número
de área de trabajo sobre la cual la función TableRevert
actúa. Si no se especifica se hará sobre el área
de trabajo activa.
¿Cómo es el vampiro
asesino?
Las
funciones TableUpdate y TableRevert devuelven valores que indican si han
sido realizadas correctamente o con fallos. TableUpdate devuelve un valor
lógico .T. indicando que la actualización ha sido completada
satisfactoriamente o una valor .F. indicando que la actualización
ha fallado en parte o completamente. TableRevert devuelve un número
que indica el número de registros que han sido restaurados.
En ambos casos es importante conocer
los valores devueltos y reaccionar a ellos. Por ejemplo, el siguiente
código podría ser usado para actualizar un bufer de la tabla
clientes.
IF NOT TableUpdate(1,.F.,”Clientes”)
Wait Window “Imposible grabar su trabajo”
TableRevert(.T.,”Clientes”)
ENDIF
La
sentencia IF comprueba el valor devuelto por el TableUpdate y actúa
en consecuencia. El TableRevert es necesario porque un TableUpdate que
falle no actualiza la tabla, pero deja el bufer sucio y este debe ser
limpiado antes de cerrar la tabla. Hay otras maneras de controlar fallos
del TableUpdate, por ejemplo;
IF NOT TableUpdate(1,.F.,”Clientes”)
IF MessageBox(“Imposible grabar su trabajo. ¿Quieres descartar los cambios?”,;
MB_YESNO,”Actualización fallida”) = IDYES
TableRevert(.T.,”Clientes”)
ENDIF
ENDIF
En
este caso el fallo del tableupdate originará que el usuario reciba
un message box preguntándole si desea descartar los cambios. Si
se escoge "si" entonces la tabla es restaurada, si no se mantendrá
en el formulario manteniendo sus cambios intactos. El usuario podrá
intentar guardar los cambios mas tarde.
Téngase en cuenta en ambos
ejemplos que no se ha puesto una selección del área de trabajo.
Esto es debido a que el área de trabajo es especificada en las
funciones y así no hay necesidad de seleccionar ningún área
de trabajo en particular.
Resumen
En
el ultimo artículo hemos revisado el sistema de almacenamiento
de tablas en bufer a grandes rasgos y descubrimos lo que puede hacer por
nosotros. Vimos que el almacenamiento en bufer puede hacer que nuestro
código sea mas simple y fácil de entender
En
este artículo han sido revisadas las dos principales funciones
que afectan al almacenamiento en bufer, TableUpdate()
y TableRevert(). Estas dos funciones nos dan un control definitivo acerca
de si las modificaciones en el bufer serán escritas en el disco
y cuando serán realizadas.
No hay comentarios. :
Publicar un comentario
Los comentarios son moderados, por lo que pueden demorar varias horas para su publicación.