AnnotationMethodHandlerAdapter.invokeHandlerMethod()
zajmuje się wywoływanie metod obsługi. W tym przypadku ModelAndView
zostanie pobrany przez ServletHandlerMethodInvoker.getModelAndView()
.
W twoim przypadku getModelAndView()
dostanie wartość zwracaną przez metodę modułu obsługi w postaci null
. Metoda getModelAndView()
sprawdza typ wartości zwracanej, ale as in Java null is never an instanceof any class, logika tej metody utworzy nowy ModelAndView
. Nowa właściwość widoku ModelAndView
ma ustawioną wartość null
.
Później z powrotem w górę stosu wywołań w DispatcherServlet.doDispatch()
, nie jest test, jeśli obiekt ModelAndView
ma View
z nim związane (mv.hasView()
). Ponieważ logika view == null
, doDispatch()
wywołuje mv.setViewName(getDefaultViewName(request))
. Przekazuje on zarejestrowanemu użytkownikowi RequestToViewNameTranslator
, którego domyślną implementacją jest DefaultRequestToViewNameTranslator
. Ta podklasa tłumaczy identyfikator URI żądania na nazwę widoku, w twoim przypadku form
.
Później doDispatch()
poprzez render()
->resolveViewName()
, ta próbka jest ViewResolver
s są dostarczane z nazwą widoku form
. W tej próbce jest używany tylko jeden obiekt ViewResolver
, . Ponadto ten InternalResourceViewResolver
został skonfigurowany w src/main/webapp/WEB-INF/spring/appServlet/servlet-context.xml
, aby dodać prefiks /WEB-INF/views/
i przyrostek .jsp
do nazwy widoku. W sumie utworzy on View
przy użyciu pliku JSP /WEB-INF/views/form.jsp
. Na szczęście plik JSP istnieje dokładnie w tej lokalizacji.
Czy fasola RequestToViewNameTranslator musi być jawnie dostarczona, czy też Spring dostarcza ją po wyjęciu z pudełka? – acvcu