

 **帮助改进此页面** 

要帮助改进本用户指南，请选择位于每个页面右侧窗格中的**在 GitHub 上编辑此页面**链接。

# 通过外部 OIDC 提供者向用户授予 Kubernetes 访问权限
<a name="authenticate-oidc-identity-provider"></a>

Amazon EKS 支持使用 OpenID Connect (OIDC) 身份提供商作为对您的集群的用户进行身份验证的方法。OIDC 身份提供者可与 AWS Identity and Access Management（IAM）结合使用或作为其替代方法。有关使用 IAM 的更多信息，请参阅[向 IAM 用户和角色授予对 Kubernetes API 的访问权限](grant-k8s-access.md)。配置集群身份验证后，您可以创建 Kubernetes `roles` 和 `clusterroles` 以将权限分配给角色，然后使用 Kubernetes `rolebindings` 和 `clusterrolebindings` 将角色绑定到身份。有关更多信息，请参阅 Kubernetes 文档中的[使用 RBAC 授权](https://kubernetes.io/docs/reference/access-authn-authz/rbac/)。
+ 您可以将一个 OIDC 身份提供商与您的集群关联。
+ Kubernetes 不提供 OIDC 身份提供者。您可以使用现有的公共 OIDC 身份提供商，也可以运行您自己的身份提供商。有关经认证提供商的列表，请参阅 OpenID 网站上的 [OpenID 认证](https://openid.net/certification/)。
+ OIDC 身份提供商的发布者 URL 必须可公开访问，以便 Amazon EKS 能够发现签名密钥。Amazon EKS 不支持拥有自签名证书的 OIDC 身份提供者。
+ 您不能禁用向集群进行 IAM 身份验证，因为在将节点加入集群时仍需要使用。
+ Amazon EKS 集群仍必须由 AWS [IAM 主体](https://docs.aws.amazon.com/IAM/latest/UserGuide/id_roles.html#iam-term-principal)创建，而不是由 OIDC 身份提供商用户创建。这是因为集群创建者与 Amazon EKS API 进行交互，而不是与 Kubernetes API 进行交互。
+ 如果为控制面板启用了 CloudWatch 日志，则将在集群的审核日志中列出经 OIDC 身份提供者验证的用户。有关更多信息，请参阅 [启用或禁用控制面板日志](control-plane-logs.md#enabling-control-plane-log-export)。
+ 您无法使用来自 OIDC 提供者的账户登录 AWS 管理控制台。您只能通过使用 AWS Identity and Access Management 账户登录 AWS 管理控制台，从而[在 AWS 管理控制台中查看 Kubernetes 资源](view-kubernetes-resources.md)。

## 关联 OIDC 身份提供商
<a name="associate-oidc-identity-provider"></a>

您需要提供商提供以下信息，然后才能将 OIDC 身份提供商与集群关联：

 **发布者 URL**   
OIDC 身份提供者的 URL，该 URL 允许 API 服务器发现用于验证令牌的公共签名密钥。该 URL 必须以 `https://` 开头，并应与提供者的 OIDC ID 令牌中的 `iss` 声明相对应。根据 OIDC 标准，允许使用路径组件，但不允许使用查询参数。通常，URL 只包含一个主机名称，如 `https://server.example.org` 或 `https://example.com`。该 URL 应指向 `.well-known/openid-configuration` 以下的级别，并且必须可通过 Internet 网公开访问。

 **客户端 ID（也称为*受众*）**   
向 OIDC 身份提供商发出身份验证请求的客户端应用程序的 ID。

您可以使用 `eksctl` 或 AWS 管理控制台 关联身份提供商。

### 使用 eksctl 关联身份提供者
<a name="identity-associate-eksctl"></a>

1. 使用以下内容创建名为 `associate-identity-provider.yaml` 的文件。将 example values 替换为您自己的值。`identityProviders` 部分中的值是从 OIDC 身份提供商处获取的。仅 `identityProviders` 下的 `name`、`type`、`issuerUrl` 和 `clientId` 设置需要相应值。

   ```
   ---
   apiVersion: eksctl.io/v1alpha5
   kind: ClusterConfig
   
   metadata:
     name: my-cluster
     region: your-region-code
   
   identityProviders:
     - name: my-provider
       type: oidc
       issuerUrl: https://example.com
       clientId: kubernetes
       usernameClaim: email
       usernamePrefix: my-username-prefix
       groupsClaim: my-claim
       groupsPrefix: my-groups-prefix
       requiredClaims:
         string: string
       tags:
         env: dev
   ```
**重要**  
不要为 `groupsPrefix` 或 `usernamePrefix` 指定 `system:` 或该字符串的任何部分。

1. 创建提供商。

   ```
   eksctl associate identityprovider -f associate-identity-provider.yaml
   ```

1. 要使用 `kubectl` 以与集群和 OIDC 身份提供者结合使用，请参阅 Kubernetes 文档中的[使用 kubectl](https://kubernetes.io/docs/reference/access-authn-authz/authentication/#using-kubectl)。

### 您可以使用 AWS 控制台关联身份提供者。
<a name="identity-associate-console"></a>

1. 打开 [Amazon EKS 控制台](https://console.aws.amazon.com/eks/home#/clusters)。

1. 选择您的集群，然后选择**访问**选项卡。

1. 在 **OIDC 身份提供者**部分中，选择“关联身份提供者”。

1. 在 **Associate OIDC Identity Provider（关联 OIDC 身份提供商）**页面上，输入或选择以下选项，然后选择 **Associate（关联）**。
   + 对于 **Name（名称）**，为提供商输入一个唯一的名称。
   + 对于 **Issuer URL（发布者 URL）**，输入您的提供商的 URL。此 URL 必须可通过 Internet 进行访问。
   + 在**客户端 ID** 中，输入 OIDC 身份提供者的客户端 ID（也称为**受众**）。
   + 对于 **Username claim（用户名声明）**，输入要用作用户名的声明。
   + 对于**组声明**，输入要用作用户的组的声明。
   + （可选）选择 **Advanced options（高级选项）**，输入或选择以下信息。
     +  **Username prefix（用户名前缀）**– 输入要加在用户名声明前面的前缀。该前缀加在用户名声明前面，以防止与现有名称发生冲突。如果您未提供值，并且用户名为 `email` 之外的值，则前缀默认为 **Issuer URL（发布者 URL）**的值。您可以使用值 ` -` 来禁用所有前缀。不要指定 `system:` 或该字符串的任何部分。
     +  **组前缀** – 输入要加在组声明前面的前缀。该前缀加在组声明前面，以防止与现有名称（如 ` system: groups`）发生冲突。例如，值 `oidc:` 会创建组名称，如 `oidc:engineering` 和 `oidc:infra`。不要指定 `system:` 或该字符串的任何部分。
     +  **Required claims（所需声明）**– 选择 **Add claim（添加声明）**，然后在客户端 ID 令牌中输入描述所需声明的一个或多个键值对。这些键值对描述了 ID 令牌中所需的声明。如果设置，则验证每个声明是否存在于具有匹配值的 ID 令牌中。

       1. 要使用 `kubectl` 以与集群和 OIDC 身份提供者结合使用，请参阅 Kubernetes 文档中的[使用 kubectl](https://kubernetes.io/docs/reference/access-authn-authz/authentication/#using-kubectl)。

## 示例 IAM policy
<a name="oidc-identity-provider-iam-policy"></a>

如果要阻止 OIDC 身份提供商与集群关联，请创建以下 IAM policy 并将其与 Amazon EKS 管理员的 IAM 账户关联。有关更多信息，请参阅《IAM 用户指南》中的[创建 IAM 策略](https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies_create.html)和[添加 IAM 身份权限](https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies_manage-attach-detach.html#add-policies-console)**以及《服务授权参考》中的 [Actions](https://docs.aws.amazon.com/service-authorization/latest/reference/list_amazonelasticcontainerserviceforkubernetes.html)。

```
{
    "Version":"2012-10-17",		 	 	 
    "Statement": [
        {
            "Sid": "denyOIDC",
            "Effect": "Deny",
            "Action": [
                "eks:AssociateIdentityProviderConfig"
            ],
            "Resource": "arn:aws:eks:us-west-2:111122223333:cluster/*"

        },
        {
            "Sid": "eksAdmin",
            "Effect": "Allow",
            "Action": [
                "eks:*"
            ],
            "Resource": "*"
        }
    ]
}
```

如果 `clientID` 为 `kubernetes` 而 `issuerUrl` 为 `https://cognito-idp.us-west-2amazonaws.com/*`，则以下示例策略允许进行 OIDC 身份提供商关联。

```
{
    "Version":"2012-10-17",		 	 	 
    "Statement": [
        {
            "Sid": "AllowCognitoOnly",
            "Effect": "Deny",
            "Action": "eks:AssociateIdentityProviderConfig",
            "Resource": "arn:aws:eks:us-west-2:111122223333:cluster/my-instance",
            "Condition": {
                "StringNotLikeIfExists": {
                    "eks:issuerUrl": "https://cognito-idp.us-west-2.amazonaws.com/*"
                }
            }
        },
        {
            "Sid": "DenyOtherClients",
            "Effect": "Deny",
            "Action": "eks:AssociateIdentityProviderConfig",
            "Resource": "arn:aws:eks:us-west-2:111122223333:cluster/my-instance",
            "Condition": {
                "StringNotEquals": {
                    "eks:clientId": "kubernetes"
                }
            }
        },
        {
            "Sid": "AllowOthers",
            "Effect": "Allow",
            "Action": "eks:*",
            "Resource": "*"
        }
    ]
}
```