⛺ MTZ(마운틴즈)
🎉 마운틴즈 소개 | About Us
등산에 관심이 생긴, 취미가 등산인, 산을 정복하고 싶은 여러분 주목!
남녀노소 누구나 '등산왕'이 될 수 있는 등산 필수앱 "MTZ"를 소개합니다!
:evergreen_tree: 웹사이트 | Website MTZ 바로가기
Link List
#### 🌎 프로젝트 문서 | [Project Docs](https://docs.google.com/spreadsheets/d/1HtE2SUzSS5GC-LgEqoSsjKZNVe2-Jc1JQHZ8GDhCGHs/edit#gid=0)
#### 🌎 Notion Link | [Notion Link](https://www.notion.so/MTZ-251008683c60489c909a51ee189279e4)
#### 🌎 PostMan API Link | [PostMan API로 Click!](https://documenter.getpostman.com/view/23686396/2s8YzUvg4o)
#### 🌎 Swagger API Link | [Swagger API로 Click!](https://www.dongjae-bk.shop/swagger-ui.html)
#### 🔑 FE Github URL | [FE GITHUB로 Click!](https://github.com/M0untainZ/MTZ-Front.git)
#### 🔒 BE Github URL | [BE GITHUB로 Click!](https://github.com/M0untainZ/MTZ-BE.git)
🔖목차
🛠 아키텍쳐 | Architecture
📖 페이지별 기능 | Feature per Page
PAGE |
FUNCTION |
📑 MAIN |
메인화면, 위치정보 기반 날씨, 추천 등산 코스, 랭킹, 인증 사진 리스트 |
📑 DETAIL 01 |
산 리스트, 산 리스트 필터, 무한 스크롤 |
📑 DETAIL 02 |
각 산에 대한 정보, 카카오맵 기반 산의 위치, 사진 인증하기 |
📑 CERTIFICATION |
인증 사진 리스트, 인증사진 지역 필터 , 무한 스크롤 |
📑 MYPAGE |
프로필 수정, 뱃지 리스트 |
📑 LOGIN |
로그인, 회원가입, 소셜(카카오) 로그인 |
💻 기술 스택 | Tech Stack
- JWT를 이용한 로그인 기능
- OAuth2 소셜 로그인 카카오톡 지원
- QueryDSL를 이용한 다양한 경우의 검색 요청 일괄 처리
- Redis를 이용한 자주 조회하는 데이터 캐싱 처리
- Slack Webhook, Logback를 이용한 배포된 서버의 에러 로그를 쉽게 확인 가능
- Route53, ELB를 활용한 HTTPS 처리
- Githib Action, S3, CodeDeploy를 이용한 CI/CD 자동 배포
- Nginx를 이용한 무중단 배포
- S3, CloudFront 캐싱 정책
- react-query 캐싱
✨ 프로젝트 기술 정보 | Project Tech Information
🔑 FRONTEND
🔒BACKEND
백엔드 개발환경
보안
AWS
CI/CD
✨ ERD
✨ 라이브러리 | Library
- @reduxjs/toolkit
- axios
- browser-image-compression
- react-icons
- react-images-uploading
- react-intersection-observer
- react-query
- react-redux
- react-router-dom
- react-scripts
- react-toastify
- redux
- redux-thunk
- styled-components
- sweetalert2
- sweetalert2-react-content
- swiper
✨트러블슈팅 | Trouble Shooting
🔑 FE
웹 성능 개선 및 캐싱
### 문제상황
![mater01](https://user-images.githubusercontent.com/102575747/207054952-d5ce91f6-ce16-49b2-ae93-8a504f6ecfd3.png)
![mater02](https://user-images.githubusercontent.com/102575747/207055031-22984a9c-888b-4434-87e6-6fbd63b7edbe.png)
- 이미지가 많이 사용되는 프로젝트 특성상 PNG 나 JPG 같은 고화질 이미지를 많이 사용함
- 이러한 이미지들은 웹 성능을 저하시킴
### 의견조율
- 화질은 최대한 유지하면서 압축률은 높일 수 있는 webp 형식의 이미지 파일로 교체
- 서버에 있는 이미지를 불러올 땐 react-query의 캐싱기능을 활용해 이미지 랜더링 속도를 향상
- 프로젝트 내부에서 사용되는 이미지들은 S3 와 CloudFront 의 캐싱 정책을 변경해 처리
### 결과
**성능테스트 결과**
![solution01](https://user-images.githubusercontent.com/102575747/207055071-9d3717f0-3179-4b80-8591-55923de26ec6.png)
![solution02](https://user-images.githubusercontent.com/102575747/207055129-9bf1ef34-c4a6-473d-b87c-6157650986e4.png)
UX측면에서 GeoLocation API 사용하기
### 문제상황
- 프로젝트에서 사용자의 현재 위치 날씨를 보여주기 위해 사용자 위치정보를 묻는 geolocation API 를 사용
- geolocation API 는 별다른 처리를 하지 않으면 페이지 로드시 곧바로 사용자에게 위치 정보 권한 요청을 보냄
![mater03](https://user-images.githubusercontent.com/102575747/207055608-b6dadfbe-908e-4960-92c7-8ec1ec9110ec.png)
하지만 이런 방식은 사용자에게 신뢰감을 줄 수 없다고 판단하였습니다.
(사용자 입장에서 어떤 목적을 가진 사이트인지 판단하기 어려운데 권한 요청을 보내면 거부감이 들기 때문)
### 의견조율
![solution06](https://user-images.githubusercontent.com/102575747/207065960-b81e6bd8-59e5-4a58-948b-5d8e771f8683.png)
![solution07](https://user-images.githubusercontent.com/102575747/207066329-9c2a1a76-086a-4dfe-a50a-abf5c07b75ab.png)
- 크롬 문서에서도 사용자에게 위치 정보를 책임감 있게 요청하라는 내용이 명시되어 있음
- 페이지 로드시 곧바로 권한 요청을 묻는게 아닌 사용자의 행동에 따라 수동적으로 권한요청을 할 수 있도록 ui 를 변경
![soluton03](https://user-images.githubusercontent.com/102575747/207055661-cf3e8d41-cd5f-49d6-9600-65fdef76d58e.png)
### 결과
- 날씨보기 버튼을 클릭하면 다음과 같이 요청을 보내고
![solution04](https://user-images.githubusercontent.com/102575747/207055774-3f6df737-b053-424b-b389-6f3ad208b9c5.png)
- 허용했을 경우에 api를 호출하는 방식으로 개선
![solution05](https://user-images.githubusercontent.com/102575747/207055827-5396abf8-05c4-4eba-8dfd-747ba6b3b1f6.png)
- 개선 후 성능 테스트 결과 Best Practices 부분도 상당히 개선된 것을 확인할 수 있음
![solution08](https://user-images.githubusercontent.com/102575747/207066391-20b979f9-ec00-4480-9ef7-e38bac21a134.png)
🔒 BE
필터 검색시 데이터 동적처리 하기
### 문제상황
- Spring Data JPA만을 가지고 프로젝트를 하던중 필터검색을 구현해야하는 상황을 맞이함
- 동적 처리를 위해 JPQL을 사용했으나 문자열을 통해서 쿼리를 만들게 되면 작성한 문자열 쿼리 중 띄어쓰기 혹은 알파벳의 오류가 있을 경우 이를 컴파일 타임에서 잡아주지 못한다는 단점이 존재했음
### 의견조율
**QueryDsl을 사용하여 동적으로 데이터를 처리해보기**
- 문자열이 아닌 자바 코드로 쿼리를 생성하여 더 쉽고 간결하며
형태도 SQL과 비슷하게 개발할 수 있어 가독성이 좋은 QueryDsl을 사용하기로 함
### 결과
![필터검색 사진](https://user-images.githubusercontent.com/97796338/206993318-228cf809-b333-48ef-9c13-d04065574542.png)
태그 조회시 데이터 처리 성능 개선
### 문제상황
사용자들에게 공통적이고 반복적으로 보여지게될 정보에 대해서 처리 속도를 높여주고 싶은 생각이 듬
### 의견조율
**Redis를 사용하여 캐싱처리 해보기**
- 같은 내용을 보여주는 데이터라면 캐싱처리를 해서 매번 DB에 접근하는것을 Redis를 통해 성능을 개선해보기로 함
### 결과
**캐싱 처리 전**
![image](https://user-images.githubusercontent.com/97796338/207011178-551d4885-7b23-4103-95b7-7da8edb6df2d.png)
**캐싱 처리 후**
![image](https://user-images.githubusercontent.com/97796338/207011365-06735785-6791-4872-a861-1c4c538f7e21.png)
CI/CD 설정 오류 해결
### 문제상황
1. EC2(Ubuntu)에서 default 메모리 설정으로 무중단 배포를 적용하니 신버전 배포 시 서버가 다운
2. EC2(Ubuntu)에 Nginx 설치에 필요한 Ruby 2.5.1 버전이 다운로드 되지 않음
3. 신버전을 배포할 때 codedepoly에서 실패가 뜨고 신버전이 배포가 되지 않음
### 의견조율
1. **메모리를 늘리는 방법을 찾아보자고 함**
- default 메모리가 1GB만 설정되어 있고 swap 설정이 안되어 있었고
1GB가 넘는 boot 파일 두개를 배포하려고 하니 default 메모리 설정이 감당을 못하고
서버가 다운되는 것같아 swap 메모리 설정을 하기로 함
2. **버전 문제인것 같다고 판단해서 버전을 바꿔보자고 함**
- Ubuntu 22.04는 OpenSSL 3.0과 함께 제공되기 때문에 Ruby 3.0 이하에서는
이를 지원하지 않는걸 확인하고 바꾸기로 함
3. **aws codedepoly error log와 EC2(Ubuntu) deploy error log를 확인해보기로 함**
- 신버전 depoly 시에 EC2(Ubuntu)에서 신버전 boot 파일을 열지 못하는 것을 확인했다
- shell script를 bash용으로 작성했는데 Ubuntu의 기본 쉘은 dash여서 호환성 문제로 script를 읽지 못함
### 결과
1. EC2(Ubuntu) default 메모리가 용량 초과 시 swap 메모리로 넘어갈 수 있게 충분한 용량을 주어 설정해줌
2. Ruby 2.5.1을 2.7로 변경하니 정상 작동
3. Ubuntu의 기본 쉘을 dash에서 bash로 변경해주고 switch 스크립트를 실행시킴
🏅MTZ 대장님들
|
조평연 |
이동재 |
오경민 |
김민석 |
이현진 |
역할 |
BE (리더) |
BE |
FE (부리더) |
FE |
FE |
🙋🏻♂️🙋🏻♀️ |
|
|
|
|
|
GITHUB |
🔗 |
🔗 |
🔗 |
🔗 |
🔗 |