CloneCursor como definir os parâmetros Reset KeepSettings ClientDataSet Delphi

Quando você clona um ClientDataSet,você cria não apenas um ponteiro adicional para um armazenamento de memória compartilhada, mas também uma visão independente dos dados. E definir corretamente os parâmetros Reset KeepSettings é crucial para ob

O foco principal deste artigo  é como definir os parâmetros Reset KeepSettings do método cloneCursor .  O que esses parâmetros trazem de diferente ao se clonar um clientDataSet ? Ou mesmo ,  o que pode ocasionar uma escolha mal feita ou uma desatenção na hora de definirmos esses parâmetros ? Antes disto vamos a uma breve introdução do método em si

Quando você clona os dados de um ClientDataSet , você cria  não apenas um ponteiro adicional para um armazenamento de memória  compartilhada, mas também uma visão independente dos dados. Quando falo de ponteiros , me refiro a necessidade de deslocarmos todos os dados sem perdermos a localização do ponteiro inicial ou vice versa .Quando  falo de visão independente de dados , falo no sentido de podermos aplicar filtros , índices , ranges nesta nova visão de dados sem afetar a visão dos dados iniciais ou vice-versa .   Apesar de termos uma Visão diferente não se pode  modificar os dados de um sem afetar o conjunto de dados do Outro , pois ele é compartilhado na memória. Toda alteração , inserção , eliminação em um , automaticamente será refletidas para o outro e vice versa .

Vamos a definição do método

procedure CloneCursor(Source :TCustomClientDataSet; Reset: Boolean; KeepSettings: Boolean = False);

Nos exemplos que se seguem iremos sempre referenciar o Objeto Ativo ClientDataSet o qual iremos clonar de CdsFonteDeDados e o Objeto que receberá essa fonte de dados de CloneCds

 
Para usa-la fazemos assim:
    cloneCds:TClientDataSet;
  begin
    cloneCds.CloneCursor(CdsFonteDeDados,Reset ??,KeepSettings ???)
  end;

O primeiro parâmetro é a fonte dos dados que vc quer clonar ou obter . Este argumento tem que ser um ClinteDataSet ativo e que aponte para o armazenamento de memória que vc quer acessar .  Muito intuitivo este argumento e dispensa comentários adicionais

O Segundo parâmetro atua juntamente com o terceiro . Porém se pudéssemos aqui utilizar uma analogia com a genética , diríamos que o segundo parâmetro é o gene dominante . de modo que o terceiro parâmetro  vai influenciar se o segundo parâmetro for recessivo . Então se o Reset:=True (Dominante) , indepedentemente do valor que se atribui para KeepSettings (False ou True) , a característica do Clone já esta traçada e não há como fazer mais nada . Então para efeito de estudo passamos a ter um conjunto de Três situações possíveis que devemos analisar e comentar que são :

vamos começar com) Reset igual a true .. KeepSettings (False ou True) tanto faz

O Parâmetro Reset como o próprio nome já diz , vai resetar toda e qualquer propriedade que possa já existir (no sentido de que já foi definida) no Clone . Que propriedades seriam estas ?  Por exemplo os valores de IndexName (ou IndexFieldNames), filter, filtered, MasterSource, MasterFields, OnFilterRecord e ProviderName

Leia com muita atenção , pois isto é importante e vou prova-lo . Imagine que vc tenha um clientDataSet com a propriedade ProviderName definida com o nome de algum TDataSetProvider . Imagine ainda que vc definiu no evento BeforeUpdateRecord deste Provider um método inerente a sua necessidade , de modo que quando vc fizer um clientDataSet.ApplayUpdates este evento seja disparado . Ai vc usa um uma fonte de dados e o repassa a este clientDataSet definindo no método o Reset como True . Mas na hora do ClientDataSet.ApplayUpdates , as coisas não ocorrem do jeito que vc pensou e depois de quatro horas (projeto grande cheio de herança..) , vc descobre que o evento BeforeUpdateRecord não esta sendo executado ... Mas como ???? A resposta pode agora ser simples , mas nem tanto obvia para quem desconhece o parâmetro Reset . Ao utilizar o Reset = True , as propriedades definidas no clientDataSet serão resetadas , e entre essas propriedades está o ProviderName . Neste caso o ProviderName estará em Branco e vc não conseguira aplicar (comitar) no Banco de Dados (ApplayUpdates)

