创建基于上下文的限制

基于上下文的限制允许您管理用户和服务对特定云资源的访问。 您可以根据上下文(如网络区域和端点类型)定义对资源的限制。 更多信息,请参阅 什么是基于上下文的限制

用户和账户级 IP 地址限制也会影响用户访问资源的能力。 您可以在“设置”页面上查看账户级 IP 地址限制。 要查看单个用户的设置,请进入“用户”页面,在“详细信息”选项卡中查看每个用户的 IP 地址限制。

准备工作

  • 要完成规则操作,必须在目标服务上分配 Identity and Access Management (IAM) 策略。
  • 要完成网络区域操作,必须在基于上下文的限制服务上分配 IAM 策略。

有关更多信息,请参阅 基于上下文的限制角色和操作

创建网络区域

通过创建网络区域,您可以建立一个允许访问请求的位置列表。 可以通过 IP 地址(如单个地址、范围或子网)和 VPC ID 指定一组或多个网络位置。 创建网络区域后,可以将其添加到规则中。

要创建网络区域,请完成以下步骤。

  1. 在 IBM Cloud 控制台中,单击管理 > 基于上下文的限制,然后选择网络区域

  2. 单击创建

    您可以使用 JSON 代码表单直接输入 JSON,单击“作为 JSON 代码输入”来创建区段,而不是使用用户界面输入来创建区段。

  3. 输入唯一的名称和描述。

  4. 输入允许访问请求来源的 IP 地址。 必要时,将 IP 地址例外情况纳入拒绝列表。

  5. 输入允许的 VPC。

    如果要在规则中允许从 VPC 访问公共端点,请在区域定义中包含任何公共网关 IP 地址和 VPC。

  6. 参考一项服务。 选择服务类型,然后选择服务。 单击添加,将服务的 IP 地址与您的网络区域关联起来。

    如果不确定服务类型,请查看表“集成了基于上下文限制的服务”。

  7. 单击“下一步”查看网络区域。

  8. 单击创建

您可以继续创建更多网络区域或创建规则。

使用 CLI 创建网络区域

通过创建网络区域,您可以建立一个允许访问请求的位置列表。 可以通过 IP 地址(如单个地址、范围或子网)和 VPC ID 指定一组或多个网络位置。 创建网络区域后,可以将其添加到规则中。

  1. 运行以下命令安装 基于上下文的限制 CLI 插件

    ibmcloud plugin install cbr
    
  2. 要创建网络区域,请使用 cbr zone-create 命令。

    下面的示例创建了一个包含允许网络位置列表的网络区域。

    ibmcloud cbr zone-create --name example-zone --description "Example zone description" --addresses 192.0.2.1,192.2.3.5-192.2.3.10
    

    下面的示例创建了一个带有服务引用的网络区域。 更多信息,请参阅 服务参考资料

    ibmcloud cbr zone-create --name example-zone-1 --description "Kube zone" --service-ref service_name=containers-kubernetes
    

    要查找可用服务引用列表,请运行 ibmcloud cbr service-ref-targets 命令。

使用 API 创建网络区

通过创建网络区域,您可以建立一个允许访问请求的位置列表。 一个或多个网络位置的集合可通过 IP 地址(如单个地址、范围或子网、VPC ID 和服务引用)来指定。 创建网络区域后,可以将其添加到规则中。

要创建网络区域,请调用 基于上下文的限制 API,如下例所示:

curl -X POST --location --header "Authorization: Bearer {iam_token}" --header "Accept: application/json" --header "Content-Type: application/json" --data '{ "name": "an example of zone", "description": "this is an example of zone", "account_id": "12ab34cd56ef78ab90cd12ef34ab56cd", "addresses": [ { "type": "ipAddress", "value": "169.23.56.234" }, { "type": "ipRange", "value": "169.23.22.0-169.23.22.255" }, { "type": "subnet", "value": "192.0.2.0/24" }, { "type": "vpc", "value": "crn:v1:bluemix:public:is:us-south:a/12ab34cd56ef78ab90cd12ef34ab56cd::vpc:r134-d98a1702-b39a-449a-86d4-ef8dbacf281e" }, { "type": "serviceRef", "ref": { "account_id": "12ab34cd56ef78ab90cd12ef34ab56cd", "service_name": "cloud-object-storage" } } ], "excluded": [ { "type": "ipAddress", "value": "169.23.22.127" } ] }' "{base_url}/v1/zones"
AddressIPAddress ipAddressModel = new AddressIPAddress.Builder()
  .type("ipAddress")
  .value("169.23.56.234")
  .build();
