Каков наилучший способ сериализации иерархий классов в Hazelcast? - PullRequest
1 голос
/ 07 апреля 2020

Я хотел бы сериализовать и кэшировать в Hazelcast @Entity, который имеет двунаправленную связь с другим @ Entity.

Я ищу то, что считается официальной наилучшей практикой в ​​таком сценарии - решение, которое бы :

  1. правильно сериализует иерархию классов, которая содержит, возможно, нулевые ссылки, а также ссылки на наборы и списки
  2. обрабатывает циклы ссылок в графе

Так В первом случае мне удалось реализовать DataSerializable в каждом @Entity моего графа. Я работаю со значениями NULL и множеств следующим образом:

@Override
public void writeData(ObjectDataOutput out) throws IOException {
    out.writeBoolean(certificationNumber != null);
    if (certificationNumber != null)
        out.writeUTF(certificationNumber);
    out.writeShort(getSkills().size());
    for (SkillEntity s: getSkills())
        s.writeData(out);
}


@Override
public void readData(ObjectDataInput in) throws IOException {
    if (in.readBoolean()) {
        certification = new CertificationEntity();
        certification.readData(in);
    }
    short size = in.readShort();
    skills = new HashSet<>();
    for(int i=0; i<size; i++)
        skills.add(in.readObject());
}

Однако нарушение циклов ссылок немного сложнее. Этот поток предлагает:

Я думаю, что он будет основан на ведении локальной карты потоков.

При сериализации вам нужно найти ваш объект для сериализации, уже находящейся на этой карте ... если это так ... вам нужно сериализовать какой-то заполнитель (например, uuid)

Если его нет в этой карте, сгенерируйте заполнитель, поместите его в эту карту и напишите фактический объект, и вы, вероятно, захотите написать заполнитель, чтобы использовать эту информацию при десериализации.

Я думаю, что это должно поместить вы в правильном направлении, но так как я не реализовал это раньше, я не знаю, есть ли здесь какие-то ошибки.

Хотя приведенное выше предложение имеет смысл, я не совсем уверен, как go о том, как это сделать, т. Е. Какой шаблон разработки программного обеспечения применить и как четко отделить мои сущности от логики сериализации c.

Любые указатели?

1 Ответ

0 голосов
/ 08 апреля 2020

Я думаю, что ответ на мой вопрос находится на странице 201 справочника «Mastering Hazelcast 3.9», который можно загрузить с веб-сайта Hazelcast.

Содержимое страницы:

public class PersonKryoSerializer implements StreamSerializer<Person> {
    private static final ThreadLocal<Kryo> kryoThreadLocal
            = new ThreadLocal<Kryo>() {
        @Override
        protected Kryo initialValue() {
            Kryo kryo = new Kryo();
            kryo.register(Person.class);
            return kryo;
        }
    };
    @Override
    public int getTypeId() {
        return 2;
    }
    @Override
    public void write(ObjectDataOutput objectDataOutput, Person product)
            throws IOException {
        Kryo kryo = kryoThreadLocal.get();
        Output output = new Output((OutputStream) objectDataOutput);
        kryo.writeObject(output, product);
        output.flush();
    }
    @Override
    public Person read(ObjectDataInput objectDataInput)
            throws IOException {
        InputStream in = (InputStream) objectDataInput;
        Input input = new Input(in);
        Kryo kryo = kryoThreadLocal.get();
        return kryo.readObject(input, Person.class);
    }
    @Override
    public void destroy() {
    }
}

PersonKryoSerializer относительно прост в реализации. Приятно то, что Kryo заботится об обнаружении циклов и генерирует намного меньше сериализованных данных, чем Java сериализация. Для одного из наших клиентов нам удалось уменьшить размер записей на карте со среднего значения в 15 килобайт, используя сериализацию Java, до среднего значения менее шести килобайт. Когда мы включили сжатие Kryo, нам удалось получить его менее трех килобайт.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...