2013-02-05 2 views
1

Delphi XE3을 사용하여 SQLite의 blob 필드에 삽입하려고합니다.Delphi XE3을 사용하여 SQLite에서 Blob에 삽입 할 수 있습니까

저는 TDBXCommand와 TSQLConnection을 이와 같이 사용하고 있습니다. 그러나 BLOB 필드를 삽입하지 않았 심지어 나는를 TSQLConnection를 사용하여 쿼리

procedure TDBXCommandHelper.Init(const AQry: String); 
begin 
    Parameters.ClearParameters; 
    Close; 
    Prepare; 
    Text := AQry; 
end; 

procedure dmDB.InsertPicture; 
const 
    QRY = 'INSERT INTO Memo(Picture) VALUES(?)'; 
var 
    LTransaction: TDBXTransaction; 
    LBlob: TDBXParameter; 
    LStream: TFileStream; 
begin 
    LTransaction := FDBCon.BeginTransaction; 
    LStream := TFileStream.Create('d:\sample.bmp', fmOpenRead); 
    LBlob := TDBXParameter.Create; 
    try 
    try 
     FDBXCmd := FDBCon.DBXConnection.CreateCommand; 
     FDBXCmd.CommandType := TDBXCommandTypes.DbxSQL; 
     FDBXCmd.Init(QRY); 

     LBlob.DataType := TDBXDataTypes.BlobType; 
     LBlob.SubType := TDBXSubDataTypes.BinarySubType; 
     LBlob.Value.SetStream(LStream, False); 
     FDBXCmd.Parameters.AddParameter(LBlob); 
     FDBXCmd.ExecuteUpdate; 
    except 
     on E: Exception do 
     FDBCon.RollbackFreeAndNil(LTransaction); 
    end; 
    FDBCon.CommitFreeAndNil(LTransaction); 
    finally 
    FreeAndNil(LStream); 
    FreeAndNil(LBlob); 
    end; 
end; 

에서 어떤 결과를 얻을 cannnot 그러나 나는 다음과 같은 시도 할 수 있습니다

procedure TInsertThread.NoteInsertExcute; 
const 
    QRY = 'INSERT INTO Memo(Picture) VALUES(:Picture)'; 
var 
    LTransaction: TDBXTransaction; 
    LParams: TParams; 
    LStream: TMemoryStream; 
begin 
    LTransaction := FDBCon.BeginTransaction; 
    LParams := TParams.Create(nil); 
    LStream := TMemoryStream.Create; 
    LStream.LoadFromFile(FValues.Values[NAME_PICTURE]); 
    try 
    LParams.CreateParam(ftBlob, 'Picture', ptInput); 
    LParams.ParamByName('Picture').LoadFromStream(LStream, ftBlob); 
    FDBCon.Execute(QRY, LParams); 
    FDBCon.CommitFreeAndNil(LTransaction); 
    finally 
    FreeAndNil(LStream); 
    FreeAndNil(LParams); 
    end; 
end; 
+0

LStream (메모리 스트림)의 내용을 base64 문자열로 인코딩하고이를 db 필드로 밀어 넣을 수 있습니다. – ComputerSaysNo

+0

"INSERT INTO Memo (Picture)"란 무엇을 의미합니까? SQLite3에는 열 정의가 없습니다. 즉, 일부 "선호도"만 있습니다. 모든 열에 모든 종류의 데이터를 삽입 할 수 있습니다. "메모()"를 제거하십시오. SQLite3은 문제없이 BLOB를 처리합니다. –

+0

anwser에 감사드립니다. 메모 테이블 이름과 테이블은 다음과 같이 정의입니다 .. 'TABLE [메모] ( [ID] INTEGER PRIMARY KEY AUTOINCREMENT NULL NOT, [사용자 ID] INTEGER NOT NULL, [날짜] 텍스트 NULL, [유형을 생성 ] TEXT NOT NULL, [값] TEXT NULL이 아님, [그림] BLOB NULL ) ' – gomsun2

답변

1

어떤 결과를 얻을 수 없습니다

function GetFileAsBytesValue(AFileName: TFileName): TArray<Byte>; 
var 
    Len: Integer; 
    LStream: TMemoryStream; 
begin 
    LStream := TMemoryStream.Create; 
    try 
    LStream.LoadFromFile(AFileName); 
    Len := LStream.Size; 

    SetLength(Result, Len); 
    Move(LStream.Memory^, Result[0], Len); 
    finally 
    LStream.Free; 
    end; 
end; 

procedure dmDB.InsertPicture; 
const 
    QRY = 'INSERT INTO Memo(Picture) VALUES(?)'; 
var 
    LTransaction: TDBXTransaction; 
    LDBXCmd: TSQLQuery; 
    LParam: TParam; 
begin 
    LTransaction := FDBCon.BeginTransaction; 
    LDBXCmd := TSQLQuery.Create(FDBCon); 
    try 
    try 
     LDBXCmd.SQLConnection := FDBCon; 
     LDBXCmd.SQL.Text := QRY; 
     LParam := LDBXCmd.Params.CreateParam(ftBlob, 'Picture', ptInput); 
     LParam.AsBlob := GetFileAsBytesValue('d:\sample.bmp'); 
     LDBXCmd.ExecSQL; 
    except 
     on E: Exception do 
     FDBCon.RollbackFreeAndNil(LTransaction); 
    end; 
    FDBCon.CommitFreeAndNil(LTransaction); 
    finally 
    LDBXCmd.Free; 
    end; 
end; 
+0

감사합니다. 나는 그것을 점검 할것이다 – gomsun2

2

간단합니다.

var 
    ms: TMemoryStream; 
    sq: TSQLQuery; 
begin 
    ms := TMemoryStream.Create; 
    ms.LoadFromFile('C:\Pictures\l.jpg'); 
    if ms <> nil then 
    begin 
    sq := TSQLQuery.Create(nil); 
    sq.SQLConnection := con1; 
    sq.SQL.Text := 'update db1 set picture= :photo ;'; 
    sq.Params.ParseSQL(sq.SQL.Text, true); 
    sq.Params.ParamByName('photo').LoadFromStream(ms, ftBlob); 
    sq.ExecSQL(); 
    end; 

.
여기서 con1은 TSQLConnection입니다.