├── .eslintrc.js ├── .github ├── ISSUE_TEMPLATE.md ├── PULL_REQUEST_TEMPLATE.md └── workflows │ └── chromatic.yml ├── .gitignore ├── .npmrc ├── README.md ├── apps ├── admin │ ├── .babelrc │ ├── .eslintrc.json │ ├── .gitignore │ ├── README.md │ ├── next.config.js │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── next.svg │ │ └── vercel.svg │ ├── sentry.client.config.ts │ ├── sentry.server.config.ts │ ├── src │ │ ├── HOF │ │ │ └── withAuthHOF.ts │ │ ├── assets │ │ │ └── Image │ │ │ │ ├── AuthBackground.svg │ │ │ │ ├── AuthImg.svg │ │ │ │ └── SignupImg.svg │ │ ├── components │ │ │ ├── Absence │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Auth │ │ │ │ ├── Login │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── CMS │ │ │ │ ├── CMSList │ │ │ │ │ └── index.tsx │ │ │ │ ├── constant.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Confirm │ │ │ │ ├── Detail │ │ │ │ │ ├── Question │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── Suggestion │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ ├── QuestionConfirm │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── SuggestionConfirm │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Generate │ │ │ │ ├── LectureGenerate │ │ │ │ │ ├── LectureAcceptableStudent │ │ │ │ │ │ └── index.tsx │ │ │ │ │ ├── LectureNameAndExplanation │ │ │ │ │ │ └── index.tsx │ │ │ │ │ ├── LecturePeriod │ │ │ │ │ │ └── index.tsx │ │ │ │ │ ├── LectureSelect │ │ │ │ │ │ └── index.tsx │ │ │ │ │ ├── LectureSubmitButton │ │ │ │ │ │ └── index.tsx │ │ │ │ │ ├── LectureTime │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── NoticeGenerate │ │ │ │ │ ├── NoticeList │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Home │ │ │ │ ├── Absence │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── Contact │ │ │ │ │ ├── ContactList │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── Notifiction │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── TodayLectures │ │ │ │ │ ├── TodayLectureList │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── SMS │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ └── common │ │ │ │ ├── Layout │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ │ ├── Nav │ │ │ │ ├── NavItem │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── NavUser │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── constant.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ │ └── Provider │ │ │ │ ├── index.tsx │ │ │ │ └── types.ts │ │ ├── config │ │ │ └── index.ts │ │ ├── constant │ │ │ ├── DayOfWeek │ │ │ │ └── constant.ts │ │ │ ├── Signup │ │ │ │ └── Signup.constant.ts │ │ │ └── Token │ │ │ │ └── Token.constant.ts │ │ ├── hooks │ │ │ ├── Attendance │ │ │ │ └── useChangeAttendanceStatus.ts │ │ │ ├── Auth │ │ │ │ ├── useLogin.ts │ │ │ │ └── useLogout.ts │ │ │ ├── Confirm │ │ │ │ └── useConfirm.ts │ │ │ ├── Lecture │ │ │ │ ├── useCreateLecture.ts │ │ │ │ └── useManageLecture.ts │ │ │ ├── Notice │ │ │ │ ├── useDeleteNotice.ts │ │ │ │ ├── usePatchNoticeStatus.ts │ │ │ │ └── useWriteNotice.ts │ │ │ └── util │ │ │ │ └── useSetSelect.ts │ │ ├── libs │ │ │ ├── Auth │ │ │ │ ├── customAxios.ts │ │ │ │ └── requestInterceptor.ts │ │ │ ├── Storage │ │ │ │ ├── Cookie.ts │ │ │ │ └── Storage.ts │ │ │ └── Token │ │ │ │ └── Token.ts │ │ ├── pages │ │ │ ├── 404.tsx │ │ │ ├── _app.tsx │ │ │ ├── _document.tsx │ │ │ ├── _error.tsx │ │ │ ├── absence │ │ │ │ └── list.tsx │ │ │ ├── ask │ │ │ │ └── confirm.tsx │ │ │ ├── cms │ │ │ │ └── [grade].tsx │ │ │ ├── createLecture.tsx │ │ │ ├── index.tsx │ │ │ ├── sign.tsx │ │ │ └── sms.tsx │ │ ├── queries │ │ │ ├── Absence │ │ │ │ └── query.ts │ │ │ ├── Attendance │ │ │ │ └── query.ts │ │ │ ├── Auth │ │ │ │ └── query.ts │ │ │ ├── Lectures │ │ │ │ └── query.ts │ │ │ ├── Member │ │ │ │ └── query.ts │ │ │ ├── Notice │ │ │ │ └── query.ts │ │ │ ├── Question │ │ │ │ └── query.ts │ │ │ └── Suggestion │ │ │ │ └── query.ts │ │ ├── repositories │ │ │ ├── AbsenceRepository │ │ │ │ ├── AbsenceRepository.ts │ │ │ │ └── AbsenceRepositoryImpl.ts │ │ │ ├── AttendanceRepository │ │ │ │ ├── AttendanceRepository.ts │ │ │ │ └── AttendanceRepositoryImpl.ts │ │ │ ├── AuthRepository │ │ │ │ ├── AuthRepository.ts │ │ │ │ └── AuthRepositoryImpl.ts │ │ │ ├── LectureRepository │ │ │ │ ├── LectureRepository.ts │ │ │ │ └── LectureRepositoryImpl.ts │ │ │ ├── MemberRepository │ │ │ │ ├── MemberRepository.ts │ │ │ │ └── MemberRepositoryImpl.ts │ │ │ ├── NoticeRepository │ │ │ │ ├── NoticeRepository.ts │ │ │ │ └── NoticeRepositoryImpl.ts │ │ │ ├── QuestionRepository │ │ │ │ ├── QuestionRepository.ts │ │ │ │ └── QuestionRepositoryImpl.ts │ │ │ └── SuggestionRepository │ │ │ │ ├── SuggestionRepository.ts │ │ │ │ └── SuggestionRepositoryImpl.ts │ │ ├── styles │ │ │ ├── globalStyle.css │ │ │ └── reset.css │ │ └── util │ │ │ └── ssr.ts │ └── tsconfig.json ├── teacher │ ├── .eslintrc.json │ ├── .gitignore │ ├── README.md │ ├── next.config.js │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── font │ │ │ └── createGlobalStyle.css │ │ ├── next.svg │ │ └── vercel.svg │ ├── src │ │ ├── HOF │ │ │ └── withAuth.ts │ │ ├── assets │ │ │ ├── Image │ │ │ │ ├── AuthBackground.svg │ │ │ │ ├── AuthImg.svg │ │ │ │ └── SignupImg.svg │ │ │ └── image │ │ │ │ ├── AttendCardProfile.svg │ │ │ │ ├── AttendIcon.svg │ │ │ │ ├── AttendTitleIcon.svg │ │ │ │ ├── TeacherLogo.svg │ │ │ │ ├── megaphoneIcon.svg │ │ │ │ └── userIcon.svg │ │ ├── components │ │ │ ├── Attend │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Auth │ │ │ │ ├── Login │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── Signup │ │ │ │ │ ├── SignupFirst │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ ├── SignupSecond │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Home │ │ │ │ ├── Attendance │ │ │ │ │ ├── AttendanceCode │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── Notifiction │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── Question │ │ │ │ │ ├── QuestionForm │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── TodayLectures │ │ │ │ │ ├── TodayLectureList │ │ │ │ │ │ ├── index.tsx │ │ │ │ │ │ └── style.ts │ │ │ │ │ └── index.tsx │ │ │ │ ├── index.tsx │ │ │ │ └── stlye.ts │ │ │ ├── Mypage │ │ │ │ ├── MyCancelLecture │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── MyLectures │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── MypageForm │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ └── common │ │ │ │ ├── Layout │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ │ ├── Nav │ │ │ │ ├── NavItem │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── NavUser │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── constant.ts │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ │ └── Provider │ │ │ │ ├── index.tsx │ │ │ │ └── types.ts │ │ ├── config │ │ │ └── index.ts │ │ ├── constant │ │ │ ├── Signup │ │ │ │ └── Signup.constant.ts │ │ │ └── Token │ │ │ │ └── Token.constant.ts │ │ ├── hooks │ │ │ ├── Attendance │ │ │ │ └── useChangeAttendanceStatus.ts │ │ │ ├── Auth │ │ │ │ ├── useLogin.ts │ │ │ │ ├── useLogout.ts │ │ │ │ └── useSignup.ts │ │ │ └── Question │ │ │ │ └── useWriteQuestion.ts │ │ ├── libs │ │ │ ├── Auth │ │ │ │ ├── customAxios.ts │ │ │ │ └── requestInterceptor.ts │ │ │ ├── storage │ │ │ │ ├── Cookie.ts │ │ │ │ └── Storage.ts │ │ │ └── token │ │ │ │ └── Token.ts │ │ ├── pages │ │ │ ├── 404.tsx │ │ │ ├── _app.tsx │ │ │ ├── _document.tsx │ │ │ ├── attend │ │ │ │ └── [id].tsx │ │ │ ├── index.tsx │ │ │ ├── myinfo.tsx │ │ │ └── sign.tsx │ │ ├── queries │ │ │ ├── AttendanceCode │ │ │ │ └── query.ts │ │ │ ├── Auth │ │ │ │ └── query.ts │ │ │ ├── Lectures │ │ │ │ └── query.ts │ │ │ ├── Member │ │ │ │ └── query.ts │ │ │ ├── Notice │ │ │ │ └── query.ts │ │ │ └── Question │ │ │ │ └── query.ts │ │ ├── repositories │ │ │ ├── AttendanceRepository │ │ │ │ ├── AttendanceRepository.ts │ │ │ │ └── AttendanceRepositoryImpl.ts │ │ │ ├── AuthRepository │ │ │ │ ├── AuthRepository.ts │ │ │ │ └── AuthRepositoryImpl.ts │ │ │ ├── LectureRepository │ │ │ │ ├── LectureRepository.ts │ │ │ │ └── LectureRepositoryImpl.ts │ │ │ ├── MemberRepository │ │ │ │ ├── MemberRepository.ts │ │ │ │ └── MemberRepositoryImpl.ts │ │ │ ├── NoticeRepository │ │ │ │ ├── NoticeRepository.ts │ │ │ │ └── NoticeRepositoryImpl.ts │ │ │ └── QuestionRepository │ │ │ │ ├── QuestionRepository.ts │ │ │ │ └── QuestionRepositoryImpl.ts │ │ ├── store │ │ │ └── lectureId.ts │ │ └── styles │ │ │ ├── globalStyle.css │ │ │ └── reset.css │ └── tsconfig.json └── user │ ├── .eslintrc.json │ ├── .gitignore │ ├── README.md │ ├── next.config.js │ ├── package.json │ ├── public │ ├── favicon.ico │ ├── font │ │ └── Pretendard-Regular.woff2 │ ├── next.svg │ └── vercel.svg │ ├── sentry.client.config.ts │ ├── sentry.server.config.ts │ ├── src │ ├── HOF │ │ └── withAuthHOF.ts │ ├── assets │ │ └── Image │ │ │ ├── AuthBackground.svg │ │ │ ├── AuthImg.svg │ │ │ └── SignupImg.svg │ ├── components │ │ ├── Auth │ │ │ ├── Login │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── Signup │ │ │ │ ├── SignupFirst │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── SignupSecond │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ └── index.tsx │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ ├── HOC │ │ │ └── withAuth.tsx │ │ ├── Home │ │ │ ├── Absence │ │ │ │ ├── AbsenceForm │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ └── index.tsx │ │ │ ├── Attend │ │ │ │ ├── AttendLectureForm │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ ├── AttendList │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ └── index.tsx │ │ │ ├── Notifiction │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── TodayLectures │ │ │ │ ├── TodayLectureList │ │ │ │ │ ├── index.tsx │ │ │ │ │ └── style.ts │ │ │ │ └── index.tsx │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ ├── Mypage │ │ │ ├── MyCancelLecture │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── MyLectures │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── MypageForm │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ ├── Register │ │ │ ├── RegistList │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ ├── Suggestion │ │ │ ├── SuggestionFrom │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ └── common │ │ │ ├── Layout │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ │ ├── Nav │ │ │ ├── NavItem │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── NavUser │ │ │ │ ├── index.tsx │ │ │ │ └── style.ts │ │ │ ├── constant.ts │ │ │ ├── index.tsx │ │ │ └── style.ts │ │ │ └── Provider │ │ │ ├── index.tsx │ │ │ └── types.ts │ ├── config │ │ └── index.ts │ ├── constant │ │ ├── Signup │ │ │ └── Signup.constant.ts │ │ └── Token │ │ │ └── Token.constant.ts │ ├── hooks │ │ ├── Absence │ │ │ └── useApplyAbsence.ts │ │ ├── Attendance │ │ │ └── useAttendance.ts │ │ ├── Auth │ │ │ ├── useLogin.ts │ │ │ ├── useLogout.ts │ │ │ ├── useSignup.ts │ │ │ └── useTokenCheck.ts │ │ └── Suggestion │ │ │ └── useSuggestionLecture.ts │ ├── libs │ │ ├── Auth │ │ │ ├── customAxios.ts │ │ │ └── requestInterceptor.ts │ │ ├── storage │ │ │ ├── Cookie.ts │ │ │ └── Storage.ts │ │ └── token │ │ │ └── Token.ts │ ├── pages │ │ ├── 404.tsx │ │ ├── _app.tsx │ │ ├── _document.tsx │ │ ├── _error.tsx │ │ ├── index.tsx │ │ ├── myinfo.tsx │ │ ├── register │ │ │ └── [grade].tsx │ │ ├── sign.tsx │ │ └── suggestion.tsx │ ├── queries │ │ ├── Absence │ │ │ └── query.ts │ │ ├── Attendance │ │ │ └── query.ts │ │ ├── Auth │ │ │ └── query.ts │ │ ├── Enrol │ │ │ └── query.ts │ │ ├── Lectures │ │ │ └── query.ts │ │ ├── Member │ │ │ └── Member.query.ts │ │ ├── Notice │ │ │ └── query.ts │ │ ├── Suggestion │ │ │ └── query.ts │ │ └── queryKey.ts │ ├── repositories │ │ ├── AbsenceRepository │ │ │ ├── AbsenceRepository.ts │ │ │ └── AbsenceRepositoryImpl.ts │ │ ├── AttendanceRepository │ │ │ ├── AttendanceRepository.ts │ │ │ └── AttendanceRepositoryImpl.ts │ │ ├── AuthRepository │ │ │ ├── AuthRepository.ts │ │ │ └── AuthRepositoryImpl.ts │ │ ├── EnrolRepository │ │ │ ├── EnrolRepository.ts │ │ │ └── EnrolRepositoryImpl.ts │ │ ├── LectureRepository │ │ │ ├── LectureRepository.ts │ │ │ └── LectureRepositoryImpl.ts │ │ ├── MemberRepository │ │ │ ├── MemberRepository.ts │ │ │ └── MemberRepositoryImpl.ts │ │ ├── NoticeRepository │ │ │ ├── NoticeRepository.ts │ │ │ └── NoticeRepositoryImpl.ts │ │ └── SuggestionRepository │ │ │ ├── SuggestionRepository.ts │ │ │ └── SuggestionRepositoryImpl.ts │ ├── styles │ │ ├── font.css │ │ └── reset.css │ └── utils │ │ └── srr.ts │ └── tsconfig.json ├── package.json ├── packages ├── checkin-icon │ ├── index.ts │ ├── package.json │ ├── src │ │ ├── Icon │ │ │ ├── CalendarIcon.tsx │ │ │ ├── CheckAbsenseIcon.tsx │ │ │ ├── DeleteIcon.tsx │ │ │ ├── IDIcon.tsx │ │ │ ├── LectureIcon.tsx │ │ │ ├── NotifictionIcon.tsx │ │ │ ├── PWIcon.tsx │ │ │ ├── PhotoIcon.tsx │ │ │ ├── ProfileIcon.tsx │ │ │ └── WriteIcon.tsx │ │ ├── Image │ │ │ ├── AuthImg.svg │ │ │ ├── Background.svg │ │ │ └── SignupImg.svg │ │ ├── Logo │ │ │ ├── CheckLogo.tsx │ │ │ ├── Logo.tsx │ │ │ └── types.ts │ │ └── Nav │ │ │ ├── AbsenceIcon.tsx │ │ │ ├── CheckSuggestionIcon.tsx │ │ │ ├── GenerateIcon.tsx │ │ │ ├── MypageIcon.tsx │ │ │ ├── NoticeIcon.tsx │ │ │ └── SchoolIcon.tsx │ └── tsconfig.json ├── checkin-queryKey │ ├── index.ts │ ├── package.json │ ├── src │ │ └── CheckInQueryKey.ts │ └── tsconfig.json ├── checkin-styled-theme │ ├── @types │ │ └── styled.d.ts │ ├── index.ts │ ├── package.json │ ├── src │ │ ├── CheckInPalette.ts │ │ ├── CheckInThemeProvider.tsx │ │ └── GlobalStyle.ts │ └── tsconfig.json ├── checkin-toastify │ ├── checkin-toast │ │ ├── ToastService.ts │ │ └── index.ts │ ├── checkin-toastContainer │ │ ├── checkinToastContainer.tsx │ │ └── checkinToastContainer.type.ts │ ├── index.ts │ ├── package.json │ └── tsconfig.json ├── checkin-types │ ├── Absence │ │ └── Absence.type.ts │ ├── Attendance │ │ └── Attendance.type.ts │ ├── Auth │ │ ├── Login │ │ │ └── Login.type.ts │ │ └── Signup │ │ │ └── Signup.type.ts │ ├── Lecture │ │ └── Lecture.type.ts │ ├── Member │ │ └── Member.type.ts │ ├── Notice │ │ └── Notice.type.ts │ ├── Question │ │ └── Question.type.ts │ ├── Suggestion │ │ └── Suggestion.type.ts │ ├── index.ts │ ├── package.json │ ├── tsconfig.json │ └── util │ │ └── response.ts ├── checkin-ui │ ├── .storybook │ │ ├── main.js │ │ └── preview.js │ ├── @types │ │ └── image.d.ts │ ├── assets │ │ ├── Icons │ │ │ ├── Calendar.svg │ │ │ ├── Club.svg │ │ │ ├── Notifiction.svg │ │ │ └── Write.svg │ │ └── Logo │ │ │ └── CheckLogo.svg │ ├── build-storybook.log │ ├── chromatic.log │ ├── components │ │ ├── Layout │ │ │ ├── Flex │ │ │ │ ├── Flex.tsx │ │ │ │ ├── style.ts │ │ │ │ └── types.ts │ │ │ └── Wrap │ │ │ │ ├── InputWrap │ │ │ │ ├── InputWrap.tsx │ │ │ │ ├── style.ts │ │ │ │ └── types.ts │ │ │ │ ├── SelectWrap │ │ │ │ ├── SelectWrap.tsx │ │ │ │ ├── style.ts │ │ │ │ └── types.ts │ │ │ │ ├── TextareaWrap │ │ │ │ ├── TextareaWrap.tsx │ │ │ │ ├── style.ts │ │ │ │ └── types.ts │ │ │ │ ├── WrapText.tsx │ │ │ │ └── types.ts │ │ └── UI │ │ │ ├── AbsenceStudent │ │ │ ├── AbsenceStudent.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── AttendacneStudent │ │ │ ├── AttendanceStudent.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Button │ │ │ ├── Button.stories.tsx │ │ │ ├── Button.tsx │ │ │ ├── DirectionButton.stories.tsx │ │ │ ├── WriteButton.stories.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Card │ │ │ ├── Card.stories.tsx │ │ │ ├── Card.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Input │ │ │ ├── AuthInput.stories.tsx │ │ │ ├── Input.tsx │ │ │ ├── TextInput.stories.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── LectureBox │ │ │ ├── LectureBox.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Modal │ │ │ ├── Modal.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── SectionHeader │ │ │ ├── SectionHeader.stories.tsx │ │ │ ├── SectionHeader.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Select │ │ │ ├── Select.stories.tsx │ │ │ ├── Select.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ │ │ ├── Text │ │ │ ├── Text.tsx │ │ │ └── style.ts │ │ │ └── Textarea │ │ │ ├── Textarea.tsx │ │ │ ├── style.ts │ │ │ └── types.ts │ ├── index.ts │ ├── package.json │ └── tsconfig.json ├── checkin-util │ ├── components │ │ └── SwitchCase.tsx │ ├── hooks │ │ ├── useBooleanState.ts │ │ └── useOutsideClick.ts │ ├── index.ts │ ├── package.json │ ├── tsconfig.json │ └── util │ │ ├── dataTransform.ts │ │ ├── dateTransform.ts │ │ ├── getRem.ts │ │ ├── patternCheck.ts │ │ ├── setLectureId.ts │ │ ├── stopEvent.ts │ │ └── stringEllipsis.ts ├── eslint-config-custom │ ├── index.js │ └── package.json └── tsconfig │ ├── base.json │ ├── nextjs.json │ ├── package.json │ └── react-library.json ├── pnpm-lock.yaml ├── pnpm-workspace.yaml └── turbo.json /.eslintrc.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | root: true, 3 | // This tells ESLint to load the config from the package `eslint-config-custom` 4 | extends: ["custom"], 5 | settings: { 6 | next: { 7 | rootDir: ["apps/*/"], 8 | }, 9 | }, 10 | }; 11 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | ##### **📘 할 내용** 2 | 3 | - 여기에 작성해 주세요 4 | 5 | --- 6 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | ##### **📘 한 내용** 2 | 3 | - 여기에 작성해 주세요 4 | 5 | --- 6 | -------------------------------------------------------------------------------- /.github/workflows/chromatic.yml: -------------------------------------------------------------------------------- 1 | # Workflow name 2 | name: "Chromatic Deployment" 3 | 4 | # Event for the workflow 5 | on: 6 | push: 7 | branches: 8 | - deploy/storybook 9 | 10 | # List of jobs 11 | jobs: 12 | test: 13 | # Operating System 14 | runs-on: ubuntu-latest 15 | # Job steps 16 | steps: 17 | - uses: actions/checkout@v1 18 | - run: yarn 19 | #👇 Adds Chromatic as a step in the workflow 20 | 21 | - uses: chromaui/action@v1 22 | # Options required for Chromatic's GitHub Action 23 | with: 24 | #👇 Chromatic projectToken, see https://storybook.js.org/tutorials/intro-to-storybook/react/ko/deploy/ to obtain it 25 | workingDir: packages/ui/ 26 | projectToken: ${{ secrets.CHROMATIC_PROJECT_TOKEN }} 27 | token: ${{ secrets.GIT_TOKEN }} 28 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | node_modules 5 | .pnp 6 | .pnp.js 7 | 8 | # testing 9 | coverage 10 | 11 | # next.js 12 | .next/ 13 | out/ 14 | build 15 | 16 | # misc 17 | .DS_Store 18 | *.pem 19 | 20 | # debug 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | 25 | # local env files 26 | .env 27 | .env.local 28 | .env.development.local 29 | .env.test.local 30 | .env.production.local 31 | 32 | # turbo 33 | .turbo 34 | 35 | # vercel 36 | .vercel 37 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | auto-install-peers = true 2 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | [스토리북](https://65433747d09cf8d71fa4ebb2-eyxbwnoura.chromatic.com/?path=/story/ui-button--common) 2 | -------------------------------------------------------------------------------- /apps/admin/.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": ["next/babel"], 3 | "plugins": [ 4 | [ 5 | "styled-components", 6 | { 7 | "ssr": true, 8 | "displayName": true, 9 | "preprocess": false 10 | } 11 | ] 12 | ] 13 | } 14 | -------------------------------------------------------------------------------- /apps/admin/.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "root": true, 3 | "extends": "next/core-web-vitals" 4 | } 5 | -------------------------------------------------------------------------------- /apps/admin/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # next.js 12 | /.next/ 13 | /out/ 14 | 15 | # production 16 | /build 17 | 18 | # misc 19 | .DS_Store 20 | *.pem 21 | 22 | # debug 23 | npm-debug.log* 24 | yarn-debug.log* 25 | yarn-error.log* 26 | 27 | # local env files 28 | .env*.local 29 | 30 | # vercel 31 | .vercel 32 | 33 | # typescript 34 | *.tsbuildinfo 35 | next-env.d.ts 36 | 37 | # Sentry Config File 38 | .sentryclirc 39 | -------------------------------------------------------------------------------- /apps/admin/next.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('next').NextConfig} */ 2 | 3 | const { withSentryConfig } = require("@sentry/nextjs"); 4 | 5 | const ENV = { 6 | ENV: process.env.NODE_ENV ?? "", 7 | API_HOST: process.env.API_HOST ?? process.env.REACT_APP_API_KEY, 8 | }; 9 | 10 | const nextConfig = { 11 | reactStrictMode: true, 12 | transpilePackages: ["@checkin/ui"], 13 | swcMinify: true, 14 | sentry: { 15 | hideSourceMaps: true, 16 | tunnelRoute: "/monitoring-tunnel", 17 | transpileClientSDK: true, 18 | }, 19 | publicRuntimeConfig: { ...ENV }, 20 | }; 21 | 22 | const sentryWebpackPluginOptions = { 23 | org: "checkin", 24 | project: "checkin-user", 25 | slient: true, 26 | }; 27 | 28 | module.exports = withSentryConfig(nextConfig, sentryWebpackPluginOptions); 29 | 30 | // Injected content via Sentry wizard below 31 | -------------------------------------------------------------------------------- /apps/admin/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Team-Growing/CheckIn-Web/f29a00909ce2cde273e972105725eafe850b8719/apps/admin/public/favicon.ico -------------------------------------------------------------------------------- /apps/admin/public/vercel.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /apps/admin/sentry.client.config.ts: -------------------------------------------------------------------------------- 1 | import * as Sentry from "@sentry/nextjs"; 2 | 3 | const SENTRY_DSN = process.env.SENTRY_DSN || process.env.NEXT_PUBLIC_SENTRY_DSN; 4 | 5 | Sentry.init({ 6 | dsn: SENTRY_DSN || "", 7 | integrations: [new Sentry.BrowserTracing(), new Sentry.Replay()], 8 | tracesSampleRate: 1.0, 9 | replaysSessionSampleRate: 0.1, 10 | replaysOnErrorSampleRate: 1.0, 11 | environment: process.env.NODE_ENV, 12 | }); 13 | -------------------------------------------------------------------------------- /apps/admin/sentry.server.config.ts: -------------------------------------------------------------------------------- 1 | import * as Sentry from "@sentry/nextjs"; 2 | 3 | const SENTRY_DSN = process.env.SENTRY_DSN || process.env.NEXT_PUBLIC_SENTRY_DSN; 4 | 5 | Sentry.init({ 6 | dsn: SENTRY_DSN || "", 7 | tracesSampleRate: 1.0, 8 | environment: process.env.NODE_ENV, 9 | }); 10 | -------------------------------------------------------------------------------- /apps/admin/src/HOF/withAuthHOF.ts: -------------------------------------------------------------------------------- 1 | import { GetServerSideProps, GetServerSidePropsContext } from "next"; 2 | import cookies from "next-cookies"; 3 | import { ACCESS_TOKEN_KEY } from "@/constant/Token/Token.constant"; 4 | import { setAccessToken } from "@/libs/Auth/customAxios"; 5 | 6 | const withAuth = (getServerSideProps: GetServerSideProps) => { 7 | return async (context: GetServerSidePropsContext) => { 8 | const accessToken = cookies(context)[ACCESS_TOKEN_KEY]; 9 | 10 | if (accessToken === undefined) { 11 | return { 12 | redirect: { 13 | destination: "/login", 14 | permanent: false, 15 | }, 16 | }; 17 | } 18 | setAccessToken(accessToken); 19 | 20 | try { 21 | return await getServerSideProps(context); 22 | } catch (error) {} 23 | }; 24 | }; 25 | 26 | export default withAuth; 27 | -------------------------------------------------------------------------------- /apps/admin/src/components/Auth/index.tsx: -------------------------------------------------------------------------------- 1 | import AuthImg from "../../assets/Image/AuthImg.svg"; 2 | import * as S from "./style"; 3 | import Login from "./Login"; 4 | 5 | const Auth = () => { 6 | return ( 7 | <> 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | ); 20 | }; 21 | 22 | export default Auth; 23 | -------------------------------------------------------------------------------- /apps/admin/src/components/Auth/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | import AuthBackground from "../../assets/Image/AuthBackground.svg"; 3 | import Image from "next/image"; 4 | 5 | export const AuthBackGround = styled.div` 6 | width: 100%; 7 | height: 100vh; 8 | display: flex; 9 | align-items: center; 10 | justify-content: center; 11 | background-image: url(${AuthBackground.src}); 12 | `; 13 | 14 | export const AuthContainer = styled.div` 15 | width: 1150px; 16 | height: 700px; 17 | border-radius: 10px; 18 | display: flex; 19 | overflow: hidden; 20 | background: rgba(255, 255, 255, 0.9); 21 | `; 22 | 23 | export const AuthPanelWrap = styled.div` 24 | min-width: 644px; 25 | max-width: 644px; 26 | height: 100%; 27 | position: relative; 28 | `; 29 | 30 | export const AuthPanel = styled(Image)` 31 | width: 100%; 32 | height: 100%; 33 | object-fit: cover; 34 | `; 35 | 36 | export const AuthWrap = styled.div` 37 | width: 100%; 38 | height: 100%; 39 | padding: 70px 72px 0 84px; 40 | `; 41 | -------------------------------------------------------------------------------- /apps/admin/src/components/CMS/constant.ts: -------------------------------------------------------------------------------- 1 | export const CmsStatusList = [ 2 | { 3 | name: "신청 대기", 4 | status: "WAITING_PERIOD", 5 | color: "#F7D356", 6 | dataStatus: "waitingPeroid", 7 | }, 8 | { 9 | name: "신청 중", 10 | status: "ENROLMENT", 11 | color: "#209915", 12 | dataStatus: "enrolment", 13 | }, 14 | { 15 | name: "수강 중", 16 | status: "COURSE_PERIOD", 17 | color: "#0073C9", 18 | dataStatus: "COURSE_PERIOD", 19 | }, 20 | { 21 | name: "종료", 22 | status: "TERMINATION", 23 | color: "#454749", 24 | dataStatus: "termination", 25 | }, 26 | ]; 27 | 28 | export const CmsStatus = [ 29 | "WAITING_PERIOD", 30 | "ENROLMENT", 31 | "COURSE_PERIOD", 32 | "TERMINATION", 33 | ]; 34 | -------------------------------------------------------------------------------- /apps/admin/src/components/Confirm/QuestionConfirm/style.ts: -------------------------------------------------------------------------------- 1 | import { CheckInColor } from "@checkin/styled-theme"; 2 | import styled from "styled-components"; 3 | 4 | export const ConfirmListContainer = styled.div``; 5 | 6 | export const ConfirmListHeader = styled.div` 7 | display: flex; 8 | align-items: center; 9 | 10 | height: 50px; 11 | border-bottom: 3px solid #636363; 12 | `; 13 | 14 | export const ConfirmTitle = styled.div``; 15 | 16 | export const ConfirmListItemContaienr = styled.div` 17 | display: flex; 18 | align-items: center; 19 | 20 | height: 50px; 21 | 22 | cursor: pointer; 23 | border-bottom: 1px solid #d2d2d2; 24 | 25 | background-color: ${CheckInColor.Background.Lightest}; 26 | &:hover { 27 | background-color: ${CheckInColor.Background.Lightbase}; 28 | } 29 | `; 30 | 31 | export const ConfirmListItem = styled.div` 32 | width: 10%; 33 | `; 34 | -------------------------------------------------------------------------------- /apps/admin/src/components/Confirm/SuggestionConfirm/style.ts: -------------------------------------------------------------------------------- 1 | import { CheckInColor } from "@checkin/styled-theme"; 2 | import styled from "styled-components"; 3 | 4 | export const ConfirmListContainer = styled.div``; 5 | 6 | export const ConfirmListHeader = styled.div` 7 | display: flex; 8 | align-items: center; 9 | 10 | height: 50px; 11 | border-bottom: 3px solid #636363; 12 | `; 13 | 14 | export const ConfirmTitle = styled.div``; 15 | 16 | export const ConfirmListItemContaienr = styled.div` 17 | display: flex; 18 | align-items: center; 19 | 20 | height: 50px; 21 | cursor: pointer; 22 | 23 | background-color: ${CheckInColor.Background.Lightest}; 24 | &:hover { 25 | background-color: ${CheckInColor.Background.Lightbase}; 26 | } 27 | border-bottom: 1px solid #d2d2d2; 28 | `; 29 | 30 | export const ConfirmListItem = styled.div` 31 | width: 10%; 32 | `; 33 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/LectureGenerate/LecturePeriod/index.tsx: -------------------------------------------------------------------------------- 1 | import { DateInputWrap, Flex } from "@checkin/ui"; 2 | import React from "react"; 3 | 4 | interface Props { 5 | lecturePeriod: { 6 | startDay: string; 7 | endDay: string; 8 | }; 9 | onChangeLecturePeriod: (e: React.ChangeEvent) => void; 10 | } 11 | 12 | const LecturePeriod = ({ lecturePeriod, onChangeLecturePeriod }: Props) => { 13 | return ( 14 | 15 | 16 | 24 | 25 | 26 | 34 | 35 | 36 | ); 37 | }; 38 | 39 | export default LecturePeriod; 40 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/LectureGenerate/LectureSubmitButton/index.tsx: -------------------------------------------------------------------------------- 1 | import { Button, Flex } from "@checkin/ui"; 2 | import React from "react"; 3 | 4 | const LectureSubmitButton = () => { 5 | return ( 6 | 7 | 10 | 11 | ); 12 | }; 13 | 14 | export default LectureSubmitButton; 15 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/LectureGenerate/LectureTime/style.ts: -------------------------------------------------------------------------------- 1 | import { getRem } from "@checkin/util"; 2 | import styled from "styled-components"; 3 | 4 | export const SelectDateBox = styled.div<{ isSelect?: boolean }>` 5 | width: 100px; 6 | height: 27px; 7 | 8 | display: flex; 9 | justify-content: center; 10 | align-items: center; 11 | 12 | border-radius: 50px; 13 | background: #f2f2f2; 14 | 15 | font-size: ${getRem(14)}; 16 | cursor: pointer; 17 | 18 | background-color: ${({ isSelect }) => (isSelect ? "#00c537" : "#F2F2F2")}; 19 | color: ${({ isSelect }) => (isSelect ? "#fff" : "#000")}; 20 | &:hover { 21 | background-color: #00c537; 22 | color: #f2f2f2; 23 | } 24 | `; 25 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/LectureGenerate/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const LectureFormContainer = styled.form` 4 | display: flex; 5 | flex-direction: column; 6 | 7 | row-gap: 34px; 8 | 9 | width: 100%; 10 | height: auto; 11 | 12 | padding: 46px 39px 43px; 13 | margin-top: 23px; 14 | 15 | background-color: #fff; 16 | `; 17 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/NoticeGenerate/NoticeList/style.ts: -------------------------------------------------------------------------------- 1 | import { getRem } from "@checkin/util"; 2 | import styled from "styled-components"; 3 | 4 | export const NoticeListContainer = styled.div` 5 | width: 100%; 6 | 7 | margin-top: 50px; 8 | 9 | display: flex; 10 | flex-direction: column; 11 | 12 | row-gap: 25px; 13 | `; 14 | 15 | export const NoticeWrap = styled.div` 16 | display: flex; 17 | justify-content: space-between; 18 | 19 | padding: 0 54px 0 54px; 20 | align-items: center; 21 | 22 | background-color: #ffffff; 23 | 24 | width: 100%; 25 | height: 64px; 26 | `; 27 | 28 | export const NoticeText = styled.p` 29 | width: 70%; 30 | color: #828282; 31 | font-size: ${getRem(18)}; 32 | font-weight: 500; 33 | `; 34 | 35 | export const NoticeCreatedAt = styled.p` 36 | font-size: 18px; 37 | font-weight: 400; 38 | line-height: 32px; 39 | `; 40 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/NoticeGenerate/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const NoticeGenerateContainer = styled.div` 4 | width: 100%; 5 | height: 100%; 6 | 7 | margin-top: 40px; 8 | `; 9 | 10 | export const NoticeFormContainer = styled.div` 11 | width: 100%; 12 | height: 210px; 13 | 14 | position: absolute; 15 | 16 | background-color: red; 17 | bottom: 0; 18 | `; 19 | 20 | export const NoticeListContainer = styled.div` 21 | width: 100%; 22 | 23 | margin-top: 50px; 24 | 25 | display: flex; 26 | flex-direction: column; 27 | 28 | row-gap: 25px; 29 | `; 30 | -------------------------------------------------------------------------------- /apps/admin/src/components/Generate/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const SuggestionContainer = styled.div` 4 | padding: 69px 105px; 5 | `; 6 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Absence/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Contact/ContactList/index.tsx: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import * as S from "./style"; 3 | import { useGetQuestionsQuery } from "@/queries/Question/query"; 4 | import { dateTransform, stringEllipsis } from "@checkin/util"; 5 | 6 | const ContactList = () => { 7 | const { data } = useGetQuestionsQuery({ limit: 5, page: 1 }); 8 | 9 | return ( 10 | <> 11 | 12 | 13 |

