[Last Call] Learn about multicloud storage options and how to improve your company's cloud strategy. Register Now

x
?
Solved

Lynx, Java, & Runtime.getRuntime().exec()

Posted on 2004-10-06
6
Medium Priority
?
1,913 Views
Last Modified: 2008-02-01
LYnx is a text based browser.  It can convert .html files to its rough equivalent in text.

I am trying to use a simple java program to call lynx.bat or lynx.exe .

Lynx.bat is located in C:\Lynx\lynx.bat

I want to use the "-dump" parameter.

Then I must put the name of the file "mydoc.htm"

Then the name of the new file "mydoctxt.txt"

So in completion it would look like this "lynx.bat -dump mydoc.htm > mydoctxt.txt"

This works completely fine from the command line, but when I try to wrap it in a simple java program, it fails.

Here is what I have so far...

package javaapplication2;
import      java.io.*;
class Main{
   
    public static void main(String argv[]) {
       
        try {
            String ls_str;
           
            //Process ls_proc = Runtime.getRuntime().exec("cmd.exe /E :1900 C:\\lynx\\lynx.exe -dump C:\\test.htm > C:\\test6.txt");
            Process ls_proc = Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm > C:\\test5.txt");

           
            DataInputStream ls_in = new DataInputStream(
            ls_proc.getInputStream());
           
           
            try {
                while ((ls_str = ls_in.readLine()) != null) {
                    System.out.println(ls_str);

                }
            } catch (IOException e) {
                System.out.println("1st catch block");
                System.exit(0);


            }
        } catch (IOException e1) {
            System.err.println(e1);
            System.out.println("2nd catch block");
            System.exit(1);
        }
       
        System.exit(0);
       
       
    }
   
   
}

When I run that a blank text file called test5.txt is created.  It is 0kb in length.  If I run it straight from the command line in windows XP though, test5.txt is created successfully.  If I uncomment out Process ls_proc = Runtime.getRuntime().exec("cmd.exe /E :1900 C:\\lynx\\lynx.exe -dump C:\\test.htm > C:\\test6.txt"); and comment out the other line, the program lags and nothing happens.

I know I have to be missing something simple here, because I whipped up the equivalent prog in VB, in like 3 minutes.
0
Comment
Question by:bullyellis
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
6 Comments
 
LVL 4

Expert Comment

by:gdrnec
ID: 12240962
I had this problem once and I think that I solved by using Runtime.exec(String[] cmdarray) method instead of all one string.

so String[] cmdarray = {"C:\\lynx\\lynx.bat","-dump","C:\\test.htm",">","C:\\test5.txt"};
Runtime.getRuntime().exec(cmdarray);

I think I remeber this solving it. Hope I'm right.

Geoff
0
 
LVL 37

Expert Comment

by:zzynx
ID: 12241055
Sure it isn't a matter of (back) slashes.

Did you try these already?

            Process ls_proc = Runtime.getRuntime().exec("cmd.exe /E :1900 C:/lynx/lynx.exe -dump C:/test.htm > C:/test6.txt");
or
            Process ls_proc = Runtime.getRuntime().exec("C:/lynx/lynx.bat -dump C:/test.htm > C:/test5.txt");
0
 
LVL 13

Accepted Solution

by:
Webstorm earned 1000 total points
ID: 12242159
Hi bullyellis,

You cannot redirect the output with ">" unless you use cmd.exe.
You have to redirect the outputstream from the Process class to a FileOutputStream like that :

String[] cmdarray = {"cmd.exe","/E:1900","/C","C:\\lynx\\lynx.bat","-dump","C:\\test.htm"};
//String[] cmdarray = {"C:\\lynx\\lynx.exe,"-dump","C:\\test.htm"};

// cmd.exe to invoke the batch file is necessary, but not for the .exe file

RunProcess ls_proc = new RunProcess(
         Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm > C:\\test5.txt"),
          System.in,false,
          new FileOutputStream("C:\\test5.txt"),true, // stdout redirection
          System.err,false);


// And the RunProcess class is :


public class RunProcess
{
    private Process p=null;
    private static final int BUFFER_SIZE=8192;
    private Thread th_in=null,th_out=null,th_err=null;
    private int ret_code=-1;

