Icon View Thread

The following is the text of the current message along with any replies.
Messages 1 to 4 of 4 total
Thread .Clear does not set to NULL
Sun, Dec 30 2007 2:48 PMPermanent Link

Roy Lambert

NLH Associates

Team Elevate Team Elevate

Tim

Remember nulls? I think you have a problem. I've tried ReturnTableToMemo (below) with the destination field set to both BLOB and CLOB, but in both cases there's a problem. In EDBManager as a CLOB it looks empty, as a BLOB it says 0 Bytes. However, when running StreamMemoToTable (also below) the .IsNull test fails, it tries to restore the table from the field and fails with a 1003 error - the stream signature is invalid.

This one is definitely a showstopper for me so unless there's a fix in 1.07 or a workround my migration is ever so slightly halted.

On the positive side, it does work when there is something in the field.

I could workround this particular one, I think, by using sql to null the field BUT I've got a lot of .Clear's in my code and I think its a significant problem.

You might also want to come up with a non-sql way to null BLOB's in EDBManager.

Roy Lambert

procedure ReturnTableToMemo(Fld: string; SrcTbl, DestTbl: TEDBTable);
var
ms: TMemoryStream;
WasEditing: boolean;
begin
ms := TMemoryStream.Create;
try
 WasEditing := (DestTbl.State in dsEditModes);
 if not WasEditing then GetRecordLock(DestTbl, 200);
 if SrcTbl.RecordCount > 0 then begin
  SrcTbl.SaveToStream(ms);
  TMemoField(DestTbl.FieldByName(Fld)).LoadFromStream(ms)
 end else DestTbl.FieldByName(Fld).Clear;
 if not WasEditing then DestTbl.Post;
finally
 ms.Free;
end;
end;

function StreamMemoToTable(Fld: string; SrcTbl: TEDBDataset; DestTbl: TEDBTable; OpenExclusive: boolean = False): boolean;
var
ms: TMemoryStream;
begin
try
 DestTbl.Close;
 DestTbl.Exclusive := True;
 ClearTable(DestTbl);
 DestTbl.Close;
 DestTbl.Exclusive := OpenExclusive;
 DestTbl.Open;
 if not SrcTbl.FieldByName(Fld).IsNull then begin
  ms := TMemoryStream.Create;
  try
   TMemoField(SrcTbl.FieldByName(Fld)).SaveToStream(ms);
   DestTbl.LoadFromStream(ms);
   DestTbl.Refresh;
   DestTbl.First;
  finally
   ms.Free;
  end;
 end;
 Result := True;
except
 Result := False;
end;
end;
Mon, Dec 31 2007 7:50 PMPermanent Link

Tim Young [Elevate Software]

Elevate Software, Inc.

Avatar

Email timyoung@elevatesoft.com

Roy,

<< Remember nulls? I think you have a problem. I've tried ReturnTableToMemo
(below) with the destination field set to both BLOB and CLOB, but in both
cases there's a problem. In EDBManager as a CLOB it looks empty, as a BLOB
it says 0 Bytes. However, when running StreamMemoToTable (also below) the
..IsNull test fails, it tries to restore the table from the field and fails
with a 1003 error - the stream signature is invalid. >>

This is an issue with the way the Delphi DB unit and the TBlobField
component attempts to Clear a BLOB or CLOB.  It basically opens a stream,
truncates it, and then frees the stream.   This, by itself, does not nullify
a BLOB column in EDB.  So, I'm going to have to come up with some sort of
workaround in the edbcomps unit for this, and it is going to have to rely on
a "magic" sequence of events, meaning that if you do the same events with a
straight TEDBBlobStream, you'll end up with a NULL column value.

--
Tim Young
Elevate Software
www.elevatesoft.com

Tue, Jan 1 2008 7:14 AMPermanent Link

Roy Lambert

NLH Associates

Team Elevate Team Elevate

Tim


>This is an issue with the way the Delphi DB unit and the TBlobField
>component attempts to Clear a BLOB or CLOB. It basically opens a stream,
>truncates it, and then frees the stream. This, by itself, does not nullify
>a BLOB column in EDB. So, I'm going to have to come up with some sort of
>workaround in the edbcomps unit for this, and it is going to have to rely on
>a "magic" sequence of events, meaning that if you do the same events with a
>straight TEDBBlobStream, you'll end up with a NULL column value.

I tried

DestTbl.FieldByName(Fld).Value := NULL;

But that didn't work either. I haven't tested .Clear with normal fields but will today if I have time after beating a piece of SQL into submission (its to late now but you should have had a competition to see who could come up with a magic DBISAM sql to ElevateDB sql convertor).

My current workround since I couldn't use SQL (indeterminate edit state for the record) is to test the size of the stream as well .IsNull on the field.

Roy Lambert
Tue, Jan 1 2008 12:35 PMPermanent Link

Tim Young [Elevate Software]

Elevate Software, Inc.

Avatar

Email timyoung@elevatesoft.com

Roy,

<< I tried

DestTbl.FieldByName(Fld).Value := NULL;

But that didn't work either. >>

No, that won't work.

<< I haven't tested .Clear with normal fields but will today if I have time
after beating a piece of SQL into submission (its to late now but you should
have had a competition to see who could come up with a magic DBISAM sql to
ElevateDB sql convertor). >>

Clear will work fine for normal fields.

<< My current workround since I couldn't use SQL (indeterminate edit state
for the record) is to test the size of the stream as well .IsNull on the
field. >>

That will work also and will be compatible with the DBISAM behavior.  DBISAM
treated a length of 0 as NULL, just like with string fields, which is why
DBISAM didn't run into this issue and EDB did.

--
Tim Young
Elevate Software
www.elevatesoft.com

Image