다양한 뉴스레터들을 파악하는 것은 힘든일입니다.
구독하고 있는 뉴스레터를 정리해주고 비슷한 주제와 접해보지 못한 관심사를 다룰 수 있도록 제작했습니다.
웹 사이트 주소: https://attraction.run/
개발기간 : 2024-04 ~ 진행중
- 메인 페이지
Light mode | Dark mode |
---|---|
- 뉴스레터 보관함
전체 화면 | 필터 | 읽은 아티클 숨김 |
---|---|---|
- 아티클 상세보기
상세보기 | 북마크 추가하기 |
---|---|
- 나머지 페이지
마이페이지 | 북마크한 아티클 | 랭킹 |
---|---|---|
- 기능
- 사용자 메일함 관리 (뉴스레터 구독시)
- 아티클/썸네일 이미지 저장 (batch)
- 뉴스레터 저장
- API-Server 모니터링 구축(Prometheus + Grafana)
- 기능
- 작성해주세요
- 기능
- 작성해주세요
- Back-end : Java, Kotlin, Spring Boot, Kafka, MariaDB
- 버전 및 이슈관리 : Github, Jira
- 협업 툴 : Discord, Notion, Jira, Swagger
- 모니터링 : Prometheus + Grafana
- CI/CD : Github Actions
- 서비스 배포 환경 : AWS
- 기획 : Figma
- Git 전략
- 코드 컨벤션
테스트 커버리지: 27%
├── java
│ └── run
│ └── attraction
│ ├── AttractionApplication.java
│ └── api
│ ├── swagger
│ │ └── SwaggerConfig.java
│ └── v1
│ ├── archive
│ │ ├── Article.java
│ │ ├── AuditableEntity.java
│ │ ├── ReadBox.java
│ │ ├── controller
│ │ │ └── ArchiveController.java
│ │ ├── dto
│ │ │ ├── ArticleDTO.java
│ │ │ ├── NewsletterDTO.java
│ │ │ ├── NewsletterEmail.java
│ │ │ ├── request
│ │ │ │ └── UserArticlesRequest.java
│ │ │ └── response
│ │ │ └── ApiResponse.java
│ │ ├── repository
│ │ │ ├── ArticleRepository.java
│ │ │ ├── ArticleRepositoryCustom.java
│ │ │ ├── ArticleRepositoryImpl.java
│ │ │ └── ReadBoxRepository.java
│ │ └── service
│ │ └── ArchiveService.java
│ ├── auth
│ │ ├── config
│ │ │ ├── ApplicationConfig.java
│ │ │ ├── AuthProviderConfig.java
│ │ │ ├── GoogleLoginConfig.java
│ │ │ ├── RedisConfig.java
│ │ │ ├── SecurityConfig.java
│ │ │ └── properties
│ │ │ └── GoogleLoginProperties.java
│ │ ├── controller
│ │ │ ├── AuthController.java
│ │ │ ├── AuthTestController.java
│ │ │ ├── FaviconController.java
│ │ │ └── advice
│ │ │ └── AuthenticationExceptionHandler.java
│ │ ├── filter
│ │ │ ├── ErrorType.java
│ │ │ ├── FilterExceptionHandler.java
│ │ │ ├── FilterMessageResponseDto.java
│ │ │ ├── HttpLogMessage.java
│ │ │ ├── RequestLogFilter.java
│ │ │ └── SessionFilter.java
│ │ ├── provider
│ │ │ ├── AuthProvider.java
│ │ │ ├── exception
│ │ │ │ ├── GoogleApiAccessTokenException.java
│ │ │ │ └── GoogleApiCodeException.java
│ │ │ ├── google
│ │ │ │ ├── GoogleOAuth.java
│ │ │ │ └── GoogleOAuthService.java
│ │ │ └── oauth
│ │ │ ├── OAuthService.java
│ │ │ └── OAuthToken.java
│ │ ├── service
│ │ │ ├── AuthService.java
│ │ │ ├── dto
│ │ │ │ ├── ReissueTokenResponseDto.java
│ │ │ │ ├── UserStateDto.java
│ │ │ │ ├── join
│ │ │ │ │ ├── CheckDuplicationRequsetDto.java
│ │ │ │ │ ├── CheckDuplicationResponseDto.java
│ │ │ │ │ └── JoinRequestDto.java
│ │ │ │ └── login
│ │ │ │ ├── FirstLoginResponseDto.java
│ │ │ │ ├── LoginRequestDto.java
│ │ │ │ └── LoginResponseDto.java
│ │ │ └── helper
│ │ │ ├── JoinHelper.java
│ │ │ └── LoginHelper.java
│ │ └── session
│ │ ├── SessionService.java
│ │ ├── dto
│ │ │ └── UserDetailBySession.java
│ │ └── exception
│ │ ├── InValidUserException.java
│ │ ├── ResignedUserException.java
│ │ ├── SessionExceptionHandler.java
│ │ └── SessionNotFoundException.java
│ ├── bookmark
│ │ ├── Bookmark.java
│ │ ├── controller
│ │ │ └── BookmarkController.java
│ │ ├── dto
│ │ │ └── BookmarkArticleRequest.java
│ │ ├── exception
│ │ │ └── BookmarkExceptionHandler.java
│ │ ├── repository
│ │ │ └── BookmarkRepository.java
│ │ └── service
│ │ └── BookmarkService.java
│ ├── exception
│ │ ├── ErrorCode.java
│ │ ├── ErrorResponse.java
│ │ └── GlobalExceptionHandler.java
│ ├── gmail
│ │ ├── config
│ │ │ ├── AsyncConfig.java
│ │ │ ├── KafkaProducerConfig.java
│ │ │ ├── ProducerProperties.java
│ │ │ └── SubscribeProducerListener.java
│ │ ├── dto
│ │ │ └── UserGmailDto.java
│ │ ├── entity
│ │ │ └── GoogleRefreshToken.java
│ │ ├── event
│ │ │ ├── SubscribeVo.java
│ │ │ ├── UserMailEventHandler.java
│ │ │ └── UserSubscribedEvent.java
│ │ ├── repository
│ │ │ └── GoogleRefreshTokenRepository.java
│ │ └── service
│ │ └── GmailService.java
│ ├── home
│ │ ├── controller
│ │ │ └── HomeController.java
│ │ └── service
│ │ ├── HomeService.java
│ │ ├── article
│ │ │ ├── HomeArticleService.java
│ │ │ └── HomeArticleServiceImpl.java
│ │ ├── dto
│ │ │ ├── article
│ │ │ │ ├── ReceivedArticleNewsletterDto.java
│ │ │ │ ├── ReceivedArticlesDto.java
│ │ │ │ └── ReceivedArticlesResponseDto.java
│ │ │ ├── categories
│ │ │ │ └── CategoriesResponseDto.java
│ │ │ ├── newsletter
│ │ │ │ ├── NewsletterDetailDto.java
│ │ │ │ └── NewslettersResponseDto.java
│ │ │ └── search
│ │ │ └── ArticleSearchDto.java
│ │ └── newsletter
│ │ ├── HomeNewsletterService.java
│ │ └── HomeNewsletterServiceImpl.java
│ ├── introduction
│ │ ├── Category.java
│ │ ├── Newsletter.java
│ │ ├── Subscription.java
│ │ ├── UserSubscribedNewsletterCategory.java
│ │ ├── config
│ │ │ ├── AutoSubscribeProducerListener.java
│ │ │ └── KafkaProducerConfig.java
│ │ ├── controller
│ │ │ ├── IntroductionController.java
│ │ │ └── SubscriptionController.java
│ │ ├── dto
│ │ │ └── response
│ │ │ ├── ApiResponse.java
│ │ │ ├── NewsletterResponse.java
│ │ │ ├── NewslettersByCategoryResponse.java
│ │ │ └── PreviousArticleResponse.java
│ │ ├── event
│ │ │ └── AutoSubscribeVo.java
│ │ ├── exception
│ │ │ ├── ErrorMessages.java
│ │ │ ├── IntroductionExceptionHandler.java
│ │ │ └── ResourceNotFoundException.java
│ │ ├── repository
│ │ │ ├── NewsletterRepository.java
│ │ │ ├── SubscriptionRepository.java
│ │ │ └── UserSubscribedNewsletterCategoryRepository.java
│ │ ├── service
│ │ │ ├── IntroductionService.java
│ │ │ ├── KafkaProducerService.java
│ │ │ └── SubscriptionService.java
│ │ └── utils
│ │ └── SubscriptionUtil.java
│ ├── monitoring
│ │ └── MicrometerConfig.java
│ ├── mypage
│ │ ├── controller
│ │ │ └── MypageController.java
│ │ └── service
│ │ ├── MypageService.java
│ │ ├── archive
│ │ │ ├── article
│ │ │ │ ├── MypageArticleService.java
│ │ │ │ └── MypageArticleServiceImpl.java
│ │ │ └── newsletter
│ │ │ ├── MypageNewsletterService.java
│ │ │ └── MypageNewsletterServiceImpl.java
│ │ ├── calendar
│ │ │ ├── MypageCalendarService.java
│ │ │ └── MypageCalendarServiceImpl.java
│ │ ├── dto
│ │ │ ├── MessageResponse.java
│ │ │ ├── archive
│ │ │ │ ├── article
│ │ │ │ │ ├── MypageArticle.java
│ │ │ │ │ ├── RecentArticleNewsletterDto.java
│ │ │ │ │ ├── RecentArticlesDto.java
│ │ │ │ │ ├── RecentArticlesResponseDto.java
│ │ │ │ │ ├── UserArticleDetail.java
│ │ │ │ │ ├── UserArticleImg.java
│ │ │ │ │ └── UserReadBoxDetail.java
│ │ │ │ └── newsletter
│ │ │ │ ├── MypageNewsletterDetail.java
│ │ │ │ └── SubscribeResponseDto.java
│ │ │ ├── calendar
│ │ │ │ ├── CalendarDay.java
│ │ │ │ └── CalendarResponseDto.java
│ │ │ └── userDetail
│ │ │ ├── UpdateImgRequestDto.java
│ │ │ ├── UpdateInterestRequestDto.java
│ │ │ ├── UpdateNicknameRequestDto.java
│ │ │ ├── UpdateOccupationRequestDto.java
│ │ │ ├── UpdateUserExpirationRequestDto.java
│ │ │ ├── UserDetailDto.java
│ │ │ └── UserDetailsResponseDto.java
│ │ └── user
│ │ ├── MypageUserService.java
│ │ └── MypageUserServiceImpl.java
│ ├── rank
│ │ ├── ConsistencyRank.java
│ │ ├── ExtensiveRank.java
│ │ ├── Rank.java
│ │ ├── ReadBoxEvent.java
│ │ ├── controller
│ │ │ └── RankController.java
│ │ ├── repository
│ │ │ ├── ConsistencyRankRepository.java
│ │ │ ├── ExtensiveRankRepository.java
│ │ │ └── ReadBoxEventRepository.java
│ │ └── service
│ │ ├── RankService.java
│ │ ├── calculator
│ │ │ ├── ConsistencyRankCalculator.java
│ │ │ └── ExtensiveRankCalculator.java
│ │ └── dto
│ │ ├── ConsistencyRankResponseDto.java
│ │ ├── ExtensiveRankResponseDto.java
│ │ └── RankDetailDto.java
│ ├── statistics
│ │ ├── AgeGroup.java
│ │ ├── AgeGroupStatistics.java
│ │ ├── NewsletterEvent.java
│ │ ├── OccupationStatistics.java
│ │ ├── controller
│ │ │ └── StatisticsController.java
│ │ ├── repository
│ │ │ ├── AgeGroupStatisticsRepository.java
│ │ │ ├── NewsletterEventRepository.java
│ │ │ └── OccupationStatisticsRepository.java
│ │ └── service
│ │ ├── StatisticsService.java
│ │ ├── ageGroup
│ │ │ └── AgeGroupStatisticsCalculator.java
│ │ └── occupation
│ │ └── OccupationStatisticsCalculator.java
│ └── user
│ ├── Interest.java
│ ├── Occupation.java
│ ├── Role.java
│ ├── User.java
│ ├── UserDetail.java
│ ├── UserValidator.java
│ ├── repository
│ │ ├── UserDetailRepository.java
│ │ └── UserRepository.java
│ ├── service
│ │ ├── UserDetailsServiceForSecurity.java
│ │ ├── UserService.java
│ │ └── UserServiceImpl.java
│ └── validator
│ ├── exception
│ │ ├── InvalidNicknameException.java
│ │ └── InvalidNicknameExceptionHandler.java
│ └── nickname
│ ├── EnglishValidator.java
│ ├── KoreanValidator.java
│ ├── NicknameValidator.java
│ ├── NumberValidator.java
│ └── SpecialValidator.java
└── resources
├── application.yml
├── credentials.json
└── data.sql