TemplatePart.java
package com.timtrense.template;
import lombok.NonNull;
import java.io.IOException;
import java.io.OutputStream;
import java.io.Writer;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.util.function.Consumer;
/**
* An object representation of a gap in a gap text (that is, a {@link Template}) that,
* when invoked on a {@link Context}, will give the actual value.
* The required method to implement by subclasses is {@link #process(Context)}.
* If invocation of that method however would create a significant amount of heap
* or processing, an implementation may override the other provided methods to be
* able to stream its results.
*
* @author Tim Trense
* @since 1.0
*/
public interface TemplatePart {
/**
* Create the actual value of the placeholder that comes from the {@link Context}.
* The result WILL be converted using {@link String#valueOf(Object)}.
* Returning {@link Object} is just a convenience.
* <p>
* Implementations MUST be stateless and MUST have no side-effects and MUST not alter the given context.
* Implementations MAY throw {@link RuntimeException} which
* will end the processing of more parts and will bubble
* up to the user of {@link Template#process(Context)}
*
* @param context the context with all the information to resolve a {@link Template} once in this very situation
* @return the value of this placeholder derived from information of the
* context. MUST be String-convertible. Not null.
*/
Object process(Context context);
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param consumer the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void process(Context context, @NonNull Consumer<Object> consumer) {
consumer.accept(process(context));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param builder the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void append(Context context, @NonNull StringBuilder builder) {
builder.append(process(context));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param buffer the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void append(Context context, @NonNull StringBuffer buffer) {
buffer.append(process(context));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param appendable the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void append(Context context, @NonNull Appendable appendable) throws IOException {
appendable.append(String.valueOf(process(context)));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param writer the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void writeTo(Context context, @NonNull Writer writer) throws IOException {
writer.write(String.valueOf(process(context)));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination
*
* @param context the context to invoke {@link #process(Context)} with
* @param outputStream the destination to push the result of the invocation of {@link #process(Context)} to
* @param charset the charset to encode the output of {@link #process(Context)} with
*/
default void writeTo(Context context, @NonNull OutputStream outputStream, @NonNull Charset charset) throws IOException {
outputStream.write(String.valueOf(process(context)).getBytes(charset));
}
/**
* Calls {@link #process(Context)} and pushes the output to the given destination.
* Equals a call to {@link #writeTo(Context, OutputStream, Charset)} with the charset being {@link StandardCharsets#UTF_8}
*
* @param context the context to invoke {@link #process(Context)} with
* @param outputStream the destination to push the result of the invocation of {@link #process(Context)} to
*/
default void writeTo(Context context, @NonNull OutputStream outputStream) throws IOException {
writeTo(context, outputStream, StandardCharsets.UTF_8);
}
}