MDAC 2.5 SDK - OLE DB Programmer's Reference
OLE DB Interfaces
Returns the column metadata needed by most consumers.
HRESULT GetColumnInfo (
ULONG * pcColumns,
DBCOLUMNINFO ** prgInfo,
OLECHAR ** ppStringsBuffer);
Parameters
pcColumns
[out]
A pointer to memory in which to return the number of columns in the rowset; this number includes the bookmark column, if there is one. If IColumnsInfo::GetColumnInfo is called on a command that does not return rows, *pcColumns is set to zero. If this method terminates due to an error, *pcColumns is set to zero.
prgInfo
[out]
A pointer to memory in which to return an array of DBCOLUMNINFO structures. One structure is returned for each column in the rowset. The provider allocates memory for the structures and returns the address to this memory; the consumer releases this memory with IMalloc::Free when it no longer needs the column information. If *pcColumns is 0 on output or terminates due to an error, the provider does not allocate any memory and ensures that *prgInfo is a null pointer on output. For more information, see "DBCOLUMNINFO Structures" in the Comments section.
ppStringsBuffer
[out]
A pointer to memory in which to return a pointer to storage for all string values (names used either within columnid or for pwszName) within a single allocation block. If no returned columns have either form of string name or if this method terminates due to error, this parameter returns a null pointer. If there are any string names, this will be a buffer containing all the values of those names. The consumer should free the buffer with IMalloc::Free when finished working with the names. If *pcColumns is zero on output, the provider does not allocate any memory and ensures that *ppStringsBuffer is a null pointer on output. Each of the individual string values stored in this buffer is terminated by a null-termination character. Therefore, the buffer may contain one or more strings, each with its own null-termination character, and may contain embedded null-termination characters.
Return Code
S_OK
The method succeeded.
E_FAIL
A provider-specific error occurred.
E_INVALIDARG
pcColumns, prgInfo, or ppStringsBuffer was a null pointer.
E_OUTOFMEMORY
The provider was unable to allocate sufficient memory in which to return the column information structures.
E_UNEXPECTED
ITransaction::Commit or ITransaction::Abort was called, and the object is in a zombie state. This error can be returned only when the method is called on a rowset.
DB_E_ERRORSINCOMMAND
The command text contained one or more errors. Providers should use OLE DB error objects to return details about the errors.
DB_E_NOCOMMAND
No command text was set. This error can be returned only when this method is called from the command object.
DB_E_NOTABLE
ICommandPrepare was not implemented, and the specific table or view does not exist in the data store.
DB_E_NOTPREPARED
The command exposed ICommandPrepare, and the command text was set but the command was not prepared. This error can be returned only when this method is called from the command object.
DB_E_NOTREENTRANT
The provider called a method from IRowsetNotify in the consumer that had not yet returned, and the provider does not support reentrancy in this method.
DB_SEC_E_PERMISSIONDENIED
The consumer did not have sufficient permission to retrieve the column information.
Comments
This function makes no logical change to the state of the object.
IColumnsInfo::GetColumnInfo returns a fixed set of column metadata in an array of DBCOLUMNINFO structures, one per column. The returned metadata is that most commonly used by consumers, such as the data type and column ID.
The order of the structures is the order in which the columns appear in the rowset (column ordinal order). This is the same order as they appear in IColumnsRowset and is predictable from the ordering of requested columns in the command text. Rowset column ordinals start at 1 and are numbered sequentially in increasing order (for example, 1, 2, 3, and so on). When a row object is derived from a rowset, the row-specific column ordinals must come after the rowset column ordinals.
Bookmark columns may be returned on any rowset, regardless of its source (for example, ICommand::Execute, IOpenRowset::OpenRowset, IColumnsRowset::GetColumnsRowset, or IDBSchemaRowset::GetRowset) or whether bookmarks were requested. When bookmarks are returned, they will always appear as the first element of *prgInfo with iOrdinal equal to zero. When processing the columns returned by IColumnsInfo::GetColumnInfo, generic consumers should be prepared to receive and handle bookmark columns appropriately (that is, not display them to the user if not appropriate for the application).
IColumnsInfo::GetColumnInfo provides a quick alternative to IColumnsRowset::GetColumnsRowset. While GetColumnsRowset returns all available column metadata, it does so in a rowset. To get the metadata, the consumer must therefore create the column metadata rowset, create one or more accessors, fetch each row in the rowset, and get the data from the rowset.
Calling IColumnsInfo::GetColumnInfo on a command before the command is executed can be an expensive operation.
IColumnsInfo::GetColumnInfo returns column metadata in DBCOLUMNINFO structures.
typedef struct tagDBCOLUMNINFO {
LPOLESTR pwszName;
ITypeInfo * pTypeInfo;
ULONG iOrdinal;
DBCOLUMNFLAGS dwFlags;
ULONG ulColumnSize;
DBTYPE wType;
BYTE bPrecision;
BYTE bScale;
DBID columnid;
} DBCOLUMNINFO;
The elements of this structure are used as described in the following table.
Element | Description |
pwszName | Pointer to the name of the column; this might not be unique. If this cannot be determined, a null pointer is returned.
The name can be different from the string part of the column ID if the column has been renamed by the command text. This name always reflects the most recent renaming of the column in the current view or command text. |
pTypeInfo | Reserved for future use. Providers should return a null pointer in pTypeInfo. |
iOrdinal | The ordinal of the column. This is zero for the bookmark column of the row, if any. Other columns are numbered starting from one. |
dwFlags | A bitmask that describes column characteristics. The DBCOLUMNFLAGS enumerated type specifies the bits in the bitmask. For more information, see the following section. |
ulColumnSize | The maximum possible length of a value in the column. For columns that use a fixed-length data type, this is the size of the data type. For columns that use a variable-length data type, this is one of the following:
For data types that do not have a length, this is set to ~0 (bitwise, the value is not 0; all bits are set to 1). |
wType | The indicator of the column's data type. If the data type of the column varies from row to row, this must be DBTYPE_VARIANT. For a list of valid type indicators, see "Type Indicators" in Appendix A. |
bPrecision | If wType is a numeric data type, this is the maximum precision of the column. The precision of columns with a data type of DBTYPE_VARNUMERIC, DBTYPE_DECIMAL, or DBTYPE_NUMERIC depends on the definition of the column. For the precision of all other numeric data types, see "Precision of Numeric Data Types" in Appendix A.
For DBTYPE_DBTIMESTAMP data types, this is the length of the string representation (assuming the maximum allowed precision of the fractional seconds component). If the column's data type is not numeric or datetime, this is ~0 (bitwise, the value is not 0; all bits are set to 1). |
bScale | If wType is DBTYPE_DECIMAL or DBTYPE_NUMERIC, this is the number of digits to the right of the decimal point. Otherwise, this is ~0 (bitwise, the value is not 0; all bits are set to 1).
For DBTYPE_DBTIMESTAMP data types, this is the length of the string representation of the fractional seconds component. |
columnid | The column ID of the column. Each column's column ID must be unique.
The column ID of a base table should be invariant under views. For more information, see "Column IDs" in Chapter 4, "Rowsets." |
The dwFlags element of the DBCOLUMNINFO structure is a bitmask that describes column characteristics. The DBCOLUMNFLAGS enumerated type specifies the bits in the bitmask; the meanings of these values are as described in the following table.
Value | Description |
DBCOLUMNFLAGS_CACHEDEFERRED | Set if when a deferred column is first read its value the column is cached by the provider. Later reads of the column are done from this cache. The contents of the cache can be overwritten by IRowsetChange::SetData or IRowsetRefresh::RefreshVisibleData. The cached value is released when the row handle is released. Otherwise, not set.
This flag can be set through the DBPROP_CACHEDEFERRED property in the Rowset property group. |
DBCOLUMNFLAGS_ISBOOKMARK | Set if the column contains a bookmark. Otherwise, not set. |
DBCOLUMNFLAGS_ISCHAPTER | Set if the column contains a chapter value. Otherwise, not set. |
DBCOLUMNFLAGS_ISCOLLECTION | Set if the provider supports direct URL binding and the column determines whether the row models a collection or a simple resource. For document source providers, this flag is set for the RESOURCE_ISCOLLECTION column of the resource rowset. |
DBCOLUMNFLAGS_ISDEFAULTSTREAM | Set if the provider supports direct URL binding, IColumnsInfo is implemented on a row object, and the column has been designated by the provider to contain the default stream of the row object. |
DBCOLUMNFLAGS_ISFIXEDLENGTH | Set if all data in the column has the same length. Otherwise, not set.
The flag is always set for fixed-length data types except DBTYPE_BSTR. The flag is set for variable-length data types (DBTYPE_STR, DBTYPE_WSTR, DBTYPE_BSTR, and DBTYPE_BYTES) if all the values are the same length. The flag is set for DBTYPE_VECTOR or DBTYPE_ARRAY columns if all elements in each vector or array are of the same length and each vector or array has the same number of elements. Otherwise, the flag is not set. The flag is not affected by DBTYPE_BYREF. |
DBCOLUMNFLAGS_ISLONG | Set if the column contains a BLOB that contains very long data. The definition of very long data is provider-specific. The setting of this flag corresponds to the value of the IS_LONG column in the PROVIDER_TYPES schema rowset for the data type.
When this flag is set, the provider supports reading the value through a storage interface. Although such BLOBs can be retrieved in a single piece with IRowset::GetData, there may be provider-specific problems in doing so. For example, the BLOB might be truncated due to machine limits on memory or GetData might fail if called more than once for the BLOB. Furthermore, when this flag is set, the provider might not be able to accurately return the maximum length of the BLOB data in ulColumnSize in the DBCOLUMNINFO structure. When this flag is not set, the BLOB can be accessed directly through IRowset::GetData. It is provider-specific whether columns without this flag can be read through a storage interface. For more information, see "Accessing BLOB Data" in Chapter 7, "BLOBs and COM Objects." |
DBCOLUMNFLAGS_ISNULLABLE | Set if consumer can set the column NULL or if the provider cannot determine whether or not the consumer can set the column to NULL. Otherwise, not set. A column may contain null values, even if it cannot be set to NULL.
If DBCOLUMNFLAGS_ISNULLABLE is set, DBCOLUMNFLAGS_MAYBENULL must also be set. |
DBCOLUMNFLAGS_ISROWID | Set if the column contains a persistent row identifier that cannot be written to and has no meaningful value except to identify the row. |
DBCOLUMNFLAGS_ISROWURL | Set if the provider supports direct URL binding, IColumnsInfo is implemented on a row object, and the column contains the URL that names the row object in the data store. |
DBCOLUMNFLAGS_ISROWVER | Set if the column contains a timestamp or other versioning mechanism that cannot be written to directly and that is automatically updated to a new, increasing value when the row is updated and committed. The data type of a version column is provider-specific. How a version column is used—for example, how two version values are compared—is also provider-specific. |
DBCOLUMNFLAGS_MAYBENULL | Set if the column can contain null values or if the provider cannot guarantee that the column cannot contain null values. Otherwise, not set. DBCOLUMNFLAGS_MAYBENULL is generally used by consumers reading data to determine whether or not they might encounter a null value. When DBCOLUMNINFO is returned in the COLUMNS rowset, DBCOLUMNFLAGS_MAYBENULL should not be set if a simple SELECT over the single column of that table would return no null values.
DBCOLUMNFLAGS_MAYBENULL can be set even if DBCOLUMNFLAGS_ISNULLABLE is not set. For example, in a left outer join, if there is no row on the right side that matches a row on the left side, the columns from the right side in the joined row contain NULLs, even if the underlying columns are non-nullable—that is, if DBCOLUMNFLAGS_ISNULLABLE is not set. |
DBCOLUMNFLAGS_MAYDEFER | Set if the column is deferred. Otherwise, not set.
A deferred column is one for which the data is not fetched from the data store until the consumer attempts to get it. That is, the data is not fetched when the row is fetched but when IRowset::GetData is called. This flag can be set through the DBPROP_DEFERRED property in the Rowset property group. For more information, see "Deferred Columns" in Chapter 4, "Rowsets." |
DBCOLUMNFLAGS_SCALEISNEGATIVE | Set if the column type is DBTYPE_VARNUMERIC and bScale represents the absolute value of the negative scale of the column. This flag is used when setting data in a DBTYPE_VARNUMERIC column. For more information, refer to "Conversions Involving DBTYPE_NUMERIC or DBTYPE_DECIMAL" in Appendix A, "Data Types." |
DBCOLUMNFLAGS_WRITE | Set if IRowsetChange::SetData can be called for the column. Otherwise, not set.
This flag can be set through the DBPROP_MAYWRITECOLUMN property in the Rowset property group. Providers never set both DBCOLUMNFLAGS_WRITE and DBCOLUMNFLAGS_WRITEUNKNOWN; they are mutually exclusive. Absence of these flags means the column is read-only. |
DBCOLUMNFLAGS_WRITEUNKNOWN | Set if the column in the base table may be updatable through some means, either through IRowsetChange::SetData or through some other mechanism.
Providers never set both DBCOLUMNFLAGS_WRITE and DBCOLUMNFLAGS_WRITEUNKNOWN; they are mutually exclusive. Absence of these flags means the column is read-only. |
See Also
IColumnsInfo::MapColumnIDs, IColumnsRowset::GetColumnsRowset, IRowsetInfo::GetProperties