import bsh.Interpreter;
public class ShellPage extends SimpleWriter {
+ private RConsole cons = new RConsole();
+ private Interpreter ip = new Interpreter(cons);
+
+ private static class RConsole implements bsh.ConsoleInterface {
+ public Console back;
+ Reader in = new StringReader("");
+
+ public void error(Object msg) {
+ if(back != null)
+ back.error(msg);
+ }
+
+ public void print(Object msg) {
+ if(back != null)
+ back.print(msg);
+ }
+
+ public void println(Object msg) {
+ if(back != null)
+ back.println(msg);
+ }
+
+ public PrintStream getOut() {
+ if(back == null)
+ return(null);
+ return(back.getOut());
+ }
+
+ public PrintStream getErr() {
+ if(back == null)
+ return(null);
+ return(back.getErr());
+ }
+
+ public Reader getIn() {
+ if(back == null)
+ return(null);
+ return(in);
+ }
+ }
+
private static class Console implements bsh.ConsoleInterface {
ByteArrayOutputStream obuf = new ByteArrayOutputStream();
ByteArrayOutputStream ebuf = new ByteArrayOutputStream();
out.println("<h1>Shell</h1>");
if((req.method() == "POST") && (cmd != null)) {
Console cons = new Console();
- Interpreter ip = new Interpreter(cons);
- Object resp;
- try {
- ip.set("req", req);
- resp = ip.eval(cmd);
- out.println("<pre>");
- out.println(Misc.htmlq((resp == null)?"(null)":(resp.toString())));
- out.println("</pre>");
- } catch(bsh.EvalError exc) {
- out.println("<h2>Evaluation error</h2>");
- out.println("<pre>");
- out.print(exc.toString());
- out.println("</pre>");
- if(exc instanceof bsh.TargetError) {
- bsh.TargetError te = (bsh.TargetError)exc;
- out.println("<h3>Target error</h3>");
- out.println("<pre>");
- te.getTarget().printStackTrace(out);
- out.println("</pre>");
+ synchronized(ip) {
+ this.cons.back = cons;
+ try {
+ Object resp;
+ try {
+ ip.set("req", req);
+ resp = ip.eval(cmd);
+ out.println("<pre>");
+ out.println(Misc.htmlq((resp == null)?"(null)":(resp.toString())));
+ out.println("</pre>");
+ } catch(bsh.EvalError exc) {
+ out.println("<h2>Evaluation error</h2>");
+ out.println("<pre>");
+ out.print(exc.toString());
+ out.println("</pre>");
+ if(exc instanceof bsh.TargetError) {
+ bsh.TargetError te = (bsh.TargetError)exc;
+ out.println("<h3>Target error</h3>");
+ out.println("<pre>");
+ te.getTarget().printStackTrace(out);
+ out.println("</pre>");
+ }
+ }
+ } finally {
+ this.cons.back = null;
}
}
String eo = new String(cons.obuf.toByteArray(), Misc.utf8);
--- /dev/null
+package dolda.jsvc.util;
+
+import dolda.jsvc.*;
+import java.lang.reflect.*;
+
+public class PerSession implements Responder {
+ private final Class<?> rcl;
+ private final Class<?> dcl;
+
+ public PerSession(Class<?> rcl, Class<?> dcl) {
+ this.rcl = rcl;
+ this.dcl = dcl;
+ }
+
+ public PerSession(Class<?> rcl) {
+ this(rcl, null);
+ }
+
+ private Object makedata(Session sess) {
+ try {
+ try {
+ return(dcl.getConstructor().newInstance());
+ } catch(NoSuchMethodException e) {
+ }
+ try {
+ return(dcl.getConstructor(Session.class).newInstance(sess));
+ } catch(NoSuchMethodException e) {
+ }
+ } catch(InstantiationException e) {
+ throw(new RuntimeException(e));
+ } catch(IllegalAccessException e) {
+ throw(new RuntimeException(e));
+ } catch(InvocationTargetException e) {
+ throw(new RuntimeException(e));
+ }
+ throw(new RuntimeException("Found no way to create an instance of " + dcl.getName()));
+ }
+
+ private Object getdata(Session sess) {
+ Object d = sess.get(dcl, null);
+ if(d == null) {
+ d = makedata(sess);
+ sess.put(dcl, d);
+ }
+ return(d);
+ }
+
+ private Responder create(Session sess) {
+ try {
+ if(dcl != null) {
+ try {
+ return((Responder)rcl.getMethod("responder", dcl).invoke(null, getdata(sess)));
+ } catch(NoSuchMethodException e) {
+ }
+ }
+ try {
+ return((Responder)rcl.getMethod("responder", Session.class).invoke(null, sess));
+ } catch(NoSuchMethodException e) {
+ }
+ try {
+ return((Responder)rcl.getMethod("responder").invoke(null));
+ } catch(NoSuchMethodException e) {
+ }
+ if(dcl != null) {
+ try {
+ return((Responder)rcl.getConstructor(dcl).newInstance(getdata(sess)));
+ } catch(NoSuchMethodException e) {
+ }
+ }
+ try {
+ return((Responder)rcl.getConstructor(Session.class).newInstance(sess));
+ } catch(NoSuchMethodException e) {
+ }
+ try {
+ return((Responder)rcl.getConstructor().newInstance());
+ } catch(NoSuchMethodException e) {
+ }
+ } catch(InstantiationException e) {
+ throw(new RuntimeException(e));
+ } catch(IllegalAccessException e) {
+ throw(new RuntimeException(e));
+ } catch(InvocationTargetException e) {
+ throw(new RuntimeException(e));
+ }
+ throw(new RuntimeException("Found no way to create a responder from the class " + rcl.getName()));
+ }
+
+ public void respond(Request req) {
+ Session sess = Session.get(req);
+ Responder resp;
+ synchronized(sess) {
+ resp = (Responder)sess.get(rcl, null);
+ if(resp == null) {
+ resp = create(sess);
+ sess.put(rcl, resp);
+ }
+ }
+ resp.respond(req);
+ }
+}