diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml new file mode 100644 index 00000000..9d30e02c --- /dev/null +++ b/.github/workflows/CI.yml @@ -0,0 +1,68 @@ +name: CI + +on: + pull_request: + branches: ['main'] + push: + branches: [ "main" ] + +jobs: + build: + runs-on: ubuntu-latest + + steps: + - name: Checkout code + uses: actions/checkout@v3 + + - name: Install dependencies + run: yarn install + + - name: Build # 빌드 + run: yarn build + + - name: Close PR, if build fails + if: ${{ failure() }} + uses: actions/github-script@v6 + with: + github-token: ${{ github.TOKEN }} + script: | + const pull_number = ${{ github.event.pull_request.number }} + const updated_title = `[BUILD FAIL] ${{ github.event.pull_request.title }}` + await github.rest.pulls.createReview({ + owner: context.repo.owner, + repo: context.repo.repo, + pull_number: pull_number, + body: '빌드에 실패했습니다.', + event: 'REQUEST_CHANGES' + }) + await github.rest.pulls.update({ + owner: context.repo.owner, + repo: context.repo.repo, + pull_number: pull_number, + title: updated_title, + state: 'closed' + }) + + push_main: + runs-on: ubuntu-latest + container: pandoc/latex + steps: + - uses: actions/checkout@v2 + - name: Install mustache (to update the date) + run: apk add ruby && gem install mustache + - name: creates output + run: sh ./build.sh + - name: Pushes to another repository + id: push_directory + uses: cpina/github-action-push-to-another-repository@main + env: + API_TOKEN_GITHUB: ${{ secrets.AUTO_ACTIONS }} + with: + source-directory: 'output' + destination-github-username: ljh0608 + destination-repository-name: ASAP_Client + user-email: ${{ secrets.LEAD_EMAIL }} + commit-message: ${{ github.event.commits[0].message }} + target-branch: main + - name: Test get variable exported by push-to-another-repository + run: echo $DESTINATION_CLONED_DIRECTORY diff --git a/src/components/common/moleculesComponents/Header.tsx b/src/components/common/moleculesComponents/Header.tsx index 8d974c4a..cbfe94db 100644 --- a/src/components/common/moleculesComponents/Header.tsx +++ b/src/components/common/moleculesComponents/Header.tsx @@ -113,10 +113,10 @@ function Header({ position, setFunnelStep }: HeaderProps) { {isNaviOpen ? ( + setIsNaviOpen((prev) => !prev)}> - @@ -160,7 +160,7 @@ const NavigationSection = styled.section` position: absolute; top: 0; right: 0; - z-index: 1; + z-index: 2; background-color: rgba(0, 0, 0, 0.7); width: 100%; height: 100vh; diff --git a/src/pages/selectSchedule/components/selectPriority/PriorityCta.tsx b/src/pages/selectSchedule/components/selectPriority/PriorityCta.tsx index f01af633..67ba3897 100644 --- a/src/pages/selectSchedule/components/selectPriority/PriorityCta.tsx +++ b/src/pages/selectSchedule/components/selectPriority/PriorityCta.tsx @@ -7,6 +7,7 @@ import styled from 'styled-components'; function PriorityCta() { const [isModalOpen, setIsModalOpen] = useState(false); + return ( <> diff --git a/src/pages/selectSchedule/components/selectPriority/PriorityDropdown.tsx b/src/pages/selectSchedule/components/selectPriority/PriorityDropdown.tsx index b4e93585..bf687250 100644 --- a/src/pages/selectSchedule/components/selectPriority/PriorityDropdown.tsx +++ b/src/pages/selectSchedule/components/selectPriority/PriorityDropdown.tsx @@ -20,27 +20,35 @@ function PriorityDropdown() { const { selectedSlots, setSelectedSlots } = useSelectContext(); const [isOpenDropDown, setIsOpenDropDown] = useState([false, false, false]); + //우선 순위 시간순 정렬을 위한 날짜 시간 파싱함수 + const parseDateTime = (dateStr: string, timeStr: string) => { + const [month, day] = dateStr.split('/'); + const formatDay = day.padStart(2, '0'); + const [hour, minute] = timeStr.split(':'); + return Number(month + formatDay + hour + minute); + }; + + const sortedSlots = Object.entries(selectedSlots) + .slice() + .sort( + (a, b) => parseDateTime(a[1].date, a[1].startSlot) - parseDateTime(b[1].date, b[1].startSlot), + ); + const formatDate = (date: string) => { const [month, day, dayOfWeek] = date.split('/'); return `${month}/${day}(${dayOfWeek})`; }; - let defaultInput1 = ''; - let defaultInput2 = ''; - let defaultInput3 = ''; - for (const key in selectedSlots) { - const item = selectedSlots[key]; + const defaultInputs = Array(3).fill(''); + Object.values(selectedSlots).forEach((item) => { const date = formatDate(item.date); const endSlot = addMinutes(item.endSlot, 30); - if (item.priority === 3) { - defaultInput1 = `${date} ${item.startSlot}~${endSlot}`; - } else if (item.priority === 2) { - defaultInput2 = `${date} ${item.startSlot}~${endSlot}`; - } else if (item.priority === 1) { - defaultInput3 = `${date} ${item.startSlot}~${endSlot}`; + if (item.priority > 0) { + defaultInputs[3 - item.priority] = `${date} ${item.startSlot}~${endSlot}`; } - } - const [input_, setInput] = useState([defaultInput1, defaultInput2, defaultInput3]); + }); + + const [input_, setInput] = useState(defaultInputs); const handleDropdown = (idx: number) => { //dropdown이 열려있을 때 @@ -62,28 +70,13 @@ function PriorityDropdown() { const handlePriority = (idx: number, item: SelectSlotType, stringSelectedSlotKey: string) => { const selectedSlotKey = parseInt(stringSelectedSlotKey); - let selectedPriority: 0 | 1 | 2 | 3 = 0; - switch (idx) { - case 0: - selectedPriority = 3; - break; - case 1: - selectedPriority = 2; - break; - case 2: - selectedPriority = 1; - break; - default: - selectedPriority = 0; - break; - } - + const selectedPriority = 3 - idx; //이전 상태를 순회하면서 선택된 우선순위를 가지고 있는 데이터를 우선순위 0으로 초기화 setSelectedSlots((prev: SelectedSlotType) => { const updatedSelectedSlots = Object.entries(prev).reduce( (acc, [key, value]) => { const prevSelectedSlotKey = parseInt(key); - //선택된 우선순위가 기존에 존재할 경우 0으로 초기화 + //우선순위를 선택한 후 다시 설정할 경우 기존 priority 0으로 초기화 if (value.priority === selectedPriority) { acc[prevSelectedSlotKey] = { ...value, priority: 0 }; } else { @@ -109,15 +102,8 @@ function PriorityDropdown() { const updatedInput = [...prev]; const endSlot = addMinutes(item.endSlot, 30); const date = formatDate(item.date); - if (idx === 0) { - updatedInput[idx] = `${date} ${item.startSlot}~${endSlot}`; - } else if (idx === 1) { - updatedInput[idx] = `${date} ${item.startSlot}~${endSlot}`; - } else if (idx === 2) { - updatedInput[idx] = `${date} ${item.startSlot}~${endSlot}`; - } else { - updatedInput[idx] = 'error'; - } + + updatedInput[idx] = `${date} ${item.startSlot}~${endSlot}`; return updatedInput; }); handleDropdown(idx); @@ -134,15 +120,7 @@ function PriorityDropdown() { {`${idx + 1}`}순위 - {idx === 0 ? ( - - ) : idx === 1 ? ( - - ) : idx === 2 ? ( - - ) : ( -
- )} + {idx === 0 ? : idx === 1 ? : } handleDropdown(idx)} value={input_[idx]} /> - - {isOpenDropDown[idx] ? ( - - {' '} - - ) : ( - - - - )} - + + {isOpenDropDown[idx] ? : } + {isOpenDropDown[idx] && ( - {Object.entries(selectedSlots).map( + {sortedSlots.map( ([key, value]) => !value.priority && ( handlePriority(idx, value, key)}> @@ -222,9 +192,6 @@ const TextWrapper = styled.div` left: 50%; transform: translate(-50%, -50%); `; -const Circle1Icon = styled(Circle1Ic)``; -const Circle2Icon = styled(Circle2Ic)``; -const Circle3Icon = styled(Circle3Ic)``; const InputWrapper = styled.div` position: relative; diff --git a/src/pages/selectSchedule/components/selectTimeSlot/SelectionColumn.tsx b/src/pages/selectSchedule/components/selectTimeSlot/SelectionColumn.tsx index 76b55ac8..7d63b3da 100644 --- a/src/pages/selectSchedule/components/selectTimeSlot/SelectionColumn.tsx +++ b/src/pages/selectSchedule/components/selectTimeSlot/SelectionColumn.tsx @@ -3,14 +3,16 @@ import { useSelectContext } from 'pages/selectSchedule/contexts/useSelectContext import { theme } from 'styles/theme'; import useSlotSeletion from './hooks/useSlotSelection'; + import Slot from '../../../../components/common/timetableComponents/parts/Slot'; function SelectionColumn({ date, timeSlots }: ColumnStructure) { const { selectedSlots } = useSelectContext(); + const selectedSlotsPerDate = Object.entries(selectedSlots).filter( ([, slot]) => slot.date === date, ); - + //test const { startSlot, onClickSlot } = useSlotSeletion(); const getTimeSlotStyle = (slotId: string, selectedEntryId?: number) => { diff --git a/src/pages/selectSchedule/components/selectTimeSlot/TimeSlotCta.tsx b/src/pages/selectSchedule/components/selectTimeSlot/TimeSlotCta.tsx index f10b78e0..5198f868 100644 --- a/src/pages/selectSchedule/components/selectTimeSlot/TimeSlotCta.tsx +++ b/src/pages/selectSchedule/components/selectTimeSlot/TimeSlotCta.tsx @@ -1,19 +1,31 @@ import Button from 'components/common/atomComponents/Button'; import Text from 'components/common/atomComponents/Text'; import { useScheduleStepContext } from 'pages/selectSchedule/contexts/useScheduleStepContext'; -import { useSelectContext } from 'pages/selectSchedule/contexts/useSelectContext'; +import { SelectedSlotType, useSelectContext } from 'pages/selectSchedule/contexts/useSelectContext'; import styled from 'styled-components'; function TimeSlotCta() { + const { selectedSlots, setSelectedSlots } = useSelectContext(); const { setScheduleStep } = useScheduleStepContext(); - const { selectedSlots } = useSelectContext(); const isValidSelection = Object.keys(selectedSlots).length !== 0; + + const resetPriorities = (selectedSlots: SelectedSlotType) => { + const updatedSelectedSlots: SelectedSlotType = {}; + for (const key in selectedSlots) { + updatedSelectedSlots[key] = { + ...selectedSlots[key], + priority: 0, + }; + } + setSelectedSlots(updatedSelectedSlots); + }; return (