2323
2424@ RestController
2525@ RequiredArgsConstructor
26- @ RequestMapping ("/api/admin/attendance " )
26+ @ RequestMapping ("/api" )
2727@ Tag (name = "관리자 출석관리" , description = "관리자용 출석 관리 API" )
2828public class AdminAttendanceController {
2929
3030 private final AttendanceService attendanceService ;
3131
3232 // 출석체크 시작
3333 @ Operation (summary = "출석 체크 시작" , description = "새로운 출석 코드를 생성하고 출석 체크를 시작합니다." )
34- @ ApiResponses ({
35- @ io .swagger .v3 .oas .annotations .responses .ApiResponse (
36- responseCode = "200" ,
37- description = "출석 코드 생성 성공" ,
38- content = @ Content (schema = @ Schema (implementation = AttendanceCodeResponse .class ))
39- ),
34+ @ ApiResponses (value = {
35+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "출석 코드 생성 성공" ),
4036 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" )
4137 })
42- @ PostMapping ("/start" )
43- public ApiResponse < AttendanceCodeResponse > startAttendance () {
38+ @ PostMapping ("/admin/attendance/ start" )
39+ public AttendanceCodeResponse startAttendance () {
4440 try {
4541 AttendanceCode code = attendanceService .generateCodeAndCreateAttendances ();
46- return ApiResponse . success ( AttendanceCodeResponse .from (code ) );
42+ return AttendanceCodeResponse .from (code );
4743 } catch (IllegalStateException e ) {
4844 // 하루 최대 출석 체크 횟수를 초과한 경우
49- return ApiResponse . error (e .getMessage ());
45+ throw new IllegalStateException (e .getMessage ());
5046 } catch (Exception e ) {
51- return ApiResponse . error ("출석 코드 생성 중 오류가 발생했습니다: " + e .getMessage ());
47+ throw new RuntimeException ("출석 코드 생성 중 오류가 발생했습니다: " + e .getMessage ());
5248 }
5349 }
5450
5551 // 현재 활성화된 출석코드 조회
5652 @ Operation (summary = "현재 활성화된 출석 코드 조회" , description = "현재 활성화된 출석 코드 정보를 조회합니다." )
57- @ ApiResponses ({
58- @ io .swagger .v3 .oas .annotations .responses .ApiResponse (
59- responseCode = "200" ,
60- description = "조회 성공" ,
61- content = @ Content (schema = @ Schema (implementation = AttendanceCodeResponse .class ))
62- ),
53+ @ ApiResponses (value = {
54+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "조회 성공" ),
6355 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "활성화된 출석 코드 없음" )
6456 })
65- @ GetMapping ("/active-code" )
66- public ApiResponse < AttendanceCodeResponse > getActiveCode () {
57+ @ GetMapping ("/admin/attendance/ active-code" )
58+ public AttendanceCodeResponse getActiveCode () {
6759 Optional <AttendanceCode > codeOpt = attendanceService .getActiveAttendanceCode ();
6860
6961 if (codeOpt .isEmpty ()) {
70- return ApiResponse . error ("현재 활성화된 출석코드가 없습니다" );
62+ throw new RuntimeException ("현재 활성화된 출석코드가 없습니다" );
7163 }
7264
73- return ApiResponse . success ( AttendanceCodeResponse .from (codeOpt .get () ));
65+ return AttendanceCodeResponse .from (codeOpt .get ());
7466 }
7567
7668 // 출석체크 종료 (코드 직접 전달)
7769 @ Operation (summary = "특정 출석 코드 만료" , description = "특정 출석 코드를 만료 처리합니다." )
78- @ ApiResponses ({
70+ @ ApiResponses (value = {
7971 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "만료 처리 성공" ),
8072 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" ),
8173 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "출석 코드를 찾을 수 없음" )
8274 })
83- @ PutMapping ("/expire" )
84- public ApiResponse < Void > expireAttendance (
85- @ Parameter (description = "만료할 출석 코드" , required = true )
75+ @ PutMapping ("/admin/attendance/ expire" )
76+ public String expireAttendance (
77+ @ Parameter (description = "만료할 출석 코드" , example = "1234" )
8678 @ RequestParam String code ) {
87- String result = attendanceService .expireAttendanceCode (code );
88-
89- if (result .equals ("출석 코드가 성공적으로 만료되었습니다" )) {
90- return ApiResponse .success (result , null );
91- } else {
92- return ApiResponse .error (result );
93- }
79+ return attendanceService .expireAttendanceCode (code );
9480 }
9581
9682 // 출석체크 종료 (가장 최근 활성화된 코드 자동 만료)
9783 @ Operation (summary = "최근 활성화된 출석 코드 만료" , description = "가장 최근 활성화된 출석 코드를 자동으로 만료 처리합니다." )
98- @ ApiResponses ({
84+ @ ApiResponses (value = {
9985 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "만료 처리 성공" ),
10086 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "활성화된 출석 코드가 없음" )
10187 })
102- @ PutMapping ("/expire-latest" )
103- public ApiResponse <Void > expireLatestAttendance () {
104- String result = attendanceService .expireLatestAttendanceCode ();
105-
106- if (result .equals ("출석 코드가 성공적으로 만료되었습니다" )) {
107- return ApiResponse .success (result , null );
108- } else {
109- return ApiResponse .error (result );
110- }
88+ @ PutMapping ("/admin/attendance/expire-latest" )
89+ public String expireLatestAttendance () {
90+ return attendanceService .expireLatestAttendanceCode ();
11191 }
11292
11393 // 출석 상태 변경 (관리자 전용)
11494 @ Operation (summary = "출석 상태 변경" , description = "관리자가 특정 사용자의 출석 상태를 변경합니다." )
115- @ ApiResponses ({
95+ @ ApiResponses (value = {
11696 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "출석 상태 변경 성공" ),
11797 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" ),
11898 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "출석 기록을 찾을 수 없음" )
11999 })
120- @ PutMapping ("/status" )
121- public ApiResponse <Void > updateAttendanceStatus (
122- @ io .swagger .v3 .oas .annotations .parameters .RequestBody (
123- description = "출석 상태 변경 요청" ,
124- required = true ,
125- content = @ Content (schema = @ Schema (implementation = UpdateAttendanceStatusReq .class ))
126- )
100+ @ PutMapping ("/admin/users/{userId}/attendance/{attendanceId}/status" )
101+ public boolean updateAttendanceStatus (
102+ @ Parameter (description = "사용자 ID" , example = "1" )
103+ @ PathVariable Long userId ,
104+ @ Parameter (description = "출석 ID" , example = "1" )
105+ @ PathVariable Long attendanceId ,
127106 @ RequestBody UpdateAttendanceStatusReq req ) {
128107
129- boolean result = attendanceService .updateAttendanceStatus (
130- req .getAttendanceId (),
131- req .isStatus ()
132- );
108+ // userId 파라미터 검증은 여기서 할 수 있음 (필요 시)
109+ return attendanceService .updateAttendanceStatus (attendanceId , req .isStatus ());
110+ }
111+
112+ // 출석 기록 삭제 (관리자 전용)
113+ @ Operation (summary = "출석 기록 삭제" , description = "관리자가 특정 사용자의 출석 기록을 삭제합니다." )
114+ @ ApiResponses (value = {
115+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "출석 기록 삭제 성공" ),
116+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" ),
117+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "출석 기록을 찾을 수 없음" )
118+ })
119+ @ DeleteMapping ("/admin/users/{userId}/attendance/{attendanceId}" )
120+ public boolean deleteAttendance (
121+ @ Parameter (description = "사용자 ID" , example = "1" )
122+ @ PathVariable Long userId ,
123+ @ Parameter (description = "출석 ID" , example = "1" )
124+ @ PathVariable Long attendanceId ) {
133125
134- if (result ) {
135- return ApiResponse .success ("출석 상태가 성공적으로 변경되었습니다" , null );
136- } else {
137- return ApiResponse .error ("출석 상태 변경에 실패했습니다. 출석 기록을 찾을 수 없습니다." );
138- }
126+ // userId 파라미터 검증은 여기서 할 수 있음 (필요 시)
127+ return attendanceService .deleteAttendance (attendanceId );
139128 }
140129
141130 // 특정 날짜와 차수에 대한 모든 학생의 출석 현황 조회
142131 @ Operation (summary = "특정 날짜와 차수의 출석 현황 조회" , description = "특정 날짜와 차수에 대한 모든 학생의 출석 현황을 조회합니다." )
143- @ ApiResponses ({
132+ @ ApiResponses (value = {
144133 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "조회 성공" ),
145134 @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" )
146135 })
147- @ GetMapping ("/list" )
148- public ApiResponse <List <UserAttendanceStatusRes >> getAllAttendanceByDateAndOrder (
149- @ Parameter (description = "조회할 날짜 (YYYY-MM-DD)" , required = true )
136+ @ GetMapping ("/admin/attendance/list" )
137+ public List <UserAttendanceStatusRes > getAllAttendanceByDateAndOrder (
138+ @ Parameter (description = "조회할 날짜 (YYYY-MM-DD)" , example = "2023-08-01" )
139+ @ RequestParam @ DateTimeFormat (iso = DateTimeFormat .ISO .DATE ) LocalDate date ,
140+ @ Parameter (description = "조회할 차수" , example = "1" )
141+ @ RequestParam int order ) {
142+ return attendanceService .findAllByDateAndOrder (date , order );
143+ }
144+
145+ // 특정 사용자의 특정 날짜와 차수 출석 기록 조회
146+ @ Operation (summary = "특정 사용자의 특정 날짜와 차수 출석 조회" , description = "특정 사용자의 특정 날짜와 차수 출석 기록을 조회합니다." )
147+ @ ApiResponses (value = {
148+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "조회 성공" ),
149+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" ),
150+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "출석 기록을 찾을 수 없음" )
151+ })
152+ @ GetMapping ("/admin/users/{userId}/attendance" )
153+ public UserAttendanceStatusRes getUserAttendanceByDateAndOrder (
154+ @ Parameter (description = "사용자 ID" , example = "1" )
155+ @ PathVariable Long userId ,
156+ @ Parameter (description = "조회할 날짜 (YYYY-MM-DD)" , example = "2023-08-01" )
150157 @ RequestParam @ DateTimeFormat (iso = DateTimeFormat .ISO .DATE ) LocalDate date ,
151- @ Parameter (description = "조회할 차수" , required = true )
158+ @ Parameter (description = "조회할 차수" , example = "1" )
152159 @ RequestParam int order ) {
160+ return attendanceService .findByUserIdAndDateAndOrder (userId , date , order );
161+ }
162+
163+ // 특정 출석 ID로 출석 기록 조회
164+ @ Operation (summary = "특정 출석 기록 조회" , description = "특정 학생의 특정 출석 기록을 ID로 조회합니다." )
165+ @ ApiResponses (value = {
166+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "조회 성공" ),
167+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "404" , description = "출석 기록을 찾을 수 없음" )
168+ })
169+ @ GetMapping ("/admin/users/{userId}/attendance/{attendanceId}" )
170+ public UserAttendanceStatusRes getAttendanceById (
171+ @ Parameter (description = "사용자 ID" , example = "1" )
172+ @ PathVariable Long userId ,
173+ @ Parameter (description = "출석 ID" , example = "1" )
174+ @ PathVariable Long attendanceId ) {
153175
154- List <UserAttendanceStatusRes > attendances = attendanceService .findAllByDateAndOrder (date , order );
155- return ApiResponse .success (attendances );
176+ UserAttendanceStatusRes attendance = attendanceService .findById (attendanceId );
177+
178+ if (attendance == null ) {
179+ throw new RuntimeException ("출석 기록을 찾을 수 없습니다" );
180+ }
181+
182+ // 요청된 userId와 조회된 출석 기록의 userId가 일치하는지 확인
183+ if (!attendance .getUserId ().equals (userId )) {
184+ throw new RuntimeException ("요청된 사용자 ID와 출석 기록의 사용자 ID가 일치하지 않습니다" );
185+ }
186+
187+ return attendance ;
188+ }
189+
190+ // 학생용 출석 현황 조회
191+ @ Operation (summary = "학생별 출석 현황 조회" , description = "특정 학생의 출석 현황을 조회합니다." )
192+ @ ApiResponses (value = {
193+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "200" , description = "조회 성공" ),
194+ @ io .swagger .v3 .oas .annotations .responses .ApiResponse (responseCode = "400" , description = "잘못된 요청" )
195+ })
196+ @ GetMapping ("/attendance/{userId}" )
197+ public List <UserAttendanceStatusRes > getUserAttendances (
198+ @ Parameter (description = "사용자 ID" , example = "1" )
199+ @ PathVariable Long userId ) {
200+ return attendanceService .findAllByUserId (userId );
156201 }
157202}
0 commit comments