4-4. MVC 시대 (실습 3)

박은서's avatar
Jan 29, 2026
4-4. MVC 시대 (실습 3)

실습 3. 어노테이션 사용하여 리플렉션으로 단일진입점 만들기

1) RequestMapping 어노테이션 생성

package ex03; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Retention(RetentionPolicy.RUNTIME) // 동작 시점(컴파일 source? 실행시점 runtime?) @Target(ElementType.METHOD) // 위치 public @interface RequestMapping { }

2) BoardController

package ex03; public class BoardController { public void insert(){ System.out.println("insert 호출됨"); } public void delete(){ System.out.println("delete 호출됨"); } @RequestMapping public void update(){ System.out.println("update 호출됨"); } }

3) App (main)

package ex03; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; public class App { public static void main(String[] args) { // 1. 키보드 입력 자리 String uri = "/join"; // 2. 다름 사람이 만든 코드 BoardController con = new BoardController(); // 2-1. 동적 클래스 분석 Method[] methods = BoardController.class.getDeclaredMethods(); for (Method m : methods) { RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class); System.out.println(rm); System.out.println(m.getName()); System.out.println("---------------------"); } } }

3-1) 결과

notion image

[참고] RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class);

💡
RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class);
➡️ @RequestMapping 어노테이션이 붙어 있는지 확인하고 가져오는 코드

4) 모든 메서드에 어노테이션 붙이기 (깃발 꽂기)

package ex03; public class BoardController { @RequestMapping public void insert(){ System.out.println("insert 호출됨"); } @RequestMapping public void delete(){ System.out.println("delete 호출됨"); } @RequestMapping public void update(){ System.out.println("update 호출됨"); } }
package ex03; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; public class App { public static void main(String[] args) { // 1. 키보드 입력 자리 String uri = "/join"; // 2. 다름 사람이 만든 코드 BoardController con = new BoardController(); // 2-1. 동적 클래스 분석 Method[] methods = BoardController.class.getDeclaredMethods(); for (Method m : methods) { RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class); System.out.println(rm); System.out.println(m.getName()); System.out.println("---------------------"); } } }

4-1) 결과

notion image

5) 어노테이션(깃발)에 번호 붙여서 구분하기

package ex03; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Retention(RetentionPolicy.RUNTIME) // 동작 시점(컴파일 source? 실행시점 runtime?) @Target(ElementType.METHOD) // 위치 public @interface RequestMapping { String value(); // 어노테이션의 속성값(value라는 이름 사용 시에만 생략 가능) }
package ex03; public class BoardController { @RequestMapping(value = "/insert") public void insert(){ System.out.println("insert 호출됨"); } @RequestMapping(value = "/delete") public void delete(){ System.out.println("delete 호출됨"); } @RequestMapping(value = "/update") public void update(){ System.out.println("update 호출됨"); } }
💡
value라는 이름 사용 시에만 키값 생략 가능 (다른 이름은 안됨)
package ex03; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; public class App { public static void main(String[] args) { // 1. 키보드 입력 자리 String uri = "/insert"; // 2. 다름 사람이 만든 코드 BoardController con = new BoardController(); // 2-1. 동적 클래스 분석 Method[] methods = BoardController.class.getDeclaredMethods(); for (Method m : methods) { RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class); if (rm.value().equals(uri)) { try { m.invoke(con); } catch (IllegalAccessException e) { throw new RuntimeException(e); } catch (InvocationTargetException e) { throw new RuntimeException(e); } } } } }

5-1) 결과

notion image

6) select 메서드 추가해서 구현

package ex03; public class BoardController { @RequestMapping("/insert") public void insert(){ System.out.println("insert 호출됨"); } @RequestMapping("/delete") public void delete(){ System.out.println("delete 호출됨"); } @RequestMapping("/update") public void update(){ System.out.println("update 호출됨"); } @RequestMapping("/select") public void select1(){ System.out.println("select 호출됨"); } }
➡️ 이제 여기서 중요한 건 메서드의 이름이 아니라 어노테이션의 value 값!
package ex03; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; public class App { public static void main(String[] args) { // 1. 키보드 입력 자리 String uri = "/select"; // 2. 다름 사람이 만든 코드 BoardController con = new BoardController(); // 2-1. 동적 클래스 분석 Method[] methods = BoardController.class.getDeclaredMethods(); for (Method m : methods) { RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class); if (rm.value().equals(uri)) { try { m.invoke(con); } catch (IllegalAccessException e) { throw new RuntimeException(e); } catch (InvocationTargetException e) { throw new RuntimeException(e); } } } } }

6-1) 결과

notion image

7) 키보드 입력 받기

package ex03; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.util.Scanner; public class App { public static void main(String[] args) { // 1. 키보드 입력 자리 Scanner sc = new Scanner(System.in); String uri = sc.nextLine(); // 2. 다름 사람이 만든 코드 BoardController con = new BoardController(); // 2-1. 동적 클래스 분석 Method[] methods = BoardController.class.getDeclaredMethods(); for (Method m : methods) { RequestMapping rm = m.getDeclaredAnnotation(RequestMapping.class); if (rm.value().equals(uri)) { try { m.invoke(con); } catch (IllegalAccessException e) { throw new RuntimeException(e); } catch (InvocationTargetException e) { throw new RuntimeException(e); } } } } }
➡️ 이제부터 App클래스는 손 댈 수 없음!!

7-1) 결과

notion image

8) 필기

notion image
Share article