In this post I will talk about implementing a custom email notification
event using OIM API.
By custom I mean, everything would be custom – ‘The Notification
Resolver ‘, Templates, Triggering code :)
Background:
OIM notification framework supports creation of custom notification
events, templates and notification resolver apart from using default ones. It
supports notification mechanism based on events, notification templates and
template resolver. Following things are important while implementing custom
notification service.
Notification Event:
An event is an operation that occurs in
Oracle Identity Manager, such as user creation, request initiation, or any
custom event created by the user. Events are associated with
Event Definitions. Event definition is the metadata that
describes the event. This are defined as XML file and imported as part of MDS
database in order to make notification event available for use.
Notification Template:
The templates are used for defining the
format of the notification. A notification template is used to send notifications. The
template supports text based and HTML based messages.It also supports
different encoding formats .These templates contains the message and which could
have some variables that gets replaced at run-time by resolver. Notification
templates are associated to specific events.
You can create new notification templates
and link them to the existing events (In this post we are going to create
custom event and not using existing one). In addition, you can define new notification events by using
notification APIs and resolver class, as described in the subsequent sections.
Notification Resolver Class:
As the name suggests, the resolver is a
java class which is responsible to resolve or substitute the values for the
variables defined in the notification template.
Notification Triggering Code:
This class will actually have the
triggering logic /sending email notification. It makes use of NotificationService
API.
Configuring the SMTP Service for
Notification:
By default, the SMTP Email Notification
Provider is disabled. This is enabled by setting the value of the enabled
attribute to true. To configure SMTP Email Notification Provider properties by
using the EmailNotificationProviderMBean,you'll have to login to EM Console
and follow the link for detailed steps: https://docs.oracle.com/cd/E27559_01/admin.1112/e27149/notification.htm#OMADM873
Flow of Notification is:
The triggering code which is in process task,
scheduler or event handler will be invoked based on the request type, from the
code the template name and template parameters are identified. The event (selected
while creating template) in it will be invoked that is nothing but the resolver
class, so through the event the actual values of attributes will be substituted
and a email will be sent to the receiver's email ids as defined in template parameter hash map.
Implementation:
Implementing the Resolver Class:
To develop a custom resolver class, one has to implement interface oracle.iam.notification.impl.NotificationEventResolver and
override the implemented methods with actual implementation. As mentioned
earlier this would resolve the data dynamically at run-time. This interface has
two methods:
The getAvailableData Method
public List<NotificationAttribute>
getAvailableData(String eventType, Map<String, Object> params);
This API will return the list of available data variables.
These variables will be available on the UI while creating/modifying the templates
and would allow users to select the variables so that they can be embedded as a
token as part of the messages on the template. These tokens are replaced
by the value passed by the resolver class at run time. Available data is
displayed in a drop down list.
The parameter "eventType" specifies the event Name
for which template is to be read.
The parameter "params" is the map which has the entity name and the corresponding value for which available data is to be fetched.
The parameter "params" is the map which has the entity name and the corresponding value for which available data is to be fetched.
The getReplacedData Method
This API would return the resolved value of the variables
present on the template at the runtime when notification is being sent.
The
parameter "eventType" specifies the event Name for which template is
to be read.
The parameter "params" is the map which has the base values such as usr_key, obj_keyetc required by the resolver implementation to resolve the rest of the variables in the template.
Use OimServer.jar to implement this interface.
The parameter "params" is the map which has the base values such as usr_key, obj_keyetc required by the resolver implementation to resolve the rest of the variables in the template.
Use OimServer.jar to implement this interface.
public class CustomNotificationResolver implements
NotificationEventResolver {
/**
* Returns the list of
available data variables.
* @see oracle.iam.notification.impl.NotificationEventResolver#getAvailableData
* (java.lang.String,
java.util.Map)
*/
@Override
public
List<NotificationAttribute> getAvailableData
(String
eventType, Map<String, Object> params) {
List<NotificationAttribute>
listAvaiableData =
new
ArrayList<NotificationAttribute>();
return listAvaiableData ;
}
/**
* This method returns
return the resolved value of the variables present in
* the template at the
runtime when notification is being sent.
* @see
oracle.iam.notification.impl.NotificationEventResolver#getReplacedData
* (java.lang.String,
java.util.Map)
*/
@SuppressWarnings("rawtypes")
@Override
public HashMap<String,
Object> getReplacedData
(String
eventType, Map<String, Object>
eventParams)
throws
Exception {
String methodName = "#getReplacedData()";
UserManager
userManager = Platform.getService(UserManager.class);
HashMap<String,
Object> resolverData =
new HashMap<String,
Object>();
logger.info(className + methodName +
"
EventType : [" +
eventType + "]");
// getting the notfication parameter
String userKey =
(String)eventParams.get("usr_key");
logger.info(className + methodName +
"Userkey : [" + userKey + "]");
// Mapping token with their actual value for user attributes.
if (userKey != null) {
NotificationService notificationService =
Platform.getService(NotificationService.class);
// getting the list of all notification attributes
List<NotificationAttribute>
notificationAttributes =
notificationService.getStaticData(eventType);
logger.info(className + methodName +
" Notification Attributes: ["
+notificationAttributes + "]");
// setting the attributes for user search
based on
the notification attributes
Set<String> userReturnAttrs = new
HashSet<String>();
for (NotificationAttribute
notificationAttribute :
notificationAttributes.get(0).getSubtree())
{
userReturnAttrs.add(notificationAttribute.getName());
}
logger.info(className + methodName +
" User Attributes: [" +userReturnAttrs+ "]");
//searching the user
//searching the user by user key and retrive
all attributes
which are added in userRetAttrs
User oUser =
userManager.getDetails(userKey, userRetAttrs, false);
HashMap<String, Object> userAttributes = oUser.getAttributes();
logger.info(className + methodName +
"Retrieving user with UserKey : [" + userKey +"]");
// setting the values in the resolved notification data Map
String key = null;
for (Map.Entry<String,
Object> entry : userAttributes.entrySet()) {
key =
entry.getKey();
if (key != null) {
if ((entry.getValue() instanceof java.util.Map)
&&
(key.equalsIgnoreCase(""))) {
key
= key.replace(' ', '_');
resolverData.put(key,
((HashMap)entry.getValue()).get(""));
} else {
key
= key.replace(' ', '_');
resolverData.put(key,
entry.getValue());
}
}
}
}
//returning the resolved data with all user information
return resolverData;
}
}
Creating Event Metadata:
<?xml
version="1.0" encoding="UTF-8"?>
<Events
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../metadata/NotificationEvent.xsd">
<EventType name="Custom Email
Notification Event">
<StaticData>
<Attribute DataType="X2-Entity"
EntityName="User" Name="User Login"/>
</StaticData>
<Resolver
class="com.idm.notification.resolver.CustomNotificationResolver ">
<Param DataType="X2-Entity"
EntityName="User" Name="usr_key"/>
</Resolver>
</EventType>
</Events>
plugin.xml :
<?xml
version="1.0" encoding="UTF-8"?>
<oimplugins
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<plugins
pluginpoint="oracle.iam.notification.impl.NotificationEventResolver">
<plugin
pluginclass="com.idm.notification.resolver.CustomNotificationResolver"
version="1.0" name="CustomNotificationResolver"/>
</plugins>
</oimplugins>
Now you may have a question,how exactly or what exactly will send/trigger the emails. OR where to write the notification logic ,what OIM entity i can use to send/trigger email and the answer is below.
OIM allows triggering email
notification through:
- Process Tasks
- Schedulers
- Event Handlers
We will see "Process task" approach for sending email notification to users and user's manager on success of target resource provisioning :
1. Go to Design Console
2. Open Adapter Factory
3. Create a Process Task Adapter "SendEmailOnResourceProvisioning"
4. Create variables and Click on add task
5. Select the java method,here it is the below method and map the input variables
6. Click save and compile
7. Status should be OK
/*This method sends notification to
userand to its
*
@param userKey,userLogin,managersLogin
*
@return void
*
*/
public void
sendEmailNotificationOnResourceProvisioning
(String userKey,String
userLogin, String
managersLogin){
String methodName = "#sendEmailNotificationOnResourceProvisioning()";
logger.entering(className, methodName);
String[] receiverUserIds = new String[] {userLogin, managersLogin};
String templateName="Email Notification Demo";
boolean status=this.notifyUser(userKey,receiverUserIds,
templateName);
logger.info(className + methodName+
"Email Notification Sent Successfully" +status);
logger.exiting(className, methodName);
}
Pass the notification template parameters:
/**
*
This method is used to notify user
* @param
notificationTemplateName - Notification Template Name
* @param userKey - user key of user
* @param userLogin
* @return status
*/
private boolean notifyUser(String
userKey,String[]
receiverUserIds, String
notificationTemplateName) {
String methodName = "#notifyUser";
logger.log(Level.FINEST, className + " " +
methodName + " START.");
HashMap<String, Object> templateParams =
new HashMap<String, Object>();
templateParams.put("usr_key", userKey);
boolean status=sendNotification(receiverUserIds,
templateParams,
notificationTemplateName);
logger.log(Level.FINEST, className + " " + methodName + " END");
return status;
}
Set the notification template parameters,NotificationEvent API is used to create the event and set the event parameters:
/**This method
sends notification to given receivers id's using notification event
* @param receiverUserIds
* @param templateParams
* @param templateName
* @return notificationStatus: Notification
sent successfully or not
* */
public static boolean
sendNotification(String[]
receiverUserIds,HashMap<String,
Object>
templateParams,String
templateName) {
String methodName = "#sendNotification()";
logger.entering(className, methodName);
boolean notificationStatus =false;
NotificationEvent notificationEvent
= new
NotificationEvent();
NotificationService
notificationService =
Platform.getService(NotificationService.class);
try {
notificationEvent.setUserIds(receiverUserIds);
notificationEvent.setTemplateName(templateName);
notificationEvent.setParams(templateParams);
logger.info(className + privateMethodName
+
"Notification
Service params:
["+notificationEvent+"]");
notificationStatus = notificationService.
notify(notificationEvent);
logger.info(className + privateMethodName
+"Email
Notification Sent : "
+ notificationStatus);
} catch (UserDetailsNotFoundException
e) {
e.printStackTrace();
} catch (EventException e) {
e.printStackTrace();
} catch
(UnresolvedNotificationDataException e) {
e.printStackTrace();
} catch
(TemplateNotFoundException e) {
e.printStackTrace();
} catch
(MultipleTemplateException e) {
e.printStackTrace();
} catch
(NotificationResolverNotFoundException e) {
e.printStackTrace();
} catch
(NotificationException e) {
e.printStackTrace();
}
return notificationStatus;
}
8. After creating the process task adapter,go to process definition of the resource,let say OID/AD.
9. Create a Process task "Send Email Notification".Select the properties as required.
10.Select the adapter "SendEmailOnResourceProvisioning" from list and map the variables.
11. Click Save.
12. Now open "Create User" process task and go to Responses tab.
13. From Responses ,select "SUCCESS" and click assign.
14. Now select the task we just created "Send Email Notification".
15. Click Save.
16. Provision a resource to a user whose email - id is set and also his managers id should be set to check the flow.
17. You can check the resource history if the task was triggered or not / successful or not.
18. If success ,an email should be sent to user and his manager.
Thanks !!
Nice blog and absolutely outstanding. You can do something much better but i still say this perfect.Keep trying for the best. Email templates google workspace
ReplyDeleteNice blog and absolutely outstanding. You can do something much better but i still say this perfect.Keep trying for the best. online calculator template
ReplyDeletecool stuff you have got and you keep update all of us. create your own quiz
ReplyDeleteReally I enjoy your site with effective and useful information. It is included very nice post with a lot of our resources.thanks for share. i enjoy this post. media kit templates The intention of web templates is to design a web site.
ReplyDelete