2008-10-24 33 views
7

मैं आज फ्रीमार्कर से टाइल 2 + फ्रीमार्कर में माइग्रेट करने की कोशिश कर रहा था।स्प्रिंग + टाइल्स 2 + फ्रीमार्कर - फ्रीमार्कर सर्वलेट के माध्यम से या स्प्रिंग के फ्रीमार्कर व्यू रिसेल्वर के माध्यम से एकीकृत करें?

मेरे फ्रीमार्कर टेम्पलेट्स वसंत.एफटीएल से आने वाले मैक्रोज़ का उपयोग करते हैं।

यदि मैं web.xml में एक फ्रीमार्कर सर्वलेट प्रदान करता हूं, तो मेरा मॉडल फ्रीमार्कर के लिए दृश्यमान है, लेकिन विशिष्ट वसंत चर (स्वाभाविक रूप से) मॉडल में पॉप्युलेट नहीं होते हैं क्योंकि स्प्रिंग्स फ्रीमार्कर व्यू इसके लिए ज़िम्मेदार है।

अगर मैं विशिष्ट यूआरएल के लिए एक अलग DispatcherServlet कॉन्फ़िगर (जैसे कि "/ TPL/*") और कहा कि सर्वलेट के लिए डिफ़ॉल्ट दृश्य रिसोल्वर के रूप में freemarker समाधानकर्ता कॉन्फ़िगर और डिफ़ॉल्ट नियंत्रक के रूप में UrlFilenameViewController प्रदान करते हैं विशेष वसंत चर, मॉडल के लिए आबादी वाले मिलता है लेकिन मेरा अपना मॉडल दृश्यमान नहीं है: यह अनुरोध विशेषता के रूप में बाध्य है। मैं $ {request.mymodel.myvar} के माध्यम से अपने मॉडल तक पहुंच सकता हूं लेकिन इस तरह मुझे अपने सभी फ्रीमार्कर टेम्पलेट्स को बदलना है और मुझे इस विचार में कुछ सुगंधित दिख रहा है।

अब मेरी समाधान UrlFilenameViewController का विस्तार करने और ModelAndView करने के लिए अनुरोध से अपने मॉडल को जोड़ने के लिए किया गया था:

protected ModelAndView handleRequestInternal(HttpServletRequest request, HttpServletResponse response) { 
     ModelAndView mav = super.handleRequestInternal(request, response); 

     HashMap<String, Object> map = new HashMap<String, Object>(); 

     Enumeration<String> attributes = request.getAttributeNames(); 

     while(attributes.hasMoreElements()) { 
      String attribute = attributes.nextElement(); 

      if("model".equals(attribute)) { 
       logger.debug("FreemarkerViewController.handleRequestInternal: putting attribute to model: " + attribute + "=" + request.getAttribute(attribute)); 
       map.put(attribute, request.getAttribute(attribute)); 
      } 
     } 
     logger.debug("FreemarkerViewController.handleRequestInternal: VIEW: " + mav.getViewName()); 
     return new ModelAndView(mav.getViewName(), map); 
    } 

लेकिन इस समाधान भी कुछ हद तक बदबूदार है - अगर मैं अपने व्यवसाय के नियंत्रकों में मॉडल में कुछ जोड़ने, मैं करने के लिए है इसे यहाँ जोड़ें।

क्या मेरी समस्या के लिए कोई सुरुचिपूर्ण समाधान है?

+0

क्या आपको कभी इसके लिए बेहतर समाधान मिला है? –

+0

मैं फ्रीमार्कर सर्वलेट और वसंत टैगलिब्स का उपयोग कर रहा हूं - वे विशेष वसंत फ्रीमार्कर मैक्रोज़ के माध्यम से उपयोग किए जा रहे सब कुछ का ख्याल रखते हैं। – miceuz

+0

http://stackoverflow.com/questions/221178/can-anyone-point-me-to-spring-mvc-tiles-freemarker-integration-example से संबंधित – Nick

उत्तर

1

मुझे याद है कि मैंने दो परियोजनाओं में एक ही समस्या हल की है। आपका दूसरा दृष्टिकोण लगभग सही है (FreeMarkerViewResolver), लेकिन अगर मुझे सही याद है तो मुझे दोनों मॉडलों को स्पष्ट रूप से पुल करने के लिए FreeMarkerView और TilesView से भी विस्तार करना पड़ा।

कस्टम टाइलें दृश्य:

public class CustomTilesView extends TilesView { 

    @Override 
    protected void exposeModelAsRequestAttributes(Map model, HttpServletRequest request) { 
     request.setAttribute(CustomFreeMarkerView.MODEL_KEY, model); 
    } 
} 

कस्टम FreeMarker दृश्य:

public class CustomFreeMarkerView extends FreeMarkerView { 

    public static final String MODEL_KEY = FreeMarkerView.class.getName() + ".MODEL"; 

    @Override 
    protected void exposeHelpers(Map model, HttpServletRequest request) throws Exception { 
     super.exposeHelpers(model, request); 
     final Map savedModel = (Map) request.getAttribute(MODEL_KEY); 
     if (savedModel != null) { 
      mergeModels(model, savedModel); 
     } 
    } 

    private void mergeModels(Map<String, Object> targetModel, Map<String, Object> recipientModel) throws ServletException { 
     for (Map.Entry<String, Object> entry : recipientModel.entrySet()) { 
      String key = entry.getKey(); 
      if (targetModel.containsKey(key)) { 
       throw new ServletException("Cannot merge models because of an existing model object of the same name: " + key); 
      } 
      targetModel.put(key, entry.getValue()); 
     } 
    } 
} 

रजिस्टर वसंत में दोनों:

<bean class="org.springframework.web.servlet.view.UrlBasedViewResolver" 
     p:viewClass="com.my.CustomTilesView" 
     p:contentType="text/html;charset=UTF-8"/> 

<bean class="org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver" 
     p:suffix=".ftl" 
     p:exposeSpringMacroHelpers="true" 
     p:viewClass="com.my.CustomFreeMarkerView" 
     p:contentType="text/html;charset=UTF-8"/> 

काम करना चाहिए।