Blob Blame History Raw
--- BeanShell/src/bsh/Interpreter.java~	2003-09-03 19:56:58.000000000 -0400
+++ BeanShell/src/bsh/Interpreter.java	2004-01-25 09:59:41.730059108 -0500
@@ -38,6 +38,13 @@
 import java.lang.reflect.Method;
 import java.lang.reflect.InvocationTargetException;
 
+import bsh.util.BshCompleter;
+import bsh.util.NameCompletionTable;
+import bsh.classpath.ClassManagerImpl;
+import org.gnu.readline.Readline;
+import org.gnu.readline.ReadlineLibrary;
+import org.gnu.readline.ReadlineReader;
+
 /**
 	The BeanShell script interpreter.
 
@@ -394,10 +401,59 @@
 			else
 				src = System.in;
 
-            Reader in = new CommandLineReader( new InputStreamReader(src));
-            Interpreter interpreter = 
-				new Interpreter( in, System.out, System.err, true );
-        	interpreter.run();
+            Reader in = null;
+            boolean usingReadline = false;
+            String backingLib = System.getProperty("bsh.console.readlinelib");
+            if (backingLib != null) {
+                try {
+                    File history = new File(System.getProperty("user.home") +
+                                            File.separator + ".bsh_history");
+                    if (!history.exists()) {
+                        try {
+                            history.createNewFile();
+                        } catch(IOException ioe) {
+                            debug("Unable to create history  " + history.getAbsolutePath());
+                        }
+                    }
+                    ReadlineLibrary lib = ReadlineLibrary.byName(backingLib);
+                    // should I wrap CommandLineReader around it?
+                    if (history.canWrite() && history.canRead()) {
+                        in = new ReadlineReader("bsh % ", history,lib);
+                    } else {
+                        in = new ReadlineReader("bsh % ",lib);
+                        debug("Unable to read/write history  " + history.getAbsolutePath());
+                    }
+                } catch (IOException ioe) {
+                    System.err.println("Unable to invoke ReadlineReader " +
+                                       "due to: " + ioe);
+                }
+            }
+            if (in == null)
+                in = new CommandLineReader( new InputStreamReader(src));
+            else
+                usingReadline = true;
+            Interpreter interpreter =
+                new Interpreter( in, System.out, System.err, true );
+            if (usingReadline) {
+                NameCompletionTable nct = new NameCompletionTable();
+                nct.add(interpreter.getNameSpace());
+
+                /** ClassManager does a lot of chatting to the stdout,
+                 *  so this has been commented out for the time being
+                 **/
+
+//              try {
+//                  BshClassManager bcm = BshClassManager.getClassManager();
+//                      if (bcm != null) {
+//                          nct.add(((ClassManagerImpl)bcm).getClassPath());
+//                      }
+//                  } catch(ClassPathException cpe) {
+//                      debug("classpath exception in name compl:" + cpe);
+//                  }
+
+                Readline.setCompleter(new BshCompleter(nct));
+            }
+            interpreter.run();
         }
     }
 
@@ -445,7 +501,7 @@
                 System.err.flush();
                 Thread.yield();  // this helps a little
 
-                if ( interactive )
+                if ( interactive && !(in instanceof ReadlineReader))
                     print( getBshPrompt() );
 
                 eof = Line();
@@ -548,10 +604,17 @@
             }
         }
 
-		if ( interactive && exitOnEOF )
-			System.exit(0);
+        if ( interactive && exitOnEOF ) {
+            /* should be done for all streams in general, but this
+             * ensures that the history for readline is flushed */
+            try {
+                in.close();
+            } catch (IOException ioe) {
+            }
+	
+            System.exit(0);
     }
-
+   }
 	// begin source and eval
 
 	/**
--- /dev/null	2003-10-19 02:52:03.000000000 -0400
+++ BeanShell/src/bsh/util/BshCompleter.java	2004-01-25 10:14:10.184458217 -0500
@@ -0,0 +1,38 @@
+package bsh.util;
+
+import org.gnu.readline.ReadlineCompleter;
+
+/**
+ * An adapter for org.gnu.readline's ReadlineCompleter interface to map to
+ * BeanShell's NameCompleter interface.
+ *
+ * @see org.gnu.readline.ReadlineReader
+ * @version $Revision: 1.1 $
+ * @author Shane Celis <shane@terraspring.com>
+ **/
+public class BshCompleter implements ReadlineCompleter {
+
+    private NameCompletion completer;
+
+    /**
+     * Constructs a <code>ReadlineCompleter</code> out of a
+     * <code>NameCompleter</code> object.
+     **/
+    public BshCompleter(NameCompletion completer) {
+        this.completer = completer;
+    }
+
+    /**
+     * Returns String of completion if unambiguous, otherwise null
+     **/
+    public String completer(String text, int state) {
+        // Not sure what state is used for in ReadlineCompleter
+        String[] completions = completer.completeName(text);
+        if (completions.length == 1 && state == 0) {
+            return completions[0];
+        } else {
+            return null;        // ambiguous result
+        }
+    }
+
+}