Skip to content

Commit

Permalink
HDDS-376. Create custom message structure for use in AuditLogging
Browse files Browse the repository at this point in the history
Contributed by Dinesh Chitlangia.
  • Loading branch information
anuengineer committed Aug 28, 2018
1 parent cb9d371 commit ac515d2
Show file tree
Hide file tree
Showing 4 changed files with 177 additions and 96 deletions.
Expand Up @@ -21,27 +21,22 @@
import org.apache.logging.log4j.Level; import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Marker; import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.message.StructuredDataMessage;
import org.apache.logging.log4j.spi.ExtendedLogger; import org.apache.logging.log4j.spi.ExtendedLogger;


import java.util.Map;


/** /**
* Class to define Audit Logger for Ozone. * Class to define Audit Logger for Ozone.
*/ */
public class AuditLogger { public class AuditLogger {


private ExtendedLogger logger; private ExtendedLogger logger;

private static final String SUCCESS = AuditEventStatus.SUCCESS.getStatus();
private static final String FAILURE = AuditEventStatus.FAILURE.getStatus();
private static final String FQCN = AuditLogger.class.getName(); private static final String FQCN = AuditLogger.class.getName();
private static final Marker WRITE_MARKER = AuditMarker.WRITE.getMarker(); private static final Marker WRITE_MARKER = AuditMarker.WRITE.getMarker();
private static final Marker READ_MARKER = AuditMarker.READ.getMarker(); private static final Marker READ_MARKER = AuditMarker.READ.getMarker();


/** /**
* Parametrized Constructor to initialize logger. * Parametrized Constructor to initialize logger.
* @param type * @param type Audit Logger Type
*/ */
public AuditLogger(AuditLoggerType type){ public AuditLogger(AuditLoggerType type){
initializeLogger(type); initializeLogger(type);
Expand All @@ -60,68 +55,53 @@ public ExtendedLogger getLogger() {
return logger; return logger;
} }


public void logWriteSuccess(AuditAction type, Map<String, String> data) { public void logWriteSuccess(AuditMessage msg) {
logWriteSuccess(type, data, Level.INFO); logWriteSuccess(Level.INFO, msg);
} }


public void logWriteSuccess(AuditAction type, Map<String, String> data, Level public void logWriteSuccess(Level level, AuditMessage msg) {
level) {
StructuredDataMessage msg = new StructuredDataMessage("", SUCCESS,
type.getAction(), data);
this.logger.logIfEnabled(FQCN, level, WRITE_MARKER, msg, null); this.logger.logIfEnabled(FQCN, level, WRITE_MARKER, msg, null);
} }



public void logWriteFailure(AuditMessage msg) {
public void logWriteFailure(AuditAction type, Map<String, String> data) { logWriteFailure(Level.ERROR, msg);
logWriteFailure(type, data, Level.INFO, null);
} }


public void logWriteFailure(AuditAction type, Map<String, String> data, Level public void logWriteFailure(Level level, AuditMessage msg) {
level) { logWriteFailure(level, msg, null);
logWriteFailure(type, data, level, null);
} }


public void logWriteFailure(AuditAction type, Map<String, String> data, public void logWriteFailure(AuditMessage msg, Throwable exception) {
Throwable exception) { logWriteFailure(Level.ERROR, msg, exception);
logWriteFailure(type, data, Level.INFO, exception);
} }


public void logWriteFailure(AuditAction type, Map<String, String> data, Level public void logWriteFailure(Level level, AuditMessage msg,
level, Throwable exception) { Throwable exception) {
StructuredDataMessage msg = new StructuredDataMessage("", FAILURE,
type.getAction(), data);
this.logger.logIfEnabled(FQCN, level, WRITE_MARKER, msg, exception); this.logger.logIfEnabled(FQCN, level, WRITE_MARKER, msg, exception);
} }


public void logReadSuccess(AuditAction type, Map<String, String> data) { public void logReadSuccess(AuditMessage msg) {
logReadSuccess(type, data, Level.INFO); logReadSuccess(Level.INFO, msg);
} }


public void logReadSuccess(AuditAction type, Map<String, String> data, Level public void logReadSuccess(Level level, AuditMessage msg) {
level) {
StructuredDataMessage msg = new StructuredDataMessage("", SUCCESS,
type.getAction(), data);
this.logger.logIfEnabled(FQCN, level, READ_MARKER, msg, null); this.logger.logIfEnabled(FQCN, level, READ_MARKER, msg, null);
} }


public void logReadFailure(AuditAction type, Map<String, String> data) { public void logReadFailure(AuditMessage msg) {
logReadFailure(type, data, Level.INFO, null); logReadFailure(Level.ERROR, msg);
} }


public void logReadFailure(AuditAction type, Map<String, String> data, Level public void logReadFailure(Level level, AuditMessage msg) {
level) { logReadFailure(level, msg, null);
logReadFailure(type, data, level, null);
} }


public void logReadFailure(AuditAction type, Map<String, String> data, public void logReadFailure(AuditMessage msg, Throwable exception) {
Throwable exception) { logReadFailure(Level.ERROR, msg, exception);
logReadFailure(type, data, Level.INFO, exception);
} }


public void logReadFailure(AuditAction type, Map<String, String> data, Level public void logReadFailure(Level level, AuditMessage msg,
level, Throwable exception) { Throwable exception) {
StructuredDataMessage msg = new StructuredDataMessage("", FAILURE,
type.getAction(), data);
this.logger.logIfEnabled(FQCN, level, READ_MARKER, msg, exception); this.logger.logIfEnabled(FQCN, level, READ_MARKER, msg, exception);
} }


Expand Down
@@ -0,0 +1,64 @@
/**
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with this
* work for additional information regarding copyright ownership. The ASF
* licenses this file to you 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
* <p>
* http://www.apache.org/licenses/LICENSE-2.0
* <p>
* 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.
*/
package org.apache.hadoop.ozone.audit;

import org.apache.logging.log4j.message.Message;

import java.util.Map;

/**
* Defines audit message structure.
*/
public class AuditMessage implements Message {

private String message;

public AuditMessage(String user, String ip, String op,
Map<String, String> params, String ret){

this.message = String.format("user=%s ip=%s op=%s %s ret=%s",
user, ip, op, params, ret);
}

@Override
public String getFormattedMessage() {
return message;
}

@Override
public String getFormat() {
return null;
}

@Override
public Object[] getParameters() {
return new Object[0];
}

@Override
public Throwable getThrowable() {
return null;
}

/**
* Use when there are custom string to be added to default msg.
* @param customMessage custom string
*/
private void appendMessage(String customMessage) {
this.message += customMessage;
}
}
Expand Up @@ -46,7 +46,7 @@
* **** Auditable *** * **** Auditable ***
* This is an interface to mark an entity as auditable. * This is an interface to mark an entity as auditable.
* This interface must be implemented by entities requiring audit logging. * This interface must be implemented by entities requiring audit logging.
* For example - KSMVolumeArgs, KSMBucketArgs. * For example - OMVolumeArgs, OMBucketArgs.
* The implementing class must override toAuditMap() to return an * The implementing class must override toAuditMap() to return an
* instance of Map<Key, Value> where both Key and Value are String. * instance of Map<Key, Value> where both Key and Value are String.
* *
Expand Down Expand Up @@ -81,21 +81,28 @@
* *** AuditMarker *** * *** AuditMarker ***
* Enum to define various Audit Markers used in AuditLogging. * Enum to define various Audit Markers used in AuditLogging.
* *
* *** AuditMessage ***
* Entity to define an audit message to be logged
* It will generate a message formatted as:
* user=xxx ip=xxx op=XXXX_XXXX {key=val, key1=val1..} ret=XXXXXX
*
* **************************************************************************** * ****************************************************************************
* Usage * Usage
* **************************************************************************** * ****************************************************************************
* Using the AuditLogger to log events: * Using the AuditLogger to log events:
* 1. Get a logger by specifying the appropriate logger type * 1. Get a logger by specifying the appropriate logger type
* Example: ExtendedLogger AUDIT = new AuditLogger(AuditLoggerType.OMLogger) * Example: ExtendedLogger AUDIT = new AuditLogger(AuditLoggerType.OMLogger)
* *
* 2. Log Read/Write and Success/Failure event as needed. * 2. Construct an instance of AuditMessage
*
* 3. Log Read/Write and Success/Failure event as needed.
* Example * Example
* AUDIT.logWriteSuccess(AuditAction type, Map<String, String> data, Level * AUDIT.logWriteSuccess(Level level, AuditMessage msg)
* level)
* *
* If logging is done without specifying Level, then Level implicitly * If logging is done without specifying Level, then Level implicitly
* defaults to INFO * defaults to INFO for xxxxSuccess() and ERROR for xxxxFailure()
* AUDIT.logWriteSuccess(AuditAction type, Map<String, String> data) * AUDIT.logWriteSuccess(AuditMessage msg)
* AUDIT.logWriteFailure(AuditMessage msg)
* *
* See sample invocations in src/test in the following class: * See sample invocations in src/test in the following class:
* org.apache.hadoop.ozone.audit.TestOzoneAuditLogger * org.apache.hadoop.ozone.audit.TestOzoneAuditLogger
Expand Down

0 comments on commit ac515d2

Please sign in to comment.