Background

Employees need access to various systems to complete their job responsibilities. Provisioning such access becomes increasingly complex due to the increase in the number of systems, the sophistication of access policies based on employment characteristics, and the need to manage changes through the employment lifecycle. Entitlement management systems (EMS) streamline this process, allowing customers to provision system access based on employee data.

Such systems must manage three cases: joiners, movers, and leavers. Joiners are employees entering the organization, movers are those taking on new responsibilities within the organization, and leavers are those employees departing from the organization. For joiners, system access must be initialized. Movers will need system access to be added or revoked, based on changes in their job responsibilities. System access is mostly revoked from leavers with procedures in place to grant limited access for ex-employees as well as the ability to efficiently re-initialize access upon return.

In this document, we will explore how customers can integrate Oracle HCM Cloud with such systems based on employees’ personal and employment information.

Prerequisites

Use JWT to access HCM data feeds and SCIM APIs. More information about configuring JWT can be found here. More information about authenticating with JWT can be found here.

Privileges

To access the tools described you will need the following privileges.

Resource Privilege Available to Roles
SCIM API ASE_REST_SERVICE_ACCESS_IDENTITY_INTEGRATION_PRIV
  • IT Security Manager (ORA_FND_IT_SECURITY_MANAGER_JOB)
  • IT_SECURITY_MGR

WARNING:

The practices outlined in this document are designed for performance. Do not use REST API to sync data from HCM.

Blueprint for Integration with Entitlement Management Systems

Integration will consist of the following phases.

  1. Policy Analysis
  2. An analysis of the policies that will be implemented is conducted. The full list of HCM attributes (personal, employment, and use account) required for defining these policies is identified

  3. Initial Sync
  4. The Entitlement Management System (EMS) will be initialized with the full list of HCM attributes. This initial sync must be performed through a file-based export (from HCM) and subsequent import into the EMS.

  5. Incremental Sync
  6. Information about changes to workers in Oracle HCM (Joiners, Movers, Leavers) will be propagated to the EMS. This information is provided through ATOM feeds. These feeds must be polled at the desired frequency. An overview of HCM ATOM feeds can be found here.

  7. Updating HCM
  8. If the Entitlement Management System (EMS) makes changes to a worker's personal, employment, or use account data, these changes must be propagated to the HCM system to ensure data consistency. These changes must be made using the user SCIM API.

Overview

To illustrate this process, let's say that we have two employees joining a company: Joe and Mary. Joe joins the company as an employee and requires access to email and the employee training system. Mary joins the company as a manager and requires access to email, the employee training system, and the manager training system. The Entitlement Management System (EMS) acts to manage system access for these new hires.

  1. The customer instructs the EMS to provide all employees with access to email and employee training. The customer also instructs the EMS to provide all managers with manager training.
  2. EMS completes an incremental sync and finds that Mary and Joe have been hired. EMS stores their person and employment information provided by HCM in their database.
  3. PersonNumber PeriodOfServiceId AssignmentId PersonName WorkEmail PrimaryPhoneNumber WorkerType BusinessUnitId OrganizationId PositionId LocationId JobId EffectiveStartDate
    966169008890736 300100591016284 300100591078074 Green, Joe 650-849-5931 EMP 300100032736497 300100037658514 300100037658162 300100037658196 300100037637824 2023-08-01
    966169008890236 300100591078068 300100591026173 King, Mary 919-234-9182 EMP 300100032736497 300100037658514 300100037658660 300100037658196 300100037658485 2023-08-01
  4. All employees at the company require access to email and employee training. EMS provisions Joe's email access through the company's email provider and also provisions Joe's employee training through the company's employee training provider. EMS then writes the email information back to HCM.
  5. PersonNumber PeriodOfServiceId AssignmentId PersonName WorkEmail PrimaryPhoneNumber WorkerType BusinessUnitId OrganizationId PositionId LocationId JobId EffectiveStartDate
    966169008890736 300100591016284 300100591078074 Green, Joe joe.green@mail.com 650-849-5931 EMP 300100032736497 300100037658514 300100037658162 300100037658196 300100037637824 2023-08-01
    966169008890236 300100591078068 300100591026173 King, Mary 919-234-9182 EMP 300100032736497 300100037658514 300100037658660 300100037658196 300100037658485 2023-08-01
  6. Mary's employment information indicates that she is a manager in addition to being an employee. EMS provisions manager training through the company's manager training provider in addition to email and employee training access granted to employees.
  7. PersonNumber PeriodOfServiceId AssignmentId PersonName WorkEmail PrimaryPhoneNumber WorkerType BusinessUnitId OrganizationId PositionId LocationId JobId EffectiveStartDate
    966169008890736 300100591016284 300100591078074 Green, Joe joe.green@mail.com 650-849-5931 EMP 300100032736497 300100037658514 300100037658162 300100037658196 300100037637824 2023-08-01
    966169008890236 300100591078068 300100591026173 King, Mary mary.king@mail.com 919-234-9182 EMP 300100032736497 300100037658514 300100037658660 300100037658196 300100037658485 2023-08-01
  8. EMS has provisioned Mary and Joe's system access based on the customer's specifications and HCM HR data.
Data Structure

HCM organizes worker data based on the employment model with two essential entities: work relationship and assignment. The work relationship defines the relationship between a person and a legal employer. While a person can have multiple work relationships, only one work relationship is the primary work relationship. Each work relationship must have at least one assignment which provides information about a person’s role. There may be multiple assignments for each work relationship, but there must be at least one assignment, marked primary, for each work relationship. The primary assignment of the primary work relationship the overall primary assignment for that person.

Organize your data using these fundamental structures. They are documented in the HCM database using the following attributes with example data outlined below.

  1. PersonNumber: a unique identifier assigned to each person in the HCM database (employee, pending worker, contingent worker, or nonworker)
  2. PeriodOfServiceID: a unique identifier assigned to each work relationship
  3. AssignmentID: a unique identifier assigned to each assignment
  4. PrimaryFlag: a flag to indicate which work relationship is a person’s primary using “Y” or “N” values
  5. PrimaryAssignmentFlag: a flag to indicate which assignment is a work relationship’s primary using “Y” or “N” values

Caution:

HCM uses two unique identifiers for a person, PersonNumber and PersonID. PersonID can vary across environments, so you must use PersonNumber for effective data management.

Initial Sync

Steps for initial sync

  1. Extract HCM data into a CSV file
  2. Encrypt the data using PGP encryption
  3. Import the encrypted CSV file into the EMS
  4. Decrypt the CSV file
  5. Load the decrypted CSV file, with any necessary transformations, into the EMS

The EMS must provide the customer with an interface that allows CSV file import. You can use a file transfer protocol (FTP), a user interface (UI) for manual upload, or a REST API. Also, the EMS must provide a mechanism to exchange PGP key.

Once the file is imported, it must be decrypted using PGP decryption. For example, you could use the following command.

gpg --decrypt <inbound_file_name> --output <output_file_name>

Tip:

Once you have accessed the CSV, you have access to relevant HCM data for entitlement management. Transform the data (as necessary) for entitlement management using person, work relationship, and assignment information to implement the necessary entitlement access policies.

Incremental Sync

Steps for incremental sync

  1. Poll for ATOM feeds. These feeds will provide information about joiner, mover, and leaver events in Oracle HCM
  2. Update the EMS with the changes to employment data, captured in the feeds
  3. Execute entitlement policies using the changed data

The feeds reduce overhead by eliminating the need for multiple full-data syncs. We will cover the different feeds, their trigger events, and the data provided by the feeds.

Employee feeds track data changes that pertain to employees, contingent workers, and pending workers. Subscribe to an employee feed with the following endpoint and proper authorization. Obtain the necessary authorization credentials from the customer.

https://<host>:<port>/hcmRestApi/atomservlet/employee/<collection>
Each data feed is triggered by particular data change events summarized in the following table.
Employee Feed Collection Trigger Event
cancelworkrelship An offer is terminated or renegotiated, global transfer, temporary assignment, or secondary work relationship is reverted to correct effective date, legal employer, or worker type
empassignment Assignment, salary, or manager information is created, updated, corrected, or deleted
empupdate Personal details username, or religion is updated
Name or legislative information is corrected or updated
Work email address, phone details, address, national identifier information, passport information, driver’s license information, citizenship information is created, updated, or deleted
newhire Employee hired, terminated employee rehired, or future-dated new hire created
payupdate Payroll is assigned or updated
termination Employee is terminated
workrelshipupdate Any attribute related to work relationship data is updated, other than changes that are already captured by the termination and work relationship cancellation feeds including hire date or primary flag information

table source

Each feed returns a different set of attributes which will be used to build your dataset. Feed attributes are returned with every event, labeled context, while conditional attributes are returned to provide additional information based on the data change, labeled changed attributes. The set of attributes returned by each feed is summarized in the table below. Use the context attributes to identify what data to add or update, then use the conditional attributes to make the addition or change. Once your data is updated, correct employee system access accordingly.

For example, when an employee's phone number is updated, the empupdate employee feed would indicate the change with contextual and conditional attributes. The contextual attributes indicate where the change takes place with standard attributes: PersonName, PersonNumber, WorkEmail, PrimaryPhoneNumber, PersonId, PeriodType, WorkerType, DMLOperation, EffectiveStartDate, and EffectiveDate. The conditional attributes indicate what change was made and only include the relevant attributes both before and after the change. In this case, the only conditional attribute is PrimaryPhoneNumber. The table below outlines the attributes you can expect for each feed. Again, the context attributes will always be indicated but conditional attributes will only be indicated when relevant to a given change event.

Employee Feed Contextual Attributes Conditional Attributes
cancelworkrelship
  • PeriodOfServiceID
  • PersonName
  • PersonNumber
  • PrimaryPhoneNumber
  • PersonId
  • PeriodType
  • WorkerType
  • DMLOperation
  • PrimaryFlag
  • EffectiveDate
  • ActionOccurrenceId
empassignment
  • AssignmentID
  • PersonNumber
  • PrimaryPhoneNumber
  • PersonId
  • PeriodType
  • WorkerType
  • DMLOperation
  • EffectiveDate
  • PeriodOfServiceId - must be configured by the customer
  • AssignmentStatusType
  • ActionCode
  • ManagerType
  • ManagerAssignmentId
  • ManagerId
  • AssignmentType
  • BusinessUnitId
  • OrganizationId
  • LegalEntityId
  • ...
