Bloqueos y Edición de Registros

Responder
Cristobal
Site Admin
Mensajes: 315
Registered for: 3 years 5 months
Spain

Bloqueos y Edición de Registros

Mensaje por Cristobal »

Esta conversación se ha mantenido en el chat de Skype del canal de Mod-Harbour, y como me ha parecido sumamente interesante, he querido transcribirla aqui
Victor, 7:25Hola.
Aprovecho este foro para lanzar una cuestión y ver sus opiniones, ya que este grupo es de modHarbour el sentido del mismo es la utilización de harbour como backend para la web ( y los diferentes temas que vayan surgiendo al respecto ) Una de las cosas que más se realiza es acceder a los datos, independientemente de su origen, y me gustaría saber su opinión o como gestionan el bloqueo de registros para su edición. Me explico; el usuario A abre una ficha para modificarla, la modifica y la guarda en la base de datos. Por supuesto, mientras la está editando no tiene la conexión a la BD abierta ni el registro bloqueado. Mientras el Usuario B hace lo mismo. Como controlan esto? una tabla con los registros que se están modificando? una marca en el registro que se está modificando? Comprobar cuando se guarda el registro si ha sido modificado por otro usuario después del inicio de la edición? utilizan solo un control o varios a la vez?
Salud!
Paquito, 10:19Hola Víctor. Respondiendo a tu cuestión.

En su día me planteé exactamente el mismo problema. Hablo de no menos de 10 años.
Hasta donde yo sabía en los foros que habitualmente transitaba (fwh/ Harbour) nunca se habia preguntado por esto ni se habia planteado el problema. Hasta cierto punto es logico, es un problema que no es ni de Fwh ni de Harbour, es un "problema" de técnica programática. Así las cosas pensé y desarrollé la siguiente idea:

- Los documentos editables tendrán un botón de edición, es decir, el usuario accederá a verlos pero sólo serán editables cuando en el momento de tenerlos en pantalla pulsen en el botón modificar. Esto es importante por lo que viene a continuación

- cuando un primer usuario pulsa el botón modificar entonces bloquea el documento y el resto de usuarios sólo pueden ver pero no modificar. En los listados aparece un bitmap a los usuarios indicando que está bloqueado y qué programa y quién lo tiene bloqueado. El bloqueo se realiza con tecnica que impida que cualquier cuelgue en la aplicacion deje el documento en modo edicion, es decir, no grabar los bloqueos en una tabla.

Y hasta ahora. Estoy abierto a mejoras
Victor, 11:32@Paquito gracias por tu planteamiento. Cuando dices que bloquea el documento, te refieres a que tienes un campo en la tabla tipo 'locked' ?
Paquito, 11:35no. eso es ruina Victor. Como comenté ese sistema dejará en caso cuelgue documentos bloqueados. Desarrollé un sistema basado en handle, porque dadme un handlevy moveré el mundo. Si tienes interés puedo profundizar

Victor, 11:37Y como saben los usuarios que está bloqueado?

Paquito, 11:42Utilizo tecnica handle. Realmente un sistema basado en el handle devuelto por FCreate.
Cuando el doc1 se bloquea creo archivo blq_doc1.txt conteniendo info de programa y usuariio. Si el file blq_doc1.txt no existe o no puede abrirse en exclusivo es que doc1 está bloqueado.
Esa es la técnica handle... Cuando el programa crashea los archivos dejan automáticamente de estar en usoEs el S.O. el que gestiona

Victor, 11:44Ok, es buena, pero en un entorno web, no se tendría acceso a estos ficheros del disco. Creo.

Cristobal. Hoy a las 11:44Yo creo que sí Victor,

Victor 11:48Como lo harías? Por API?Me refiero a que cuando le pides, por ejemplo, una lista de documentos, para devolverla con la marca de si está bloqueado o no, hay que tomar una lista de los ficheros .txt que hayan y procesarlos con la lista de documentos, correcto?

Paquito, 11:55Si la pregunta es para mi respondo:
Si asi lo hago y funcionando en desktop 100% Ni un problema en no menos de 10 añosLa tecnica vale para bloquear y compartir cualquier cosa sin miedo a crashes

Victor, 11:58Exacto @Paquito, a eso me refiero. En un entorno web, haces la petición de los datos, te los devuelve, los muestras por pantalla (edición) pero no puedes tienen un fichero abierto en el disco mientras editas, en ese momento puedes hasta estar totalmente desconectado. Pero igualmente estás editando.Para Desktop es una muy buena opción, pero no sé cómo se aplicaría en un entorno web.

Pedro, 12:06Para web yo he utilizado un campo timestamp que se actualiza cada vez que se modifica un registro.
Al leer para edición me traigo también el timestamp y al recibir el submit del formulario primero compruebo si el timestamp a cambiado.
En caso de que no cambie, quiere decir que nadie lo ha editado y simplemente lo actualizo.
Si está cambiado hay que decidir qué haces;
- ¿ Le devuelves al nevegador el formulario indicándole los campos en conflicto.?
- ¿Le avisas del conflicto y que vuelva a editarlo?
- ¿ Admites la edición y guardas en algún log el conflicto ?
- ¿Cualquier otra opción ?

Victor, 12:09Gracias @Pedro. Este sistema lo he planteado también. Lo veo válido para web.
Cristobal, @Victor , Evidentemente si podemos establecer ahora las estructuras, creo que una buena opción a tener en cuenta, es la de añadir a nuestras estructuras de bases de datos un campo de tipo [ = ] ModTime, que se actualiza automáticamente por parte de harbour cada vez que el registro es modificado. Consultando dicho campo tenemos la información de si ha sido modificado o no.Para mí, últimamente este tipo de campos para trabajar con DBFs es imprescindibley creo que se puede hacer compatible si utilizas otras BBDD

Victor, 12:24Exacto. Serían updated_at y created_at (copia directa de eloquent) :)

Cristobal, 12:25Por ahí van los tiros, evidentemente, el enfoque es el de darle amplitud de miras teniendo en cuenta el ORM que estás desarrollandoEn el caso de no poder ( o simplemente ser complicado en ese momento ) modificar las estructuras de los DBFs que ya tienes funcionando, tenemos otras posibles técnicas a nuestra disposición
Paquito, 12:27@PedroVictor Casajuana Mas Casajuana Mas, Hoy a las 12:09Válido para web pero ineficiente IMHO porque sólo se sabe al final. Un usuario un cuarto de hora modificando un pedido y luego se lo rechaza el sistema. Es para blasfemar en arameo12:28Tienes toda la razón, @Paquito, ahí es donde entraría un timer para consultar de vez en cuando el estado de ese campo y combinarlo con tu técnica del "bitmap" o mensajito, no?

Victor, 12:32En este caso se podría recurrir a sockets, como hace Google Drive, y mostrar los usuarios que están dentro. Ya sería ir a otro nivel.

Cristobal, 12:34Sin tener que irnos tan lejos, considero el tema que estamos hablando tan sumamente importante como para entender que para dar una cumplida solución ( digamos al 99% ) hemos de asumir utilizar varias técnicas combinadas ( al menos 2 )

Victor, 12:34Exacto

Cristobal, 12:36Yo utilizo los ModTime, evidentemente, y un sistema de logs. Pero, eso sí, que sea transparente para mí: que se lo "curre" harbour.

Paquito, 12:41Aunque hable de .dbfs esto que digo valdriía para toda base de datos:

Otro sistema que nunca indagué ni usé fue explotar la capacidad de Harbour para hacer multiples bloqueos en la misma .dbf.

Imaginaros/ imagínense que tenemos una .dbf con documento_tipo documento_numero documento_usuario. Si cada vez que hacemos una entrada (o buscamos) y bloqueamos, quizá podría hacer el mismo papel que los archivos blq_.txt que propuse anteriormente

Cristobal, 12:42Harbour también dispone del tipo [ ^ ] RowVers 8 Row version number; modification count of this record

Paquito, 12:42---
Asi pues el sistema, para que sea lo más parecido a optimo, tiene que ser:

1 - Resistente a crashes y
2 - Debe avisar del bloqueo PREVIAMENTE

Cristobal, 12:43Ahí es donde se cae mi planteamiento tal y como lo he hecho, en el punto 2

Paquito, 12:45Yo lo que digo es tener una .dbf bloqueos.dbf, aunque la App tire de mySql da igual, lo haremos en una .dbf sacando provecho de la posibilidad de bloquear multiples registros bloqueados en una misma .dbf que tiene harbourBloqueos.dbf sustituiria a mi sistema de bloqueos por handle.
Aunque nunca usé bloqueos multiples en Harbour, en teoria deberia funcionar y valdria, por supuesto, tanto para desktop como para web
Paquito, 12:53---

Se podria tener un .dbf de bloqueos por cada tipo de documento. Asi blq_Albaranes.dbf seria la gestionadora de bloqueo de Albaranes.dbf blq_Pedidos.dbf lo mismo de Pedidos... Mi gusto es tener todo en la misma .dbf asi que me gusta mas un bloqueos.dbf separado por tipo de documento. De esta manera tambien se puede usar para otro tipo de documentos o situaciones. Se podria bloquear por ejemplo contadores, antes de dar contador, se bloquea. Cuando se genera una hoja de carga, que es un documento no fisico, sino que se compone al vuelo a partir de otros documentos, se puede validar que no haya ya uno generado. Se puede bloquear asimismo que dos usuarios no entren a la vez a una determinada opcion del menu.

Es decir el sistema de bloqueos va mucho mas alla de la mera edicion de documentos.

dbRLock() -> Bloqueo de multiples registros en una misma work area (por el mismo usuario, evidentemente)
https://www.itlnet.net/programming/prog ... 2e977.html
Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo
El secreto de la felicidad no está en hacer lo que te gusta, sino en que te guste lo que haces

Cristobal
Site Admin
Mensajes: 315
Registered for: 3 years 5 months
Spain

Mensaje por Cristobal »

Continuacion: ( me he dado cuenta que no se han colocado bien algunos mensajes en su linea temporal )
Paquito, 10:25Nota 1. ¿ Qué implica lo anterior ? Pues que todos los formularios, en todos sus controles tendrán una cláusula WHEN lEditable y lEditable será .t. sólo cuando se pulse el botón Modificar y sólo se podrá pulsar el botón modificar cuando ningún otro usuario tenga bloqueado el documento.
Nota 2. El uso del botón modificar es opcional. se trataría de que al entrar a editar un documento, este será editable dependiendo de si está o no bloqueado por otro usuario
Cristobal 10:48@Paquito creo que tu enfoque es muy acertado: evitas los problemas posteriores que se puedan plantear. Sólo una duda: cómo evitas que un usuario deje "indefinidamente" un registro bloqueado en edición ( lo típico de que se vaya a desayunar ), usas un timer y valoras la inactividad ?
Paquito, 11:32Cristóbal. No contemplo abandono por dicumento pero si abandono total por inactividad del programa. En todo caso el sistema muestra un icono por linea en el grid que permite con el ratón ver el usuario y programa bloqueantes.

El sistema de bloqueo para impedir edición lo uso rambien en algunos listados que exigen la no edición del documento... Es decir bloqueo para procesar y no para editar
Paquito, 13:09Como corolario:
Un sistema de bloqueo resistente a crashes es una maravilla. Con él se puede controlar el acceso usuarios y ordenar el flujo concurrente de operaciones.
No sé si otros motores soportan multiples bloqueos, pero Harbour Dbf RDD si lo soporta y con una sola Bloqueos.dbf tenemos la posibilidad de ordenar las acciones de nuestros usuarios con anticipacion. Ya nuestros usuarios no necesitarán aprender arameo

Victor, 13:25Pero creo que estamos en lo mismo. Desde el front se pide un registro al back por API. Se le devuelve un Json (o XML ) con la info y el front la modifica. Ahí ya no hay ningún rlock en la dbf, porque se ha cerrado la conexión.El único "hilo" que podría existir que nos indicaste en tiempo real si hay otro modificando lo mismo, sería por sockets. Pero eso ya es a parte de un (por ejemplo) ORM.
Paquito, 13:38Cuando pide un registro ahi se debe comprobar si está bloqueado. Si está bloqueado entonces se devuelve un .t. pero se deja ver pero no modificar

Paquito, 13:48Un simple CLOSE Bloqueos en el submit debería unlockear el registro
Victor, 14:25Cuando pide un registro ahi se debe comprobar si está bloqueado. Si está bloqueado entonces se devuelve un .t. pero se deja ver pero no modificar
Paquito Mix, Hoy a las 13:38Exacto, pero en web los bloqueos mientras editas, no se pueden hacer. (Creo) como bien has dicho al principio, esto no es tema harbour, es más técnicas de programación o cómo resolver este problema independiente del lenguaje. Navegare a ver que encuentro. @Paquito muchas gracias, interesante conversación. Creo que entre el tostón de ayer y la paliza de hoy, me vais a pillar manía... Gracias por pasar el tema al foro @Cristobal
Buen provecho a todos y buen finde!
Paquito, 14:33"Exacto, pero en web los bloqueos mientras editas, no se pueden hacer."

No sé si me hice entender o no te entendí.
Cuando se hace el request y justo antes de traer los datos hacer el bloqueo. Cuando se hace el submit hacer el desbloqueo.
Y si es cuestión de técnica programática, pero la técnica de bloqueo múltiple (sobre .dbf) veo dificil que se pueda hacer en otras plataformas. Buen provecho y buen finde... A por los tercios !!!!

Charly, 14:47Olvidaros de tener registros bloqueados en entorno web. Si, cuando realizas un proceso, pero cuando acabas, se acaba todo...

Cristobal: 15:32Algunas veces no es tanto por bloquear el registro, que como bien dices, se acabó la operación, ahí acaba todo, sino por disponer información del estado en el que se encuentra, o si ha habido variaciones desde que lo adquirió otro usuario.
Hay dos tipos de personas: las que te hacen perder el tiempo y las que te hacen perder la noción del tiempo
El secreto de la felicidad no está en hacer lo que te gusta, sino en que te guste lo que haces

Avatar de Usuario
VictorCasajuanaMas
Mensajes: 31
Registered for: 3 years 1 month
Spain

Mensaje por VictorCasajuanaMas »

Con el permiso de los administradores y si no lo ven conveniente que lo borren, pongo un link a una conversación del grupo de google sobre ADO Harbour que me pareció muy interesante en su día, con soluciones muy buenas sobre este tema, aunque no tengan mucha cabida en el mundo web: https://groups.google.com/g/ado-harbour ... JjaZWKAgAJ

Avatar de Usuario
VictorCasajuanaMas
Mensajes: 31
Registered for: 3 years 1 month
Spain

Mensaje por VictorCasajuanaMas »

Y como resumen de lo que se ha comentado, creo que "el santo grial" no existe en el tema de bloqueos en entornos web tal y como lo trabajamos con los DBF a nivel local o red. Hay que cambiar la lógica y evaluar los estados de los registros cuando se leen para modificarse y posteriormente al guardarlos, en ese momento es donde hay que trabajar la lógica, ya sea con timestamps, comparando el registro modificado con el anterior, dando al usuario opción a que hacer, hacerlo automático, etc... pero con esto no se puede definir un standard, ya que cada aplicación/problema tendrá sus necesidades y su lógica.

hmpaquito
Mensajes: 13
Registered for: 3 years 3 months
Spain

Mensaje por hmpaquito »

Por si a alguien no le quedó claro mi idea, aún mis escasos conocimientos en entorno web, si lo veo posible, si alguien lo quiere rebatir:

En request:
lBloqueado:= lEstaBloqueado("ALBARAN", cNumero)
lEditable:= !lBloqueado


En edicion:
Controles de edicion sin posibilidad de edicion, solo mostrar


En submit/ cancelacion de edicion:
Desbloquear("ALBARAN", cNumero)


¿ Qué razón puede haber para que no funcione ? ¿ Que no es la forma en que lo hacen en PHP/ Python/ Java ? No parece razón suficiente.

Avatar de Usuario
VictorCasajuanaMas
Mensajes: 31
Registered for: 3 years 1 month
Spain

Mensaje por VictorCasajuanaMas »

El tema es, como mantienes el bloqueo del registro si no tienes una conexión, vínculo o handle directo con los datos? En entorno web no tienes acceso directo a la base de datos.
Tú haces el request al API, el API ejecuta un proceso, puedes bloquear lo que quieras, el API termina el proceso y devuelve una respuesta, en ese momento, el proceso del API se termina, se muere y se cierran todos los vínculos hacia la base de datos.
Por eso lancé la consulta de qué métodos utilizabais para, en el caso web que se cierra todo una vez se ha finalizado la consulta, para indicar que un registro estaba bloqueado por otro usuario.

Salud!

hmpaquito
Mensajes: 13
Registered for: 3 years 3 months
Spain

Mensaje por hmpaquito »

Hola Víctor,

Pues sí. El sistema requiere "mantener estado". Se podría hacer haciendo que el sistema forme parte del cuore del mod o el server en cuestion, siempre que sea posible.

Salu2

Avatar de Usuario
VictorCasajuanaMas
Mensajes: 31
Registered for: 3 years 1 month
Spain

Mensaje por VictorCasajuanaMas »

No se trata del mod ni del servidor, es la propia tecnología web la que trabaja así.

Responder