001package io.jstach.opt.spring.webmvc; 002 003import java.util.Map; 004 005import org.springframework.web.servlet.View; 006import org.springframework.web.servlet.view.RedirectView; 007 008import io.jstach.jstache.JStache; 009import io.jstach.jstache.JStacheInterfaces; 010import io.jstach.jstachio.JStachio; 011import jakarta.servlet.http.HttpServletRequest; 012import jakarta.servlet.http.HttpServletResponse; 013 014/** 015 * Another way to use JStachio with Spring MVC is to have models implement Springs 016 * {@link View} interface. You can enforce that your models implement this interface with 017 * {@link JStacheInterfaces}. 018 * <p> 019 * The model will use the static jstachio singleton that will be the spring one. 020 * <p> 021 * This approach has pros and cons. It makes your models slightly coupled to Spring MVC 022 * but allows you to return different views if say you had to redirect on some inputs 023 * ({@link RedirectView}). 024 * 025 * @author agentgt 026 * 027 */ 028public interface JStachioModelView extends View { 029 030 @SuppressWarnings("exports") 031 @Override 032 default void render(Map<String, ?> model, HttpServletRequest request, HttpServletResponse response) 033 throws Exception { 034 035 String contentType = getContentType(); 036 if (contentType != null) { 037 response.setContentType(contentType); 038 } 039 try (var w = response.getWriter()) { 040 jstachio().execute(model(), w); 041 } 042 043 } 044 045 /** 046 * Returns the jstachio singleton by default. 047 * @return stachio singleton by default. 048 * @see JStachio#setStaticJStachio(java.util.function.Supplier) 049 */ 050 default JStachio jstachio() { 051 return JStachio.of(); 052 } 053 054 /** 055 * The model to be rendered by {@link #jstachio()}. 056 * @return model defaulting to <code>this</code> instance. 057 */ 058 default Object model() { 059 return this; 060 } 061 062 /** 063 * Creates a spring view from a model with content type: 064 * "<code>text/html; charset=utf-8</code>". 065 * @param model an instance of a class annotated with {@link JStache}. 066 * @return view ready for rendering 067 */ 068 public static JStachioModelView of(Object model) { 069 return of(model, "text/html; charset=utf-8"); 070 } 071 072 /** 073 * Creates a spring view from a model. 074 * @param model an instance of a class annotated with {@link JStache}. 075 * @param contentType See {@link #getContentType()} 076 * @return view ready for rendering 077 */ 078 public static JStachioModelView of(Object model, String contentType) { 079 return new JStachioModelView() { 080 @Override 081 public Object model() { 082 return model; 083 } 084 085 @Override 086 public String getContentType() { 087 return contentType; 088 } 089 }; 090 } 091 092}