Skip to content

Commit

Permalink
Merge pull request #612 from woowacourse-teams/feat/611-update-infras…
Browse files Browse the repository at this point in the history
…tructure

인프라 개편 작업 (백엔드 dockerize 및 현재 운영 구조 코드에 반영)
  • Loading branch information
solo5star authored Jan 8, 2024
2 parents 82452e4 + 148f4d1 commit 0b6555a
Show file tree
Hide file tree
Showing 7 changed files with 103 additions and 123 deletions.
63 changes: 27 additions & 36 deletions infrastructure/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,72 +7,63 @@

<!-- omit from toc -->
## Table of Contents
- [ci](#ci)
- [운영](#운영)
- [주요 인스턴스 목록](#주요-인스턴스-목록)
- [환경변수](#환경변수)
- [설치 방법](#설치-방법)
- [prod](#prod)
- [CI](#ci)
- [주요 인스턴스 목록](#주요-인스턴스-목록-1)
- [환경변수](#환경변수-1)
- [설치 방법](#설치-방법-1)

<br><br>

## ci
CI/CD를 수행하는 인스턴스입니다. ci/ 폴더의 파일들 및 `docker-compose.yml` 에는 CI/CD 환경에 필요한 코드 및 서비스들이 있습니다.
## 운영
`infrastructure` 폴더의 파일들 및 `infrastructure/docker-compose.yml` 에는 운영 환경에 필요한 코드 및 서비스들이 있습니다.

### 주요 인스턴스 목록
* **TeamCity**: CI/CD 시스템입니다
* **TeamCity Agent 1, 2, 3**: 빌드 및 배포를 수행하는 에이전트입니다.
* **Webhook Broker**: TeamCity Webhook 메세지를 Slack Webhook 으로 전달해주는 Webhook 브로커입니다.
* **nginx**: 프론트엔드 html, css, js 정적 리소스 서빙 및 백엔드 서버 리버스 프록시 역할을 수행합니다
* **MySQL**: 백엔드에서 사용하는 DB입니다
* **Spring**: API 요청 및 비즈니스 로직을 수행하는 Spring 서버 인스턴스입니다

### 환경변수
|이름|설명|예시|
|-|-|-|
|`SLACK_WEBHOOK_URL`|빌드 결과 알림을 받을 Slack Webhook URL 입니다|`https://hooks.slack.com/services/XXXXXXXXXXX/XXXXXXXXXXX/XXXXXXXXXXXXXXXXXXXXXXXX`|
|`SLACK_CHANNEL`|빌드 결과 알림 메세지가 전송될 Slack 채널입니다|`C05PNZ142H6S`|

|`MYSQL_ROOT_PASSWORD`|MySQL DB root 계정의 패스워드입니다|`supersecretpassword`|
|`MYSQL_USER`|MySQL DB 사용자 계정 이름입니다|`myuser`|
|`MYSQL_PASSWORD`|MySQL DB 사용자 계정의 패스워드입니다|`supersecretpassword`|
|`AUTH_KEY`|JWT 발급에 사용될 Secret Key 입니다|`supersecretkey`|
|`AUTH_GOOGLE_CLIENTID`|Google OAuth 에서 제공하는 Client ID 값입니다|`780816631155-gbvyo1o7r2pn95qc4ei9d61io4uh48hl.apps.googleusercontent.com`|
|`AUTH_GOOGLE_CLIENTSECRET`|Google OAuth 에서 제공하는 Client Secret 값입니다|`GOCSPX-XXX`|
|`AUTH_KAKAO_CLIENTID`|Kakao OAuth 에서 제공하는 Client ID 값입니다|`ccd9ea 136632b1fe01c0e918381`|
|`AUTH_KAKAO_CLIENTSECRET`|Kakao OAuth 에서 제공하는 Client Secret 값입니다|`l7BpJ8YxvFotJYEu2WkH4NsvWM9qy47E`|

### 설치 방법
```bash
cd ci
docker compose up -d
```
위의 명령으로 TeamCity 서버 및 에이전트, Webhook 브로커를 실행시킬 수 있습니다.
Agent Authorize는 Web UI에서 직접 해야 합니다.
nginx와 MySQL, Spring Server를 켜주면 됩니다.

<br><br>

## prod
운영 환경에서 사용하는 인스턴스입니다. prod/ 폴더의 파일들 및 `docker-compose.yml` 에는 운영 환경에 필요한 코드 및 서비스들이 있습니다.
## CI
`infrastructure/ci/` 폴더의 파일들 및 `infrastructure/ci/docker-compose.yml` 에는 CI/CD 환경에 필요한 코드 및 서비스들이 있습니다.

### 주요 인스턴스 목록
* **nginx**: 프론트엔드 html, css, js 정적 리소스 서빙 및 백엔드 서버 리버스 프록시 역할을 수행합니다
* **MySQL**: 백엔드에서 사용하는 DB입니다
* **certbot**: HTTPS 인증서 발급을 수행합니다
* **TeamCity**: CI/CD 시스템입니다
* **TeamCity Agent 1, 2, 3**: 빌드 및 배포를 수행하는 에이전트입니다.
* **Webhook Broker**: TeamCity Webhook 메세지를 Slack Webhook 으로 전달해주는 Webhook 브로커입니다.

### 환경변수
|이름|설명|예시|
|-|-|-|
|`DOMAIN`|HTTPS 인증서를 발급받을 도메인 이름입니다|`www.example.com`|
|`EMAIL`|HTTPS 인증서를 발급받을 때 사용할 이메일입니다|`[email protected]`|
|`MYSQL_ROOT_PASSWORD`|MySQL DB root 계정의 패스워드입니다|`supersecretpassword`|
|`MYSQL_USER`|MySQL DB 사용자 계정 이름입니다|`myuser`|
|`MYSQL_PASSWORD`|MySQL DB 사용자 계정의 패스워드입니다|`supersecretpassword`|
|`SLACK_WEBHOOK_URL`|빌드 결과 알림을 받을 Slack Webhook URL 입니다|`https://hooks.slack.com/services/XXXXXXXXXXX/XXXXXXXXXXX/XXXXXXXXXXXXXXXXXXXXXXXX`|
|`SLACK_CHANNEL`|빌드 결과 알림 메세지가 전송될 Slack 채널입니다|`C05PNZ142H6S`|

### 설치 방법
```bash
cd prod
docker compose up certbot
```
먼저, certbot을 사용하여 HTTPS 인증서를 발급받아야 합니다. certbot은 [HTTP-01 challenge](https://letsencrypt.org/docs/challenge-types/#http-01-challenge) 방법을 사용하여 HTTPS 인증서 발급을 시도할 것입니다. 이 방법을 사용하기 위해 certbot은 80 포트를 점유하여 웹 서버를 열기 때문에 nginx와 함께 켜면 안됩니다.

```bash
docker compose up -d web
```
HTTPS 인증서 발급이 완료되면 nginx를 켜주세요.

```bash
docker compose up -d mysql
cd ci
docker compose up -d
```
MySQL은 위 과정과 상관없이 별도로 켜주면 됩니다.
위의 명령으로 TeamCity 서버 및 에이전트, Webhook 브로커를 실행시킬 수 있습니다.
Agent Authorize는 Web UI에서 직접 해야 합니다.
4 changes: 2 additions & 2 deletions infrastructure/ci/docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -74,8 +74,8 @@ services:
- ./webhook-broker:/app
command: run --allow-net --allow-read --allow-env /app/app.js
environment:
- SLACK_WEBHOOK_URL=${SLACK_WEBHOOK_URL:?'SLACK_WEBHOOK_URL required'}
- SLACK_CHANNEL=${SLACK_CHANNEL:?'SLACK_CHANNEL required'}
- SLACK_WEBHOOK_URL=${SLACK_WEBHOOK_URL:?}
- SLACK_CHANNEL=${SLACK_CHANNEL:?}
- SLACK_USERNAME=TeamCity
- 'SLACK_ICON_EMOJI=:teamcity:'

Expand Down
56 changes: 56 additions & 0 deletions infrastructure/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
version: "3.8"
services:
web:
image: nginx
restart: unless-stopped
ports:
- 80:80
volumes:
- ./nginx.conf.template:/etc/nginx/templates/default.conf.template

mysql:
image: library/mysql:8.0.33
restart: unless-stopped
ports:
- 20000:3306
volumes:
- db-data:/var/lib/mysql
command:
- mysqld
- --character-set-server=utf8mb4
- --collation-server=utf8mb4_general_ci
environment:
- MYSQL_DATABASE=yozm-cafe
- MYSQL_ROOT_PASSWORD=${MYSQL_ROOT_PASSWORD:?}
- MYSQL_USER=${MYSQL_USER:?}
- MYSQL_PASSWORD=${MYSQL_PASSWORD:?}
- TZ=Asia/Seoul

server:
build:
context: ../server
restart: unless-stopped
ports:
- 8080:8080
environment:
- SPRING_DATASOURCE_URL=jdbc:mysql://mysql:3306/yozm-cafe?useSSL=false&allowPublicKeyRetrieval=true&characterEncoding=UTF-8&serverTimezone=UTC
- SPRING_DATASOURCE_USERNAME=${MYSQL_USER:?}
- SPRING_DATASOURCE_PASSWORD=${MYSQL_PASSWORD:?}
- SPRING_AUTH_KEY=${AUTH_KEY:?}

- SPRING_AUTH_GOOGLE_TOKENURI=https://www.googleapis.com/oauth2/v4/token
- SPRING_AUTH_GOOGLE_AUTHURI=https://accounts.google.com/o/oauth2/v2/auth
- SPRING_AUTH_GOOGLE_REDIRECTURI=http://localhost:3000/auth/google
- SPRING_AUTH_GOOGLE_SCOPE=https%3A//www.googleapis.com/auth/userinfo.profile
- SPRING_AUTH_GOOGLE_CLIENTID=${AUTH_GOOGLE_CLIENTID:?}
- SPRING_AUTH_GOOGLE_CLIENTSECRET=${AUTH_GOOGLE_CLIENTSECRET:?}

- SPRING_AUTH_KAKAO_TOKENURI=https://kauth.kakao.com/oauth/token
- SPRING_AUTH_KAKAO_AUTHURI=https://kauth.kakao.com/oauth/authorize
- SPRING_AUTH_KAKAO_REDIRECTURI=http://localhost:3000/auth/kakao
- SPRING_AUTH_KAKAO_SCOPE=openid,profile_nickname,profile_image
- SPRING_AUTH_KAKAO_CLIENTID=${AUTH_KAKAO_CLIENTID:?}
- SPRING_AUTH_KAKAO_CLIENTSECRET=${AUTH_KAKAO_CLIENTSECRET:?}

volumes:
db-data:
10 changes: 10 additions & 0 deletions infrastructure/nginx.conf.template
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
server {
listen 80;

client_max_body_size 0;

location /api {
rewrite ^/api(.*)$ $1 break;
proxy_pass http://server:8080;
}
}
51 changes: 0 additions & 51 deletions infrastructure/prod/docker-compose.yml

This file was deleted.

23 changes: 0 additions & 23 deletions infrastructure/prod/nginx.conf.template

This file was deleted.

19 changes: 8 additions & 11 deletions server/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -1,24 +1,21 @@
version: "3.8"
services:
mysql:
platform: linux/arm64/v8
image: library/mysql:8.0.33
ports:
- 20000:3306
volumes:
- db-data:/var/lib/mysql
command:
- mysqld
- --character-set-server=utf8mb4
- --collation-server=utf8mb4_general_ci
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: yozm-cafe
MYSQL_USER: user
MYSQL_PASSWORD: password
MYSQL_USER: ${DB_USERNAME:?}
MYSQL_PASSWORD: ${DB_PASSWORD:?}
TZ: Asia/Seoul
command: [ "mysqld", "--character-set-server=utf8mb4", "--collation-server=utf8mb4_general_ci" ]
volumes:
- db-data:/var/lib/mysql
# my.cnf의 server_id 값은 복제에 참여한 MySQL 서버들이 고유하게 가지고 있는 식별 값이다.
# 이 값은 바이너리 로그에 이벤트별로 이벤트가 최초로 발생한 MySQL을 식별하기 위해 사용되며, 기본값이 모두 1이다.
# 이 때문에 Master 서버와 Slave 서버를 구별할 수 있도록 Slave 서버의 server_id를 바꾸어 주기 위해 volume 매핑을 진행해야한다.
# my.cnf 파일이 존재해야한다.
- ./my.cnf:/etc/my.cnf

volumes:
db-data:

0 comments on commit 0b6555a

Please sign in to comment.