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

TripPage, TripEditPage 리팩토링 #537

Merged
merged 15 commits into from
Sep 4, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
15 commits
Select commit Hold shift + click to select a range
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
13 changes: 10 additions & 3 deletions frontend/.storybook/preview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,7 @@ import { initialize, mswDecorator } from 'msw-storybook-addon';

import { HangLogProvider, Spinner } from 'hang-log-design-system';

import { axiosInstance } from '../src/api/axiosInstance';
import { ACCESS_TOKEN_KEY } from '../src/constants/api';
import { ACCESS_TOKEN_KEY, NETWORK } from '../src/constants/api';
import { handlers } from '../src/mocks/handlers';

initialize();
Expand Down Expand Up @@ -48,7 +47,15 @@ const preview: Preview = {

export default preview;

const queryClient = new QueryClient();
const queryClient = new QueryClient({
defaultOptions: {
queries: {
retry: NETWORK.RETRY_COUNT,
suspense: true,
useErrorBoundary: true,
},
},
});

const localStorageResetDecorator = (Story) => {
window.localStorage.clear();
Expand Down
6 changes: 0 additions & 6 deletions frontend/cypress/e2e/login.cy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ describe('로그인', () => {

it('웹 사이트 처음 방문 시 서비스 소개 페이지를 볼 수 있다.', () => {
cy.findByText('로그인');
cy.findByText('회원가입');
cy.findByText('시작하기');
});

Expand All @@ -25,11 +24,6 @@ describe('로그인', () => {
cy.location('pathname').should('eq', PATH.LOGIN);
});

it('회원가입 버튼을 클릭하면 회원가입 페이지로 이동한다.', () => {
cy.findByText('회원가입').click();
cy.location('pathname').should('eq', PATH.SIGN_UP);
});

it('로그인하면 메인 페이지 화면이 여행 목록 페이지로 변경된다.', () => {
cy.findByText('로그인').click();

Expand Down
25 changes: 11 additions & 14 deletions frontend/cypress/e2e/trip.cy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,10 @@ describe('여행 수정 페이지', () => {
});
});

it('여행 수정 페이지에서 "여행 정보 수정" 버튼과 "저장" 버튼을 볼 수 있다.', () => {
it('여행 수정 페이지에서 "여행 정보 수정" 버튼과 "완료" 버튼을 볼 수 있다.', () => {
cy.findByText('여행 정보 수정');

cy.findByText('저장');
cy.findByText('완료');
});

it('여행 수정 페이지에서 선택 된 날짜 길이 만큼 데이로그 탭이 만들어져 있다.', () => {
Expand All @@ -62,7 +62,7 @@ describe('여행 수정 페이지', () => {
cy.findByPlaceholderText('소제목').should('have.value', title);

items.forEach((item: TripItemData) => {
cy.get('h6').contains(item.title);
cy.get('p').contains(item.title);
});
});
});
Expand All @@ -74,7 +74,7 @@ describe('여행 수정 페이지', () => {
const { items } = expectedData.dayLogs[1];

items.forEach((item: TripItemData) => {
cy.get('h6').contains(item.title);
cy.get('p').contains(item.title);
});
});
});
Expand Down Expand Up @@ -289,7 +289,7 @@ describe('여행 아이템 추가', () => {

cy.findByRole('dialog').should('not.exist');

cy.get('h6').contains('샹젤리제 거리 -> 에펠탑 지하철').should('exist');
cy.get('p').contains('샹젤리제 거리 -> 에펠탑 지하철').should('exist');
});

it('여행 아이템 추가 모달에서 필수 정보 외에도 입력하고 아이템을 추가한 후에 여행 아이템 목록에서 볼 수 있다.', () => {
Expand All @@ -310,7 +310,7 @@ describe('여행 아이템 추가', () => {

cy.findByRole('dialog').should('not.exist');

cy.get('h6').contains('샹젤리제 거리 -> 에펠탑 지하철').should('exist');
cy.get('p').contains('샹젤리제 거리 -> 에펠탑 지하철').should('exist');

cy.findByText('샹젤리제 거리 -> 에펠탑 지하철').parent().find('svg').should('have.length', 6);
cy.findByText('샹젤리제 거리 -> 에펠탑 지하철')
Expand Down Expand Up @@ -339,16 +339,14 @@ describe('여행 아이템 수정', () => {
cy.wait(4000);
});

it('여행 아이템의 더 보기 버튼을 클릭해서 여행 아이템을 수정할 수 있다.', () => {
cy.get('button[aria-label="더 보기 메뉴"]').first().click({ force: true });
cy.findByText('수정').click();
it('여행 아이템의 수정 버튼을 클릭해서 여행 아이템을 수정할 수 있다.', () => {
cy.get('svg[aria-label="수정"]').first().click({ force: true });

cy.findByRole('dialog').should('be.visible');
});

it.skip('여행 아이템 수정 모달을 열면 여행 아이템 정보가 입력되어 있다.', () => {
cy.get('button[aria-label="더 보기 메뉴"]').first().click({ force: true });
cy.findByText('수정').click();
cy.get('svg[aria-label="수정"]').first().click({ force: true });

cy.fixture('trip.json').then((expectedData) => {
const { items } = expectedData.dayLogs[0];
Expand All @@ -365,8 +363,7 @@ describe('여행 아이템 수정', () => {
});

it.skip('여행 아이템 수정 모달에서 여행 아이템 정보를 수정하면 여행 아이템 목록에서 변경된 정보를 볼 수 있다.', () => {
cy.get('button[aria-label="더 보기 메뉴"]').first().click({ force: true });
cy.findByText('수정').click();
cy.get('svg[aria-label="수정"]').first().click({ force: true });

cy.findByRole('radio', { name: /기타/ }).click();
cy.get('#title').type(' 택시');
Expand All @@ -383,7 +380,7 @@ describe('여행 아이템 수정', () => {
const { items } = expectedData.dayLogs[0];
const firstItem: TripItemData = items[0];

cy.get('h6').contains(`${firstItem.title} 택시`).should('exist');
cy.get('p').contains(`${firstItem.title} 택시`).should('exist');

cy.findByText(`${firstItem.title} 택시`)
.parent()
Expand Down
3 changes: 3 additions & 0 deletions frontend/src/assets/svg/bin-icon.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/svg/edit-icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions frontend/src/components/common/DayLogList/DayLogList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { Tab, Tabs } from 'hang-log-design-system';
import DayLogItem from '@components/common/DayLogItem/DayLogItem';
import { containerStyling } from '@components/common/DayLogList/DayLogList.style';

import { useTripDates } from '@hooks/trip/useTripDates';
import { useTrip } from '@hooks/trip/useTrip';

import { formatMonthDate } from '@utils/formatter';

Expand All @@ -26,7 +26,7 @@ const DayLogList = ({
onTabChange,
openAddModal,
}: DayLogListProps) => {
const { dates } = useTripDates(tripId);
const { dates } = useTrip(tripId);

return (
<section css={containerStyling}>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,6 @@ export const moreButtonStyling = css({
'& svg': {
width: '20px',
height: '20px',

'& path': {
stroke: Theme.color.white,
strokeWidth: 1.5,
},
},
});

Expand All @@ -38,3 +33,23 @@ export const moreMenuListStyling = css({
color: Theme.color.gray800,
},
});

export const svgButtonStyling = css({
width: '20px',
height: '20px',
marginLeft: '12px',

cursor: 'pointer',
});

export const binIconStyling = css({
'& path': {
stroke: Theme.color.white,
},
});

export const editIconStyling = css({
'& path': {
fill: Theme.color.white,
},
});
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import { useNavigate } from 'react-router-dom';

import { Button, Menu, MenuItem, MenuList, useOverlay } from 'hang-log-design-system';
import { Button } from 'hang-log-design-system';

import {
moreButtonStyling,
moreMenuListStyling,
moreMenuStyling,
binIconStyling,
editIconStyling,
svgButtonStyling,
} from '@components/common/TripInformation/TripButtons/TripButtons.style';
import TripShareButton from '@components/common/TripInformation/TripShareButton/TripShareButton';

Expand All @@ -15,7 +15,8 @@ import type { TripData } from '@type/trip';

import { PATH } from '@constants/path';

import MoreIcon from '@assets/svg/more-icon.svg';
import BinIcon from '@assets/svg/bin-icon.svg';
import EditIcon from '@assets/svg/edit-icon.svg';

interface TripButtonsProps {
tripId: number;
Expand All @@ -25,7 +26,6 @@ interface TripButtonsProps {
export const TripButtons = ({ tripId, sharedCode }: TripButtonsProps) => {
const navigate = useNavigate();
const deleteTripMutation = useDeleteTripMutation();
const { isOpen: isMenuOpen, open: openMenu, close: closeMenu } = useOverlay();

const goToEditPage = () => {
navigate(PATH.EDIT_TRIP(tripId));
Expand All @@ -50,17 +50,8 @@ export const TripButtons = ({ tripId, sharedCode }: TripButtonsProps) => {
가계부
</Button>
<TripShareButton tripId={tripId} sharedCode={sharedCode} />
<Menu css={moreMenuStyling} closeMenu={closeMenu}>
<button css={moreButtonStyling} type="button" aria-label="더 보기 메뉴" onClick={openMenu}>
<MoreIcon />
</button>
{isMenuOpen && (
<MenuList css={moreMenuListStyling}>
<MenuItem onClick={goToEditPage}>수정</MenuItem>
<MenuItem onClick={handleDeleteButtonClick}>삭제</MenuItem>
</MenuList>
)}
</Menu>
<EditIcon css={[svgButtonStyling, editIconStyling]} onClick={goToEditPage} />
<BinIcon css={[svgButtonStyling, binIconStyling]} onClick={handleDeleteButtonClick} />
</>
);
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ const TripEditButtons = ({ tripId, openEditModal }: TripEditButtonsProps) => {
여행 정보 수정
</Button>
<Button variant="primary" size="small" onClick={() => navigate(`/trip/${tripId}`)}>
저장
완료
</Button>
</>
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -56,10 +56,14 @@ export const descriptionStyling = css({
export const buttonContainerStyling = css({
position: 'absolute',
top: Theme.spacer.spacing4,
right: Theme.spacer.spacing4,
right: '50px',
display: 'flex',
alignItems: 'center',
gap: Theme.spacer.spacing1,

'@media screen and (max-width: 600px)': {
right: Theme.spacer.spacing4,
},
});

export const badgeStyling = css({
Expand All @@ -85,6 +89,6 @@ export const badgeWrapperStyling = css({
},

'@media screen and (max-width: 600px)': {
width: 'calc(100vw - 220px)',
width: 'calc(100vw - 232px)',
},
});
31 changes: 15 additions & 16 deletions frontend/src/components/common/TripInformation/TripInformation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,63 +17,62 @@ import {
} from '@components/common/TripInformation/TripInformation.style';
import TripInfoEditModal from '@components/trip/TripInfoEditModal/TripInfoEditModal';

import { useTrip } from '@hooks/trip/useTrip';

import { mediaQueryMobileState } from '@store/mediaQuery';

import { formatDate } from '@utils/formatter';

import type { TripData } from '@type/trip';

import DefaultThumbnail from '@assets/png/trip-information_default-thumbnail.png';

interface TripInformationProps extends Omit<TripData, 'dayLogs'> {
interface TripInformationProps {
tripId: number;
isEditable?: boolean;
isShared?: boolean;
}

const TripInformation = ({
isEditable = true,
isShared = false,
...information
}: TripInformationProps) => {
const TripInformation = ({ isEditable = true, isShared = false, tripId }: TripInformationProps) => {
const isMobile = useRecoilValue(mediaQueryMobileState);

const { isOpen: isEditModalOpen, close: closeEditModal, open: openEditModal } = useOverlay();

const { tripData } = useTrip(tripId);

return (
<>
<header css={sectionStyling}>
<Box css={imageWrapperStyling}>
<div />
<img src={information.imageUrl ?? DefaultThumbnail} alt="여행 대표 이미지" />
<img src={tripData.imageUrl ?? DefaultThumbnail} alt="여행 대표 이미지" />
</Box>
<Box tag="section">
<Box css={badgeWrapperStyling}>
{information.cities.map(({ id, name }) => (
{tripData.cities.map(({ id, name }) => (
<Badge key={id} css={badgeStyling}>
{name}
</Badge>
))}
</Box>
<Heading css={titleStyling} size={isMobile ? 'medium' : 'large'}>
{information.title}
{tripData.title}
</Heading>
<Text>
{formatDate(information.startDate)} - {formatDate(information.endDate)}
{formatDate(tripData.startDate)} - {formatDate(tripData.endDate)}
</Text>
<Text css={descriptionStyling} size="small">
{information.description}
{tripData.description}
</Text>
</Box>
<Box css={buttonContainerStyling}>
{isEditable ? (
<TripEditButtons tripId={information.id} openEditModal={openEditModal} />
<TripEditButtons tripId={tripData.id} openEditModal={openEditModal} />
) : (
!isShared && <TripButtons tripId={information.id} sharedCode={information.sharedCode} />
!isShared && <TripButtons tripId={tripData.id} sharedCode={tripData.sharedCode} />
)}
</Box>
</header>
{isEditModalOpen && (
<TripInfoEditModal isOpen={isEditModalOpen} onClose={closeEditModal} {...information} />
<TripInfoEditModal isOpen={isEditModalOpen} onClose={closeEditModal} {...tripData} />
)}
</>
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@ import { css } from '@emotion/react';
import { Theme } from 'hang-log-design-system';

export const shareButtonStyling = css({
marginLeft: Theme.spacer.spacing3,
height: '20px',
marginLeft: '12px',
border: 'none',

backgroundColor: 'transparent',
Expand Down
Loading