AddressIPAddressRange ipRangeAddressModel = new AddressIPAddressRange.Builder()
  .type("ipRange")
  .value("169.23.22.0-169.23.22.255")
  .build();
AddressSubnet subnetAddressModel = new AddressSubnet.Builder()
  .type("subnet")
  .value("192.0.2.0/24")
  .build();
AddressVPC vpcAddressModel = new AddressVPC.Builder()
  .type("vpc")
  .value(vpcCRN)
  .build();
ServiceRefValue serviceRefValueModel = new ServiceRefValue.Builder()
  .accountId(accountID)
  .serviceName("cloud-object-storage")
  .build();
AddressServiceRef serviceRefAddressModel = new AddressServiceRef.Builder()
  .type("serviceRef")
  .ref(serviceRefValueModel)
  .build();
AddressIPAddress excludedIPAddressModel = new AddressIPAddress.Builder()
  .type("ipAddress")
  .value("169.23.22.127")
  .build();
CreateZoneOptions createZoneOptions = new CreateZoneOptions.Builder()
  .name("an example of zone")
  .accountId(accountID)
  .description("this is an example of zone")
  .addresses(java.util.Arrays.asList(ipAddressModel, ipRangeAddressModel, subnetAddressModel, vpcAddressModel, serviceRefAddressModel))
  .excluded(java.util.Arrays.asList(excludedIPAddressModel))
  .build();

Response<Zone> response = contextBasedRestrictionsService.createZone(createZoneOptions).execute();
Zone zone = response.getResult();

System.out.println(zone);
// Request models needed by this operation.

// AddressIPAddress
const ipAddressModel = {
  type: 'ipAddress',
  value: '169.23.56.234',
};
// AddressIPAddressRange
const ipRangeAddressModel = {
  type: 'ipRange',
  value: '169.23.22.0-169.23.22.255',
};
// AddressSubnet
const subnetAddressModel = {
  type: 'subnet',
  value: '192.0.2.0/24',
};
// AddressVPC
const vpcAddressModel = {
  type: 'vpc',
  value: vpcCRN,
};
// AddressServiceRef
const serviceRefAddressModel = {
  type: 'serviceRef',
  ref: {
    account_id: accountId,
    service_name: 'cloud-object-storage',
  },
};
// AddressIPAddress
const excludedIPAddressModel = {
  type: 'ipAddress',
  value: '169.23.22.127',
};

const params = {
  name: 'an example of zone',
  accountId,
  addresses: [ipAddressModel, ipRangeAddressModel, subnetAddressModel, vpcAddressModel, serviceRefAddressModel],
  excluded: [excludedIPAddressModel],
  description: 'this is an example of zone',
};

try {
  const res = await contextBasedRestrictionsService.createZone(params);
  zoneId = res.result.id;
  zoneRev = res.headers.etag;
  console.log(JSON.stringify(res.result, null, 2));
} catch (err) {
  console.warn(err);
}
ip_address_model = {
  'type': 'ipAddress',
  'value': '169.23.56.234',
}
ip_range_address_model = {
  'type': 'ipRange',
  'value': '169.23.22.0-169.23.22.255',
}
subnet_address_model = {
  'type': 'subnet',
  'value': '192.0.2.0/24',
}
vpc_address_model = {
  'type': 'vpc',
  'value': vpc_crn,
}
service_ref_address_model = {
  'type': 'serviceRef',
  'ref': {
    'account_id': account_id,
    'service_name': 'cloud-object-storage',
  }
}
excluded_ip_address_model = {
  'type': 'ipAddress',
  'value': '169.23.22.127',
}

zone = context_based_restrictions_service.create_zone(
  name='an example of zone',
  account_id=account_id,
  addresses=[ip_address_model, ip_range_address_model, subnet_address_model, vpc_address_model, service_ref_address_model],
  excluded=[excluded_ip_address_model],
  description='this is an example of zone',
).get_result()

