Hi Paul,
I've slowly worked my way through a set of java code for a dynamic sql
building package. The end result will be using the beanshell to
maintain a connection pool and then have elisp execute calls through
this layer to retrieve a list of tables, then a list of columns for
chosen tables. (Then, whatever my little database heart could desire
and my little elisp mind could handle)
I have a set of java classes that seem to be doing what I need and I
have been spending the last few weeks trying to integrate these into
Emacs using your beanshell.el interface to the beanshell.
What I would like to get from you is some feedback on making the
beanshell.el a package on its own. Right now, it is very jde specific
with one of the big pieces of this specificity being that it uses the
jde-global-classpath and looks for ant stuff.
How feasible would you think the beanshell.el being a standalone package
is? I could envision a layer on both sides of it, where we have a set
of java classes that return elisp structures and the corresponding elisp
structures that call java. Then, the java written to be used by elisp
could be divorced from the elisp syntax.
On the more practical side of the house, I could see any changes to this
package being very risky to the jdee, and therefore out of the question.
On a functionality question, it seems there are exactly two types of
eval operations,
1) eval java without evaling any returning elisp
2) eval java and in return eval elisp into Emacs.
What I'm not sure of at the moment is whether the first option will wait
on the beanshell process to complete? Its hard to debug because when I
edebug the bsh-eval, everything works (edebug is slow enough that any
time lag that might be causing a problem goes unnoticed). When I
execute the individual sexps, the final result is also successful. Its
when I execute the steps as one elisp call, that I get a beanshell
error.
Here is the elisp code that is behaving in the manner I've described.
(defun get-tables ()
(interactive)
(bsh-eval "EJMetaData localMetaData = new EJMetaData
(\"oracle\",\"GALEN\",\"1521\",\"ORA8172\",\"system\",\"manager\");")
(completing-read "Tables: " (bsh-eval "localMetaData.getTables();" t)))
The reason I'm splitting this into two calls is because I want the
beanshell to maintain a connection pool (using a Hashmap). Elisp will
define the connection name (based on the SQL buffer name) with the exact
name the java code will use to define the connection. Then, the elisp
call to it can either find an already established connection or create
one. (So far, I've decided my package will be called ejsql for Emacs
JDBC SQL).
When I execute the two lines by themselves, I get my completing read.
When I execute the get-tables function, I get the following error in the
*Messages* buffer
Starting the BeanShell. Please wait...
Error evaluating Lisp result of Java expression evaluation.
Java expression: localMetaData.getTables();.
Java evaluation result: BeanShell 1.1a16 - by Pat Niemeyer ([EMAIL PROTECTED])
.
condition-case: Error evaluating Java expresson. See *Messages* buffer.
I then look in the *bsh* buffer and I see the elisp result which should
have been eval'd into Elisp (which was completely missed by the second
bsh-eval). I'm guessing that the elisp execution is faster than my java
code's execution and that the bsh-eval isn't forcing a wait on each line
to finish.
I'd like to fix this in your beanshell.el. Maybe have a third
functionality which doesn't eval, but also wait on the process to
finish.
An issue for me would be testing any changes for affects to the jde. If
you are open to the idea, would you be willing to run a testing suite
against any new beanshell.el patches I might author, or show me how to
test the jde?
What do you think?
On Mon, 3 Jun 2002, [EMAIL PROTECTED] wrote:
> Hi Galen,
>
> The JDE uses Java primarily for tasks that require introspection,
> e.g., determining all the methods, fields, and ancestors of a
> class. Using Java for this purpose requires some scheme for
> interfacing the JDEE to a virtual machine.
>
> The approach that the JDE uses is based on the BeanShell. As you may
> know, the BeanShell is an interpreter that executes Java
> statements. The JDE includes a command-line interface to the BeanShell
> that allows a user to start and terminate a BeanShell session and
> interact with the BeanShell in an Emacs buffer. The JDEE passes Java
> statements entered in the buffer to the BeanShell via interprocess I/O
> for evaluation and displays the result in the buffer.
>
> The JDEE also includes a function, jde-jeval-r, that allows a Lisp
> program to use the same interface to send Java statements to the
> BeanShell for evaluation. jde-jeval-r assumes that the result of
> evaluating the Java statement is a Lisp expression and evaluates
> the Lisp expression. The idea here is that the JDEE speaks to Java
> (via the BeanShell) in Java and Java speaks back (via standard out on
> the BeanShell process) in Elisp. This, of course, assumes that the
> Java side of the dialogue has been written specifically to communicate
> with the Elisp side.
>
> For example, here is a complete implementation for an "Echo wizard" in
> which the Java side echod a string sent to it by the Elisp side in the
> Emacs minibuffer, using the Elisp "message" function.
>
>
> // Java file EchoWizard.java
> // compile this file and make sure that it
> // in jde-global-classpath (the BeanShell always
> // starts with jde-global-classpath
> package jde.wizard;
> public class EchoWizard {
>
> public static void echo(String msg) {
> System.out.println("(message \"" + msg + "\")");
> }
>
>}
>
> ;; echo-wizard.el
> (require 'jde)
> (jde-jeval-r "jde.wizard.EchoWizard.echo(\"sleepy hollow\");")
>
> You can find numerous instances of this "design pattern" in
> the JDE Elisp source code by searching for jde-jeval-r. The
> Java side of the dialog initiated by the Lisp code resides
> in the java subdirectory of the JDE directory.
>
> I hope this is clear. If not, I'd be happy to answer any further
> questions you have.
>
> - Paul
>
>
> Galen Boyer writes:
> > Paul,
> >
> > Have you written a simple elisp function and a couple of java
> > classes it calls that you could point me to in the JDE code?
> >
> > I'm starting a little project to use jdbc to build a dynamic sql
> > builder within Emacs and would like to use your code as my
> > blueprint. I've spent some time in your code and am a bit stumped.
> > I'm looking for an overall understanding of how and when you write
> > elisp versus java and how you keep a JVM running and available for
> > Emacs but your code is very sophisticated, which is hindering my
> > simplistic understanding needs. If there is a "sort of" simple
> > example where you have an elisp class, with methods that invoke a
> > simple java class I'd appreciate what their names are, and maybe a
> > couple of lines explaining the mapping. Actually, the examples
> > don't need to be simple as much as I need to know what the starting
> > elisp code is and when this elisp code actually ends for a
> > particular JDE behaviour. This would allow me to stay on track as
> > I gleam your strategies from your code.
> >
> > Thanks.
> > --
> > Galen deForest Boyer
> > Sweet dreams and flying machines in pieces on the ground.
> >
--
Galen deForest Boyer
Sweet dreams and flying machines in pieces on the ground.