0

I am working on a project where I need to compile and execute a Haskell file over cmd which I start/control with Java. That is what it looks like now:

public class CmdTest {
public static void main(String[] args) throws Exception {
    ProcessBuilder builder = new ProcessBuilder( "cmd.exe", "/c", "cd \"C:\\Users\\ray\\Documents\\Project\" && ghci ", "test.hs");
    builder.redirectErrorStream(true);
    Process p = builder.start();
    BufferedReader r = new BufferedReader(new InputStreamReader(p.getInputStream()));
    String line;
    while (true) {
        line = r.readLine();
        if (line == null) { break; }
        System.out.println(line);
    }
}
}

So far so good. Then i tried to execute my actual haskell-function(testfunction) by writing it directly behind the "test.hs" and i tried to write "..."test.hs", "testfunction 2");" and many more way, but i cant load it, when i add any of those. Please tell me how i can fix it and get it running. Thx for your time

Ray

R4y
  • 3
  • 2
  • http://stackoverflow.com/questions/2141148/best-way-to-call-haskell-functions-from-within-java and http://stackoverflow.com/questions/10370177/communication-between-java-and-haskell may help. – agad Jan 09 '15 at 14:44

1 Answers1

1

Provided your file test.hs looks like

module Main where

testfunction :: Int -> IO ()
testFunction n = print n

main :: IO ()
main = do
    testfunction 2

Then you can call it without compilation from Java using the runhaskell command:

public class CmdTest {
public static void main(String[] args) throws Exception {
    ProcessBuilder builder = new ProcessBuilder(
        "cmd.exe",
        "/c",
        "cd \"C:\\Users\\ray\\Documents\\Project\" && runhaskell ",
        "test.hs");
    builder.redirectErrorStream(true);
    Process p = builder.start();
    BufferedReader r = new BufferedReader(new InputStreamReader(p.getInputStream()));
    String line;
    while (true) {
        line = r.readLine();
        if (line == null) { break; }
        System.out.println(line);
    }
}
}

The important parts to note:

Your Haskell file has to explicitly be module Main or have no module declaration (it's implicitly Main, but it's always good idea to be explicit), it has to have a function called main with type IO (), and the use of the runhaskell command. The ghci command is for running an interactive REPL, much like IPython or irb, it is not meant for running a source file as a script. You also can't just specify which function inside the .hs file to run, your file has to be an executable. You wouldn't expect this to work for Java

// SayHello.java
public class SayHello {
    public static void sayHello(String name) {
        System.out.print("Hello, ");
        System.out.println(name);
    }
}

And then run it as

> java SayHello.java SayHello.sayHello "World"

You have to compile it first and have the target function called from some public static void main(String[] args). The same goes for Haskell, you have to have a main function to run anything, and runhaskell will simply compile and run your code in one step.

bheklilr
  • 53,530
  • 6
  • 107
  • 163