print(json.dumps(zone, indent=2))
ipAddressModel := &contextbasedrestrictionsv1.AddressIPAddress{
  Type:  core.StringPtr("ipAddress"),
  Value: core.StringPtr("169.23.56.234"),
}
ipRangeAddressModel := &contextbasedrestrictionsv1.AddressIPAddressRange{
  Type:  core.StringPtr("ipRange"),
  Value: core.StringPtr("169.23.22.0-169.23.22.255"),
}
subnetAddressModel := &contextbasedrestrictionsv1.AddressSubnet{
  Type:  core.StringPtr("subnet"),
  Value: core.StringPtr("192.0.2.0/24"),
}
vpcAddressModel := &contextbasedrestrictionsv1.AddressVPC{
  Type:  core.StringPtr("vpc"),
  Value: core.StringPtr(vpcCRN),
}
serviceRefAddressModel := &contextbasedrestrictionsv1.AddressServiceRef{
  Type: core.StringPtr("serviceRef"),
  Ref: &contextbasedrestrictionsv1.ServiceRefValue{
    AccountID:   core.StringPtr(accountID),
    ServiceName: core.StringPtr("cloud-object-storage"),
  },
}
excludedIPAddressModel := &contextbasedrestrictionsv1.AddressIPAddress{
  Type:  core.StringPtr("ipAddress"),
  Value: core.StringPtr("169.23.22.127"),
}

createZoneOptions := contextBasedRestrictionsService.NewCreateZoneOptions()
createZoneOptions.SetName("an example of zone")
createZoneOptions.SetAccountID(accountID)
createZoneOptions.SetDescription("this is an example of zone")
createZoneOptions.SetAddresses([]contextbasedrestrictionsv1.AddressIntf{ipAddressModel, ipRangeAddressModel, subnetAddressModel, vpcAddressModel, serviceRefAddressModel})
createZoneOptions.SetExcluded([]contextbasedrestrictionsv1.AddressIntf{excludedIPAddressModel})

zone, response, err := contextBasedRestrictionsService.CreateZone(createZoneOptions)
if err != nil {
  panic(err)
}
b, _ := json.MarshalIndent(zone, "", "  ")
fmt.Println(string(b))

要查找可用服务引用列表,请调用 ListAvailableServicerefTargets 方法。

使用 Terraform 创建网络区域

通过创建网络区域,您可以建立一个允许访问请求的位置列表。 一个或多个网络位置的集合可通过 IP 地址(如单个地址、范围或子网、VPC ID 和服务引用)来指定。 创建网络区域后,可以将其添加到规则中。

要创建网络区域,请使用 Terraform 资源 cbr_zone

  1. 要安装 Terraform CLI 并为 Terraform 配置 IBM Cloud Provider 插件,请遵循 IBM Cloud® 上的 Terraform 入门 教程。 该插件抽象了用于完成这项任务的 IBM Cloud API。

  2. 创建名为 main.tf 的 Terraform 配置文件。 在该文件中,您可以使用 HashiCorp 配置语言添加创建网络区域的配置。 更多信息,请参阅 Terraform 文档

    下面的示例创建了一个允许使用单个 IP 地址的网络区域,并明确排除了一个信号 IP 地址。

    resource "ibm_cbr_zone" "cbr_zone" {
      account_id = "12ab34cd56ef78ab90cd12ef34ab56cd"
      addresses {
            type = "ipAddress"
            value = "169.23.56.234"
      }
      description = "this is an example of zone"
      excluded {
            type = "ipAddress"
            value = "202.38.89.897"
      }
      name = "an example of zone"
    }
    

另外,也可以使用 Terraform IBM Modules(TIM)for CBR Zone 创建基于上下文限制的区域,或更新现有区域中的地址。 了解 Terraform IBM 模块

下面的示例显示了如何使用模块定义网络区域:

module "cbr" {
  source  = "terraform-ibm-modules/cbr/ibm"
  version = "X.X.X" # Replace with the latest version

  cbr_zones = [
    {
      name             = "my-network-zone"
      zone_description = "Zone for approved IP ranges and VPCs"
      addresses = [
        { type = "ipRange", value = "10.0.0.0/8" }, # use your valid/supported CIDR range.
        { type = "vpc",     value = "abcxxxx..." } # provide vpc crn
      ]
    }
  ]
}

有关输入的完整列表和使用示例,请参阅 GitHub 上的 " 基于上下文的限制 "模块

创建规则

通过创建规则来定义对云资源的限制。