Segundo caso) Reset:= False ; KeepSettings:=False 

O Reset sendo False o método passa a olhar para a definição do terceiro parâmetro para definir o comportamente do clone . Como  o terceiro parâmetro nesta situação tb é Falso , o gene dominante será o Reset . O Reset=false implica que as propriedades que o clone usará são as que forem definidas (forem ou estão) pelo clientDataSetFonte . Que propriedades seriam essas ? Mais uma vez , os valores de IndexName (ou IndexFieldNames), filter, filtered, MasterSource, MasterFields, OnFilterRecord e ProviderName .

Agora pense novamente na situação levantada acima , onde vc tem clientDataSet com a propriedade ProviderName definida com o nome de algum TDataSetProvider . Imagine ainda que vc definiu no evento BeforeUpdateRecord deste Provider um método inerente a sua necessidade , de modo que quando vc fizer um clientDataSet.ApplayUpdates este evento seja disparado . Irá ocorrer novamente um problema , porque o ProviderName que foi definido originalmente pelo clone será apagado e sobre escrito pelo ProviderName que foi definido pelo clientDataSetFonte e o tão esperado evento BeforeUpdateRecord  que vc escreveu não será disparado . Por conta da sobreposição o ProviderName do Clone aponta (na verdade não se trata de um ponteiro mas por hora pensemos assim) para o TDataSetProvider que foi definido no CdsFonteDeDados , e é o evento BeforeUpdateRecord deste Provider que será excecutado ..

 
Terceiro caso) Reset:= False ; KeepSettings:=True

O Reset sendo False o método passa a olhar para a definição do terceiro parâmetro para definir o comportamento do clone . Como  o terceiro parâmetro nesta situação é True, o gene dominante será o KeepSettings . O  KeepSettings qnd dominante implica que as propriedades que do clone não serão sobrescritas pelo clientDataSetFonte . Que propriedades seriam essas ? Pela terceira vez, os valores de IndexName (ou IndexFieldNames), filter, filtered, MasterSource, MasterFields, OnFilterRecord e ProviderName .

Pela terceira vez pensaremos na situação levantada acima , onde vc tem clientDataSet com a propriedade ProviderName definida com o nome de algum TDataSetProvider . Imagine ainda que vc definiu no evento BeforeUpdateRecord deste Provider um método inerente a sua necessidade , de modo que quando vc fizer um clientDataSet.ApplayUpdates este evento seja disparado . Como agora o ProviderName do Clone e as demais propriedades (digamos assim , são as originais as que foram previamente definidas) , o tão esperado evento BeforeUpdateRecord  será executado ... Ebaaaaaaaaaaaaaaaaaaaaaaaa . Ufa , consegui !!!!!

Com isto percebem que para clonar uma fonte de dados teremos então tres possíveis situações

A forma que vc irá utilizar este importante método sera inerente á sua necessidade, a intenção aqui foi mostrar possiveis causas de erros e dores de cabeça ao se utilizar o método . Vale ressaltar que o último parâmetro é opcional ( caso não se define ele assumirá KeepSettings=False )

No mais ainda tem alguma particularidades que não foram abordadas , por questões de tempo , paciência e espaço . O que deve ficar claro que é muito bonito usar cloneCursor , mas devemos saber por onde passam as coisas . No mais , estou aberto a qualquer crítica e de prontidão para recebe-la , meu muito obrigado e atê a próxima .

Link Original
http://marcosalles.wordpress.com/2011/02/17/clonecursor-como-definir-os-parametros-reset-keepsettings/
Ebook exclusivo
Dê um upgrade no início da sua jornada. Crie sua conta grátis e baixe o e-book

Artigos relacionados