Stay organized with collections
Save and categorize content based on your preferences.
When you create a custom cloud
control,
you use Common Expression Language (CEL) expressions to create the rules that
evaluate the properties of the scanned resource.
Your expressions can be checks of a single value or more complex
compound expressions that check multiple values or conditions. Either way,
the expression must resolve to a boolean false to trigger a finding.
CEL expressions that evaluate resource properties must conform to the
following rules:
The properties that you specify in a CEL expression must be properties
of the scanned resource, as defined in the API definition of the resource
type.
All enums in a CEL expression must be represented as
strings. For example, the following is a valid expression for the
cloudkms.googleapis.com/CryptoKeyVersion resource type:
resource.data.state = "PENDING_GENERATION"
The result of the CEL expressions that you define in the condition property
must be a Boolean. A finding is triggered only if the result is false.
For more information about CEL, see the following:
[[["Easy to understand","easyToUnderstand","thumb-up"],["Solved my problem","solvedMyProblem","thumb-up"],["Other","otherUp","thumb-up"]],[["Hard to understand","hardToUnderstand","thumb-down"],["Incorrect information or sample code","incorrectInformationOrSampleCode","thumb-down"],["Missing the information/samples I need","missingTheInformationSamplesINeed","thumb-down"],["Other","otherDown","thumb-down"]],["Last updated 2025-09-03 UTC."],[],[],null,["| **Preview**\n|\n|\n| This feature is subject to the \"Pre-GA Offerings Terms\" in the General Service Terms section\n| of the [Service Specific Terms](/terms/service-terms#1).\n|\n| Pre-GA features are available \"as is\" and might have limited support.\n|\n| For more information, see the\n| [launch stage descriptions](/products#product-launch-stages).\n\n\u003cbr /\u003e\n\n| Enterprise [service tier](/security-command-center/docs/service-tiers) (requires [organization-level activation](/security-command-center/docs/activate-scc-overview#overview_of_organization-level_activation))\n\nWhen you create a [custom cloud\ncontrol](/security-command-center/docs/compliance-manager-apply-framework#create-custom-cloud-control),\nyou use Common Expression Language (CEL) expressions to create the rules that\nevaluate the properties of the scanned resource.\n\nYour expressions can be checks of a single value or more complex\ncompound expressions that check multiple values or conditions. Either way,\nthe expression must resolve to a boolean `false` to trigger a finding.\n\nCEL expressions that evaluate resource properties must conform to the\nfollowing rules:\n\n- The properties that you specify in a CEL expression must be properties\n of the scanned resource, as defined in the API definition of the resource\n type.\n\n- All enums in a CEL expression must be represented as\n strings. For example, the following is a valid expression for the\n `cloudkms.googleapis.com/CryptoKeyVersion` resource type:\n\n ```\n resource.data.state = \"PENDING_GENERATION\"\n ```\n- The result of the CEL expressions that you define in the `condition` property\n must be a Boolean. A finding is triggered only if the result is `false`.\n\nFor more information about CEL, see the following:\n\n- [The CEL spec](https://github.com/google/cel-spec)\n- [The CEL language definition](https://github.com/google/cel-spec/blob/master/doc/langdef.md)\n\nExample CEL expressions\n\nThe following table lists some CEL expressions that you can use to\nevaluate resource properties.\n\n| Resource type | Description | CEL expression |\n|-----------------------------------------------|----------------------------------------------------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|\n| `cloudkms.googleapis.com/CryptoKey` | Check the Cloud KMS key rotation period | `has(resource.data.rotationPeriod) && resource.data.rotationPeriod \u003c duration('60h')` |\n| `compute.googleapis.com/Network` | Match Virtual Private Cloud peering rule to network peers | `resource.data.selfLink.matches('https://www.googleapis.com/compute/v1/projects/`\u003cvar translate=\"no\"\u003ePROJECT_ID\u003c/var\u003e`/global/networks/default``') || resource.data.peerings.exists(p, p.network.matches('https://www.googleapis.com/compute/v1/projects/`\u003cvar translate=\"no\"\u003ePROJECT_ID\u003c/var\u003e`/global/networks/shared$``'))` |\n| `cloudfunctions.googleapis.com/CloudFunction` | Only allow internal ingress traffic for a Cloud Run function | `has(resource.data.ingressSettings) && resource.data.ingressSettings.matches('ALLOW_INTERNAL_ONLY')` |\n| `compute.googleapis.com/Instance` | Resource name matches pattern | `resource.data.name.matches('^gcp-vm-(linux|windows)-v\\\\\\\\d+$')` |\n| `serviceusage.googleapis.com/Service` | Only allow storage-related APIs to be enabled | `resource.data.state == 'ENABLED' && !( resource.data.name.matches('storage-api.googleapis.com') || resource.data.name.matches('bigquery-json.googleapis.com') || resource.data.name.matches('bigquery.googleapis.com') || resource.data.name.matches('sql-component.googleapis.com') || resource.data.name.matches('spanner.googleapis.com'))` |\n| `sqladmin.googleapis.com/Instance` | Only permit public IP addresses that are on the allowlist | `(resource.data.instanceType == 'CLOUD_SQL_INSTANCE' && resource.data.backendType == 'SECOND_GEN' && resource.data.settings.ipConfiguration.ipv4Enabled ) && (resource.data.ipAddresses.all(ip, ip.type != 'PRIMARY' || ip.ipAddress.matches('`\u003cvar translate=\"no\"\u003eIP_ADDRESS\u003c/var\u003e`')))` |\n| `dataproc.googleapis.com/Cluster` | Check if project IDs in a Dataproc cluster contain the substrings `testing` or `development` | `has(resource.data.projectId) && !resource.data.projectId.contains('testing') || !resource.data.projectId.contains('development')` |"]]