Built-in Parameterized Policies
EAP

 
Please contact us if you would like to try out this early access feature.

Parameterized policies support query parameters that allow you to configure their behavior directly in the policy name. These are configured using the parameterizedPolicy key and provide a flexible way to customize consent policies without writing custom interceptors.

See Built-in Fixed Policies for policies that don't require parameters.

Query Parameter Syntax

Query parameters are appended to the policy name using standard URL query string syntax:

PolicyName?param1=value1&param2=value2

Key features:

  • Parameters are separated by &
  • Multi-valued parameters can be specified by repeating the parameter name: param=val1&param=val2
  • Comma-separated values are also permitted in a single key: param=val1,val2
  • Parameters are parsed and made available to the policy implementation

Note: Individual policies may have stricter validation checks and forbid multi-valued parameters at their discretion.

RedactFhirPathsWhen

The RedactFhirPathsWhen policy allows you to redact (remove) specific elements from FHIR resources based on the resource type and the consent purpose of the requesting user or client. This is useful for scenarios where certain data elements should be hidden based on the purpose of the request.

Overview

This policy uses FHIRPath expressions to identify which elements should be redacted from resources. It can be configured to:

  • Always redact specific elements from certain resource types
  • Conditionally redact elements based on the consent purpose in the user's session
  • Use a whitelist approach (only redact when purpose matches)
  • Use a blacklist approach (redact unless purpose matches)

Parameters

The RedactFhirPathsWhen policy accepts the following query parameters:

ParameterRequiredMulti-valuedDescription
_typeYesYes (comma-separated)The FHIR resource type(s) to apply redaction to. Examples: Patient, ExplanationOfBenefit, Patient,Observation
fhirpathYesYes (repeated)FHIRPath expression(s) identifying the elements to redact. Can be specified multiple times for multiple paths. Note: Comma separation is not supported; each FHIRPath must be its own fhirpath= entry. We recommend avoiding the | operator in FHIRPath expressions due to issues with how FHIRPath evaluation treats them during deduplication.
consent-purposeNoYes (comma-separated)Whitelist mode: Only apply redaction when the session's consent purpose matches one of these codes.
consent-purpose:notNoYes (comma-separated)Blacklist mode: Skip redaction when the session's consent purpose matches one of these codes.
Note: If neither consent-purpose nor consent-purpose:not is specified, redaction will always be applied to matching resource types.

Setting the Consent Purpose

The consent purpose must be set on the user or client session before the consent evaluation occurs. This is typically done in an authentication callback script using the setConsentPurpose() method.

User Sessions

For user-based authentication flows (e.g., SMART on FHIR), set the consent purpose in the onAuthenticateSuccess callback:

function onAuthenticateSuccess(theOutcome, theOutcomeFactory, theContext) {
    var username = theOutcome.username.toUpperCase();

    if (username === 'USER_A') {
        // Treatment purpose - clinical care access
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'TREAT');
    } else if (username === 'USER_B') {
        // Research purpose - de-identified access
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'HRESCH');
    }

    return theOutcome;
}

Client Sessions

For client credentials flows, the consent purpose can also be set on OAuth2ClientSessionDetailsJson. This is configured similarly through client authentication callbacks:

function onAuthenticateSuccess(theOutcome, theOutcomeFactory, theContext) {
    var clientId = theOutcome.clientId;

    if (clientId === 'research-app') {
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'HRESCH');
    } else if (clientId === 'clinical-app') {
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'TREAT');
    }

    return theOutcome;
}

See Authentication Callback Scripts for more details.

Common Consent Purpose Codes

The following purpose codes from http://terminology.hl7.org/CodeSystem/v3-ActReason are commonly used:

CodeDescription
TREATTreatment - clinical care
HPAYMTHealthcare Payment - billing and claims
HOPERATHealthcare Operations
HRESCHHealthcare Research
PATRQTPatient Request - patient accessing their own data
BTGBreak The Glass - emergency access
PUBHLTHPublic Health

Examples

Example 1: Always Redact Patient Name

This example always removes the name element from Patient resources, regardless of consent purpose:

{
    "willSeeResource": {
        "consentRules": [
            {
                "name": "REDACT_PATIENT_NAME",
                "parameterizedPolicy": "RedactFhirPathsWhen?_type=Patient&fhirpath=Patient.name"
            }
        ]
    }
}

Result: All users see Patient resources without the name element.

Example 2: Redact Financial Data Unless Patient Request

This example redacts financial information from ExplanationOfBenefit resources unless the user's consent purpose is PATRQT (Patient Request):

{
    "willSeeResource": {
        "consentRules": [
            {
                "name": "REDACT_EOB_FINANCIALS",
                "parameterizedPolicy": "RedactFhirPathsWhen?_type=ExplanationOfBenefit&consent-purpose:not=PATRQT&fhirpath=ExplanationOfBenefit.total&fhirpath=ExplanationOfBenefit.payment&fhirpath=ExplanationOfBenefit.item.adjudication"
            }
        ]
    }
}

