11

I have an Akka application with actors written in Scala and others in Java. In one case a Scala Actor writes an Array[Byte] and I need to deserialize this from a Java Actor. In this use-case I ultimately need a String representation in Java of the Array[Byte] so that would also solve my problem.

Scala Actor:

val outputStream = new java.io.ByteArrayOutputStream()
val bufferedOutputStream = new java.io.BufferedOutputStream(outputStream, 1024)
val exitCode : Integer = processBuilder #> bufferedOutputStream !
bufferedOutputStream.flush
val content = outputStream.toByteArray // this gives an Array[Byte]
javaActorRef.tell(content, getSelf())

Java Actor:

/**
 * {@inheritDoc}
 */
@Override
public void onReceive(Object object) throws Exception {
    // object has a Scala Array[Byte] how do I convert here to 
    // byte[] or to String?
SkyWalker
  • 11,704
  • 14
  • 65
  • 144
  • Are they different? I thought you could access Scala objects from Java since they're both JVM technologies. What have you tried? If you're trying to pass strings, can you pass a char[] array? – mttdbrd Mar 13 '14 at 13:48
  • I could send Strings and it is no problem. However, the Scala actor that sends the Array[Byte] is generic because it just takes the stdout of any command. In some use-cases the output is String as in this case but the Actor could be used in other contexts where the output of a process is binary, too. – SkyWalker Mar 13 '14 at 13:50

3 Answers3

22

Scala's Array[Byte] is already a Java's byte[]. Proof:

object ScalaSide extends Application {
  val a = Array[Byte](1, 2, 3)

  JavaSide.doSmth(a)
}

--

import java.util.Arrays;

public class JavaSide {
    public static void doSmth(Object arr) {
        byte[] b = (byte[]) arr;
        System.out.println(Arrays.toString(b));
    }
} 

Result:

[1, 2, 3]
om-nom-nom
  • 60,231
  • 11
  • 174
  • 223
serejja
  • 19,968
  • 6
  • 54
  • 69
0

I don't see that the tell method in Scala uses the stdout. It sends an Any and the onReceive in Java takes an Object. All you need to do is check in your Java onReceive like this:

public void onReceive(Object object) throws Exception {

    if (object instanceof byte[]) {

        doSomething();
    }
    else if....
mttdbrd
  • 1,731
  • 11
  • 17
-1

Since what you said is valid (and considering all sources I checked - it is), this should work as well:

Java call:

private byte[] loadFile() throws FileNotFoundException, IOException {
    return FileLoader.loadBytesFromFile(fileToLoad);
}

of Scala method:

def loadBytesFromFile(fileToLoad: File): Array[Byte] = {
    return Source.fromFile(fileToLoad).map(_.toByte).toArray
}

However, inside the Java method loadFile() I get:

incompatible types: Array cannot be converted to byte[]
  • If you have a problem, which you seem to have from your final two lines, you should ask it as a new question, not post it as an answer. You can include a link to this question if you feel it helps explain your question (use the share link under the question). – Bill Woodger Apr 29 '15 at 21:11