001package io.jstach.opt.spring.webmvc; 002 003import java.util.ArrayList; 004import java.util.List; 005 006import org.eclipse.jdt.annotation.Nullable; 007import org.springframework.context.ApplicationContext; 008import org.springframework.web.servlet.HandlerInterceptor; 009import org.springframework.web.servlet.ModelAndView; 010import org.springframework.web.servlet.config.annotation.InterceptorRegistry; 011import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; 012 013import jakarta.servlet.http.HttpServletRequest; 014import jakarta.servlet.http.HttpServletResponse; 015 016/** 017 * A {@link HandlerInterceptor} that automatically applies all 018 * {@link JStachioModelViewConfigurer} instances to views before rendering. Also 019 * implements {@link WebMvcConfigurer} so that it registers itself when the servlet 020 * context starts. 021 * 022 * @author dsyer 023 */ 024@SuppressWarnings("exports") 025public class ViewSetupHandlerInterceptor implements HandlerInterceptor, WebMvcConfigurer { 026 027 private final List<JStachioModelViewConfigurer> configurers = new ArrayList<>(); 028 029 private final ApplicationContext context; 030 031 /** 032 * Injected context will be searched for {@link JStachioModelViewConfigurer} 033 * @param context autowired. 034 */ 035 public ViewSetupHandlerInterceptor(ApplicationContext context) { 036 for (String name : context.getBeanNamesForType(JStachioModelViewConfigurer.class)) { 037 this.configurers.add((JStachioModelViewConfigurer) context.getBean(name)); 038 } 039 this.context = context; 040 } 041 042 /** 043 * {@inheritDoc} If the modelAndView is a {@link JStachioModelView} then it will be 044 * configured with all of the found {@link JStachioModelViewConfigurer} in the 045 * application context. 046 */ 047 @Override 048 public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, 049 ModelAndView modelAndView) throws Exception { 050 @Nullable 051 JStachioModelView view = findView(modelAndView); 052 if (view != null) { 053 Object page = view.model(); 054 for (JStachioModelViewConfigurer configurer : configurers) { 055 configurer.configure(page, modelAndView.getModel(), request); 056 } 057 } 058 } 059 060 private @Nullable JStachioModelView findView(ModelAndView modelAndView) { 061 if (modelAndView != null) { 062 if (modelAndView.getView() instanceof JStachioModelView) { 063 return (JStachioModelView) modelAndView.getView(); 064 } 065 if (this.context.getBean(modelAndView.getViewName()) instanceof JStachioModelView view) { 066 return view; 067 } 068 } 069 return null; 070 } 071 072 @Override 073 public void addInterceptors(InterceptorRegistry registry) { 074 registry.addInterceptor(this); 075 } 076 077}