コンテンツにスキップ

EKS Public Endpoint

検証日: 2026-05-22 / リージョン: ap-northeast-1

カスタム SCP の説明

背景: EKS クラスターエンドポイントのパブリックアクセス

EKS クラスターは、Kubernetes API サーバへの 2 つの経路を持つ。

設定説明
endpointPublicAccessインターネット経由(パブリック)のアクセス経路の有効/無効
endpointPrivateAccessVPC 内(プライベート)のアクセス経路の有効/無効

クラスター作成時のデフォルトは endpointPublicAccess=true / endpointPrivateAccess=false で、何も設定しないとパブリック経路のみ有効な状態になる。Security Hub CSPM の EKS.1 はこの設定をチェックし、endpointPublicAccess=true の場合に FAILED となる。

詳細は EKS.1 を参照。

このカスタム SCP の役割

EKS の eks:endpointPublicAccess 条件キー(Bool 型)は 2026 年 4 月に追加された比較的新しい機能で、eks:CreateCluster / eks:UpdateClusterConfig API でリクエストパラメータの値を SCP で評価できる。これにより、endpointPublicAccess=true を指定する操作のみを Deny できる。

Control Tower の標準予防コントロールには EKS のパブリックアクセスを直接制御するものが存在しない。代わりに VPC BPA(宣言型ポリシー) によるネットワーク層での実害ブロックが選択肢となるが、EKS の API サーバエンドポイントは VPC BPA の対象外(EKS が管理するパブリック DNS で AWS バックボーン経由のアクセスとなるため)。よって本カスタム SCP が予防コントロールとしての主軸となる。

適用順序の注意

EKS クラスターは作成時にパブリック化可能なため、SSM.7 のような「事前設定 → SCP 適用」の順序制約はない。SCP を先に適用しても問題ない。

ただし、本 SCP は予防コントロールであり、SCP 適用前から存在するパブリック EKS クラスターは endpointPublicAccess=false に強制されない。SCP 適用前に Security Hub の EKS.1 finding で棚卸しし、既存の違反クラスターを修正する運用フローを推奨する。

本 SCP は endpointPublicAccess=true のみを Deny する。endpointPublicAccess=false への変更は通過するが、endpointPrivateAccess=false のままだと Kubernetes API への経路が完全に途絶える。プライベート化する際は endpointPrivateAccess=true も同時に設定すること。

SCP の内容

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "DenyEksPublicEndpoint",
      "Effect": "Deny",
      "Action": [
        "eks:CreateCluster",
        "eks:UpdateClusterConfig"
      ],
      "Resource": "*",
      "Condition": {
        "Bool": {
          "eks:endpointPublicAccess": "true"
        }
      }
    }
  ]
}

Conditioneks:endpointPublicAccess: true の場合のみ Deny するため、endpointPublicAccess=false を指定する操作(または endpointPublicAccess を指定しない作成・変更操作で暗黙のデフォルトが false 解決されるケース)は引き続き許可される。

対象 API について

API役割
eks:CreateClusterクラスター新規作成時のパブリックアクセス有効化を阻止
eks:UpdateClusterConfig既存クラスターのパブリックアクセス有効化変更を阻止

UpdateClusterConfig--resources-vpc-config endpointPublicAccess=true のような形でエンドポイント設定を変更する API。それ以外の用途(ロギング設定、認証モードなど)でも使われるが、eks:endpointPublicAccess: true 条件にマッチしない呼び出しは Deny されない。

検証環境

検証環境の構成図

