Control access to apps based on user & device context

Context-Aware Access examples for Advanced mode

This article describes use cases for Context-Aware Access that include policies using custom access levels.  In these examples, you create custom access levels in Advanced mode, using Common Expressions Language (CEL).

Note that if you prefer, you can also use functions and macros when building custom access levels using CEL expressions.

For examples of access levels developed in Basic mode (using the Context-Aware access interface), go to Context-Aware Access examples for Basic mode.

Authentication examples

Expand section  |  Collapse all

Allow access to users based on the strength of the user's login credentials

To improve the security of access to applications which contain sensitive data you can determine how the user authenticated to the system to decide whether they get access to the application.

For example, users logged in with just a password can only be allowed to access applications that do not contain any sensitive information, whereas a user logged in with a hardware security key as a second factor can be allowed to access the most sensitive enterprise applications.

This access level uses request.auth attributes to verify that the users log in using both a password and a hardware key for 2-step verification, and can access sensitive applications.

request.auth.claims.crd_str.pwd == true && request.auth.claims.crd_str.hwk == true
Allow access to users with strong authentication credentials

Often administrators want to enforce access to corporate resources only after the user has authenticated with strong credentials. The following example uses levels and request.auth attributes as follows: 

  • If a user is coming from a corporate device, any MFA, except SMS, method will suffice (Methods can be push notification, hardware or software security key, or one time password)
  • If a user is coming from a NON-corporate device, then either a hardware or software security key must be used

// Require basic MFA (not SMS) on corporate devices and security key (hardware or software) if not
levels.Require_Secure_Device &&
(
  (
     levels.Require_Corporate_Device &&
     request.auth.claims.crd_str.mfa &&
     !request.auth.claims.crd_str.sms
  ) ||
  (
     !levels.Require_Corporate_Device &&
     (
        request.auth.claims.crd_str.hwk || request.auth.claims.crd_str.swk
     )
  )
)

Device examples

Expand section  |  Collapse all & go to top

Allow access from a device based on signals reported by a BeyondCorp Alliance partner

You can use device signals reported by a BeyondCorp Alliance partner. In this example, Lookout Software is used as the application.

This access level uses the device attribute to verify that the device used to access Google Workspace is reported by Lookout as compliant with policies, and the health score is Very Good.

device.vendors["Lookout"].is_compliant_device == true && device.vendors["Lookout"].device_health_score == DeviceHealthScore.VERY_GOOD
Allow access only from a managed Chrome browser with latest updates

This access level uses the device attribute to verify that users are using the latest version of a managed Chrome browser, and allows access only through such a browser.

device.chrome.management_state == ChromeManagementState.CHROME_MANAGEMENT_STATE_BROWSER_MANAGED && device.chrome.versionAtLeast("94.0.4606.81") 
Allow access using an enterprise certificate

You can use enterprise certificates for devices in custom access levels to determine if a device is a corporate-owned asset. This access level uses the device attribute for the asset verification. Read Configuring enterprise certificate conditions for more information and examples.

A device can have more than one certificate. Enterprise certificates are used in a custom access level using the exists() macro. For example:

device.certificates.exists(cert, predicate)

In this example, cert is a simple identifier to use in the variable predicate to bind to the device enterprise certificate. The exists() macro combines per-element predicate results with the or (||) operator. Macros return true if at least one certificate satisfies the predicate expression.

The table below lists attributes you can use to form CEL expressions to use with custom access levels.  Note that string comparisons are case sensitive.

Attribute Description Example of predicate
expression
(where cert is an
identifier of macros)
is_valid

True if the certificate is valid and not expired.
(boolean)

cert.is_valid
cert_fingerprint Fingerprint of the certificate
(base64 unpadded SHA256)
cert.cert_fingerprint == origin.
clientCertFingerprint()
root_ca_fingerprint Fingerprint of root CA certificate used to sign this certificate
(base64 unpadded SHA256)
cert.root_ca_fingerprint == "the_fingerprint"
issuer

Issuer name
(fully expanded names)

To find the issuer name, run the following command on the cert:

$ openssl x509 -in ca_1.crt -noout
-issuer
issuer=
/C=IN/ST=UP/L=NCR/O=BCEDemo/
OU=BCEDemo_1/CN=inter_1/
emailAddress=[email protected]

The issuer string used in the access level is the reverse of the output and the “/” replaced by a comma, for example:

[email protected], CN=inter_1, OU=BCEDemo_1, O=BCEDemo, L=NCR, ST=UP, C=IN

cert.issuer == "EMAILADDRESS=test_inter1
@beyondcorp.in, CN=inter_1, OU=BCEDemo_1, O=BCEDemo, L=NCR, ST=UP, C=IN"
subject Subject name of the certificate
(fully expanded names)
cert.subject == "CA_SUB"
serial_number

Serial number of the certificate
(string)

cert.serial_number == “123456789”
template_id Template Id of X.509 extension Certificate Template for the certificate
(string)
cert.template_id == "1.3.6.1.4.1.311.21.
8.15608621.11768144.
5720724.
16068415.6889630.81.
2472537.7784047"

