Microsoft KB Archive/231351: Difference between revisions
m (Text replacement - "<" to "<") |
m (Text replacement - """ to """) |
||
(2 intermediate revisions by the same user not shown) | |||
Line 65: | Line 65: | ||
The above error is caused by the wrong syntax in the Open method on the recordset in following line:<br /> | The above error is caused by the wrong syntax in the Open method on the recordset in following line:<br /> | ||
<pre class="codesample"> pRs- | <pre class="codesample"> pRs->Open("select * from authors", | ||
_variant_t (pConn), | _variant_t (pConn), | ||
adOpenDynamic, adLockOptimistic, adCmdText); | adOpenDynamic, adLockOptimistic, adCmdText); | ||
Line 78: | Line 78: | ||
</div> | </div> | ||
<br /> | <br /> | ||
The above error was caused by not using client-side cursors for an | The above error was caused by not using client-side cursors for an "Optimize" property in the following line of code:<br /> | ||
<pre class="codesample"> pRs- | <pre class="codesample"> pRs->Fields->GetItem("au_lname")->Properties->GetItem("Optimize")->Value = true; | ||
</pre> | </pre> | ||
Line 91: | Line 91: | ||
<pre class="codesample">// START ADO VC++ TUTORIAL | <pre class="codesample">// START ADO VC++ TUTORIAL | ||
#define INITGUID | #define INITGUID | ||
#import | #import "c:\Program Files\Common Files\System\ADO\msado15.dll" no_namespace rename("EOF", "EndOfFile") | ||
#include <stdio.h | #include <stdio.h> | ||
#include <icrsint.h | #include <icrsint.h> | ||
void dump_com_error(_com_error & | void dump_com_error(_com_error &e) | ||
{ | { | ||
printf( | printf("Error\n"); | ||
printf( | printf("\a\tCode = %08lx\n", e.Error()); | ||
printf( | printf("\a\tCode meaning = %s", e.ErrorMessage()); | ||
_bstr_t bstrSource(e.Source()); | _bstr_t bstrSource(e.Source()); | ||
_bstr_t bstrDescription(e.Description()); | _bstr_t bstrDescription(e.Description()); | ||
printf( | printf("\a\tSource = %s\n", (LPCSTR) bstrSource); | ||
printf( | printf("\a\tDescription = %s\n", (LPCSTR) bstrDescription); | ||
} | } | ||
Line 142: | Line 142: | ||
// Step 1: Open a connection | // Step 1: Open a connection | ||
pConn- | pConn->Open("dsn=pubs;", "sa", "", adConnectUnspecified); | ||
// Step 2: Create a command | // Step 2: Create a command | ||
// Step 3: Execute the command | // Step 3: Execute the command | ||
pRs- | pRs->CursorLocation = adUseClient; // FIX #3: NEED CLIENT CURSOR FOR BATCH UPDATES! | ||
pRs- | pRs->Open("select * from authors", | ||
_variant_t((IDispatch*)pConn), // FIX #4: MUST CAST SMART POINTER TO LPDISPATCH! | _variant_t((IDispatch*)pConn), // FIX #4: MUST CAST SMART POINTER TO LPDISPATCH! | ||
adOpenDynamic, | adOpenDynamic, | ||
Line 154: | Line 154: | ||
adCmdText); | adCmdText); | ||
if (FAILED(hr = pRs- | if (FAILED(hr = pRs->QueryInterface(__uuidof(IADORecordBinding), | ||
(LPVOID*)& | (LPVOID*)&picRs))) | ||
_com_issue_error(hr); | _com_issue_error(hr); | ||
if (FAILED(hr = picRs- | if (FAILED(hr = picRs->BindToRecordset(&rs))) | ||
_com_issue_error(hr); | _com_issue_error(hr); | ||
// Step 4: Manipulate the data | // Step 4: Manipulate the data | ||
pRs- | pRs->Fields->Item["au_lname"]->Properties->Item["Optimize"]->Value = true; // FIX #6: USE PROPER SMART POINTER SYNTAX. | ||
//pRs- | //pRs->Fields->GetItem("au_lname")->Properties->GetItem("Optimize")->Value = true; | ||
pRs- | pRs->Sort = "au_lname ASC"; | ||
pRs- | pRs->Filter = "phone LIKE '415 5*'"; | ||
pRs- | pRs->MoveFirst(); | ||
while (VARIANT_FALSE == pRs- | while (VARIANT_FALSE == pRs->EndOfFile) | ||
{ | { | ||
printf( | printf("\a\tName: %s\t %s\tPhone: %s\n", | ||
(rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : | (rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : ""), | ||
(rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : | (rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : ""), | ||
(rs.lphoneStatus == adFldOK ? rs.m_szphone : | (rs.lphoneStatus == adFldOK ? rs.m_szphone : "")); | ||
if (rs.lphoneStatus == adFldOK) | if (rs.lphoneStatus == adFldOK) | ||
memcpy(rs.m_szphone, | memcpy(rs.m_szphone, "777", 3); | ||
if (FAILED(hr = picRs- | if (FAILED(hr = picRs->Update(&rs))) | ||
_com_issue_error(hr); | _com_issue_error(hr); | ||
Line 186: | Line 186: | ||
// extracted and placed in the CCustomRs C++ instance variables. | // extracted and placed in the CCustomRs C++ instance variables. | ||
pRs- | pRs->MoveNext(); | ||
} | } | ||
pRs- | pRs->Filter = (long) adFilterNone; | ||
// Step 5: Update the data | // Step 5: Update the data | ||
pConn- | pConn->BeginTrans(); | ||
try | try | ||
{ | { | ||
pRs- | pRs->UpdateBatch(adAffectAll); | ||
// Step 6, part A: Conclude the update | // Step 6, part A: Conclude the update | ||
pConn- | pConn->CommitTrans(); | ||
} | } | ||
Line 204: | Line 204: | ||
{ | { | ||
// Step 6, part B: Conclude the update | // Step 6, part B: Conclude the update | ||
pRs- | pRs->Filter = (long) adFilterConflictingRecords; | ||
pRs- | pRs->MoveFirst(); | ||
while (VARIANT_FALSE == pRs- | while (VARIANT_FALSE == pRs->EndOfFile) | ||
{ | { | ||
printf( | printf("\a\tConflict: Name = %s\t %s\n", | ||
(rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : | (rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : ""), | ||
(rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : | (rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : "")); | ||
pRs- | pRs->MoveNext(); | ||
} | } | ||
pConn- | pConn->RollbackTrans(); | ||
} | } | ||
} | } | ||
catch (_com_error & | catch (_com_error &e) | ||
{ | { | ||
dump_com_error(e); | dump_com_error(e); |
Latest revision as of 13:44, 21 July 2020
Article ID: 231351
Article Last Modified on 10/17/2003
APPLIES TO
- Microsoft Data Access Components Software Development Kit 2.0
- Microsoft Data Access Components Software Development Kit 2.1
- Microsoft ActiveX Data Objects 2.0
- Microsoft ActiveX Data Objects 2.1
This article was previously published under Q231351
SUMMARY
The ADO Visual C++ Tutorial in MSDN has problems in the code that can cause one or more compilation or run-time errors.
To get to this tutorial, do the following:
- Start MSDN, click the Contents tab.
- Navigate as follows: Platform SDK, Data Access Service, Microsoft Data Access 2.1 SDK, Microsoft ActiveX Data Objects (ADO), Microsoft ADO Programmer's Reference.
- From the Microsoft ADO Programmer's Reference, navigate as follows: Learning ADO, ADO and RDS Tutorials, ADO Tutorial, ADO Tutorial (VC++).
One error that the user may get at run time is the following:
The above error is caused by the wrong syntax in the Open method on the recordset in following line:
pRs->Open("select * from authors", _variant_t (pConn), adOpenDynamic, adLockOptimistic, adCmdText);
Another error that the user may get at run time is the following:
The above error was caused by not using client-side cursors for an "Optimize" property in the following line of code:
pRs->Fields->GetItem("au_lname")->Properties->GetItem("Optimize")->Value = true;
MORE INFORMATION
Following is the code that corrects the above mentioned errors. Just replace the code from the sample with the following code:
// START ADO VC++ TUTORIAL #define INITGUID #import "c:\Program Files\Common Files\System\ADO\msado15.dll" no_namespace rename("EOF", "EndOfFile") #include <stdio.h> #include <icrsint.h> void dump_com_error(_com_error &e) { printf("Error\n"); printf("\a\tCode = %08lx\n", e.Error()); printf("\a\tCode meaning = %s", e.ErrorMessage()); _bstr_t bstrSource(e.Source()); _bstr_t bstrDescription(e.Description()); printf("\a\tSource = %s\n", (LPCSTR) bstrSource); printf("\a\tDescription = %s\n", (LPCSTR) bstrDescription); } class CCustomRs : public CADORecordBinding { BEGIN_ADO_BINDING(CCustomRs) ADO_VARIABLE_LENGTH_ENTRY2(1, adVarChar, m_szau_lname, sizeof(m_szau_lname), lau_lnameStatus, false) ADO_VARIABLE_LENGTH_ENTRY2(2, adVarChar, m_szau_fname, sizeof(m_szau_fname), lau_fnameStatus, false) ADO_VARIABLE_LENGTH_ENTRY2(3, adVarChar, m_szphone, sizeof(m_szphone), lphoneStatus, true) END_ADO_BINDING() public: CHAR m_szau_lname[41]; ULONG lau_lnameStatus; CHAR m_szau_fname[41]; ULONG lau_fnameStatus; CHAR m_szphone[12]; ULONG lphoneStatus; }; VOID main() { HRESULT hr; IADORecordBinding *picRs = NULL; ::CoInitialize(NULL); try { _ConnectionPtr pConn(__uuidof(Connection)); // FIX #1: DON'T USE PROGID! _RecordsetPtr pRs(__uuidof(Recordset)); // FIX #2: DON'T USE PROGID! CCustomRs rs; // Step 1: Open a connection pConn->Open("dsn=pubs;", "sa", "", adConnectUnspecified); // Step 2: Create a command // Step 3: Execute the command pRs->CursorLocation = adUseClient; // FIX #3: NEED CLIENT CURSOR FOR BATCH UPDATES! pRs->Open("select * from authors", _variant_t((IDispatch*)pConn), // FIX #4: MUST CAST SMART POINTER TO LPDISPATCH! adOpenDynamic, adLockBatchOptimistic, // FIX #5: MUST USE adLockBatchOptimistic adCmdText); if (FAILED(hr = pRs->QueryInterface(__uuidof(IADORecordBinding), (LPVOID*)&picRs))) _com_issue_error(hr); if (FAILED(hr = picRs->BindToRecordset(&rs))) _com_issue_error(hr); // Step 4: Manipulate the data pRs->Fields->Item["au_lname"]->Properties->Item["Optimize"]->Value = true; // FIX #6: USE PROPER SMART POINTER SYNTAX. //pRs->Fields->GetItem("au_lname")->Properties->GetItem("Optimize")->Value = true; pRs->Sort = "au_lname ASC"; pRs->Filter = "phone LIKE '415 5*'"; pRs->MoveFirst(); while (VARIANT_FALSE == pRs->EndOfFile) { printf("\a\tName: %s\t %s\tPhone: %s\n", (rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : ""), (rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : ""), (rs.lphoneStatus == adFldOK ? rs.m_szphone : "")); if (rs.lphoneStatus == adFldOK) memcpy(rs.m_szphone, "777", 3); if (FAILED(hr = picRs->Update(&rs))) _com_issue_error(hr); // Change the current row of the Recordset. // Recordset data for the new current row will automatically be // extracted and placed in the CCustomRs C++ instance variables. pRs->MoveNext(); } pRs->Filter = (long) adFilterNone; // Step 5: Update the data pConn->BeginTrans(); try { pRs->UpdateBatch(adAffectAll); // Step 6, part A: Conclude the update pConn->CommitTrans(); } catch (_com_error) { // Step 6, part B: Conclude the update pRs->Filter = (long) adFilterConflictingRecords; pRs->MoveFirst(); while (VARIANT_FALSE == pRs->EndOfFile) { printf("\a\tConflict: Name = %s\t %s\n", (rs.lau_fnameStatus == adFldOK ? rs.m_szau_fname : ""), (rs.lau_lnameStatus == adFldOK ? rs.m_szau_lname : "")); pRs->MoveNext(); } pConn->RollbackTrans(); } } catch (_com_error &e) { dump_com_error(e); } CoUninitialize(); } // END ADO VC++ TUTORIAL
Microsoft has confirmed that this is a bug in ADO VC Tutorial in MSDN version April 99 for Winodws 95/98/NT4.0.
REFERENCES
For additional information about using ADO in Visual C++, please see the following articles in the Microsoft Knowledge Base:
220152 Sample: ADOVC1 Simple ADO/VC++ Application
185033 FILE: Adoacc.exe Demonstrates Using ADO with Access 97
Additional query words: problem problematic MDAC
Keywords: kbdatabase kbdocfix kbdocerr KB231351