package org.textfiledatatools.core.logger;

import org.textfiledatatools.core.Record;

import java.util.Objects;
import java.util.function.Consumer;

/**
 * A RecordLogger logs a {@link Record}.
 * <p>
 * It should not throw a RuntimeException (like NullPointerException).
 * It must be thread-safe and null-safe.
 * It must be <code>non-interfering</code>.
 * <p>
 * This is a functional interface whose functional method is {@link #log(Record)}.
 *
 * @author Mathias Kalb
 * @see java.util.function.Consumer
 * @see java.util.stream.Stream#peek(Consumer)
 * @since 0.1
 */
@FunctionalInterface
public interface RecordLogger<T extends Record> {

    static <T extends Record> RecordLogger<T> concat(RecordLogger<? super T> firstRecordLogger,
                                                     RecordLogger<? super T> secondRecordLogger) {
        Objects.requireNonNull(firstRecordLogger);
        Objects.requireNonNull(secondRecordLogger);
        return (T record) -> {
            firstRecordLogger.log(record);
            secondRecordLogger.log(record);
        };
    }

    static <T extends Record> RecordLogger<T> concat(RecordLogger<? super T> firstRecordLogger,
                                                     RecordLogger<? super T> secondRecordLogger,
                                                     RecordLogger<? super T> thirdRecordLogger) {
        Objects.requireNonNull(firstRecordLogger);
        Objects.requireNonNull(secondRecordLogger);
        Objects.requireNonNull(thirdRecordLogger);
        return (T record) -> {
            firstRecordLogger.log(record);
            secondRecordLogger.log(record);
            thirdRecordLogger.log(record);
        };
    }

    void log(T record);

    default RecordLogger<T> andThen(RecordLogger<? super T> afterRecordLogger) {
        Objects.requireNonNull(afterRecordLogger);
        return (T record) -> {
            log(record);
            afterRecordLogger.log(record);
        };
    }

}

@@ -79,16 +79,94 @@
 Record;%0A
+import org.textfiledatatools.core.filter.RecordFilter;%0A%0Aimport java.util.List;
 %0Aimport 
@@ -219,16 +219,52 @@
 onsumer;
+%0Aimport java.util.function.Function;
 %0A%0A/**%0A *
@@ -1809,24 +1809,1788 @@
   %7D;%0A    %7D%0A%0A
+    static %3CT extends Record%3E RecordLogger%3CT%3E conditionalLogger(List%3CRecordFilter%3C? super T%3E%3E loggerConditions,%0A                                                                List%3CRecordLogger%3C? super T%3E%3E recordLoggers) %7B%0A        Objects.requireNonNull(loggerConditions);%0A        Objects.requireNonNull(recordLoggers);%0A        if (loggerConditions.size() != recordLoggers.size()) %7B%0A            throw new IllegalArgumentException();%0A        %7D%0A        return (T record) -%3E %7B%0A            for (int i = 0; i %3C loggerConditions.size(); i++) %7B%0A                if (loggerConditions.get(i).isValid(record)) %7B%0A                    recordLoggers.get(i).log(record);%0A                %7D%0A            %7D%0A        %7D;%0A    %7D%0A%0A    static %3CT extends Record%3E RecordLogger%3CT%3E splitter(RecordFilter%3C? super T%3E splitCondition,%0A                                                       RecordLogger%3C? super T%3E trueRecordLogger,%0A                                                       RecordLogger%3C? super T%3E falseRecordLogger) %7B%0A        Objects.requireNonNull(splitCondition);%0A        Objects.requireNonNull(trueRecordLogger);%0A        Objects.requireNonNull(falseRecordLogger);%0A        return (T record) -%3E %7B%0A            if (splitCondition.isValid(record)) %7B%0A                trueRecordLogger.log(record);%0A            %7D else %7B%0A                falseRecordLogger.log(record);%0A            %7D%0A        %7D;%0A    %7D%0A%0A    static %3CT extends Record%3E RecordLogger%3CT%3E splitter(Function%3C? super T, Integer%3E splitFunction,%0A                                                       List%3CRecordLogger%3C? super T%3E%3E recordLoggers) %7B%0A        Objects.requireNonNull(splitFunction);%0A        Objects.requireNonNull(recordLoggers);%0A        return (T record) -%3E recordLoggers.get(splitFunction.apply(record)).log(record);%0A    %7D%0A%0A
     void log

Add new static methods to RecordLogger (copy of RecordConsumer)