Creating the EKS cluster
This document walks you through the creation of an EKS cluster.
Before you begin
- Verify that your environment meets the System requirements and prerequisites and Hardware cluster requirements.
- Prepare for installation.
- Log in to the OpenShift® command-line interface.
- Downloading the Guardium Insights CASE file and set up your environment for dependencies.
Procedure
- In the EKS console, click Create:
- Configure the cluster details by setting the cluster name, Kubernetes version (1.29 or 1.30), and IAM role. If a role is not
created, make sure that it has the correct permissions.
- Click Create a role in IAM console:
- Select AWS service and then set the Service or use case to EKS and EKS - Cluster:
- Click Next.
- Confirm and click Next and then provide a Role name. Add all the required tags, and then click Create role.
- Select Allow cluster administrator access and EKS API and ConfigMap. If needed, you can also add tags.
- To configure subnets, use the default selection, choose IPv4, and set the Cluster endpoint access to Public and private:
- Select Prometheus, if needed. Set Send Prometheus metrics to Amazon Managed Service for Prometheus to on and select API server:
- To finalize cluster setup, proceed through the add-on and version pages by clicking Next and then click Create and wait for the status to become Active:
- Create EC2 instances for the EKS cluster:
- Configure the node group:
- Set the Name and IAM policy for the cluster nodes. If you have not yet set the IAM nodes policy, create one with the following properties.
- Create a role.
- Click Next and then search for these permission policies in the
IAM console and add them to the IAM role:
AmazonEBSCSIDriverPolicy
AmazonEC2ContainerRegistryReadOnly
AmazonEKS_CNI_Policy
AmazonEKSWorkerNodePolicy
aws-loadbalancer-policy
If you do not have the
aws-loadbalancer-policy
policy, you need to manually create it in your IAM:{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "iam:CreateServiceLinkedRole" ], "Resource": "*", "Condition": { "StringEquals": { "iam:AWSServiceName": "elasticloadbalancing.amazonaws.com" } } }, { "Effect": "Allow", "Action": [ "ec2:DescribeAccountAttributes", "ec2:DescribeAddresses", "ec2:DescribeAvailabilityZones", "ec2:DescribeInternetGateways", "ec2:DescribeVpcs", "ec2:DescribeVpcPeeringConnections", "ec2:DescribeSubnets", "ec2:DescribeSecurityGroups", "ec2:DescribeInstances", "ec2:DescribeNetworkInterfaces", "ec2:DescribeTags", "ec2:GetCoipPoolUsage", "ec2:DescribeCoipPools", "elasticloadbalancing:DescribeLoadBalancers", "elasticloadbalancing:DescribeLoadBalancerAttributes", "elasticloadbalancing:DescribeListeners", "elasticloadbalancing:DescribeListenerCertificates", "elasticloadbalancing:DescribeSSLPolicies", "elasticloadbalancing:DescribeRules", "elasticloadbalancing:DescribeTargetGroups", "elasticloadbalancing:DescribeTargetGroupAttributes", "elasticloadbalancing:DescribeTargetHealth", "elasticloadbalancing:DescribeTags", "elasticloadbalancing:DescribeTrustStores" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "cognito-idp:DescribeUserPoolClient", "acm:ListCertificates", "acm:DescribeCertificate", "iam:ListServerCertificates", "iam:GetServerCertificate", "waf-regional:GetWebACL", "waf-regional:GetWebACLForResource", "waf-regional:AssociateWebACL", "waf-regional:DisassociateWebACL", "wafv2:GetWebACL", "wafv2:GetWebACLForResource", "wafv2:AssociateWebACL", "wafv2:DisassociateWebACL", "shield:GetSubscriptionState", "shield:DescribeProtection", "shield:CreateProtection", "shield:DeleteProtection" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "ec2:AuthorizeSecurityGroupIngress", "ec2:RevokeSecurityGroupIngress" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "ec2:CreateSecurityGroup" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "ec2:CreateTags" ], "Resource": "arn:aws:ec2:*:*:security-group/*", "Condition": { "StringEquals": { "ec2:CreateAction": "CreateSecurityGroup" }, "Null": { "aws:RequestTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "ec2:CreateTags", "ec2:DeleteTags" ], "Resource": "arn:aws:ec2:*:*:security-group/*", "Condition": { "Null": { "aws:RequestTag/elbv2.k8s.aws/cluster": "true", "aws:ResourceTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "ec2:AuthorizeSecurityGroupIngress", "ec2:RevokeSecurityGroupIngress", "ec2:DeleteSecurityGroup" ], "Resource": "*", "Condition": { "Null": { "aws:ResourceTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:CreateLoadBalancer", "elasticloadbalancing:CreateTargetGroup" ], "Resource": "*", "Condition": { "Null": { "aws:RequestTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:CreateListener", "elasticloadbalancing:DeleteListener", "elasticloadbalancing:CreateRule", "elasticloadbalancing:DeleteRule" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:AddTags", "elasticloadbalancing:RemoveTags" ], "Resource": [ "arn:aws:elasticloadbalancing:*:*:targetgroup/*/*", "arn:aws:elasticloadbalancing:*:*:loadbalancer/net/*/*", "arn:aws:elasticloadbalancing:*:*:loadbalancer/app/*/*" ], "Condition": { "Null": { "aws:RequestTag/elbv2.k8s.aws/cluster": "true", "aws:ResourceTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:AddTags", "elasticloadbalancing:RemoveTags" ], "Resource": [ "arn:aws:elasticloadbalancing:*:*:listener/net/*/*/*", "arn:aws:elasticloadbalancing:*:*:listener/app/*/*/*", "arn:aws:elasticloadbalancing:*:*:listener-rule/net/*/*/*", "arn:aws:elasticloadbalancing:*:*:listener-rule/app/*/*/*" ] }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:ModifyLoadBalancerAttributes", "elasticloadbalancing:SetIpAddressType", "elasticloadbalancing:SetSecurityGroups", "elasticloadbalancing:SetSubnets", "elasticloadbalancing:DeleteLoadBalancer", "elasticloadbalancing:ModifyTargetGroup", "elasticloadbalancing:ModifyTargetGroupAttributes", "elasticloadbalancing:DeleteTargetGroup" ], "Resource": "*", "Condition": { "Null": { "aws:ResourceTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:AddTags" ], "Resource": [ "arn:aws:elasticloadbalancing:*:*:targetgroup/*/*", "arn:aws:elasticloadbalancing:*:*:loadbalancer/net/*/*", "arn:aws:elasticloadbalancing:*:*:loadbalancer/app/*/*" ], "Condition": { "StringEquals": { "elasticloadbalancing:CreateAction": [ "CreateTargetGroup", "CreateLoadBalancer" ] }, "Null": { "aws:RequestTag/elbv2.k8s.aws/cluster": "false" } } }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:RegisterTargets", "elasticloadbalancing:DeregisterTargets" ], "Resource": "arn:aws:elasticloadbalancing:*:*:targetgroup/*/*" }, { "Effect": "Allow", "Action": [ "elasticloadbalancing:SetWebAcl", "elasticloadbalancing:ModifyListener", "elasticloadbalancing:AddListenerCertificates", "elasticloadbalancing:RemoveListenerCertificates", "elasticloadbalancing:ModifyRule" ], "Resource": "*" } ] }
- Click Next and choose a role name. You can also add a description and tags, and then click Create role.
- Return to the node creation page and choose the role name that you created.
- Configure the node tags.
When you add tags for your EKS nodes, the minimum node specification must be
5 different EC2 m6a.4xlarge
instances to support both Guardium Insights and IBM Cloud Pak® foundational services. The Disk size must be at least100 GiB
. - Use the Specify networking page to verify that the nodes can
communicate with the cluster and that the VPC that you choose is NFC-enabled.
- Select any of the subnet names and click
Next. For example,
subnet-0fXXX
.In a separate browser tab or window, open http://console.aws.amazon.com/vpcconsole/. Then copy the subnet name that you retrieved from the console (for example,
'subnet-05757b5b55bf78109 | gi-eks-vpc-subnet-private1-us-east-la
), and search for it in the VPC console within your AWS account. - In the Subnets tab, select your subnet and go to its Route table.
- In the Route tables page, click Edit routes:
- Add the NAT Gateway (NGW) to your VPC so your EKS cluster can communicate with your EC2 instances:
- Select any of the subnet names and click
Next.
- Review all settings and then click Create. Note: The EKS cluster takes between 5 and 15 minutes to create.
- Version 3.4.x Complete the following steps in your
terminal.
- Set the access key and secret key credentials for your AWS
account:
sudo vi~/.aws/credentials
[default] aws_access_key_id= aws_secret_access_key= aws_session_token=
For more information, see https://docs.aws.amazon.com/cli/v1/userguide/cli-authentication-user.html#cli-authentication-user-get.
- Get the cluster information.
aws sts get-caller-identity
- Set the environment for your cluster.
aws eks update-kubeconfig --region us-east-2 --name cluster-name
Update the
fileSystemId
in this manifest.export efs_file_system_id=fs-xxxxxxxxxxxxxxx
cat <<EOF | kubectl apply -f - apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: efs-sc parameters: directoryPerms: "777" fileSystemId: $efs_file_system_id gid: "0" provisioningMode: efs-ap uid: "0" provisioner: efs.csi.aws.com reclaimPolicy: Delete volumeBindingMode: Immediate EOF
To confirm that the environment is set, issue this command:
oc get sc
The results should be similar to:
NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE efs-sc efs.csi.aws.com Delete Immediate false 123m gp2 (default) kubernetes.io/aws-ebs Delete WaitForFirstConsumer false 39h
In addition, ensure that these parameters (777 permission) are included in the EFS claim storage class:Parameters: directoryPerms=777,fileSystemId=fs-005891f4dab28cd06,gid=0,provisioningMode=efs-ap,uid=0
For example:oc describe sc efs-sc Provisioner: efs.csi.aws.com Parameters: directoryPerms=777,fileSystemId=fs-088163fcae75a1740,gid=0,provisioningMode=efs-ap,uid=0 AllowVolumeExpansion: <unset> MountOptions: <none> ReclaimPolicy: Delete VolumeBindingMode: Immediate Events: <none>
apiVersion: gi.ds.isc.ibm.com/v1 kind: GuardiumInsights metadata: name: GI_INSTANCE_NAME #gi-sample namespace: NAMESPACE #staging spec: dependency-security: networkPolicy: egresses: enabled: false egress-required-allow: egress: - ports: - protocol: UDP port: 443 - protocol: TCP port: 443 - protocol: UDP port: 53 - protocol: TCP port: 53 - port: 5353 protocol: UDP - port: 5353 protocol: TCP version: 3.5.0 license: accept: true licenseType: "L-YRPR-ZV3BA6" dependency-postgres: podContainerSecurityContextParams: fsGroup: 0 runAsUser: 1000 runAsNonRoot: true dependency-kafka: podContainerSecurityContextParams: fsGroup: 0 runAsUser: 1000 runAsNonRoot: true dependency-redis: podContainerSecurityContextParams: fsGroup: 0 runAsUser: 1000 runAsNonRoot: true guardium-agent-cert-generator: podContainerSecurityContextParams: fsGroup: 0 runAsUser: 1000 mini-snif: podContainerSecurityContextParams: allowPrivilegeEscalation: false capabilities: drop: - ALL privileged: false readOnlyRootFilesystem: false runAsNonRoot: false replicaCount: 1 dependency-db2: db2instance: nodes: 2 storage: - name: meta spec: accessModes: - ReadWriteMany resources: requests: storage: 100Gi limits: storage: 1000Gi storageClassName: efs-sc type: create - name: data spec: accessModes: - ReadWriteOnce resources: requests: storage: 100Gi storageClassName: gp2 type: template - name: backup spec: accessModes: - ReadWriteMany resources: requests: storage: 100Gi limits: storage: 2000Gi storageClassName: efs-sc type: create - name: tempts spec: accessModes: - ReadWriteOnce resources: requests: storage: 100Gi limits: storage: 1000Gi storageClassName: gp2 type: template - name: archivelogs spec: accessModes: - ReadWriteMany resources: requests: storage: 200Gi limits: storage: 1000Gi storageClassName: efs-sc type: create guardiumInsightsGlobal: deploymentOptions: prometheusType: disabled fsGroupGid: 0 networkPolicyPodToPod: enabled: false backupsupport: enabled: "false" name: backup-pvc-support image: insightsPullSecret: ibm-entitlement-key repository: cp.icr.io/cp/ibm-guardium-insights size: GI_SIZE insights: ingress: hostName: HOST_NAME #example - namespace.apps.cluster_name.guardium-insights.com domainName: DOMAIN_NAME #example - apps.cluster_name.guardium-insights.com ics: namespace: NAMESPACE #staging registry: common-service storageClassName: efs-sc storageClassNameRWO: gp2 deploySettings: nonOCP: true ensureDb2InstallPlacement: true ssh-service: serviceAnnotations: service.beta.kubernetes.io/aws-load-balancer-internal: "false"
echo ${file_system_id}
Apply the
StorageClass
usingenvsubst
for substitution.Create a file named efs.yaml and update these parameters:
- Change the
storage_class_name
toefs-sc
. - Replace the
fileSsystemId
parameter with the output ofecho ${file_system_id}
.
Apply the YAML file:oc apply -f efs.yaml
Sample EFS storage class manifest:
apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: ${storage_class_name} parameters: directoryPerms: "777" fileSystemId: ${file_system_id} gid: "0" provisioningMode: efs-ap uid: "0" provisioner: efs.csi.aws.com reclaimPolicy: Delete volumeBindingMode: Immediate
oc get sc NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE efs-sc efs.csi.aws.com Delete Immediate false 123m gp2 (default) kubernetes.io/aws-ebs Delete WaitForFirstConsumer false 39h
Note: By default, you might have a gp2 storage class on your EKS cluster - however, it is recommended that you use gp3 for improved performance and deployment. For more information, see Migrating Amazon EKS clusters from gp2 to gp3 EBS volumes.If you keep the gp2 storage cluster and the
default
value is not in front of it, patch it with this command:kubectl patch storageclass gp2 -p '{"metadata": {"annotations":{"storageclass.kubernetes.io/is-default-class":"true"}}}'
- Change the
- Set the access key and secret key credentials for your AWS
account: