Integrating with ADP | A-Z

High-Level Requirements

  1. Cloud Elements customer is already an ADP Partner or is actively pursuing a partnership with ADP.
  2. ADP Partner has completed a security review with ADP (integration with Cloud Elements satisfies this requirement).
  3. ADP Partner sandbox credentials have been provided to Partner (ClientID, ClientSecret, SSL Certs, SSL Cert Private Key).
  4. ADP Partner has requested APIs required for integration to be enabled on their ADP sandbox.
  5. With steps 1-3 completed, Cloud Elements can begin development and enhancing our community ADP element.
  6. ADP Partner is required to build ADP Marketplace Application (this cannot be handled by Cloud Elements, although we can provide consulting and assistance).
  7. ADP Partner goes through Marketplace Flow review with ADP.
  8. ADP Marketplace Application is published to ADP Marketplace for public consumption.

Technical Deep Dive

In this article, we will articulate the processes 

  • Authenticating the ADP element
  • ADP Marketplace Flow
  • ADP Marketplace Flow with Cloud Elements Architecture | Instance Creation and making API calls on behalf of an end customer

Authenticating the ADP element

  1. Locate the ADP SSL Certificate and Private Key

The ADP element requires a few extra steps to authenticate. The Cloud Elements customer will receive credentials including an SSL Certificate and SSL Certificate Private Key. If you're not sure what these are, they should be text files that end in .pem, .p7b, .key .cer

The files should look something like this. Note that the base64 encoded string will be much longer; they are shortened for visibility below.


We'll also need a Private Key; this is sometimes also in the .pem file, but may also be a separate .key file

The Private Key should look something like this:

2. Create a Base64 encoded JavaKeystore

Using the SSL Certificate file and the SSL Certificate Private Key files, follow the steps to create a Base64 Encoded JavaKeystore for use with the ADP element as articulated in this article.

ADP Marketplace Flow

ADP requires that all of its partners put a solution on the ADP Marketplace (Cloud Elements excluded); as a Cloud Elements, customer this will be a requirement in order to offer ADP integrations.

The diagram below shows the ADP Marketplace Subscription Flow, this is how a new end user will enable the ADP integration. For example, if Cloud Elements customer "CECustomerZ" offers and integration and "EndCustomerX" subscribes to the CECustomerZ ADP Marketplace offering, these are the technical steps that need to occur. Note that ADP does not manage who has subscribed and who hasn't; CECustomerZ is responsible for managing who has subscribed and who hasn't and respond to ADP accordingly regarding whether or not the user should be able to subscribe.

Although the above diagram may be complicated, the steps are articulated below, with each number lining up with that of the diagram:
  1. EndCustomerX clicks subscribe to the CECustomerZ ADP Marketplace Application in the ADP Marketplace

1.1. A webhook notification is sent from ADP to CECustomerZ (not through Cloud Elements). The webhook will contain a simple notification indicating that something happened but containing no event data, it will have a query parameter on the HTTP POST request of an eventUrl which we will call next to retrieve the actual event data. The incoming webhook will look like this:

HTTP POST to https://{CECustomerZ-WebhookURL}?eventUrl=https://apps.adp.com/api/integration/v1/events/7462383-2827472-362454528

Headers of HTTP POST 