일자

14 |

문의 내용

15 |

이름

16 |
17 | {data?.data.value.map((data) => ( 18 | 19 |

{dateTransform.hyphen(data.createdAt)}

20 |

{`${stringEllipsis(data.title, 25)}`}

21 |

{data.questioner.name}

22 |
23 | ))} 24 |
25 | 26 | ); 27 | }; 28 | 29 | export default ContactList; 30 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Contact/ContactList/style.ts: -------------------------------------------------------------------------------- 1 | import { getRem } from "@checkin/util"; 2 | import styled from "styled-components"; 3 | 4 | export const ContactListContainer = styled.div` 5 | width: 100%; 6 | 7 | display: flex; 8 | flex-direction: column; 9 | `; 10 | 11 | export const ContactListTitle = styled.div` 12 | width: 100%; 13 | 14 | display: flex; 15 | align-items: center; 16 | justify-content: space-between; 17 | position: sticky; 18 | top: 0px; 19 | z-index: 3; 20 | background-color: #fff; 21 | border-bottom: 1px solid #cdd0dc; 22 | 23 | p { 24 | font-size: ${getRem(16)}; 25 | color: #6c7072; 26 | font-weight: 400; 27 | } 28 | `; 29 | 30 | export const ContactListText = styled.div` 31 | height: 50px; 32 | 33 | width: 100%; 34 | 35 | display: flex; 36 | align-items: center; 37 | justify-content: space-between; 38 | cursor: pointer; 39 | border-bottom: 1px solid #cdd0dc; 40 | 41 | p { 42 | color: #202325; 43 | font-size: ${getRem(16)}; 44 | font-weight: 400; 45 | } 46 | 47 | &:hover { 48 | background-color: #f2f2f2f2; 49 | } 50 | `; 51 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Contact/index.tsx: -------------------------------------------------------------------------------- 1 | import { Card, CardTitle, Flex } from "@checkin/ui"; 2 | import React from "react"; 3 | import { WriteIcon } from "@checkin/icon"; 4 | import ContactList from "./ContactList"; 5 | import styled from "styled-components"; 6 | import Link from "next/link"; 7 | 8 | const Contact = () => { 9 | return ( 10 | 11 | 12 | 13 | 14 | 담당자 문의 15 | 16 | 더보기 17 | 18 | 19 | 20 | 21 | 22 | ); 23 | }; 24 | 25 | export default Contact; 26 | 27 | const Container = styled.div` 28 | width: 100%; 29 | height: 100%; 30 | overflow: auto; 31 | margin-top: 20px; 32 | 33 | ::-webkit-scrollbar { 34 | display: none; 35 | } 36 | `; 37 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Notifiction/index.tsx: -------------------------------------------------------------------------------- 1 | import { CardTitle } from "@checkin/ui"; 2 | import React, { useState } from "react"; 3 | import { NotifictionIcon } from "@checkin/icon"; 4 | import { NoticeContainer, NoticeContent } from "./style"; 5 | import { useGetActiveNoticeQuery } from "@/queries/Notice/query"; 6 | 7 | const Notifiction = () => { 8 | const { data } = useGetActiveNoticeQuery(); 9 | const [noticeLength, setNoticeLength] = useState(data?.data.length! - 1); 10 | 11 | setTimeout(() => { 12 | if (noticeLength !== 0) { 13 | setNoticeLength(noticeLength - 1); 14 | } else { 15 | setNoticeLength(data?.data.length! - 1); 16 | } 17 | }, 3000); 18 | return ( 19 | 20 | 21 | 22 | 공지사항 23 | 24 | {data?.data[noticeLength]?.content} 25 |

{`${data?.data.length! - noticeLength}/${data?.data.length}`}

26 |
27 | ); 28 | }; 29 | 30 | export default Notifiction; 31 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/Notifiction/style.ts: -------------------------------------------------------------------------------- 1 | import { getRem } from "@checkin/util"; 2 | import styled from "styled-components"; 3 | 4 | export const NoticeContent = styled.div` 5 | width: 70%; 6 | color: #828282; 7 | font-size: ${getRem(18)}; 8 | font-weight: 500; 9 | `; 10 | 11 | export const NoticeContainer = styled.div` 12 | width: 92.5%; 13 | height: 6vh; 14 | 15 | display: flex; 16 | align-items: center; 17 | 18 | position: relative; 19 | overflow: hidden; 20 | column-gap: 63px; 21 | padding-left: 29px; 22 | 23 | border-radius: 5px; 24 | border: 1px solid #cdd0dc; 25 | background: #fff; 26 | `; 27 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/TodayLectures/TodayLectureList/index.tsx: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { LectureBox } from "@checkin/ui"; 3 | import { LectureListWrapper } from "./style"; 4 | import { LecturesResponse } from "@checkin/types"; 5 | 6 | interface Props { 7 | data: LecturesResponse; 8 | } 9 | 10 | const TodayLecturesList = ({ data }: Props) => { 11 | return ( 12 |
13 | 14 |
15 | {data.data.map((data) => ( 16 | 25 | ))} 26 |
27 |
28 |
29 | ); 30 | }; 31 | 32 | export default TodayLecturesList; 33 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/TodayLectures/TodayLectureList/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const LectureListWrapper = styled.div` 4 | width: 100%; 5 | height: 100%; 6 | 7 | display: flex; 8 | 9 | column-gap: 20px; 10 | `; 11 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/TodayLectures/index.tsx: -------------------------------------------------------------------------------- 1 | import { Card, CardTitle } from "@checkin/ui"; 2 | import React from "react"; 3 | import { LectureIcon } from "@checkin/icon"; 4 | import TodayLecturesList from "./TodayLectureList"; 5 | import { useGetTodayLecturesQuery } from "@/queries/Lectures/query"; 6 | 7 | const TodayLectures = () => { 8 | const { data } = useGetTodayLecturesQuery(); 9 | 10 | return ( 11 | 12 | 13 | 14 | 오늘의 방과후 15 | 16 | {data?.data.length === 0 &&
오늘의 방과후는 없습니다
} 17 | {data?.data && } 18 |
19 | ); 20 | }; 21 | 22 | export default TodayLectures; 23 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/index.tsx: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import * as S from "./style"; 3 | import TodayLectures from "./TodayLectures"; 4 | import Notifiction from "./Notifiction"; 5 | import { Flex } from "@checkin/ui"; 6 | import AbsenceList from "./Absence"; 7 | import Contact from "./Contact"; 8 | 9 | const Home = () => { 10 | return ( 11 | 12 | 13 | 14 | 22 | 23 | 24 | 25 | 26 | ); 27 | }; 28 | 29 | export default Home; 30 | -------------------------------------------------------------------------------- /apps/admin/src/components/Home/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const HomeContainer = styled.div` 4 | width: 100%; 5 | height: 100%; 6 | 7 | display: flex; 8 | flex-direction: column; 9 | justify-content: center; 10 | align-items: center; 11 | 12 | row-gap: 15px; 13 | `; 14 | -------------------------------------------------------------------------------- /apps/admin/src/components/SMS/style.ts: -------------------------------------------------------------------------------- 1 | import styled from "styled-components"; 2 | 3 | export const CheckAttendanceContainer = styled.div` 4 | padding: 69px 104px; 5 | `; 6 | -------------------------------------------------------------------------------- /apps/admin/src/components/common/Layout/index.tsx: -------------------------------------------------------------------------------- 1 | import Nav from "../Nav"; 2 | import { Container, Wrap } from "./style"; 3 | import { useRouter } from "next/router"; 4 | 5 | interface Props { 6 | children: React.ReactNode; 7 | } 8 | 9 | const Layout = ({ children }: Props) => { 10 | const { pathname } = useRouter(); 11 | return ( 12 | <> 13 | 14 | {pathname !== "/sign" &&