Search code examples
spring-bootjdbctemplateaudit-trail

Simple Http request logging to DB


Is there a way to log http requests to a database without using the spring actuator? My program is a spring application that uses JDBCtemplate for writing to the database. I keep seeing solutions that write to the console log but I need something that I can store in a persistent database to act as an audit trail of sorts.


Solution

  • Assuming you have already set up the database and created a table for the audit trail, you could extend the DispatcherServlet class to intercept a request and write the information to the created table.

    @Configuration
    public class LoggableDispatcherServlet extends DispatcherServlet {
    
        @Autowired
        JdbcTemplate jdbcTemplate;
    
        @Override
        protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
            try {
                super.doDispatch(request, response);
            } finally {
                log(request, response);
            }
        }
    
        private void log(HttpServletRequest request, HttpServletResponse response) {
            String timeStamp = new SimpleDateFormat("MM/dd/yyyy HH:mm:ss").format(new Date());
    
            AuditUser auditUser = new AuditUser();
            auditUser.setUsername(request.getUserPrincipal().getName());
            auditUser.setTimestamp(timeStamp);
            auditUser.setResponseCode(response.getStatus());
            auditUser.setRequestUrl(request.getRequestURI());
            auditUser.setRequestMethod(request.getMethod());
    
            jdbcTemplate.update("INSERT INTO AuditUsers (username, requestTimestamp, responseCode, requestUrl, requestMethod) VALUES " +
                    " (?, ?, ?, ?, ?)", auditUser.getUsername(), auditUser.getTimestamp(), auditUser.getResponseCode(),
                    auditUser.getRequestUrl(), auditUser.getRequestMethod());
        }
    }
    

    You can replace the AuditUser declaration with your entity class for storing the information you need. For me, I wanted to store the principal (as my application uses spring security), the time of the request, the response code, request URL, and request method. Of course you can choose what you want to include/exclude by editing the log (HttpServletRequest request, HttpServletResponse response) method. Also, make sure to edit the the query to match the table and columns you created. Hope this helps!