{
"oauth_consumer_key":"CECustomerZ-api-54884",
"oauth_nonce":"-6388782544256055801",
"oauth_signature":"zQFPcCTRK+4ibhpH7HWL/QXzhTY=",
"oauth_signature_method":"HMAC-SHA1",
"oauth_timestamp":"1558553959",
"oauth_version":"1.0",

Do NOT respond to this GET request with the eventURL, your server needs to hang for many seconds and wait while we complete steps 2.1-3 before we can respond. Failure to do so will cause downstream API failures.

2. Make an Oauth1 Signed GET request to the eventUrl from step 1.1, in our example this is https://apps.adp.com/api/integration/v1/events/7462383-2827472-362454528
To make a signed GET request, you'll need one extra parameter oauth_consumer_key which can be found in CECustomerZ's ADP Marketplace where they are developing their marketplace app. This will need to be included along with the rest of the Oauth1 signature. For more info on Oauth1 signed requests see the Oauth1 docs: https://oauth1.wp-api.org/docs/basics/Signing.html
2.1 If the Signed GET request is valid to the eventUrl, the event data will be returned. The event data will contain the required parameter organizationOID and associateOID  which are required to manage who is subscribed and who is not subscribed in CECustomerZ's database.
Example Event data response from the signed GET request to the eventUrl:
{
                "type":"SUBSCRIPTION_ORDER",
                "marketplace":{
                  "partner":"ADP",
                  "baseUrl":"https://apps.adp.com"
                },
                "applicationUuid":null,
                "flag":"DEVELOPMENT",
                "creator":{
                  "uuid":"xxxxxxxxxxxxxxx",
                  "openId":"https://apps.adp.com/openid/id
              /xxxxxxx",
                               "email":"xxxxx",
                            "firstName":"xxxxx",
                            "lastName":"xxxxx",
                            "language":"en",
                            "locale":"en-US",
                            "address":null,
                            "attributes":null
                          },
                          "payload":{
                            "user":null,
                            "company":{
                              "uuid":"xxxxxxxxxxx",
                              "externalId":"G2C35DY4DKE133Y8",
                              "name":"xxxxxxx",
                              "email":null,
                              "phoneNumber":null,
                              "website":null,
                              "country":"US"
                            },
                            "account":null,
                            "addonInstance":null,
                            "addonBinding":null,
                            "order":{
                              "editionCode":"FREE",
                              "addonOfferingCode":null,
                              "pricingDuration":"MONTHLY",
                              "items":[],
                              "customAttributes":[]
Page 27 of 54 ADP and the ADP logo are registered trademarks of ADP, LLC. ADP A more human resource. is a service mark of ADP, LLC. Copyright © 2016 ADP, LLC.
adp.com
 
},
                      "notice":null,
                      "configuration":{
                        "organizationOID":"xxxxxxx",
                        "applicationID":null,
                        "associateOID":"xxxxxxx"
} },
                    "returnUrl":null,
                    "links":[]
}


2.1.2. This step is not described in the diagram above but is necessary to complete. Since ADP does not manage who has subscribed and who has not, once you retrieve the eventUrl data above, CECustomerZ will check in CECustomerZ's database to see if that OrganizationOID for EndCustomerX has already subscribed. This means these are the unique identifiers you should pair with CECustomerZ's application unique identifiers to manage a 1:1 relationship of customers in CECustomerZ's app to subscribers of the CECustomerZs' ADP Marketplace App.

3. Remember how in step 1.1 we said not to respond to the webhook just yet? Now we will. After we decide whether EndCustomerX has already subscribed or not we will respond to ADP letting them know whether to proceed with the subscription order of CECustomerXs' ADP Marketplace App. Either respond success or failure, where accountIdentifier is the OrganizationOID

Example Webhook Response to step 1.1


3.1. ADP will let EndCustomerX know whether the subscription order has processed or failed based on the webhook response in step 3.

This concludes the marketplace work handled by CECustomerZ.


ADP Marketplace Flow with Cloud Elements Architecture | Instance Creation and making API calls on behalf of an end customer


Now that EndCustomerX has successfully subscribed to CECustomerZ's ADP Marketplace App, we still need to retrieve the ClientID and ClientSecret for that customer so we can create an instance for EndCustomerX and make API calls on their behalf. 

  1. Make an API call to the ADP element GET /consumer-application-subscription-credentials. This should be done on an ADP element instance authenticated with CECustomerZ's ADP API credentials. You'll need the OrganizationOID from the last set of steps. 
  2. In the response retrieve the ClientID and ClientSecret for EndCustomerX

Example Response:

3. Finally, make an instance and provide the new ClientID and ClientSecret to authenticate on behalf of EndCustomerX and start making API calls on their behalf! 

4. Done!!!