AWS EC2 서버 구축

구본식·2022년 8월 22일
3

프로젝트 진행에 앞서 AWS EC2를 이용해서 서버 구축 및 배포,재배포를 테스트 해볼것이다.

💡참고로 CI/CD를 하기위해서 사이드 프로젝트 마지막에 배포시 gitAction,jenkis등의 tool를 사용하여 해볼 예정이다. 또한 필요한 프로그램을 지금은 직접 설치하는데 AWS가 제공하는 엘라스틱빈 스톡을 사용하여 직접 필요한 기능들을 설치하지 않을것이다.

지금은 서버구축, 배포, 재배포를 하나씩 명령어를 통해 해보고 github 소스코드를 다운 받아 빌드하는 방식으로 해보겠다. 마지막에 자동재시작, 재배포를 스프립트로 작성하여 쉽게 할수 있게 해볼것이다.

1. AWS EC2 인스턴스 생성 및 설정

AWS 페이지에 접속하여 기본적인 회원가입을 한다.

ubuntu 20.0.4 버전과 인스턴스 유형을 t2.micro로 설정하였다.

💡참고
AWS는 서버를 대여해주는 서비스 이며 각 서버들을 인스턴스라고 멸칭한다.
최초 회원가입시 1년간 한달에 750시간 무료로 서버를 사용가능하다. 또한 인스턴스 유형이 t2.micro에 한해서만 무료이다.

이부분은 많은곳에서 정보를 찾아볼수 있으니 넘어가겠다.

2. AWS EC2 포트 개방(인바운드 규칙 정하기)

웹으로 해당 AWS EC2 서버에 접속을 하기위해서 해당 ip의 port를 개방해야 된다. 이부분은 인바운드 규칙에서 설정할 수있다.

tomcat를 통한 웹애플리케이션의 포트 번호를 "8888"로 설정하였고 아래 포트는 규모가 크지않은 프로젝트 이기 때문에 AWS EC2 RDS를 사용하지 않고 서버내에서 MySQL을 설치하여 가동하는 구조이다.
그렇기 때문에 MySQL를 MysqlWorkbench를 통해 외부에서 접속할수 있도록 하기 위해서 "3306" 포트를 열어두었다.

💡더불어
프로젝트 배포 단계에서 시간이 된다면 AWS EC2 RDS 서버를 따로 구축해서 연결해보겠다!!
지금 안한 이유는 이건 쉬울거 같아서 사실 넘어감...ㅎㅎ 그리구 서버를 2개 대여하니깐 추가로 비용이 발생하지 않을까?? 싶어서..ㅎㅎ

3. AWS EC2 서버에 필요한 프로그램 설치


3.1 MySQL 설치

사실 AWS EC2 서버내에 DB를 설치하여 가동하는 것은 좋지 않은 것이다.
일반적으로 AWS RDS 서버를 따로 DB로 구동하게된다. 하지만 해당 프로젝트는
프론트엔드 개발자 한분과 협업하여 진행되기 때문에 프로젝트 규모가 크지않아 이러한 방식으로 진행하였다.

1. ubuntu 패키지 정보 업데이트

sudo apt update

2. MySQL 설치

sudo apt install || mysql-server

3. 설치 확인 및 버전 확인

mysql --version

4. mysql 실행 여부 확인

sudo apt-get install net-tools : "nply"과 같은 명렁어를 나중에 사용하기 위해 다운
netstat -nlpt : 실행중인 포트 확인 -> "127.0.0.1:33060"가 나오니 작동중인걸 확인됨!
temp

5. mysql 외부 접속 설정

서버내에서 DB를 확인하고 할수 없으니 외부에서 mysqlworkbench를 통해서 접속하여 볼수 있게 하기 위해서

(1) mysqld.cnf 파일 수정
cd /etc/mysql/mysql.conf.d
sudo vi mysqld.cnf : bind-address를 127.0.0.1 -> 0.0.0.0으로 변경

(2) mysql 접속
sudo mysql -u root -p : 패스워드를 설정했으면 입력하고 접속

(3) 외부 접속 계정 설정 및 권한 부여
create user '계정이름'@'%' indentified by '패스워드';
grant all privileges on *.* '계정이름'@'%' with grant option;

(4) AWS EC2 인스턴스에 mysql 접속 포트 추가

