@SuppressWarnings("unchecked") private CompatibilityResult<T> ensureFieldCompatibility( List<Tuple2<TypeSerializer<?>, TypeSerializerConfigSnapshot>> previousSerializersAndConfigs) { TypeSerializer<Object>[] convertSerializers = new TypeSerializer[fieldSerializers.length]; boolean requiresMigration = false; for (int index = 0; index < previousSerializersAndConfigs.size(); index++) { CompatibilityResult<Object> compatResult = resolveFieldCompatibility(previousSerializersAndConfigs, index); if (compatResult.isRequiresMigration()) { requiresMigration = true; if (compatResult.getConvertDeserializer() != null) { convertSerializers[index] = new TypeDeserializerAdapter<>(compatResult.getConvertDeserializer()); } else { return CompatibilityResult.requiresMigration(); } } } return requiresMigration ? createMigrationCompatResult(convertSerializers) : CompatibilityResult.compatible(); }
@Override public CompatibilityResult<T> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { if (configSnapshot instanceof CopyableValueSerializerConfigSnapshot && valueClass.equals(((CopyableValueSerializerConfigSnapshot<?>) configSnapshot).getTypeClass())) { return CompatibilityResult.compatible(); } else { return CompatibilityResult.requiresMigration(); } }
/** * This cannot be removed until {@link TypeSerializerConfigSnapshot} is no longer supported. */ @Override public CompatibilityResult<Lockable<E>> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { // backwards compatibility path CompatibilityResult<E> inputCompatibilityResult = CompatibilityUtil.resolveCompatibilityResult( configSnapshot.restoreSerializer(), UnloadableDummyTypeSerializer.class, configSnapshot, elementSerializer); return (inputCompatibilityResult.isRequiresMigration()) ? CompatibilityResult.requiresMigration() : CompatibilityResult.compatible(); }
@Override public TypeSerializerSchemaCompatibility<T> resolveSchemaCompatibility( TypeSerializer<T> newSerializer) { // in prior versions, the compatibility check was in the serializer itself, so we // delegate this call to the serializer. final CompatibilityResult<T> compatibility = newSerializer.ensureCompatibility(this); return compatibility.isRequiresMigration() ? TypeSerializerSchemaCompatibility.incompatible() : TypeSerializerSchemaCompatibility.compatibleAsIs(); } }
@Override public CompatibilityResult<T> ensureCompatibility(TypeSerializerConfigSnapshot configSnapshot) { // We can not remove this method, as long as we support restoring into CompositeTypeSerializerConfigSnapshot. // Previously (pre 1.8), multiple composite serializers were using this class directly as their snapshot class. if (configSnapshot instanceof ConfigSnapshot) { List<Tuple2<TypeSerializer<?>, TypeSerializerConfigSnapshot>> previousSerializersAndConfigs = ((CompositeTypeSerializerConfigSnapshot) configSnapshot).getNestedSerializersAndConfigs(); if (previousSerializersAndConfigs.size() == fieldSerializers.length) { return ensureFieldCompatibility(previousSerializersAndConfigs); } } return CompatibilityResult.requiresMigration(); }
@Override public CompatibilityResult<Serializable> ensureCompatibility(TypeSerializerConfigSnapshot configSnapshot) { // always assume compatibility since we're just a proxy for migration return CompatibilityResult.compatible(); }
@Override public CompatibilityResult<T> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { if (configSnapshot instanceof WritableSerializerConfigSnapshot && typeClass.equals(((WritableSerializerConfigSnapshot<?>) configSnapshot).getTypeClass())) { return CompatibilityResult.compatible(); } else { return CompatibilityResult.requiresMigration(); } }
newSerializer); if (!initialResult.isRequiresMigration()) { return initialResult; } else { return CompatibilityResult.requiresMigration((TypeSerializer<T>) precedingSerializer); } else { return CompatibilityResult.compatible();
namespaceSerializer); if (keySerializerCompatibility.isRequiresMigration() || namespaceSerializerCompatibility.isRequiresMigration()) { throw new IllegalStateException("Tried to initialize restored TimerService " + "with incompatible serializers than those used to snapshot its state.");
private CompatibilityResult<T> createMigrationCompatResult(TypeSerializer<Object>[] convertSerializers) { PrecomputedParameters precomputed = PrecomputedParameters.precompute(this.precomputed.immutableTargetType, convertSerializers); return CompatibilityResult.requiresMigration(createSerializerInstance(precomputed, convertSerializers)); }
fieldSerializers[i]); if (compatResult.isRequiresMigration()) { requiresMigration = true; if (compatResult.getConvertDeserializer() != null) { convertFieldSerializers[i] = new TypeDeserializerAdapter<>(compatResult.getConvertDeserializer()); } else { return CompatibilityResult.requiresMigration(); return CompatibilityResult.compatible(); } else { return CompatibilityResult.requiresMigration( createSerializerInstance(tupleClass, convertFieldSerializers)); return CompatibilityResult.requiresMigration();
@SuppressWarnings("unchecked") @Override public CompatibilityResult<T> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { if (configSnapshot instanceof ValueSerializerConfigSnapshot) { final ValueSerializerConfigSnapshot<T> config = (ValueSerializerConfigSnapshot<T>) configSnapshot; if (type.equals(config.getTypeClass())) { // currently, simply checking the type of the value class is sufficient; // in the future, if there are more Kryo registrations, we should try to resolve that return CompatibilityResult.compatible(); } } return CompatibilityResult.requiresMigration(); }
/** * This cannot be removed until {@link TypeSerializerConfigSnapshot} is no longer supported. */ @Override public CompatibilityResult<Lockable<E>> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { // backwards compatibility path CompatibilityResult<E> inputCompatibilityResult = CompatibilityUtil.resolveCompatibilityResult( configSnapshot.restoreSerializer(), UnloadableDummyTypeSerializer.class, configSnapshot, elementSerializer); return (inputCompatibilityResult.isRequiresMigration()) ? CompatibilityResult.requiresMigration() : CompatibilityResult.compatible(); }
@Test public void testReconfiguration() { // mock the previous ordering of enum constants to be BAR, PAULA, NATHANIEL PublicEnum[] mockPreviousOrder = {PublicEnum.BAR, PublicEnum.PAULA, PublicEnum.NATHANIEL}; // now, the actual order of FOO, BAR, PETER, NATHANIEL, EMMA, PAULA will be the "new wrong order" EnumSerializer<PublicEnum> serializer = new EnumSerializer<>(PublicEnum.class); // verify that the serializer is first using the "wrong order" (i.e., the initial new configuration) assertEquals(PublicEnum.FOO.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.FOO).intValue()); assertEquals(PublicEnum.BAR.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.BAR).intValue()); assertEquals(PublicEnum.PETER.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.PETER).intValue()); assertEquals(PublicEnum.NATHANIEL.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.NATHANIEL).intValue()); assertEquals(PublicEnum.EMMA.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.EMMA).intValue()); assertEquals(PublicEnum.PAULA.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.PAULA).intValue()); // reconfigure and verify compatibility CompatibilityResult<PublicEnum> compatResult = serializer.ensureCompatibility( new EnumSerializer.EnumSerializerConfigSnapshot<>(PublicEnum.class, mockPreviousOrder)); assertFalse(compatResult.isRequiresMigration()); // after reconfiguration, the order should be first the original BAR, PAULA, NATHANIEL, // followed by the "new enum constants" FOO, PETER, EMMA PublicEnum[] expectedOrder = {PublicEnum.BAR, PublicEnum.PAULA, PublicEnum.NATHANIEL, PublicEnum.FOO, PublicEnum.PETER, PublicEnum.EMMA}; int i = 0; for (PublicEnum constant : expectedOrder) { assertEquals(i, serializer.getValueToOrdinal().get(constant).intValue()); i++; } assertTrue(Arrays.equals(expectedOrder, serializer.getValues())); }
@Override public CompatibilityResult<T> ensureCompatibility(TypeSerializerConfigSnapshot configSnapshot) { if (configSnapshot instanceof ConfigSnapshot) { List<Tuple2<TypeSerializer<?>, TypeSerializerConfigSnapshot>> previousSerializersAndConfigs = ((CompositeTypeSerializerConfigSnapshot) configSnapshot).getNestedSerializersAndConfigs(); if (previousSerializersAndConfigs.size() == fieldSerializers.length) { return ensureFieldCompatibility(previousSerializersAndConfigs); } } return CompatibilityResult.requiresMigration(); }
sharedBufferSerializer); if (!sharedBufCompatResult.isRequiresMigration() && !eventCompatResult.isRequiresMigration()) { return CompatibilityResult.compatible(); } else { if (eventCompatResult.getConvertDeserializer() != null && sharedBufCompatResult.getConvertDeserializer() != null) { return CompatibilityResult.requiresMigration( new NFASerializer<>( new TypeDeserializerAdapter<>(eventCompatResult.getConvertDeserializer()), new TypeDeserializerAdapter<>(sharedBufCompatResult.getConvertDeserializer()))); return CompatibilityResult.requiresMigration();
@Override public CompatibilityResult<Object> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { return compatible ? CompatibilityResult.compatible() : CompatibilityResult.requiresMigration(); } }
/** * This cannot be removed until {@link TypeSerializerConfigSnapshot} is no longer supported. */ @Override public CompatibilityResult<Lockable<E>> ensureCompatibility(TypeSerializerConfigSnapshot<?> configSnapshot) { // backwards compatibility path CompatibilityResult<E> inputCompatibilityResult = CompatibilityUtil.resolveCompatibilityResult( configSnapshot.restoreSerializer(), UnloadableDummyTypeSerializer.class, configSnapshot, elementSerializer); return (inputCompatibilityResult.isRequiresMigration()) ? CompatibilityResult.requiresMigration() : CompatibilityResult.compatible(); }
@Test public void testSerializeReconfiguredEnumSerializer() throws Exception { // mock the previous ordering of enum constants to be BAR, PAULA, NATHANIEL PublicEnum[] mockPreviousOrder = {PublicEnum.BAR, PublicEnum.PAULA, PublicEnum.NATHANIEL}; // now, the actual order of FOO, BAR, PETER, NATHANIEL, EMMA, PAULA will be the "new wrong order" EnumSerializer<PublicEnum> serializer = new EnumSerializer<>(PublicEnum.class); // verify that the serializer is first using the "wrong order" (i.e., the initial new configuration) assertEquals(PublicEnum.FOO.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.FOO).intValue()); assertEquals(PublicEnum.BAR.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.BAR).intValue()); assertEquals(PublicEnum.PETER.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.PETER).intValue()); assertEquals(PublicEnum.NATHANIEL.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.NATHANIEL).intValue()); assertEquals(PublicEnum.EMMA.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.EMMA).intValue()); assertEquals(PublicEnum.PAULA.ordinal(), serializer.getValueToOrdinal().get(PublicEnum.PAULA).intValue()); // reconfigure and verify compatibility CompatibilityResult<PublicEnum> compatResult = serializer.ensureCompatibility( new EnumSerializer.EnumSerializerConfigSnapshot<>(PublicEnum.class, mockPreviousOrder)); assertFalse(compatResult.isRequiresMigration()); // serialize and deserialize again the serializer byte[] serializedSerializer = InstantiationUtil.serializeObject(serializer); serializer = InstantiationUtil.deserializeObject(serializedSerializer, Thread.currentThread().getContextClassLoader()); // verify that after the serializer was read, the reconfigured constant ordering is untouched PublicEnum[] expectedOrder = {PublicEnum.BAR, PublicEnum.PAULA, PublicEnum.NATHANIEL, PublicEnum.FOO, PublicEnum.PETER, PublicEnum.EMMA}; int i = 0; for (PublicEnum constant : expectedOrder) { assertEquals(i, serializer.getValueToOrdinal().get(constant).intValue()); i++; } assertTrue(Arrays.equals(expectedOrder, serializer.getValues())); }
private CompatibilityResult<T> createMigrationCompatResult(TypeSerializer<Object>[] convertSerializers) { PrecomputedParameters precomputed = PrecomputedParameters.precompute(this.precomputed.immutableTargetType, convertSerializers); return CompatibilityResult.requiresMigration(createSerializerInstance(precomputed, convertSerializers)); }