TN042 : Recommandations du développeur concernant le pilote ODBC
Remarque
La note technique suivante n'a pas été mise à jour depuis son inclusion initiale dans la documentation en ligne. Par conséquent, certaines procédures et rubriques peuvent être obsolètes ou incorrectes. Pour obtenir les informations les plus récentes, il est recommandé de rechercher l'objet qui vous intéresse dans l'index de la documentation en ligne.
Cette note décrit les instructions pour les enregistreurs de pilotes ODBC. Il décrit les exigences générales et les hypothèses des fonctionnalités ODBC que les classes de base de données MFC effectuent, ainsi que divers détails sémantiques attendus. Les fonctionnalités de pilote requises pour prendre en charge les trois CRecordset
modes Open (forwardOnly, instantané et dynaset) sont décrites.
Bibliothèque de curseurs ODBC
Les classes de base de données MFC présentent des fonctionnalités à l’utilisateur qui, dans de nombreux cas, dépassent les fonctionnalités fournies par la plupart des pilotes ODBC de niveau 1. Heureusement, la bibliothèque de curseurs ODBC se couche entre les classes de base de données et le pilote, et fournit automatiquement une grande partie de cette fonctionnalité supplémentaire.
Par exemple, la plupart des pilotes 1.0 ne prennent pas en charge le défilement vers l’arrière. La bibliothèque de curseurs peut détecter cela et met en cache les lignes du pilote et les présente comme demandés lors des appels FETCH_PREV dans SQLExtendedFetch
.
Un autre exemple important de dépendance de la bibliothèque de curseurs est positionné sur les mises à jour. La plupart des pilotes 1.0 n’ont pas non plus de mises à jour positionnées, mais la bibliothèque de curseurs génère des instructions de mise à jour qui identifient une ligne cible sur la source de données en fonction de ses valeurs de données mises en cache actuelles ou d’une valeur d’horodatage mise en cache.
La bibliothèque de classes n’utilise jamais plusieurs ensembles de lignes. Par conséquent, les quelques SQLSetPos
instructions sont toujours appliquées à la ligne 1 de l’ensemble de lignes.
CDatabases
Chacun CDatabase
alloue un seul HDBC. (Si CDatabase
la ExecuteSQL
fonction est utilisée, un HSTMT est temporairement alloué.) Par conséquent, si plusieurs CDatabase
sont requis, plusieurs disques HDBCpar HENV doivent être pris en charge.
Les classes de base de données nécessitent la bibliothèque de curseurs. Cela est reflété dans un SQLSetConnections
appel SQL_ODBC_CURSORS, SQL_CUR_USE_ODBC.
SQLDriverConnect
, SQL_DRIVER_COMPLETE est utilisé pour CDatabase::Open
établir la connexion à la source de données.
Le pilote doit prendre en charge SQLGetInfo SQL_ODBC_API_CONFORMANCE
>= SQL_OAC_LEVEL1, SQLGetInfo SQL_ODBC_SQL_CONFORMANCE
>= SQL_OSC_MINIMUM.
Pour que les transactions soient prises en charge pour les CDatabase
jeux d’enregistrements dépendants SQLGetInfo SQL_CURSOR_COMMIT_BEHAVIOR
et les SQL_CURSOR_ROLLBACK_BEHAVIOR doivent avoir SQL_CR_PRESERVE. Sinon, les tentatives d’exécution du contrôle de transaction sont ignorées.
SQLGetInfo SQL_DATA_SOURCE_READ_ONLY
doit être pris en charge. Si elle retourne « Y », aucune opération de mise à jour n’est effectuée sur la source de données.
Si l’objet CDatabase
ReadOnly est ouvert, une tentative de définition de la source de données en lecture seule est effectuée avec SQLSetConnectOption SQL_ACCESS_MODE
, SQL_MODE_READ_ONLY.
Si les identificateurs nécessitent un guillemet, ces informations doivent être retournées par le pilote avec un SQLGetInfo SQL_IDENTIFIER_QUOTE_CHAR
appel.
À des fins de débogage, SQLGetInfo SQL_DBMS_VER
et SQL_DBMS_NAME sont récupérées à partir du pilote.
SQLSetStmtOption SQL_QUERY_TIMEOUT
et SQL_ASYNC_ENABLE peuvent être appelées sur un CDatabase
HDBC.
SQLError
peut être appelé avec n’importe quel ou tous les arguments NULL.
Bien sûr, SQLAllocEnv
, SQLAllocConnect
SQLDisconnect
et SQLFreeConnect
doit être pris en charge.
ExecuteSQL
Outre l’allocation et la libération d’un HSTMT temporaire, ExecuteSQL
des appelsSQLExecDirect
, SQLFetch
SQLNumResultCol
et SQLMoreResults
. SQLCancel
peut être appelé sur le HSTMT.
GetDatabaseName
SQLGetInfo SQL_DATABASE_NAME
sera appelé.
BeginTrans, CommitTrans, Rollback
SQLSetConnectOption SQL_AUTOCOMMIT
et SQLTransact SQL_COMMIT
, SQL_ROLLBACK et SQL_AUTOCOMMIT seront appelés si des demandes de transaction sont effectuées.
CRecordsets
SQLAllocStmt
, ( SQLPrepare
SQLExecute
Pour Open
et Requery
) SQLExecDirect
(pour les opérations de mise à jour) SQLFreeStmt
doit être pris en charge. SQLNumResultCols
et SQLDescribeCol
sera appelé sur le jeu de résultats à différents moments.
SQLSetParam
est largement utilisé pour lier des données de paramètre et DATA_AT_EXEC fonctionnalités.
SQLBindCol
est largement utilisé pour inscrire des emplacements de stockage de données de colonne de sortie auprès d’ODBC.
Deux SQLGetData
appels sont utilisés pour récupérer des données SQL_LONG_VARCHAR et SQL_LONG_VARBINARY . Le premier appel tente de trouver la longueur totale de la valeur de colonne en appelant SQLGetData
avec cbMaxValue de 0, mais avec une valeur valide de cpValue. Si ccpValue contient SQL_NO_TOTAL, une exception est levée. Sinon, un HGLOBAL est alloué et un autre SQLGetData
appel effectué pour récupérer l’intégralité du résultat.
Mise à jour
Si le verrouillage pessimiste est demandé, SQLGetInfo SQL_LOCK_TYPES
sera interrogé. Si SQL_LCK_EXCLUSIVE n’est pas pris en charge, une exception est levée.
Les tentatives de mise à jour d’un (instantané ou d’une CRecordset
feuille de réponse dynamique) entraînent l’allocation d’un deuxième HSTMT. Pour les pilotes qui ne prennent pas en charge le deuxième HSTMT, la bibliothèque de curseurs simule cette fonctionnalité. Malheureusement, cela peut parfois signifier forcer la requête actuelle sur le premier HSTMT à se terminer avant de traiter la demande du deuxième HSTMT.
SQLFreeStmt SQL_CLOSE
et SQL_RESET_PARAMS et SQLGetCursorName
seront appelés pendant les opérations de mise à jour.
S’il existe des CLongBinarys dans outputColumns, la fonctionnalité de DATA_AT_EXEC ODBC doit être prise en charge. Cela inclut le retour de SQL_NEED_DATA à partir de SQLExecDirect
, SQLParamData
et SQLPutData
.
SQLRowCount
est appelé après l’exécution pour vérifier que seul 1 enregistrement a été mis à jour par le SQLExecDirect
.
Curseurs ForwardOnly
Seules SQLFetch
les Move
opérations sont requises. Notez que les curseurs forwardOnly ne prennent pas en charge les mises à jour.
Curseurs d’instantanés
La fonctionnalité d’instantané nécessite SQLExtendedFetch
une prise en charge. Comme indiqué ci-dessus, la bibliothèque de curseurs ODBC détecte lorsqu’un pilote ne prend pas en charge SQLExtendedFetch
et fournit la prise en charge nécessaire elle-même.
SQLGetInfo
, SQL_SCROLL_OPTIONS doit prendre en charge SQL_SO_STATIC.
Curseurs dynaset
Voici la prise en charge minimale requise pour ouvrir une feuille de réponse dynamique :
SQLGetInfo
, SQL_ODBC_VER doit retourner > « 01 ».
SQLGetInfo
, SQL_SCROLL_OPTIONS doit prendre en charge SQL_SO_KEYSET_DRIVEN.
SQLGetInfo
, SQL_ROW_UPDATES doit retourner « Y ».
SQLGetInfo
, SQL_POSITIONED_UPDATES doit prendre en charge SQL_PS_POSITIONED_DELETE et SQL_PS_POSITIONED_UPDATE.
En outre, si le verrouillage pessimiste est demandé, un appel à SQLSetPos
irow 1, fRefresh FALSE et fLock SQL_LCK_EXCLUSIVE sera effectué.