이부분은 위에 그림에서 보듯이 설정을 해놓았다.!


3.2 JDK 설치

sudo apt-update
sudo apt install openjdk-11-jdk

해당 글은 AWS EC2 서버를 구축하는 것이 목표이기 때문에 JDK의 역할,기능들은 넘어가고 필요한 단계별 해야할 일을 설명할것이다.


3.3 github 에서 소스코드 다운받기

💡참고
지금은 github에 소스코드을 올리면 해당 소스코드를 서버로 다운받아 build 하는 방식으로 하였다. 하지만 gitaction을 나중에 사용하여 github에 소스코드를 업데이트 할때마다 gitaction이 이를 감지하여 AWS EC2환경과 동일한 환경에서 build test를 하여 정상적이라면 AWS EC2 서버로 build 된 .jar.파일만 전송하도록 할 것이다.

git clone https://github.com/https://github.com/BonSik-Koo/AMS_Algoritrim-Mannage-Service.git : 해당 주소에서 소스코드를 서버로 다운 받는다.


3.4 gradlew 실행권한 주기

초기에는 해당 gradlew를 실행할수 있는 권한이 없기 때문에 권한을 줘야된다.

cd ~/AMS_Algoritrim-Mannage-Service : 해당 디렉토리로 이동
chmod u+x gradlew : 실행권한 주기


3.5 gradlew로 프로젝트를 jar파일로 변경하기

./gradlew build : test코드를 포함해서 프로젝트를 실행파일(jar파일)로 만든다.

정상적으로 마치면 build라는 디렉토리가 새로 생기게 된다.


3.6 java로 jar 실행(배포) -> "nohup으로 실행"

현재 AWS EC2 서버를 MobaXterm이라는 프로그램으로 원격접속하여 사용하고 있다.
이러한 상황에서 그냥 java jar를 실행하게 되면 Mobaxterm 프로그램을 종료하게 되면 자동으로 jar파일도 종료되게 된다. 이러한 문제점을 막기 위해 "백그라운드 실행"을 해야된다.

`cd ~/AMS_Algoritrim-Mannage-Service/build/libs` : 해당 디렉토리로 이동

`nohup java -jar /home/ubuntu/AMS_Algoritrim-Mannage-Service/build/libs/AMS-0.0.1-SNAPSHOT.jar 1>~/log.out 2>~/error.out &`

해당 jar파일을 시작했을때 출력되는 문구에 대해서 표준출력은 log.out파일에 쓰고, 에러출력은 error.out파일에 쓰게 한다. 이렇게 분리하게 되면 *.jar파일 실행시 정상적으로 실행이 안된 경우 error.out파일만 확인하여 이유를 확인하면 된다.

또한 마지막에 & 기호가 백그라운드로 실행하겠다는 의미가 된다.

💡추가
기본적으로 AWS EC2는 미국기준의 시간으로 되어있기 때문에 로그같은 것을 찍을때 시간이 미국시간이 나타난다. 그렇기때문에 한국 시간으로 바꾸어 주는것이 좋다.

timedatectl : 미국시간으로 되어있는지 확인
timedatectl list-timezones | grep Seoul : 타임리스트에서 Seoul이 있는지 확인
sudo timedatectl set-timezone Asiz/Seoul : 설정 변경


3.7 Linux crontab 사용하기

crontab 은 리눅스서버에서 예약된 작업을 실행시키는 스케쥴러의 역할을 한다.

💡여기서 사용하는 이유?
: 실행중인(배포된) 프로그램이 종료되었을때 자동으로 재시각이 되지않는다. 그렇면 관리자가 직접 프로그램을 실행시켜야된다. 이러한 과정이 번거롭기 때문에 필요한 기능을 스크립트
작성하여cron으로 등록하여 주기적으로 실행되게 한다.

(1) 재시작을 위한 스크립트(spring.restart.sh)

SPRING_PID=$(pgrep -f AMS-0.0.1-SNAPSHOT.jar)
SPRING_PATH="/home/ubuntu/AMS_Algoritrim-Mannage-Service/build/libs/AMS-0.0.1-SNAPSHOT.jar"

echo $SPRING_PID
echo $SPRING_PATH

