Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[All] 모모의 세번째 배포를 축하해요 : ) #405

Merged
merged 14 commits into from
Oct 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 7 additions & 17 deletions .github/workflows/backend-dev-cd.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ name: Backend Dev CD
on:
workflow_dispatch:
push:
branches: ['develop']
branches: [ 'develop' ]

jobs:
detect-changes:
Expand Down Expand Up @@ -83,7 +83,7 @@ jobs:

be-depoly:
needs: be-build
runs-on: [self-hosted, linux, ARM64, dev]
runs-on: [ self-hosted, linux, ARM64, dev ]
defaults:
run:
shell: bash
Expand All @@ -103,20 +103,10 @@ jobs:
- name: docker pull
run: docker pull ${{ secrets.DOCKERHUB_USERNAME }}/momo-api-dev

# 2. 기존 컨테이너 중지
- name: docker stop container
run: docker stop $(docker ps -q) 2>/dev/null || true

# 3. 도커 컨테이너 실행
- name: docker run new container
run: >-
docker run --name momo-api-dev
--rm -d -p 8080:8080
--volume=$HOME/security:/momo/security:ro
--volume=$HOME/logs:/momo/logs
--env SPRING_PROFILE=dev
${{ secrets.DOCKERHUB_USERNAME }}/momo-api-dev

# 4. 미사용 이미지를 정리
# 2. 실행 컨테이너 중 app 서비스만 재시작
- name: Restart app service
run: docker compose -f $HOME/security/docker-compose-dev.yml restart app --no-deps

# 3. 미사용 이미지를 정리
- name: delete old docker image
run: docker system prune -f
2 changes: 1 addition & 1 deletion .github/workflows/frontend-ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ name: Frontend CI

on:
pull_request:
branches: ['develop']
branches: ['main', 'develop']

