org.nuxeo.ecm.platform.audit.service.LogEntryProvider.java Source code

Java tutorial

Introduction

Here is the source code for org.nuxeo.ecm.platform.audit.service.LogEntryProvider.java

Source

/*
 * (C) Copyright 2006-2008 Nuxeo SA (http://nuxeo.com/) and others.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 * Contributors:
 *     Stephane Lacoin (Nuxeo EP Software Engineer)
 */

package org.nuxeo.ecm.platform.audit.service;

import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import javax.persistence.EntityManager;
import javax.persistence.Query;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.nuxeo.ecm.platform.audit.api.FilterMapEntry;
import org.nuxeo.ecm.platform.audit.api.LogEntry;
import org.nuxeo.ecm.platform.audit.api.query.AuditQueryException;
import org.nuxeo.ecm.platform.audit.api.query.DateRangeParser;
import org.nuxeo.ecm.platform.audit.impl.LogEntryImpl;

public class LogEntryProvider implements BaseLogEntryProvider {

    private static final Log log = LogFactory.getLog(LogEntryProvider.class);

    protected final EntityManager em;

    private LogEntryProvider(EntityManager em) {
        this.em = em;
    }

    public static LogEntryProvider createProvider(EntityManager em) {
        return new LogEntryProvider(em);
    }

    protected void doPersist(LogEntry entry) {
        // Set the log date in java right before saving to the database. We
        // cannot set a static column definition to
        // "TIMESTAMP DEFAULT CURRENT_TIMESTAMP" as MS SQL Server does not
        // support the TIMESTAMP column type and generating a dynamic
        // persistence configuration that would depend on the database is too
        // complicated.
        entry.setLogDate(new Date());
        em.persist(entry);
    }

    protected List<?> doPublishIfEntries(List<?> entries) {
        if (entries == null || entries.size() == 0) {
            return entries;
        }
        Object entry = entries.get(0);
        if (entry instanceof LogEntry) {
            for (Object logEntry : entries) {
                doPublish((LogEntry) logEntry);
            }
        }
        return entries;
    }

    protected List<LogEntry> doPublish(List<LogEntry> entries) {
        for (LogEntry entry : entries) {
            doPublish(entry);
        }
        return entries;
    }

    protected LogEntry doPublish(LogEntry entry) {
        if (entry.getExtendedInfos() != null) {
            entry.getExtendedInfos().size(); // force lazy loading
        }
        return entry;
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#addLogEntry(org
     * .nuxeo.ecm.platform.audit.api.LogEntry)
     */
    @Override
    public void addLogEntry(LogEntry entry) {
        doPersist(entry);
    }

    public void addLogEntries(List<LogEntry> entries) {
        for (LogEntry entry : entries) {
            doPersist(entry);
        }
    }

    @SuppressWarnings("unchecked")
    @Override
    public List<LogEntry> getLogEntriesFor(String uuid, String repositoryId) {
        if (log.isDebugEnabled()) {
            log.debug("getLogEntriesFor() UUID=" + uuid + " and repositoryId=" + repositoryId);
        }
        Query query = em.createNamedQuery("LogEntry.findByDocumentAndRepository");
        query.setParameter("docUUID", uuid);
        query.setParameter("repositoryId", repositoryId);
        return doPublish(query.getResultList());
    }

    @SuppressWarnings("unchecked")
    @Override
    public List<LogEntry> getLogEntriesFor(String uuid) {
        if (log.isDebugEnabled()) {
            log.debug("getLogEntriesFor() UUID=" + uuid);
        }
        Query query = em.createNamedQuery("LogEntry.findByDocument");
        query.setParameter("docUUID", uuid);
        return doPublish(query.getResultList());
    }

