简体   繁体   中英

How do I override a parent class method to perform some work at the beginning and the end of the method?

I have extended the javax.http.servlet.HttpServlet class to add some methods to the class for my use. All of my servlets for my app will extend this new class. A bare bones version of this class is as follows:

public class MyCustomServletClass extends HttpServlet{

    protected void startWork(){
        // do some stuff
    }

    protected void finishWork(){
        // do more stuff
    }

}

These two methods are to be executed at the beginning/end of every HttpServlet request method (eg doGet, doPost, etc). Here is a simple example of a servlet that I could create using my custom MyCustomServletClass:

public class SomeServlet extends MyCustomServletClass{

    protected void doGet(HttpServletRequest request, HttpServletResponse response){
        this.startWork();

        // some servlet specific work here

        this.finishWork();
    }

}

So my question is this : is there some way in Java to make the doGet method automatically run these two methods at the beginning/end of the method ?

I'm trying to find a good way to not have to manually call startWork() and endWork() in every doGet, doPost, etc in every single servlet that I have. I'd like to just be able to extend MyCustomServletClass, implement doGet, and have startWork() be called at the start behind the scenes and endWork() be called at the end behind the scenes.

Ideally, in my servlets which extend MyCustomServletClass, a doGet method would simply be:

protected void doGet(HttpServletRequest request, HttpServletResponse response){
    // doGet specific work here
}

without the need to manually call my two parent methods every time.

I could do startWork() in the constructor I suppose, but I don't think I really have enough control over the servlet's lifespan to do endWork() in the destructor.

Is there a way to make these two methods executed at the start/end of doGet automatically and behind the scenes?

You could use a template method to automatically call your methods and delegate the implementation to another overridable method:

public class MyCustomServletClass extends HttpServlet {
    @Override
    protected final void doGet(HttpServletRequest request, HttpServletResponse response) {
        startWork();
        get();
        endWork();
    }

    protected void get(HttpServletRequest request, HttpServletResponse response) {
        // default implementation, should be overridden
        super.doGet(request, response);
    }
}

Note that doGet() is declared final to prevent an implementer from erroneously overriding it.

Another option might be injecting your methods with AOP .

This is the kind of thing that servlet filters were designed to address:

@WebFilter(servletNames={ "MyCustomServlet", ... })
public class WorkWrapperFilter implements Filter {

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
    }

    @Override
    public void destroy() {
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        try {
            startWork();
            chain.doFilter(request, response);
        } finally {
            finishWork();
        }
    }

    private void startWork(){
        // do some stuff
    }

    private void finishWork(){
        // do more stuff
    }

}

This allows you to perform operations that are orthogonal to your servlet function in a way that is completely decoupled from it.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM