Página 1 de 1
Bloqueio e desbloqueio de registro
Enviado: 14 Jun 2012 00:00
por Vandi
Boa noite...
Gostaria de saber o que está errado nêsse trecho de uma rotina, pois não está funcionando como deveria...
Código: Selecionar todos
*
* Verifica se o registro está bloqueado para edição:
* Em caso negativo - bloqueia
* Em caso positivo - mostra uma mensagem e sai
*
IF!EMPR->(DBRLOCK(RECNO()))
EMPR->(DBRLOCK(RECNO()))
ELSE
ALERT('O REGISTRO ESTA EM USO. TENTE MAIS TARDE!!!')
EXIT
ENDIF
*
PegaVariaveis()
*
Edita()
*
GetVariaveis()
*
* Le os dados alterados
READ
*
* Solicita confirmacao atraves da rotina Alerta()
*
if Alerta("Confirma a alteração?","ATENÇÃO",MB_YESNO,MB_ICONQUESTION) == IDYES
* Grava dados
GravaDados()
EMPR->(DBRUNLOCK()) //Libera os registros para uso
EMPR->(DBCOMMIT())
*
endif
*
*
Agradecimentos,
Gilvandi
Bloqueio e desbloqueio de registro
Enviado: 14 Jun 2012 00:41
por alxsts
Olá!
DbRLock() funciona em Clipper 5.2 e 5.3. Verifique se não está em Eof() ( Recno() = LastRec() + 1 )
Se não der certo, use o tradicional RLock() e Unlock.
Rotina com bloqueio e desbloqueio de registro
Enviado: 14 Jun 2012 14:55
por Vandi
Boa tarde...
Gostaria, se possível, que alguém disponibilizasse aqui no forum uma pequena rotina a título de exemplo com bloqueio e desbloqueio de registro, inclusive de verificação para ver se tal registro está bloqueado ou não.
Peço isso pq estou "quebrando a cabeça" aqui com um sistema de uso próprio e, até o momento, não conseguí resolver. Tbém não obtive êxito nas buscas que já fiz.
Agradecimentos antecipados,
Gilvandi
Bloqueio e desbloqueio de registro
Enviado: 14 Jun 2012 17:59
por Imatech
Tente novamente...
Código: Selecionar todos
* Verifica se o registro está bloqueado para edição:
* Em caso negativo - bloqueia
* Em caso positivo - mostra uma mensagem e sai
LOCAL lTime := .F.
LOCAL iTime := 0
PegaVariaveis()
Edita()
GetVariaveis()
* Edita Variaveis
READ
* Atualiza varivel
iTime := Seconds()
* Tenta Bloqueio do Registro em Até 2 Segundos
While !( lTime )
* Tenta Bloqueio do Registro
IF EMPR->( DBRLOCK() )
* Sucesso
lTime := .T.
ELSE
* Verifica Limite de Tempo para tentativas...
IF ( ( Seconds() - iTime ) > 2 )
* Tempo Excedido: Abandona loop
EXIT
ENDIF
* Aguarda 1/10 de segundo para nova tentativa
Inkey( 1/10 )
ENDIF
ENDDO
* Se Bloqueou o Registro...
If ( lTime )
* Solicita confirmacao atraves da rotina Alerta()
if Alerta("Confirma a alteração?","ATENÇÃO",MB_YESNO,MB_ICONQUESTION) == IDYES
* Grava dados
GravaDados()
* Salva Arquivo
EMPR->( DBCOMMIT() )
* LIbera registro
EMPR->( DBRUNLOCK() ) //Libera os registros para uso
ELSE
ALERT('O REGISTRO ESTA EM USO. TENTE MAIS TARDE!!!')
ENDIF
Rotina com bloqueio e desbloqueio de registro
Enviado: 14 Jun 2012 18:12
por Imatech
Saber se esta bloqueado/em uso: DBRLOCK()
Código: Selecionar todos
* Verifica se o registro está bloqueado para edição:
* Em caso negativo - bloqueia
* Em caso positivo - mostra uma mensagem e sai
LOCAL lTime := .T.
LOCAL iTime := 0
PegaVariaveis()
Edita() // Essa função parece fazer a mesma coisa da proxima: GetVariaveis()
GetVariaveis()
* Edita Variaveis
READ
* Verifica Tecla Escape
If LastKey() # 27
* Solicita confirmacao atraves da rotina Alerta()
if Alerta("Confirma a alteração?","ATENÇÃO",MB_YESNO,MB_ICONQUESTION) == IDYES
* Atualiza varivel
iTime := Seconds()
* Tenta Bloqueio do Registro em Até 2 Segundos
While ( lTime )
* Tenta Bloqueio do Registro
IF EMPR->( DBRLOCK() )
* Grava dados // Parece função desnecessparia
GravaDados()
* Salva Arquivo
EMPR->( DBCOMMIT() )
* LIbera registro
EMPR->( DBRUNLOCK() ) //Libera os registros para uso
ELSE
* Verifica Limite de Tempo para tentativas...
IF ( ( Seconds() - iTime ) > 2 )
* Tempo Excedido: Abandona loop
ALERT('O REGISTRO ESTA EM USO. TENTE MAIS TARDE!!!')
lTime := .F.
ELSE
* Aguarda 1/10 de segundo para nova tentativa
Inkey( 1/10 )
ENDIF
ENDIF
ENDDO
ENDIF
ENDIF
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 02:36
por rochinha
Amiguinhos,
Eu colocaria o trecho:
Código: Selecionar todos
* Tenta Bloqueio do Registro em Até 2 Segundos
While !( lTime )
* Tenta Bloqueio do Registro
IF EMPR->( DBRLOCK() )
* Sucesso
lTime := .T.
ELSE
* Verifica Limite de Tempo para tentativas...
IF ( ( Seconds() - iTime ) > 2 )
* Tempo Excedido: Abandona loop
EXIT
ENDIF
* Aguarda 1/10 de segundo para nova tentativa
Inkey( 1/10 )
ENDIF
ENDDO
Após:
Código: Selecionar todos
* Solicita confirmacao atraves da rotina Alerta()
if Alerta("Confirma a alteração?","ATENÇÃO",MB_YESNO,MB_ICONQUESTION) == IDYES
* Grava dados
GravaDados()
Pois não tem porque eu travar um registro se escolher não confirmar depois.
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 11:58
por alxsts
Olá!
Também acho que a ordem lógica no código postado está incorreta. Da forma como está, enquanto os gets são lidos algum outro usuário pode alterar o registro e na hora que esta rotina grava, desfaz as alterações do outro usuário.
Creio que a sequencia certa é:
- assim que a alteração for sinalizada, fazer um refresh no registro a alterar ( DbSkip(0) ) e o lock
- receber os novos dados (Gets) enquanto o lock no registro está ativo
- solicitar confirmação da alteração
- se confirmado: - gravar - commit
- unlock
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 15:22
por Imatech
Concordo em Gênero, Numero e Grau... kkk ( Código gerado a partir do exemplo do usuario := bug )
Segue correção melhorada do exemplo... (não testado)
Código: Selecionar todos
* Verifica se o registro está bloqueado para edição:
* Em caso negativo - bloqueia
* Em caso positivo - mostra uma mensagem e sai
LOCAL lTime := .T.
LOCAL iTime := 0
PegaVariaveis()
Edita() // Essa função parece fazer a mesma coisa da proxima: GetVariaveis()
GetVariaveis()
* Edita Variaveis
READ
* Verifica Tecla Escape
If LastKey() # 27
* Solicita confirmacao atraves da rotina Alerta()
if Alerta("Confirma a alteração?","ATENÇÃO",MB_YESNO,MB_ICONQUESTION) == IDYES
* Atualiza varivel
iTime := Seconds()
* Tenta Bloqueio do Registro em Até 2 Segundos
While ( lTime )
* Tenta Bloqueio do Registro
IF EMPR->( DBRLOCK() )
* Grava dados // Parece função desnecessparia
GravaDados()
* Salva Arquivo
EMPR->( DBCOMMIT() )
* LIbera registro
EMPR->( DBRUNLOCK() ) //Libera os registros para uso
ELSE
* Verifica Limite de Tempo para tentativas...
IF ( ( Seconds() - iTime ) > 2 )
* Tempo Excedido: Abandona loop
ALERT('O REGISTRO ESTA EM USO. TENTE MAIS TARDE!!!')
lTime := .F.
ELSE
* Aguarda 1/10 de segundo para nova tentativa
Inkey( 1/10 )
ENDIF
ENDIF
ENDDO
ENDIF
ENDIF
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 15:37
por alxsts
Olá!
O lock tem que estar antes do READ...
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 15:51
por Imatech
MInha opinião prática é a mesma do amigo Rochinha:
Pois não tem porque eu travar um registro se escolher não confirmar depois.
Ou o usuario ficar uma eternidade para confirmar/cancelar a operação...
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 15:57
por alxsts
Olá!
Aí cai no caso de alguem alterar enquanto os gets são executados.
O ideal é fazer o lock antes e usar o Get TimeOut (um getsys alterado). Assim, se o usuário demorar a terminar a edição, o sistema cancela o READ.
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 16:04
por Imatech
Olá alxsts...
Desejo sucesso na sua concepção...
Tente aplicar isso em SGDB...
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 16:35
por alxsts
Olá!
Agradeço a gentileza e desejo-lhe o mesmo sucesso em suas concepções.
Esse conceito foi muito utilizado e ainda hoje roda em muitos sistemas Clipper.
Querer comparar isso a um SGBD relacional, que é autocontido, gerencia a concorrência, tem controle de transações e integridade referencial e oferece a possibilidade de trabalhar com record sets desconectados é besteira. Mas mesmo assim eles oferecem os recursos de lock de registro, como Select for update (Oracle, DB2, MySql) e Rowlock no SQL Server. Com isso, conforme a necessidade, tem-se a liberdade para ecolher entre bloqueio otimista ou pessimista.
As técnicas que estamos discutindo foram usadas em xBase justamente por seus "bancos de dados" serem apenas amontoados de tabelas e índices, sem os recursos de um SGBD, onde o programador é quem tem que controlar a concorrência.
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 17:12
por Imatech
Olá alxsts...
Sem discussão sobre o sexo dos anjos...
Ajuste o codigo a seu bel prazer (ou faça um post completo para manutenção de dados)... o usuario escolhe que implementação usar...
Abç...
Bloqueio e desbloqueio de registro
Enviado: 15 Jun 2012 17:31
por alxsts
Olá!
Nem precisava dizer isso..