    public RunProcess(
        final Process p,
        final InputStream p_in,   final boolean in_close,
        final OutputStream p_out, final boolean out_close,
        final OutputStream p_err, final boolean err_close)
    {
        this.p=p;

        // Process. OUT
        (th_out=new Thread(){
            byte b[]=new byte[BUFFER_SIZE];
            InputStream inp=p.getInputStream();
            public void run()
            {
                try{
                    for(;;)
                    {
                        int sz=inp.read(b);
                        if (p_out!=null) p_out.write(b,0,sz);
                    }
                }catch(Exception e){}
            }
        }).start();

        // Process. ERR
        (th_err=new Thread(){
            byte b[]=new byte[BUFFER_SIZE];
            InputStream inp=p.getErrorStream();
            public void run()
            {
                try{
                    for(;;)
                    {
                        int sz=inp.read(b);
                        if (p_err!=null) p_err.write(b,0,sz);
                    }
                }catch(Exception e){}
            }
        }).start();

        if (p_in!=null)
        // Process. IN
        (th_in=new Thread(){
            byte b[]=new byte[BUFFER_SIZE];
            OutputStream outp=p.getOutputStream();
            public void run()
            {
                try{
                    for(;;)
                    {
                        int sz=p_in.read(b);
                        outp.write(b,0,sz);
                    }
                }catch(Exception e){}
            }
        }).start();

        (new Thread(){
            public void run()
            {
                try{
                    ret_code=p.waitFor();
                }catch(Exception ex){}
                if (th_in!=null) th_in.interrupt();
                try{if (in_close&&(p_in!=null)) p_in.close();}catch(Exception ex){}
                try{if (out_close&&(p_out!=null)) p_out.close();}catch(Exception ex){}
                try{if (err_close&&(p_err!=null)) p_err.close();}catch(Exception ex){}
                if (th_out!=null) th_out.interrupt();
                if (th_err!=null) th_err.interrupt();
            }
        }).start();
    }

    public int getReturnCode()
    {
        return ret_code;
    }

    public int waitFor() throws Exception
    {
        return p.waitFor();
    }

    public void destroy()
    {
        p.destroy();
    }
}
0
Industry Leaders: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 92

Expert Comment

by:objects
ID: 12244080
Here an examples of handing the output from a Process that you should be able to easily adapt to your requirements.

http://www.objects.com.au/java/examples/util/ConsoleExec.do
0
 

Author Comment

by:bullyellis
ID: 12244728
WebStorm,

Your code works kind of.

The problem I ran into was

RunProcess ls_proc = new RunProcess(
         Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm > C:\\test5.txt"),
          System.in,false,
          new FileOutputStream("C:\\test5.txt"),true, // stdout redirection
          System.err,false);

The 2 instances of "test5.txt" can not be named the same thing.

I get an error that "The process cannot access the file because it is being used by another process."  And again I get the empty text file.

However if I change the code to

RunProcess ls_proc = new RunProcess(
         Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm > C:\\testa.txt"),
          System.in,false,
          new FileOutputStream("C:\\testb.txt"),true, // stdout redirection
          System.err,false);

Then I get both testa and testb.  testa.txt works correctly and is what I want.  testb.txt however is another empty text file.

Could you explain this ?

0
 
LVL 13

Expert Comment

by:Webstorm
ID: 12257048
bullyellis, thanks for the points

When you specify a redirection with '>', cmd.exe will redirect output to this file. So, nothing will be written to the process's stdout stream, and you get an empty file.
If you specify a FileOutputStream you don't have to specify another redirection in the command line and it's only usable with cmd.exe :

RunProcess ls_proc = new RunProcess(
         Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm"),
          System.in,false,
          new FileOutputStream("C:\\testa.txt"),true, // stdout redirection
          System.err,false);

Or

RunProcess ls_proc = new RunProcess(
         Runtime.getRuntime().exec("C:\\lynx\\lynx.bat -dump C:\\test.htm > C:\\testa.txt"),
          System.in,false,
          System.out,false,
          System.err,false);

0

Featured Post

Free Tool: IP Lookup

Get more info about an IP address or domain name, such as organization, abuse contacts and geolocation.

One of a set of tools we are providing to everyone as a way of saying thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Java contains several comparison operators (e.g., <, <=, >, >=, ==, !=) that allow you to compare primitive values. However, these operators cannot be used to compare the contents of objects. Interface Comparable is used to allow objects of a cl…
Java had always been an easily readable and understandable language.  Some relatively recent changes in the language seem to be changing this pretty fast, and anyone that had not seen any Java code for the last 5 years will possibly have issues unde…
This tutorial covers a practical example of lazy loading technique and early loading technique in a Singleton Design Pattern.
This tutorial covers a step-by-step guide to install VisualVM launcher in eclipse.
Suggested Courses

650 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question