2015/04/17

dbExpress SetSchemaInfo 取得結構的勘誤之處

dbExpress 的 SetSchemaInfo 一直以來都很接近 ADO 的 OpenSchema,連取得的表格格式都很接近。

先來看看TADOConnection.OpenSchema和TSQLConnection.SetSchemaInfo各別取得的表格:

Get Primary Key Schema Information
ADODBX
TABLE_CATALOGRECNO
TABLE_SCHEMACATALOG_NAME
TABLE_NAMESCHEMA_NAME
COLUMN_NAMETABLE_NAME
COLUMN_GUIDINDEX_NAME
COLUMN_PROPIDPKEY_NAME
ORDINALCOLUMN_NAME
PK_NAMECOLUMN_POSITION

INDEX_TYPESORT_ORDERFILTER
表1:ADO參數為"siPrimaryKeys",DBX為stIndexes

看起來一切是如此美好。

但沒想到在dbExpress 4之後,SetSchemaInfo做了一些調整;dbExpress 4下使用SQLConnection.SetSchemaInfo取得的表格居然是:

dbExpress 4: SetSchemaInfo stIndexes
CatalogName
SchemaName
TableName
IndexName
ConstraintName
IsPrimary
IsUnique
IsAscending
表2:DBX 4實際取得的Schema表格

結果COLUMN_NAME被取消了,如此一來,要使用DBX就無法直接使用SetSchemaInfo來取得Primary Key欄位。

只是,每一版The Structure of Metadata Datasets卻從來沒有更新及說明替代方法,實在是很讓人傷腦筋。

可參閱:


2015/04/21 更新:


然而,事實上早就有了更好的解決方法:
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
// 方法一
function GetTableIndexColumns(aConnection: TSQLConnection; value: string) :
OleVariant;
begin
  ADataSet:= TSQLDataSet.Create(nil);
  try
    ADataSet.SqlConnection := aConnection;
    ADataSet.DbxCommandType := TDBXCommandTypes.DbxMetaData;
    ADataSet.CommandText := TDBXMetaDataCommandsEx.GetColumns + ' ' + aSchema + '.' + Value;
    ADataSet.Open;
    // Do something with the indexes
  Finally
    ADataset.Free;
  end;
end;
// 方法二
procedure TMainForm.Button2Click(Sender: TObject);
var
  Cmd: TDBXCommand;
  R: TDBXReader;
begin
  DBCon.Open;
  Cmd := DBCon.DBXConnection.CreateCommand;
  Cmd.CommandType := TDBXCommandTypes.DbxMetaData;
  Cmd.Text := TDBXMetaDataCommandsEx.GetColumns + ' ' + 'SysFields';
  R := Cmd.ExecuteQuery;
  while R.Next do
  begin
    if R.Value[TDBXColumnsColumns.IsAutoIncrement].AsBoolean then
      Memo1.Lines.Add(R.Value['ColumnName'].AsString);
  end;
  R.Free;
  Cmd.Free;
end;

在“dbExpress 4 New Feature Overview”裡的“dbExpress Metadata Improvements”一段中有提到:


 The dbExpress 3 metadata was not rich enough for database tooling and did not support all of the metadata types expected from an ADO.NET 2.0 driver. New metadata providers support provides much greater capability.

New metadata providers for 9 different database backends are written completely in Delphi. Full source code to all metadata providers is included in the product.


原來DBX3的SetScheamaInfo並非支援全部的資料庫。

深深覺得自己dbExpress還學得不夠透徹呀!

參考資料:

沒有留言:

張貼留言