001/*
002 * (C) Copyright 2006-2017 Nuxeo (http://nuxeo.com/) and others.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 *
016 * Contributors:
017 *     Nuxeo - initial API and implementation
018 */
019package org.nuxeo.ecm.platform.audit.api;
020
021import static org.nuxeo.ecm.platform.audit.api.BuiltinLogEntryData.LOG_DOC_UUID;
022import static org.nuxeo.ecm.platform.audit.api.BuiltinLogEntryData.LOG_REPOSITORY_ID;
023
024import java.util.Collections;
025import java.util.Date;
026import java.util.LinkedList;
027import java.util.List;
028import java.util.Map;
029import java.util.stream.Collectors;
030
031import org.nuxeo.ecm.core.query.sql.model.Predicates;
032import org.nuxeo.ecm.core.query.sql.model.QueryBuilder;
033import org.nuxeo.ecm.platform.audit.api.query.AuditQueryException;
034import org.nuxeo.ecm.platform.audit.api.query.DateRangeParser;
035
036/**
037 * Interface for reading data from the Audit service.
038 *
039 * @author tiry
040 */
041public interface AuditReader {
042
043    /**
044     * Returns the logs given a doc uuid and a repository id.
045     *
046     * @param uuid the document uuid
047     * @param repositoryId the repository id
048     * @return a list of log entries
049     * @since 8.4
050     */
051    default List<LogEntry> getLogEntriesFor(String uuid, String repositoryId) {
052        return queryLogs(new AuditQueryBuilder().predicate(Predicates.eq(LOG_DOC_UUID, uuid))
053                                                .and(Predicates.eq(LOG_REPOSITORY_ID, repositoryId))
054                                                .defaultOrder());
055    }
056
057    /**
058     * Returns the logs given a doc uuid.
059     *
060     * @param uuid the document uuid
061     * @return a list of log entries
062     * @deprecated since 8.4, use {@link #getLogEntriesFor(String, String)} instead.
063     */
064    @Deprecated
065    default List<LogEntry> getLogEntriesFor(String uuid) {
066        return queryLogs(
067                new AuditQueryBuilder().predicate(Predicates.eq(LOG_DOC_UUID, uuid))
068                                       .defaultOrder());
069    }
070
071    /**
072     * Returns the logs given a doc uuid, a map of filters and a default sort.
073     *
074     * @param uuid the document uuid
075     * @param filterMap the map of filters to apply
076     * @param doDefaultSort the default sort to set (eventDate desc)
077     * @return a list of log entries
078     * @deprecated since 9.3, this method doesn't take into account the document repository, use
079     *             {@link #queryLogs(QueryBuilder)} instead.
080     */
081    @Deprecated
082    List<LogEntry> getLogEntriesFor(String uuid, Map<String, FilterMapEntry> filterMap, boolean doDefaultSort);
083
084    /**
085     * Returns a given log entry given its id.
086     *
087     * @param id the log entry identifier
088     * @return a LogEntry instance
089     */
090    LogEntry getLogEntryByID(long id);
091
092    /**
093     * Returns the logs given a collection of predicates and a default sort.
094     *
095     * @param builder the query builder to fetch log entries
096     * @return a list of log entries
097     * @since 9.3
098     */
099    List<LogEntry> queryLogs(QueryBuilder builder);
100
101    /**
102     * Returns the list of log entries.
103     * <p>
104     * Note we will use NXQL in the future when the search engine will index history.
105     *
106     * @see org.nuxeo.ecm.platform.audit.api.query.DateRangeQueryConstants
107     * @param eventIds the event ids.
108     * @param dateRange a preset date range.
109     * @return a list of log entries.
110     */
111    default List<LogEntry> queryLogs(String[] eventIds, String dateRange) {
112        return queryLogsByPage(eventIds, (String) null, (String[]) null, null, 0, 10000);
113    }
114
115    /**
116     * Returns the batched list of log entries.
117     * <p>
118     * Note we will use NXQL in the future when the search engine will index history.
119     *
120     * @see org.nuxeo.ecm.platform.audit.api.query.DateRangeQueryConstants
121     * @param eventIds the event ids.
122     * @param dateRange a preset date range.
123     * @param category add filter on events category
124     * @param path add filter on document path
125     * @param pageNb page number (ignore if <=1)
126     * @param pageSize number of results per page
127     * @return a list of log entries.
128     */
129    default List<LogEntry> queryLogsByPage(String[] eventIds, String dateRange, String category, String path, int pageNb,
130            int pageSize) {
131        return queryLogsByPage(eventIds, dateRange, new String[] { category }, path, pageNb, pageSize);
132    }
133
134    default List<LogEntry> queryLogsByPage(String[] eventIds, String dateRange, String[] categories, String path, int pageNb,
135            int pageSize) {
136
137        Date limit = null;
138        if (dateRange != null) {
139            try {
140                limit = DateRangeParser.parseDateRangeQuery(new Date(), dateRange);
141            } catch (AuditQueryException aqe) {
142                aqe.addInfo("Wrong date range query. Query was " + dateRange);
143                throw aqe;
144            }
145        }
146        return queryLogsByPage(eventIds, limit, categories, path, pageNb, pageSize);
147    }
148
149    /**
150     * Returns the batched list of log entries.
151     * <p>
152     * Note we will use NXQL in the future when the search engine will index history.
153     *
154     * @see org.nuxeo.ecm.platform.audit.api.query.DateRangeQueryConstants
155     * @param eventIds the event ids.
156     * @param limit filter events by date from limit to now
157     * @param category add filter on events category
158     * @param path add filter on document path
159     * @param pageNb page number (ignore if <=1)
160     * @param pageSize number of results per page
161     * @return a list of log entries.
162     */
163    default List<LogEntry> queryLogsByPage(String[] eventIds, Date limit, String category, String path, int pageNb,
164            int pageSize) {
165        return queryLogsByPage(eventIds, limit, new String[] { category }, path, pageNb, pageSize);
166    }
167
168    List<LogEntry> queryLogsByPage(String[] eventIds, Date limit, String[] categories, String path, int pageNb,
169            int pageSize);
170
171    /**
172     * Returns a batched list of log entries. WhereClause is a native where clause for the backend: here EJBQL 3.0 must
173     * be used if implementation of audit backend is JPA (< 7.3 or audit.elasticsearch.enabled=false) and JSON if
174     * implementation is Elasticsearch.
175     */
176    default List<LogEntry> nativeQueryLogs(String whereClause, int pageNb, int pageSize) {
177        return nativeQuery(whereClause, pageNb, pageSize).stream()
178                                                         .filter(LogEntry.class::isInstance)
179                                                         .map(LogEntry.class::cast)
180                                                         .collect(Collectors.toCollection(LinkedList::new));
181    }
182
183    /**
184     * Returns a batched list of entries. query string is a native query clause for the backend : here EJBQL 3.0 must be
185     * used if implementation of audit backend is JPA (< 7.3 or audit.elasticsearch.enabled=false) and JSON if
186     * implementation is Elasticsearch.
187     */
188    default List<?> nativeQuery(String query, int pageNb, int pageSize) {
189        return nativeQuery(query, Collections.<String, Object> emptyMap(), pageNb, pageSize);
190    }
191
192    /**
193     * Returns a batched list of entries.
194     *
195     * @param query a JPA query language query if implementation of audit backend is JPA (< 7.3 or
196     *            audit.elasticsearch.enabled=false) and JSON if implementation is Elasticsearch
197     * @param params parameters for the query
198     * @param pageNb the page number (starts at 1)
199     * @param pageSize the number of results per page
200     */
201    List<?> nativeQuery(String query, Map<String, Object> params, int pageNb, int pageSize);
202
203    /**
204     * Returns the latest log id matching events and repository or 0 when no match found.
205     *
206     * @since 9.3
207     */
208    long getLatestLogId(String repositoryId, String... eventIds);
209
210    /**
211     * Returns up to limit log entries matching events and repository with log id greater or equal to logIdOffset.
212     *
213     * @since 9.3
214     */
215    List<LogEntry> getLogEntriesAfter(long logIdOffset, int limit, String repositoryId, String... eventIds);
216
217}