1

I converted an object to json String and storing it as Blob in Datastax using ByteBuffer.wrap(attributes.getBytes()). How can I convert that back to String and assert in my tests? I tried using org.apache.commons.lang3.SerializationUtils.deserialize(entity.getAttributes().array()) but getting an exception

org.apache.commons.lang3.SerializationException: java.io.StreamCorruptedException: invalid stream header: 7B226F70

at org.apache.commons.lang3.SerializationUtils.deserialize(SerializationUtils.java:197)
at org.apache.commons.lang3.SerializationUtils.deserialize(SerializationUtils.java:223)
at com.homedepot.productassortment.fullfeed.util.InstallSkusToProductAssortmentConverterTest.convertInstallSkuToProductAssortmentEntity(InstallSkusToProductAssortmentConverterTest.java:50)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
at org.junit.runner.JUnitCore.run(JUnitCore.java:160)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:68)
at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)
Erick Ramirez
  • 13,964
  • 1
  • 18
  • 23
gcpdev-guy
  • 460
  • 1
  • 10
  • 23
  • Do you really have the need to encapsulate your 'attributes.getBytes()' inside a ByteBuffer ? You could just store your array directly and deserialise it... – Julien Revault d'A... Jan 30 '19 at 15:57
  • Didn't get your question. Attributes is a string and ByteBuffer.wrap(takes a bytearray) hence calling getBytes() on it – gcpdev-guy Jan 30 '19 at 16:19
  • https://stackoverflow.com/questions/3982704/how-to-serialize-bytebuffer – Ng Sharma Jan 30 '19 at 16:49
  • The error suggests that the data it is not serialized through the Java serialization mechanism. Using `String.getBytes` is just a direct string-to-bytes conversion (`7B226F70` is `{"op` in ASCII, which to me looks like the start of a JSON string converted to bytes). Make sure you use the correct mechanism (which is `new String(thebytes)`. Note though that it would be better to explicitly specify the character set, because right now you're relying on platform specific encoding – Mark Rotteveel Jan 30 '19 at 16:50
  • https://kafka.apache.org/10/javadoc/org/apache/kafka/common/serialization/ByteBufferDeserializer.html – Ng Sharma Jan 30 '19 at 16:51

1 Answers1

1

You should try something like this :

byte[] bytes = attributes.getBytes( StandardCharsets.UTF_8 );
ByteBuffer.wrap(bytes);

I added StandardCharsets.UTF_8 as getBytes() uses the default charset of your platform. then you can get your bytes back with something like :

String original = new String( entity.getAttributes(), StandardCharsets.UTF_8 );

In fact I don't know what type is your entity.getAttributes() but if it is a byte[] it should work.

  • Thanks, it worked. I wasn't using characrerset when I called getBytes on the attributes string. – gcpdev-guy Jan 30 '19 at 18:21
  • @Julien Using this method `new String( entity.getAttributes(), StandardCharsets.UTF_8 );` returns garbage characters (?) in between the text if the text is not in English, seems like some bytes are missed while decoding. Any solution for that issue? – Om Infowave Developers Aug 06 '22 at 05:37