Examples of commonly-used policies:

Validate that the device has a valid enterprise certificate signed by the company root certificate

device.certificates.exists(cert, cert.is_valid && cert.root_ca_fingerprint == "ROOT_CA_FINGERPRINT")

Validate the issuer of the enterprise certificate on the device

device.certificates.exists(cert, cert.is_valid && cert.issuer == "[email protected], CN=inter_1, OU=BCEDemo_1, O=BCEDemo, L=NCR, ST=UP, C=IN”)

Allow access to devices with disk encryption and screen lock enabled

This example uses the device attribute to require both disk encryption and screen lock to be enabled. In addition, the device has to be approved by administrators.

By default, all devices created by Endpoint Verification are approved. However, there are cases where you may want to block a device such as when a device is lost. In these cases you would not want these devices to be able to access the corporate resources.

For other access level examples in this document, we will assume this access level has the name Require_Secure_Device.  

// Require disk encryption and screen lock enabled 
// This is applicable across all major platforms (Windows, Mac, Linux, CrOS, iOS, Android)
// This foundational and should be depended upon by all other access levels
device.encryption_status == DeviceEncryptionStatus.ENCRYPTED &&
device.is_secured_with_screenlock &&
device.is_admin_approved_device

Allow access to devices using Chrome browser with basic security requirements

In this example the access level uses the device attribute to require Chrome browser with basic security requirements.

// Require Chrome to be managed at profile or browser level, must have
// security event reporting enabled and must be version 97 or greater
levels.Require_Secure_Device &&
(
  device.chrome.management_state == ChromeManagementState.CHROME_MANAGEMENT_STATE_BROWSER_MANAGED ||
  device.chrome.management_state == ChromeManagementState.CHROME_MANAGEMENT_STATE_PROFILE_MANAGED
) &&
device.chrome.is_security_event_analysis_enabled &&
device.chrome.versionAtLeast("97")

Allow access to devices using Chrome browser with security requirements

This example uses the device attribute to require that the user comes from a managed Chrome browser or profile, and that Chrome has threat and data protection connectors turned on. The example uses the levels attribute to refer to the previously described Require Managed Chrome access level. The following example assumes the dependent access level is named Require_Managed_Chrome

// Require managed chrome (dependent on “Require_Managed_Chrome” access level)
// and require content inspection for downloads as well as URL check enabled
levels.Require_Managed_Chrome &&
device.chrome.is_file_download_analysis_enabled &&
device.chrome.is_realtime_url_check_enabled

Allow access to company-owned devices

A requirement for controlling access is to only allow access when the device is managed or owned by the company. There are many ways to determine whether a device is corporate-owned or managed, including:

  • If a device has a serial number that matches one that’s in the company’s asset management system
  • If a device has a valid enterprise certificate that’s issued by the company

These two approaches can be used in the following custom access level that uses levels and device attributes to determine if the device is corporate-owned or managed.

// The device is a corporate if one of the following conditions is true:
// 1. If the serial number matches what the admin has uploaded
// 2. If the device has a valid enterprise-issued certificate
levels.Require_Secure_Device &&
(
   device.is_corp_owned_device ||
   device.certificates.exists(cert, cert.is_valid && cert.root_ca_fingerprint == "SOME_ROOT_CA_FINGERPRINT")
)

The fingerprint is the unpadded base64 encoded sha256 digest (in binary format) of the DER-encoded certificate. The string can be generated from the certificate in PEM format using the following procedure with openssl:

$ openssl x509 -in cert.pem -out cert.der -outform DER
$ openssl dgst -sha256 -binary cert.der >  digest.sha
$ openssl base64 -in digest.sha

Only allow access when device data from CrowdStrike is fresh
There are two timestamps that CrowdStrike issues as part of the Falcon Zero Trust Assessments (ZTA) score:
  • Issued at timestamp (iat) 
  • Expiry timestamp (exp) (which seems to be 2 weeks from issued at Timestamp in the current release)

The access level uses the device attribute to ensure that CrowdStrike data is fresh. Note that Chrome Enterprise Premium has an innate delay of 90 minutes for consuming any new assessment from Falcon ZTA, so using durations less than an hour is ill-advised. 

// Ensure one of these conditions is true for data from Crowdstrike:
// Must meet one of these conditions
// 1. Device was assessed within the last day
// 2. Assessment has not expired (2 weeks since last iat)
“CrowdStrike” in device.vendors && (
   request.time - timestamp(device.vendors["CrowdStrike"].data["iat"]) < duration("1d") ||
   timestamp(device.vendors["CrowdStrike"].data["exp"]) - request.time > duration("0m")
)

Allow access when BeyondCorp Alliance considers a device to be compliant

Chrome Enterprise Premium works with many BeyondCorp Alliance ecosystem partners to integrate their device signals and context into the Chrome Enterprise Premium solution. Partners can share any number of attributes with Chrome Enterprise Premium , and one of them is the is_compliant_device attribute. The following example uses the device attribute to show how we can check if any of the BeyondCorp Alliance partners have integrated with Chrome Enterprise Premium and consider the device to be compliant.

The exists macro expands the expression for each of the BeyondCorp Alliance partners with a || (or) operator.

// Check to see if any of the BCA partners consider the device to be compliant
["CrowdStrike", "Tanium", "PANW", "Check Point", "Lookout"].exists(
   v, v in device.vendors && device.vendors[v].is_compliant_device
)

Allow access when Android verified boot status is green

This example uses device attributes to ensure that devices are running a safe version of Android.

Verified Boot checks if executed code comes from a trusted source (usually device OEMs), rather than from an attacker or corruption. For details, go to Verified Boot.

// Require green Android verified boot status
device.android_device_security.verified_boot == true

Allow access to devices that pass CTS compliance checks

This example uses device attributes to require devices to pass Compatibility Test Suite (CTS) compliance checks. For details, go to Compatibility Test Suite.

// Require devices to pass CTS compliance checks
device.android_device_security.cts_profile_match == true

Allow access to devices that have Google Play Protect Verify Apps turned on

This example uses device attributes to require devices to have Google Play Protect Verify Apps turned on.

Verify Apps scans apps for threats when they’re installed from sources other than Google Play. It also periodically scans devices for potentially harmful apps. Verify Apps is on by default. For devices under advanced management, you can specify whether users can turn it off. For more information, see Apply settings for Android mobile devices.

// Require devices to have Google Play Protect Verify Apps enabled
device.android_device_security.verify_apps_enabled == true

Do not allow access to devices that have potentially harmful apps

This example uses device attributes to deny access to devices that have potentially harmful apps. These apps are often called malware. For details, go to Potentially Harmful Applications (PHAs).

// Deny access to devices that have potentially harmful appsandroid_device_security.has_potentially_harmful_apps != true

Time-based access examples

Expand section  |  Collapse all & go to top

Only allow access to shift workers during their shift hours

Enterprises want to ensure that their shift workers can only access corporate resources during their shift hours. The following access levels use the levels attribute to define 3 shifts during Monday to Friday.

// Shift 1 - Monday to Friday, midnight to 8am
levels.Require_Secure_Device &&
request.time.getDayOfWeek("America/Los_Angeles") >= 1 &&
request.time.getDayOfWeek("America/Los_Angeles") <= 5 &&
request.time.timeOfDay("America/Los_Angeles").between('00:00:00', '08:00:00')


// Shift 2 - Monday to Friday, 8am to 4pm
levels.Require_Secure_Device &&
request.time.getDayOfWeek("America/Los_Angeles") >= 1 &&
request.time.getDayOfWeek("America/Los_Angeles") <= 5 &&
request.time.timeOfDay("America/Los_Angeles").between('08:00:00', '16:00:00')


// Shift 3 - Monday to Friday, 4pm to midnight
levels.Require_Secure_Device &&
request.time.getDayOfWeek("America/Los_Angeles") >= 1 &&
request.time.getDayOfWeek("America/Los_Angeles") <= 5 &&
request.time.timeOfDay("America/Los_Angeles").between('16:00:00', '00:00:00')


// Allow shift workers to access resources from Monday to Friday between 9 AM to 5 PM, except for July fourth.
levels.Require_Secure_Device &&
request.time.getDayOfWeek("America/Los_Angeles") >= 1 &&
request.time.getDayOfWeek("America/Los_Angeles") <= 5 &&
!(
  request.time.getMonth("America/Los_Angeles") == 6 &&
  request.time.getDayOfMonth("America/Los_Angeles") == 3
) &&
request.time.timeOfDay("America/Los_Angeles").between('09:30:00', '17:00:00')

Allow temporary access

Enterprises sometimes want to allow break glass access during emergencies when the administrator does not have access to a secure device but needs emergency access for a short period of time. 

In this case, create a time and location-constrained access level using the levels attribute, and assign it to the specific administrator. When this access level is assigned, it would only be valid during the time specified. After this time period expires, the administrator access would again be controlled by existing requirements.

// Allow temporary access to resources on March 1, 2022, between 10 PM to midnight,
// and this access must come from within the US region.
levels.Require_Secure_Device &&
request.time.between('2022-03-01T23:00:00+08:00', '2022-03-02T23:59:59+08:00') &&
origin.region_code == “US”
// Note that the end time is exclusive, so the above potentially has 2 seconds that 
// the users may not have access. Another option is to use this 
// !between(‘00:00:01’,’16:00:00’)
 

Combine conditions from two levels example

Define a new access level by combining conditions from two access levels

This access level uses levels attributes, and requires that users meet the combined conditions of two access levels. In this example, access_level_name_1 and access_level_name_2 refer to Internal Name.

levels.access_level_name_1 && levels.access_level_name_2

 

Was this helpful?

How can we improve it?
Search
Clear search
Close search
Google apps
Main menu
8639625275628971306
true
Search Help Center
true
true
true
true
true
73010
false
false