use of org.nuxeo.ecm.platform.audit.api.LogEntry in project nuxeo-drive-server by nuxeo.
the class AuditChangeFinder method getUpperBound.
/**
* Return the last available log id in the audit log table (primary key) to be used as the upper bound of the event
* log id range clause in the change query.
*/
@Override
@SuppressWarnings("unchecked")
public long getUpperBound() {
AuditReader auditService = Framework.getService(AuditReader.class);
String auditQuery = "from LogEntry log order by log.id desc";
if (log.isDebugEnabled()) {
log.debug("Querying audit log for greatest id: " + auditQuery);
}
List<LogEntry> entries = (List<LogEntry>) auditService.nativeQuery(auditQuery, 1, 1);
if (entries.isEmpty()) {
if (log.isDebugEnabled()) {
log.debug("Found no audit log entries, returning -1");
}
return -1;
}
return entries.get(0).getId();
}
use of org.nuxeo.ecm.platform.audit.api.LogEntry in project nuxeo-drive-server by nuxeo.
the class AuditChangeFinder method getFileSystemChanges.
protected List<FileSystemItemChange> getFileSystemChanges(CoreSession session, Set<IdRef> lastActiveRootRefs, SynchronizationRoots activeRoots, Set<String> collectionSyncRootMemberIds, long lowerBound, long upperBound, boolean integerBounds, int limit) throws TooManyChangesException {
String principalName = session.getPrincipal().getName();
List<FileSystemItemChange> changes = new ArrayList<FileSystemItemChange>();
// Note: lastActiveRootRefs is not used: we could remove it from the
// public API
// and from the client as well but it might be useful to optimize future
// alternative implementations FileSystemChangeFinder component so it
// might
// be better to leave it part of the public API as currently.
// Find changes from the log under active roots or events that are
// linked to the un-registration or deletion of formerly synchronized
// roots
List<LogEntry> entries = queryAuditEntries(session, activeRoots, collectionSyncRootMemberIds, lowerBound, upperBound, integerBounds, limit);
// query with the actual active roots.
for (LogEntry entry : entries) {
if (NuxeoDriveEvents.EVENT_CATEGORY.equals(entry.getCategory())) {
if (log.isDebugEnabled()) {
log.debug(String.format("Detected sync root change for user '%s' in audit log:" + " invalidating the root cache and refetching the changes.", principalName));
}
NuxeoDriveManager driveManager = Framework.getService(NuxeoDriveManager.class);
driveManager.invalidateSynchronizationRootsCache(principalName);
driveManager.invalidateCollectionSyncRootMemberCache(principalName);
Map<String, SynchronizationRoots> synchronizationRoots = driveManager.getSynchronizationRoots(session.getPrincipal());
SynchronizationRoots updatedActiveRoots = synchronizationRoots.get(session.getRepositoryName());
Set<String> updatedCollectionSyncRootMemberIds = driveManager.getCollectionSyncRootMemberIds(session.getPrincipal()).get(session.getRepositoryName());
entries = queryAuditEntries(session, updatedActiveRoots, updatedCollectionSyncRootMemberIds, lowerBound, upperBound, integerBounds, limit);
break;
}
}
if (entries.size() >= limit) {
throw new TooManyChangesException("Too many changes found in the audit logs.");
}
for (LogEntry entry : entries) {
if (log.isDebugEnabled()) {
log.debug(String.format("Handling log entry %s", entry));
}
FileSystemItemChange change = null;
DocumentRef docRef = new IdRef(entry.getDocUUID());
ExtendedInfo fsIdInfo = entry.getExtendedInfos().get("fileSystemItemId");
if (fsIdInfo != null) {
// been updated, we just know the FileSystemItem id and name.
if (log.isDebugEnabled()) {
log.debug(String.format("Found extended info in audit log entry: document has been deleted, moved," + " is an unregistered synchronization root or its security has been updated," + " we just know the FileSystemItem id and name."));
}
boolean isChangeSet = false;
// current user still has access to the document.
if (!"deleted".equals(entry.getEventId()) && session.exists(docRef)) {
change = getFileSystemItemChange(session, docRef, entry, fsIdInfo.getValue(String.class));
if (change != null) {
if (NuxeoDriveEvents.MOVED_EVENT.equals(entry.getEventId())) {
// virtual event.
if (log.isDebugEnabled()) {
log.debug(String.format("Document %s (%s) has been moved to another synchronzation root, not adding entry to the change summary.", entry.getDocPath(), docRef));
}
continue;
}
isChangeSet = true;
}
}
if (!isChangeSet) {
// FileSystemItem id and name to the FileSystemItemChange entry.
if (log.isDebugEnabled()) {
log.debug(String.format("Document %s (%s) doesn't exist or is not adaptable as a FileSystemItem, only providing the FileSystemItem id and name to the FileSystemItemChange entry.", entry.getDocPath(), docRef));
}
String fsId = fsIdInfo.getValue(String.class);
String eventId;
if (NuxeoDriveEvents.MOVED_EVENT.equals(entry.getEventId())) {
// Move to a non synchronization root
eventId = NuxeoDriveEvents.DELETED_EVENT;
} else {
// Deletion, unregistration or security update
eventId = entry.getEventId();
}
change = new FileSystemItemChangeImpl(eventId, entry.getEventDate().getTime(), entry.getRepositoryId(), entry.getDocUUID(), fsId, null);
}
if (log.isDebugEnabled()) {
log.debug(String.format("Adding FileSystemItemChange entry to the change summary: %s", change));
}
changes.add(change);
} else {
// unregistered synchronization root nor a security update denying access to the current user.
if (log.isDebugEnabled()) {
log.debug(String.format("No extended info found in audit log entry %s (%s): this is not a deleted document, a moved document," + " an unregistered synchronization root nor a security update denying access to the current user.", entry.getDocPath(), docRef));
}
if (!session.exists(docRef)) {
if (log.isDebugEnabled()) {
log.debug(String.format("Document %s (%s) doesn't exist, not adding entry to the change summary.", entry.getDocPath(), docRef));
}
// try to propagate this event.
continue;
}
// Let's try to adapt the document as a FileSystemItem to
// provide it to the FileSystemItemChange entry.
change = getFileSystemItemChange(session, docRef, entry, null);
if (change == null) {
// Non-adaptable documents are ignored
if (log.isDebugEnabled()) {
log.debug(String.format("Document %s (%s) is not adaptable as a FileSystemItem, not adding any entry to the change summary.", entry.getDocPath(), docRef));
}
} else {
if (log.isDebugEnabled()) {
log.debug(String.format("Adding FileSystemItemChange entry to the change summary: %s", change));
}
changes.add(change);
}
}
}
return changes;
}
use of org.nuxeo.ecm.platform.audit.api.LogEntry in project nuxeo-drive-server by nuxeo.
the class NuxeoDriveFileSystemDeletionListener method fireVirtualEventLogEntries.
protected void fireVirtualEventLogEntries(DocumentModel doc, String eventName, Principal principal, String impactedUserName, CoreSession session) {
if (Framework.getService(AuditLogger.class) == null) {
// The log is not deployed (probably in unittest)
return;
}
List<LogEntry> entries = new ArrayList<>();
// XXX: shall we use the server local for the event date or UTC?
Date currentDate = Calendar.getInstance(NuxeoDriveManagerImpl.UTC).getTime();
FileSystemItem fsItem = getFileSystemItem(doc, eventName);
if (fsItem == null) {
// roots in order to make Drive add / remove them if needed
if (NuxeoDriveEvents.SECURITY_UPDATED_EVENT.equals(eventName)) {
for (DocumentModel childSyncRoot : getChildSyncRoots(doc, session)) {
FileSystemItem childSyncRootFSItem = getFileSystemItem(childSyncRoot, eventName);
if (childSyncRootFSItem != null) {
entries.add(computeLogEntry(eventName, currentDate, childSyncRoot.getId(), childSyncRoot.getPathAsString(), principal.getName(), childSyncRoot.getType(), childSyncRoot.getRepositoryName(), childSyncRoot.getCurrentLifeCycleState(), impactedUserName, childSyncRootFSItem));
}
}
}
} else {
entries.add(computeLogEntry(eventName, currentDate, doc.getId(), doc.getPathAsString(), principal.getName(), doc.getType(), doc.getRepositoryName(), doc.getCurrentLifeCycleState(), impactedUserName, fsItem));
}
if (!entries.isEmpty()) {
EventContext eventContext = new EventContextImpl(entries.toArray());
Event event = eventContext.newEvent(NuxeoDriveEvents.VIRTUAL_EVENT_CREATED);
Framework.getService(EventProducer.class).fireEvent(event);
}
}
use of org.nuxeo.ecm.platform.audit.api.LogEntry in project nuxeo-drive-server by nuxeo.
the class NuxeoDriveFileSystemDeletionListener method computeLogEntry.
protected LogEntry computeLogEntry(String eventName, Date eventDate, String docId, String docPath, String principal, String docType, String repositoryName, String currentLifeCycleState, String impactedUserName, FileSystemItem fsItem) {
AuditLogger logger = Framework.getService(AuditLogger.class);
LogEntry entry = logger.newLogEntry();
entry.setEventId(eventName);
entry.setEventDate(eventDate);
entry.setCategory(NuxeoDriveEvents.EVENT_CATEGORY);
entry.setDocUUID(docId);
entry.setDocPath(docPath);
entry.setPrincipalName(principal);
entry.setDocType(docType);
entry.setRepositoryId(repositoryName);
entry.setDocLifeCycle(currentLifeCycleState);
Map<String, ExtendedInfo> extendedInfos = new HashMap<String, ExtendedInfo>();
if (impactedUserName != null) {
extendedInfos.put("impactedUserName", logger.newExtendedInfo(impactedUserName));
}
// We do not serialize the whole object as it's too big to fit in a
// StringInfo column
extendedInfos.put("fileSystemItemId", logger.newExtendedInfo(fsItem.getId()));
extendedInfos.put("fileSystemItemName", logger.newExtendedInfo(fsItem.getName()));
entry.setExtendedInfos(extendedInfos);
return entry;
}
use of org.nuxeo.ecm.platform.audit.api.LogEntry in project nuxeo-drive-server by nuxeo.
the class ESAuditChangeFinder method queryAuditEntries.
@Override
protected List<LogEntry> queryAuditEntries(CoreSession session, SynchronizationRoots activeRoots, Set<String> collectionSyncRootMemberIds, long lowerBound, long upperBound, boolean integerBounds, int limit) {
List<LogEntry> entries = queryESAuditEntries(session, activeRoots, collectionSyncRootMemberIds, lowerBound, upperBound, integerBounds, limit);
// Post filter the output to remove (un)registration that are unrelated
// to the current user.
// TODO move this to the ES query
List<LogEntry> postFilteredEntries = new ArrayList<>();
String principalName = session.getPrincipal().getName();
for (LogEntry entry : entries) {
ExtendedInfo impactedUserInfo = entry.getExtendedInfos().get("impactedUserName");
if (impactedUserInfo != null && !principalName.equals(impactedUserInfo.getValue(String.class))) {
// ignore event that only impact other users
continue;
}
if (log.isDebugEnabled()) {
if (log.isDebugEnabled()) {
log.debug(String.format("Change detected: %s", entry));
}
}
postFilteredEntries.add(entry);
}
return postFilteredEntries;
}
Aggregations