I have pulled the DAO source code from the support folder of VC6 SP6, as
suggested in the Service Pack Readme.
Any suggestions on how to proceed? I appreciate that DAO is just not used
any longer, but this would breath a bit of life back into an old product, so
I am keen to get it working.
Thanks
Granta Guy
I understand that your application loaded old version DLLs DAO350.DLL and
MSJET35.DLL but not DAO360.DLL and MSJET40.DLL after your application was
ported from VC6.0 to VS2005.
If I have misunderstood, please let me know.
Could you please let me know your Windows OS version and Office version?
I am not sure if you had installed the latest service pack for Microsoft
Jet4.0 database engine, but you may refer to this article first:
How to obtain the latest service pack for the Microsoft Jet 4.0 Database
Engine
http://support.microsoft.com/kb/239114/en-us
I wrote a simple project with CDaoDatabase and CDaoRecordset in Visual
Studio 2005 and it worked fine with loading dao360.dll and msjet40.dll at
runtime in my Windows XP SP2 machine with Microsoft Office 2003 installed.
My sample code is as following:
#include "afxdao.h"
..
void CMyDaoView::GetSales(int nId,CList<CString,CString&>& lstSales)
{
CString strId;
COleVariant varValue;
m_db.Open(_T("F:\\Test\\DB\\Access\\Sales.mdb"),FALSE,FALSE,_T(""));
strId.Format(_T("SELECT CustName FROM Customer WHERE CustId=%d"),nId);
m_rs.m_pDatabase = &m_db;
m_rs.Open(dbOpenDynaset,strId.GetBuffer(100),dbForwardOnly);
while(!m_rs.IsEOF())
{
m_rs.GetFieldValue(_T("CustName"),varValue);
CString strVal(varValue.bstrVal);
INT_PTR pCount = lstSales.GetCount();
if(pCount == 0)
lstSales.AddHead(strVal);
else
lstSales.InsertAfter(lstSales.GetHeadPosition(),strVal);
m_rs.MoveNext();
}
m_rs.Close();
m_db.Close();
}
Then I ran the MDI application and used Process Monitor to monitor the
process and I found that C:\Program Files\Common Files\Microsoft
Shared\DAO\dao360.dll and C:\WINDOWS\system32\msjet40.dll were loaded. I
recommend that you check if the two DLLs are located in the right path in
your computer and try manually running "regsvr32 <dao360.dll's path>" to
see if it helps.
If the above suggestions do not help, I recommend that you mail me
(changliw_at_microsoft_dot_com) a small sample project so that I can
reproduce your issue at my side.
If you have any other questions or concerns, please feel free to let me
know. Have a good day!
Best regards,
Charles Wang
Microsoft Online Community Support
=====================================================
When responding to posts, please "Reply to Group" via
your newsreader so that others may learn and benefit
from this issue.
======================================================
This posting is provided "AS IS" with no warranties, and confers no rights.
======================================================
The DAO SDK was shipped, I think, with vanilla VC 6 as a separate install.
The original version supported jet3.5, but there was an update to DAO3.6 that
was shipped as extra files in the support folder (according to the readme of
SP5 or SP6 for VC). It is this dll (DDAO36.dll) that I need to rebuild, since
it uses MFC string classes.
I am up-to-date with DAO and Office - and when I open the original project
in VC6, it loads up the correct DAO DLL's.
The problem, I suspect, is that the DAO 3.6 SDK was a bit shambolic - a
bunch of files shipped in the support folder of VC 6 Service Pack.
Unfortunately, it was shipped with a whole bunch of other support files and
lumped in together, so picking out the pieces is a bit tricky.
Has this cleared the picture a bit? I will also look at the MFC dao classes
to see if there is a close enough mapping to perhaps switch to them instead,
which might be a possibility.
Thanks!
Granta Guy
.....
TCHAR stmt[1024];
HRESULT hr = CoInitialize(NULL);
if(FAILED(hr))
return;
DAO::_DBEnginePtr pDbEngine(__uuidof(DAO::DBEngine));
DAO::RecordsetPtr pRs;
DAO::FieldsPtr pFields;
DAO::DatabasePtr pDb;
pDb = pDbEngine->OpenDatabase(_T("F:\\Test\\DB\\Access\\Sales.mdb"));
pRs = pDb->OpenRecordset(_T("Customer"),DAO::dbOpenTable);
if(pRs->RecordCount!=0)
{
int n = 0;
this->m_lscResult.InsertColumn(0,_T("Customer Id"),LVCFMT_LEFT,80);
this->m_lscResult.InsertColumn(1,_T("Customer Name"),LVCFMT_LEFT,100);
this->m_lscResult.InsertColumn(2,_T("Description"),LVCFMT_LEFT,300);
pRs->MoveFirst();
while(!pRs->TEof)
{
pFields = pRs->GetFields();
int nId = (int)(pFields->GetItem(_T("CustId"))->GetValue());
CString strId;
strId.Format(_T("%d"),nId);
CString strName = pFields->GetItem(_T("CustName"))->GetValue();
CString strDesc = pFields->GetItem(_T("CustDesc"))->GetValue();
this->m_lscResult.InsertItem(n,strId.GetBuffer(0));
this->m_lscResult.SetItemText(n,1,strName.GetBuffer(0));
this->m_lscResult.SetItemText(n,2,strDesc.GetBuffer(0));
++n;
pRs->MoveNext();
}
}
pRs->Close();
pDb->Close();
CoUninitialize();
----------------------------------------------------------------------------
-------------------------------------------
If you have any other questions or concerns, please feel free to let me
know. Have a nice day!
Best regards,
Charles Wang
Microsoft Online Community Support
======================================================
But one issue has arisen. DAO SDK had a method called GetRowsEx on a
recordset. There is a method called SetGetRowsExInt that is key:
prs->QueryInterface(IID_ICDAORecordset, (void **)&pGetRows);
I don't yet know what this CDAORecordset is; can you shed any light on that
one?
Otherwise, I think it will be successful, so thanks for your help.
GrantaGuy
As you can see, it has the same behavior as Recordset. However I could not
find any documents explaining this. I will try to consult the product team
on this issue to see if they could give me some information. Since this SDK
is very old, I am not sure if I could get a response now, however if there
is any response I will let you know.
If you have any questions or concerns, please feel free to let me know.
Have a nice day!
Best regards,
Charles Wang
Microsoft Online Community Support
=====================================================
From this header file, you can see the following declarations:
#undef INTERFACE
#define INTERFACE ICDAORecordset
DECLARE_INTERFACE_(ICDAORecordset, IDispatch)
{
STDMETHOD(GetRows) (THIS_ LONG cRowsToSkip, LONG cCol,
LPDAOCOLUMNBINDING prgBndCol, ULONG cbRowLen, LPDAOFETCHROWS pFetchRows)
PURE;
STDMETHOD(SetNotify) (THIS_ REFIID riid, BOOL fNotify);
STDMETHOD(GetNotify) (THIS_ REFIID riid, BOOL *fNotify);
STDMETHOD(OnBeforeNotify) (THIS_ REFIID riid, DWORD cat, DWORD rsn,
VARIANT v1, VARIANT v2);
STDMETHOD(OnAfterNotify) (THIS_ REFIID riid, DWORD cat, DWORD rsn, VARIANT
v1, VARIANT v2, HRESULT hr);
STDMETHOD(PutLock) (THIS_ BOOL f);
STDMETHOD(GetLock) (THIS_ BOOL *f);
STDMETHOD(AddGetRowsErr) (THIS_ HRESULT hr) PURE;
};
So now we can conclude that the CDAORecordset in DAO SDK is a seperate
class with exposing ICDAORecordset interface which contains the above
interface functions.
Hope this helps. If you have any questions or concerns, please feel free to
let me know. Have a good day!
Best regards,
Charles Wang
Microsoft Online Community Support
=====================================================
If you have any questions or concerns in future, please feel free to post
here. Have a nice day!
Best regards,
Charles Wang
Microsoft Online Community Support
======================================================