George
08/24/2022, 3:48 PMio.rsocket.kotlin.RSocketError$ApplicationError: No handler for destination
. So im investigation a bit the spring code and i figured the routing-metada are not decoded properly, also i turned up the debugger in spring and it confirmed it for me after this: DefaultMetadataExtractor : Values extracted from metadata: {} with registrations for [].
So anyone has any ideas? Thanks in advance 🙂Oleg Yukhnevich
08/24/2022, 3:59 PMGeorge
08/24/2022, 4:08 PMinternal inline fun <reified T, reified R> RSocket.hubRequestChannel(
route: String,
incomingFlow: Flow<T>
): Flow<HubPayload<R>> {
val routePayload = routePayload(route)
val payloads = incomingFlow.map { protoBufFormat.encodeToPayload(route, it) }
return requestChannel(routePayload, payloads).map { protoBufFormat.decodeFromPayload(it) }
}
internal fun routePayload(route: String): Payload {
return buildPayload {
data(ByteReadPacket.Empty)
metadata(RoutingMetadata(route))
}
}
internal inline fun <reified T> ProtoBuf.encodeToPayload(route: String, value: T): Payload = buildPayload {
data(encodeToByteArray(value))
metadata(RoutingMetadata(route))
}
and i see in RoutingMetadata class, the mime type is "message/x.rsocket.routing.v0", 0x7E
Spring code: Note sure if this the right piece
private void extractEntry(ByteBuf content, @Nullable String mimeType, Map<String, Object> result) {
if (content.readableBytes() == 0) {
return;
}
EntryExtractor<?> extractor = this.registrations.get(mimeType);
if (extractor != null) {
extractor.extract(content, result);
return;
}
if (mimeType != null && mimeType.equals(WellKnownMimeType.MESSAGE_RSOCKET_ROUTING.getString())) {
Iterator<String> iterator = new RoutingMetadata(content).iterator();
if (iterator.hasNext()) {
result.put(MetadataExtractor.ROUTE_KEY, iterator.next());
}
}
}
which i guess it check for Message_rsocket_routing which is : "message/x.rsocket.routing.v0", (byte) 0x7E
i have not enabled the debugger but after this function the debugger logs:
if (logger.isDebugEnabled()) {
logger.debug("Values extracted from metadata: " + result +
" with registrations for " + this.registrations.keySet() + ".");
}
George
08/24/2022, 4:09 PMOleg Yukhnevich
08/24/2022, 4:34 PMconnectionConfig {
payloadMimeType = PayloadMimeType(
data = WellKnownMimeType.ApplicationJson, //or something different
metadata = WellKnownMimeType.MessageRSocketRoutingMetadata
)
}
George
08/25/2022, 2:20 PMpayloadMimeType= PayloadMimeType(
data = WellKnownMimeType.ApplicationOctetStream,
metadata = WellKnownMimeType.MessageRSocketCompositeMetadata
And in every request i have
internal fun routePayload(route: String): Payload {
return buildPayload {
data(ByteReadPacket.Empty)
compositeMetadata {
add(RoutingMetadata(route))
}
}
}
Oleg Yukhnevich
08/25/2022, 2:22 PMGeorge
08/25/2022, 2:23 PMGeorge
08/25/2022, 2:29 PMOleg Yukhnevich
08/25/2022, 2:39 PMGeorge
08/25/2022, 2:49 PMhandleAndReply
(which is similar for me at least 😛 to the requestChannel). But at the end probably this has nothing to do with the client since it just implements properly the RSocket
interface.