permissions:
checks: write
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ public class RoutingDataSource extends AbstractRoutingDataSource {
protected Object determineCurrentLookupKey() {
boolean currentTransactionReadOnly = TransactionSynchronizationManager.isCurrentTransactionReadOnly();
String key = currentTransactionReadOnly ? DataSourceConfig.REPLICA_SERVER : DataSourceConfig.SOURCE_SERVER;
log.info("Activated Datasource: {}", key);
log.debug("Activated Datasource: {}", key);
return key;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,12 +50,4 @@ public ResponseEntity<Void> logout(@PathVariable String uuid) {
public MomoApiResponse<List<String>> findAttendeesOfMeeting(@PathVariable String uuid) {
return new MomoApiResponse<>(attendeeService.findAll(uuid));
}

/**
* TEMP: 비밀번호 마이그레이션 이후 삭제될 메서드입니다.
*/
@PostMapping("/api/v1/attendee/update-password")
public MomoApiResponse<Integer> updatePassword() {
return new MomoApiResponse<>(attendeeService.updateAllPassword());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import kr.momo.service.meeting.MeetingConfirmService;
import kr.momo.service.meeting.MeetingService;
import kr.momo.service.meeting.dto.ConfirmedMeetingResponse;
import kr.momo.service.meeting.dto.MeetingHomeResponse;
import kr.momo.service.meeting.dto.MeetingConfirmRequest;
import kr.momo.service.meeting.dto.MeetingConfirmResponse;
import kr.momo.service.meeting.dto.MeetingCreateRequest;
Expand Down Expand Up @@ -73,6 +74,12 @@ public MomoApiResponse<ConfirmedMeetingResponse> findConfirmedMeeting(@PathVaria
return new MomoApiResponse<>(response);
}

@GetMapping("/api/v1/meetings/{uuid}/home")
public MomoApiResponse<MeetingHomeResponse> findMeetingHome(@PathVariable String uuid) {
MeetingHomeResponse response = meetingService.findMeetingHome(uuid);
return new MomoApiResponse<>(response);
}

@PatchMapping("/api/v1/meetings/{uuid}/lock")
public void lock(@PathVariable String uuid, @AuthAttendee long id) {
meetingService.lock(uuid, id);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import kr.momo.service.meeting.dto.MeetingConfirmResponse;
import kr.momo.service.meeting.dto.MeetingCreateRequest;
import kr.momo.service.meeting.dto.MeetingCreateResponse;
import kr.momo.service.meeting.dto.MeetingHomeResponse;
import kr.momo.service.meeting.dto.MeetingResponse;
import kr.momo.service.meeting.dto.MeetingSharingResponse;
import org.springframework.http.ResponseEntity;
Expand Down Expand Up @@ -147,4 +148,11 @@ ResponseEntity<Void> cancelConfirmedMeeting(
@PathVariable @Schema(description = "약속 UUID") String uuid,
@AuthAttendee @Schema(hidden = true) long id
);

@Operation(summary = "약속 입장 정보 조회", description = "약속 입장에 필요한 정보를 조회하는 API 입니다.")
@ApiSuccessResponse.NoContent("약속 입장 정보 조회 성공")
@ApiErrorResponse.BadRequest(ERROR_CODE_TABLE_HEADER + """
| NOT_FOUND_MEETING | 존재하지 않는 약속 정보 입니다. |
""")
MomoApiResponse<MeetingHomeResponse> findMeetingHome(@PathVariable @Schema(description = "약속 UUID") String uuid);
}
Original file line number Diff line number Diff line change
Expand Up @@ -63,24 +63,4 @@ public List<String> findAll(String uuid) {
.map(Attendee::name)
.toList();
}

/**
* TEMP: 비밀번호 마이그레이션 이후 삭제될 메서드입니다.
*/
@Transactional
public Integer updateAllPassword() {
List<Attendee> attendees = attendeeRepository.findAll();
List<Attendee> rawAttendees = attendees.stream()
.filter(attendee -> attendee.getPassword().getPassword().length() < 15)
.toList();
rawAttendees.forEach(
attendee -> {
String rawPassword = attendee.getPassword().getPassword();
String encodedPassword = passwordEncoder.encode(rawPassword);
attendee.updatePassword(encodedPassword);
}
);
attendeeRepository.saveAll(rawAttendees);
return rawAttendees.size();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
import kr.momo.exception.code.AttendeeErrorCode;
import kr.momo.exception.code.MeetingErrorCode;
import kr.momo.service.auth.JwtManager;
import kr.momo.service.meeting.dto.MeetingHomeResponse;
import kr.momo.service.meeting.dto.MeetingCreateRequest;
import kr.momo.service.meeting.dto.MeetingCreateResponse;
import kr.momo.service.meeting.dto.MeetingResponse;
Expand Down Expand Up @@ -110,6 +111,13 @@ public MeetingSharingResponse findMeetingSharing(String uuid) {
return MeetingSharingResponse.from(meeting);
}

@Transactional(readOnly = true)
public MeetingHomeResponse findMeetingHome(String uuid) {
Meeting meeting = meetingRepository.findByUuid(uuid)
.orElseThrow(() -> new MomoException(MeetingErrorCode.NOT_FOUND_MEETING));
return MeetingHomeResponse.from(meeting);
}

@Transactional
public void lock(String uuid, long id) {
Meeting meeting = meetingRepository.findByUuid(uuid)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package kr.momo.service.meeting.dto;

import io.swagger.v3.oas.annotations.media.Schema;
import kr.momo.domain.meeting.Meeting;

@Schema(description = "약속 입장 응답")
public record MeetingHomeResponse(

@Schema(description = "약속 이름")
String meetingName,

@Schema(description = "약속 유형")
String type
) {
public static MeetingHomeResponse from(Meeting meeting) {
return new MeetingHomeResponse(meeting.getName(), meeting.getType().name());
}
}
2 changes: 1 addition & 1 deletion backend/src/main/resources/security
Original file line number Diff line number Diff line change
Expand Up @@ -689,4 +689,18 @@ private MeetingConfirmRequest getValidFindRequest(AvailableDate tomorrow) {
Timeslot.TIME_0600.startTime()
);
}

@DisplayName("약속 입장 정보를 조회하면 200 상태 코드를 응답한다.")
@Test
void findMeetingHome() {
Meeting meeting = MeetingFixture.MOVIE.create();
meeting = meetingRepository.save(meeting);

RestAssured.given().log().all()
.pathParam("uuid", meeting.getUuid())
.contentType(ContentType.JSON)
.when().get("/api/v1/meetings/{uuid}/home")
.then().log().all()
.statusCode(HttpStatus.OK.value());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import java.time.LocalTime;
import java.time.ZoneId;
import java.util.List;
import java.util.UUID;
import kr.momo.domain.attendee.Attendee;
import kr.momo.domain.attendee.AttendeeRepository;
import kr.momo.domain.availabledate.AvailableDate;
Expand All @@ -24,6 +25,7 @@
import kr.momo.exception.code.MeetingErrorCode;
import kr.momo.fixture.AttendeeFixture;
import kr.momo.fixture.MeetingFixture;
import kr.momo.service.meeting.dto.MeetingHomeResponse;
import kr.momo.service.meeting.dto.MeetingCreateRequest;
import kr.momo.service.meeting.dto.MeetingResponse;
import kr.momo.service.meeting.dto.MeetingSharingResponse;
Expand Down Expand Up @@ -258,4 +260,28 @@ void throwsExceptionWhenUnlockAttendeeGuest() {
.isInstanceOf(MomoException.class)
.hasMessage(AttendeeErrorCode.ACCESS_DENIED.message());
}

@DisplayName("UUID로 약속 입장 정보를 조회한다.")
@Test
void findMeetingHome() {
Meeting meeting = meetingRepository.save(MeetingFixture.GAME.create());
String uuid = meeting.getUuid();

MeetingHomeResponse result = meetingService.findMeetingHome(uuid);

assertAll(
() -> assertThat(result.meetingName()).isEqualTo(meeting.getName()),
() -> assertThat(result.type()).isEqualTo(meeting.getType().name())
);
}

@DisplayName("약속 입장 정보를 조회시 UUID가 존재하지 않으면 예외가 발생한다.")
@Test
void throwsExceptionWhenFindHomeNoMeeting() {
String uuid = UUID.randomUUID().toString();

assertThatThrownBy(() -> meetingService.findMeetingHome(uuid))
.isInstanceOf(MomoException.class)
.hasMessage(MeetingErrorCode.NOT_FOUND_MEETING.message());
}
}
5 changes: 5 additions & 0 deletions frontend/jest.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,4 +9,9 @@ module.exports = {
},
setupFiles: ['./jest.polyfills.js'],
reporters: ['default', ['jest-junit', { outputDirectory: 'reports', outputName: 'report.xml' }]],

moduleNameMapper: {
'^@utils/(.*)$': '<rootDir>/src/utils/$1',
'^@constants/(.*)$': '<rootDir>/src/constants/$1',
},
};
6 changes: 4 additions & 2 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@
"scripts": {
"prod": "webpack server --open --config webpack.prod.js",
"dev": "webpack server --open --config webpack.dev.js",
"build:prod": "NODE_ENV=production webpack --config webpack.prod.js && npm run sentry:sourcemaps",
"build:dev": "NODE_ENV=production webpack --config webpack.prod.js",
"build:prod-analyzer": "NODE_ENV=production USE_BUNDLE_ANALYZER=true webpack --config webpack.prod.js && npm run sentry:sourcemaps",
"build:prod": "NODE_ENV=production USE_BUNDLE_ANALYZER=false webpack --config webpack.prod.js && npm run sentry:sourcemaps",
"build:dev-analyzer": "NODE_ENV=production USE_BUNDLE_ANALYZER=true webpack --config webpack.prod.js && npm run sentry:sourcemaps",
"build:dev": "NODE_ENV=production USE_BUNDLE_ANALYZER=false webpack --config webpack.prod.js",
"sentry:sourcemaps": "sentry-cli sourcemaps inject ./dist && sentry-cli sourcemaps upload -o momo2024 -p momo-harry-test /dist",
"lint:css": "stylelint '**/*.styles.ts' --fix",
"test": "jest",
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/assets/images/attendeeCheck.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 1 addition & 1 deletion frontend/src/assets/images/check.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions frontend/src/assets/images/exclamation.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
7 changes: 6 additions & 1 deletion frontend/src/assets/images/logoSunglass.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
1 change: 0 additions & 1 deletion frontend/src/components/Schedules/Schedules.styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ export const s_container = css`
export const s_relativeContainer = css`
position: relative;
flex: 1;
max-height: fit-content;
`;

export const s_selectModeButtonsContainer = css`
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import { css } from '@emotion/react';

export const s_bottomFixedStyles = css`
width: calc(100% + 1.6rem * 2);
max-width: 43rem;

/* 버튼 컴포넌트의 full variants를 사용하려고 했으나 6rem보다 height값이 작아 직접 높이를 정의했어요(@해리)
full 버튼에 이미 의존하고 있는 컴포넌트들이 많아서 높이를 full 스타일을 변경할 수는 없었습니다.
*/
height: 6rem;
box-shadow: 0 -4px 4px rgb(0 0 0 / 25%);
`;

export const s_bottomFixedButtonContainer = (height = 0) => css`
position: fixed;
bottom: 0;
left: 0;
transform: translateY(-${height}px);

display: flex;
align-items: center;
justify-content: center;

width: 100%;
height: 6rem;

background-color: transparent;
`;
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import type { ButtonHTMLAttributes } from 'react';
import React from 'react';

import { Button } from '../Button';
import { s_bottomFixedButtonContainer, s_bottomFixedStyles } from './BottomFixedButton.styles';

interface BottomFixedButtonProps extends ButtonHTMLAttributes<HTMLButtonElement> {
children: React.ReactNode;
height?: number;
isLoading?: boolean;
}

export default function BottomFixedButton({
children,
height = 0,
isLoading = false,
...props
}: BottomFixedButtonProps) {
return (
<div css={s_bottomFixedButtonContainer(height)}>
<Button
variant="primary"
size="full"
isLoading={isLoading}
borderRadius={0}
customCss={s_bottomFixedStyles}
{...props}
>
{children}
</Button>
</div>
);
}
Loading