Move AMQP serializer toward the new common abstract itnerface

Allow unique serializer factories to be created per unique set of
WhiteList / Class Loader pair. Remove default consruction of the
SerializerFactory to force use of the FactoryFactory to get the generic
factory and thus access to it's ClassLoader
This commit is contained in:
Katelyn Baker 2017-08-08 15:35:55 +01:00
parent 9149900938
commit 139eef2ccb
21 changed files with 241 additions and 219 deletions

View File

@ -41,11 +41,17 @@ abstract class AbstractAMQPSerializationScheme : SerializationScheme {
rpcClientSerializerFactory(context) rpcClientSerializerFactory(context)
SerializationContext.UseCase.RPCServer -> SerializationContext.UseCase.RPCServer ->
rpcServerSerializerFactory(context) rpcServerSerializerFactory(context)
else -> SerializerFactory(context.whitelist) // TODO pass class loader also else -> SerializerFactory(context.whitelist, context.deserializationClassLoader)
} }
}.also { registerCustomSerializers(it) } }.also { registerCustomSerializers(it) }
} }
fun getSerializerFactory(): SerializerFactory {
return serializerFactoriesForContexts.computeIfAbsent(Pair(AllWhitelist, deserializationClassLoader)) {
SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
}
}
override fun <T : Any> deserialize(byteSequence: ByteSequence, clazz: Class<T>, context: SerializationContext): T { override fun <T : Any> deserialize(byteSequence: ByteSequence, clazz: Class<T>, context: SerializationContext): T {
val serializerFactory = getSerializerFactory(context) val serializerFactory = getSerializerFactory(context)
return DeserializationInput(serializerFactory).deserialize(byteSequence, clazz) return DeserializationInput(serializerFactory).deserialize(byteSequence, clazz)

View File

@ -12,6 +12,7 @@ import net.corda.nodeapi.internal.serialization.amqp.AmqpHeaderV1_0
import net.corda.nodeapi.internal.serialization.amqp.DeserializationInput import net.corda.nodeapi.internal.serialization.amqp.DeserializationInput
import net.corda.nodeapi.internal.serialization.amqp.SerializationOutput import net.corda.nodeapi.internal.serialization.amqp.SerializationOutput
import net.corda.nodeapi.internal.serialization.amqp.SerializerFactory import net.corda.nodeapi.internal.serialization.amqp.SerializerFactory
import net.corda.nodeapi.internal.serialization.amqp.SerializerFactoryFactory
/** /**
* This [Kryo] custom [Serializer] switches the object graph of anything annotated with `@CordaSerializable` * This [Kryo] custom [Serializer] switches the object graph of anything annotated with `@CordaSerializable`
@ -34,4 +35,4 @@ class KryoAMQPSerializer(val serializationFactory: SerializationFactory, val ser
input.readBytes(allBytes, peekedBytes.size, size - peekedBytes.size) input.readBytes(allBytes, peekedBytes.size, size - peekedBytes.size)
return serializationFactory.deserialize(allBytes.sequence(), type, serializationContext) return serializationFactory.deserialize(allBytes.sequence(), type, serializationContext)
} }
} }

View File

@ -151,8 +151,10 @@ abstract class CustomSerializer<T> : AMQPSerializer<T> {
* @param unmake A lambda that extracts the string value for an instance, that defaults to the [toString] method. * @param unmake A lambda that extracts the string value for an instance, that defaults to the [toString] method.
*/ */
abstract class ToString<T>(clazz: Class<T>, withInheritance: Boolean = false, abstract class ToString<T>(clazz: Class<T>, withInheritance: Boolean = false,
private val maker: (String) -> T = clazz.getConstructor(String::class.java).let { `constructor` -> { string -> `constructor`.newInstance(string) } }, private val maker: (String) -> T = clazz.getConstructor(String::class.java).let {
private val unmaker: (T) -> String = { obj -> obj.toString() }) : Proxy<T, String>(clazz, String::class.java, /* Unused */ SerializerFactory(), withInheritance) { `constructor` -> { string -> `constructor`.newInstance(string) }
},
private val unmaker: (T) -> String = { obj -> obj.toString() }) : Proxy<T, String>(clazz, String::class.java, /* Unused */ SerializerFactoryFactory.get(), withInheritance) {
override val additionalSerializers: Iterable<CustomSerializer<out Any>> = emptyList() override val additionalSerializers: Iterable<CustomSerializer<out Any>> = emptyList()

View File

@ -20,7 +20,7 @@ data class ObjectAndEnvelope<out T>(val obj: T, val envelope: Envelope)
* @param serializerFactory This is the factory for [AMQPSerializer] instances and can be shared across multiple * @param serializerFactory This is the factory for [AMQPSerializer] instances and can be shared across multiple
* instances and threads. * instances and threads.
*/ */
class DeserializationInput(internal val serializerFactory: SerializerFactory = SerializerFactory()) { class DeserializationInput(internal val serializerFactory: SerializerFactory = SerializerFactoryFactory.get()) {
// TODO: we're not supporting object refs yet // TODO: we're not supporting object refs yet
private val objectHistory: MutableList<Any> = ArrayList() private val objectHistory: MutableList<Any> = ArrayList()

View File

@ -14,7 +14,7 @@ import kotlin.collections.LinkedHashSet
* @param serializerFactory This is the factory for [AMQPSerializer] instances and can be shared across multiple * @param serializerFactory This is the factory for [AMQPSerializer] instances and can be shared across multiple
* instances and threads. * instances and threads.
*/ */
open class SerializationOutput(internal val serializerFactory: SerializerFactory = SerializerFactory()) { open class SerializationOutput(internal val serializerFactory: SerializerFactory = SerializerFactoryFactory.get()) {
// TODO: we're not supporting object refs yet // TODO: we're not supporting object refs yet
private val objectHistory: MutableMap<Any, Int> = IdentityHashMap() private val objectHistory: MutableMap<Any, Int> = IdentityHashMap()
private val serializerHistory: MutableSet<AMQPSerializer<*>> = LinkedHashSet() private val serializerHistory: MutableSet<AMQPSerializer<*>> = LinkedHashSet()

View File

@ -44,11 +44,13 @@ import javax.annotation.concurrent.ThreadSafe
// TODO: need to rethink matching of constructor to properties in relation to implementing interfaces and needing those properties etc. // TODO: need to rethink matching of constructor to properties in relation to implementing interfaces and needing those properties etc.
// TODO: need to support super classes as well as interfaces with our current code base... what's involved? If we continue to ban, what is the impact? // TODO: need to support super classes as well as interfaces with our current code base... what's involved? If we continue to ban, what is the impact?
@ThreadSafe @ThreadSafe
class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) { class SerializerFactory(val whitelist: ClassWhitelist, cl : ClassLoader) {
private val serializersByType = ConcurrentHashMap<Type, AMQPSerializer<Any>>() private val serializersByType = ConcurrentHashMap<Type, AMQPSerializer<Any>>()
private val serializersByDescriptor = ConcurrentHashMap<Any, AMQPSerializer<Any>>() private val serializersByDescriptor = ConcurrentHashMap<Any, AMQPSerializer<Any>>()
private val customSerializers = CopyOnWriteArrayList<CustomSerializer<out Any>>() private val customSerializers = CopyOnWriteArrayList<CustomSerializer<out Any>>()
private val classCarpenter = ClassCarpenter() private val classCarpenter = ClassCarpenter(cl)
val classloader : ClassLoader
get() = classCarpenter.classloader
/** /**
* Look up, and manufacture if necessary, a serializer for the given type. * Look up, and manufacture if necessary, a serializer for the given type.
@ -176,15 +178,18 @@ class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) {
} }
} }
/**
* Iterate over an AMQP schema, for each type ascertain weather it's on ClassPath of [classloader] amd
* if not use the [ClassCarpenter] to generate a class to use in it's place
*/
private fun processSchema(schema: Schema, sentinal: Boolean = false) { private fun processSchema(schema: Schema, sentinal: Boolean = false) {
val carpenterSchemas = CarpenterSchemas.newInstance() val carpenterSchemas = CarpenterSchemas.newInstance()
for (typeNotation in schema.types) { for (typeNotation in schema.types) {
try { try {
processSchemaEntry(typeNotation, classCarpenter.classloader) }
} catch (e: ClassNotFoundException) { catch (e: ClassNotFoundException) {
if (sentinal || (typeNotation !is CompositeType)) throw e if (sentinal || (typeNotation !is CompositeType)) throw e
typeNotation.carpenterSchema( typeNotation.carpenterSchema(classloader, carpenterSchemas = carpenterSchemas)
classLoaders = listOf(classCarpenter.classloader), carpenterSchemas = carpenterSchemas)
} }
} }
@ -195,10 +200,9 @@ class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) {
} }
} }
private fun processSchemaEntry(typeNotation: TypeNotation, private fun processSchemaEntry(typeNotation: TypeNotation) {
cl: ClassLoader = DeserializedParameterizedType::class.java.classLoader) {
when (typeNotation) { when (typeNotation) {
is CompositeType -> processCompositeType(typeNotation, cl) // java.lang.Class (whether a class or interface) is CompositeType -> processCompositeType(typeNotation) // java.lang.Class (whether a class or interface)
is RestrictedType -> processRestrictedType(typeNotation) // Collection / Map, possibly with generics is RestrictedType -> processRestrictedType(typeNotation) // Collection / Map, possibly with generics
} }
} }
@ -210,7 +214,6 @@ class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) {
} }
private fun processCompositeType(typeNotation: CompositeType, private fun processCompositeType(typeNotation: CompositeType,
cl: ClassLoader = DeserializedParameterizedType::class.java.classLoader) {
// TODO: class loader logic, and compare the schema. // TODO: class loader logic, and compare the schema.
val type = typeForName(typeNotation.name, cl) val type = typeForName(typeNotation.name, cl)
get(type.asClass() ?: throw NotSerializableException("Unable to build composite type for $type"), type) get(type.asClass() ?: throw NotSerializableException("Unable to build composite type for $type"), type)
@ -322,11 +325,9 @@ class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) {
else -> throw NotSerializableException("Unable to render type $type to a string.") else -> throw NotSerializableException("Unable to render type $type to a string.")
} }
private fun typeForName( private fun typeForName(name: String, classloader: ClassLoader): Type {
name: String,
cl: ClassLoader = DeserializedParameterizedType::class.java.classLoader): Type {
return if (name.endsWith("[]")) { return if (name.endsWith("[]")) {
val elementType = typeForName(name.substring(0, name.lastIndex - 1)) val elementType = typeForName(name.substring(0, name.lastIndex - 1), classloader)
if (elementType is ParameterizedType || elementType is GenericArrayType) { if (elementType is ParameterizedType || elementType is GenericArrayType) {
DeserializedGenericArrayType(elementType) DeserializedGenericArrayType(elementType)
} else if (elementType is Class<*>) { } else if (elementType is Class<*>) {
@ -349,7 +350,7 @@ class SerializerFactory(val whitelist: ClassWhitelist = AllWhitelist) {
else -> throw NotSerializableException("Not able to deserialize array type: $name") else -> throw NotSerializableException("Not able to deserialize array type: $name")
} }
} else { } else {
DeserializedParameterizedType.make(name, cl) DeserializedParameterizedType.make(name, classloader)
} }
} }
} }

View File

@ -0,0 +1,22 @@
package net.corda.nodeapi.internal.serialization.amqp
import net.corda.core.serialization.SerializationContext
import net.corda.core.serialization.ClassWhitelist
import net.corda.nodeapi.internal.serialization.AllWhitelist
/**
* Factory singleton that maps unique Serializer Factories from a pair of WhitleList and ClassLoader
*/
object SerializerFactoryFactory {
val factories : MutableMap<Pair<ClassWhitelist, ClassLoader>, SerializerFactory> = mutableMapOf()
fun get(context: SerializationContext) : SerializerFactory =
factories.computeIfAbsent(Pair(context.whitelist, context.deserializationClassLoader)) {
SerializerFactory(context.whitelist, context.deserializationClassLoader)
}
fun get() : SerializerFactory =
factories.computeIfAbsent(Pair(AllWhitelist, ClassLoader.getSystemClassLoader())) {
SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
}
}

View File

@ -4,13 +4,11 @@ import net.corda.nodeapi.internal.serialization.amqp.CompositeType
import net.corda.nodeapi.internal.serialization.amqp.Field as AMQPField import net.corda.nodeapi.internal.serialization.amqp.Field as AMQPField
import net.corda.nodeapi.internal.serialization.amqp.Schema as AMQPSchema import net.corda.nodeapi.internal.serialization.amqp.Schema as AMQPSchema
fun AMQPSchema.carpenterSchema( fun AMQPSchema.carpenterSchema(classloader: ClassLoader) : CarpenterSchemas {
loaders: List<ClassLoader> = listOf<ClassLoader>(ClassLoader.getSystemClassLoader()))
: CarpenterSchemas {
val rtn = CarpenterSchemas.newInstance() val rtn = CarpenterSchemas.newInstance()
types.filterIsInstance<CompositeType>().forEach { types.filterIsInstance<CompositeType>().forEach {
it.carpenterSchema(classLoaders = loaders, carpenterSchemas = rtn) it.carpenterSchema(classloader, carpenterSchemas = rtn)
} }
return rtn return rtn
@ -19,10 +17,9 @@ fun AMQPSchema.carpenterSchema(
/** /**
* if we can load the class then we MUST know about all of it's composite elements * if we can load the class then we MUST know about all of it's composite elements
*/ */
private fun CompositeType.validatePropertyTypes( private fun CompositeType.validatePropertyTypes(classloader: ClassLoader) {
classLoaders: List<ClassLoader> = listOf<ClassLoader>(ClassLoader.getSystemClassLoader())) {
fields.forEach { fields.forEach {
if (!it.validateType(classLoaders)) throw UncarpentableException(name, it.name, it.type) if (!it.validateType(classloader)) throw UncarpentableException(name, it.name, it.type)
} }
} }
@ -34,24 +31,21 @@ fun AMQPField.typeAsString() = if (type == "*") requires[0] else type
* b) add the class to the dependency tree in [carpenterSchemas] if it cannot be instantiated * b) add the class to the dependency tree in [carpenterSchemas] if it cannot be instantiated
* at this time * at this time
* *
* @param classLoaders list of classLoaders, defaulting toe the system class loader, that might * @param classloader the class loader provided dby the [SerializationContext]
* be used to load objects
* @param carpenterSchemas structure that holds the dependency tree and list of classes that * @param carpenterSchemas structure that holds the dependency tree and list of classes that
* need constructing * need constructing
* @param force by default a schema is not added to [carpenterSchemas] if it already exists * @param force by default a schema is not added to [carpenterSchemas] if it already exists
* on the class path. For testing purposes schema generation can be forced * on the class path. For testing purposes schema generation can be forced
*/ */
fun CompositeType.carpenterSchema( fun CompositeType.carpenterSchema(classloader: ClassLoader,
classLoaders: List<ClassLoader> = listOf<ClassLoader>(ClassLoader.getSystemClassLoader()), carpenterSchemas: CarpenterSchemas,
carpenterSchemas: CarpenterSchemas, force: Boolean = false) {
force: Boolean = false) { if (classloader.exists(name)) {
if (classLoaders.exists(name)) { validatePropertyTypes(classloader)
validatePropertyTypes(classLoaders)
if (!force) return if (!force) return
} }
val providesList = mutableListOf<Class<*>>() val providesList = mutableListOf<Class<*>>()
var isInterface = false var isInterface = false
var isCreatable = true var isCreatable = true
@ -62,7 +56,7 @@ fun CompositeType.carpenterSchema(
} }
try { try {
providesList.add(classLoaders.loadIfExists(it)) providesList.add(classloader.loadClass(it))
} catch (e: ClassNotFoundException) { } catch (e: ClassNotFoundException) {
carpenterSchemas.addDepPair(this, name, it) carpenterSchemas.addDepPair(this, name, it)
isCreatable = false isCreatable = false
@ -73,7 +67,7 @@ fun CompositeType.carpenterSchema(
fields.forEach { fields.forEach {
try { try {
m[it.name] = FieldFactory.newInstance(it.mandatory, it.name, it.getTypeAsClass(classLoaders)) m[it.name] = FieldFactory.newInstance(it.mandatory, it.name, it.getTypeAsClass(classloader))
} catch (e: ClassNotFoundException) { } catch (e: ClassNotFoundException) {
carpenterSchemas.addDepPair(this, name, it.typeAsString()) carpenterSchemas.addDepPair(this, name, it.typeAsString())
isCreatable = false isCreatable = false
@ -110,33 +104,18 @@ val typeStrToType: Map<Pair<String, Boolean>, Class<out Any?>> = mapOf(
Pair("byte", false) to Byte::class.javaObjectType Pair("byte", false) to Byte::class.javaObjectType
) )
fun AMQPField.getTypeAsClass( fun AMQPField.getTypeAsClass(classloader: ClassLoader) = typeStrToType[Pair(type, mandatory)] ?: when (type) {
classLoaders: List<ClassLoader> = listOf<ClassLoader>(ClassLoader.getSystemClassLoader())
) = typeStrToType[Pair(type, mandatory)] ?: when (type) {
"string" -> String::class.java "string" -> String::class.java
"*" -> classLoaders.loadIfExists(requires[0]) "*" -> classloader.loadClass(requires[0])
else -> classLoaders.loadIfExists(type) else -> classloader.loadClass(type)
} }
fun AMQPField.validateType( fun AMQPField.validateType(classloader: ClassLoader) = when (type) {
classLoaders: List<ClassLoader> = listOf<ClassLoader>(ClassLoader.getSystemClassLoader())
) = when (type) {
"byte", "int", "string", "short", "long", "char", "boolean", "double", "float" -> true "byte", "int", "string", "short", "long", "char", "boolean", "double", "float" -> true
"*" -> classLoaders.exists(requires[0]) "*" -> classloader.exists(requires[0])
else -> classLoaders.exists(type) else -> classloader.exists(type)
} }
private fun List<ClassLoader>.exists(clazz: String) = this.find { private fun ClassLoader.exists(clazz: String) = run {
try { it.loadClass(clazz); true } catch (e: ClassNotFoundException) { false } try { this.loadClass(clazz); true } catch (e: ClassNotFoundException) { false } }
} != null
private fun List<ClassLoader>.loadIfExists(clazz: String): Class<*> {
this.forEach {
try {
return it.loadClass(clazz)
} catch (e: ClassNotFoundException) {
return@forEach
}
}
throw ClassNotFoundException(clazz)
}

View File

@ -18,7 +18,8 @@ interface SimpleFieldAccess {
operator fun get(name: String): Any? operator fun get(name: String): Any?
} }
class CarpenterClassLoader : ClassLoader(Thread.currentThread().contextClassLoader) { class CarpenterClassLoader (parentClassLoader: ClassLoader = Thread.currentThread().contextClassLoader) :
ClassLoader(parentClassLoader) {
fun load(name: String, bytes: ByteArray) = defineClass(name, bytes, 0, bytes.size) fun load(name: String, bytes: ByteArray) = defineClass(name, bytes, 0, bytes.size)
} }
@ -66,14 +67,14 @@ class CarpenterClassLoader : ClassLoader(Thread.currentThread().contextClassLoad
* *
* Equals/hashCode methods are not yet supported. * Equals/hashCode methods are not yet supported.
*/ */
class ClassCarpenter { class ClassCarpenter(cl: ClassLoader = Thread.currentThread().contextClassLoader) {
// TODO: Generics. // TODO: Generics.
// TODO: Sandbox the generated code when a security manager is in use. // TODO: Sandbox the generated code when a security manager is in use.
// TODO: Generate equals/hashCode. // TODO: Generate equals/hashCode.
// TODO: Support annotations. // TODO: Support annotations.
// TODO: isFoo getter patterns for booleans (this is what Kotlin generates) // TODO: isFoo getter patterns for booleans (this is what Kotlin generates)
val classloader = CarpenterClassLoader() val classloader = CarpenterClassLoader(cl)
private val _loaded = HashMap<String, Class<*>>() private val _loaded = HashMap<String, Class<*>>()
private val String.jvm: String get() = replace(".", "/") private val String.jvm: String get() = replace(".", "/")

View File

@ -73,9 +73,7 @@ abstract class MetaCarpenterBase (val schemas : CarpenterSchemas, val cc : Class
// we're out of blockers so we can now create the type // we're out of blockers so we can now create the type
if (schemas.dependencies[dependent]?.second?.isEmpty() ?: false) { if (schemas.dependencies[dependent]?.second?.isEmpty() ?: false) {
(schemas.dependencies.remove (dependent)?.first as CompositeType).carpenterSchema ( (schemas.dependencies.remove (dependent)?.first as CompositeType).carpenterSchema (
classLoaders = listOf<ClassLoader> ( classloader = cc.classloader,
ClassLoader.getSystemClassLoader(),
cc.classloader),
carpenterSchemas = schemas) carpenterSchemas = schemas)
} }
} }

View File

@ -4,7 +4,7 @@ import org.apache.qpid.proton.codec.Data
class TestSerializationOutput( class TestSerializationOutput(
private val verbose: Boolean, private val verbose: Boolean,
serializerFactory: SerializerFactory = SerializerFactory()) : SerializationOutput(serializerFactory) { serializerFactory: SerializerFactory = SerializerFactoryFactory.get()) : SerializationOutput(serializerFactory) {
override fun writeSchema(schema: Schema, data: Data) { override fun writeSchema(schema: Schema, data: Data) {
if (verbose) println(schema) if (verbose) println(schema)

View File

@ -18,7 +18,7 @@ class DeserializeAndReturnEnvelopeTests {
val a = A(10, "20") val a = A(10, "20")
val factory = SerializerFactory() val factory = SerializerFactoryFactory.get()
fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz) fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz)
val obj = DeserializationInput(factory).deserializeAndReturnEnvelope(serialise(a)) val obj = DeserializationInput(factory).deserializeAndReturnEnvelope(serialise(a))
@ -34,7 +34,7 @@ class DeserializeAndReturnEnvelopeTests {
val b = B(A(10, "20"), 30.0F) val b = B(A(10, "20"), 30.0F)
val factory = SerializerFactory() val factory = SerializerFactoryFactory.get()
fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz) fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz)
val obj = DeserializationInput(factory).deserializeAndReturnEnvelope(serialise(b)) val obj = DeserializationInput(factory).deserializeAndReturnEnvelope(serialise(b))

View File

@ -8,7 +8,7 @@ import net.corda.nodeapi.internal.serialization.carpenter.*
// those classes don't exist within the system's Class Loader the deserialiser will be forced to carpent // those classes don't exist within the system's Class Loader the deserialiser will be forced to carpent
// versions of them up using its own internal class carpenter (each carpenter houses it's own loader). This // versions of them up using its own internal class carpenter (each carpenter houses it's own loader). This
// replicates the situation where a receiver doesn't have some or all elements of a schema present on it's classpath // replicates the situation where a receiver doesn't have some or all elements of a schema present on it's classpath
class DeserializeNeedingCarpentrySimpleTypesTest { class DeserializeNeedingCarpentrySimpleTypesTest : AmqpCarpenterBase() {
companion object { companion object {
/** /**
* If you want to see the schema encoded into the envelope after serialisation change this to true * If you want to see the schema encoded into the envelope after serialisation change this to true
@ -21,7 +21,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleInt() { fun singleInt() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"int" to NonNullableField(Integer::class.javaPrimitiveType!!) "int" to NonNullableField(Integer::class.javaPrimitiveType!!)
))) )))
@ -41,7 +41,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleIntNullable() { fun singleIntNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"int" to NullableField(Integer::class.java) "int" to NullableField(Integer::class.java)
))) )))
@ -57,7 +57,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleIntNullableNull() { fun singleIntNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"int" to NullableField(Integer::class.java) "int" to NullableField(Integer::class.java)
))) )))
@ -73,7 +73,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleChar() { fun singleChar() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"char" to NonNullableField(Character::class.javaPrimitiveType!!) "char" to NonNullableField(Character::class.javaPrimitiveType!!)
))) )))
@ -86,7 +86,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleCharNullable() { fun singleCharNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"char" to NullableField(Character::class.javaObjectType) "char" to NullableField(Character::class.javaObjectType)
))) )))
@ -99,7 +99,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleCharNullableNull() { fun singleCharNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"char" to NullableField(java.lang.Character::class.java) "char" to NullableField(java.lang.Character::class.java)
))) )))
@ -112,7 +112,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleLong() { fun singleLong() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"long" to NonNullableField(Long::class.javaPrimitiveType!!) "long" to NonNullableField(Long::class.javaPrimitiveType!!)
))) )))
@ -126,7 +126,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleLongNullable() { fun singleLongNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"long" to NullableField(Long::class.javaObjectType) "long" to NullableField(Long::class.javaObjectType)
))) )))
@ -140,7 +140,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleLongNullableNull() { fun singleLongNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"long" to NullableField(Long::class.javaObjectType) "long" to NullableField(Long::class.javaObjectType)
))) )))
@ -153,7 +153,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleBoolean() { fun singleBoolean() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"boolean" to NonNullableField(Boolean::class.javaPrimitiveType!!) "boolean" to NonNullableField(Boolean::class.javaPrimitiveType!!)
))) )))
@ -166,7 +166,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleBooleanNullable() { fun singleBooleanNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"boolean" to NullableField(Boolean::class.javaObjectType) "boolean" to NullableField(Boolean::class.javaObjectType)
))) )))
@ -179,7 +179,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleBooleanNullableNull() { fun singleBooleanNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"boolean" to NullableField(Boolean::class.javaObjectType) "boolean" to NullableField(Boolean::class.javaObjectType)
))) )))
@ -192,7 +192,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleDouble() { fun singleDouble() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"double" to NonNullableField(Double::class.javaPrimitiveType!!) "double" to NonNullableField(Double::class.javaPrimitiveType!!)
))) )))
@ -205,7 +205,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleDoubleNullable() { fun singleDoubleNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"double" to NullableField(Double::class.javaObjectType) "double" to NullableField(Double::class.javaObjectType)
))) )))
@ -218,7 +218,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleDoubleNullableNull() { fun singleDoubleNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"double" to NullableField(Double::class.javaObjectType) "double" to NullableField(Double::class.javaObjectType)
))) )))
@ -231,7 +231,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleShort() { fun singleShort() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"short" to NonNullableField(Short::class.javaPrimitiveType!!) "short" to NonNullableField(Short::class.javaPrimitiveType!!)
))) )))
@ -244,7 +244,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleShortNullable() { fun singleShortNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"short" to NullableField(Short::class.javaObjectType) "short" to NullableField(Short::class.javaObjectType)
))) )))
@ -257,7 +257,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleShortNullableNull() { fun singleShortNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"short" to NullableField(Short::class.javaObjectType) "short" to NullableField(Short::class.javaObjectType)
))) )))
@ -270,7 +270,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleFloat() { fun singleFloat() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"float" to NonNullableField(Float::class.javaPrimitiveType!!) "float" to NonNullableField(Float::class.javaPrimitiveType!!)
))) )))
@ -283,7 +283,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleFloatNullable() { fun singleFloatNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"float" to NullableField(Float::class.javaObjectType) "float" to NullableField(Float::class.javaObjectType)
))) )))
@ -296,7 +296,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleFloatNullableNull() { fun singleFloatNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"float" to NullableField(Float::class.javaObjectType) "float" to NullableField(Float::class.javaObjectType)
))) )))
@ -309,7 +309,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleByte() { fun singleByte() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"byte" to NonNullableField(Byte::class.javaPrimitiveType!!) "byte" to NonNullableField(Byte::class.javaPrimitiveType!!)
))) )))
@ -324,7 +324,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleByteNullable() { fun singleByteNullable() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"byte" to NullableField(Byte::class.javaObjectType) "byte" to NullableField(Byte::class.javaObjectType)
))) )))
@ -339,7 +339,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun singleByteNullableNull() { fun singleByteNullableNull() {
val clazz = ClassCarpenter().build(ClassSchema("single", mapOf( val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf(
"byte" to NullableField(Byte::class.javaObjectType) "byte" to NullableField(Byte::class.javaObjectType)
))) )))
@ -353,11 +353,10 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun simpleTypeKnownInterface() { fun simpleTypeKnownInterface() {
val clazz = ClassCarpenter().build (ClassSchema( val clazz = ClassCarpenter().build (ClassSchema(
"oneType", mapOf("name" to NonNullableField(String::class.java)), testName(), mapOf("name" to NonNullableField(String::class.java)),
interfaces = listOf (I::class.java))) interfaces = listOf (I::class.java)))
val testVal = "Some Person" val testVal = "Some Person"
val classInstance = clazz.constructors[0].newInstance(testVal) val classInstance = clazz.constructors[0].newInstance(testVal)
val serialisedBytes = TestSerializationOutput(VERBOSE, sf).serialize(classInstance) val serialisedBytes = TestSerializationOutput(VERBOSE, sf).serialize(classInstance)
val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes) val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes)
@ -368,7 +367,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
@Test @Test
fun manyTypes() { fun manyTypes() {
val manyClass = ClassCarpenter().build (ClassSchema("many", mapOf( val manyClass = ClassCarpenter().build (ClassSchema(testName(), mapOf(
"intA" to NonNullableField (Int::class.java), "intA" to NonNullableField (Int::class.java),
"intB" to NullableField (Integer::class.java), "intB" to NullableField (Integer::class.java),
"intC" to NullableField (Integer::class.java), "intC" to NullableField (Integer::class.java),
@ -397,7 +396,7 @@ class DeserializeNeedingCarpentrySimpleTypesTest {
"byteB" to NullableField (Byte::class.javaObjectType), "byteB" to NullableField (Byte::class.javaObjectType),
"byteC" to NullableField (Byte::class.javaObjectType)))) "byteC" to NullableField (Byte::class.javaObjectType))))
val serialisedBytes = TestSerializationOutput(VERBOSE, sf).serialize( val serialisedBytes = TestSerializationOutput(VERBOSE, factory).serialize(
manyClass.constructors.first().newInstance( manyClass.constructors.first().newInstance(
1, 2, null, 1, 2, null,
"a", "b", null, "a", "b", null,

View File

@ -3,22 +3,21 @@ package net.corda.nodeapi.internal.serialization.amqp
import org.junit.Test import org.junit.Test
import kotlin.test.* import kotlin.test.*
import net.corda.nodeapi.internal.serialization.carpenter.* import net.corda.nodeapi.internal.serialization.carpenter.*
import net.corda.nodeapi.internal.serialization.AllWhitelist
interface I { interface I {
fun getName() : String fun getName() : String
} }
/** // These tests work by having the class carpenter build the classes we serialise and then deserialise them
* These tests work by having the class carpenter build the classes we serialise and then deserialise them // within the context of a second serialiser factory. The second factory is required as the first, having
* within the context of a second serialiser factory. The second factory is required as the first, having // been used to serialise the class, will have cached a copy of the class and will thus bypass the need
* been used to serialise the class, will have cached a copy of the class and will thus bypass the need // to pull it out of the class loader.
* to pull it out of the class loader. //
* // However, those classes don't exist within the system's Class Loader and thus the deserialiser will be forced
* However, those classes don't exist within the system's Class Loader and thus the deserialiser will be forced // to carpent versions of them up using its own internal class carpenter (each carpenter houses it's own loader). This
* to carpent versions of them up using its own internal class carpenter (each carpenter houses it's own loader). This // replicates the situation where a receiver doesn't have some or all elements of a schema present on it's classpath
* replicates the situation where a receiver doesn't have some or all elements of a schema present on it's classpath class DeserializeNeedingCarpentryTests : AmqpCarpenterBase() {
*/
class DeserializeNeedingCarpentryTests {
companion object { companion object {
/** /**
* If you want to see the schema encoded into the envelope after serialisation change this to true * If you want to see the schema encoded into the envelope after serialisation change this to true
@ -32,7 +31,7 @@ class DeserializeNeedingCarpentryTests {
@Test @Test
fun verySimpleType() { fun verySimpleType() {
val testVal = 10 val testVal = 10
val clazz = ClassCarpenter().build(ClassSchema("oneType", mapOf("a" to NonNullableField(Int::class.java)))) val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf("a" to NonNullableField(Int::class.java))))
val classInstance = clazz.constructors[0].newInstance(testVal) val classInstance = clazz.constructors[0].newInstance(testVal)
val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance) val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance)
@ -66,16 +65,20 @@ class DeserializeNeedingCarpentryTests {
val testValA = 10 val testValA = 10
val testValB = 20 val testValB = 20
val testValC = 20 val testValC = 20
val clazz = ClassCarpenter().build(ClassSchema("oneType", mapOf("a" to NonNullableField(Int::class.java)))) val clazz = ClassCarpenter().build(ClassSchema("${testName()}_clazz",
mapOf("a" to NonNullableField(Int::class.java))))
val concreteA = clazz.constructors[0].newInstance(testValA) val concreteA = clazz.constructors[0].newInstance(testValA)
val concreteB = clazz.constructors[0].newInstance(testValB) val concreteB = clazz.constructors[0].newInstance(testValB)
val concreteC = clazz.constructors[0].newInstance(testValC) val concreteC = clazz.constructors[0].newInstance(testValC)
val deserialisedA = DeserializationInput(sf2).deserialize(TestSerializationOutput(VERBOSE, sf1).serialize(concreteA)) val deserialisedA = DeserializationInput(sf2).deserialize(
TestSerializationOutput(VERBOSE, sf1).serialize(concreteA))
assertEquals (testValA, deserialisedA::class.java.getMethod("getA").invoke(deserialisedA)) assertEquals (testValA, deserialisedA::class.java.getMethod("getA").invoke(deserialisedA))
val deserialisedB = DeserializationInput(sf2).deserialize(TestSerializationOutput(VERBOSE, sf1).serialize(concreteB)) val deserialisedB = DeserializationInput(sf2).deserialize(
TestSerializationOutput(VERBOSE, sf1).serialize(concreteB))
assertEquals (testValB, deserialisedA::class.java.getMethod("getA").invoke(deserialisedB)) assertEquals (testValB, deserialisedA::class.java.getMethod("getA").invoke(deserialisedB))
assertEquals (deserialisedA::class.java, deserialisedB::class.java) assertEquals (deserialisedA::class.java, deserialisedB::class.java)
@ -84,8 +87,10 @@ class DeserializeNeedingCarpentryTests {
// won't already exist and it will be carpented a second time showing that when A and B are the // won't already exist and it will be carpented a second time showing that when A and B are the
// same underlying class that we didn't create a second instance of the class with the // same underlying class that we didn't create a second instance of the class with the
// second deserialisation // second deserialisation
val lsf = SerializerFactory() val lfactory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
val deserialisedC = DeserializationInput(lsf).deserialize(TestSerializationOutput(VERBOSE, lsf).serialize(concreteC)) val deserialisedC = DeserializationInput(lfactory).deserialize(
TestSerializationOutput(VERBOSE, lfactory).serialize(concreteC))
assertEquals (testValC, deserialisedC::class.java.getMethod("getA").invoke(deserialisedC)) assertEquals (testValC, deserialisedC::class.java.getMethod("getA").invoke(deserialisedC))
assertNotEquals (deserialisedA::class.java, deserialisedC::class.java) assertNotEquals (deserialisedA::class.java, deserialisedC::class.java)
assertNotEquals (deserialisedB::class.java, deserialisedC::class.java) assertNotEquals (deserialisedB::class.java, deserialisedC::class.java)
@ -94,7 +99,7 @@ class DeserializeNeedingCarpentryTests {
@Test @Test
fun simpleTypeKnownInterface() { fun simpleTypeKnownInterface() {
val clazz = ClassCarpenter().build (ClassSchema( val clazz = ClassCarpenter().build (ClassSchema(
"oneType", mapOf("name" to NonNullableField(String::class.java)), testName(), mapOf("name" to NonNullableField(String::class.java)),
interfaces = listOf (I::class.java))) interfaces = listOf (I::class.java)))
val testVal = "Some Person" val testVal = "Some Person"
val classInstance = clazz.constructors[0].newInstance(testVal) val classInstance = clazz.constructors[0].newInstance(testVal)
@ -108,7 +113,7 @@ class DeserializeNeedingCarpentryTests {
@Test @Test
fun arrayOfTypes() { fun arrayOfTypes() {
val clazz = ClassCarpenter().build(ClassSchema("oneType", mapOf("a" to NonNullableField(Int::class.java)))) val clazz = ClassCarpenter().build(ClassSchema(testName(), mapOf("a" to NonNullableField(Int::class.java))))
data class Outer (val a : Array<Any>) data class Outer (val a : Array<Any>)
@ -142,8 +147,8 @@ class DeserializeNeedingCarpentryTests {
fun reusedClasses() { fun reusedClasses() {
val cc = ClassCarpenter() val cc = ClassCarpenter()
val innerType = cc.build(ClassSchema("inner", mapOf("a" to NonNullableField(Int::class.java)))) val innerType = cc.build(ClassSchema("${testName()}.inner", mapOf("a" to NonNullableField(Int::class.java))))
val outerType = cc.build(ClassSchema("outer", mapOf("a" to NonNullableField(innerType)))) val outerType = cc.build(ClassSchema("${testName()}.outer", mapOf("a" to NonNullableField(innerType))))
val inner = innerType.constructors[0].newInstance(1) val inner = innerType.constructors[0].newInstance(1)
val outer = outerType.constructors[0].newInstance(innerType.constructors[0].newInstance(2)) val outer = outerType.constructors[0].newInstance(innerType.constructors[0].newInstance(2))
@ -160,7 +165,7 @@ class DeserializeNeedingCarpentryTests {
@Test @Test
fun nestedTypes() { fun nestedTypes() {
val cc = ClassCarpenter() val cc = ClassCarpenter()
val nestedClass = cc.build (ClassSchema("nestedType", val nestedClass = cc.build (ClassSchema(testName(),
mapOf("name" to NonNullableField(String::class.java)))) mapOf("name" to NonNullableField(String::class.java))))
val outerClass = cc.build (ClassSchema("outerType", val outerClass = cc.build (ClassSchema("outerType",
@ -169,23 +174,6 @@ class DeserializeNeedingCarpentryTests {
val classInstance = outerClass.constructors.first().newInstance(nestedClass.constructors.first().newInstance("name")) val classInstance = outerClass.constructors.first().newInstance(nestedClass.constructors.first().newInstance("name"))
val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance) val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance)
val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes) val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes)
val inner = deserializedObj::class.java.getMethod("getInner").invoke(deserializedObj)
assertEquals("name", inner::class.java.getMethod("getName").invoke(inner))
}
@Test
fun repeatedNestedTypes() {
val cc = ClassCarpenter()
val nestedClass = cc.build (ClassSchema("nestedType",
mapOf("name" to NonNullableField(String::class.java))))
data class outer(val a: Any, val b: Any)
val classInstance = outer (
nestedClass.constructors.first().newInstance("foo"),
nestedClass.constructors.first().newInstance("bar"))
val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance) val serialisedBytes = TestSerializationOutput(VERBOSE, sf1).serialize(classInstance)
val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes) val deserializedObj = DeserializationInput(sf2).deserialize(serialisedBytes)
@ -195,7 +183,7 @@ class DeserializeNeedingCarpentryTests {
@Test @Test
fun listOfType() { fun listOfType() {
val unknownClass = ClassCarpenter().build (ClassSchema("unknownClass", mapOf( val unknownClass = ClassCarpenter().build (ClassSchema(testName(), mapOf(
"v1" to NonNullableField(Int::class.java), "v1" to NonNullableField(Int::class.java),
"v2" to NonNullableField(Int::class.java)))) "v2" to NonNullableField(Int::class.java))))
@ -223,7 +211,7 @@ class DeserializeNeedingCarpentryTests {
"gen.Interface", "gen.Interface",
mapOf("age" to NonNullableField (Int::class.java)))) mapOf("age" to NonNullableField (Int::class.java))))
val concreteClass = cc.build (ClassSchema ("gen.Class", mapOf( val concreteClass = cc.build (ClassSchema (testName(), mapOf(
"age" to NonNullableField (Int::class.java), "age" to NonNullableField (Int::class.java),
"name" to NonNullableField(String::class.java)), "name" to NonNullableField(String::class.java)),
interfaces = listOf (I::class.java, interfaceClass))) interfaces = listOf (I::class.java, interfaceClass)))

View File

@ -1,5 +1,6 @@
package net.corda.nodeapi.internal.serialization.amqp; package net.corda.nodeapi.internal.serialization.amqp;
import net.corda.nodeapi.internal.serialization.AllWhitelist;
import net.corda.core.serialization.SerializedBytes; import net.corda.core.serialization.SerializedBytes;
import org.apache.qpid.proton.codec.DecoderImpl; import org.apache.qpid.proton.codec.DecoderImpl;
import org.apache.qpid.proton.codec.EncoderImpl; import org.apache.qpid.proton.codec.EncoderImpl;
@ -167,7 +168,7 @@ public class JavaSerializationOutputTests {
} }
private Object serdes(Object obj) throws NotSerializableException { private Object serdes(Object obj) throws NotSerializableException {
SerializerFactory factory = new SerializerFactory(); SerializerFactory factory = new SerializerFactory(AllWhitelist.INSTANCE, ClassLoader.getSystemClassLoader());
SerializationOutput ser = new SerializationOutput(factory); SerializationOutput ser = new SerializationOutput(factory);
SerializedBytes<Object> bytes = ser.serialize(obj); SerializedBytes<Object> bytes = ser.serialize(obj);

View File

@ -14,7 +14,6 @@ import net.corda.nodeapi.RPCException
import net.corda.nodeapi.internal.serialization.AbstractAMQPSerializationScheme import net.corda.nodeapi.internal.serialization.AbstractAMQPSerializationScheme
import net.corda.nodeapi.internal.serialization.EmptyWhitelist import net.corda.nodeapi.internal.serialization.EmptyWhitelist
import net.corda.nodeapi.internal.serialization.amqp.SerializerFactory.Companion.isPrimitive import net.corda.nodeapi.internal.serialization.amqp.SerializerFactory.Companion.isPrimitive
import net.corda.nodeapi.internal.serialization.amqp.custom.*
import net.corda.testing.MEGA_CORP import net.corda.testing.MEGA_CORP
import net.corda.testing.MEGA_CORP_PUBKEY import net.corda.testing.MEGA_CORP_PUBKEY
import org.apache.qpid.proton.amqp.* import org.apache.qpid.proton.amqp.*
@ -136,8 +135,9 @@ class SerializationOutputTests {
data class PolymorphicProperty(val foo: FooInterface?) data class PolymorphicProperty(val foo: FooInterface?)
private fun serdes(obj: Any, private fun serdes(obj: Any,
factory: SerializerFactory = SerializerFactory(), factory: SerializerFactory = SerializerFactoryFactory.get(),
freshDeserializationFactory: SerializerFactory = SerializerFactory(), freshDeserializationFactory: SerializerFactory = SerializerFactory(
AllWhitelist, ClassLoader.getSystemClassLoader()),
expectedEqual: Boolean = true, expectedEqual: Boolean = true,
expectDeserializedEqual: Boolean = true): Any { expectDeserializedEqual: Boolean = true): Any {
val ser = SerializationOutput(factory) val ser = SerializationOutput(factory)
@ -285,13 +285,13 @@ class SerializationOutputTests {
@Test(expected = NotSerializableException::class) @Test(expected = NotSerializableException::class)
fun `test whitelist`() { fun `test whitelist`() {
val obj = Woo2(4) val obj = Woo2(4)
serdes(obj, SerializerFactory(EmptyWhitelist)) serdes(obj, SerializerFactory(EmptyWhitelist, ClassLoader.getSystemClassLoader()))
} }
@Test @Test
fun `test annotation whitelisting`() { fun `test annotation whitelisting`() {
val obj = AnnotatedWoo(5) val obj = AnnotatedWoo(5)
serdes(obj, SerializerFactory(EmptyWhitelist)) serdes(obj, SerializerFactory(EmptyWhitelist, ClassLoader.getSystemClassLoader()))
} }
@Test(expected = NotSerializableException::class) @Test(expected = NotSerializableException::class)
@ -387,10 +387,10 @@ class SerializationOutputTests {
@Test @Test
fun `test custom serializers on public key`() { fun `test custom serializers on public key`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(PublicKeySerializer) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.PublicKeySerializer)
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(PublicKeySerializer) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.PublicKeySerializer)
val obj = MEGA_CORP_PUBKEY val obj = MEGA_CORP_PUBKEY
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
} }
@ -398,16 +398,16 @@ class SerializationOutputTests {
@Test @Test
fun `test annotation is inherited`() { fun `test annotation is inherited`() {
val obj = InheritAnnotation("blah") val obj = InheritAnnotation("blah")
serdes(obj, SerializerFactory(EmptyWhitelist)) serdes(obj, SerializerFactory(EmptyWhitelist, ClassLoader.getSystemClassLoader()))
} }
@Test @Test
fun `test throwables serialize`() { fun `test throwables serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(ThrowableSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(ThrowableSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory2))
val t = IllegalAccessException("message").fillInStackTrace() val t = IllegalAccessException("message").fillInStackTrace()
val desThrowable = serdes(t, factory, factory2, false) as Throwable val desThrowable = serdes(t, factory, factory2, false) as Throwable
@ -416,11 +416,11 @@ class SerializationOutputTests {
@Test @Test
fun `test complex throwables serialize`() { fun `test complex throwables serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(ThrowableSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(ThrowableSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory2))
try { try {
try { try {
@ -447,11 +447,11 @@ class SerializationOutputTests {
@Test @Test
fun `test suppressed throwables serialize`() { fun `test suppressed throwables serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(ThrowableSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(ThrowableSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory2))
try { try {
try { try {
@ -469,11 +469,11 @@ class SerializationOutputTests {
@Test @Test
fun `test flow corda exception subclasses serialize`() { fun `test flow corda exception subclasses serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(ThrowableSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(ThrowableSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory2))
val obj = FlowException("message").fillInStackTrace() val obj = FlowException("message").fillInStackTrace()
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
@ -481,11 +481,11 @@ class SerializationOutputTests {
@Test @Test
fun `test RPC corda exception subclasses serialize`() { fun `test RPC corda exception subclasses serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(ThrowableSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(ThrowableSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.ThrowableSerializer(factory2))
val obj = RPCException("message").fillInStackTrace() val obj = RPCException("message").fillInStackTrace()
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
@ -525,7 +525,7 @@ class SerializationOutputTests {
@Test @Test
fun `test transaction state`() { fun `test transaction state`() {
val state = TransactionState<FooState>(FooState(), MEGA_CORP) val state = TransactionState(FooState(), MEGA_CORP)
val factory = SerializerFactory() val factory = SerializerFactory()
AbstractAMQPSerializationScheme.registerCustomSerializers(factory) AbstractAMQPSerializationScheme.registerCustomSerializers(factory)
@ -542,11 +542,11 @@ class SerializationOutputTests {
@Test @Test
fun `test currencies serialize`() { fun `test currencies serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(CurrencySerializer) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.CurrencySerializer)
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(CurrencySerializer) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.CurrencySerializer)
val obj = Currency.getInstance("USD") val obj = Currency.getInstance("USD")
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
@ -554,11 +554,11 @@ class SerializationOutputTests {
@Test @Test
fun `test big decimals serialize`() { fun `test big decimals serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(BigDecimalSerializer) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.BigDecimalSerializer)
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(BigDecimalSerializer) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.BigDecimalSerializer)
val obj = BigDecimal("100000000000000000000000000000.00") val obj = BigDecimal("100000000000000000000000000000.00")
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
@ -566,11 +566,11 @@ class SerializationOutputTests {
@Test @Test
fun `test instants serialize`() { fun `test instants serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(InstantSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.InstantSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(InstantSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.InstantSerializer(factory2))
val obj = Instant.now() val obj = Instant.now()
serdes(obj, factory, factory2) serdes(obj, factory, factory2)
@ -578,11 +578,11 @@ class SerializationOutputTests {
@Test @Test
fun `test StateRef serialize`() { fun `test StateRef serialize`() {
val factory = SerializerFactory() val factory = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory.register(InstantSerializer(factory)) factory.register(net.corda.nodeapi.internal.serialization.amqp.custom.InstantSerializer(factory))
val factory2 = SerializerFactory() val factory2 = SerializerFactory(AllWhitelist, ClassLoader.getSystemClassLoader())
factory2.register(InstantSerializer(factory2)) factory2.register(net.corda.nodeapi.internal.serialization.amqp.custom.InstantSerializer(factory2))
val obj = StateRef(SecureHash.randomSHA256(), 0) val obj = StateRef(SecureHash.randomSHA256(), 0)
serdes(obj, factory, factory2) serdes(obj, factory, factory2)

View File

@ -4,8 +4,8 @@ import net.corda.nodeapi.internal.serialization.amqp.Field
import net.corda.nodeapi.internal.serialization.amqp.Schema import net.corda.nodeapi.internal.serialization.amqp.Schema
import net.corda.nodeapi.internal.serialization.amqp.TypeNotation import net.corda.nodeapi.internal.serialization.amqp.TypeNotation
import net.corda.nodeapi.internal.serialization.amqp.CompositeType import net.corda.nodeapi.internal.serialization.amqp.CompositeType
import net.corda.nodeapi.internal.serialization.amqp.SerializerFactory
import net.corda.nodeapi.internal.serialization.amqp.SerializationOutput import net.corda.nodeapi.internal.serialization.amqp.SerializationOutput
import net.corda.nodeapi.internal.serialization.amqp.SerializerFactoryFactory
fun mangleName(name: String) = "${name}__carpenter" fun mangleName(name: String) = "${name}__carpenter"
@ -37,7 +37,7 @@ fun Schema.mangleNames(names: List<String>): Schema {
} }
open class AmqpCarpenterBase { open class AmqpCarpenterBase {
var factory = SerializerFactory() var factory = SerializerFactoryFactory.get()
fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz) fun serialise(clazz: Any) = SerializationOutput(factory).serialize(clazz)
fun testName(): String = Thread.currentThread().stackTrace[2].methodName fun testName(): String = Thread.currentThread().stackTrace[2].methodName

View File

@ -63,7 +63,7 @@ class CompositeMembers : AmqpCarpenterBase() {
assertEquals("b", amqpSchemaB.fields[1].name) assertEquals("b", amqpSchemaB.fields[1].name)
assertEquals("int", amqpSchemaB.fields[1].type) assertEquals("int", amqpSchemaB.fields[1].type)
val metaSchema = obj.envelope.schema.carpenterSchema() val metaSchema = obj.envelope.schema.carpenterSchema(ClassLoader.getSystemClassLoader())
// if we know all the classes there is nothing to really achieve here // if we know all the classes there is nothing to really achieve here
assert(metaSchema.carpenterSchemas.isEmpty()) assert(metaSchema.carpenterSchemas.isEmpty())
@ -92,7 +92,7 @@ class CompositeMembers : AmqpCarpenterBase() {
assert(obj.obj is B) assert(obj.obj is B)
amqpSchema.carpenterSchema() amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
} }
@Test @Test
@ -112,7 +112,7 @@ class CompositeMembers : AmqpCarpenterBase() {
assert(obj.obj is B) assert(obj.obj is B)
val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("B"))) val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("B")))
val carpenterSchema = amqpSchema.carpenterSchema() val carpenterSchema = amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
assertEquals(1, carpenterSchema.size) assertEquals(1, carpenterSchema.size)
@ -140,7 +140,7 @@ class CompositeMembers : AmqpCarpenterBase() {
assert(obj.obj is B) assert(obj.obj is B)
val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B"))) val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B")))
val carpenterSchema = amqpSchema.carpenterSchema() val carpenterSchema = amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// just verify we're in the expected initial state, A is carpentable, B is not because // just verify we're in the expected initial state, A is carpentable, B is not because
// it depends on A and the dependency chains are in place // it depends on A and the dependency chains are in place
@ -200,7 +200,7 @@ class CompositeMembers : AmqpCarpenterBase() {
val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B"))) val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B")))
amqpSchema.carpenterSchema() amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
} }
@Test(expected = UncarpentableException::class) @Test(expected = UncarpentableException::class)
@ -226,7 +226,7 @@ class CompositeMembers : AmqpCarpenterBase() {
val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B"))) val amqpSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B")))
amqpSchema.carpenterSchema() amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
} }
@Suppress("UNUSED") @Suppress("UNUSED")
@ -251,7 +251,7 @@ class CompositeMembers : AmqpCarpenterBase() {
assert(obj.obj is C) assert(obj.obj is C)
val carpenterSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B"))) val carpenterSchema = obj.envelope.schema.mangleNames(listOf(classTestName("A"), classTestName("B")))
TestMetaCarpenter(carpenterSchema.carpenterSchema()) TestMetaCarpenter(carpenterSchema.carpenterSchema(ClassLoader.getSystemClassLoader()))
} }
/* /*

View File

@ -45,14 +45,14 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertTrue(obj.obj is A) assertTrue(obj.obj is A)
val serSchema = obj.envelope.schema val serSchema = obj.envelope.schema
assertEquals(2, serSchema.types.size) assertEquals(2, serSchema.types.size)
val l1 = serSchema.carpenterSchema() val l1 = serSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// since we're using an envelope generated by seilaising classes defined locally // since we're using an envelope generated by seilaising classes defined locally
// it's extremely unlikely we'd need to carpent any classes // it's extremely unlikely we'd need to carpent any classes
assertEquals(0, l1.size) assertEquals(0, l1.size)
val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"))) val mangleSchema = serSchema.mangleNames(listOf(classTestName("A")))
val l2 = mangleSchema.carpenterSchema() val l2 = mangleSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
assertEquals(1, l2.size) assertEquals(1, l2.size)
val aSchema = l2.carpenterSchemas.find { it.name == mangleName(classTestName("A")) } val aSchema = l2.carpenterSchemas.find { it.name == mangleName(classTestName("A")) }
@ -88,13 +88,13 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals(2, serSchema.types.size) assertEquals(2, serSchema.types.size)
val l1 = serSchema.carpenterSchema() val l1 = serSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
assertEquals(0, l1.size) assertEquals(0, l1.size)
val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"))) val mangleSchema = serSchema.mangleNames(listOf(classTestName("A")))
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
val l2 = mangleSchema.carpenterSchema() val l2 = mangleSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
assertEquals(1, l2.size) assertEquals(1, l2.size)
@ -132,7 +132,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals(3, serSchema.types.size) assertEquals(3, serSchema.types.size)
val l1 = serSchema.carpenterSchema() val l1 = serSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// since we're using an envelope generated by serialising classes defined locally // since we're using an envelope generated by serialising classes defined locally
// it's extremely unlikely we'd need to carpent any classes // it's extremely unlikely we'd need to carpent any classes
@ -141,7 +141,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
// pretend we don't know the class we've been sent, i.e. it's unknown to the class loader, and thus // pretend we don't know the class we've been sent, i.e. it's unknown to the class loader, and thus
// needs some carpentry // needs some carpentry
val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"))) val mangleSchema = serSchema.mangleNames(listOf(classTestName("A")))
val l2 = mangleSchema.carpenterSchema() val l2 = mangleSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
assertEquals(1, l2.size) assertEquals(1, l2.size)
@ -180,14 +180,14 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals(3, serSchema.types.size) assertEquals(3, serSchema.types.size)
val l1 = serSchema.carpenterSchema() val l1 = serSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// since we're using an envelope generated by serialising classes defined locally // since we're using an envelope generated by serialising classes defined locally
// it's extremely unlikely we'd need to carpent any classes // it's extremely unlikely we'd need to carpent any classes
assertEquals(0, l1.size) assertEquals(0, l1.size)
val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"))) val mangleSchema = serSchema.mangleNames(listOf(classTestName("A")))
val l2 = mangleSchema.carpenterSchema() val l2 = mangleSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
assertEquals(1, l2.size) assertEquals(1, l2.size)
@ -235,7 +235,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals(4, serSchema.types.size) assertEquals(4, serSchema.types.size)
val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"), classTestName("B"))) val mangleSchema = serSchema.mangleNames(listOf(classTestName("A"), classTestName("B")))
val cSchema = mangleSchema.carpenterSchema() val cSchema = mangleSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
val bName = mangleName(classTestName("B")) val bName = mangleName(classTestName("B"))
@ -292,7 +292,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
// ignore the return as we expect this to throw // ignore the return as we expect this to throw
serSchema.mangleNames(listOf( serSchema.mangleNames(listOf(
classTestName("A"), "${this.javaClass.`package`.name}.I")).carpenterSchema() classTestName("A"), "${this.javaClass.`package`.name}.I")).carpenterSchema(ClassLoader.getSystemClassLoader())
} }
@Test @Test
@ -315,7 +315,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
val amqpSchema = serSchema.mangleNames(listOf(classTestName("A"), "${this.javaClass.`package`.name}.I")) val amqpSchema = serSchema.mangleNames(listOf(classTestName("A"), "${this.javaClass.`package`.name}.I"))
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
val iName = mangleName("${this.javaClass.`package`.name}.I") val iName = mangleName("${this.javaClass.`package`.name}.I")
val carpenterSchema = amqpSchema.carpenterSchema() val carpenterSchema = amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// whilst there are two unknown classes within the envelope A depends on I so we can't construct a // whilst there are two unknown classes within the envelope A depends on I so we can't construct a
// schema for A until we have for I // schema for A until we have for I
@ -362,7 +362,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
val iName = mangleName("${this.javaClass.`package`.name}.I") val iName = mangleName("${this.javaClass.`package`.name}.I")
val iiName = mangleName("${this.javaClass.`package`.name}.II") val iiName = mangleName("${this.javaClass.`package`.name}.II")
val carpenterSchema = amqpSchema.carpenterSchema() val carpenterSchema = amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// there is nothing preventing us from carpenting up the two interfaces so // there is nothing preventing us from carpenting up the two interfaces so
// our initial list should contain both interface with A being dependent on both // our initial list should contain both interface with A being dependent on both
@ -414,7 +414,7 @@ class InheritanceSchemaToClassCarpenterTests : AmqpCarpenterBase() {
val aName = mangleName(classTestName("A")) val aName = mangleName(classTestName("A"))
val iName = mangleName("${this.javaClass.`package`.name}.I") val iName = mangleName("${this.javaClass.`package`.name}.I")
val iiiName = mangleName("${this.javaClass.`package`.name}.III") val iiiName = mangleName("${this.javaClass.`package`.name}.III")
val carpenterSchema = amqpSchema.carpenterSchema() val carpenterSchema = amqpSchema.carpenterSchema(ClassLoader.getSystemClassLoader())
// Since A depends on III and III extends I we will have to construct them // Since A depends on III and III extends I we will have to construct them
// in that reverse order (I -> III -> A) // in that reverse order (I -> III -> A)

View File

@ -36,7 +36,10 @@ class MultiMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("int", amqpSchema.fields[1].type) assertEquals("int", amqpSchema.fields[1].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
assertEquals(1, carpenterSchema.size) assertEquals(1, carpenterSchema.size)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") } val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }
@ -77,7 +80,10 @@ class MultiMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("string", amqpSchema.fields[1].type) assertEquals("string", amqpSchema.fields[1].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
assertEquals(1, carpenterSchema.size) assertEquals(1, carpenterSchema.size)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") } val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }

View File

@ -30,7 +30,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("int", amqpSchema.fields[0].type) assertEquals("int", amqpSchema.fields[0].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)
@ -58,7 +61,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
val amqpSchema = obj.envelope.schema.types[0] as CompositeType val amqpSchema = obj.envelope.schema.types[0] as CompositeType
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)
@ -90,7 +96,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("long", amqpSchema.fields[0].type) assertEquals("long", amqpSchema.fields[0].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)
@ -122,7 +131,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("short", amqpSchema.fields[0].type) assertEquals("short", amqpSchema.fields[0].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)
@ -154,7 +166,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("double", amqpSchema.fields[0].type) assertEquals("double", amqpSchema.fields[0].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)
@ -186,7 +201,10 @@ class SingleMemberCompositeSchemaToClassCarpenterTests : AmqpCarpenterBase() {
assertEquals("float", amqpSchema.fields[0].type) assertEquals("float", amqpSchema.fields[0].type)
val carpenterSchema = CarpenterSchemas.newInstance() val carpenterSchema = CarpenterSchemas.newInstance()
amqpSchema.carpenterSchema(carpenterSchemas = carpenterSchema, force = true) amqpSchema.carpenterSchema(
classloader = ClassLoader.getSystemClassLoader(),
carpenterSchemas = carpenterSchema,
force = true)
val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!! val aSchema = carpenterSchema.carpenterSchemas.find { it.name == classTestName("A") }!!
val aBuilder = ClassCarpenter().build(aSchema) val aBuilder = ClassCarpenter().build(aSchema)