if [ -z "$SPRING_PID" ]; then
        echo "스프링 종료된 상태...."
        echo "스프링 재시작 ...."
        echo "스프링 재시작 - $(date)" 1>>/home/ubuntu/cron-restart/spring-restart.log
        nohup java -jar $SPRING_PATH 1>/home/ubuntu/log.out 2>/home/ubuntu/error.out &
else
        echo "스프링 시작된 상태...."
fi

(2) 종료를 위한 스크립트(spring.stop.sh)

echo "SPRINGBOOT STOP...."
SPRING_PID=$(pgrep -f AMS-0.0.1.SNAPSHOT.jar)
kill -9 $SPRING_PID

(3) 종료시 재시작되는 스크립트를 포함한 cron 등록 스크립트(display.sh)

# 1. 최초 배포 프로세스
echo "depoly start ..."
echo "1. JDK install"
echo "2. github project download"
echo "3. gradlew 실행 권한 주기"
echo "4. project build 하기"
echo "5. ubuntu timezone setting 하기"
echo "6. nohup으로 springboot 실행시키기"

#2. 스프링 서버종료시 재시작
echo "crontab 등록 - spring restart..."
crontab -l > crontab_new #crontab의 주석을 복사
echo "* * * * * /home/ubuntu/cron-restart/spring.restart.sh" 1>> crontab_new #지속적으로 실행시킬 스크립트 설정
crontab crontab_new #cron 으로 등록
rm crontab_new

위 (1),(2),(3) 개의 스크립트 생성후 모두 chmod u+x 스크립트이름으로 실행권한을 부여해준다.

* * * * *의 의미는 cron 1분 간격으로 등록한 스크립트를 실행한다는 의미이다.

depoly.sh을 한번 실행하게 되면 Linux cron으로 등록되게 되고 매 1분마다 프로그램 실행여부를 확인하고 종료시 자동으로 지속하여 실행 시켜준다.

(4) 재배포를 위한 스크립트(redeploy.sh)

echo "Springboot redelopy..."

echo "Springboot Stop..."
SPRING_PID=$(pgrep -f AMS-0.0.1-SNAPSHOT.jar)
kill -9 $SPRING_PID

echo "file delete"
rm -rf /home/ubuntu/AMS_Algoritrim-Mannage-Service

echo "git clone download"
git clone https://github.com/BonSik-Koo/AMS_Algoritrim-Mannage-Service.git

cd /home/ubuntu/AMS_Algoritrim-Mannage-Service
chmod u+x gradlew

echo "build..."
./gradlew build

nohup java -jar /home/ubuntu/AMS_Algoritrim-Mannage-Service/build/libs/AMS-0.0.1-SNAPSHOT.jar 1>/home/ubuntu/log.out 2>/home/ubuntu/error.out &

재배포를 해야되는 상황이면 github에 소스코드를 업데이트 하고 해당 redeploy.sh을 실행하게 되면 서버에서 실행되고 있는 프로그램을 종료하고 디렉토리 또한 삭제한 후 github에서 변경된 소스코드를 다운받은뒤 빌드하여 실행시켜준다.

처음에 deploy.sh을 실행시켜 자동 재시작이 되게 만들었기 때문에 여기서는 해당 스크립트를 실행시켜주지 않아도 된다.


✅마치며...
지금은 단순히 서버 구축, 배포, 재배포를 직접 명령어를 통해 하고 스크림트와 cron을 통해 구현해보았다. 다시 한번 말하자면 나중에 프로젝트 배포할때는 gitaction tools을 사용하여 github에 소스코드를 업데이트 하면 자동으로 build를 하여 jar 파일만 AWS EC2 서버에 배포되게 할것이다.
해당 tools을 사용하게 되면 재배포 할때 기존 서버를 종료시키지 않고 CI/CD를 할수 있을 것이다.

시간이 있다면 AWS RDS서버를 사용하여 DB전용 서버를 구축하여 연결해볼것이고 엘라스틱빈 스톡을 사용하여 기본적인 필요한 프로그램이 설치된 서버를 사용해볼 것이다. 또한 서버를 여러대 구축하여 AWS 로드 밸런서 를 사용하여 이용자들의 수가 급증했을때 이용자를 여러서버에 분배시킬수 있게 해볼것이다.

profile
백엔드 개발자를 꿈꾸며 기록중💻

0개의 댓글