묻고 답해요
141만명의 커뮤니티!! 함께 토론해봐요.
인프런 TOP Writers
-
미해결스프링 MVC 2편 - 백엔드 웹 개발 활용 기술
국제화 기본 설정 테스트 코드 실패
=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? 예2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? 3. 질문 잘하기 메뉴얼을 읽어보셨나요? 예[질문 내용]스프링 메시지 소스 사용 강의 2분 50초 정도에 나오는 테스트 코드가 계속 실패해서 문의 드립니다.계속 hello 값을 가져오는것 같은데, 설정 값은강의에서 제시한 그대로 인데, 기본 디폴트 값이 영어로 되어 있는걸까요? 혹시나 해서 Local.KOREA(N)을 모두 적용해보았으나 역시 같은 에러가 발생합니다.코드 내용은 위와 같습니다. 원인이 뭘까요? ㅠㅠ
-
미해결스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
MVC 프레임워크 만들기-유연한 컨트롤러1 - v5 질문있습니다.
MVC 프레임워크 만들기-유연한 컨트롤러1 - v5 28분49초 위 사진처럼 get뒤에 url주소가 어떻게 호출되는건가요? put주소를 틀린거를 줬는데요.
-
미해결스프링 핵심 원리 - 기본편
TestBean 질문
학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.1. 강의 내용과 관련된 질문을 남겨주세요.2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.(자주 하는 질문 링크: https://bit.ly/3fX6ygx)3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)[질문 내용]ApplicationContext ac = new AnnotationConfigApplicationContext(TestBean.class); 이 부분에서 TestBean.class이 클래스에는 @Configuration, @Bean도 없음으로 설정정보로 쓰이는게 아니라 그냥 단순히 빈으로만 등록된다는건가요?
-
해결됨스프링 시큐리티 완전 정복 [6.x 개정판]
http 파일이 잘 안 먹힐 때
### 로그인 POST http://localhost:8080/login Content-Type: application/json { "username": "user", "password": "1111" } > {% client.global.set("JSESSIONID", response.headers.valueOf("Set-Cookie").split(";")[0].split("=")[1]) %} ### 루트 접속 GET http://localhost:8080/ Accept: application/json Cookie: JSESSIONID={{JSESSIONID}}강의에서 설명하신 대로 따라해봤는데 http 파일이 잘 작동하지 않는 문제가 있었습니다.이 부분이 잘 안 먹혀서 찾아봤는데 인프런 현재 CTO이신 '향로'님 블로그쪽에 이 내용이 정리가 되어 있는 것을 확인할 수 있었습니다.- https://jojoldu.tistory.com/366> {% %} 를 http 파일에 작성하고, 이 사이에서 응답이 온 데이터를 전역변수로 저장해둘 수 있습니다.이후 로그인할 때 Cookie: JSESSIONID={{JSESSIONID}} 와 같이 전역변수에서 꺼내서 사용하면 명시적으로 쿠키를 지정해서 전달할 수 있어서 작동이 잘 됩니다.
-
미해결스프링 핵심 원리 - 고급편
포인트컷 지시자와 매개변수 전달
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오) 네2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오) 네3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오) 네[질문 내용]매개변수 관련된 부분 학습 중에 헷갈리는 내용이 있어서 질문 드립니다.예를 들어 @annotation은 특정 어노테이션 기반으로 aop 프록시 대상을 정하는 것으로 배웠고, 다음과 같이 사용했습니다. @Around("@annotation(hello.aop.member.annotation.MethodAop)") public Object doAtAnnotation(ProceedingJoinPoint joinPoint) throws Throwable { log.info("[@annotation] {}", joinPoint.getSignature()); return joinPoint.proceed(); }그런데 매개변수 전달에서 @annotation은 특정 annotation을 전달하는 것으로도 보이는데요, @Before("allMember() && @annotation(annotation)") public void atAnnotation(JoinPoint joinPoint, MethodAop annotation) { log.info("[@annotation]{}, annotationValue={}", joinPoint.getSignature(), annotation.value()); }그렇다면 두 번째 경우에, aop 프록시 대상에 @MethodAop를 갖고 있는 대상에 대해서 적용이 되는 걸까요? 해당 어노테이션만 전달하는 건지, 해당 어노테이션을 갖고 있는 경우에 적용하는 기능까지 포함된 건지 (이 경우엔 생략된걸까요?) 궁금합니다
-
해결됨스프링 MVC 2편 - 백엔드 웹 개발 활용 기술
<label > id와 <input> id 맞추기
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예)[질문 내용]안녕하세요 강사님강의 10분 ~ 12분 사이에서 <label>태그와 <input> 태그의 id를 맞추기 위해서th:for="${#ids.prev('regions')}"를 사용한다고 하셨는데th: each 에서 제공하는 두 번째 파라미터를 활용해서 regionStat.index나 regionStat.Count로 id를 맞추는 방식은 어떨까요?
-
미해결스프링 핵심 원리 - 고급편
포인트컷 지정, 매개변수 전달
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오) 예2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오) 예3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오) 예[질문 내용]안녕하세요 포인트컷 지시자에서 표현식 중 매개변수 전달에 대해서 헷갈리는 부분이 있어서 질문 남깁니다.예를 들어 @annotation 지시자의 경우에는 해당 annotation이 있는 경우에 aop 적용 대상으로 인식하는 것으로 배웠는데요, @Around("@annotation(hello.aop.member.annotation.MethodAop)") public Object doAtAnnotation(ProceedingJoinPoint joinPoint) throws Throwable { log.info("[@annotation] {}", joinPoint.getSignature()); return joinPoint.proceed(); }@annotation을 매개변수 전달로도 사용할 수 있다고 강의에서 배웠습니다.
-
미해결실전! 스프링 부트와 JPA 활용2 - API 개발과 성능 최적화
fetch join 4개만 나오는건 알겠는데 json에서는 다른이유
학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.1. 강의 내용과 관련된 질문을 남겨주세요.2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.(자주 하는 질문 링크: https://bit.ly/3fX6ygx)3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)[질문 내용]join을 하면4개가 나오는데id가 같지만 orderItems는 서로 다르게 나옵니다. 근데 왜 json에서는 orderItems 중복되서 왜 똑같이 나오는건가요? 그리고 값이 왜 orderItems는 여러개씩 출력이 되는거죠? 사실상 sql시 하나씩 setter로 들어가서 출력되지않나요? 예) "orderItems": [ { "itemName": "JPA1 BOOK", "orderPrice": 10000, "count": 1 }, { "itemName": "JPA2 BOOK", "orderPrice": 20000, "count": 2 } ] 위와 같이 orderItems가 두개가 나옵니다.근데 sql은 하나씩 출력이 되는데 그러면 "orderItems": [ { "itemName": "JPA1 BOOK", "orderPrice": 10000, "count": 1 } ]위와 같이 하나만 출력이 되어야하는거 아닌가요?setter로 매핑 되면 그렇지않나요?
-
해결됨스프링 부트 - 핵심 원리와 활용
default 와 JDK 21
[질문 내용]김영한님의 코드를 받았을 때, Gradle JVM = azul-15 로 되어 있었는데, 제가 JDK 21 버전으로 바꾸었고, 추후에 "자식 컨테이너를 시작하는 중 오류 발생" 하는 문제가 생겼습니다.Run에서 JRE 를 default 에서 JDK21로 바꾸니 문제는 해결되었는데, 추후에 문제는 없을지 궁금하여 질문 남깁니다!!
-
해결됨스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
브라우저에서 url로 접근할때
브라우저에서 url로 접근할때는 메소드 속성이 무조건 GET인가요?
-
미해결스프링 핵심 원리 - 기본편
CoreApplication 오류
학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.1. 강의 내용과 관련된 질문을 남겨주세요.2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.(자주 하는 질문 링크: https://bit.ly/3fX6ygx)3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)[질문 내용] overriding= true 까지 변경했음에도 불구하고 강의에서는 CoreApplication.java가 잘 실행되는데 저는 오류가 뜹니다. 찾아본 결과로는 @SpringBootApplication은 @Configuration, @ComponentScan, @EnableAutoConfiguration을 포함하는 메타 애노테이션입니다. 이렇게 포함되어 있기 때문에 @SpringBootApplication이 있는 클래스를 기준으로 스프링 부트 애플리케이션은 해당 패키지부터 모든 빈을 스캔하게 됩니다.따라서 AutoAppConfig에서의 excludeFilters 설정은 적용되지 않습니다. 스프링 부트가 이미 해당 패키지부터 모든 빈을 스캔하고 있기 때문에 AutoAppConfig에서 추가적인 스캔 설정을 하더라도 무시됩니다.이러한 이유로 AutoAppConfig에서의 excludeFilters 설정은 실행되지 않습니다.Q1. 이러한 이유로 안된다고 하는데 강의에서는 되는 이유는 버전차이인건가요?? Q2.AutoAppConfiguration, AppConfiguration,CoreApplication 이 모두 같은 패키지 안에 같은 계층에 존재하고 CoreApplication 얘가 이미 모든 빈을 스캔해서 exclude설정은 무시된다는 거로 이해했습니다만 맞나요?
-
해결됨스프링 MVC 2편 - 백엔드 웹 개발 활용 기술
ModelAttribute
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예)[질문 내용]ModelAttribute로 regions,itemTypes,deliveryCodes를 FormItemController가 처리가는 모든 view에 넘겨줬습니다. 그러면, item도 거의 모든 함수에서 사용되니까, item도 Modelattribute의 이런 사용법을 사용해도 되나요? 안된다면 왜 그런가요?
-
해결됨스프링 부트 - 핵심 원리와 활용
config 우선순위
[질문 내용]@Import(MyDataSourceConfigV3.class) @SpringBootApplication(scanBasePackages = {"hello.datasource","hello.pay"})이렇게 두개의 config를 적용할때스프링 부트가 MyDataSourceConfig와 PayConfig를읽는 순서를 정확히 알고 싶습니다 !
-
미해결스프링 핵심 원리 - 고급편
Gradle과 Intellij IDEA의 실행 결과 차이가 발생합니다.
[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예)[질문 내용]Intellij IDEA를 실행했을때 whitelabel error가 뜨고 Gradle로 실행했을때는 정상적으로 작동이 되는지 잘 모르겠습니다.<Gradle로 실행했을 때><Intellij IDEA로 실행했을 때>2024-04-24T10:14:45.934+09:00 ERROR 11612 --- [advanced] [nio-8080-exec-1] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed: java.lang.IllegalArgumentException: Name for argument of type [java.lang.String] not specified, and parameter name information not available via reflection. Ensure that the compiler uses the '-parameters' flag.] with root causejava.lang.IllegalArgumentException: Name for argument of type [java.lang.String] not specified, and parameter name information not available via reflection. Ensure that the compiler uses the '-parameters' flag. at org.springframework.web.method.annotation.AbstractNamedValueMethodArgumentResolver.updateNamedValueInfo(AbstractNamedValueMethodArgumentResolver.java:187) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.method.annotation.AbstractNamedValueMethodArgumentResolver.getNamedValueInfo(AbstractNamedValueMethodArgumentResolver.java:162) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.method.annotation.AbstractNamedValueMethodArgumentResolver.resolveArgument(AbstractNamedValueMethodArgumentResolver.java:108) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.method.support.HandlerMethodArgumentResolverComposite.resolveArgument(HandlerMethodArgumentResolverComposite.java:122) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.method.support.InvocableHandlerMethod.getMethodArgumentValues(InvocableHandlerMethod.java:224) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:178) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:118) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:926) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:831) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:87) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:1089) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:979) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:1014) ~[spring-webmvc-6.1.6.jar:6.1.6] at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:903) ~[spring-webmvc-6.1.6.jar:6.1.6] at jakarta.servlet.http.HttpServlet.service(HttpServlet.java:564) ~[tomcat-embed-core-10.1.20.jar:6.0] at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:885) ~[spring-webmvc-6.1.6.jar:6.1.6] at jakarta.servlet.http.HttpServlet.service(HttpServlet.java:658) ~[tomcat-embed-core-10.1.20.jar:6.0] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:206) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:150) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51) ~[tomcat-embed-websocket-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:175) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:150) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:100) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.1.6.jar:6.1.6] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:175) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:150) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.springframework.web.filter.FormContentFilter.doFilterInternal(FormContentFilter.java:93) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.1.6.jar:6.1.6] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:175) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:150) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:201) ~[spring-web-6.1.6.jar:6.1.6] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.1.6.jar:6.1.6] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:175) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:150) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:167) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:90) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:482) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:115) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:93) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:74) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:344) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:391) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:63) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:896) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1736) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:52) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.util.threads.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1191) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.util.threads.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:659) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:63) ~[tomcat-embed-core-10.1.20.jar:10.1.20] at java.base/java.lang.Thread.run(Thread.java:833) ~[na:na] Chat GPT로 물어봤는데 이해가 되지 않아서 질문 남깁니다. 두 방식으로 돌렸을 때 왜 이런 차이가 발생하는 건가요??
-
미해결스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
인텔리제이 디버그 질문입니다.
디버그가 왜 안되나요? 바로 톰캣 실행되는데요. 예를들어 디버그 모드면 watch부분이랑 뷰네임이 뭐가 들어가는지 보여야 하는거 아닌가요? 해당 코드는 view모델3부분입니다. 추가질문입니다. 제가 아래 2번째 사진(빨간색 박스)를 클릭했을 때 디버깅이 시작됩니다. (그전까지는 안되요.) 보통 파이참같은 경우 코드에서 중단점 설정 후 디버그를 누르면 바로 디버깅 모드 전환이 되는데요. 인텔리제이는 코드 중단점을 설정해놓아도 톰캣 스타트 시켜놓고(첫번째사진처럼) html에서 화면을 클릭해야 해당 디버깅이 들어가지나요?
-
미해결스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
Model 추가 - v3 질문입니다.
Model 추가 - v3 23분 질문입니다.FrontControllerServletV3 코드입니다.package com.example.servservlet.web.frontcontroller.v3;import com.example.servservlet.web.frontcontroller.MyView;import com.example.servservlet.web.frontcontroller.v3.ControllerV3;import com.example.servservlet.web.frontcontroller.ModelView;import com.example.servservlet.web.frontcontroller.v3.controller.MemberFormControllerV3;import com.example.servservlet.web.frontcontroller.v3.controller.MemberListControllerV3;import com.example.servservlet.web.frontcontroller.v3.controller.MemberSaveControllerV3;import jakarta.servlet.ServletException;import jakarta.servlet.annotation.WebServlet;import jakarta.servlet.http.*;import java.io.IOException;import com.example.servservlet.domain.member.Member;import com.example.servservlet.domain.member.MemberRepository;import com.example.servservlet.web.frontcontroller.v1.ControllerV1;import jakarta.servlet.RequestDispatcher;import jakarta.servlet.ServletException;import jakarta.servlet.http.HttpServletRequest;import jakarta.servlet.http.HttpServletResponse;import java.io.IOException;import java.util.List;import java.io.IOException;import java.util.HashMap;import java.util.Map;@WebServlet(name = "frontControllerServletV3", urlPatterns = "/front-controller/v3/*")public class FrontControllerServletV3 extends HttpServlet { private Map<String, ControllerV3> controllerMap = new HashMap<>(); public FrontControllerServletV3() { controllerMap.put("/front-controller/v3/members/new-form", new MemberFormControllerV3()); controllerMap.put("/front-controller/v3/members/save", new MemberSaveControllerV3()); controllerMap.put("/front-controller/v3/members", new MemberListControllerV3()); } @Override protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { String requestURI = request.getRequestURI(); ControllerV3 controller = controllerMap.get(requestURI); if (controller == null) { response.setStatus(HttpServletResponse.SC_NOT_FOUND); return; } //MemberFormControllerV3,MemberSaveControllerV3 내용을 paramMap에 저장한다. Map<String, String> paramMap = createParamMap(request); ModelView mv = controller.process(paramMap); //질문1. 자식 controller를 부모 ModelView에 저장하는 다형성을 뜻하는건가요?ModelView에 .process함수가 없는데 왜 저장하는거에요? //질문2. 아래부분에서 for문(반복문)이 없고 한개의 뷰네임을 저장하면 나머지 2개의 뷰 처리는 어떻게 하는건가요? //아니면 원래 반복문은 없고 요청이 있는 get(requestURI)만 viewName에 저장하는건가요? // 예를들어 /front-controller/v3/members/save 이면 viewName에 MemberSaveControllerV3()이부분을 저장하는게 맞나요? String viewName = mv.getViewName();//MemberFormControllerV3,MemberSaveControllerV3 내용 중 한개의 뷰네임을 저장한다. MyView view = viewResolver(viewName);//물리적 주소 저장 view.render(mv.getModel(), request, response); } private MyView viewResolver(String viewName) { return new MyView("/WEB-INF/views/" + viewName + ".jsp"); } private Map<String, String> createParamMap(HttpServletRequest request) { Map<String, String> paramMap = new HashMap<>(); request.getParameterNames().asIterator() .forEachRemaining(paramName -> paramMap.put(paramName, request.getParameter(paramName))); return paramMap; //<-질문3. 이 부분이 강의에서 각각 파라미터 네임을 계속 꺼내서 저장한다고 하셨는데 반복을 의미하는건가요? }}
-
미해결스프링 시큐리티 완전 정복 [6.x 개정판]
405에러가 발생합니다. 이유를 잘 모르겠습니다.
1package com.attendance.scheduler.infra.config.security; import lombok.RequiredArgsConstructor; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.security.web.SecurityFilterChain; @Configuration @RequiredArgsConstructor @EnableWebSecurity public class SecurityConfig { public static final String[] ENDPOINTS_WHITELIST = { "/", "/submit", "/completion", "/class/**", "/board/**", "/join/**", "/cert/**", "/help/**", "/comment/**", "/css/**", "/js/**" }; private final CustomAuthenticationFailureHandler customAuthenticationFailureHandler; @Bean public PasswordEncoder passwordEncoder() { return new BCryptPasswordEncoder(); } @Bean public SecurityFilterChain adminFilterChain(HttpSecurity httpSecurity) throws Exception { httpSecurity .csrf(AbstractHttpConfigurer::disable) .securityMatcher("/admin/**","/manage/**") .authorizeHttpRequests(auth -> auth .requestMatchers("/admin/**") .hasAuthority("ADMIN") .requestMatchers("/manage/**") .hasAnyAuthority("ADMIN", "TEACHER") .anyRequest().authenticated()) .formLogin(httpSecurityFormLoginConfigurer -> httpSecurityFormLoginConfigurer .defaultSuccessUrl("/manage/class", true) .failureHandler(customAuthenticationFailureHandler) .loginPage("/login") .loginProcessingUrl("/login") ) .logout(httpSecurityFormLogoutConfigurer -> httpSecurityFormLogoutConfigurer .logoutUrl("/logout") .invalidateHttpSession(true) .deleteCookies("JSESSIONID") .logoutSuccessUrl("/")) .sessionManagement(sessionManagement -> sessionManagement .invalidSessionUrl("/login") .maximumSessions(1) .maxSessionsPreventsLogin(true) .expiredUrl("/login")); return httpSecurity.build(); } } 2package com.attendance.scheduler.infra.config.security; import com.attendance.scheduler.admin.domain.AdminEntity; import com.attendance.scheduler.admin.repository.AdminJpaRepository; import com.attendance.scheduler.infra.config.security.Admin.AdminDetails; import com.attendance.scheduler.infra.config.security.User.TeacherDetails; import com.attendance.scheduler.teacher.domain.TeacherEntity; import com.attendance.scheduler.teacher.repository.TeacherJpaRepository; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springframework.security.core.userdetails.UserDetails; import org.springframework.security.core.userdetails.UserDetailsService; import org.springframework.security.core.userdetails.UsernameNotFoundException; import org.springframework.stereotype.Component; @Slf4j @Component @RequiredArgsConstructor public class AccountDetailService implements UserDetailsService { private final AdminJpaRepository adminJpaRepository; private final TeacherJpaRepository teacherJpaRepository; @Override public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { log.info("teacherId = {}", username); final TeacherEntity teacherEntity = teacherJpaRepository .findByUsernameIs(username); if(teacherEntity != null){ return new TeacherDetails(teacherEntity); } else { final AdminEntity adminEntity = adminJpaRepository .findByUsernameIs(username); if (adminEntity != null) { log.info("adminId = {}", username); return new AdminDetails(adminEntity); } } throw new UsernameNotFoundException(username); } }3<form method='post' th:action="@{/login}" th:object="${login}"> 로그인을 진행하면 405에러가 계속 발생합니다. 이유를 찾고 있으나 아이디와 비밀번호를 입력해도 2번 코드의 로그에 남지 않습니다. 혹시 이유를 알려주실수 있을까요? 감사합니다.
-
미해결스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술
findAll 테스트 전에는 오류 없었는데 findAll 테스트 했더니 findbyName에서 에러 났어요..
학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.1. 강의 내용과 관련된 질문을 남겨주세요.2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.(자주 하는 질문 링크: https://bit.ly/3fX6ygx)3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.=========================================[질문 템플릿]1. 강의 내용과 관련된 질문인가요? (예/아니오)2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)[질문 내용]여기에 질문 내용을 남겨주세요.전체 코드입니다.package com.example.hellospring.repository; import com.example.hellospring.domain.Member; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.Test; import java.util.List; import java.util.Optional; class MemoryMemberRepositoryTest { MemberRepository repository = new MemoryMemberRepository(); @Test public void save(){ Member member = new Member(); member.setName("spring"); repository.save(member); Member result = repository.findById(member.getId()).get(); // Assertions.assertEquals(member, result); Assertions.assertThat(member).isEqualTo(result); } @Test public void findByName(){ Member member1 = new Member(); member1.setName("spring1"); repository.save(member1); Member member2 = new Member(); member2.setName("spring2"); repository.save(member2); Member result = repository.findByName("spring1").get(); Assertions.assertThat(result).isEqualTo(member1); } @Test public void findAll(){ Member member1 = new Member(); member1.setName("spring1"); repository.save(member1); Member member2 = new Member(); member2.setName("spring2"); repository.save(member2); List<Member> result = repository.findAll(); Assertions.assertThat(result.size()).isEqualTo(2); } } 참고로 save 테스트에서 에러가 발생해서 findById 를 String -> Long 으로 바꾼 상태입니다.package com.example.hellospring.repository; import com.example.hellospring.domain.Member; import java.util.List; import java.util.Optional; public interface MemberRepository { Member save(Member member); Optional<Member> findById(Long id); Optional<Member> findByName(String name); List<Member> findAll(); } package com.example.hellospring.repository; import com.example.hellospring.domain.Member; import java.util.*; public class MemoryMemberRepository implements MemberRepository { private static Map<Long, Member> store = new HashMap<>(); private static long sequence = 0L; @Override public Member save(Member member) { member.setId(++sequence); store.put(member.getId(), member); return member; } @Override public Optional<Member> findById(Long id) { return Optional.ofNullable(store.get(id)); } @Override public Optional<Member> findByName(String name) { return store.values().stream() .filter(member -> member.getName().equals(name)) .findAny(); } @Override public List<Member> findAll() { return new ArrayList<>(store.values()); } }
-
미해결견고한 결제 시스템 구축
혹시.. 실습 코드 제공 받을때 코틀린이 아닌 자바 언어 받을수 있을까요?...
사실 코틀린은 제가 한번도 사용해 본적도 없고 이번에 프로젝트 구성할때 자바로 만들 계획이라서요. 그렇다고 선생님 실습 코드를 전부 그래도 사용하는것은 아닌데요. 강의 보면서 자바로 구성된 코드를 보면서 공부하면 이해하는데 도움이 많이 될것 같아서요... 부탁드립니다!!
-
해결됨스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술
"HttpServletRequest - 기본 사용법" 강의 내용 중 질문
처음 http://localhost:8080/request-header?username=hello 로 URL 입력 후 콘솔을 확인하면 아래와 같이 Header 편의 조회가 출력되었습니다.이후에 Postman을 통해서 다음과 같이 hello! 라는 메시지를 POST 방식으로 전송을 한 후 콘솔을 확인해 보니 아래와 같이 출력되었습니다.이때 Postman을 통해 보낸 방식에서 cookie가 조회되지 않는 이유는 Postman을 사용해서 POST 요청을 할 때 쿠키 설정을 따로 해주지 않아서 그런거고 크롬에서 URL을 검색해서 GET 방식으로 조회할 때는 크롬이 자동으로 쿠키를 할당해준건거요...??