本記事のコマンドは、--profile 指定がない場合は Workload アカウントで実行する。Master アカウントでの操作には --profile Master を指定する。事前に export AWS_PROFILE=Workload でデフォルトを設定しておくと便利。

  • 検証アカウント: Workload(AWS_PROFILE=Workload
  • ポリシー操作アカウント: Master(AWS_PROFILE=Master
  • リージョン: ap-northeast-1
  • 対象 OU: <OU ID>

検証の流れ

    flowchart LR
    s1[1. EKS クラスター作成<br/>endpointPublicAccess=true] --> s2[2. SCP 適用前のベースライン確認<br/>EKS.1 FAILED]
    s2 --> s3[3. プライベート化<br/>EKS.1 PASSED 復帰]
    s3 --> s4[4. カスタム SCP 作成]
    s4 --> s5[5. OU にアタッチ]
    s5 --> s6[6. パブリック化が Deny されることを確認]
    s6 --> s7[7. プライベート維持の操作は引き続き許可されることを確認]
    s7 --> s8[8. SCP デタッチ]
    s8 --> s9[9. パブリック化が再び成功することを確認]
    s9 --> s10[10. クリーンアップ]
  

結果

検証項目結果
ステップ 6.1: update-cluster-configendpointPublicAccess=true 明示時の Deny✓ AccessDeniedException
ステップ 6.2: create-clusterendpointPublicAccess=true 明示時の Deny✓ AccessDeniedException(explicit deny in a service control policy)
ステップ 6.3: create-clusterendpointPublicAccess 未指定時の Deny(暗黙のデフォルト)✓ AccessDeniedException(暗黙のデフォルト true を捕捉)
ステップ 6.4: update-cluster-config でエンドポイント設定以外の変更は通過✓ InProgress(LoggingUpdate)
ステップ 7: プライベート維持の操作は許可✓(InvalidParameterException / CREATING)
ステップ 9: SCP デタッチ後にパブリック化が再び成功✓ Successful、PublicAccess: true

1. 事前準備(EKS クラスター作成)

既存リソースのクリーンアップ確認

aws eks list-clusters \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'clusters' \
  --output json
[]

過去検証で残存しているクラスターがあれば、本検証前に削除する。

IAM ロール作成

cat <<'EOF' > /tmp/eks-trust.json
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {"Service": "eks.amazonaws.com"},
      "Action": "sts:AssumeRole"
    }
  ]
}
EOF

aws iam create-role \
  --role-name eks-scp-test-cluster-role \
  --assume-role-policy-document file:///tmp/eks-trust.json \
  --query 'Role.Arn' \
  --output text \
  --profile Workload
arn:aws:iam::<Workload アカウント ID>:role/eks-scp-test-cluster-role
aws iam attach-role-policy \
  --role-name eks-scp-test-cluster-role \
  --policy-arn arn:aws:iam::aws:policy/AmazonEKSClusterPolicy \
  --profile Workload

(出力なし)

aws iam list-attached-role-policies \
  --role-name eks-scp-test-cluster-role \
  --query 'AttachedPolicies[].PolicyName' \
  --output text \
  --profile Workload
AmazonEKSClusterPolicy

サブネット情報取得

VPC_ID=$(aws ec2 describe-vpcs \
  --filters Name=is-default,Values=true \
  --query 'Vpcs[0].VpcId' \
  --output text \
  --region ap-northeast-1 \
  --profile Workload)

aws ec2 describe-subnets \
  --filters Name=vpc-id,Values=$VPC_ID \
  --query 'Subnets[0:2].[SubnetId,AvailabilityZone]' \
  --output text \
  --region ap-northeast-1 \
  --profile Workload
subnet-<ID-1>	ap-northeast-1a
subnet-<ID-2>	ap-northeast-1c

EKS は異なる AZ の最低 2 サブネットが必要なので、2 つの ID を環境変数に保持する。

SUBNET_1=subnet-<ID-1>
SUBNET_2=subnet-<ID-2>

クラスター作成(endpointPublicAccess=true

ROLE_ARN=$(aws iam get-role \
  --role-name eks-scp-test-cluster-role \
  --query 'Role.Arn' \
  --output text)

aws eks create-cluster \
  --name eks-scp-test \
  --role-arn $ROLE_ARN \
  --resources-vpc-config subnetIds=$SUBNET_1,$SUBNET_2,endpointPublicAccess=true,endpointPrivateAccess=false \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.{Name:name,Status:status,PublicAccess:resourcesVpcConfig.endpointPublicAccess}' \
  --output json
{
    "Name": "eks-scp-test",
    "Status": "CREATING",
    "PublicAccess": true
}

ACTIVE 待ち

while true; do
  STATUS=$(aws eks describe-cluster \
    --name eks-scp-test \
    --region ap-northeast-1 \
    --profile Workload \
    --query 'cluster.status' \
    --output text)
  echo "$(date '+%H:%M:%S') status: $STATUS"
  case "$STATUS" in
    ACTIVE) break ;;
    FAILED) echo "クラスター作成に失敗しました"; break ;;
    *) sleep 30 ;;
  esac
