How to write tag in my spring project?

可紊 提交于 2019-11-29 02:18:10

JSP tag objects are not managed by Spring, they are managed by the servlet container. As a result, you cannot autowire stuff into your tags.

If you need to get hold of beans from the spring appcontext, then your Spring MVC controller needs to set the bean as a request attribute (using request.setAttribute()), so that the tag object can get hold of it.

Have a try by utilizing RequestContextAwareTag. It will offer you methods to obtain RequestContext and then WebApplicaitonContext. Have a look at here.

Annotate your Tag-Implementation with @Configurable and add <context:component-scan base-package="your.webapp"> to your Spring-Configuration.

Check out these spring packages in the spring reference docs and in the spring source:

  • org.springframework.web.servlet.tags
  • org.springframework.web.servlet.tags.form
  • If nothing else, those will show you how the spring developers wrote the spring tags.

    What you could do is create a static method like this:

    public static void autowireAllFor(Object target) {
        AutowiredAnnotationBeanPostProcessor bpp = new AutowiredAnnotationBeanPostProcessor();
        bpp.setBeanFactory(...yourBeanFactory...);
        bpp.processInjection(target);
    }
    

    and then for your tag you could do

    public class YourTag extends TagSupport {
    
       @Autowired
       private SomeBean someBean;
    
       public YourTag() {
          YourHelperClass.autowireAllFor(this);
       }
    }
    

    The obvious disadvantage of this approach is that you have to do this for every constructor, but as TagSupport only has one, it should not be a problem. You can go even one step further and create a helper superclass which always guarantees autowiring:

    public class SpringTagSupport extends TagSupport {
       public SpringTagSupport() {
          super();
          YourHelperClass.autowireAllFor(this);
       }
    }
    

    The rest is as easy as extending your classes from SpringTagSupport.

    First I write this:

    public abstract class SpringSuportedTag  extends SimpleTagSupport{
    
    protected WebApplicationContext _applicationContext;
    
    protected WebApplicationContext getSpringContext(){
        PageContext pageContext = (PageContext) getJspContext();
        if(_applicationContext==null){
            _applicationContext = RequestContextUtils.getWebApplicationContext(
                    pageContext.getRequest(),
                    pageContext.getServletContext()
                );
            initCustomBeans();
        }
        return _applicationContext;
    }
    
    protected abstract void initCustomBeans();
    
    /**
     * Deprecated for inserting extra logic. Use {@link #doTagWithSpring()} instead.
     */
    @Override
    @Deprecated
    public void doTag() throws JspException, IOException {
        getSpringContext();
        doTagWithSpring();
    }
    
    
    abstract void doTagWithSpring() throws JspException, IOException;
    }
    

    And usage:

    public class SlotTag extends SpringSuportedTag {
    
    //  @Resource(name="userDetailHolder")
    //  not work here
    UserDetailHolder userDetail;
    
    private String slotname;
    
    public String getSlotname() {
        return slotname;
    }
    
    public void setSlotname(String slotname) {
        this.slotname = slotname;
    }
    
    @Override
    void doTagWithSpring() throws JspException, IOException {
        PageContext pageContext = (PageContext) getJspContext();
        String userDetailCode = pageContext.getAttribute(InitWidgetUserTag.KAY_USERDETAIL,  PageContext.PAGE_SCOPE).toString();
        userDetail.init(userDetailCode);
        String pageID = pageContext.getAttribute(InitWidgetUserTag.KAY_PAGEID,  PageContext.PAGE_SCOPE).toString();
    
        getJspContext().getOut().println("<b>slot for user:"+userDetail.getUserId()+"</b>");
    }
    
    @Override
    protected void initCustomBeans() {
        userDetail = (UserDetailHolder) getSpringContext().getBean("userDetailHolder");
    
    }
    }
    

    It's work. But than i found this: Spring supported Tag Libraries. Truth in my progect I still use own solution.

    Nitesh Tripathi

    Use :-

    import org.springframework.web.servlet.tags.RequestContextAwareTag;
    
    public class FetchTagNameTag extends RequestContextAwareTag {
    
    //   @Autowired
    
      // private TaskService taskService;
    
       @Override
    
        protected int doStartTagInternal() throws Exception {
    
    TaskService taskService=  getRequestContext().getWebApplicationContext().getBean(TaskService.class);
    
    
        return 0;
       }
    
    易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
    该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!