empupdate
  • PersonName
  • PersonNumber
  • WorkEmail
  • PrimaryPhoneNumber
  • PersonId
  • PeriodType
  • WorkerType
  • DMLOperation
  • EffectiveStartDate
  • EffectiveDate
  • ActionCode
  • AssignmentStatusType
  • ManagerType
  • ManagerAssignmentId
  • ManagerId
  • BusinessUnitId
  • OrganizationId
  • AssignmentId
  • LegalEntityId
  • JobId
  • AddressLine1
  • Country
  • PostalCode
  • PhoneNumber
  • UserName
  • EmailAddress
  • EmailType
  • ...
newhire
  • PeriodOfServiceId
  • PersonName
  • PersonNumber
  • PrimaryPhoneNumber
  • PersonId
  • PeriodType
  • WorkerType
  • DMLOperation
  • EffectiveDate
NA
termination
  • PersonNumber
  • PeriodOfServiceId
  • DMLOperation
  • PeriodType
  • PersonName
  • WorkerType
  • PrimaryFlag
  • PersonId
  • PrimaryPhoneNumber
  • EffectiveStartDate
  • EffectiveDate
  • ActualTerminationDate
workrelshipupdate
  • PeriodOfServiceId
  • PersonName
  • PersonNumber
  • PrimaryPhoneNumber
  • PersonId
  • PeriodType
  • WorkerType
  • DMLOperation
  • EffectiveStartDate
  • PrimaryFlag
  • EffectiveDate
  • PrimaryFlag
  • DateStart

Note:

In order to link your data using PersonNumber, PeriodOfServiceID, and AssignmentID, you must instruct your customer to update the configuration of the Person's Assignment Changed feed (empassignment) to include the PeriodOfServiceID in context. This must be updated for the following SourceObjectNames: CWKAssignmentDEO, ContractDEO, Employee Assignment, and PWAssignmentDEO. In order to add the PeriodOfServiceID to the empassignment feed, follow the instructions linked here. The correct configuration can be seen below.

WARNING:

Without configuring the Person Assignment Changed feed correctly, the context data does not provide enough information to structure the database.

Joiner Scenarios

Hire Worker

The newhire ATOM feed provides information about workers who are hired after the initial sync. The new hire will appear in the data feed on the effective date, not necessarily the date that the new hire is entered into the HCM system. The newhire JSON payload is displayed below. Use the empassignment feed for new hire assignment information.

ATOM: newhire

<entry> <title type="text"> <![CDATA[Meyerson, Barbara Hired]]> </title> <summary type="text"> <![CDATA[Employee Period of Service Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100589785737", "PersonName" : "Meyerson, Barbara", "PersonNumber" : "966169008890206", "PrimaryPhoneNumber" : "", "PersonId" : "300100589785723", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "EffectiveStartDate" : "2023-06-29", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PersonNumber" : "300100589785723" }, { "DateStart" : "2023-06-29" } ] }]]>

ATOM: empassignment

<entry> <title type="text"> <![CDATA[Meyerson, Barbara's Assignment Created]]> </title> <summary type="text"> <![CDATA[Person Contract Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "ContractId" : "300100589785746", "PersonName" : "Meyerson, Barbara", "PersonNumber" : "966169008890206", "PrimaryPhoneNumber" : "", "PersonId" : "300100589785723", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "AssignmentId" : "300100589785738", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PeriodOfServiceId" : "300100589785737" } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonNamePeriodType WorkerType EffectiveStartDate

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate
966169008890206 300100589785737 300100589785738 Meyerson, Barbara E EMP 2023-06-29
Add Pending Worker

A pending worker is a person who's yet to start employment and doesn't have a person record in the application. You create a pending worker record with a date that's effective before the hire date.

When a pending worker is added, the newhire feed returns the following personal and employment information. Use the empassignment feed for new hire assignment information.

ATOM: newhire

<entry> <title type="text"> <![CDATA[Gainsboro, Jennifer Hired]]> </title> <summary type="text"> <![CDATA[Pending Worker Period of Service Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100589792532", "PersonName" : "Gainsboro, Jennifer", "PersonNumber" : "966169008890210", "PrimaryPhoneNumber" : "", "PersonNumber" : "300100589792517", "PeriodType" : "P", "WorkerType" : "PWK", "DMLOperation" : "INSERT", "EffectiveStartDate" : "2023-06-29", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PersonNumber" : "300100589792517" }, { "DateStart" : "2023-06-29" } ] }]]>

ATOM: empassignment