done
HH:MM:SS status: CREATING
(数分間 CREATING を繰り返す。実測では約 7 分で ACTIVE になる)
HH:MM:SS status: ACTIVE
aws eks wait cluster-active は使わない。状態遷移が eventually consistent のため、即座に ACTIVE 扱いで終了するケースがある(公式ドキュメント明記)。describe-cluster でのポーリングが確実。

2. SCP 適用前のベースライン確認(EKS.1 FAILED)

Config ルールの手動トリガー

RULE_NAME=$(aws configservice describe-config-rules \
  --query "ConfigRules[?contains(ConfigRuleName, 'eks-endpoint-no-public-access')].ConfigRuleName" \
  --output text \
  --region ap-northeast-1 \
  --profile Workload)

aws configservice start-config-rules-evaluation \
  --config-rule-names $RULE_NAME \
  --region ap-northeast-1 \
  --profile Workload

(出力なし)

Config 評価結果確認

sleep 30

aws configservice get-compliance-details-by-config-rule \
  --config-rule-name $RULE_NAME \
  --query 'EvaluationResults[?EvaluationResultIdentifier.EvaluationResultQualifier.ResourceId==`eks-scp-test`].{ResourceId:EvaluationResultIdentifier.EvaluationResultQualifier.ResourceId,Compliance:ComplianceType,RecordedTime:ResultRecordedTime}' \
  --region ap-northeast-1 \
  --profile Workload
[
    {
        "ResourceId": "eks-scp-test",
        "Compliance": "NON_COMPLIANT",
        "RecordedTime": "<評価時刻>"
    }
]

Security Hub finding 確認

aws securityhub get-findings \
  --filters '{"ComplianceSecurityControlId":[{"Comparison":"EQUALS","Value":"EKS.1"}],"ResourceId":[{"Comparison":"PREFIX","Value":"arn:aws:eks:ap-northeast-1:<Workload アカウント ID>:cluster/eks-scp-test"}]}' \
  --query 'Findings[0].{Status:Compliance.Status,Severity:Severity.Label,UpdatedAt:UpdatedAt}' \
  --region ap-northeast-1 \
  --profile Workload
{
    "Status": "FAILED",
    "Severity": "HIGH",
    "UpdatedAt": "<更新時刻>"
}

3. プライベート化(EKS.1 PASSED 復帰)

UPDATE_ID=$(aws eks update-cluster-config \
  --name eks-scp-test \
  --resources-vpc-config endpointPublicAccess=false,endpointPrivateAccess=true,publicAccessCidrs=0.0.0.0/0 \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'update.id' \
  --output text)

echo "UPDATE_ID=$UPDATE_ID"
UPDATE_ID=<update-uuid>
update-cluster-config--resources-vpc-config を指定する際、publicAccessCidrs を省略すると既存値が継承される。明示指定が確実。

更新完了待ち

while true; do
  STATUS=$(aws eks describe-update \
    --name eks-scp-test \
    --update-id $UPDATE_ID \
    --region ap-northeast-1 \
    --profile Workload \
    --query 'update.status' \
    --output text)
  echo "$(date '+%H:%M:%S') update status: $STATUS"
  case "$STATUS" in
    Successful) break ;;
    Failed|Cancelled) echo "更新に失敗しました"; break ;;
    *) sleep 30 ;;
  esac
done
HH:MM:SS update status: InProgress
(数分間 InProgress を繰り返す。実測では約 5 分で Successful になる)
HH:MM:SS update status: Successful

EKS.1 PASSED 復帰確認

aws configservice start-config-rules-evaluation \
  --config-rule-names $RULE_NAME \
  --region ap-northeast-1 \
  --profile Workload

sleep 30

