Mais dúvidas com Insert usando MestreDetalhe (DatasetField)
Seguinte outro probleminha foi identificado usando a estrutura mestre detalhe... quando fazemos uma inserção de um detalhe que já tenha um mestre criado e persistido no banco de dados ele funciona perfeitamente. Porém como os ID's são campos auto-incremento, quando inserimos o mestre e o detalhe juntos e enviamos o pacote para o servidor para ser persistido evidentemente ele não persiste o detalhe porque o mestre ainda não possui um identificador. Sabemos que teremos de fazer isso na mão mas alguém sabe se a embarcadeiro pensou em algo?
Desde já agradeço as colaborações!
Desde já agradeço as colaborações!
Samuel Silva
Curtidas 0
Respostas
André Silveira
18/03/2011
Para esse caso em específico não.
Pois segundo a Embarcadero, deve-se usar o mínimo de recursos do banco de dados, por isso você deverá implementar uma forma de retornar o código, pode ser por uma procedure no banco que incremente o código e atualize um tabela de códigos por exemplo.
Atenciosamente,
André Luis da Silveira.
Pois segundo a Embarcadero, deve-se usar o mínimo de recursos do banco de dados, por isso você deverá implementar uma forma de retornar o código, pode ser por uma procedure no banco que incremente o código e atualize um tabela de códigos por exemplo.
Atenciosamente,
André Luis da Silveira.
GOSTEI 0
Marco Salles
18/03/2011
Um modo elegante de contornar este problema é vc definir uma constante tipada que sera sempre decrementada a medida que for dando o insert na Tabela Mestre .. Assim , vc define na mão mesmo este valores . O valor negativo é para não ter duplicidade. Na hora que vc for de fato commitar .
Os valores corretos da chave serão atulizados geralmente em uma consulta e é utilizado o UpdateRecord do TDataSetProvider
Um exemplo disso é este codigo
procedure TDm_Dados.dtsfornecedorBeforeUpdateRecord(Sender: TObject;
SourceDS: TDataSet; DeltaDS: TCustomClientDataSet; UpdateKind: TUpdateKind;
var Applied: Boolean);
{$J+}
const
Id: Integer = -1;
{$J-}
begin if (UpdateKind = ukInsert) then
begin
if (SourceDS = sqlfornecedor) then
begin
if (DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0) then
begin
Id := GenID('FORNECEDOR');
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
end;
end
else
if (SourceDS = sqlcontato) then
if (DeltaDS.FieldByName('CHAVE_CONTATO').Value < 0) then
begin
if DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0 then
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
DeltaDS.FieldByName('CHAVE_CONTATO').NewValue := GenID('CONTATO');
end;
end;
end; Tirado do Link https://www.devmedia.com.br/forum/delphi/395811-Master-Detail-com-incremento-negativo.html
SourceDS: TDataSet; DeltaDS: TCustomClientDataSet; UpdateKind: TUpdateKind;
var Applied: Boolean);
{$J+}
const
Id: Integer = -1;
{$J-}
begin if (UpdateKind = ukInsert) then
begin
if (SourceDS = sqlfornecedor) then
begin
if (DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0) then
begin
Id := GenID('FORNECEDOR');
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
end;
end
else
if (SourceDS = sqlcontato) then
if (DeltaDS.FieldByName('CHAVE_CONTATO').Value < 0) then
begin
if DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0 then
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
DeltaDS.FieldByName('CHAVE_CONTATO').NewValue := GenID('CONTATO');
end;
end;
end; Tirado do Link https://www.devmedia.com.br/forum/delphi/395811-Master-Detail-com-incremento-negativo.html
GOSTEI 0
Samuel Silva
18/03/2011
Um modo elegante de contornar este problema é vc definir uma constante tipada que sera sempre decrementada a medida que for dando o insert na Tabela Mestre .. Assim , vc define na mão mesmo este valores . O valor negativo é para não ter duplicidade. Na hora que vc for de fato commitar .
Os valores corretos da chave serão atulizados geralmente em uma consulta e é utilizado o UpdateRecord do TDataSetProvider
Um exemplo disso é este codigo
procedure TDm_Dados.dtsfornecedorBeforeUpdateRecord(Sender: TObject;
SourceDS: TDataSet; DeltaDS: TCustomClientDataSet; UpdateKind: TUpdateKind;
var Applied: Boolean);
{$J+}
const
Id: Integer = -1;
{$J-}
begin
if (UpdateKind = ukInsert) then
begin
if (SourceDS = sqlfornecedor) then
begin
if (DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0) then
begin
Id := GenID('FORNECEDOR');
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
end;
end
else
if (SourceDS = sqlcontato) then
if (DeltaDS.FieldByName('CHAVE_CONTATO').Value < 0) then
begin
if DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0 then
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
DeltaDS.FieldByName('CHAVE_CONTATO').NewValue := GenID('CONTATO');
end;
end;
end;
Tirado do Link
https://www.devmedia.com.br/forum/delphi/395811-Master-Detail-com-incremento-negativo.html
Os valores corretos da chave serão atulizados geralmente em uma consulta e é utilizado o UpdateRecord do TDataSetProvider
Um exemplo disso é este codigo
procedure TDm_Dados.dtsfornecedorBeforeUpdateRecord(Sender: TObject;
SourceDS: TDataSet; DeltaDS: TCustomClientDataSet; UpdateKind: TUpdateKind;
var Applied: Boolean);
{$J+}
const
Id: Integer = -1;
{$J-}
begin
if (UpdateKind = ukInsert) then
begin
if (SourceDS = sqlfornecedor) then
begin
if (DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0) then
begin
Id := GenID('FORNECEDOR');
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
end;
end
else
if (SourceDS = sqlcontato) then
if (DeltaDS.FieldByName('CHAVE_CONTATO').Value < 0) then
begin
if DeltaDS.FieldByName('CHAVE_FORNECEDOR').Value < 0 then
DeltaDS.FieldByName('CHAVE_FORNECEDOR').NewValue := Id;
DeltaDS.FieldByName('CHAVE_CONTATO').NewValue := GenID('CONTATO');
end;
end;
end;
Tirado do Link
https://www.devmedia.com.br/forum/delphi/395811-Master-Detail-com-incremento-negativo.html
Valeu...
GOSTEI 0
Samuel Silva
18/03/2011
Para esse caso em específico não.
Pois segundo a Embarcadero, deve-se usar o mínimo de recursos do banco de dados, por isso você deverá implementar uma forma de retornar o código, pode ser por uma procedure no banco que incremente o código e atualize um tabela de códigos por exemplo.
Atenciosamente,
André Luis da Silveira.
Pois segundo a Embarcadero, deve-se usar o mínimo de recursos do banco de dados, por isso você deverá implementar uma forma de retornar o código, pode ser por uma procedure no banco que incremente o código e atualize um tabela de códigos por exemplo.
Atenciosamente,
André Luis da Silveira.
Valeu....
GOSTEI 0