trouble with modifying mail content in outlook 2007 before sending

R

Raiv

I am trying to replace content of e-mail attachment handling
Outlook::ApplicationEvents::OnNewMailEx event.

And I have a trouble: mail is sending without replacement of item, new item
is simply added as another attachment. the most confusing thing that "sent
items" folder of the outlook shows correct mail item, but it comes with two
attachments to mail receiver.

Maybe the trouble is in the outlook threads? May the mail be sent before
replacement save is complete? is there any walkaround to wait for full mail
saving before it sent?


static bool SetBinaryByTag_MAPI(IDispatch *object, ULONG tag,
const void *data, int size)
{
bool ret = false;
LOG_ENTER_PTR(object);

IUnknown *iunkObject = ObtainMAPIOBJECT(object);
if (iunkObject)
{
CComQIPtr<IMAPIProp, &IID_IMAPIProp> mapiObject(iunkObject);
ret = SetBinaryByKnownObjectAndTag(mapiObject, tag, data, size);
iunkObject->Release();
}

LOG_RETURN_INT(ret);
return ret;
}

bool MAPIPropWrapper::SetPropertyByTag(IDispatch *object,
ULONG tag, const void *data, int size,
bool useMAPI)
{
bool ret = false;
LOG_ENTER("object = %p, useMAPI = %d, isMAPIInit = %d", object, useMAPI,
m_isMAPIInit);

if (!useMAPI)
{
ret = SetBinaryByTag_PA(object, tag, data, size);
}
else
{
if (m_isMAPIInit)
{
ret = SetBinaryByTag_MAPI(object, tag, data, size);
}
}

LOG_RETURN_INT(ret);
return ret;
}


bool MAPIPropWrapper::SaveChanges(IDispatch *object, bool useMAPI, ULONG
flags)
{
bool ret = false;
LOG_ENTER("object = %p, useMAPI = %d, isMAPIInit = %d, flags = 0x%08X",
object, useMAPI, m_isMAPIInit, flags);

if (!useMAPI)
{
/* PropertyAccessor automatically save changes after property changed. */
ret = true;
}
else
{
if (m_isMAPIInit)
{
IUnknown *iunkObject = ObtainMAPIOBJECT(object);
if (iunkObject)
{
CComQIPtr<IMAPIProp, &IID_IMAPIProp> mapiObject(iunkObject);
if (!mapiObject)
{
LOG_ERROR("Obtain invalid MAPI object %p!", iunkObject);
}
else
{
HRESULT hr = mapiObject->SaveChanges(flags);
if (FAILED(hr))
{
LOG_ERROR_HRESULT("mapiObject->SaveChanges()", hr);
}
else
{
ret = true;
}
}
iunkObject->Release();
}
}
}

LOG_RETURN_INT(ret);
return ret;
}


bool MAPIWrapper::ReplaceAttachmentData(IDispatch *mail, int num,
void *data, int dataSize)
{
bool ret = true;

CComPtr<Outlook::Attachments> attachments;
CComQIPtr<Outlook::_MailItem> mailItem(mail);
if (!mailItem)
{
ret = false;
}
else
{
HRESULT hr = mailItem->get_Attachments(&attachments);
if (FAILED(hr))
{
ret = false;
}
else
{
CComPtr<Outlook::Attachment> attachment;
hr = attachments->Item(CComVariant(num), &attachment);
if (FAILED(hr))
{
ret = false;
}
else
{
bool localUseMAPI = true;
ret = SetPropertyByTag(attachment, PR_ATTACH_DATA_BIN,
data, dataSize, localUseMAPI);
if (ret)
{
CComVariant v(true);
ret = SetPropertyByTag(attachment, PR_ATTACHMENT_HIDDEN, v,
localUseMAPI);
}
if (ret)
{
ret = SaveChanges(attachment, localUseMAPI, FORCE_SAVE);
}
}
}
}
return ret;
}


class variables:
CComPtr<IDispatch> m_mail;
int attachmentNum;
void* binaryData;
int dataSize;

Event handler:

{
...
bool ret= ReplaceAttachmentData(m_mail, attachmentNum,
binaryData, dataSize)
....
// another modifications
....
if(ret)
{
ret = MAPIWrapper::SaveMail(m_mail);
}
return ret;
}


I use MSVC2005sp1 + Outlook2007 12.0.4518.1014
 
K

Ken Slovak - [MVP - Outlook]

I'm confused. Why are you using NewMailEx(), an event that fires when new
emails come into Inbox, and then referring to sent items and sending them?
What does one have to do with the other?

If you want to handle an event when items are sent to strip or replace
attachments why not use either Application_ItemSend() or the Send() event
for an open item?

NewMailEx() would be a completely wrong event for what you say you want.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top