aws configservice get-compliance-details-by-config-rule \
  --config-rule-name $RULE_NAME \
  --query 'EvaluationResults[?EvaluationResultIdentifier.EvaluationResultQualifier.ResourceId==`eks-scp-test`].{ResourceId:EvaluationResultIdentifier.EvaluationResultQualifier.ResourceId,Compliance:ComplianceType}' \
  --region ap-northeast-1 \
  --profile Workload
[
    {
        "ResourceId": "eks-scp-test",
        "Compliance": "COMPLIANT"
    }
]

4. カスタム SCP 作成

cat <<'EOF' > /tmp/eks-public-endpoint-scp.json
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "DenyEksPublicEndpoint",
      "Effect": "Deny",
      "Action": [
        "eks:CreateCluster",
        "eks:UpdateClusterConfig"
      ],
      "Resource": "*",
      "Condition": {
        "Bool": {
          "eks:endpointPublicAccess": "true"
        }
      }
    }
  ]
}
EOF

POLICY_ID=$(aws organizations create-policy \
  --name DenyEksPublicEndpoint \
  --description "Deny EKS cluster create/update with endpointPublicAccess=true" \
  --type SERVICE_CONTROL_POLICY \
  --content file:///tmp/eks-public-endpoint-scp.json \
  --profile Master \
  --query 'Policy.PolicySummary.Id' \
  --output text)

echo "POLICY_ID=$POLICY_ID"
POLICY_ID=p-<ポリシー ID>

5. OU にアタッチ

aws organizations attach-policy \
  --policy-id $POLICY_ID \
  --target-id <OU ID> \
  --profile Master

(出力なし)

アタッチ確認

aws organizations list-policies-for-target \
  --target-id <OU ID> \
  --filter SERVICE_CONTROL_POLICY \
  --profile Master \
  --query "Policies[?Id=='$POLICY_ID'].{Name:Name,Type:Type}" \
  --output json
[
    {
        "Name": "DenyEksPublicEndpoint",
        "Type": "SERVICE_CONTROL_POLICY"
    }
]

SCP の反映には数秒のラグがあるため、次のステップに進む前に少し待つ。

sleep 30

6. パブリック化が Deny されることを確認

6.1 update-cluster-configendpointPublicAccess=true を明示指定した場合

既存クラスターのパブリックアクセスを再度有効化しようとし、SCP で Deny されることを確認する。

aws eks update-cluster-config \
  --name eks-scp-test \
  --resources-vpc-config endpointPublicAccess=true,endpointPrivateAccess=true,publicAccessCidrs=0.0.0.0/0 \
  --region ap-northeast-1 \
  --profile Workload 2>&1
An error occurred (AccessDeniedException) when calling the UpdateClusterConfig operation: User is not authorized to perform this action

explicit deny in a service control policy というメッセージが含まれることから、SCP による拒否であることを確認できる。

設定値が変わっていないことを確認

aws eks describe-cluster \
  --name eks-scp-test \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.{Status:status,PublicAccess:resourcesVpcConfig.endpointPublicAccess,PrivateAccess:resourcesVpcConfig.endpointPrivateAccess}'
{
    "Status": "ACTIVE",
    "PublicAccess": false,
    "PrivateAccess": true
}

設定値は endpointPublicAccess=false のまま維持されている。

6.2 create-clusterendpointPublicAccess=true を明示指定した場合

新規作成も Deny されることを確認する。

aws eks create-cluster \
  --name eks-scp-test-public \
  --role-arn $ROLE_ARN \
  --resources-vpc-config subnetIds=$SUBNET_1,$SUBNET_2,endpointPublicAccess=true,endpointPrivateAccess=false \
  --region ap-northeast-1 \
  --profile Workload 2>&1
An error occurred (AccessDeniedException) when calling the CreateCluster operation: User: arn:aws:sts::<Workload アカウント ID>:assumed-role/<ロール名>/<セッション名> is not authorized to perform: eks:CreateCluster on resource: arn:aws:eks:ap-northeast-1:<Workload アカウント ID>:cluster/eks-scp-test-public with an explicit deny in a service control policy
CreateCluster のエラーメッセージには with an explicit deny in a service control policy が含まれる。一方、UpdateClusterConfig(ステップ 6.1)のエラーメッセージには含まれず User is not authorized to perform this action のみとなる。CloudTrail 上は両方とも errorCode: AccessDenied で同一であり、どちらも SCP による Deny である。クライアントに返るメッセージの文言が異なるのは EKS の API 層の実装差異。

endpointPublicAccess=true を指定した新規作成も Deny される。

6.3 create-clusterendpointPublicAccess を指定しない場合(暗黙のデフォルト)

EKS の endpointPublicAccess のデフォルト値は true--resources-vpc-config でこのフラグを指定せずに create-cluster を呼んだ場合、SCP の Bool 条件キーが暗黙のデフォルト値 true を捕捉するかを実測する。

aws eks create-cluster \
  --name eks-scp-test-default \
  --role-arn $ROLE_ARN \
  --resources-vpc-config subnetIds=$SUBNET_1,$SUBNET_2 \
  --region ap-northeast-1 \
  --profile Workload 2>&1
An error occurred (AccessDeniedException) when calling the CreateCluster operation: User: arn:aws:sts::<Workload アカウント ID>:assumed-role/<ロール名>/<セッション名> is not authorized to perform: eks:CreateCluster on resource: arn:aws:eks:ap-northeast-1:<Workload アカウント ID>:cluster/eks-scp-test-default with an explicit deny in a service control policy

--endpoint-public-access の指定がなくても、暗黙のデフォルト値が true に解決されるケースでは SCP の Bool 条件キーで Deny される。RDS.2 の検証(rds:PubliclyAccessible)と同じ挙動。

RDS.2 の検証では、Bool 条件キーが暗黙のデフォルト値も捕捉することが実機確認できた(--publicly-accessible を指定せずに default 名 DBSG で作成した場合に Deny された)。EKS でも同じ挙動が期待されるが、サービスごとに条件キー評価の実装が異なる可能性があるため、実機検証で確定する。

6.4 update-cluster-configendpointPublicAccess を含まない変更は通過することを確認

SCP の Condition は eks:endpointPublicAccess: true のみなので、エンドポイント設定を変更しない UpdateClusterConfig(ロギング設定変更など)は SCP を通過するはずであることを確認する。

aws eks update-cluster-config \
  --name eks-scp-test \
  --logging '{"clusterLogging":[{"types":["api"],"enabled":true}]}' \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'update.{id:id,status:status,type:type}' \
  --output json
{
    "id": "<update-uuid>",
    "status": "InProgress",
    "type": "LoggingUpdate"
}

endpointPublicAccess を含まない UpdateClusterConfig は SCP を通過する。

7. プライベート維持の操作は引き続き許可されることを確認

endpointPublicAccess=false を維持する操作は SCP を通過することを確認する。

7.1 update-cluster-configendpointPublicAccess=false を明示指定

UPDATE_ID=$(aws eks update-cluster-config \
  --name eks-scp-test \
  --resources-vpc-config endpointPublicAccess=false,endpointPrivateAccess=true,publicAccessCidrs=0.0.0.0/0 \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'update.id' \
  --output text)

echo "UPDATE_ID=$UPDATE_ID"
An error occurred (InvalidParameterException) when calling the UpdateClusterConfig operation: Cluster is already at the desired configuration with endpointPrivateAccess: true , endpointPublicAccess: false, and Public Endpoint Restrictions: [0.0.0.0/0]

既に同じ設定のため InvalidParameterException が返る。SCP による AccessDeniedException ではないことから、SCP を通過していることが確認できる。

7.2 create-clusterendpointPublicAccess=false を明示指定

aws eks create-cluster \
  --name eks-scp-test-private \
  --role-arn $ROLE_ARN \
  --resources-vpc-config subnetIds=$SUBNET_1,$SUBNET_2,endpointPublicAccess=false,endpointPrivateAccess=true \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.{Name:name,Status:status}' \
  --output json
{
    "Name": "eks-scp-test-private",
    "Status": "CREATING"
}

endpointPublicAccess=false を指定した新規作成は SCP を通過する。本ステップでは作成完了を待たずに次に進んで良い(クリーンアップで削除する)。

8. SCP デタッチ

