이 연재글은 EKS(Elastic Kubernetes Service) 실습의 4번째 글입니다.

이번 시간에는 kubernetes cluster에 배포된 application에서 외부 시스템에 접속이 가능한지 확인하는 방법에 대하여 살펴보겠습니다. 일반적으로 aws에서 eks(kubernetes) cluster 생성 시 별도의 vpc를 구성하여 사용합니다. 따라서 개발자 입장에서는 별도의 network에 구성된 kubernetes cluster에 docker application을 배포하기 전에 외부 vpc의 자원들(db, cache 등…)에 접근이 가능한지 확인할 필요가 있습니다.

아래 이미지의 경우 극단적인 경우인데 각각의 aws 자원들이 서로 다른 VPC에 존재하는 경우입니다. 이런 경우 요청받는 쪽에서 Port를 열어주는 작업이 필요하거나 VPC 간에 Peering Connection 또는 Transit Gateway 등의 VPC간 통신이 가능하도록 하는 세팅이 필요합니다.

하지만 eks에 배포되는 docker image의 경우 OS를 포함하지 않고 단독으로 application으로만 구성되는 경우가 대부분이기 때문에 해당 pod에 접속하더라도 telnet과 같은 명령어를 사용할 수 없어 통신이 가능한지 여부를 판단하기 어렵습니다.

해결책

가장 간단한 해결책은 Linux Docker 이미지를 eks cluster에 배포하고 해당 pod에 접속하여 telnet 명령을 내려보는 것입니다. 하지만 명령 한두 개 내려보자고 OS 자체를 배포하는 것은 배보다 배꼽이 더 큰 경우라 부담이 될 수 있습니다. minimal한 docker이미지로 유명한 alpine 리눅스를 설치해 보는것이 답이 될 수도 있겠지만 실습에서는 busybox를 설치하여 telnet 명령어를 사용해 보도록 하겠습니다.

busybox

BusyBox는 하나의 실행 파일 안에 스트립 다운된 일부 유닉스 도구들을 제공하는 소프트웨어이다. 리눅스, 안드로이드, FreeBSD와 같은 다양한 POSIX 환경에서 실행되지만 도구들 중 다수가 리눅스 커널이 제공하는 인터페이스와 함께 동작하도록 설계되어 있다. 자원이 매우 적은 임베디드 운영 체제를 위해 작성되었다.

busybox는 linux 명령어를 사용할 수 있게 해주는 Compact한 소프트웨어라고 보면 됩니다. busybox를 설치하면 linux 환경이 아니라도 linux 명령어를 대부분 사용할 수 있습니다. 더구나 busybox는 docker image로 제공이 되므로 바로 설치하여 사용해 볼 수 있습니다.

다음 명령을 이용하면 kubernetes cluste에 busybox를 빠르게 배포하고 바로 shell 환경을 열어 사용할 수 있습니다. exit로 shell에서 빠져나오면 busybox도 cluster에서 제거되므로 커넥션을 가능여부를 간단하게 체크하는데 유용합니다.

$ kubectl run busybox --rm -it --image busybox --restart=Never
/ # telnet rds.ap-northeast-2.amazonaws.com 3306
Connected rds.ap-northeast-2.amazonaws.com
/ # telnet kafka.ap-northeast-2.amazonaws.com 9092
Connected kafka.ap-northeast-2.amazonaws.com
/ # telnet redis.ap-northeast-2.amazonaws.com 6379
Connected redis.ap-northeast-2.amazonaws.com

busybox에서 사용가능한 linux command

https://www.commandlinux.com/man-page/man1/busybox.1.html

[, [[, acpid, adjtimex, ar, arp, arping, ash, awk, basename, blockdev, brctl, bunzip2, bzcat, bzip2, cal, cat, chgrp, 
chmod, chown, chroot, chvt, clear, cmp, cp, cpio, crond, crontab, cttyhack, cut, date, dc, dd, deallocvt, depmod, 
devmem, df, diff, dirname, dmesg, dnsdomainname, dos2unix, dpkg, dpkg-deb, du, dumpkmap, dumpleases, echo, ed, egrep, 
env, expand, expr, false, fdisk, fgrep, find, fold, free, freeramdisk, fstrim, ftpget, ftpput, getopt, getty, grep, 
groups, gunzip, gzip, halt, head, hexdump, hostid, hostname, httpd, hwclock, id, ifconfig, ifdown, ifup, init, insmod, 
ionice, ip, ipcalc, kill, killall, klogd, last, less, ln, loadfont, loadkmap, logger, login, logname, logread, losetup, 
ls, lsmod, lzcat, lzma, lzop, lzopcat, md5sum, mdev, microcom, mkdir, mkfifo, mknod, mkswap, mktemp, modinfo, modprobe, 
more, mount, mt, mv, nameif, nc, netstat, nslookup, od, openvt, passwd, patch, pidof, ping, ping6, pivot_root, poweroff,
printf, ps, pwd, rdate, readlink, realpath, reboot, renice, reset, rev, rm, rmdir, rmmod, route, rpm, rpm2cpio, run-parts,
 sed, seq, setkeycodes, setsid, sh, sha1sum, sha256sum, sha512sum, sleep, sort, start-stop-daemon, stat, strings, stty, 
su, sulogin, swapoff, swapon, switch_root, sync, sysctl, syslogd, tac, tail, tar, taskset, tee, telnet, telnetd, test, 
tftp, time, timeout, top, touch, tr, traceroute, traceroute6, true, tty, tunctl, udhcpc, udhcpd, umount, uname, 
uncompress, unexpand, uniq, unix2dos, unlzma, unlzop, unxz, unzip, uptime, usleep, uudecode, uuencode, vconfig, vi, watch,
watchdog, wc, wget, which, who, whoami, xargs, xz, xzcat, yes, zcat

busybox에 없는 curl 명령 사용하기

$ kubectl run curl -it --rm --image curlimages/curl -- sh
$ curl ifconfig.me
34.64.165.51

Mysql 접속 가능 여부, 조회 테스트

k8s service -> mysql 통신 테스트를 하거나 직접 쿼리 조회가 필요할 경우 mysql cli을 k8s상에 구동시켜 테스트 해볼 수 있습니다.

$ kubectl run mysql-client --image=mysql:5.7 -it --rm --restart=Never -- /bin/bash
bash-4.2# mysql -h [mysql 호스트] -u[유저ID] -p[DB패스워드]
연재글 이동[이전글] EKS Cluster에 Docker Image 배포하기
[다음글] EKS에 ALB 적용하여 서비스 노출하기(Ingress Application Loadbalancer)