

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# 在 Amazon EKS 上部署範例 Java 微服務，並使用 Application Load Balancer 公開微服務
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer"></a>

*Vijay Thompson 和 Akkamahadevi 租用數學，Amazon Web Services*

## 總結
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-summary"></a>

此模式說明如何使用`eksctl`命令列公用程式和 Amazon Elastic Container Registry (Amazon ECR)，將範例 Java 微服務部署為 Amazon Elastic Kubernetes Service (Amazon EKS) 上的容器化應用程式。您可以使用 Application Load Balancer 來負載平衡應用程式流量。

## 先決條件和限制
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-prereqs"></a>

**先決條件**
+ 作用中的 AWS 帳戶
+ 在 macOS、Linux 或 Windows 上安裝和設定 AWS Command Line Interface (AWS CLI) 1.7 版或更新版本
+ 執行中的 [Docker 協助程式](https://docs.docker.com/config/daemon/)
+ 在 macOS、Linux 或 Windows 上安裝和設定的`eksctl`命令列公用程式 （如需詳細資訊，請參閱 [Amazon EKS 文件中的 Amazon EKS – eksctl 入門](https://docs.aws.amazon.com/eks/latest/userguide/getting-started-eksctl.html)。)
+ 在 macOS、Linux 或 Windows 上安裝和設定的`kubectl`命令列公用程式 （如需詳細資訊，請參閱 Amazon EKS 文件中的[安裝或更新 kubectl](https://docs.aws.amazon.com/eks/latest/userguide/install-kubectl.html)。)

**限制**
+ 此模式不包含 Application Load Balancer 的 SSL 憑證安裝。

## Architecture
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-architecture"></a>

**目標技術堆疊**
+ Amazon ECR
+ Amazon EKS
+ Elastic Load Balancing

**目標架構**

下圖顯示用於在 Amazon EKS 上容器化 Java 微服務的架構。

![\[部署為 Amazon EKS 上容器化應用程式的 Java 微服務。\]](http://docs.aws.amazon.com/zh_tw/prescriptive-guidance/latest/patterns/images/pattern-img/e1dd8ab0-9e1e-4d2b-b7af-89d3e583e57c/images/aaca4fd9-5aaa-4df5-aebd-02a2ed881c3b.png)


## 工具
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-tools"></a>
+ [Amazon Elastic Container Registry (Amazon ECR)](https://docs.aws.amazon.com/AmazonECR/latest/userguide/what-is-ecr.html) 是一種受管容器映像登錄服務，安全、可擴展且可靠。
+ [Amazon Elastic Kubernetes Service (Amazon EKS)](https://docs.aws.amazon.com/eks/latest/userguide/getting-started.html) 可協助您在 AWS 上執行 Kubernetes，而無需安裝或維護您自己的 Kubernetes 控制平面或節點。
+ [AWS Command Line Interface (AWS CLI)](https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-welcome.html) 是一種開放原始碼工具，可協助您透過命令列 shell 中的命令與 AWS 服務互動。
+ [Elastic Load Balancing](https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/what-is-load-balancing.html) 會自動將傳入流量分散到一或多個可用區域中的多個目標，例如 Amazon Elastic Compute Cloud (Amazon EC2) 執行個體、容器和 IP 地址。
+ [eksctl](https://eksctl.io/) 可協助您在 Amazon EKS 上建立叢集。
+ [kubectl](https://kubernetes.io/docs/tasks/tools/install-kubectl/) 可讓您針對 Kubernetes 叢集執行命令。
+ [Docker](https://www.docker.com/) 可協助您在稱為容器的套件中建置、測試和交付應用程式。

## 史詩
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-epics"></a>

### 使用 eksctl 建立 Amazon EKS 叢集
<a name="create-an-amazon-eks-cluster-by-using-eksctl"></a>


| 任務 | Description | 所需的技能 | 
| --- | --- | --- | 
| 建立 Amazon EKS 叢集。 | 若要建立使用兩個 t2.small Amazon EC2 執行個體做為節點的 Amazon EKS 叢集，請執行下列命令：<pre>eksctl create cluster --name <your-cluster-name> --version <version-number> --nodes=1 --node-type=t2.small</pre>程序可能需要 15 到 20 分鐘。建立叢集之後，適當的 Kubernetes 組態會新增至您的 [kubeconfig](https://docs.aws.amazon.com/eks/latest/userguide/create-kubeconfig.html) 檔案。您可以使用 `kubeconfig` 檔案搭配 `kubectl`****，在後續步驟中部署應用程式。 | 開發人員、系統管理員 | 
| 驗證 Amazon EKS 叢集。 | 若要確認叢集已建立且您可以連線到叢集，請執行 `kubectl get nodes`命令。 | 開發人員、系統管理員 | 

### 建立 Amazon ECR 儲存庫並推送 Docker 映像。
<a name="create-an-amazon-ecr-repository-and-push-the-docker-image"></a>


| 任務 | Description | 所需的技能 | 
| --- | --- | --- | 
| 建立 Amazon ECR 儲存庫。 | 遵循 Amazon ECR 文件中[建立私有儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/repository-create.html)的指示。 | 開發人員、系統管理員 | 
| 建立 POM XML 檔案。 | 根據此模式[額外資訊](#deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-additional)區段中`pom.xml`*的範例 POM 檔案*程式碼來建立檔案。 | 開發人員、系統管理員 | 
| 建立來源檔案。 | 根據下列範例，在`src/main/java/eksExample`路徑`HelloWorld.java`中建立名為 的來源檔案：<pre>package eksExample;<br />import static spark.Spark.get;<br /><br />public class HelloWorld {<br />    public static void main(String[] args) {<br />        get("/", (req, res) -> {<br />            return "Hello World!";<br />        });<br />    }<br />}</pre>請務必使用下列目錄結構：<pre>├── Dockerfile<br />├── deployment.yaml<br />├── ingress.yaml<br />├── pom.xml<br />├── service.yaml<br />└── src<br />    └── main<br />        └── java<br />            └── eksExample<br />                └── HelloWorld.java</pre> |  | 
| 建立 Dockerfile。 | `Dockerfile` 根據此模式[額外資訊](#deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-additional)區段中*的範例 Dockerfile *程式碼建立 。 | 開發人員、系統管理員 | 
| 建置並推送 Docker 映像。 | 在您希望 `Dockerfile`建置、標記映像並將映像推送至 Amazon ECR 的目錄中，執行下列命令：<pre>aws ecr get-login-password --region <region>| docker login --username <username> --password-stdin <account_number>.dkr.ecr.<region>.amazonaws.com<br />docker buildx build --platform linux/amd64 -t hello-world-java:v1 .<br />docker tag hello-world-java:v1 <account_number>.dkr.ecr.<region>.amazonaws.com/<repository_name>:v1<br />docker push <account_number>.dkr.ecr.<region>.amazonaws.com/<repository_name>:v1</pre>修改上述命令中的 AWS 區域、帳戶號碼和儲存庫詳細資訊。請務必記下映像 URL 以供日後使用。具有 M1 晶片的 macOS 系統在建置與在 AMD64 平台上執行的 Amazon EKS 相容的映像時發生問題。若要解決此問題，請使用 [Docker buildx](https://docs.docker.com/engine/reference/commandline/buildx/) 建置適用於 Amazon EKS 的 Docker 映像。 |  | 

### 部署 Java 微服務
<a name="deploy-the-java-microservices"></a>


| 任務 | Description | 所需的技能 | 
| --- | --- | --- | 
| 建立部署檔案。 | `deployment.yaml` 根據此模式[額外資訊](#deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-additional)區段中*的範例部署檔案程式碼，建立名為 的 YAML 檔案*。使用您先前複製的映像 URL 做為 Amazon ECR 儲存庫映像檔案的路徑。 | 開發人員、系統管理員 | 
| 在 Amazon EKS 叢集上部署 Java 微服務。 | 若要在 Amazon EKS 叢集中建立部署，請執行 `kubectl apply -f deployment.yaml`命令。 | 開發人員、系統管理員 | 
| 驗證 Pod 的狀態。 | [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/prescriptive-guidance/latest/patterns/deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer.html) | 開發人員、系統管理員 | 
| 建立服務。 | [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/prescriptive-guidance/latest/patterns/deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer.html) | 開發人員、系統管理員 | 
| 安裝 AWS Load Balancer 控制器附加元件。 | 遵循 Amazon EKS 文件中[安裝 AWS Load Balancer 控制器附加元件](https://docs.aws.amazon.com/eks/latest/userguide/aws-load-balancer-controller.html)的指示。您必須安裝 附加元件，才能為 Kubernetes 服務建立 Application Load Balancer 或 Network Load Balancer。 | 開發人員、系統管理員 | 
| 建立輸入資源。 | `ingress.yaml` 根據此模式[額外資訊](#deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-additional)區段中*的範例輸入資源檔案程式碼，建立名為 的 YAML 檔案*。 | 開發人員、系統管理員 | 
| 建立 Application Load Balancer。 | 若要部署輸入資源並建立 Application Load Balancer，請執行 `kubectl apply -f ingress.yaml`命令。 | 開發人員、系統管理員 | 

### 測試應用程式。
<a name="test-the-application"></a>


| 任務 | Description | 所需的技能 | 
| --- | --- | --- | 
| 測試並驗證應用程式。 | [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/prescriptive-guidance/latest/patterns/deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer.html) | 開發人員、系統管理員 | 

## 相關資源
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-resources"></a>
+ [建立私有儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/repository-create.html) (Amazon ECR 文件）
+ [推送 Docker 映像](https://docs.aws.amazon.com/AmazonECR/latest/userguide/docker-push-ecr-image.html) (Amazon ECR 文件）
+ [輸入控制器 ](https://www.eksworkshop.com/beginner/130_exposing-service/ingress_controller_alb/)(Amazon EKS 研討會）
+ [Docker buildx](https://docs.docker.com/engine/reference/commandline/buildx/) (Docker 文件）

## 其他資訊
<a name="deploy-a-sample-java-microservice-on-amazon-eks-and-expose-the-microservice-using-an-application-load-balancer-additional"></a>

**POM 檔案範例**

```
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>


  <groupId>helloWorld</groupId>
  <artifactId>helloWorld</artifactId>
  <version>1.0-SNAPSHOT</version>


  <dependencies>
    <dependency>
      <groupId>com.sparkjava</groupId><artifactId>spark-core</artifactId><version>2.0.0</version>
    </dependency>
  </dependencies>
  <build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId><artifactId>maven-jar-plugin</artifactId><version>2.4</version>
        <configuration><finalName>eksExample</finalName><archive><manifest>
              <addClasspath>true</addClasspath><mainClass>eksExample.HelloWorld</mainClass><classpathPrefix>dependency-jars/</classpathPrefix>
            </manifest></archive>
        </configuration>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId><artifactId>maven-compiler-plugin</artifactId><version>3.1</version>
        <configuration><source>1.8</source><target>1.8</target></configuration>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId><artifactId>maven-assembly-plugin</artifactId>
        <executions>
          <execution>
            <goals><goal>attached</goal></goals><phase>package</phase>
            <configuration>
              <finalName>eksExample</finalName>
              <descriptorRefs><descriptorRef>jar-with-dependencies</descriptorRef></descriptorRefs>
              <archive><manifest><mainClass>eksExample.HelloWorld</mainClass></manifest></archive>
            </configuration>
          </execution>
        </executions>
      </plugin>
    </plugins>
  </build>
</project>
```

**範例 Dockerfile**

```
FROM bellsoft/liberica-openjdk-alpine-musl:17

RUN apk add maven
WORKDIR /code

# Prepare by downloading dependencies
ADD pom.xml /code/pom.xml
RUN ["mvn", "dependency:resolve"]
RUN ["mvn", "verify"]

# Adding source, compile and package into a fat jar
ADD src /code/src
RUN ["mvn", "package"]

EXPOSE 4567
CMD ["java", "-jar", "target/eksExample-jar-with-dependencies.jar"]
```

**部署檔案範例**

```
apiVersion: apps/v1
kind: Deployment
metadata:
  name: microservice-deployment
spec:
  replicas: 2
  selector:
    matchLabels:
      app.kubernetes.io/name: java-microservice
  template:
    metadata:
      labels:
        app.kubernetes.io/name: java-microservice
    spec:
      containers:
      - name: java-microservice-container
        image: .dkr.ecr.amazonaws.com/:
        ports:
        - containerPort: 4567
```

**服務檔案範例**

```
apiVersion: v1
kind: Service
metadata:
  name: "service-java-microservice"
spec:
  ports:
    - port: 80
      targetPort: 4567
      protocol: TCP
  type: NodePort
  selector:
    app.kubernetes.io/name: java-microservice
```

**範例輸入資源檔案**

```
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: "java-microservice-ingress"
  annotations:
    kubernetes.io/ingress.class: alb
    alb.ingress.kubernetes.io/load-balancer-name: apg2
    alb.ingress.kubernetes.io/target-type: ip
  labels:
    app: java-microservice
spec:
  rules:
    - http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: "service-java-microservice"
                port:
                  number: 80
```