Tutorial: Using Kong Kubernetes Ingress Controller as an API Gateway
Using Kong Kubernetes Ingress Controller as an API Gateway
- 최근 IT에서 restructuring, modernization 을 수행하기 위한 주요 전략으로 Kubernetes 를 이용하는 것을 권장하고 있다.
- 이를 통해 모놀리식 시스템을 디커플링 시킨다.
-
API Gateway, Kubernetes Ingress Controller 와 같은 시스템을 찾고 있으며, API 트래픽을 최소한의 코스트로 확장할 수 있도록 하고자 한다.
- API Gateway 는 마이크로 서비스 아키텍처의 핵심 컴포넌트이다.
- API Gateway 는 분산 시스템의 단일 엔트리 포인트로 동작한다. 이는 단일화된 인터페이스를 제공하여 클라이언트가 시스템 통합을 위한 별도 기술을 알 필요 없이 다양한 마이크로 서비스로 부터 응답을 수행할 수 있도록 하고 있다.
API Gateway 사용 케이스
- 인바운드 요청을 적합한 마이크로 서비스로 라우팅한다.
- 복수의 백엔드 서비스로 부터 집계된 응답을 단일화된 인터페이스로 표현한다.
- 호출자에 의해서 포맷된 형태의 응답으로 마이크로 서비스를 변환한다.
- 비 기능/정책 을 구현한다. 이는 인증, 로깅, 모니터링, 그리고 추적가능성, 레이팅 리밋, IP 필터링, 공격 완화 등.
- 불루 그린/ 카타리 릴리즈와 같은 배포 전략을 이용할 수 있도록 해준다.
“API gateway들은 마이크로 서비스 아키텍처의 개발, 관리를 쉽게 해준다. 결과적으로 개발팀이 각각의 비즈니스 로직에 집중할 수 있도록 한다. “
Kubernetes
- Kubernetes 는 분산 아키텍처를 위한 호스팅 플랫폼이 되었다.
- 이는 auto-scaling, fault-tolerance, zero-downtime deployment 를 즉시 실행할 수 있도록 해준다.
- 넓게 수용되고, 표준 접근 방법으로 디자인된 API를 제공한다.
- Kubernetes 는 복잡한 시스템을 훨씬 쉽게 배포하고 관리할 수 있도록, 제품 및 도구를 생성했다.
Kong Kubernetes
- Native Kubernetes 어플리케이션처럼 Kong 은 다른 쿠버네티스 리소스와 같이 설치되고, 관리될 수 있다.
- 이는 CNCF 프로젝트에 잘 통합되며, pod 배포와 같은 클러스터 이벤트에 응답하고, zero-downtime 을 업데이트 할 수 있다.
- 그리고 또한 매우 훌륭한 플러그인 에코 스시템과 네이티브 gRPC 가 있다.
Use Case: Routing API Calls to Backend Services
아티클을 관리가능한 크기로 관리하기 위해서, 단일의 직관적인 사용 케이스를 이용할 것이다.
- 쿠버네티스 클러스터를 생성하고, 2개의 더미 마이크로 서비스를 디플로이 한다.
- “foo”, “bar”가 그것이다.
- Kong 은 들어오는 요청을 /foo 에 대허서 foo 마이크로 서비스로 전달하고, /bar 에 대해서 bar 마이크로 서비스로 전달한다.
사전준비
- 작업을 수행하기 위해서 필요한 사항
- 아래 내용은 DigitalOcean 클러스터를 이용하여 Kubernetes 를 생성한다.
- 이를 통해 가능한 리얼 환경의 시나리오를 생성하였다.
- 만약 로컬에서 작업을 원한다면 minikube 혹은 kinD 를 이용할 수 있다.
- 아마도 이를 이용하기 위해서 fake load-balancer가 필요할 것이다. 이는 minikube tunnel 혹은 port forward 를 수행하여 API gateway 로 보내야한다.
: DigitalOcean 필요사항
- DigitalOcean 계정
- DigitalOcean API token 을 통해서 읽고/쓰기 수행
-
doctl 명령어 툴
- Docker 이미지를 푸시하고, 우리의 마이크로 서비스로 노출시키기 위해서 다음이 필요하다.
- Docker
- Docker Hub 계정
노트: 선택적으로, 이미지를 이미 생성된 것을 이용할 수 있다.
그리고 kubectl 을 통해서 Kubernetes cluster 에 접근하자.
Setting Up doctl
- doctl 설치 이후에, DigitalOcean API token 을 이용하기 위한 인증이 필요하다.
$ doctl auth init
...
Enter your access token: <-- paste your API token, when prompted
Validating token... OK
Create Kubernetes Cluster
- 이제 doctl을 이용하여 인증했고, Kubernetes cluster 를 생성할 수 있다.
$ doctl kubernetes cluster create mycluster --size s-1vcpu-2gb --count 1
이는 쿠버네티스를 DigitalOcean 에서 동작하게 한다. 이는 비용이 발생한다. %0.01/hour 이다. 기억할 것은 작업이 끝나면 반드시 제거하길 바란다.
- 생성 커맨드를 완료하면, 최소한의 워커노드 1개가 만들어진다.
- 이것은 가장작고, 가장 단순한 클러스터이다.
-
doctl kubernetes –help를 통해서 옵션을 살펴볼 수 있다.
- 이 커맨드는 몇분 정도 소요된다. 긜고 다음과 같은 결과를 볼 것이다.
$ doctl kubernetes cluster create mycluster --size s-1vcpu-2gb --count 1
Notice: Cluster is provisioning, waiting for cluster to be running
....................................................
Notice: Cluster created, fetching credentials
Notice: Adding cluster credentials to kubeconfig file found in "/Users/david/.kube/config"
Notice: Setting current-context to do-nyc1-mycluster
ID Name Region Version Auto Upgrade Status Node Pools
4cf2159a-01c1-423c-907d-51f19c3f9a01 mycluster nyc1 1.20.2-do.0 false running mycluster-default-pool
- 보는바와 같이 커맨드는 자동적으로 클러스터 계정을 생성하고, ~/.kube/config 파일이 만들어진다.
- 그리고 클러스터에 kubectl 을 통해서 접근이 가능하다.
$ kubectl get namespace
NAME STATUS AGE
default Active 24m
kube-node-lease Active 24m
kube-public Active 24m
kube-system Active 24m
Create Dummy Microservices
- 백엔드 마이크로 서비스를 표현하기 위해서 몇가지 간단한 Python Flask 어플리케이션을 생성하였다.
- 이는 JSON 스트링을 반환한다.
foo.py
from flask import Flask
app = Flask(__name__)
@app.route('/foo')
def hello():
return '{"msg":"Hello from the foo microservice"}'
if __name__ == "__main__":
app.run(debug=True, host='0.0.0.0')
다음 Dockerfile 은 도커 이미지를 빌드하고 디플로이 할 수 있다.
Dockerfile
FROM python:3-alpine
WORKDIR /app
RUN echo "Flask==1.1.1" > requirements.txt
RUN pip install -r requirements.txt
COPY foo.py .
EXPOSE 5000
CMD ["python", "foo.py"]
이 파일들은 우리의 “foo”와 “bar” 서비스를 위한 것이다.
https://gist.github.com/digitalronin/424134ef9a68a11ddcccaed3878b7c68 에서 foo, bar 에 대한 마이크로 서비스 도커 이미지 생성을 위한 스크립트를 확인하자.
노트: 이미 위 이미지를 만들고 푸시할 필요가 없다. 이미 만들어 진것을 사용하면 된다.
Deploy Dummy Microservices
- 각 마이크로 서비스를 배포하기 위해서 Deployment, Service 매니페스트를 작성해야한다. “foo”, “bar”
- “foo” 를 위한 manifest 는 다음과 같다.
foo.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: foo-deployment
spec:
replicas: 1
selector:
matchLabels:
app: foo
template:
metadata:
labels:
app: foo
spec:
containers:
- name: api
image: digitalronin/foo-microservice:0.1
ports:
- containerPort: 5000
---
apiVersion: v1
kind: Service
metadata:
name: foo-service
labels:
app: foo-service
spec:
ports:
- port: 5000
name: http
targetPort: 5000
selector:
app: foo
https://gist.github.com/digitalronin/401910f3848f92bb32fb129273a0c889 에서 다운로드 받을 수 있다.
이후 다음과 같이 실행해주자.
$ kubectl apply -f foo.yaml
$ kubectl apply -f bar.yaml
Access the Service
다음과 같이 올바르게 서비스가 수행하고 있는지 다음 명령어로 체크해보자.
$ kubectl port-forward service/foo-service 5000:5000
그리고 다른 터미널에서 다음을 수행하자.
$ curl http://localhost:5000/foo
{"msg":"Hello from the foo microservice"}
Install Kong for Kubernetes
Now that you have our two microservices running in our Kubernetes cluster, let’s install Kong.
There are several options for this, which you will find in the documentation. I’m going to apply the manifest directly, like this:
- 이제 쿠버네티스 클러스터에 2개의 마이크로 서비스를 운영하게 되었다. 이제 Kong 을 설치해보자.
- 여기에는 몇가지 옵션이 있다. 도큐먼트 에서 설정정보를 확인할 수 있다.
- 여기서는 설정 정보를 바로 실행하자.
$ kubectl create -f https://bit.ly/k4k8s
출력 결과는 다음과 같다.
...
service/kong-proxy created
service/kong-validation-webhook created
deployment.apps/ingress-kong created
노트: 당신은 몇가지 API가 deprecatation 된 것을 확인할 수 있다. 이는 무시하면 된다. Kong은 API 버젼 선택을 통해서 Kong Ingress Controller 는 가능한 가장 광범위한 Kubernetes 버젼을 지원할 수 있다.
Kong 인스톨은 DigitalOcean load balancer 를 생성할 것이다. 이는 인터넷에 점점인 엔드포인트로, API 콜을 통해서 우리의 마이크로 서비스에 접속할 수 있다.
노트: DigitalOcean 로드 밸런서는 비용이 발생한다. 그러니 끝나고 나면 로드 밸런서를 제거하라.
로드밸런서를 생성하는 것은 몇분 걸린다. 프로그래스는 다음과 같이 읽어보자.
$ kubectl -n kong get service kong-proxy
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kong-proxy LoadBalancer 10.245.14.22 <pending> 80:32073/TCP,443:30537/TCP 71s
일단 로드밸런서가 생성이 되면 EXTERNAL_IP 값이
$ kubectl -n kong get service kong-proxy
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kong-proxy LoadBalancer 10.245.14.22 167.172.7.192 80:32073/TCP,443:30537/TCP 3m45s
편리하게 하기 위해서, IP 넘버를 환경변수로 노출하자.
$ export PROXY_IP=167.172.7.192 # <--- use your own EXTERNAL-IP number here
아제 Kong 가 동작하는지 체크 할 수 있다.
$ curl $PROXY_IP
{"message":"no Route matched with those values"}
노트: 위 결과는 올바른 결과이다. 왜냐하면 아직 API 콜을 수신하기 위한 방법을 알지 못하기 때문이다.
Configure Kong Gateway
당신은 이제 Ingress 리소스를 아래와 같은 Kong 설정을 통해서 이용할 수 있게 되었다.
foo-ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: foo
namespace: default
spec:
ingressClassName: kong
rules:
- http:
paths:
- path: /foo
pathType: Prefix
backend:
service:
name: foo-service
port:
number: 5000
아래 gist 는 양쪽 모두의 마이크로 서비스에 대한 ingress 를 설정한 것이다.
$ kubectl apply -f foo-ingress.yaml
$ kubectl apply -f bar-ingress.yaml
당신은 curl 을 체크할 수 있다.
$ curl $PROXY_IP/foo
{"msg":"Hello from the foo microservice"}
$ curl $PROXY_IP/bar
{"msg":"Hello from the bar microservice"}
What Else Can You Do?
이번 아티클에서 다음을 수행했다.
- Kubernetes 클러스터를 DigitalOcean 으로 배포 했다.
- Docker 이미지를 생성했다. 이는 foo, bar 2개이다.
- 마이크로 서비스를 Kubernetes cluster를 디플로이 했다.
- Kong Ingress Controller 를 인스톨 했다.
- Kong 을 설정하고, 적합한 백엔드 마이크로 서비스로 라우팅 했다.
Kong 의 하나의 단순한 사용을 확인해봤다. 이는 시작 포인트이다. Kong for Kubernetes 를 통해서, 볓가지 예제를 확인할 수 있다.
Authentication
authentication 플러그인을 Kong에 추가하자.
이를 통해서 JSON Web Token(JWT) 이 올바른 값인지 검증할 수 있다. 이를 통해서 각 호출이 ACL(Access Control List) 에 맞는지 체크할 것이다. 이를 통해서 관련된 오페레이션을 수행할 수 있다.
Certificate management
당신은 또한 통합 인증 관리를 제공하여, 프로비젼을 할 수 있고, 자동 SSL 리뉴얼 인증을 API 엔드 포인트에 수행할 수 있다.
gRPC 지원
Kong 은 gPRC를 지원한다.
또한 Kong 을 통해서 다 많은 일을 할 수 있다.
- https://docs.konghq.com/kubernetes-ingress-controller/1.1.x/guides/using-ingress-with-grpc/?_ga=2.117987273.1135189218.1620283336-269059471.1620283336
- https://docs.konghq.com/kubernetes-ingress-controller/1.1.x/deployment/minikube/?_ga=2.140095603.1135189218.1620283336-269059471.1620283336
API gateway 는 마이크로 서비스 아키텍처의 핵심 부분이다. Kong Ingress Controller 은 쿠버네티스 클러스터에서 이러한 롤을 잘 수행한다.
당신은 다른 쿠버네티스 리소스처럼 동일한 방법으로 관리할 수 있다.