Choosing the right interfaces
Universal Data Access for Microsoft® Windows® and Windows NT® Operating Systems
White Paper
This White Paper proposes a definition for a base level of functionality which any provider must implement in order to work with the majority of consumers. Additional levels are also defined that provide functionality over and above the base level. The provider writer may either implement this additional functionality natively or can take advantage of proposed service components which would provide generic implementations of extensions, such as scrolling or notifications.
© 1997 Microsoft Corporation. All rights reserved.
The information contained in this document represents the current view of Microsoft Corporation on the issues discussed as of the date of publication. Because Microsoft must respond to changing market conditions, it should not be interpreted to be a commitment on the part of Microsoft, and Microsoft cannot guarantee the accuracy of any information presented after the date of publication.
This White Paper is for informational purposes only. MICROSOFT MAKES NO WARRANTIES, EXPRESS OR IMPLIED, IN THIS DOCUMENT.
Microsoft, Visual Basic, Windows, and Windows NT are registered trademarks of Microsoft Corporation.
Other product or company names mentioned herein may be the trademarks of their respective owners.
Microsoft Corporation · One Microsoft Way · Redmond, WA 98052-6399 · USA
0997
To meet its goal of providing data access to all types of data in a COM (Component Object Model) environment, Microsoft® OLE DB is designed as a component technology. In OLE DB, data sources expose the interfaces that reflect their functionality, and common components can be built on top of those interfaces to expose more robust data models. To define a component architecture, OLE DB identifies common characteristics between different data providers and services, and defines common interfaces to expose those characteristics. So, for example, while a rowset may be obtained through a number of very different mechanisms, the end result is still a rowset, with well-defined interfaces, methods and characteristics. With OLE DB, navigating the result of a complex multi-table join is no different than navigating the results of an opened text file containing tabular data. Defining common interfaces in this manner allows components to more efficiently augment the individual data provider's native functionality.
An OLE DB provider exposes OLE DB interfaces over some type of data. OLE DB providers include everything from a full SQL DBMS to a text file or data stream. Obviously these data providers have different functionality, and it's important not to limit that functionality. But at the same time it's not reasonable to expect all providers that expose simple tabular data to implement a full-blown query engine as well.
Once the base functionality is defined, the next step is to view the additional functionality as incremental additions to this base functionality. Thus, the more sophisticated providers can expose these advanced features in addition to the base level interfaces. Furthermore, individual service components can be built to implement these features on top of the simpler providers.
Developers writing OLE DB consumers can choose their level of interoperability with OLE DB providers. Consumers may be written to consume a specific provider, in which case they are designed to be aware of the functionality of the provider. Or, they may be written to consume generic providers. In order to consume generic providers, the consumer may do one of the following:
The following table describes the minimum level of functionality that a consumer can expect to be supported when talking to any OLE DB provider. The table is broken into three columns:
Object | Base interfaces | Updatable |
DataSource | IConnectionPointContainer for: - IDBAsynchNotify |
|
IDatasource1 | ||
IDBAsynchStatus2 | ||
IDBCreateSession | ||
IDBInitialize | ||
IDBProperties | ||
IPersist | ||
ISupportErrorInfo | ||
DataSource Behavior | DBPROP_INIT_PROMPT3 | |
Session | IGetDataSource | |
IOpenRowset | ||
ISessionProperties | ||
ISupportErrorInfo |
Object | Base interfaces | Updatable |
Rowset | IAccessor | IRowsetChange |
IColumnsInfo | ||
IConnectionPointContainer for: - IDBAsynchNotify - IRowsetNotify |
||
IConvertType | ||
IDBAsynchStatus2 | ||
IRowset | ||
IRowsetFind | ||
IRowsetIdentity | ||
IRowsetInfo | ||
IRowsetLocate | ||
IRowPosition1 | ||
IRowsetScroll | ||
ISupportErrorInfo | ||
Rowset Behavior | DBPROP_ CANHOLDROWS | DBPROP_ REMOVEDELETED |
DBPROP_ CANFETCHBACKWARDS | DBPROP_ OWNUPDATEDELETE | |
DBPROP_ CANSCROLLBACKWARDS | DBPROP_ OWNINSERT |
1These interfaces are always supported by common components in the SDK. They are never implemented directly by providers.
2Support for IDBAsynchStatus does not require that the provider support any operations asynchronously. In the non-asynch case, the provider would simply block when creating or initializing the object, and return a completion status whenever GetStatus was called.
3DBPROP_INIT_PROMPT is required if any initialization properties are required in order to connect to the provider. If calling Initialize() succeeds on a freshly created Datasource, the provider does not need to support this property.
Providers support the native functionality of the data which they expose. However, in order to be consumed by generic consumers, providers must be able to support at least the minimum base consumer functionality defined in the previous table. You can develop a provider to support the minimum level of functionality in one of three ways:
In addition, providers may expose interfaces for the extended functionality described in the next section.
All providers must be either apartment or free threaded, and must support aggregation of the DataSource, Session, and Rowset. If applicable, providers must support the aggregation of the Command and View objects.
It's important for provider writers to implement the full set of interfaces that apply to their particular type of data. At a minimum, the provider must implement the interfaces and behavior listed in Table 2 to be considered a generic OLE DB provider. Providers implementing the minimum provider functionality can rely on common service components available in the SDK to implement the base consumer functionality, as shown in Figure 1.
Object | Any base provider | Updatable providers |
DataSource | IDBCreateSession | |
IDBInitialize | ||
IDBProperties | ||
IPersist | ||
DataSource Behavior | DBPROP_INIT_PROMPT1 | |
Session | IGetDataSource | |
IOpenRowset | ||
ISessionProperties | ||
Rowset | IAccessor | IRowsetChange |
IConvertType | ||
IColumnsInfo | ||
IRowset | ||
IRowsetIdentity | ||
IRowsetInfo | ||
Rowset Behavior | DBPROP_CANHOLDROWS | DBPROP_ OWNUPDATEDELETE |
DBPROP_OWNINSERT | ||
DBPROP_ REMOVEDELETED |
1DBPROP_INIT_PROMPT is required if any initialization properties are required in order to connect to the provider. If calling Initialize() succeeds on a freshly created Datasource, the provider does not need to support this property.
Supporting an interface means supporting all methods within that interface. No methods return E_NOTIMPL.
Supporting a property means supporting the setting of and associated behavior of all possible values for a property.
Supporting the required rowset properties means that setting any combination of the required properties must yield a rowset that reflects at least those properties. It does not mean that those properties are always true for any rowset if the property has not been requested by the user.
Providers that implement the full set of base interfaces can be consumed by general consumers without the support of additional service components, as shown in Figure 2.
Providers implementing the following functionality in addition to the minimum provider functionality are consumed as base providers:
Object | Any base provider | Updatable providers |
DataSource | IConnectionPointContainer for: - IDBAsynchNotify |
|
IDBAsynchStatus | ||
ISupportErrorInfo | ||
Session | ISupportErrorInfo | |
Rowset | IDBAsynchStatus | |
IConnectionPointContainer for: - IRowsetNotify - IDBAsynchNotify |
||
IRowsetFind | ||
IRowsetLocate | ||
IRowsetScroll | ||
ISupportErrorInfo | ||
Rowset Behavior | DBPROP_ CANSCROLLBACKWARDS1 | |
DBPROP_ CANFETCHBACKWARDS1 |
1Providers that support the property DBPROP_CANSCROLLBACKWARDS must also support the property DBPROP_CANFETCHBACKWARDS.
General purpose providers may support additional functionality. It is advantageous that providers support as many extended interfaces as apply to their particular type of data.
In addition to common interface extensions, providers may expose specialized interfaces for the following sets of extended functionality:
Object | Any provider | Updatable providers | Transacted providers |
DataSource | IDataSourceAdmin | ||
IDBInfo2 | |||
IPersistFile | |||
Session | IDBSchemaRowset | ITransactionJoin | |
IDBView1 | ITransactionObject | ||
IDBCreateCommand2 | |||
IIndexDefinition | |||
ITableDefinition | |||
View1 | IViewFilter | ||
IViewSort | |||
IColumnsInfo | |||
IAccessor | |||
ISupportErrorInfo | |||
IViewRowset | |||
IViewChapter | |||
Command2 | IAccessor | ||
ICommand | |||
ICommandText | |||
IColumnsInfo | |||
ICommandPrepare | |||
IColumnsRowset | |||
ICommandProperties | |||
ICommandWithParameters | |||
IConvertType | |||
ISupportErrorInfo | |||
Command Behavior | MAXTABLESINSELECT>1 | ||
Custom Error | ISQLErrorInfo | ||
Multiple Results | IMultipleResults | ||
Rowset | IColumnsRowset | IRowsetResynch | |
IRowsetIdentity | IRowsetUpdate | ||
IRowsetLocate | |||
IChapteredRowset1 |
Object | Any provider | Updatable providers | Transacted providers |
Rowset (cont.) | IRowsetView1 | ||
IRowsetIndex3 | |||
Rowset Behavior | DBPROP_ LITERALBOOKMARKS | DBPROP_CHANGE INSERTEDROWS | DBPROP_ COMMITPRESERVE |
DBPROP_ ORDEREDBOOKMARKS | DBPROP_RETURN PENDINGROWS | DBPROP_ ABORTPRESERVE | |
DBPROP_ LITERALIDENTITY | DBPROP_ IMMOBILEROWS | ||
DBPROP_ BOOKMARKSKIPPED | |||
DBPROP_OTHERINSERT | |||
DBPROP_ OTHERUPDATEDELETE | |||
DBPROP_ STRONGIDENTITY | |||
BLOB Support | DBPROP_OLEOBJECTS | ||
DBPROP_MULTIPLE STORAGEOBJECTS | |||
DBPROP_STRUCTURED STORAGE | |||
ISequentialStream | |||
IStream | |||
IStorage | |||
ILockBytes | |||
DBPROP_BLOCKING STORAGEOBJECTS=FALSE |
1Extended functionality that may be exposed by providers which support Rowset Processing.
2Extended functionality that may be exposed by providers which support Commands.
3Extended functionality that may be exposed by providers which support Index navigation.
Generic consumers must be prepared for providers that don't support the extended interfaces. Consumers may handle such providers in several different ways:
The consumer can return an error indicating that the provider is not capable of supporting required functionality.
For the latest information on OLE DB, check out our World Wide Web site at http://www.microsoft.com/oledb.