Result:

  • Users with PATRQT purpose see the full ExplanationOfBenefit including financial details
  • All other users see ExplanationOfBenefit with total, payment, and adjudication elements removed

Example 3: De-identify Data for Research

This example removes identifying information when the consent purpose is HRESCH (Healthcare Research):

{
    "willSeeResource": {
        "consentRules": [
            {
                "name": "DEIDENTIFY_FOR_RESEARCH",
                "parameterizedPolicy": "RedactFhirPathsWhen?_type=Patient,Observation&consent-purpose=HRESCH&fhirpath=Patient.name&fhirpath=Patient.address&fhirpath=Patient.telecom&fhirpath=Patient.birthDate&fhirpath=Patient.identifier"
            }
        ]
    }
}

Result:

  • Users with HRESCH purpose see Patient and Observation resources with identifying elements removed
  • Users with other purposes (e.g., TREAT) see the full resources

Example 4: Multiple Resource Types with Different Paths

This example applies different redaction rules to multiple resource types:

{
    "willSeeResource": {
        "consentRules": [
            {
                "name": "REDACT_CLAIM_FINANCIALS",
                "parameterizedPolicy": "RedactFhirPathsWhen?_type=Claim,ExplanationOfBenefit&consent-purpose:not=HPAYMT,PATRQT&fhirpath=Claim.total&fhirpath=ExplanationOfBenefit.total&fhirpath=ExplanationOfBenefit.payment"
            }
        ]
    }
}

Result:

  • Users with HPAYMT or PATRQT purpose see full financial information
  • Other users have financial totals and payment information redacted

End-to-End Worked Example

 

This section walks through a complete scenario showing how consent purpose affects data visibility.

Scenario

A healthcare system needs to provide different levels of data access:

  • Clinicians (purpose: TREAT) should see all patient data
  • Researchers (purpose: HRESCH) should see de-identified patient data

Step 1: Configure Authentication Script

Create an authentication callback script that assigns consent purpose based on the user:

function onAuthenticateSuccess(theOutcome, theOutcomeFactory, theContext) {
    var username = theOutcome.username.toUpperCase();

    if (username === 'DR_SMITH') {
        // Clinician - treatment purpose
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'TREAT');
    } else if (username === 'RESEARCHER_JONES') {
        // Researcher - research purpose
        theOutcome.setConsentPurpose('http://terminology.hl7.org/CodeSystem/v3-ActReason', 'HRESCH');
    }

    return theOutcome;
}

Step 2: Configure Consent Module

Configure the consent module to redact identifying information for research purposes:

{
    "willSeeResource": {
        "consentRules": [
            {
                "name": "DEIDENTIFY_FOR_RESEARCH",
                "parameterizedPolicy": "RedactFhirPathsWhen?_type=Patient&consent-purpose=HRESCH&fhirpath=Patient.name&fhirpath=Patient.birthDate&fhirpath=Patient.address&fhirpath=Patient.telecom"
            }
        ]
    }
}

Step 3: Test the Results

Sample Patient Resource

{
    "resourceType": "Patient",
    "id": "patient-123",
    "name": [
        {
            "family": "Johnson",
            "given": ["Alice", "Marie"]
        }
    ],
    "birthDate": "1985-03-15",
    "gender": "female",
    "address": [
        {
            "line": ["123 Main Street"],
            "city": "Springfield",
            "state": "IL",
            "postalCode": "62701"
        }
    ],
    "telecom": [
        {
            "system": "phone",
            "value": "555-123-4567"
        }
    ]
}

What DR_SMITH (TREAT purpose) sees:

The full Patient resource with all elements intact.

What RESEARCHER_JONES (HRESCH purpose) sees:

{
    "resourceType": "Patient",
    "id": "patient-123",
    "gender": "female"
}

The name, birthDate, address, and telecom elements have been redacted, leaving only non-identifying information.

Troubleshooting

 

Redaction Not Applied

If redaction is not being applied as expected:

  1. Check the consent purpose is set: Verify that setConsentPurpose() is being called in your authentication script. You can log the purpose for debugging.

  2. Verify resource type: Ensure the _type parameter matches the FHIR resource type exactly (e.g., Patient not patient).

  3. Check FHIRPath syntax: Ensure your FHIRPath expressions are valid. The expression should reference the element to remove, not a primitive value.

  4. Review consent rule order: Rules are evaluated in order. Ensure your redaction rule comes before any PROCEED or AUTHORIZED rules that might short-circuit evaluation.

Elements Not Being Removed

If some elements are not being removed:

  1. Check the FHIRPath expression: Use a FHIRPath evaluator to test your expression against sample resources.

  2. Multiple paths: For complex resources, you may need multiple fhirpath parameters to cover all variations of an element.