package meerkat.bulletinboard;

import com.google.protobuf.ByteString;
import meerkat.crypto.Digest;
import meerkat.protobuf.BulletinBoardApi.*;

import java.util.Collection;

/**
 * Created by Arbel Deutsch Peled on 01-Mar-16.
 * This interface is used to create checksums of Bulletin Board messages IDs
 * This is useful in comparing database states
 */
public interface Checksum {

    /**
     * Sets the Digest method which is used in creating message IDs from the messages themselves
     * This method must be called with an initialized Digest before calling any methods that receive a parameter of type BulletinBoardMessage
     * @param digest is the Digest that will be used to create message IDs from Bulletin Board Messages
     */
    public void setDigest(Digest digest);

    /**
     * Used to reset the current checksum state
     */
    public void reset();

    /**
     * Update the current checksum with the given ID
     * @param messageID is the message ID to be added
     */
    public void update(MessageID messageID);

    /**
     * Update the current checksum with the given collection of IDs
     * @param messageIDs contains the message IDs
     */
    public void update(Collection<MessageID> messageIDs);

    /**
     * Update the current checksum with the given ID
     * @param messageID is the message ID to be added
     */
    public void update(ByteString messageID);

    /**
     * Update the current checksum with the given ID
     * @param messageID is the message ID to be added
     */
    public void update(byte[] messageID);

    /**
     * Update the current checksum with the message ID of the given message
     * @param bulletinBoardMessage is the message whose ID should be added to the checksum
     * @throws IllegalStateException if a Digest has not been set before calling this method
     */
    public void digestAndUpdate(BulletinBoardMessage bulletinBoardMessage) throws IllegalStateException;


    /**
     * Update the current checksum with the message IDs of the given messages
     * @param bulletinBoardMessages contains the messages whose IDs should be added to the checksum
     * @throws IllegalStateException if a Digest has not been set before calling this method
     */
    public void digestAndUpdate(Collection<BulletinBoardMessage> bulletinBoardMessages) throws IllegalStateException;

    /**
     * Returns the current checksum without changing the checksum state
     * @return the current checksum
     */
    public long getChecksum();

    /**
     * Updates the current checksum with the given ID and returns the resulting checksum
     * The checksum is not reset afterwards
     * @param messageID is the message ID to be added
     * @return the updated checksum
     */
    public long getChecksum(MessageID messageID);

    /**
     * Updates the current checksum with the given ID and returns the resulting checksum
     * The checksum is not reset afterwards
     * @param messageID is the message ID to be added
     * @return the updated checksum
     */
    public long getChecksum(ByteString messageID);

    /**
     * Updates the current checksum with the given ID and returns the resulting checksum
     * The checksum is not reset afterwards
     * @param messageID is the message ID to be added
     * @return the updated checksum
     */
    public long getChecksum(byte[] messageID);

    /**
     * Updates the current checksum with the given IDs and returns the resulting checksum
     * The checksum is not reset afterwards
     * @param messageIDs contains the message IDs to be added
     * @return the updated checksum
     */
    public long getChecksum(Collection<MessageID> messageIDs);

    /**
     * Updates the current checksum with the message ID of the given message
     * The checksum is not reset afterwards
     * @param bulletinBoardMessage is the message whose ID should be added to the checksum
     * @return the updated checksum
     */
    public long digestAndGetChecksum(BulletinBoardMessage bulletinBoardMessage) throws IllegalStateException;

    /**
     * Updates the current checksum with the message IDs of the given messages
     * The checksum is not reset afterwards
     * @param bulletinBoardMessages contains the messages whose IDs should be added to the checksum
     * @return the updated checksum
     */
    public long digestAndGetChecksum(Collection<BulletinBoardMessage> bulletinBoardMessages) throws IllegalStateException;

}
