001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      https://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017
018package org.apache.commons.codec.binary;
019
020import java.util.function.Supplier;
021
022/**
023 * Builds input and output stream instances in {@link BaseNCodec} format.
024 *
025 * @param <T> the stream type to build.
026 * @param <C> A {@link BaseNCodec} subclass.
027 * @param <B> the builder subclass.
028 * @since 1.20.0
029 */
030public abstract class AbstractBaseNCodecStreamBuilder<T, C extends BaseNCodec, B extends AbstractBaseNCodecStreamBuilder<T, C, B>> implements Supplier<T> {
031
032    private C baseNCodec;
033    private boolean encode;
034
035    /**
036     * Constructs a new instance.
037     */
038    public AbstractBaseNCodecStreamBuilder() {
039        baseNCodec = newBaseNCodec();
040    }
041
042    @SuppressWarnings("unchecked")
043    B asThis() {
044        return (B) this;
045    }
046
047    /**
048     * Gets the codec to encode/decode a stream.
049     *
050     * @return the codec to encode/decode a stream.
051     */
052    protected C getBaseNCodec() {
053        return baseNCodec;
054    }
055
056    /**
057     * Gets whether to encode or decode a stream.
058     *
059     * @return whether to encode or decode a stream.
060     */
061    protected boolean getEncode() {
062        return encode;
063    }
064
065    /**
066     * Creates a new BaseNCodec subclass of type C.
067     *
068     * @return a new BaseNCodec subclass of type C.
069     */
070    protected abstract C newBaseNCodec();
071
072    /**
073     * Sets a BaseNCodec subclass of type C.
074     *
075     * @param baseNCodec a BaseNCodec subclass of type C.
076     * @return {@code this} instance.
077     */
078    public B setBaseNCodec(final C baseNCodec) {
079        this.baseNCodec = baseNCodec != null ? baseNCodec : newBaseNCodec();
080        return asThis();
081    }
082
083    /**
084     * Sets whether we should encode all data read (true), or if false if we should decode.
085     *
086     * @param encode encode or decode.
087     * @return {@code this} instance.
088     */
089    public B setEncode(final boolean encode) {
090        this.encode = encode;
091        return asThis();
092    }
093}