Overview

This guide explains how to integrate Gradial with Adobe Experience Manager (AEM) 6.5. AEM 6.5 supports multiple authentication methods, with OAuth 2.0 being the preferred approach for enhanced security and granular access control.

Authentication Methods

AEM 6.5 supports two primary authentication methods for external integrations:

OAuth 2.0 Client (Preferred)

Recommended approach offering fine-grained access control through custom OAuth scopes. Provides better security, audit trails, and permission management.

Basic Authentication

Secondary option using username/password credentials. Simpler to implement but less secure and granular than OAuth.
OAuth 2.0 is strongly recommended for production environments due to its superior security model, token-based authentication, and granular permission controls.

OAuth 2.0 Integration Steps

Basic OAuth integration includes:
  1. Creating and configuring an OAuth client
  2. Defining custom OAuth scopes and assigning them appropriate permissions
  3. Configuring user permissions for scope access
  4. Granting the oauthservice user the same privileges (plus access control privileges)
  5. Providing Gradial with the OAuth client credentials (and private key if 2-legged OAuth)

OAuth 2.0 Technical Details

AEM supports two OAuth authentication flows:

On-behalf-of (3-legged)

Tied to individual user permissions. This flow requires user authentication and consent.

Service-to-service (2-legged)

Machine-to-machine communication with no user intervention. Uses JWT tokens for authentication.
Gradial’s access is always additionally governed by custom-defined OAuth scopes.

Integration Steps

1

Create an OAuth Client

  1. Log in as an admin or service account
  2. Go to <AEM-HOST>/libs/granite/oauth/content/clients.html, click Create
  3. Name the client (e.g., Gradial)
  4. For 3-legged OAuth, set the redirect to: https://www.gradial.com/api/v1/auth/aem65/oauth2/callback
  5. Obtain the Client ID and Secret and share them securely with Gradial
Always keep OAuth credentials secure and never share them in public repositories or documentation.
2

Define Custom OAuth Scopes

What are OAuth Scopes?OAuth scopes are Java classes that define specific permissions for API access. Each scope:
  • Maps to specific JCR paths in your AEM repository
  • Defines the exact privileges (read, write, version management, etc.)
  • Controls what operations the OAuth client can perform
  • Appears in user consent dialogs during authorization
Example Scope ImplementationThe following complete example demonstrates how to create an OAuth scope for asset upload permissions:
This example demonstrates:
  • Asset upload permissions to /content/dam
  • Required JCR privileges (read, write, lock management, version management)
  • Proper OSGi component configuration
  • User-friendly description for consent dialogs
Standard Scopes for Gradial IntegrationThe typical set of scopes Gradial requires:
  • ReadAllScope.java: Read access to / for component/template definitions, dynamic media publishing, etc.
  • AuthorLaunchesScope.java: Create and manage launches at /content/launches
  • AuthorTagsScope.java: Create and manage tags at /content/cq:tags
  • AssetsUploadScope.java: Upload assets to /content/dam
  • AssetsPublishScope.java: Publish assets from the DAM
Custom Scope Development for Multi-Site EnvironmentsTechnical Requirement: Each unique content path or permission requirement needs its own OAuth scope class. This is a development task that requires creating, compiling, and deploying Java classes.

When You Need Custom Scopes

Multi-Site Architecture:
  • If your AEM instance manages multiple websites with different permission boundaries
  • When authors have access to specific sites but not others
  • Example: Authors for Site A can access /content/sitea but not /content/siteb
Specialized Content Types:
  • Experience Fragments with site-specific access patterns
  • Campaign content with restricted access
  • Multi-brand environments with separate governance
Permission Granularity:
  • Different operations (read vs write) for different content areas
  • Workflow-specific permissions (launches vs direct editing)
  • Integration-specific requirements (publish vs author operations)

Scope Creation Examples

Example 1: Site-Specific Author Scopes
// Site A Author Scope
private static final String RESOURCE_URI = "/content/sitea";
private static final String SCOPE_NAME = "sitea_author";

// Site B Author Scope  
private static final String RESOURCE_URI = "/content/siteb";
private static final String SCOPE_NAME = "siteb_author";
Example 2: Experience Fragment Scopes
// Site-specific Experience Fragments
private static final String RESOURCE_URI = "/content/experience-fragments/sitea";
private static final String SCOPE_NAME = "sitea_experience_fragments";
Example 3: Operation-Specific Scopes
// Read-only content access
private static final String RESOURCE_URI = "/content/sitea";
private static final String SCOPE_NAME = "sitea_read_only";
// Only includes PrivilegeConstants.JCR_READ in getPrivileges()

// Full authoring access
private static final String RESOURCE_URI = "/content/sitea";  
private static final String SCOPE_NAME = "sitea_full_author";
// Includes JCR_READ, REP_WRITE, JCR_LOCK_MANAGEMENT, etc.

Engineering Implementation Process

Step 1: Analyze Your Content Architecture
  • Map out all content paths that need different access controls
  • Identify user groups and their permission boundaries
  • Document required operations per content area
Step 2: Design Scope Classes
  • Create one scope class per unique permission requirement
  • Name scopes descriptively (e.g., SiteAAuthorScope, SiteBExperienceFragmentScope)
  • Set appropriate RESOURCE_URI and privilege combinations
Step 3: Development and Deployment
  1. Create Java Classes: Base each on the ExampleScope.java template above
  2. Compile to OSGi Bundle: Package all scopes into a single bundle
  3. Deploy to AEM: Install bundle on all author instances
  4. Verify Registration: Check OAuth client configuration shows new scopes
  5. Test Access: Validate each scope grants expected permissions
Step 4: Permission Alignment
  • Ensure authenticating users have JCR permissions matching each scope’s RESOURCE_URI
  • Update user group memberships to align with scope boundaries
  • Test OAuth authorization with different user accounts
Each scope must have a corresponding user permission. If a scope grants access to /content/sitea but the authenticating user lacks permissions to that path, OAuth authorization will fail.
This is a one-time engineering effort per AEM environment. Once scopes are deployed, they can be reused across multiple OAuth clients and integrations.

Alternative: Dynamic Scopes Package

Simplified Scope Management OptionFor organizations that prefer to avoid custom Java development, Gradial offers a pre-built dynamic scopes package that enables scope configuration through OSGi settings instead of code deployment.Benefits of Dynamic Scopes:
  • No Java development required
  • Configure scopes via OSGi configuration files
  • Update scope permissions without code deployments
  • Ideal for environments with limited development resources
  • Supports the same permission granularity as custom scopes
How It Works:
  • Deploy Gradial’s dynamic scopes OSGi bundle once
  • Create scope configurations using OSGi .config files
  • Define resource paths and permissions declaratively
  • Manage scope changes through configuration management
Interested in Dynamic Scopes? Contact your Gradial representative to learn more about the dynamic scopes package and whether it’s suitable for your environment and requirements.
Gradial can provide additional scope templates for specific use cases if needed.
3

Configure User Permissions

Who performs this step: AEM Administrator or user with security administration privilegesOAuth scopes only work if the authenticating user has the corresponding JCR permissions. This section details the permissions required for both the authenticating user and the oauthservice system user.

Required JCR Permissions

The authenticating user needs specific read and write permissions that match your OAuth scope definitions:Read Permissions Required:
  • /apps - Application configurations and components
  • /bin - Binary servlets and utilities
  • /conf - Configuration settings
  • /content - All content areas
  • /libs - System libraries
Write Permissions Required:
  • /content/launches - For launch-based workflows (default)
  • OR /content/<your-website-path> - Direct content modification (if not using launches)
  • /content/dam - Digital Asset Management operations
  • /content/cq:tags - Tag management
Special Permissions Required:
  • jcr:versionManagement on /content/launches - Required for version control operations on launches
  • jcr:lockManagement on relevant paths - Required for content locking during edits

Permission Assignment for Authenticating Users

The user who authorizes OAuth access must have permissions that match the requested scopes:
  1. Navigate to AEM Security Console
    • Go to ToolsSecurityUsers
    • Locate the user account that will authorize OAuth access
  2. Assign to Author Groups
    • Add the user to appropriate author groups
    • Ensure the groups have permissions matching your OAuth scopes
  3. Verify Scope Alignment
    • If your scope grants access to /content/mysite, ensure the user has author permissions for that path
    • If using asset scopes, ensure the user can upload/manage assets in the corresponding DAM folders
OAuth authorization will fail if the authenticating user lacks permissions for the requested scopes. The user must have at least the same permissions defined in your OAuth scope classes.

Permission Verification

Test user permissions before OAuth configuration:
  1. Access Control Testing
    • Navigate to <AEM-HOST>:<PORT>/security/permissions.html
    • Search for the user account
    • Verify permissions match your OAuth scope paths
  2. Content Access Testing
    • Log in as the user and verify they can access/modify content in scope paths
    • Test launch creation if using launch-based workflows
    • Test asset upload if using DAM scopes
4

Configure oauthservice System User Permissions

