配置安全政策

Media CDN 使用 Google Cloud Armor 安全政策来防止不受欢迎的流量访问其服务。您可以根据以下条件允许或拒绝请求:

  • IPv4 和 IPv6 地址及范围 (CIDR)
  • 国家/地区代码(地理位置)
  • 第 7 层过滤
  • Google 威胁情报(需要 Google Cloud Armor Enterprise 层级)

借助这些功能,您可以限制特定位置(您在这些位置有内容许可限制)的用户下载内容,仅允许公司 IP 地址访问测试或预演端点,并拒绝已知恶意客户端 IP 地址的访问。

您可以通过插入具有可配置名称和值的自定义标头来修饰 Google Cloud Armor 允许的请求。

Google Cloud Armor 与 Google 威胁情报的集成可让您控制来自已知恶意 IP 地址和网域的流量,从而提供高级威胁防护。

Google Cloud Armor 安全政策适用于通过媒体 CDN 传送的所有内容,包括缓存内容和缓存未命中内容。

Google Cloud Armor 安全政策是按 Media CDN 服务配置的,所有发往相应服务 IP 地址(或主机名)的请求都会始终强制执行该安全政策。不同的服务可以应用不同的安全政策,并且您可以根据需要为不同的地理位置创建多个服务。

如需更精细地保护内容(按用户级别),建议您结合使用签名网址和签名 Cookie 与 Google Cloud Armor 政策。

当 Media CDN 在对第 7 层标头过滤边缘安全政策进行规则评估时,如果 referer 标头设置为以下任一值,则不会考虑该标头:

  • 多个网址
  • 相对网址
  • 包含用户信息或 fragment 组件的有效绝对网址

配置安全政策

按照以下说明配置安全政策。

准备工作

如需将 Google Cloud Armor 安全政策附加到 Media CDN 服务,请确保满足以下条件:

您还需要以下 Identity and Access Management 权限,才能授权、创建安全政策并将安全政策附加到 Media CDN 服务:

  • compute.securityPolicies.addAssociation
  • compute.securityPolicies.create
  • compute.securityPolicies.delete
  • compute.securityPolicies.get
  • compute.securityPolicies.list
  • compute.securityPolicies.update
  • compute.securityPolicies.use

需要将现有证书附加到 Media CDN 服务的用户只需要以下 IAM 权限:

  • compute.securityPolicies.get
  • compute.securityPolicies.list
  • compute.securityPolicies.use

roles/networkservices.edgeCacheUser 角色包含所有这些权限。

创建安全政策

Google Cloud Armor 安全政策由多条规则组成,每条规则都定义了一组请求匹配条件(即表达式)和一项操作。例如,一个表达式可以包含针对位于印度的客户的匹配逻辑,关联的操作为 allow。如果请求与规则不匹配,Google Cloud Armor 会继续评估下一条规则,直到尝试完所有规则。

安全政策具有 allow 操作的默认规则。默认规则允许与前面的规则不匹配的请求。如果您希望仅接受与前面的规则匹配的请求,并拒绝所有其他请求,则可以将此规则更改为 deny 规则。allow

以下示例展示了如何创建一条规则,以使用 HTTP 403 阻止所有地理位置位于澳大利亚的客户端,并允许所有其他请求。

gcloud

如需创建类型为 CLOUD_ARMOR_EDGE 的新政策,请使用 gcloud compute security-policies create 命令

gcloud compute security-policies create block-australia \
    --type="CLOUD_ARMOR_EDGE" --project="PROJECT_ID"

这会创建一个政策,其中包含一条优先级最低 (priority: 2147483647) 的默认允许规则:

