package anastore.proto;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.*;

/**
 * Helpers for dealing with complex data types in the toString and
 * serialization methods of protocol messages.
 */
class Util
{
    private Util()
    {
    }

    /**
     * Add a short summary of a Map<Long, Long> to a string builder.
     */
    public static void summarize(StringBuilder out, Map<Long, Long> map)
    {
        int i = 0;
        for (Map.Entry<Long, Long> entry : map.entrySet()) {
            if (i != 0)
                out.append(',');
            out.append(entry.getKey().toString());
            out.append('@');
            out.append(entry.getValue().toString());
            if (i++ == 5) {
                out.append(",...");
                break;
            }
        }
    }

    /**
     * Write out a Map<Long, Long> using a compact native-type
     * representation.
     */
    public static void writeMapLongLong(ObjectOutputStream s,
                                        Map<Long, Long> map)
        throws IOException
    {
        s.writeInt(map.size());
        for (Map.Entry<Long, Long> entry : map.entrySet()) {
            s.writeLong(entry.getKey());
            s.writeLong(entry.getValue());
        }
    }

    /**
     * Read a map written by writeMapLongLong.
     */
    public static Map<Long, Long> readMapLongLong(ObjectInputStream s)
        throws IOException
    {
        int size = s.readInt();
        Map<Long, Long> map = new HashMap<Long, Long>(size);
        for (int i = 0; i < size; ++i) {
            long k = s.readLong();
            long v = s.readLong();
            map.put(k, v);
        }
        return map;
    }

    /**
     * Add a short summary of a Set<Long> to a string builder.
     */
    public static void summarize(StringBuilder out, Set<Long> set)
    {
        int i = 0;
        for (Long v : set) {
            if (i != 0)
                out.append(',');
            out.append(v.toString());
            if (i++ == 10) {
                out.append(",...");
                break;
            }
        }
    }

    /**
     * Write out a Set<Long> using a compact native-type
     * representation.
     */
    public static void writeSetLong(ObjectOutputStream s,
                                    Set<Long> set)
        throws IOException
    {
        s.writeInt(set.size());
        for (long v : set) {
            s.writeLong(v);
        }
    }

    /**
     * Read a set written by writeSetLong.
     */
    public static Set<Long> readSetLong(ObjectInputStream s)
        throws IOException
    {
        int size = s.readInt();
        Set<Long> set = new HashSet<Long>(size);
        for (int i = 0; i < size; ++i) {
            long v = s.readLong();
            set.add(v);
        }
        return set;
    }
}
