This chapter explains how applications (also known as audit clients) can use the Oracle Fusion Middleware Audit Framework to provide auditing capabilities. 11g Release 1 (11.1.1.6.0) introduces an audit service that enables you to integrate with the audit framework programmatically to log audit events and generate compliance reports using the same capabilities available to Oracle components.
Using the audit service, applications can:
create event definitions without the use of custom tables
register with the audit service when you deploy the application
change event definitions when redeploying the application
change audit configuration settings at run-time
This chapter contains these topics:
Section 28.2, "Integrating the Application with the Audit Framework"
Section 28.4, "Register Application with the Registration Service"
As Figure 28-1 shows, Java EE applications running on Oracle WebLogic Server can integrate with and leverage the audit framework seamlessly:
During application deployment or audit service start-up, a client such as a Java EE application or Oracle component registers with the audit service. The registration service updates the metadata store with the latest audit definitions contained in component_events.xml and related files.
See Also:
Section 12.3 for details about the audit flow.
The rest of this chapter explains how you can integrate your applications with the audit flow to log audit events and create audit reports.
Take these steps to integrate your application with the audit framework:
Create an audit definition file, component_events.xml
.
Package the component_events.xml
file and component_events_xlf.jar in the application EAR
file.
Add the audit event API to the application code to enable it to log audit events.
Integrate with a reporting tool such as Oracle Business Intelligence Publisher for reporting.
Update the audit event definition and redeploy as needed.
The following sections provide more details on these tasks:
This task involves creating the following files:
component_events.xml definition file
translation files
Create the audit definition component_events.xml file for your application.
For details about the composition of the component_events.xml file, and an example file, see Section 12.5.1.
When creating your audit definition file, you must be aware of certain rules that the registration service uses to create the audit metadata for the application. These include:
Version numbers. Any change to an audit event definition requires that the version ID be modified by changing the minor and/or major number.
For more information about versioning, see Section 12.5.3.1.
Attribute mapping tables for unique mappings between your application's attribute definitions and database columns. Each custom attribute must have a mapping order number in its definition.
For more information about attribute mapping, see Section 12.5.3.2.
Create the translation files required for your application.
Generate the files in XLIFF format and store them in component_events_xlf.jar; during registration, this information is stored in the audit metadata store along with the component audit event definition.
Java EE applications can be registered by packaging component_events.xml
and component_events_xlf.jar
in the META-INF
folder of the application's EAR files. The audit registration service will process them automatically when the application is deployed.
Note:
The filenames must be component_events.xml
and component_events_xlf.jar
respectively.
This section explains the various mechanisms by which applications can register with the audit service:
By default, the following registration activity occurs when you deploy, redeploy or undeploy the application:
Deployment - Registers the audit event definition to the audit metadata store if the application is not yet registered.
Redeployment - Upgrades the component audit event definition if the component is already registered. See Section 12.5.3.1 for details.
Undeployment - Removes the application's audit event definition from the audit metadata store.
Custom audit registration parameters are set in the WebLogic deployment descriptor weblogic-application.xml
, which is also packaged in the META-INF folder of the application EAR files.
Note:
A different descriptor file is used by other application servers. See Oracle Fusion Middleware Third-Party Application Server Guide for details.
Table 28-1 shows the parameters with their options:
Table 28-1 Parameters for Audit Registration Service
Parameter | Option | Description |
---|---|---|
opss.audit.registration |
OVERWRITE |
Register component audit definition whether or not it is registered. |
UPGRADE |
Register component audit definition according to versioning support. |
|
DISABLE |
Do not register component audit definition. |
|
opss.audit.deregistration |
DELETE (default option) |
Delete component audit definition from audit store when undeploying applications. |
DISABLE |
Keep component audit definition in audit store when undeploying applications. |
|
opss.audit.componentType |
Set the custom component type. (Optional) |
Examples of weblogic-application.xml
The following sample from a weblogic-application.xml file demonstrates the use of registration and de-registration options:
<wls:application-param> <wls:param-name>opss.audit.registration</wls:param-name> <wls:param-value>DISABLE</wls:param-value> </wls:application-param> <wls:application-param> <wls:param-name>opss.audit.registration</wls:param-name> <wls:param-value>OVERWRITE</wls:param-value> </wls:application-param> <wls:application-param> <wls:param-name>opss.audit.unregistration</wls:param-name> <wls:param-value>DELETE</wls:param-value> </wls:application-param> <wls:application-param> <wls:param-name>opss.audit.unregistration</wls:param-name> <wls:param-value>DISABLE</wls:param-value> </wls:application-param>
You can register your application to audit service by invoking audit registration service programmatically. The registration logic is as follows:
AuditService auditService = JpsServiceLocator.getServiceLocator().lookup(AuditService.class); AuditRegistration auditReg = <instance of AuditRegistration implementation>; AccessController.doPrivileged(new PrivilegedExceptionAction<Object>() { public Object run() throws AuditException, IOException { auditService.register(auditReg); return null; } });
Invoking auditService.register requires that clients be granted AuditStoreAccessPermission with create, upgrade actions. For details about setting grants, see Section 28.6.2.
Here is an example of registering the audit service programmatically:
// JpsContextFactory ctxFactory = JpsContextFactory.getContextFactory(); JpsContext ctx = ctxFactory.getContext(); //get audit service final AuditService auditService = ctx.getServiceInstance(AuditService.class); //create an audit registration instance final AuditRegistration auditReg = new SampleRegistration(); //call audit service API to register audit event definition AccessController.doPrivileged(new PrivilegedExceptionAction<Object>() { public Object run() throws AuditException, IOException { auditService.register(auditReg); return null; } });
The audit framework's Audit Administration Service (admin service) provides a set of APIs to query audit metadata and get/set audit runtime policy. The admin service is invoked as follows:
AuditService auditService = JpsContextFactory.getContextFactory().getContext().getServiceInstance(AuditService.class); AuditAdminService auditAdminService = auditService.getAdminService();
This section explains how to use the admin service APIs.
The APIs to query audit metadata are as follows:
Set<String> getComponentNames() throws AuditException; Map<String, ? extends AttributeGroup> getGenericAttributeGroups() throws AuditException; Collection<? extends EventCategory> getSystemEvents() throws AuditException; ComponentDefinition getComponentDef(String componentType) throws AuditException; AttributesDatabaseMap getAttributesMap(String componentType) throws AuditException; AttributesDatabaseMap getSystemAttributesMap() throws AuditException;
The following example demonstrates how to use the APIs to query audit metadata:
//search events and attributes for a component Set<String> components = auditAdminService.getComponentNames(); for (String componentType : components) { ComponentDefinition componentDef = auditAdminService.getComponentDef(componentType); //get attributes of a component AttributeGroup attrGroup = componentDef.getAttributes(); for (AuditAttribute attr : attrGroup.getAttributes()) { AuditAttribute.DataType type = attr.getAttributeType(); String attrName = attr.getName(); } //get events of a component Collection<? extends EventCategory> events = componentDef.getEvents(); for (EventCategory category : events) { if (category.isComponentSpecific()) { // isComponentSpecific() is true means the category is belong to a component, otherwise is system category Collection<? extends Event> categoryEvents = category.getAllEvents(); } } }
The APIs to retrieve and set audit runtime policy are as follows:
AuditPolicy getAuditPolicy(String componentType) throws AuditException; void setAuditPolicy(String componentType, AuditPolicy auditPolicy) throws AuditException;
The following example shows how to use the APIs to first obtain and then set the audit policy for a component:
//get runtime policy for component JPS final String componentType = "JPS"; AuditPolicy policy = auditAdminService.getAuditPolicy(componentType); String filterLevel = policy.getFilterLevel(); //set runtim policy for component JPS final AuditPolicy newPolicy = new AuditPolicy("All", null, null); //setAuditPolicy() requires AuditStoreAccessPermission(<componentType>, "modify"); AccessController.doPrivileged(new PrivilegedExceptionAction<Object>(){ public Object run() throws AuditException { auditAdminService.setAuditPolicy(componentType, newPolicy); return null; } });
Applications can programmatically access the run-time audit service to generate their own audit events using the client API.
The audit client API is as follows:
See Also:
Section 28.6.2 for the prerequisite to using getAuditor
.
Interface AuditService { Auditor getAuditor(String componentType); void register(AuditRegistration auditRegistration); void unregister(AuditRegistration auditRegistration); } Interface Auditor { boolean log(AuditEvent ev); boolean isEnabled(); boolean isEnabled(String categoryName, String eventType, boolean eventStatus, Map<String, Object> properties); } public class oracle.security.jps.service.audit.AuditEvent { public AuditEvent(AuditContext ctx, String eventType, String eventCategory, boolean eventStatus, String messageText); public void setApplicationName(String applicationName) public void setAttribute(String attributeName, Object attributeValue) public void setAttributeBoolean(String attributeName, boolean attributeValue) public void setAttributeBoolean(String attributeName, Boolean attributeValue) public void setAttributeBooleans(String attributeName, boolean[] values) public void setAttributeByteArray(String attributeName, byte[] attributeValue) public void setAttributeDate(String attributeName, Date attributeValue) public void setAttributeDates(String attributeName, Date[] values) public void setAttributeDouble(String attributeName, double attributeValue) public void setAttributeDoubles(String attributeName, double[] values) public void setAttributeFloat(String attributeName, float attributeValue) public void setAttributeFloats(String attributeName, float[] values) public void setAttributeInt(String attributeName, int attributeValue) public void setAttributeInts(String attributeName, int[] values) public void setAttributeLong(String attributeName, long attributeValue) public void setAttributeLongs(String attributeName, long[] values) public void setAttributeString(String attributeName, String attributeValue) public void setAttributeStrings(String attributeName, String[] values) public void setComponentName(String componentName) public void setComponentType(String componentType) public void setContextFields(String contextFields) public void setECID(String ecid) public void setEventCategory(String category) public void setEventDefinition(Object eventDefinition) public void setEventStatus(boolean status) public void setEventTimestamp(long eventTimestamp) public void setEventType(String eventType) public void setFailureCode(String failureCode) public void setHostId(String hostId) public void setHostNetworkAddr(String hostNetworkAddr) public void setInitiator(String initiator) public void setInstanceId(String instanceId) public void setMessageText(String messageText) public void setModuleId(String moduleId) public void setOracleHome(String oracleHome) public void setOracleInstance(String oracleInstance) public void setProcessId(String processId) public void setRemoteIP(String value) public void setResource(String value) public void setRID(String rid) public void setRoles(String value) public void setTarget(String value) public void setTargetComponentType(String targetComponentType) public void setThreadId(String threadId) public void setTransactionId(String transactionId) }
Subsequent sections explain how to obtain permissions and a run-time auditor instance.
Audit clients must have AuditStoreAccessPermission to invoke the Audit API. In this example, the grant allows application MyApp
to call auditService.getAuditor("MyApp")
in AccessController.doPrivileged
block:
<grant> <grantee> <codesource> <url>file:${oracle.deployed.app.dir}/MyApp${oracle.deployed.app.ext}</url> </codesource> </grantee> <permissions> <permission> <class>oracle.security.jps.service.audit.AuditStoreAccessPermission</class> <name>comp1</name> <actions>action1,action2,….</actions> </permission> </permissions> </grant>
where the <actions> are a comma-separated list of authorized actions relating to the audit API that the audit client needs to invoke. The possible actions are as follows:
Action | Authorizes client to |
---|---|
create |
Call AuditService.register(AuditRegistration) to register a new audit component. |
upgrade |
Call AuditService.register(AuditRegistration) to upgrade an existing audit component event definition. |
delete |
Call AuditService.unregister(AuditRegistration) to de-register an audit component. |
read |
Call AuditService.getAuditor(String componentType) to get an instance of component auditor. |
modify |
Call AuditAdminService.setAuditPolicy(String componentType, AuditPolicy auditPolicy) to modify audit policy. |
After your application registers to the audit service, it can get its runtime auditor instance programmatically from the OPSS audit service, as shown in the following sample code fragment:
//Gets audit service instance final AuditService auditService = JpsServiceLocator.getServiceLocator().lookup(AuditService.class); //Gets Auditor instance for application 'MyApp' Auditor auditor = AccessController.doPrivileged( new PrivilegedExceptionAction<Auditor>() { public Auditor run() throws AuditException { return auditService.getAuditor("MyApp"); } }); final String category = "Transaction"; final String eventName = "deposit"; //Check if event 'deposit' is enabled in filtering. boolean enabled = auditor.isEnabled(category, eventName, "true", null); if (enabled) { AuditContext ctx = new AuditContext(); String message = "deposit transaction"; //Creates an audit event AuditEvent ev = new AuditEvent(ctx, eventName, category, "true", message); //Sets event attributes ev.setInitiator("johnsmith"); ev.setAttributeInt("accounting:AccountNumber", 2134567); ev.setAttributeDate("accounting:Date", new Date()); ev.setAttributeFloat("accounting:Amount", 100.00); //Logs audit event boolean ret = auditor.log(event); }
The ultimate goal of audit integration is to create reports of audit events stored in audit database tables. As described in Section 13.6.1, audit events are saved into the common attribute table iau_common
(Section 12.4.2.2), and the custom attribute tables iau_custom_nnn
(Section 12.4.2.4). OPSS Common Audit Framework generates SQL scripts for components to create Oracle database views which component reporting applications can use to query audit event data from audit database tables.
The following steps (some of which you have already accomplished) are required:
Integrate with the audit framework using dynamic or declarative registration (Section 28.2 through Section 28.4).
Configure audit policies so that the run-time audit service logs events to generate audit data (Section 28.5 and Section 28.6).
Configure the audit loader to ensure bus-stop files are migrated to the database (Section 13.2).
Use the createAuditDBView
command to generate a SQL script of audit definitions ("Viewing Audit Definitions for your Component" in Section 12.5.3.2).
Log in to the database as the IAU schema user to create a view using the SQL script from the previous step.
Configure your reporting application to query the view.
See Also:
Chapter 14, "Using Audit Analysis and Reporting"; Section 14.6.2 is specially useful for custom reporting.
Here is a sample output of createAuditDBView
for component ApplicationAudit
:
-- Audit View for Component CREATE VIEW ApplicationAudit_AUDITVIEW AS SELECT IAU_AUDITSERVICE.IAU_TRANSACTIONID AS AUDITSERVICE_TRANSACTIONID, IAU_COMMON.IAU_COMPONENTTYPE AS ComponentType, IAU_COMMON.IAU_MAJORVERSION AS MajorVersion, IAU_COMMON.IAU_MINORVERSION AS MinorVersion, IAU_COMMON.IAU_INSTANCEID AS InstanceId, IAU_COMMON.IAU_HOSTID AS HostId, IAU_COMMON.IAU_HOSTNWADDR AS HostNwaddr, IAU_COMMON.IAU_MODULEID AS ModuleId, IAU_COMMON.IAU_PROCESSID AS ProcessId, IAU_COMMON.IAU_ORACLEHOME AS OracleHome, IAU_COMMON.IAU_HOMEINSTANCE AS HomeInstance, IAU_COMMON.IAU_ECID AS ECID, IAU_COMMON.IAU_RID AS RID, IAU_COMMON.IAU_CONTEXTFIELDS AS ContextFields, IAU_COMMON.IAU_SESSIONID AS SessionId, IAU_COMMON.IAU_TARGETCOMPONENTTYPE AS TargetComponentType, IAU_COMMON.IAU_APPLICATIONNAME AS ApplicationName, IAU_COMMON.IAU_EVENTTYPE AS EventType, IAU_COMMON.IAU_EVENTCATEGORY AS EventCategory, IAU_COMMON.IAU_EVENTSTATUS AS EventStatus, IAU_COMMON.IAU_TSTZORIGINATING AS TstzOriginating, IAU_COMMON.IAU_THREADID AS ThreadId, IAU_COMMON.IAU_COMPONENTNAME AS ComponentName, IAU_COMMON.IAU_INITIATOR AS Initiator, IAU_COMMON.IAU_MESSAGETEXT AS MessageText, IAU_COMMON.IAU_FAILURECODE AS FailureCode, IAU_COMMON.IAU_REMOTEIP AS RemoteIP, IAU_COMMON.IAU_TARGET AS Target, IAU_COMMON.IAU_RESOURCE AS IAU_RESOURCE, IAU_COMMON.IAU_ROLES AS Roles, IAU_COMMON.IAU_DOMAINNAME AS DomainName, IAU_COMMON.IAU_COMPONENTDATA AS ComponentData, IAU_COMMON.IAU_AUDITUSER AS AuditUser, IAU_COMMON.IAU_TENANTID AS TenantId, IAU_COMMON.IAU_TRANSACTIONID AS TransactionId, IAU_COMMON.IAU_USERTENANTID AS UserTenantId, IAU_CUSTOM.IAU_INT_001 AS AccountNumber, IAU_CUSTOM.IAU_DATETIME_001 AS Date, IAU_CUSTOM.IAU_FLOAT_001 AS Amount, IAU_CUSTOM.IAU_STRING_002 AS Status, IAU_CUSTOM.IAU_FLOAT_002 AS Balance, IAU_USERSESSION.IAU_AUTHENTICATIONMETHOD AS AuthenticationMethod FROM IAU_AUDITSERVICE, IAU_COMMON, IAU_CUSTOM, IAU_USERSESSION WHERE IAU_COMMON.IAU_ID = IAU_AUDITSERVICE.IAU_ID AND IAU_COMMON.IAU_ID = IAU_CUSTOM.IAU_ID AND IAU_COMMON.IAU_ID = IAU_USERSESSION.IAU_ID AND IAU_COMMON.IAU_ComponentType = 'ApplicationAudit';
Using Oracle Business Intelligence Publisher
You can leverage Oracle Business Intelligence Publisher to generate reports from your application's audit data, utilizing the same reporting capabilities available to Oracle components.
The basic steps are as follows:
Use a database view (created with the help of the createAuditDBView
command) to generate an Oracle BI Publisher report template.
Set up the Oracle BI Publisher report service.
Copy the report template into Oracle BI Publisher to view component audit events.
Generate reports with Oracle BI Publisher.
As the application's audit requirements evolve, you can update the integration to reflect the changes. The steps are as follows:
Update the audit definition file. Be mindful of the versioning rules as you take this step.
See Also:
Redeploy the application EAR file with the updated event definition file. Alternatively, you can notify the audit registration service of the existence of a newer version.
Verify your changes.