package net.ion.script;
import java.io.File;
import java.util.Date;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import junit.framework.TestCase;
import net.ion.craken.node.ReadSession;
import net.ion.craken.node.Repository;
import net.ion.craken.node.crud.Craken;
import net.ion.framework.util.InfinityThread;
import net.ion.nradon.EventSourceConnection;
import net.ion.nradon.EventSourceHandler;
import net.ion.nradon.EventSourceMessage;
import net.ion.nradon.Radon;
import net.ion.nradon.WebSocketConnection;
import net.ion.nradon.WebSocketHandler;
import net.ion.nradon.ajax.BroadEchoWebSocket;
import net.ion.nradon.config.RadonConfiguration;
import net.ion.nradon.handler.SimpleStaticFileHandler;
import net.ion.script.rhino.MyOutput;
import net.ion.script.rhino.Scripter;
public class TestSlide extends TestCase {
public void testSlide() throws Exception {
ExecutorService webThread = Executors.newSingleThreadExecutor();
final Pusher pusher = new Pusher();
Scripter rhiner = Scripter.create().start() ;
rhiner.start() ;
Craken r = Craken.inmemoryCreateWithTest();
r.start() ;
Radon radon = RadonConfiguration.newBuilder(9000)
.add("/websocket/{id}", new BroadEchoWebSocket())
.add("/script/{id}", new ScriptWebSocket(rhiner, r))
.add("/events/{id}", new EventSourceHandler() {
public void onOpen(EventSourceConnection conn) throws Exception {
pusher.addConnection(conn);
}
public void onClose(EventSourceConnection conn) throws Exception {
pusher.removeConnection(conn);
}
})
.add("/*", new SimpleStaticFileHandler(new File("./resource/docs/"))).createRadon() ;
radon.start().get() ;
pusher.pushPeriodicallyOn(webThread);
new InfinityThread().startNJoin() ;
}
private static class ScriptWebSocket implements WebSocketHandler {
private List<WebSocketConnection> connections = new CopyOnWriteArrayList<WebSocketConnection>() ;
private final Scripter engine;
private final Repository r;
public ScriptWebSocket(Scripter engine, Repository r) {
this.engine = engine ;
this.r = r ;
}
@Override
public void onClose(WebSocketConnection wconn) throws Throwable {
connections.remove(wconn) ;
}
@Override
public void onMessage(WebSocketConnection wconn, String script) throws Throwable {
ReadSession session = r.login("test");
final MyOutput output = new MyOutput();
session.credential().tracer(output) ;
engine.directCall(wconn.getString("id"), script) ;
wconn.send(output.readOut()) ;
}
@Override
public void onMessage(WebSocketConnection wconn, byte[] abyte0) throws Throwable {
onMessage(wconn, new String(abyte0)) ;
}
@Override
public void onOpen(WebSocketConnection wconn) throws Throwable {
connections.add(wconn) ;
}
@Override
public void onPing(WebSocketConnection wconn, byte[] abyte0) throws Throwable {
}
@Override
public void onPong(WebSocketConnection wconn, byte[] abyte0) throws Throwable {
}
}
private static class Pusher {
private List<EventSourceConnection> connections = new CopyOnWriteArrayList<EventSourceConnection>() ;
private int count = 1;
public void addConnection(EventSourceConnection conn) {
conn.data("id", count++);
connections.add(conn);
broadcast("Client " + conn.data("id") + " joined");
}
public void removeConnection(EventSourceConnection conn) {
connections.remove(conn);
broadcast("Client " + conn.data("id") + " left");
}
public void pushPeriodicallyOn(ExecutorService webThread) throws InterruptedException, ExecutionException {
while (true) {
Thread.sleep(1000 * 2) ;
webThread.submit(new Runnable() {
public void run() {
broadcast(new Date().toString());
}
}).get();
}
}
private void broadcast(String message) {
for (EventSourceConnection connection : connections) {
connection.send(new EventSourceMessage(message + ", clients:" + connections.size()));
}
}
}
}