aws organizations detach-policy \
  --policy-id $POLICY_ID \
  --target-id <OU ID> \
  --profile Master

(出力なし)

デタッチ確認

aws organizations list-policies-for-target \
  --target-id <OU ID> \
  --filter SERVICE_CONTROL_POLICY \
  --profile Master \
  --query "Policies[?Id=='$POLICY_ID'].Id" \
  --output json
[]

SCP デタッチの反映にも数秒〜数分のラグがあるため、次のステップに進む前に少し待つ。

sleep 60

9. パブリック化が再び成功することを確認

UPDATE_ID=$(aws eks update-cluster-config \
  --name eks-scp-test \
  --resources-vpc-config endpointPublicAccess=true,endpointPrivateAccess=true,publicAccessCidrs=0.0.0.0/0 \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'update.id' \
  --output text)

echo "UPDATE_ID=$UPDATE_ID"
UPDATE_ID=<update-uuid>

SCP デタッチ後、endpointPublicAccess=true への変更が成功する。

設定変更を確認

while true; do
  STATUS=$(aws eks describe-update \
    --name eks-scp-test \
    --update-id $UPDATE_ID \
    --region ap-northeast-1 \
    --profile Workload \
    --query 'update.status' \
    --output text)
  echo "$(date '+%H:%M:%S') update status: $STATUS"
  case "$STATUS" in
    Successful) break ;;
    Failed|Cancelled) break ;;
    *) sleep 30 ;;
  esac
done

aws eks describe-cluster \
  --name eks-scp-test \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.{Status:status,PublicAccess:resourcesVpcConfig.endpointPublicAccess}'
HH:MM:SS update status: InProgress
...
HH:MM:SS update status: Successful
{
    "Status": "ACTIVE",
    "PublicAccess": true
}

10. クリーンアップ

aws organizations delete-policy \
  --policy-id $POLICY_ID \
  --profile Master

(出力なし)

aws eks delete-cluster \
  --name eks-scp-test \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.status' \
  --output text
DELETING
# eks-scp-test-private が作成されている場合は削除
aws eks delete-cluster \
  --name eks-scp-test-private \
  --region ap-northeast-1 \
  --profile Workload \
  --query 'cluster.status' \
  --output text 2>&1 || echo "クラスター不存在、スキップ"
DELETING
# 削除完了待ち
for CLUSTER in eks-scp-test eks-scp-test-private; do
  while aws eks describe-cluster \
    --name $CLUSTER \
    --region ap-northeast-1 \
    --profile Workload >/dev/null 2>&1; do
    echo "$(date '+%H:%M:%S') $CLUSTER deleting..."
    sleep 30
  done
  echo "$CLUSTER deleted"
done
HH:MM:SS eks-scp-test deleting...
...
eks-scp-test deleted
eks-scp-test-private deleted
aws iam detach-role-policy \
  --role-name eks-scp-test-cluster-role \
  --policy-arn arn:aws:iam::aws:policy/AmazonEKSClusterPolicy \
  --profile Workload

aws iam delete-role \
  --role-name eks-scp-test-cluster-role \
  --profile Workload

(出力なし)

付録: その他の利用可能な EKS 条件キー

2026 年 4 月の追加で、EKS は本記事で扱った eks:endpointPublicAccess 以外にも以下の Bool 型条件キーを提供している。組織のポリシーに応じて、複数を組み合わせた SCP 設計が可能。以下は Service Authorization Reference に基づく情報であり、本記事では実機検証していない。

条件キー想定用途
eks:endpointPrivateAccessBoolプライベートエンドポイントの有効化を強制(endpointPublicAccess=false 単独だと API 経路が完全消滅するリスクがあるため、両方を組み合わせる運用が現実的)
eks:deletionProtectionBool削除保護の無効化を Deny
eks:bootstrapClusterCreatorAdminPermissionsBoolクラスター作成者への Kubernetes admin 自動付与を Deny
eks:authenticationModeString認証モード(API / API_AND_CONFIG_MAP / CONFIG_MAP)の特定値強制

詳細は Service Authorization Reference for EKS を参照。

参考

Amazonアソシエイトリンク