要创建规则,请完成以下步骤。

  1. 在 IBM Cloud 控制台中,单击管理 > 基于上下文的限制,然后选择规则

  2. 单击创建

  3. 在规则中选择要针对的服务。 然后,单击下一步

    为 IAM 访问组服务创建基于上下文的限制时,不符合规则的用户无法查看账户中的任何组,包括公共访问组。

  4. (可选)选择操作受规则限制的 API 范围。 更多信息,请参阅 定义规则范围

    并非所有服务都支持通过 API 对规则进行范围划分。

  5. 根据所选属性将限制范围扩大到所有资源特定资源

  6. 单击审查 > 继续

  7. 添加一个或多个上下文。 选择端点类型和网络区域,然后单击添加

    • 默认情况下,当切换按钮设置为“否”时,允许从所有服务支持的端点类型进行访问。 将切换设置为“是”,以便只允许特定的端点类型。

    如果要在规则中允许从 VPC 访问公共端点,请在区域定义中包含任何公共网关 IP 地址和 VPC。

    • 您可以将现有网络区域添加到规则中,也可以创建新区域添加到规则中。 更多信息,请参阅 创建网络区域
  8. 单击继续

  9. 提供独特的描述。

  10. 选择执行规则的方式。 您可以在创建规则时决定如何执行规则,并随时更新规则执行情况。

    • 启用:执行规则。 被拒绝的访问尝试会在 Activity Tracker Event Routing 中报告。
    • 禁用:不执行该规则。 限制不会应用到您的帐户资源。 如果不准备启用规则,请选择此选项。
    • 仅报告:监控规则对用户的影响,但不强制执行。 所有访问账户资源的尝试都会被记录在 Activity Tracker Event Routing 中。 建议在强制实施规则之前进行 30 天的监视。
  11. 单击创建

使用 CLI 创建规则

要通过创建规则来定义对云资源的限制,请使用 ibmcloud cbr rule-create 命令。 下面的示例创建了一条针对 Kubernetes Service 的规则,只允许来自指定网络区域的专用端点访问服务。

ibmcloud cbr rule-create --description 'Example Rule Description' --service-name kms --context-attributes endpointType=private --zone-id 93de8d3f588ab2c457ff576c364d1145 --enforcement-mode report

对于 enforcement-mode 选项,CLI 接受的值为 enableddisabledreport。 如果未指定执行,则默认启用该规则。 更多信息,请参阅“规则执行”。

使用 API 创建规则

要通过创建规则为云资源创建限制,请调用 基于上下文的限制 API。 下面的示例创建了一条已启用的规则,该规则以 Kubernetes Service 为目标,只允许来自指定网络区域的请求访问服务。

curl -X POST --location --header "Authorization: Bearer {iam_token}" --header "Accept: application/json" --header "Content-Type: application/json" --data '{ "description": "this is an example of rule", "resources": [ { "attributes": [ { "name": "accountId", "value": "12ab34cd56ef78ab90cd12ef34ab56cd" }, { "name": "serviceName", "value": "kms" } ] } ], "contexts": [ { "attributes": [ { "name": "networkZoneId", "value": "65810ac762004f22ac19f8f8edf70a34" } ] } ], "enforcement_mode": "enabled" }' "{base_url}/v1/rules"
RuleContextAttribute ruleContextAttributeModel = new RuleContextAttribute.Builder()
  .name("networkZoneId")
  .value(zoneID)
  .build();
RuleContext ruleContextModel = new RuleContext.Builder()
  .attributes(java.util.Arrays.asList(ruleContextAttributeModel))
  .build();
ResourceAttribute resourceAttributeModelAccountID = new ResourceAttribute.Builder()
  .name("accountId")
  .value(accountID)
  .build();
ResourceAttribute resourceAttributeModelServiceName = new ResourceAttribute.Builder()
  .name("serviceName")
  .value(serviceName)
  .build();
ResourceTagAttribute resourceTagAttributeModel = new ResourceTagAttribute.Builder()
  .name("tagName")
  .value("tagValue")
  .build();
Resource resourceModel = new Resource.Builder()
  .addAttributes(resourceAttributeModelAccountID)
  .addAttributes(resourceAttributeModelServiceName)
  .tags(java.util.Arrays.asList(resourceTagAttributeModel))
  .build();
CreateRuleOptions createRuleOptions = new CreateRuleOptions.Builder()
  .description("this is an example of rule")
  .addContexts(ruleContextModel)
  .addResources(resourceModel)
  .enforcementMode("enabled")
  .build();

Response<Rule> response = contextBasedRestrictionsService.createRule(createRuleOptions).execute();
Rule rule = response.getResult();

System.out.println(rule);
ruleID = rule.getId();
ruleRev = response.getHeaders().values("Etag").get(0);
// Request models needed by this operation.

// RuleContextAttribute
const ruleContextAttributeModel = {
  name: 'networkZoneId',
  value: zoneId,
};