Created [https://www.googleapis.com/compute/v1/projects/PROJECT_ID/global/securityPolicies/block-australia].

然后,您可以添加优先级更高的规则:

gcloud compute security-policies rules create 1000 \
    --security-policy=block-australia --description "block AU" \
    --expression="origin.region_code == 'AU'" --action="deny-403"

输出如下所示:

Updated [https://www.googleapis.com/compute/v1/projects/PROJECT_ID/global/securityPolicies/block-australia].

Terraform

resource "google_compute_security_policy" "default" {
  name        = "block-australia"
  type        = "CLOUD_ARMOR_EDGE"
  description = "block AU"

  rule {
    action      = "deny(403)"
    description = "block AU"
    priority    = "1000"
    match {
      expr {
        expression = "origin.region_code == 'AU'"
      }
    }
  }
  rule {
    action   = "allow"
    priority = "2147483647"
    match {
      versioned_expr = "SRC_IPS_V1"
      config {
        src_ip_ranges = ["*"]
      }
    }
    description = "default rule"
  }
}

如果您检查该政策,会看到两条规则:第一条规则会屏蔽来自澳大利亚的请求 (origin.region_code == 'AU'),而第二条规则(优先级最低)会允许与优先级较高的规则不匹配的所有流量。

kind: compute#securityPolicy
name: block-australia
rules:
- action: deny(403)
  description: block AU
  kind: compute#securityPolicyRule
  match:
    expr:
      expression: origin.region_code == 'AU'
  preview: false
  priority: 1000
- action: allow
  description: default rule
  kind: compute#securityPolicyRule
  match:
    config:
      srcIpRanges:
      - '*'
    versionedExpr: SRC_IPS_V1
  preview: false
  priority: 2147483647
  ruleNumber: '1'
type: CLOUD_ARMOR_EDGE

将规则添加到安全政策

Google Cloud Armor 安全政策是一组规则,与第 7 层的特性相匹配,以保护面向外部的应用或服务。每条规则都针对传入流量进行评估。

这些属性可用于安全政策中的 HTTP 请求:request.headersrequest.methodrequest.pathrequest.schemerequest.query。如需详细了解如何为安全政策规则编写表达式,请参阅 Google Cloud Armor 自定义规则语言参考文档

Google Cloud Armor 安全政策规则包含一个匹配条件和一个满足该条件时要执行的操作。

gcloud

如需为安全政策创建规则,请使用 gcloud compute security-policies rules create PRIORITY 命令。将 PRIORITY 替换为政策中规则的优先级:

gcloud compute security-policies rules create PRIORITY \
    --security-policy POLICY_NAME \
    --description DESCRIPTION \
    --src-ip-ranges IP_RANGES | --expression EXPRESSION \
    --action=[ allow | deny-403 | deny-404 | deny-502 ] \
    --preview

将政策附加到服务

gcloud

如需将现有的 Google Cloud Armor 政策附加到 Media CDN 服务,请使用 gcloud edge-cache services update 命令

gcloud edge-cache services update MY_SERVICE \
    --edge-security-policy=SECURITY_POLICY

更新安全政策中的规则

使用以下说明更新 Google Cloud Armor 安全政策中的单条规则。或者,您也可以以原子方式更新安全政策中的多个规则

gcloud

使用 gcloud compute security-policies rules update 命令

gcloud compute security-policies rules update PRIORITY [ \
    --security-policy POLICY_NAME  \
    --description DESCRIPTION  \
    --src-ip-ranges IP_RANGES  | --expression EXPRESSION \
    --action=[ allow | deny-403 | deny-404 | deny-502 ]  \
    --preview
  ]
  

例如,以下命令将更新优先级为 1111 的规则,以允许来自 IP 地址范围 192.0.2.0/24 的流量:

gcloud compute security-policies rules update 1111 \
    --security-policy my-policy \
    --description "allow traffic from 192.0.2.0/24" \
    --src-ip-ranges "192.0.2.0/24" \
    --action "allow"

如需更新规则的优先级,必须使用 REST API。如需了解详情,请参阅 securityPolicies.patchRule 方法

查看政策附件

如需查看现有服务关联的政策,请检查(描述)该服务。

gcloud

如需查看附加到 Media CDN 服务的 Google Cloud Armor 政策,请使用 gcloud edge-cache services describe 命令

gcloud edge-cache services describe MY_SERVICE

服务的 edgeSecurityPolicy 字段描述了附加的政策:

name: "MY_SERVICE"
edgeSecurityPolicy: "SECURITY_POLICY

移除政策

如需移除现有政策,请更新关联的服务并传递一个空字符串作为政策。

gcloud

使用 gcloud edge-cache services update 命令

  gcloud edge-cache services update MY_SERVICE \
      --edge-security-policy=""

edgeSecurityPolicy 字段现在已从 gcloud edge-cache services describe MY_SERVICE 命令的输出中省略。

示例

请参考以下详细的用例示例。

示例:确定被阻止的请求

您必须为给定的 Edge Cache 服务启用日志记录,才能记录被阻止的请求。

过滤政策允许或拒绝的请求会记录到 Logging。如需过滤被拒绝的请求,针对 prod-video-service 配置的以下日志记录查询如下所示:

resource.type="edge_cache_service"
jsonPayload.statusDetails="denied_by_security_policy"

示例:自定义响应代码

您可以配置 Google Cloud Armor 规则,以返回特定状态代码作为与给定规则关联的操作。在大多数情况下,最好返回 HTTP 403 DENY 状态代码,以明确表明客户端已被规则屏蔽。

支持的状态代码包括:

  • HTTP 403 Forbidden
  • HTTP 404 Not Found
  • HTTP 502 Bad Gateway

以下示例展示了如何配置返回的状态代码:

如需指定 [allow | deny-403 | deny-404 | deny-502] 之一作为与规则关联的操作,请运行以下命令。此示例将规则配置为返回 HTTP 502 状态代码。

gcloud compute security-policies rules create 1000 \
    --security-policy=block-australia --description "block AU" \
    --expression="origin.region_code == 'AU'" --action="deny-502"

安全政策中的每条规则都可以定义不同的状态代码响应。

示例:拒绝某个国家/地区以外的客户端,但允许特定 IP 地址

媒体投放中的一个常见情况是,拒绝来自您没有内容许可或付款机制的区域的客户端的连接。

例如,您可能希望仅允许位于印度境内的客户以及许可名单中的任何 IP 地址(包括内容合作伙伴和您自己员工的 IP 地址)位于 192.0.2.0/24 范围内的客户,并拒绝所有其他客户。

使用 Google Cloud Armor 自定义规则语言,以下表达式可实现此目的:

origin.region_code == "IN" || inIpRange(origin.ip, '192.0.2.0/24')

此表达式配置为 allow 规则,并配置了默认 deny 规则以匹配所有其他客户端。安全政策始终有一条默认规则。您通常会将其配置为 default deny,以阻止您未明确允许的流量。在其他情况下,您可能会选择阻止部分流量和default allow所有其他流量。

在安全政策输出中,请注意以下事项:

  • 优先级最高的 (priority: 0) 规则允许来自印度来自已定义 IP 地址列表的流量。
  • 优先级最低的规则表示 default deny。规则引擎会拒绝优先级较高的规则计算结果不为 true 的所有客户端。
  • 您可以使用布尔值运算符组合多个规则。

该政策允许来自印度境内客户端的流量,允许来自指定 IP 范围的客户端的流量,并拒绝所有其他流量

当您查看政策的详细信息时,输出类似于以下内容:

kind: compute#securityPolicy
name: allow-india-only
type: "CLOUD_ARMOR_EDGE"
rules:
- action: allow
  description: ''
  kind: compute#securityPolicyRule
  match:
    expr:
      expression: origin.region_code == "IN" || inIpRange(origin.ip, '192.0.2.0/24')
  preview: false
  priority: 0
- action: deny(403)
  description: Default rule, higher priority overrides it
  kind: compute#securityPolicyRule
  match:
    config:
      srcIpRanges:
      - '*'
    versionedExpr: SRC_IPS_V1
  preview: false
  priority: 2147483647

您还可以使用 {region_code} 标头变量设置自定义响应标头。可以使用 JavaScript 检查此标头,并将其反映给客户端。

示例:阻止来自已知恶意 IP 地址的流量

以下 Google Cloud Armor 自定义规则语言表达式会阻止来自被识别为恶意的 IP 地址的流量:

evaluateThreatIntelligence('iplist-known-malicious-ips')

该表达式指示 Google Cloud Armor 根据 Google 持续更新的已知恶意 IP 地址列表检查传入请求,从而提供强大的自动化保护。

如需自动屏蔽恶意 IP 地址,您可以配置边缘安全政策,并使用 Google Threat Intelligence 规则。

以下 Google Cloud CLI 命令展示了如何向现有政策(例如 my-edge-policy)添加新的 Google 威胁情报规则:

  gcloud compute security-policies create my-edge-policy \
      --type=CLOUD_ARMOR_EDGE

  gcloud edge-cache services update my-edge-cache-service \
      --edge-security-policy "my-edge-policy"

  gcloud compute security-policies rules create 1000 \
      --security-policy "my-edge-policy" \
      --expression "evaluateThreatIntelligence('iplist-known-malicious-ips')" \
      --action "deny-403"

示例:按 IP 地址和 IP 范围屏蔽恶意客户端

使用 Google Cloud Armor 自定义规则语言,以下表达式可实现此目的:

inIpRange(origin.ip, '192.0.2.2/32') || inIpRange(origin.ip, '192.0.2.170/32')

您可以屏蔽 IPv4 中最多 /8 位掩码的 IP 范围,以及 IPv6 中最多 /32 位掩码的 IP 范围。对于流媒体平台,一种常见做法是屏蔽代理或 VPN 提供商的出站 IP 范围,以最大限度地减少规避内容许可的情况:

inIpRange(origin.ip, '192.0.2.0/24') || inIpRange(origin.ip, '198.51.100.0/24') || inIpRange(origin.ip, '203.0.113.0/24') || inIpRange(origin.ip, '2001:DB8::B33F:2002/64')

支持 IPv4 和 IPv6 地址范围。

示例:仅允许使用固定的地理位置列表

如果您有一份国家/地区代码列表,可以使用布尔值 OR 运算符 || 来组合匹配条件。

使用 Google Cloud Armor 自定义规则语言,以下表达式允许来自澳大利亚或新西兰的用户:

origin.region_code == "AU" || origin.region_code == "NZ"

此外,还可以将此规则与 origin.ipinIpRange(origin.ip, '...') 表达式结合使用,以允许测试人员、合作伙伴和公司 IP 范围(即使他们不在指定地理位置范围内)访问。

具有自定义表达式的每条规则的子表达式数量都有明确的文档记录。如果您需要组合更多子表达式,请在单个政策中定义多条规则。

示例:屏蔽来自一组特定国家/地区的客户端

一个不太常见的示例可能是阻止来自一组特定国家/地区的客户端,但允许来自所有其他国家/地区的请求。

为此,您可以创建一个政策,该政策会阻止相应国家/地区和任何无法确定其区域的客户端,然后回退到针对所有其他请求的默认允许规则。

以下示例描述了一项政策,该政策会阻止来自加拿大的客户端以及位置未知的任何客户端,但允许所有其他流量:

  kind: compute#securityPolicy
  name: block-canada
  type: "CLOUD_ARMOR_EDGE"
  rules:
  - action: deny(403)
    description: ''
    kind: compute#securityPolicyRule
    match:
      expr:
        expression: origin.region_code == "CA" || origin.region_code == "ZZ"
    preview: false
    priority: 0
  - action: allow
    description: Default rule, higher priority overrides it
    kind: compute#securityPolicyRule
    match:
      config:
        srcIpRanges:
        - '*'
      versionedExpr: SRC_IPS_V1
    preview: false
    priority: 2147483647

示例:拒绝包含特定标头的缓存内容请求

边缘安全政策适用于以附加了该政策的任何 Media CDN 服务为目标的所有请求。此政策强制执行发生在任何缓存查找之前。边缘安全政策不允许的请求会被拒绝,并返回配置的状态代码。

以下表达式与来自 IP 地址 1.2.3.4 的请求匹配,并且在 user-agent 标头中包含字符串 user1

inIpRange(origin.ip, '1.2.3.4/32') && request.headers['user-agent'].contains('user1')

以下命令会将过滤规则 105 添加到边缘安全政策 my-edge-policy(该政策已附加到 Media CDN 服务):

gcloud compute security-policies rules create 105 \
    --security-policy "my-edge-policy" \
    --expression = "inIpRange(origin.ip, '1.2.3.4/32') && request.headers['user-agent'].contains('charlie')" \
    --action= deny-403 \
    --description="block requests from IP addresses in which the user-agent header contains the string charlie"
    

记录违规处置措施

每个请求日志都会详细说明应用了哪些安全政策,以及请求是被允许 (ALLOW) 还是被拒绝 (DENY)。

如需启用日志记录,请确保您的服务中 logConfig.enable 设置为 true。未启用日志记录的服务不会记录安全政策事件。

如果客户端位于美国境外,并且名为 deny-non-us-clients 的安全政策正在生效,该政策会拒绝源自美国境外的请求,那么被拒绝的请求的日志条目如下所示:

enforcedSecurityPolicy:
  name: deny-non-us-clients
  outcome: DENY

未附加 Google Cloud Armor 政策的服务的 enforcedSecurityPolicy.name 值为 no_policyoutcome 值为 ALLOW。例如,未附加政策的服务的请求日志条目具有以下值:

enforcedSecurityPolicy:
  name: no_policy
  outcome: ALLOW

了解 GeoIP 分类

Media CDN 依赖于 Google 的内部 IP 分类数据源,以从 IP 地址中派生出地理位置(区域、州/省或城市)。如果您要从多个提供商处迁移或在多个提供商之间分流,则有时可能会有少量 IP 地址与不同的位置相关联。

  • Google Cloud Armor 使用 ISO 3166-1 alpha 2 区域代码将客户端与地理位置相关联。
  • 例如,US 表示美国,AU 表示澳大利亚。
  • 在某些情况下,一个区域对应一个国家/地区,但并非总是如此。例如,US 代码包括美国各州、一个特区和六个美国本土外地区。
  • 如需了解详情,请参阅 Unicode 技术标准中的 unicode_region_subtag
  • 对于无法推导位置的客户端,origin.region_code 设置为 ZZ

您可以向 Media CDN 端点(使用 routing.routeRules[].headerActions[].responseHeadersToAdd[])的响应标头添加地理位置数据,也可以反映提供给 Cloud Function 的地理位置数据,以便在初始集成和测试期间验证地理位置 IP 数据源之间的任何差异。

此外,Media CDN 请求日志还包含 clientRegion 和其他特定于客户端的数据,您可以根据现有数据源验证这些数据。

后续步骤