Last modified: July 23, 2011

Applies to: Outlook

Opens a recipient entry that has data residing in a host address book provider.

HRESULT OpenTemplateID(
  ULONG cbTemplateID,
  LPENTRYID lpTemplateID,
  ULONG ulTemplateFlags,
  LPCIID lpInterface,


[in] The byte count in the template identifier pointed to by the lpTemplateID parameter.


[in] A pointer to the template identifier, or PR_TEMPLATEID (PidTagTemplateid) property, of the recipient entry to be opened.


[in] A bitmask of flags used to indicate how to open the entry represented by the template identifier. The following flag can be set:


The host provider is creating a new entry in its container based on the entry represented by the template identifier. The IABLogon::OpenTemplateID method should either perform specific initialization of the host provider's entry by using the IMAPIProp : IUnknown implementation in the lpMAPIPropData parameter, or return a custom IMAPIProp interface implementation in the lppMAPIPropNew parameter.


[in] A pointer to the host provider's property object and implementation of an interface derived from IMAPIProp.


[in] A pointer to the interface identifier (IID) that represents the type of interface pointer to be returned in the lppMAPIPropNew parameter. Passing null returns the standard messaging user interface, IMailUser : IMAPIProp.


[out] A pointer to the bound property object and an implementation of an interface derived from IMAPIProp.


[out] Reserved; must be null.


The appropriate code was successfully bound to related data in the host provider.


The object does not support template IDs.


The template identifier passed in the lpTemplateID parameter is not recognized by the address book provider.

The IABLogon::OpenTemplateID method is implemented only by address book providers that need to maintain control over copies of their entries that are located in the containers of host providers. Providers that implement OpenTemplateID are known as foreign address book providers. Host providers call IMAPISupport::OpenTemplateID to create a copied entry or open the copied entry, and MAPI passes on the call to IABLogon::OpenTemplateID. IABLogon::OpenTemplateID opens the entry and binds the code that controls it to data in the host provider.

Rather than use an entry identifier, IABLogon::OpenTemplateID uses another property, the entry's template identifier, PR_TEMPLATEID. Template identifiers should be supported for entries whose code must be bound to data in a host provider.

Some examples of when an address book provider should implement IABLogon::OpenTemplateID are as follows:

  • To periodically update the data for a copied entry so that it stays synchronized with the original.

  • To implement functionality that the host provider cannot implement, such as dynamically populating a list that appears in the entry's details table from data on a server.

  • To control the interaction between properties in the host provider's entry and the original entry, such as computing the PR_EMAIL_ADDRESS (PidTagEmailAddress) from the values of the edit controls in the details display that contain different components of the address.

When a host provider copies or creates an entry from your provider and you supply a property object implementation through IABLogon::OpenTemplateID, you handle most of the calls to maintain the entry. However, because it is up to the host provider to forward these calls to you, the host provider can intercept any call and perform custom processing before forwarding the call.

You should use the following guidelines in your property object implementations:

  • When IMAPIProp::GetProps is called, determine whether the request is for a computed property and, if it is, handle it. Transfer all requests for noncomputed properties to the host provider.

  • When IMAPIProp::OpenProperty is called to open any table except the details display table, handle the request. Most tables cannot be copied accurately to the host provider. You must generate the IMAPITable implementation for these requested tables. The details table PR_DETAILS_TABLE (PidTagDetailsTable) property must be copied to the host provider. This allows this provider to generate the table locally. You might want to wrap the display table implementation to generate display table notifications.

  • When IMAPIProp::SetProps is called, the host provider can validate the data before letting you set the properties. You can verify that all of the necessary properties were set or computed. If an error is detected, return the appropriate error value and, if you can, any additional explanation through IMAPIProp::GetLastError.

  • When IMAPIProp::SaveChanges is called, the host provider might want to perform processing before you save the entry. You should save any data that is affected by the changed properties, such as a new address, in the host provider's entry.

In general, make your implementation of the entry that you pass back to the host provider intercept all of the methods to perform context-specific manipulation of the relevant properties. If the FILL_ENTRY flag is passed in the ulTemplateFlags parameter, set all properties for the entry.

If you return a new property object in the lppMAPIPropNew parameter, call the IUnknown::AddRef method of the host provider's property object to maintain a reference. All calls through the bound object that the IMAPIProp implementation returned in lppMAPIPropNew should be routed to their corresponding method in the host property object after they are dealt with by the bound object.

The property identifiers of any named properties that are passed through your bound property object are in your provider's identifier namespace. Your implementation of the IMAPIProp::GetNamesFromIDs method should determine the names of the properties so that it can perform any template-specific tasks. Similarly, properties that your provider passes on to the host provider must also be in your namespace. For example, if you set a named property in OpenTemplateID, you should use one of your identifiers for the name—creating it, if necessary, by calling the IMAPIProp::GetIDsFromNames method.

If you do not recognize the entry identifier passed in lpTemplateID, return MAPI_E_UNKNOWN_ENTRYID.

For more information about how to work with address book template identifiers, see Acting as a Foreign Address Book Provider.

© 2016 Microsoft