    @SuppressWarnings("unchecked")
    @Override
    public List<LogEntry> getLogEntriesFor(String uuid, Map<String, FilterMapEntry> filterMap,
            boolean doDefaultSort) {
        if (log.isDebugEnabled()) {
            log.debug("getLogEntriesFor() UUID=" + uuid);
        }

        if (filterMap == null) {
            filterMap = new HashMap<String, FilterMapEntry>();
        }

        StringBuilder queryStr = new StringBuilder();
        queryStr.append(" FROM LogEntry log WHERE log.docUUID=:uuid ");

        Set<String> filterMapKeySet = filterMap.keySet();
        for (String currentKey : filterMapKeySet) {
            FilterMapEntry currentFilterMapEntry = filterMap.get(currentKey);
            String currentOperator = currentFilterMapEntry.getOperator();
            String currentQueryParameterName = currentFilterMapEntry.getQueryParameterName();
            String currentColumnName = currentFilterMapEntry.getColumnName();

            if ("LIKE".equals(currentOperator)) {
                queryStr.append(" AND log.").append(currentColumnName).append(" LIKE :")
                        .append(currentQueryParameterName).append(" ");
            } else {
                queryStr.append(" AND log.").append(currentColumnName).append(currentOperator).append(":")
                        .append(currentQueryParameterName).append(" ");
            }
        }

        if (doDefaultSort) {
            queryStr.append(" ORDER BY log.eventDate DESC");
        }

        Query query = em.createQuery(queryStr.toString());

        query.setParameter("uuid", uuid);

        for (String currentKey : filterMapKeySet) {
            FilterMapEntry currentFilterMapEntry = filterMap.get(currentKey);
            String currentOperator = currentFilterMapEntry.getOperator();
            String currentQueryParameterName = currentFilterMapEntry.getQueryParameterName();
            Object currentObject = currentFilterMapEntry.getObject();

            if ("LIKE".equals(currentOperator)) {
                query.setParameter(currentQueryParameterName, "%" + currentObject + "%");
            } else {
                query.setParameter(currentQueryParameterName, currentObject);
            }
        }

        return doPublish(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#getLogEntryByID (long)
     */
    public LogEntry getLogEntryByID(long id) {
        if (log.isDebugEnabled()) {
            log.debug("getLogEntriesFor() logID=" + id);
        }
        return doPublish(em.find(LogEntryImpl.class, id));
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#nativeQueryLogs (java.lang.String, int, int)
     */
    @SuppressWarnings("unchecked")
    public List<LogEntry> nativeQueryLogs(String whereClause, int pageNb, int pageSize) {
        Query query = em.createQuery("from LogEntry log where " + whereClause);
        if (pageNb > 1) {
            query.setFirstResult((pageNb - 1) * pageSize);
        } else if (pageNb == 0) {
            log.warn("Requested pageNb equals 0 but page index start at 1. Will fallback to fetch the first page");
        }
        query.setMaxResults(pageSize);
        return doPublish(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#nativeQuery(java .lang.String, int, int)
     */
    public List<?> nativeQuery(String queryString, int pageNb, int pageSize) {
        Query query = em.createQuery(queryString);
        if (pageNb > 1) {
            query.setFirstResult((pageNb - 1) * pageSize);
        }
        query.setMaxResults(pageSize);
        return doPublishIfEntries(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#nativeQuery(java .lang.String, java.util.Map, int,
     * int)
     */
    public List<?> nativeQuery(String queryString, Map<String, Object> params, int pageNb, int pageSize) {
        if (pageSize <= 0) {
            pageSize = 1000;
        }
        Query query = em.createQuery(queryString);
        for (Entry<String, Object> en : params.entrySet()) {
            query.setParameter(en.getKey(), en.getValue());
        }
        if (pageNb > 1) {
            query.setFirstResult((pageNb - 1) * pageSize);
        }
        query.setMaxResults(pageSize);
        return doPublishIfEntries(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#queryLogs(java. lang.String[], java.lang.String)
     */
    @SuppressWarnings("unchecked")
    public List<LogEntry> queryLogs(String[] eventIds, String dateRange) {
        Date limit;
        try {
            limit = DateRangeParser.parseDateRangeQuery(new Date(), dateRange);
        } catch (AuditQueryException aqe) {
            aqe.addInfo("Wrong date range query. Query was " + dateRange);
            throw aqe;
        }

        String queryStr = "";
        if (eventIds == null || eventIds.length == 0) {
            queryStr = "from LogEntry log" + " where log.eventDate >= :limit" + " ORDER BY log.eventDate DESC";
        } else {
            String inClause = "(";
            for (String eventId : eventIds) {
                inClause += "'" + eventId + "',";
            }
            inClause = inClause.substring(0, inClause.length() - 1);
            inClause += ")";

            queryStr = "from LogEntry log" + " where log.eventId in " + inClause + " AND log.eventDate >= :limit"
                    + " ORDER BY log.eventDate DESC";
        }

        if (log.isDebugEnabled()) {
            log.debug("queryLogs() =" + queryStr);
        }
        Query query = em.createQuery(queryStr);
        query.setParameter("limit", limit);

        return doPublish(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#queryLogsByPage (java.lang.String[], java.lang.String,
     * java.lang.String[], java.lang.String, int, int)
     */
    public List<LogEntry> queryLogsByPage(String[] eventIds, String dateRange, String[] categories, String path,
            int pageNb, int pageSize) {
        Date limit = null;
        try {
            limit = DateRangeParser.parseDateRangeQuery(new Date(), dateRange);
        } catch (AuditQueryException aqe) {
            aqe.addInfo("Wrong date range query. Query was " + dateRange);
            throw aqe;
        }
        return queryLogsByPage(eventIds, limit, categories, path, pageNb, pageSize);
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#queryLogsByPage (java.lang.String[], java.util.Date,
     * java.lang.String[], java.lang.String, int, int)
     */
    @SuppressWarnings("unchecked")
    public List<LogEntry> queryLogsByPage(String[] eventIds, Date limit, String[] categories, String path,
            int pageNb, int pageSize) {
        if (eventIds == null) {
            eventIds = new String[0];
        }
        if (categories == null) {
            categories = new String[0];
        }

        StringBuilder queryString = new StringBuilder();

        queryString.append("from LogEntry log where ");

        if (eventIds.length > 0) {
            String inClause = "(";
            for (String eventId : eventIds) {
                inClause += "'" + eventId + "',";
            }
            inClause = inClause.substring(0, inClause.length() - 1);
            inClause += ")";

            queryString.append(" log.eventId IN ").append(inClause);
            queryString.append(" AND ");
        }
        if (categories.length > 0) {
            String inClause = "(";
            for (String cat : categories) {
                inClause += "'" + cat + "',";
            }
            inClause = inClause.substring(0, inClause.length() - 1);
            inClause += ")";
            queryString.append(" log.category IN ").append(inClause);
            queryString.append(" AND ");
        }

        if (path != null && !"".equals(path.trim())) {
            queryString.append(" log.docPath LIKE '").append(path).append("%'");
            queryString.append(" AND ");
        }

        queryString.append(" log.eventDate >= :limit");
        queryString.append(" ORDER BY log.eventDate DESC");

        Query query = em.createQuery(queryString.toString());

        query.setParameter("limit", limit);

        if (pageNb > 1) {
            query.setFirstResult((pageNb - 1) * pageSize);
        }
        query.setMaxResults(pageSize);

        return doPublish(query.getResultList());
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#removeEntries(java .lang.String, java.lang.String)
     */
    @Override
    @SuppressWarnings("unchecked")
    public int removeEntries(String eventId, String pathPattern) {
        // TODO extended info cascade delete does not work using HQL, so we
        // have to delete each
        // entry by hand.
        Query query = em.createNamedQuery("LogEntry.findByEventIdAndPath");
        query.setParameter("eventId", eventId);
        query.setParameter("pathPattern", pathPattern + "%");
        int count = 0;
        for (LogEntry entry : (List<LogEntry>) query.getResultList()) {
            em.remove(entry);
            count += 1;
        }
        if (log.isDebugEnabled()) {
            log.debug("removed " + count + " entries from " + pathPattern);
        }
        return count;
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#countEventsById (java.lang.String)
     */
    public Long countEventsById(String eventId) {
        Query query = em.createNamedQuery("LogEntry.countEventsById");
        query.setParameter("eventId", eventId);
        return (Long) query.getSingleResult();
    }

    /*
     * (non-Javadoc)
     * @see org.nuxeo.ecm.platform.audit.service.LogEntryProvider#findEventIds()
     */
    @SuppressWarnings("unchecked")
    public List<String> findEventIds() {
        Query query = em.createNamedQuery("LogEntry.findEventIds");
        return (List<String>) query.getResultList();
    }

}