Issues encountered for customized sorting and search criteria


(Jiachuan Li) #1

Hi Team

As I haven’t got one resolution on stackoverflow several days, so just re-post it here, hope can get some comments.

There are two issues I encountered and I can reproduce them based on M13 tutorial code.

Issue 1: “Not an entity” error for customized sorting option.
Based on M13 tutorial ExampleApi.kt code, I added one customized sorting option(sort by iou value) for “getIOUs” method, code as below:
/**
* Displays all IOU states that exist in the node’s vault.
*/
@GET
@Path(“ious”)
@Produces(MediaType.APPLICATION_JSON)
fun getIOUs(): List<StateAndRef> {
val sorting = Sort(setOf(Sort.SortColumn(SortAttribute.Custom(IOUSchemaV1.PersistentIOU::class.java, “value”), Sort.Direction.DESC)))
val vaultStates = services.vaultQueryBy(sorting = sorting)
return vaultStates.states
}

But when I try to browse “api/example/ious” page, below error was found and page could not be shown.
not_an_entity

The persistent state should be defined already by the tutorial code, so I am not sure what’s wrong with the sorting code.

Issue 2: “is not annotated or on the whitelist” error for customized search criteria
Based on M13 tutorial ExampleApi.kt code, I added one customized search criteria(recipient name like ‘%1%’) for “getIOUs” method, code as below:
@GET
@Path(“ious”)
@Produces(MediaType.APPLICATION_JSON)
fun getIOUs(): List<StateAndRef> {
val logicalExpression = builder { IOUSchemaV1.PersistentIOU::recipientName.like("%1%") }
val criteria = QueryCriteria.VaultCustomQueryCriteria(logicalExpression)
val vaultStates = services.vaultQueryBy(criteria)
return vaultStates.states
}

But when I try to browse “api/example/ious” page, below error was found and page could not be shown
[WARN ] 2017-08-01T15:49:13,780 [qtp598183031-132] server.HttpChannel.handle - //localhost:10007/api/example/ious

javax.servlet.ServletException: javax.servlet.ServletException: com.esotericsoftware.kryo.KryoException: Class com.example.api.ExampleApi$getIOUs$logicalExpression$1$1 is not annotated or on the whitelist, so cannot be used in serialization
Serialization trace:
property (net.corda.core.node.services.vault.Column$Kotlin)
column (net.corda.core.node.services.vault.CriteriaExpression$ColumnPredicateExpression)
expression (net.corda.core.node.services.vault.QueryCriteria$VaultCustomQueryCriteria)
	at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:139) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:134) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.Server.handle(Server.java:524) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:319) [jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.java:253) [jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.io.AbstractConnection$ReadCallback.succeeded(AbstractConnection.java:273) [jetty-io-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.io.FillInterest.fillable(FillInterest.java:95) [jetty-io-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.io.SelectChannelEndPoint$2.run(SelectChannelEndPoint.java:93) [jetty-io-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.util.thread.strategy.ExecuteProduceConsume.executeProduceConsume(ExecuteProduceConsume.java:303) [jetty-util-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.util.thread.strategy.ExecuteProduceConsume.produceConsume(ExecuteProduceConsume.java:148) [jetty-util-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.util.thread.strategy.ExecuteProduceConsume.run(ExecuteProduceConsume.java:136) [jetty-util-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:671) [jetty-util-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.util.thread.QueuedThreadPool$2.run(QueuedThreadPool.java:589) [jetty-util-9.3.9.v20160517.jar:9.3.9.v20160517]
	at java.lang.Thread.run(Unknown Source) [?:1.8.0_144]
Caused by: javax.servlet.ServletException: com.esotericsoftware.kryo.KryoException: Class com.example.api.ExampleApi$getIOUs$logicalExpression$1$1 is not annotated or on the whitelist, so cannot be used in serialization
Serialization trace:
property (net.corda.core.node.services.vault.Column$Kotlin)
column (net.corda.core.node.services.vault.CriteriaExpression$ColumnPredicateExpression)
expression (net.corda.core.node.services.vault.QueryCriteria$VaultCustomQueryCriteria)
	at org.glassfish.jersey.servlet.WebComponent.serviceImpl(WebComponent.java:489) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.WebComponent.service(WebComponent.java:427) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:388) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:341) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:228) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:845) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:583) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1174) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:511) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1106) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:119) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	... 13 more
