ViewResolver
ViewResolver в Spring MVC преобразует логическое имя представления в объект View, который умеет сформировать HTTP-ответ.
Контроллер может вернуть имя шаблона и модель:
@Controller
class ProfileController {
@GetMapping("/profile")
String profile(Model model) {
model.addAttribute("name", "Alex");
return "profile";
}
}Здесь "profile" — не готовый HTML и не путь, который обязан существовать буквально. Зарегистрированные ViewResolver пытаются подобрать представление с таким логическим именем.
Место в обработке запроса
Упрощённая цепочка Spring MVC:
DispatcherServlet
→ HandlerMapping
→ controller
→ имя view + model
→ ViewResolver
→ View.render(...)
→ HTTP responseЕсли контроллер возвращает ModelAndView, результат тот же: модель и логическое имя передаются механизму представлений.
Пример с JSP
@Configuration
@EnableWebMvc
class WebConfig implements WebMvcConfigurer {
@Bean
ViewResolver jspViewResolver() {
var resolver = new InternalResourceViewResolver();
resolver.setPrefix("/WEB-INF/views/");
resolver.setSuffix(".jsp");
return resolver;
}
}Имя "profile" будет преобразовано в /WEB-INF/views/profile.jsp.
Для Thymeleaf или FreeMarker используются соответствующие интеграции и resolver-ы. В Spring Boot значительную часть конфигурации обычно создаёт автоконфигурация на основании зависимостей и настроек приложения.
Когда ViewResolver не участвует
Для REST-ответа представление обычно не требуется:
@RestController
class ProfileApi {
@GetMapping("/api/profile")
ProfileDto profile() {
return new ProfileDto("Alex");
}
}Здесь результат обрабатывает HttpMessageConverter: например, Jackson сериализует DTO в JSON. То же относится к методу с @ResponseBody.
Частые ошибки
- использовать
@RestController, а затем ожидать поиск HTML-шаблона; - возвращать имя с расширением или полным путём, хотя prefix и suffix уже настроены;
- путать перенаправление
redirect:/pathс рендерингом view; - держать JSP в каталоге, который не совпадает с настройкой resolver-а;
- считать
ViewResolverмеханизмом маршрутизации: URL сопоставляет с контроллеромHandlerMapping.
На собеседовании
Чем ViewResolver отличается от HttpMessageConverter?
ViewResolver выбирает представление для серверного рендеринга модели. HttpMessageConverter преобразует тело запроса или возвращаемый объект в формат вроде JSON, XML или текста.