// RuleContext
const ruleContextModel = {
  attributes: [ruleContextAttributeModel],
};

// ResourceAttribute
const resourceAttributeAccountIdModel = {
  name: 'accountId',
  value: accountId,
};

// Resource Attribute
const resourceAttributeServiceNameModel = {
  name: 'serviceName',
  value: serviceName,
  operator: 'stringEquals',
};

// Resource
const resourceModel = {
  attributes: [resourceAttributeAccountIdModel, resourceAttributeServiceNameModel],
};

const params = {
  contexts: [ruleContextModel],
  resources: [resourceModel],
  description: 'this is an example of rule',
  enforcementMode: 'enabled',
};

try {
  const res = await contextBasedRestrictionsService.createRule(params);
  ruleId = res.result.id;
  ruleRev = res.headers.etag;
  console.log(JSON.stringify(res.result, null, 2));
} catch (err) {
  console.warn(err);
}
rule_context_attribute_model = {
  'name': 'networkZoneId',
  'value': zone_id,
}

rule_context_model = {
  'attributes': [rule_context_attribute_model],
}

resource_attribute_account_id_model = {
  'name': 'accountId',
  'value': account_id,
}

resource_attribute_service_name_model = {
  'name': 'serviceName',
  'value': service_name,
}

resource_model = {
  'attributes': [resource_attribute_account_id_model, resource_attribute_service_name_model],
}

rule = context_based_restrictions_service.create_rule(
  contexts=[rule_context_model],
  resources=[resource_model],
  description='this is an example of rule',
  enforcement_mode='enabled'
).get_result()

print(json.dumps(rule, indent=2))
ruleContextAttributeModel := &contextbasedrestrictionsv1.RuleContextAttribute{
  Name:  core.StringPtr("networkZoneId"),
  Value: core.StringPtr(zoneID),
}

ruleContextModel := &contextbasedrestrictionsv1.RuleContext{
  Attributes: []contextbasedrestrictionsv1.RuleContextAttribute{*ruleContextAttributeModel},
}

resourceModel := &contextbasedrestrictionsv1.Resource{
  Attributes: []contextbasedrestrictionsv1.ResourceAttribute{
    {
      Name:  core.StringPtr("accountId"),
      Value: core.StringPtr(accountID),
    },
    {
      Name:  core.StringPtr("serviceName"),
      Value: core.StringPtr(serviceName),
    },
  },
  Tags: []contextbasedrestrictionsv1.ResourceTagAttribute{
    {
      Name:  core.StringPtr("tagName"),
      Value: core.StringPtr("tagValue"),
    },
  },
}

createRuleOptions := contextBasedRestrictionsService.NewCreateRuleOptions()
createRuleOptions.SetDescription("this is an example of rule")
createRuleOptions.SetContexts([]contextbasedrestrictionsv1.RuleContext{*ruleContextModel})
createRuleOptions.SetResources([]contextbasedrestrictionsv1.Resource{*resourceModel})
createRuleOptions.SetEnforcementMode(contextbasedrestrictionsv1.CreateRuleOptionsEnforcementModeEnabledConst)
rule, response, err := contextBasedRestrictionsService.CreateRule(createRuleOptions)
if err != nil {
  panic(err)
}
b, _ := json.MarshalIndent(rule, "", "  ")
fmt.Println(string(b))

使用 Terraform 创建规则

要通过创建规则来定义对云资源的限制,请使用 Terraform 资源 cbr_rule

  1. 要安装 Terraform CLI 并为 Terraform 配置 IBM Cloud Provider 插件,请遵循 IBM Cloud® 上的 Terraform 入门 教程。 该插件抽象了用于完成这项任务的 IBM Cloud API。

  2. 创建名为 main.tf 的 Terraform 配置文件。 在该文件中,您可以使用 HashiCorp 配置语言添加配置,以创建基于上下文的限制规则。 更多信息,请参阅 Terraform 文档

    下面的示例创建了一条针对特定 Kubernetes Service API 的规则,只允许指定网络区域的专用端点调用与该 API 相关的操作。

    resource "ibm_cbr_rule" "cbr_rule" {
      contexts {
            attributes {
                name = "endpointType"
                value = "private"
            }
      }
      description = "this is an example of rule"
      enforcement_mode = "enabled"
      operations {
            api_types {
                api_type_id = "api_type_id"
            }
      }
      resources {
            attributes {
                name = "serviceName"
                value = "containers-kubernetes"
                operator = "equals"
            }
      }
    }