mirror of
https://github.com/HeidiSQL/HeidiSQL.git
synced 2025-08-06 18:24:26 +08:00
Refactor exclusion of virtual columns in various places:
* introduce TDBQuery.ColIsVirtal() returning a boolean for a column index, and use that instead of examining a columns virtuality everywhere * exclude virtual column when exporting SQL code in the grid export dialog - see #53 * sql export dialog must not activate edit mode on a result, as this introduces endless loops * instead, move some code out of PrepareEditing into PrepareColumnAttributes, which we can now call separately without activating edit mode
This commit is contained in:
@ -595,6 +595,7 @@ type
|
|||||||
function ColIsPrimaryKeyPart(Column: Integer): Boolean; virtual; abstract;
|
function ColIsPrimaryKeyPart(Column: Integer): Boolean; virtual; abstract;
|
||||||
function ColIsUniqueKeyPart(Column: Integer): Boolean; virtual; abstract;
|
function ColIsUniqueKeyPart(Column: Integer): Boolean; virtual; abstract;
|
||||||
function ColIsKeyPart(Column: Integer): Boolean; virtual; abstract;
|
function ColIsKeyPart(Column: Integer): Boolean; virtual; abstract;
|
||||||
|
function ColIsVirtual(Column: Integer): Boolean;
|
||||||
function ColAttributes(Column: Integer): TTableColumn;
|
function ColAttributes(Column: Integer): TTableColumn;
|
||||||
function IsNull(Column: Integer): Boolean; overload; virtual; abstract;
|
function IsNull(Column: Integer): Boolean; overload; virtual; abstract;
|
||||||
function IsNull(Column: String): Boolean; overload;
|
function IsNull(Column: String): Boolean; overload;
|
||||||
@ -615,6 +616,7 @@ type
|
|||||||
function TableName: String; virtual; abstract;
|
function TableName: String; virtual; abstract;
|
||||||
function QuotedDbAndTableName: String;
|
function QuotedDbAndTableName: String;
|
||||||
procedure DiscardModifications;
|
procedure DiscardModifications;
|
||||||
|
procedure PrepareColumnAttributes;
|
||||||
procedure PrepareEditing;
|
procedure PrepareEditing;
|
||||||
property RecNo: Int64 read FRecNo write SetRecNo;
|
property RecNo: Int64 read FRecNo write SetRecNo;
|
||||||
property Eof: Boolean read FEof;
|
property Eof: Boolean read FEof;
|
||||||
@ -6109,7 +6111,7 @@ begin
|
|||||||
Result := nil;
|
Result := nil;
|
||||||
if (Column < 0) or (Column >= FColumnOrgNames.Count) then
|
if (Column < 0) or (Column >= FColumnOrgNames.Count) then
|
||||||
raise EDatabaseError.CreateFmt(_('Column #%s not available.'), [IntToStr(Column)]);
|
raise EDatabaseError.CreateFmt(_('Column #%s not available.'), [IntToStr(Column)]);
|
||||||
if FEditingPrepared then begin
|
if FColumns <> nil then begin
|
||||||
for i:=0 to FColumns.Count-1 do begin
|
for i:=0 to FColumns.Count-1 do begin
|
||||||
if FColumns[i].Name = FColumnOrgNames[Column] then begin
|
if FColumns[i].Name = FColumnOrgNames[Column] then begin
|
||||||
Result := FColumns[i];
|
Result := FColumns[i];
|
||||||
@ -6181,6 +6183,18 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
function TDBQuery.ColIsVirtual(Column: Integer): Boolean;
|
||||||
|
var
|
||||||
|
Col: TTableColumn;
|
||||||
|
begin
|
||||||
|
Result := False;
|
||||||
|
Col := ColAttributes(Column);
|
||||||
|
if Col <> nil then begin
|
||||||
|
Result := not Col.Virtuality.IsEmpty;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
function TMySQLQuery.IsNull(Column: Integer): Boolean;
|
function TMySQLQuery.IsNull(Column: Integer): Boolean;
|
||||||
begin
|
begin
|
||||||
if FEditingPrepared and Assigned(FCurrentUpdateRow) then
|
if FEditingPrepared and Assigned(FCurrentUpdateRow) then
|
||||||
@ -6256,17 +6270,14 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
procedure TDBQuery.PrepareEditing;
|
procedure TDBQuery.PrepareColumnAttributes;
|
||||||
var
|
var
|
||||||
CreateCode, Dummy, DB: String;
|
CreateCode, Dummy, DB: String;
|
||||||
DBObjects: TDBObjectList;
|
DBObjects: TDBObjectList;
|
||||||
LObj, Obj: TDBObject;
|
LObj, Obj: TDBObject;
|
||||||
begin
|
begin
|
||||||
// Try to fetch column names and keys
|
// Try to fetch column names and keys
|
||||||
if FEditingPrepared then
|
|
||||||
Exit;
|
|
||||||
// This is probably a VIEW, so column names need to be fetched differently
|
// This is probably a VIEW, so column names need to be fetched differently
|
||||||
|
|
||||||
Obj := nil;
|
Obj := nil;
|
||||||
if FDBObject <> nil then
|
if FDBObject <> nil then
|
||||||
Obj := FDBObject
|
Obj := FDBObject
|
||||||
@ -6294,6 +6305,15 @@ begin
|
|||||||
lntView:
|
lntView:
|
||||||
Connection.ParseViewStructure(CreateCode, Obj, FColumns, Dummy, Dummy, Dummy, Dummy, Dummy);
|
Connection.ParseViewStructure(CreateCode, Obj, FColumns, Dummy, Dummy, Dummy, Dummy, Dummy);
|
||||||
end;
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
procedure TDBQuery.PrepareEditing;
|
||||||
|
begin
|
||||||
|
// Try to fetch column names and keys and init update data
|
||||||
|
if FEditingPrepared then
|
||||||
|
Exit;
|
||||||
|
PrepareColumnAttributes;
|
||||||
FreeAndNil(FUpdateData);
|
FreeAndNil(FUpdateData);
|
||||||
FUpdateData := TUpdateData.Create(True);
|
FUpdateData := TUpdateData.Create(True);
|
||||||
FEditingPrepared := True;
|
FEditingPrepared := True;
|
||||||
|
@ -759,7 +759,7 @@ begin
|
|||||||
tmp := tmp + ' (';
|
tmp := tmp + ' (';
|
||||||
Col := Grid.Header.Columns.GetFirstVisibleColumn;
|
Col := Grid.Header.Columns.GetFirstVisibleColumn;
|
||||||
while Col > NoColumn do begin
|
while Col > NoColumn do begin
|
||||||
if Col <> ExcludeCol then
|
if (Col <> ExcludeCol) and (not GridData.ColIsVirtual(Col)) then
|
||||||
tmp := tmp + GridData.Connection.QuoteIdent(Grid.Header.Columns[Col].Text)+', ';
|
tmp := tmp + GridData.Connection.QuoteIdent(Grid.Header.Columns[Col].Text)+', ';
|
||||||
Col := Grid.Header.Columns.GetNextVisibleColumn(Col);
|
Col := Grid.Header.Columns.GetNextVisibleColumn(Col);
|
||||||
end;
|
end;
|
||||||
@ -829,7 +829,9 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
efSQLInsert, efSQLReplace, efSQLDeleteInsert: begin
|
efSQLInsert, efSQLReplace, efSQLDeleteInsert: begin
|
||||||
if GridData.IsNull(Col) then
|
if GridData.ColIsVirtual(Col) then
|
||||||
|
Data := ''
|
||||||
|
else if GridData.IsNull(Col) then
|
||||||
Data := 'NULL'
|
Data := 'NULL'
|
||||||
else if (GridData.DataType(Col).Index = dtBit) and GridData.Connection.Parameters.IsMySQL then
|
else if (GridData.DataType(Col).Index = dtBit) and GridData.Connection.Parameters.IsMySQL then
|
||||||
Data := 'b' + esc(Data)
|
Data := 'b' + esc(Data)
|
||||||
@ -839,6 +841,7 @@ begin
|
|||||||
Data := esc(Data)
|
Data := esc(Data)
|
||||||
else if Data = '' then
|
else if Data = '' then
|
||||||
Data := esc(Data);
|
Data := esc(Data);
|
||||||
|
if not Data.IsEmpty then
|
||||||
tmp := tmp + Data + ', ';
|
tmp := tmp + Data + ', ';
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
@ -4533,7 +4533,6 @@ var
|
|||||||
i: Integer;
|
i: Integer;
|
||||||
Value: String;
|
Value: String;
|
||||||
IsNull, AllowNewNode: Boolean;
|
IsNull, AllowNewNode: Boolean;
|
||||||
TableCol: TTableColumn;
|
|
||||||
begin
|
begin
|
||||||
Grid := ActiveGrid;
|
Grid := ActiveGrid;
|
||||||
Results := GridResult(Grid);
|
Results := GridResult(Grid);
|
||||||
@ -4559,8 +4558,7 @@ begin
|
|||||||
continue; // Ignore invisible key column
|
continue; // Ignore invisible key column
|
||||||
if Results.ColIsPrimaryKeyPart(i) then
|
if Results.ColIsPrimaryKeyPart(i) then
|
||||||
continue; // Empty value for primary key column
|
continue; // Empty value for primary key column
|
||||||
TableCol := Results.ColAttributes(i);
|
if Results.ColIsVirtual(i) then
|
||||||
if (TableCol <> nil) and (not TableCol.Virtuality.IsEmpty) then
|
|
||||||
continue; // Don't copy virtual column value
|
continue; // Don't copy virtual column value
|
||||||
Results.RecNo := DupeNum^;
|
Results.RecNo := DupeNum^;
|
||||||
Value := Results.Col(i);
|
Value := Results.Col(i);
|
||||||
|
@ -1602,9 +1602,6 @@ begin
|
|||||||
TargetDbAndObject := Quoter.QuoteIdent(DBObj.Name);
|
TargetDbAndObject := Quoter.QuoteIdent(DBObj.Name);
|
||||||
if ToDb then
|
if ToDb then
|
||||||
TargetDbAndObject := Quoter.QuoteIdent(FinalDbName) + '.' + TargetDbAndObject;
|
TargetDbAndObject := Quoter.QuoteIdent(FinalDbName) + '.' + TargetDbAndObject;
|
||||||
// Parse columns, so we can check for special things like virtual columns
|
|
||||||
ColumnList := TTableColumnList.Create(True);
|
|
||||||
DBObj.Connection.ParseTableStructure(DBObj.CreateCode, ColumnList, nil, nil);
|
|
||||||
Offset := 0;
|
Offset := 0;
|
||||||
RowCount := 0;
|
RowCount := 0;
|
||||||
// Calculate limit so we select ~100MB per loop
|
// Calculate limit so we select ~100MB per loop
|
||||||
@ -1623,6 +1620,7 @@ begin
|
|||||||
Inc(Offset, Limit);
|
Inc(Offset, Limit);
|
||||||
if Data.RecordCount = 0 then
|
if Data.RecordCount = 0 then
|
||||||
break;
|
break;
|
||||||
|
Data.PrepareColumnAttributes;
|
||||||
BaseInsert := 'INSERT INTO ';
|
BaseInsert := 'INSERT INTO ';
|
||||||
if comboExportData.Text = DATA_INSERTNEW then
|
if comboExportData.Text = DATA_INSERTNEW then
|
||||||
BaseInsert := 'INSERT IGNORE INTO '
|
BaseInsert := 'INSERT IGNORE INTO '
|
||||||
@ -1630,7 +1628,7 @@ begin
|
|||||||
BaseInsert := 'REPLACE INTO ';
|
BaseInsert := 'REPLACE INTO ';
|
||||||
BaseInsert := BaseInsert + TargetDbAndObject + ' (';
|
BaseInsert := BaseInsert + TargetDbAndObject + ' (';
|
||||||
for i:=0 to Data.ColumnCount-1 do begin
|
for i:=0 to Data.ColumnCount-1 do begin
|
||||||
if ColumnList[i].Virtuality.IsEmpty then
|
if not Data.ColIsVirtual(i) then
|
||||||
BaseInsert := BaseInsert + Quoter.QuoteIdent(Data.ColumnNames[i]) + ', ';
|
BaseInsert := BaseInsert + Quoter.QuoteIdent(Data.ColumnNames[i]) + ', ';
|
||||||
end;
|
end;
|
||||||
Delete(BaseInsert, Length(BaseInsert)-1, 2);
|
Delete(BaseInsert, Length(BaseInsert)-1, 2);
|
||||||
@ -1644,7 +1642,7 @@ begin
|
|||||||
if not IsFirstRowInChunk then
|
if not IsFirstRowInChunk then
|
||||||
Row := Row + ','+CRLF+#9+'(';
|
Row := Row + ','+CRLF+#9+'(';
|
||||||
for i:=0 to Data.ColumnCount-1 do begin
|
for i:=0 to Data.ColumnCount-1 do begin
|
||||||
if not ColumnList[i].Virtuality.IsEmpty then
|
if Data.ColIsVirtual(i) then
|
||||||
Continue;
|
Continue;
|
||||||
if Data.IsNull(i) then
|
if Data.IsNull(i) then
|
||||||
Row := Row + 'NULL'
|
Row := Row + 'NULL'
|
||||||
|
Reference in New Issue
Block a user