Caused by: com.esotericsoftware.kryo.KryoException: Class com.example.api.ExampleApi$getIOUs$logicalExpression$1$1 is not annotated or on the whitelist, so cannot be used in serialization
Serialization trace:
property (net.corda.core.node.services.vault.Column$Kotlin)
column (net.corda.core.node.services.vault.CriteriaExpression$ColumnPredicateExpression)
expression (net.corda.core.node.services.vault.QueryCriteria$VaultCustomQueryCriteria)
	at net.corda.core.serialization.CordaClassResolver.checkClass(CordaClassResolver.kt:65) ~[corda-core-0.13.0.jar:?]
	at net.corda.core.serialization.CordaClassResolver.getRegistration(CordaClassResolver.kt:35) ~[corda-core-0.13.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.getRegistration(Kryo.java:488) ~[kryo-4.0.0.jar:?]
	at net.corda.nodeapi.RPCKryo.getRegistration(RPCStructures.kt:74) ~[corda-node-api-0.13.0.jar:?]
	at com.esotericsoftware.kryo.util.DefaultClassResolver.writeClass(DefaultClassResolver.java:97) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.writeClass(Kryo.java:540) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.ObjectField.write(ObjectField.java:76) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.CompatibleFieldSerializer.write(CompatibleFieldSerializer.java:66) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.writeObject(Kryo.java:575) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.ObjectField.write(ObjectField.java:80) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.CompatibleFieldSerializer.write(CompatibleFieldSerializer.java:66) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.writeObject(Kryo.java:575) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.ObjectField.write(ObjectField.java:80) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.CompatibleFieldSerializer.write(CompatibleFieldSerializer.java:66) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.writeClassAndObject(Kryo.java:651) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.CollectionSerializer.write(CollectionSerializer.java:100) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.serializers.CollectionSerializer.write(CollectionSerializer.java:40) ~[kryo-4.0.0.jar:?]
	at com.esotericsoftware.kryo.Kryo.writeClassAndObject(Kryo.java:651) ~[kryo-4.0.0.jar:?]
	at net.corda.core.serialization.KryoKt.serialize(Kryo.kt:169) ~[corda-core-0.13.0.jar:?]
	at net.corda.core.serialization.KryoKt$serialize$1.execute(Kryo.kt:151) ~[corda-core-0.13.0.jar:?]
	at net.corda.core.serialization.KryoKt$serialize$1.execute(Kryo.kt) ~[corda-core-0.13.0.jar:?]
	at com.esotericsoftware.kryo.pool.KryoPoolQueueImpl.run(KryoPoolQueueImpl.java:61) ~[kryo-4.0.0.jar:?]
	at net.corda.core.serialization.KryoKt.serialize(Kryo.kt:151) ~[corda-core-0.13.0.jar:?]
	at net.corda.core.serialization.KryoKt.serialize$default(Kryo.kt:150) ~[corda-core-0.13.0.jar:?]
	at net.corda.nodeapi.RPCApi$ClientToServer$RpcRequest.writeToClientMessage(RPCApi.kt:103) ~[corda-node-api-0.13.0.jar:?]
	at net.corda.client.rpc.internal.RPCClientProxyHandler.invoke(RPCClientProxyHandler.kt:197) ~[corda-rpc-0.13.0.jar:?]
	at com.sun.proxy.$Proxy22.vaultQueryBy(Unknown Source) ~[?:?]
	at com.example.api.ExampleApi.getIOUs(ExampleApi.kt:122) ~[kotlin-source-0.1.jar:?]
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[?:1.8.0_144]
	at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) ~[?:1.8.0_144]
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) ~[?:1.8.0_144]
	at java.lang.reflect.Method.invoke(Unknown Source) ~[?:1.8.0_144]
	at org.glassfish.jersey.server.model.internal.ResourceMethodInvocationHandlerFactory$1.invoke(ResourceMethodInvocationHandlerFactory.java:81) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher$1.run(AbstractJavaResourceMethodDispatcher.java:144) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher.invoke(AbstractJavaResourceMethodDispatcher.java:161) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.internal.JavaResourceMethodDispatcherProvider$TypeOutInvoker.doDispatch(JavaResourceMethodDispatcherProvider.java:205) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher.dispatch(AbstractJavaResourceMethodDispatcher.java:99) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:389) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.ResourceMethodInvoker.apply(ResourceMethodInvoker.java:347) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.model.ResourceMethodInvoker.apply(ResourceMethodInvoker.java:102) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.ServerRuntime$2.run(ServerRuntime.java:326) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.internal.Errors$1.call(Errors.java:271) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.internal.Errors$1.call(Errors.java:267) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.internal.Errors.process(Errors.java:315) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.internal.Errors.process(Errors.java:297) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.internal.Errors.process(Errors.java:267) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.process.internal.RequestScope.runInScope(RequestScope.java:317) ~[jersey-common-2.25.jar:?]
	at org.glassfish.jersey.server.ServerRuntime.process(ServerRuntime.java:305) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.server.ApplicationHandler.handle(ApplicationHandler.java:1154) ~[jersey-server-2.25.jar:?]
	at org.glassfish.jersey.servlet.WebComponent.serviceImpl(WebComponent.java:473) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.WebComponent.service(WebComponent.java:427) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:388) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:341) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:228) ~[jersey-container-servlet-core-2.25.jar:?]
	at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:845) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:583) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1174) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:511) ~[jetty-servlet-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1106) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:119) ~[jetty-server-9.3.9.v20160517.jar:9.3.9.v20160517]
	... 13 more