About the oauthservice UserThe oauthservice is a built-in system user that AEM creates to handle OAuth token operations. This user must have enhanced permissions beyond regular users to manage access control for OAuth scopes.

Required Permissions for oauthservice

The oauthservice user needs all the same permissions as your authenticating users plus additional access control privileges:Standard Permissions (same as authenticating users):
  • Read access to: /apps, /bin, /conf, /content, /etc, /home, /libs, /var
  • Write access to: /content/launches, /content/dam, /content/cq:tags, or your specific site paths
  • Special permissions: jcr:versionManagement, jcr:lockManagement
Additional System Privileges Required:
  • jcr:readAccessControl - Read permission metadata and access control lists
  • jcr:modifyAccessControl - Modify access control for OAuth scope validation

Permission Assignment Steps

  1. Access the Security Console
    • Navigate to <AEM-HOST>:<PORT>/security/permissions.html/principal/oauthservice?filter=user
    • This shows current permissions for the oauthservice user
  2. Verify Current Permissions
    • Check that oauthservice has read access to all paths defined in your OAuth scopes
    • Verify write access to content paths where Gradial will operate
  3. Add Missing Permissions
    • Add any missing read/write permissions to match your OAuth scope definitions
    • Ensure jcr:readAccessControl and jcr:modifyAccessControl are present
  4. Alternative: Group-Based Assignment
    • Create a dedicated “OAuth Service Users” group
    • Assign all required permissions to the group
    • Add oauthservice user to the group
The oauthservice user must have equal or greater permissions than your OAuth scopes grant. Missing permissions will cause OAuth authorization failures.
The oauthservice user automatically appears in AEM after the first OAuth request. If not visible, complete the OAuth client setup first.
5

Configure OAuth Server Authentication Handler

What this step does: Configures AEM to prioritize OAuth authentication over other authentication methods.

Access OSGi Configuration

  1. Open the Configuration Manager
    • Navigate to <AEM-HOST>:<PORT>/system/console/configMgr
    • Use admin credentials to access the OSGi console
  2. Locate the OAuth Handler
    • Search for “Adobe Granite OAuth Server Authentication Handler”
    • Click the configuration name to open the editor

Required Configuration Settings

Configure the following properties:
PropertyValuePurpose
jaas.ranking1100Sets priority over other auth handlers
jaas.controlFlagsufficientAllows OAuth to satisfy auth requirements
oauth.offline.validationtrueEnables token validation without callbacks
jaas.realmNamejackrabbit.oakSpecifies the security realm
path/Applies OAuth to all paths

Step-by-Step Configuration

  1. Set Authentication Priority
    • Find jaas.ranking field
    • Enter 1100 (or higher if you have custom auth handlers with high rankings)
    • This ensures OAuth takes precedence over basic authentication
  2. Configure Control Flag
    • Set jaas.controlFlag to sufficient
    • This allows OAuth to fulfill authentication requirements independently
  3. Enable Offline Validation
    • Check oauth.offline.validation to true
    • Enables token validation without requiring external callbacks
  4. Set Realm and Path
    • jaas.realmName: Use jackrabbit.oak (AEM’s default security realm)
    • path: Set to / to apply OAuth authentication to all AEM paths
  5. Save Configuration
    • Click “Save” to apply the changes
    • The configuration takes effect immediately

Example OSGi Configuration File

For deployment automation, use this .config file format:
jaas.controlFlag="sufficient"
oauth.offline.validation=B"true"
jaas.ranking=I"1100"
jaas.realmName="jackrabbit.oak"
path="/"
The “B” prefix indicates Boolean type and “I” indicates Integer type in OSGi configuration files.

Verification

After configuration:
  1. Check that the configuration appears in the OSGi console
  2. Verify no error messages in the AEM error logs
  3. Test OAuth authentication with a simple scope request
Incorrect jaas.ranking values may cause OAuth authentication to be bypassed. Ensure the ranking is higher than other authentication handlers.
6

Configure Service-to-Service (2-Legged)

  1. In the OAuth client config, click Download Private Key
  2. Securely provide the private key to Gradial for JWT signing
7

Testing

To test scopes, open the consent URL:
http://<AEM-HOST>:<PORT>/oauth/authorize?response_type=code&client_id=CLIENT_ID&scope=SCOPE1 SCOPE2&redirect_uri=REDIRECT_URI
You should see a bullet for each requested scope. Authorizing should return a code in the URL bar if the user has permissions to the scopes. If the user does not have permissions, it will not return a code.
Gradial can provide a separate testing guide for completing the flow to retrieve and use access tokens if needed.

Need Help?

Contact your Gradial representative for additional support with your AEM 6.5 integration.