<entry> <title type="text"> <![CDATA[Gainsboro, Jennifer's Assignment Created]]> </title> <summary type="text"> <![CDATA[Person Contract Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "ContractId" : "300100589792542", "PersonName" : "Gainsboro, Jennifer", "PersonNumber" : "966169008890210", "PrimaryPhoneNumber" : "", "PersonId" : "300100589792517", "PeriodType" : "P", "WorkerType" : "PWK", "DMLOperation" : "INSERT", "AssignmentId" : "300100589792533", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PeriodOfServiceId" : "300100589792532" } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate
966169008890210 300100589792532 300100589792533 Gainsboro, Jennifer P PWK 2023-06-29
Rehire Worker

When a worker is rehired, a new work relationship is created for an existing person. The newhire feed will share the same information for any hired employee included below. To identify the hire as a rehire, you must check your data for an existing PersonNumber. Use the empassignment feed for new hire assignment information.

ATOM: newhire

<entry> <title type="text"> <![CDATA[Goode, Rachel Hired]]> </title> <summary type="text"> <![CDATA[Employee Period of Service Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100592814666", "PersonName" : "Goode, Rachel", "PersonNumber" : "966169008890235", "PrimaryPhoneNumber" : "", "PersonId" : "300100591067571", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "EffectiveStartDate" : "2023-06-30", "EffectiveDate" : "2023-07-03" } ], "Changed Attributes" : [ { "PersonNumber" : "300100591067571" }, { "DateStart" : "2023-07-03" } ] }]]>

ATOM: empassignment

<entry> <title type="text"> <![CDATA[Goode, Rachel's Assignment Created]]> </title> <summary type="text"> <![CDATA[Person Contract Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "ContractId" : "300100592814675", "PersonName" : "Goode, Rachel", "PersonNumber" : "966169008890235", "PrimaryPhoneNumber" : "", "PersonId" : "300100591067571", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "AssignmentId" : "300100592814667", "EffectiveDate" : "2023-07-03" } ], "Changed Attributes" : [ { "PeriodOfServiceId" : "300100592814666" } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate Terminated ActualTerminationDate
966169008890235 Goode, Rachel E EMP 2023-06-21 Y 2023-07-03

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate Terminated ActualTerminationDate
966169008890235 300100592814666 300100592814667 Goode, Rachel E EMP 2023-06-21 N

Mover Scenarios

Convert Pending Worker

When a pending worker is converted to either an employee or contingent worker, the newhire feed returns the following information. Use the empassignment feed for assignment information.

ATOM: newhire

<entry> <title type="text"> <![CDATA[Gainsboro, Jennifer Hired]]> </title> <summary type="text"> <![CDATA[Employee Period of Service Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100589792959", "PersonName" : "Gainsboro, Jennifer", "PersonNumber" : "966169008890210", "PrimaryPhoneNumber" : "", "PersonId" : "300100589792517", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "EffectiveStartDate" : "2023-06-29", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PersonNumber" : "300100589792517" }, { "DateStart" : "2023-06-29" } ] }]]>

ATOM: empassignment

<entry> <title type="text"> <![CDATA[Gainsboro, Jennifer's Assignment Created]]> </title> <summary type="text"> <![CDATA[Person Contract Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "ContractId" : "300100589792969", "PersonName" : "Gainsboro, Jennifer", "PersonNumber" : "966169008890210", "PrimaryPhoneNumber" : "", "PersonId" : "300100589792517", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "AssignmentId" : "300100589792960", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PeriodOfServiceId" : "300100589792959" } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate
966169008890210 300100589792532 300100589792533 Gainsboro, Jennifer P PWK 2023-06-29

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate
966169008890210 300100589792532 300100589792533 Gainsboro, Jennifer E EMP 2023-06-29
Work Relationship Change

For example, when the primary work relationship is updated, we observe the following changes.

ATOM: workrelshipupdate

<entry> <title type="text"><![CDATA[Gomez, Joe Work Relationship Updated]]></title> <summary type="text"><![CDATA[Employee Work Relationship Updated]]></summary> <content type="text"><![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100575314782", "PersonName" : "Gomez, Joe", "PersonNumber" : "966169008890196", "WorkEmail" : "sendmail-test-discard@oracle.com", "PrimaryPhoneNumber" : "966 016 7283904", "PersonId" : "300100575314616", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "UPDATE", "EffectiveStartDate" : "2023-06-01", "PrimaryFlag" : "Y", "EffectiveDate" : "2023-06-08" } ], "Changed Attributes" : [ { "PrimaryFlag" : { "old" : "N", "new" : "Y" } } ] }]]>

ATOM: workrelshipupdate

<entry> <title type="text"><![CDATA[Gomez, Joe Work Relationship Updated]]></title> <summary type="text"><![CDATA[Employee Work Relationship Updated]]></summary> <content type="text"><![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100575314628", "PersonName" : "Gomez, Joe", "PersonNumber" : "966169008890196", "WorkEmail" : "sendmail-test-discard@oracle.com", "PrimaryPhoneNumber" : "966 016 7283904", "PersonId" : "300100575314616", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "UPDATE", "EffectiveStartDate" : "2023-06-01", "PrimaryFlag" : "N", "EffectiveDate" : "2023-06-08" } ], "Changed Attributes" : [ { "PrimaryFlag" : { "old" : "Y", "new" : "N" } } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PrimaryFlag PeriodType WorkerType EffectiveStartDate
966169008890196 300100575314782 300100589792278 Gomez, Joe N E EMP 2023-06-01
966169008890196 300100575314628 300100589792930 Gomez, Joe Y E EMP 2023-06-01

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PrimaryFlag PeriodType WorkerType EffectiveStartDate
966169008890196 300100575314782 300100589792278 Gomez, Joe Y E EMP 2023-06-01
966169008890196 300100575314628 300100589792930 Gomez, Joe N E EMP 2023-06-01
Assignment Change

When a new assignment is created or updated, the empassignment feed returns the following.

ATOM: empassignment

<entry> <title type="text"> <![CDATA[Collins, Bert's Assignment Created]]> </title> <summary type="text"> <![CDATA[Person Assignment Created]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "AssignmentId" : "300100575317800", "PersonName" : "Collins, Bert", "PersonNumber" : "966169008890200", "WorkEmail" : "sendmail-test-discard@oracle.com", "PrimaryPhoneNumber" : "1 342 874-3921", "PersonId" : "300100575316056", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "INSERT", "EffectiveDate" : "2023-06-29" } ], "Changed Attributes" : [ { "PrimaryWorkTermsFlag" : "N" }, { "TimeNormalFinish" : "17:00" }, { "ActionCode" : "TEMP_ASG" }, { "AssignmentStatusType" : "ACTIVE" }, { "AssignmentType" : "E" }, { "Frequency" : "D" }, { "TimeNormalStart" : "08:00" }, { "BusinessUnitId" : "300100037658074" }, { "AssignmentName" : "E966169008890200" }, { "WorkAtHome" : "N" }, { "PrimaryAssignmentFlag" : "N" }, { "AssignmentId" : "300100575317800" }, { "NormalHours" : "8" }, { "EffectiveStartDate" : "2023-06-29" }, { "ManagerFlag" : "N" }, { "PersonTypeId" : "100010025072012" }, { "LegalEntityId" : "100000015338042" }, { "AssignmentNumber" : "E966169008890200-3" }, { "EffectiveEndDate" : "4712-12-31" }, { "PrimaryWorkRelationFlag" : "Y" } ], "FlexFields" : [ { "FlexFieldCode" : "PER_ASG_LEG_DDF", "ContextCode" : null, "Changed Attributes" : [ { "affordableHraOffered" : "N" }, { "affordableHraZipCode" : "Primary Residence" } ] } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PrimaryAssignmentFlag AssignmentStatusType PeriodType WorkerType EffectiveStartDate
966169008890200 300100591037852 300100591037853 Walsh, Scott Y ACTIVE E EMP 2023-06-30

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PrimaryAssignmentFlag AssignmentStatusType PeriodType WorkerType EffectiveStartDate
966169008890200 300100591037852 300100591037853 Walsh, Scott Y ACTIVE E EMP 2023-06-30
966169008890200 300100591037852 300100591067380 Walsh, Scott N ACTIVE E EMP 2023-06-30

Tip:

You can assume that newly created assignments will have ACTIVE status and that the first work relationship or assignment to be created will be primary unless otherwise noted.
Promote Worker

When an employee is promoted and there are changes to the employee's assignment information, the empupdate and empassignment feeds will provide information.

ATOM: empupdate, empassignment

<entry> <title type="text"> <![CDATA[King, Mary's Assignment Updated]]> </title> <summary type="text"> <![CDATA[Person Assignment Updated]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "AssignmentId" : "300100591078074", "PersonName" : "King, Mary", "PersonNumber" : "966169008890236", "PrimaryPhoneNumber" : "", "PersonId" : "300100591078054", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "UPDATE", "EffectiveDate" : "2023-06-30" } ], "Changed Attributes" : [ { "ActionCode" : { "old" : "HIRE", "new" : "PROMOTION" } }, { "AssignmentName" : { "old" : "E966169008890236", "new" : "AUTO_GHR_JOB03" } }, { "OrganizationId" : { "old" : null, "new" : "300100037658514" } }, { "PositionId" : { "old" : null, "new" : "300100037658660" } }, { "LocationId" : { "old" : null, "new" : "300100037658196" } }, { "JobId" : { "old" : null, "new" : "300100037658485" } } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate OrganizationId PositionId LocationID JobId
966169008890236 300100591078068 300100591078074 King, Mary E EMP 2023-06-30

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate OrganizationId PositionId LocationID JobId
966169008890236 300100591078068 300100591078074 King, Mary E EMP 2023-06-30 300100037658514 300100037658660 300100037658196 300100037658485

Tip:

In this case, the promotion updates the existing assignment, so we can assume that information excluded from changed attributes stays the same. This includes AssignmentId and PeriodOfServiceID.
Transfer Worker

When an employee is transferred, the empupdate and empassignment feeds will provide the same information about the transfer.

ATOM: empupdate, empassignment

<entry> <title type="text"> <![CDATA[Goode, Rachel's Assignment Updated]]> </title> <summary type="text"> <![CDATA[Person Assignment Updated]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "AssignmentId" : "300100591067591", "PersonName" : "Goode, Rachel", "PersonNumber" : "966169008890235", "PrimaryPhoneNumber" : "", "PersonId" : "300100591067571", "PeriodType" : "E", "WorkerType" : "EMP", "DMLOperation" : "UPDATE", "EffectiveDate" : "2023-06-30" } ], "Changed Attributes" : [ { "ActionCode" : { "old" : "HIRE", "new" : "TRANSFER" } }, { "BusinessUnitId" : { "old" : "300100037658147", "new" : "300100037658212" } }, { "AssignmentName" : { "old" : "E966169008890235", "new" : "AUTO_GHR_JOB07" } }, { "OrganizationId" : { "old" : null, "new" : "300100037658538" } }, { "PositionId" : { "old" : null, "new" : "300100037658684" } }, { "LocationId" : { "old" : null, "new" : "300100037658414" } }, { "JobId" : { "old" : null, "new" : "300100037658578" } } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate BusinessUnitId OrganizationId PositionId LocationId JobId
966169008890235 300100591067585 300100591067591 Goode, Rachel E EMP 2023-06-30 300100037658147

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate BusinessUnitId OrganizationId PositionId LocationId JobId
966169008890235 300100591067585 300100591067591 Goode, Rachel E EMP 2023-06-30 300100037658212 300100037658538 300100037658684 300100037658414 300100037658578

Tip:

In this case, we can infer that the PeriodOfServiceID and AssignmentID remain the same since no assignment or work relationship changes are noted in the feeds. Instead we observe changes related to an existing assignment.

Leaver Scenarios

Termination

There are two ways to terminate an employee. The first is by terminating them in the system. When an employee is terminated, the termination feed returns the following information. Note that the termination will appear in the feed on the effective date, not necessarily the date that the termination is entered into the system.

ATOM: termination

The second way to terminate an employee is by cancelling all of their work relationships. When a work relationship is cancelled, the cancelworkrelship feed will provide the following information. When a work relationship is cancelled, you must check if the employee has another active work relationship, or if they have been terminated.

ATOM: cancelworkrelship

<entry> <title type="text"> <![CDATA[Goode, Rachel's Work Relationship Cancelled]]> </title> <summary type="text"> <![CDATA[Person Work Relationship Cancelled]]> </summary> <content type="text"> <![CDATA[{ "Context" : [ { "PeriodOfServiceId" : "300100591067585", "PersonName" : "Goode, Rachel", "PersonNumber" : "966169008890235", "PrimaryPhoneNumber" : "", "PersonId" : "300100591067571", "PeriodType" : "E", "WorkerType" : "E", "DMLOperation" : "DELETE", "EffectiveStartDate" : "2023-06-30", "PrimaryFlag" : "Y", "EffectiveDate" : "2023-07-03" } ], "Changed Attributes" : [ { "PeriodOfServiceId" : "300100591067585" }, { "ActionOccurrenceId" : "300100591067584" } ] }]]>

Before

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate Terminated ActualTerminationDate
966169008890235 300100591067585 300100591067591 Goode, Rachel E EMP 2023-06-30 N

After

PersonNumber PeriodOfServiceId AssignmentId PersonName PeriodType WorkerType EffectiveStartDate Terminated ActualTerminationDate
966169008890235 Goode, Rachel E EMP 2023-06-30 Y 2023-07-03

Tip:

When an employee has no work relationships, we can infer that the employee has been terminated.

Updating HCM

WARNING:

SCIM APIs should only be used to make necessary changes to HCM data including username or user email information to support SSO functionality.

Steps for updating HCM

  1. Get relevant user or role IDs needed to make desired updates
  2. Make a bulk API call to update username, email, or role information as needed
Bulk API Calls

Bulk API calls allow you to perform multiple operations at the same time and reduces strain on the system. Use the following path to make bulk API calls.

https://<host>:<port>/hcmRestApi/scim/Bulk

In the request include the following parameters:

  1. method: the type of operation being performed (ex: POST, PATCH)
  2. path: relative path of the resource
  3. data: resource data as it would appear for the POST or PATCH resource operation
  4. bulkId: identifier for a newly created resource, unique within the bulk request and created by the client

SCIM API request

{ "Operations":[ { "method":"PATCH", "path":"/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "bulkId":"clientBulkId1", "data":{ "schemas":[ "urn:scim:schemas:core:2.0:User" ], "userName":"Rachel.Goode" } }, { "method":"PATCH", "path":"/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "bulkId":"clientBulkId1", "data":{ "schemas":[ "urn:scim:schemas:core:2.0:User" ], "emails":[ { "value":"rachel.goode@adcdat05.us.oracle.com", "type":"W", "primary": true } ] } } ] }

SCIM API response

{ "schemas": [ "urn:scim:schemas:core:2.0:Bulk" ], "Operations": [ { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "method": "PATCH", "bulkId": "clientBulkId1", "status": { "code": "200" } }, { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "method": "PATCH", "bulkId": "clientBulkId1", "status": { "code": "500", "description": "PER_IIP_2410-Error occured while updating MasteredIn Flag" } } ] }
Get user ID

Make a GET call to the SCIM API to identify the user ID of the user you'd like to update. Users can be identified by their personNumber as seen below. Make calls in sets of 6 as demostrated below to reduce strain on the system.

https://:/hcmRestApi/scim/Users?filter=personNumber eq "<personNumber1>" or personNumber eq "<personNumber2>" or personNumber eq "<personNumber3>" or personNumber eq "<personNumber4>" or personNumber eq "<personNumber5>" or personNumber eq "<personNumber6>"

An example response is shown below. The ID on line 6 will be used to make user related updates.

{ "itemsPerPage": 2, "startIndex": 1, "Resources": [ { "id": "FE8B6B1DE81A22FFE053A3561BACA0B5", "meta": { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81A22FFE053A3561BACA0B5", "resourceType": "User", "created": "2023-06-30 18:05:51.000", "lastModified": "2023-07-04 09:07:17.000" }, "schemas": [ "urn:scim:schemas:core:2.0:User", "urn:scim:schemas:extension:fa:2.0:faUser" ], "userName": "Mary.King", "name": { "familyName": "Hamilton", "givenName": "Mary" }, "displayName": "Mary Hamilton", "preferredLanguage": "en", "active": true, "roles": [ { "id": "40C4AE052EC2582286A6A0FB1514656C", "displayName": "Employee", "description": "Identifies the person as an employee.", "value": "ORA_PER_EMPLOYEE_ABSTRACT" } ], "urn:scim:schemas:extension:fa:2.0:faUser": { "workerInformation": { "personNumber": "966169008890236", "manager": "null", "job": "AUTO_GHR_JOB03", "businessUnit": "AUTO_GHR_BUSINESS UNIT02", "department": "AUTO_GHR_DEPARTMENT03" }, "userCategory": "DEFAULT", "accountType": "Person", } }, { "id": "FE8B6B1DE81922FFE053A3561BACA0B5", "meta": { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "resourceType": "User", "created": "2023-06-30 16:42:59.000", "lastModified": "2023-07-10 21:21:08.361" }, "schemas": [ "urn:scim:schemas:core:2.0:User", "urn:scim:schemas:extension:fa:2.0:faUser" ], "userName": "Rachel.Goode", "name": { "familyName": "Goode", "givenName": "Rachel" }, "displayName": "Rachel Goode", "preferredLanguage": "en", "active": true, "emails": [ { "primary": true, "type": "W", "value": "rachel.goode@adcdat05.us.oracle.com" } ], "roles": [ { "id": "40C4AE052EC2582286A6A0FB1514656C", "displayName": "Employee", "description": "Identifies the person as an employee.", "value": "ORA_PER_EMPLOYEE_ABSTRACT" } ], "urn:scim:schemas:extension:fa:2.0:faUser": { "workerInformation": { "personNumber": "966169008890235", "manager": "null", "department": "null" }, "userCategory": "DEFAULT", "accountType": "Person", } }, ... ] }
Get Role ID

Make a GET call to the SCIM API using the role name of the role you want to update to identify the role ID.

https://<host>:<port>/hcmRestApi/scim/Roles?filter=name eq "<role name>"

The response for role name "ORA_PER_HUMAN_RESOURCE_ANALYST_JOB" shown below. The id on line 6 will be used to make role related updates.

{ { "itemsPerPage": 1, "startIndex": 1, "Resources": [ { "id": "55361929311C580B560EB8BA5C4C1886", "meta": { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Roles/55361929311C580B560EB8BA5C4C1886", "resourceType": "Role", "created": "2009-05-12 11:27:39.226", "lastModified": "2023-07-07 10:07:02.788" }, "schemas": [ "urn:oracle:apps:scim:schemas:fa:1.0:Role" ], "name": "ORA_PER_HUMAN_RESOURCE_ANALYST_JOB", "displayName": "Human Resource Analyst", "description": "Performs duties of a human resources analyst.", "category": "JOB", "members": [ { "value": "66CDCB0BCBF6A655E050F80AD42D67A7" }, { "value": "66CDCB583FF13502E050F80AD42D67F7" }, { "value": "66CDCB0BCAA1A655E050F80AD42D67A7" }, ... ] } ] }
Update User Username

Identify the user's ID and patch the updated data as a JSON in the body of the request with the follow schema structure and appropriate authorization.

https://<host>:<port>/hcmRestApi/scim/Users/<user ID>
{ "schemas":[ "urn:scim:schemas:core:2.0:User" ], "userName":"<username>" }

Example response data shown below.

{ "id": "FE8B6B1DE81922FFE053A3561BACA0B5", "meta": { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "resourceType": "User", "created": "2023-06-30 16:42:59.000", "lastModified": "2023-07-03 18:37:29.535" }, "schemas": [ "urn:scim:schemas:core:2.0:User", "urn:scim:schemas:extension:fa:2.0:faUser" ], "userName": "Rachel.Goode", "name": { "familyName": "Goode", "givenName": "Rachel" }, "displayName": "Rachel Goode", "preferredLanguage": "en", "active": true, "emails": [ { "primary": true, "type": "W", "value": "rachel.goode@adcdat05.us.oracle.com" } ], "roles": [ { "id": "40C4AE052EC2582286A6A0FB1514656C", "displayName": "Employee", "description": "Identifies the person as an employee.", "value": "ORA_PER_EMPLOYEE_ABSTRACT" } ], "urn:scim:schemas:extension:fa:2.0:faUser": { "workerInformation": { "personNumber": "966169008890235", "manager": "null", "businessUnit": "AUTO_GHR_BUSINESS UNIT02", "department": "null" }, "userCategory": "DEFAULT", "accountType": "Person", } }
Update User Email

Identify the user's ID and patch the updated data as a JSON in the body of the request with the follow schema structure and appropriate authorization.

https://<host>:<port>/hcmRestApi/scim/Users/<user ID>
{ "schemas":[ "urn:scim:schemas:core:2.0:User" ], "emails": [ { "value": "<email>", "type": "W", "primary": true } ] }

Example response data shown below.

{ "id": "FE8B6B1DE81922FFE053A3561BACA0B5", "meta": { "location": "https://fa-eqmp-pintlabfadev.fa.ocs.oc-test.com:443/hcmRestApi/scim/Users/FE8B6B1DE81922FFE053A3561BACA0B5", "resourceType": "User", "created": "2023-06-30 16:42:59.000", "lastModified": "2023-07-03 18:29:29.264" }, "schemas": [ "urn:scim:schemas:core:2.0:User", "urn:scim:schemas:extension:fa:2.0:faUser" ], "userName": "RACHEL.GOODE", "name": { "familyName": "Goode", "givenName": "Rachel" }, "displayName": "Rachel Goode", "preferredLanguage": "en", "active": true, "emails": [ { "primary": true, "type": "W", "value": "rachel.goode@adcdat05.us.oracle.com" } ], "roles": [ { "id": "40C4AE052EC2582286A6A0FB1514656C", "displayName": "Employee", "description": "Identifies the person as an employee.", "value": "ORA_PER_EMPLOYEE_ABSTRACT" } ], "urn:scim:schemas:extension:fa:2.0:faUser": { "workerInformation": { "personNumber": "966169008890235", "manager": "null", "businessUnit": "AUTO_GHR_BUSINESS UNIT02", "department": "null" }, "userCategory": "DEFAULT", "accountType": "Person", } }
Add Role to User

Identify the user ID and role ID to make a patch with the updated data as a JSON in the body of the request with the follow schema structure and appropriate authorization.

https://<host>:<port>/hcmRestApi/scim/Roles/<role ID>
{ "schemas":[ "urn:oracle:apps:scim:schemas:fa:1.0:Role" ], "members":[ {"value":<user id>", "operation":"ADD"} ] }
Remove Role to User

Identify the user ID and role ID to make a patch with the updated data as a JSON in the body of the request with the follow schema structure and appropriate authorization.

https://<host>:<port>/hcmRestApi/scim/Roles/<role ID>
{ "schemas":[ "urn:oracle:apps:scim:schemas:fa:1.0:Role" ], "members":[ {"value":<user id>", "operation":"REMOVE"} ] }

Complete user API documentation linked here.

Segregation of Duties (SoD)

Purpose:

Provisioning access to employees must comply with Financial Separation of Duties (SoD) and restrictive use access controls to meet SOX and other ICFR mandates. This is particularly important for user access to Fusion ERP and EPM modules. The orchestration of the access can be done with Auto Provisioning and Advanced Access Requests within Fusion or using 3rd party systems for managing entitlements, provisioning or IDM across multiple apps.

This section explains how 3rd party systems can integrate Fusion web services to manage SoD and sensitive access risk before and after provisioning roles to users.

There are three steps to using Fusion SoD webservices for user access requests:
Step 1 - Initiate Access Request for Fusion

Initiate access request for one or more Fusion Roles, and if needed, security context values (MDA). In this step, HR events such as joiner, movers and leavers triggers Fusion Role requests. Access requests for Fusion ERP include both functional and data security permissions (MDA). Note that the access request for Fusion should not be provisioned until Steps 2 and 3 below are complete. It could be the case that the access request includes a significant violation of SoD controls and should not be provisioned.

Step 2 - Analyze for SoD and access violations

Analyze access request for potential SOD and sensitive access controls violations. Use Fusion Risk Management APIs to simulate SOD analysis if Fusion roles are approved. The results of the webservice automatically include the user's current Fusion Roles and data security assignments in the analysis. The Fusion SOD engine also unbundles nested Fusion roles and data security values for fine grain analysis required by auditors.

Perform analysis
POST https://servername.fa.us2.oraclecloud.com/fscmRestApi/resources/11.13.18.05/advancedControlsRolesProvisioning/action/runUserProvisioningAnalysis
{ "userName":"AP_Manager", "roleAndAttributes":{ "GTG_ENTERPRISE_RISK_AND_CONTROL_MANAGER_JOB":[ "BUSINESS_UNIT = Vision China", "LEDGER_SET = Vision Italy" ], "ORA_GTG_APPLICATION_ACCESS_AUDITOR_JOB":[ "LEDGER_SET = FR Ledger", "LEDGER_SET = Progress FR", "Location = NA" ] } }

Example response data shown below.

{ "result": "1" }
Get Status
POST https://servername.fa.us2.oraclecloud.com/fscmRestApi/resources/11.13.18.05/advancedControlsRolesProvisioning/action/getRequestStatus
{ "requestId": "1" }

Example response data shown below.

{ "result": "Job Completed>" }
Get Result
GET https://servername.fa.us2.oraclecloud.com/fscmRestApi/resources/11.13.18.05/advancedControlsRolesProvisioning/advancedControlsRolesProvisioning/{advancedControlsRolesProvisioningUniqID}

Example response data shown below.

{ "controlId": 86731, "controlName": "Enter journal and view risk", "inputRoleCode": "PROV_TEST_ROLE2", "inputRoleName": Prov Test Role2", "incidentPath": "Enter Journal By Spreadsheet", "conflictingRole": "Prov Test Role1", "links": [ { "rel": "self", "href": "https://servername.fa.us2.oraclecloud.com/fscmRestApi/resources/11.13.18.05/advancedControlsRolesProvisioning/14", "name": "advancedControlsRolesProvisioning", "kind": "item" }, { "rel": "canonical", "href": "https://servername.fa.us2.oraclecloud.com/fscmRestApi/resources/11.13.18.05/advancedControlsRolesProvisioning/14", "name": "advancedControlsRolesProvisioning", "kind": "item" } ] }
Step 3 - Provision approved roles and document exceptions

For no violations in step 2, complete or grant roles. For violations in step 2, route details to relevant process owners for review and comments. If the process owner accepts the violations, update the status of access incidents to "approved" including justification comments in Fusion Risk Management for audit reporting. If the process owner does not accept a particular violation, do not provision that Fusion Role. Note that a single Access Request can have multiple Fusion Roles. The SOD violation is calculated at the role level. So, for a given Access Request, you may provision some Fusion Roles and deny the rest.

For a comprehensive guide on Fusion security best practices and step-by-step instructions, please review this POST
To Run all advanced controls jobs review this documentation

Related resources mentioned in this document

Acknowledgements

  • Authors - Haley Wixom (Product Management Intern, Human Capital Management), Girish Anantharaju (Director, Product Management, Fusion Applications Security)

More Learning Resources

Explore other labs on docs.oracle.com/learn or access more free learning content on the Oracle Learning YouTube channel. Additionally, visit education.oracle.com/learning-explorer to become an Oracle Learning Explorer.

For product documentation, visit Oracle Help Center.