Changeset 96
- Timestamp:
- 07/04/13 20:29:50 (11 years ago)
- Location:
- java/main
- Files:
-
- 23 added
- 5 deleted
- 81 edited
Legend:
- Unmodified
- Added
- Removed
-
java/main/pom.xml
r88 r96 147 147 <workingDirectory>/home/psniegowski/mgr/framsticks</workingDirectory> 148 148 <arguments> 149 < !-- <argument>-ea</argument> -->149 <argument>-ea</argument> 150 150 <argument>-Xdebug</argument> 151 151 <argument>-Xrunjdwp:transport=dt_socket,address=4711,server=y,suspend=n</argument> -
java/main/src/main/java/com/framsticks/communication/ClientConnection.java
r90 r96 11 11 import com.framsticks.util.dispatching.Dispatcher; 12 12 import com.framsticks.util.dispatching.Dispatching; 13 import com.framsticks.util.dispatching.JoinableState; 13 14 import com.framsticks.util.lang.Pair; 14 15 import com.framsticks.util.lang.Strings; 16 17 import org.apache.log4j.Level; 15 18 import org.apache.log4j.Logger; 16 19 17 20 import java.io.IOException; 18 21 import java.net.Socket; 19 import java.net.SocketException;20 22 import java.util.*; 21 23 import java.util.regex.Matcher; … … 39 41 } 40 42 43 public ClientConnection(String address) { 44 super(address, "client connection"); 45 Matcher matcher = addressPattern.matcher(address); 46 if (!matcher.matches()) { 47 log.fatal("invalid address: " + address); 48 hostName = null; 49 port = 0; 50 return; 51 } 52 hostName = matcher.group(1); 53 port = matcher.group(3) != null ? Integer.parseInt(matcher.group(3)) : 9009; 54 } 41 55 42 56 protected StateFunctor connectedFunctor; 43 44 @Override45 protected void joinableStart() {46 try {47 log.debug("connecting to " + address);48 49 socket = new Socket(hostName, port);50 51 socket.setSoTimeout(500);52 53 log.debug("connected to " + hostName + ":" + port);54 connected = true;55 runThreads();56 57 connectedFunctor.call(null);58 } catch (SocketException e) {59 log.error("failed to connect: " + e);60 connectedFunctor.call(e);61 } catch (IOException e) {62 log.error("buffer creation failure");63 connectedFunctor.call(e);64 // close();65 }66 }67 68 57 69 58 private static abstract class InboundMessage { … … 78 67 currentFilePath = path; 79 68 } 69 80 70 protected void finishCurrentFile() { 81 71 if (currentFileContent == null) { … … 84 74 files.add(new File(currentFilePath, new ListSource(currentFileContent))); 85 75 currentFilePath = null; 86 currentFileContent = null;76 currentFileContent = null; 87 77 } 88 78 89 79 public abstract void startFile(String path); 90 80 91 public void addLine(String line) {81 public final void addLine(String line) { 92 82 assert line != null; 93 83 assert currentFileContent != null; 94 currentFileContent.add(line .substring(0, line.length() - 1));84 currentFileContent.add(line); 95 85 } 96 86 … … 127 117 public void startFile(String path) { 128 118 finishCurrentFile(); 129 if ( path == null) {119 if (!Strings.notEmpty(path)) { 130 120 assert request instanceof ApplicationRequest; 131 path = ((ApplicationRequest)request).getPath(); 132 } 121 path = ((ApplicationRequest) request).getPath(); 122 } 123 Strings.assureNotEmpty(path); 133 124 initCurrentFile(path); 134 125 } 135 126 136 127 public void eof() { 128 assert Strings.notEmpty(currentFilePath); 137 129 finishCurrentFile(); 138 130 //no-operation … … 153 145 } 154 146 } 147 155 148 private Map<Integer, SentQuery<?>> queryMap = new HashMap<>(); 156 157 149 158 150 protected final String hostName; … … 161 153 private static Pattern addressPattern = Pattern.compile("^([^:]*)(:([0-9]+))?$"); 162 154 163 public ClientConnection(String address) {164 super(address);165 Matcher matcher = addressPattern.matcher(address);166 if (!matcher.matches()) {167 log.fatal("invalid address: " + address);168 hostName = null;169 port = 0;170 return;171 }172 hostName = matcher.group(1);173 port = matcher.group(3) != null ? Integer.parseInt(matcher.group(3)) : 9009;174 }175 155 176 156 private SentQuery<?> currentlySentQuery; 177 178 157 179 158 public <C extends Connection> void send(Request request, ResponseCallback<C> callback) { … … 184 163 public <C> void send(Request request, Dispatcher<C> dispatcher, ResponseCallback<? extends C> callback) { 185 164 186 if ( !isConnected()) {165 if (getState().ordinal() > JoinableState.RUNNING.ordinal()) { 187 166 log.fatal("not connected"); 188 167 return; 189 168 } 169 190 170 final SentQuery<C> sentQuery = new SentQuery<C>(); 191 171 sentQuery.request = request; … … 193 173 sentQuery.dispatcher = dispatcher; 194 174 195 senderThread.dispatch(new RunAt<Connection>() {175 senderThread.dispatch(new RunAt<Connection>() { 196 176 @Override 197 177 public void run() { … … 220 200 message.append(" ").append(id); 221 201 } 202 message.append(" "); 222 203 sentQuery.request.construct(message); 223 204 String out = message.toString(); 224 205 225 206 output.println(out); 207 output.flush(); 226 208 log.debug("sending query: " + out); 227 209 … … 234 216 notifyAll(); 235 217 } 236 */ 237 } 238 218 */ 219 } 239 220 240 221 @Override … … 272 253 } 273 254 274 public void sendQueryVersion(final int version, finalStateFunctor stateFunctor) {275 send(new VersionRequest().version(version), new StateCallback<Connection>( ) {255 public void sendQueryVersion(final int version, StateFunctor stateFunctor) { 256 send(new VersionRequest().version(version), new StateCallback<Connection>(stateFunctor) { 276 257 @Override 277 public void call(Exception e) { 278 if (e != null) { 279 log.fatal("failed to upgrade protocol to version: " + version); 280 return; 281 } 258 public void callImpl() { 282 259 protocolVersion = version; 283 260 if (version < 4) { 284 261 /** it is an implicit loop here*/ 285 sendQueryVersion(version + 1, stateFunctor);262 sendQueryVersion(version + 1, move()); 286 263 return; 287 264 } 288 send(new UseRequest().feature("request_id"), new StateCallback<Connection>( ) {265 send(new UseRequest().feature("request_id"), new StateCallback<Connection>(move()) { 289 266 @Override 290 public void call(Exception e) { 291 requestIdEnabled = e == null; 292 /* 293 synchronized (ClientConnection.this) { 294 ClientConnection.this.notifyAll(); 295 } 296 */ 297 if (!requestIdEnabled) { 298 log.fatal("protocol negotiation failed"); 299 stateFunctor.call(new Exception("protocol negotiation failed", e)); 300 return; 301 } 302 stateFunctor.call(null); 267 public void handle(FramsticksException exception) { 268 requestIdEnabled = false; 269 log.fatal("protocol negotiation failed"); 270 super.handle(new FramsticksException().msg("protocol negotiation failed").cause(exception)); 271 } 272 273 @Override 274 public void callImpl() { 275 requestIdEnabled = true; 303 276 } 304 277 }); … … 307 280 }); 308 281 } 309 310 282 311 283 private synchronized SentQuery<?> fetchQuery(Integer id, boolean remove) { … … 348 320 349 321 protected void processEvent(String rest) { 350 Matcher matcher = eventPattern.matcher(rest);322 Matcher matcher = Request.EVENT_PATTERN.matcher(rest); 351 323 if (!matcher.matches()) { 352 324 log.error("invalid event line: " + rest); … … 363 335 } 364 336 365 366 337 protected void processMessageStartingWith(String line) { 367 Pair<String, String> command = Strings.splitIntoPair(line, ' ', "\n"); 368 if (command.first.equals("event")) { 369 processEvent(command.second); 370 return; 371 } 372 Pair<Integer, String> rest = parseRest(command.second); 373 374 if (command.first.equals("file")) { 375 SentQuery<?> sentQuery = fetchQuery(rest.first, false); 376 sentQuery.startFile(rest.second); 377 processMessage(sentQuery); 378 return; 379 } 380 381 SentQuery<?> sentQuery = fetchQuery(rest.first, true); 382 if (sentQuery == null) { 383 return; 384 } 385 log.debug("parsing response for request " + sentQuery); 386 387 sentQuery.dispatchResponseProcess(new Response(command.first.equals("ok"), rest.second, sentQuery.getFiles())); 338 try { 339 Pair<CharSequence, CharSequence> command = Request.takeIdentifier(line); 340 if (command.first.equals("event")) { 341 processEvent(command.second.toString()); 342 return; 343 } 344 Pair<Integer, CharSequence> rest = takeRequestId(command.second); 345 346 if (command.first.equals("file")) { 347 SentQuery<?> sentQuery = fetchQuery(rest.first, false); 348 sentQuery.startFile(rest.second.toString()); 349 processMessage(sentQuery); 350 return; 351 } 352 353 SentQuery<?> sentQuery = fetchQuery(rest.first, true); 354 if (sentQuery == null) { 355 return; 356 } 357 log.debug("parsing response for request " + sentQuery); 358 359 sentQuery.dispatchResponseProcess(new Response(command.first.equals("ok"), rest.second.toString(), sentQuery.getFiles())); 360 } catch (FramsticksException e) { 361 throw new FramsticksException().msg("failed to process message").arg("starting with line", line).cause(e); 362 } 388 363 } 389 364 390 365 @Override 391 366 protected void receiverThreadRoutine() { 392 while (connected) { 367 while (isRunning() && !isConnected()) { 368 log.debug("connecting to " + address); 369 try { 370 socket = new Socket(hostName, port); 371 } catch (IOException e) { 372 log.info(this + " failed to connect (retrying): " + e); 373 Dispatching.sleep(0.5); 374 } 375 } 376 377 log.debug(this + " connected"); 378 try { 379 socket.setSoTimeout(500); 380 setupStreams(); 381 } catch (Exception e) { 382 throw new FramsticksException().msg("failed to initialize socket").cause(e).arg("connection", this); 383 } 384 385 connectedFunctor.call(); 386 387 while (isRunning() && isConnected()) { 393 388 try { 394 389 processMessageStartingWith(getLine()); 395 390 } catch (Exception e) { 391 log.log(isRunning() ? Level.ERROR : Level.DEBUG, "caught exception: ", e); 396 392 break; 397 393 } 398 394 } 399 }400 401 395 interrupt(); 396 finish(); 397 } 402 398 } -
java/main/src/main/java/com/framsticks/communication/Connection.java
r90 r96 12 12 import java.net.Socket; 13 13 import java.net.SocketTimeoutException; 14 import java.util.regex.Matcher;15 import java.util.regex.Pattern;16 14 17 15 import com.framsticks.util.dispatching.AbstractJoinable; … … 33 31 protected Socket socket = null; 34 32 35 protected volatile boolean connected = false;36 37 33 public boolean requestIdEnabled = false; 38 34 … … 43 39 } 44 40 protected final String address; 41 protected final String description; 45 42 46 43 protected final Thread<Connection> senderThread = new Thread<>(); 47 44 protected final Thread<Connection> receiverThread = new Thread<>(); 48 protected final JoinableCollection<Thread<Connection>> threads = new JoinableCollection<>(true); 45 protected final JoinableCollection<Thread<Connection>> threads = new JoinableCollection<>(); 46 47 protected void setUpThreadNames(String name) { 48 } 49 49 50 50 /** 51 51 * 52 52 */ 53 public Connection(String address ) {53 public Connection(String address, String description) { 54 54 this.address = address; 55 this.description = description; 56 threads.setObservableName(address + " connection threads"); 55 57 threads.add(senderThread); 56 58 threads.add(receiverThread); 57 } 58 public boolean isConnected() { 59 return connected; 60 } 61 62 63 protected static final String ARGUMENT_PATTERN_FRAGMENT = "((?:\\S+)|(?:\"[^\"]*\"))"; 64 protected static final Pattern requestIdEnabledPattern = Pattern.compile("^\\s*([0-9]+)(?:\\s+" + ARGUMENT_PATTERN_FRAGMENT + ")?\\n$"); 65 protected static final Pattern requestIDisabledPattern = Pattern.compile("^\\s*" + ARGUMENT_PATTERN_FRAGMENT + "?\\n$"); 66 protected static final Pattern eventPattern = Pattern.compile("^\\s*(\\S+)\\s*(\\S+)\\n"); 67 68 69 protected final Pair<Integer, String> parseRest(String rest) { 70 Matcher matcher = (requestIdEnabled ? requestIdEnabledPattern : requestIDisabledPattern).matcher(rest); 71 if (!matcher.matches()) { 72 log.fatal("unmatched first line of input: " + rest); 73 return null; 74 } 75 return new Pair<Integer, String>(requestIdEnabled ? Integer.parseInt(matcher.group(1)) : null, matcher.group(requestIdEnabled ? 2 : 1)); 59 60 senderThread.setName(description + " thread " + address + " sender"); 61 receiverThread.setName(description + " thread " + address + " receiver"); 62 } 63 64 public synchronized boolean isConnected() { 65 return socket != null && socket.isConnected(); 66 } 67 68 69 // protected static final String ARGUMENT_PATTERN_FRAGMENT = "((?:\\S+)|(?:\\\"[^\"]*\\\"))"; 70 // protected static final Pattern REQUEST_ID_ENABLED_PATTERN = Pattern.compile("^\\s*([0-9]+)(?:\\s+" + ARGUMENT_PATTERN_FRAGMENT + ")?$"); 71 // protected static final Pattern REQUEST_ID_DISABLED_PATTERN = Pattern.compile("^\\s*" + ARGUMENT_PATTERN_FRAGMENT + "?$"); 72 73 // // protected final Pair<String, String> breakLine(String line) 74 // protected final Pair<Integer, String> parseRest(String rest) { 75 // Matcher matcher = (requestIdEnabled ? REQUEST_ID_ENABLED_PATTERN : REQUEST_ID_DISABLED_PATTERN).matcher(rest); 76 // if (!matcher.matches()) { 77 // log.fatal("unmatched first line of input: '" + rest + "'"); 78 // return null; 79 // } 80 // return new Pair<Integer, String>(requestIdEnabled ? Integer.parseInt(matcher.group(1)) : null, matcher.group(requestIdEnabled ? 2 : 1)); 81 // } 82 83 protected final Pair<Integer, CharSequence> takeRequestId(CharSequence line) { 84 return Request.takeRequestId(requestIdEnabled, line); 76 85 } 77 86 … … 81 90 int iterator = 0; 82 91 int bufferStart = 0; 83 char[] readBuffer = new char[BUFFER_LENGTH];92 final char[] readBuffer = new char[BUFFER_LENGTH]; 84 93 85 94 protected String getLine() { 86 StringBuilder lineBuffer = new StringBuilder();95 final StringBuilder lineBuffer = new StringBuilder(); 87 96 try { 88 97 while (!Thread.interrupted()) { … … 92 101 continue; 93 102 } 94 lineBuffer.append(readBuffer, bufferStart, iterator - bufferStart + 1); 103 /** Do not append new line. */ 104 lineBuffer.append(readBuffer, bufferStart, iterator - bufferStart); 95 105 ++iterator; 96 106 bufferStart = iterator; 97 107 return lineBuffer.toString(); 98 108 } 99 lineBuffer.append(readBuffer, bufferStart, readChars - bufferStart); 109 final int length = readChars - bufferStart; 110 if (length > 0) { 111 assert bufferStart >= 0 && bufferStart < BUFFER_LENGTH; 112 assert bufferStart + length <= BUFFER_LENGTH; 113 lineBuffer.append(readBuffer, bufferStart, length); 114 } 100 115 101 116 readChars = 0; … … 118 133 protected abstract void receiverThreadRoutine(); 119 134 120 protected void setUpThread(Thread<Connection> thread, String name) { 121 thread.setName("connection thread " + address + " " + name); 122 } 123 124 protected void runThreads() { 135 136 protected void setupStreams() { 125 137 try { 126 138 output = new PrintWriter(new OutputStreamWriter(socket.getOutputStream(), Encoding.getFramsticksCharset()), true); 127 139 input = new BufferedReader(new InputStreamReader(socket.getInputStream(), Encoding.getFramsticksCharset())); 140 synchronized (this) { 141 this.notifyAll(); 142 } 128 143 } catch (IOException e) { 129 log.error("buffer creation failure"); 130 return; 144 throw new FramsticksException().msg("failed to setup streams").cause(e).arg("connection", this); 131 145 } 132 133 setUpThread(senderThread, "sender");134 setUpThread(receiverThread, "receiver");135 Dispatching.use(threads, this);136 137 receiverThread.dispatch(new RunAt<Connection>() {138 @Override139 public void run() {140 receiverThreadRoutine();141 }142 });143 144 146 } 145 147 … … 153 155 } 154 156 155 @Override156 protected void joinableInterrupt() {157 protocolVersion = -1;158 159 connected = false;160 Dispatching.drop(threads, this);161 162 // finish();163 }164 157 165 158 @Override … … 193 186 194 187 @Override 188 public String getName() { 189 return description + " " + address; 190 } 191 192 @Override 193 protected void joinableStart() { 194 Dispatching.use(threads, this); 195 196 senderThread.dispatch(new RunAt<Connection>() { 197 @Override 198 public void run() { 199 synchronized (Connection.this) { 200 while (state.equals(JoinableState.RUNNING) && output == null) { 201 Dispatching.wait(Connection.this, 500); 202 } 203 } 204 } 205 }); 206 207 receiverThread.dispatch(new RunAt<Connection>() { 208 @Override 209 public void run() { 210 receiverThreadRoutine(); 211 } 212 }); 213 } 214 215 @Override 216 protected void joinableInterrupt() { 217 protocolVersion = -1; 218 Dispatching.drop(threads, this); 219 finish(); 220 } 221 222 223 @Override 195 224 protected void joinableJoin() throws InterruptedException { 196 225 Dispatching.join(threads); 197 198 226 } 199 227 -
java/main/src/main/java/com/framsticks/communication/File.java
r77 r96 1 1 package com.framsticks.communication; 2 2 3 import java.util.ArrayList; 4 import java.util.List; 5 6 import javax.annotation.Nonnull; 7 3 8 import com.framsticks.params.SourceInterface; 9 // import com.framsticks.util.lang.Strings; 4 10 5 11 /** … … 7 13 */ 8 14 public final class File { 9 10 15 protected final String path; 16 protected final SourceInterface content; 11 17 12 public File(String path, SourceInterface content) { 13 this.path = path; 14 this.content = content; 15 } 18 public File(@Nonnull String path, @Nonnull SourceInterface content) { 19 // assert Strings.notEmpty(path); 20 this.path = path; 21 this.content = content; 22 } 16 23 17 18 19 24 public String getPath() { 25 return path; 26 } 20 27 21 public SourceInterface getContent() { 22 return content; 23 } 28 public SourceInterface getContent() { 29 return content; 30 } 31 32 public static List<File> single(File file) { 33 List<File> result = new ArrayList<File>(); 34 result.add(file); 35 return result; 36 } 24 37 } -
java/main/src/main/java/com/framsticks/communication/Request.java
r84 r96 1 1 package com.framsticks.communication; 2 2 3 import java.util.regex.Matcher; 4 import java.util.regex.Pattern; 5 3 6 import com.framsticks.communication.queries.*; 7 import com.framsticks.util.FramsticksException; 8 import com.framsticks.util.lang.Pair; 4 9 5 10 /** … … 8 13 public abstract class Request { 9 14 15 public abstract String getCommand(); 16 17 protected abstract StringBuilder construct(StringBuilder buffer); 18 19 20 21 10 22 public static void quoteValue(StringBuilder builder, String value) { 11 23 String quote = ((value.indexOf(' ') > 0) || (value.length() == 0) ? "\"" : ""); … … 13 25 } 14 26 15 public abstract String getCommand(); 16 17 protected abstract StringBuilder construct(StringBuilder buffer); 18 //private static Pattern queryPattern = Pattern.compile("^(\\S+)\\s+(\\S+)(?:\\s+(\\S+))?$"); 27 public static Request parse(CharSequence type, CharSequence rest) { 28 final Request request = Request.createRequestByTypeString(type.toString()); 29 request.parseRest(rest); 30 return request; 31 } 19 32 20 33 public static Request createRequestByTypeString(String type) { 21 if (type.equals("get")) { 22 return new GetRequest(); 34 switch (type) { 35 case "get": return new GetRequest(); 36 case "set": return new SetRequest(); 37 case "info": return new InfoRequest(); 38 case "call": return new CallRequest(); 39 case "reg": return new RegistrationRequest(); 40 case "use": return new UseRequest(); 41 case "version": return new VersionRequest(); 23 42 } 24 if (type.equals("set")) { 25 return new SetRequest(); 26 } 27 if (type.equals("info")) { 28 return new InfoRequest(); 29 } 30 if (type.equals("call")) { 31 return new CallRequest(); 32 } 33 if (type.equals("reg")) { 34 return new RegistrationRequest(); 35 } 36 if (type.equals("use")) { 37 return new UseRequest(); 38 } 39 if (type.equals("version")) { 40 return new VersionRequest(); 41 } 42 return null; 43 throw new FramsticksException().msg("unknown request type").arg("type", type); 43 44 } 44 45 45 public abstract void parseRest(Stringrest);46 public abstract CharSequence parseRest(CharSequence rest); 46 47 47 48 @Override 48 49 public String toString() { 49 return construct(new StringBuilder().append(getCommand())).toString();50 return getCommand() + " request"; 50 51 } 52 53 public String stringRepresentation() { 54 return construct(new StringBuilder().append(getCommand()).append(" ")).toString(); 55 } 56 57 public static final Pattern EVENT_PATTERN = Pattern.compile("^\\s*(\\S+)\\s*(\\S+)"); 58 59 public static final Pattern STRING_BREAKER_PATTERN = Pattern.compile("^\\s*(?:(?:\\\"([^\"]*)\\\")|([^ ]+))\\s*(.*)$"); 60 public static final Pattern IDENTIFIER_BREAKER_PATTERN = Pattern.compile("^\\s*([^ ]+)\\s*(.*)$"); 61 62 // public static Matcher match(Pattern pattern, CharSequence line) { 63 // Matcher matcher = pattern.matcher(line); 64 // if (!matcher.matches()) { 65 // return null; 66 // // throw new FramsticksException().msg("failed to take").arg("pattern", pattern).arg("line", line); 67 // } 68 // return matcher; 69 // } 70 71 public static Pair<CharSequence, CharSequence> takeIdentifier(CharSequence line) { 72 Matcher matcher = IDENTIFIER_BREAKER_PATTERN.matcher(line); 73 if (!matcher.matches()) { 74 return null; 75 } 76 return new Pair<CharSequence, CharSequence>(line.subSequence(matcher.start(1), matcher.end(1)), line.subSequence(matcher.start(2), matcher.end(2))); 77 } 78 79 public static CharSequence takeGroup(CharSequence input, Matcher matcher, int group) { 80 // return (matcher.start(group) == matcher.end(group)) ? null : input.subSequence(matcher.start(group), matcher.end(group)); 81 return input.subSequence(matcher.start(group), matcher.end(group)); 82 } 83 84 public static Pair<CharSequence, CharSequence> takeString(CharSequence line) { 85 Matcher matcher = STRING_BREAKER_PATTERN.matcher(line); 86 if (!matcher.matches()) { 87 return null; 88 } 89 assert ((matcher.start(1) == -1) != (matcher.start(2) == -1)); 90 return new Pair<CharSequence, CharSequence>(takeGroup(line, matcher, (matcher.start(1) != -1 ? 1 : 2)), takeGroup(line, matcher, 3)); 91 } 92 93 protected static final Pattern REQUEST_ID_BREAKER_PATTERN = Pattern.compile("^\\s*([0-9]+)\\s*(.*)$"); 94 95 protected final static Pair<Integer, CharSequence> takeRequestId(boolean withId, CharSequence line) { 96 if (withId) { 97 Matcher matcher = REQUEST_ID_BREAKER_PATTERN.matcher(line); 98 if (!matcher.matches()) { 99 return null; 100 } 101 return new Pair<Integer, CharSequence>(Integer.valueOf(takeGroup(line, matcher, 1).toString()), takeGroup(line, matcher, 2)); 102 } 103 return new Pair<Integer, CharSequence>(null, line); 104 } 105 106 public static StringBuilder quoteArgumentIfNeeded(StringBuilder builder, Object argument) { 107 String r = argument.toString(); 108 if (r.indexOf(' ') != -1) { 109 builder.append('"').append(r).append('"'); 110 } else { 111 builder.append(r); 112 } 113 return builder; 114 } 115 51 116 } -
java/main/src/main/java/com/framsticks/communication/Response.java
r77 r96 7 7 */ 8 8 public class Response { 9 10 11 9 protected final boolean ok; 10 protected final String comment; 11 protected final List<File> files; 12 12 13 14 15 16 17 13 public Response(boolean ok, String comment, List<File> files) { 14 this.ok = ok; 15 this.comment = comment; 16 this.files = files; 17 } 18 18 19 20 21 19 public final String getComment() { 20 return comment; 21 } 22 22 23 24 25 23 public final boolean getOk() { 24 return ok; 25 } 26 26 27 28 29 27 public final List<File> getFiles() { 28 return files; 29 } 30 30 31 32 33 31 public final boolean hasFiles() { 32 return files != null && !files.isEmpty(); 33 } 34 34 } -
java/main/src/main/java/com/framsticks/communication/ResponseCallback.java
r85 r96 1 1 package com.framsticks.communication; 2 3 import com.framsticks.util.FramsticksException; 4 import com.framsticks.util.dispatching.ExceptionResultHandler; 2 5 3 6 /** 4 7 * @author Piotr Sniegowski 5 8 */ 6 public interface ResponseCallback<C> { 7 public void process(Response response); 9 public abstract class ResponseCallback<C> implements ExceptionResultHandler { 10 public abstract void process(Response response); 11 12 @Override 13 public void handle(FramsticksException e) { 14 process(new Response(false, e.getMsg(), null)); 15 } 16 8 17 } -
java/main/src/main/java/com/framsticks/communication/ServerConnection.java
r90 r96 3 3 import com.framsticks.communication.queries.*; 4 4 import com.framsticks.params.SourceInterface; 5 import com.framsticks.util.FramsticksException; 6 import com.framsticks.util.lang.Holder; 5 7 import com.framsticks.util.lang.Pair; 6 8 import com.framsticks.util.lang.Strings; 9 10 import org.apache.log4j.Level; 7 11 import org.apache.log4j.Logger; 8 12 … … 20 24 21 25 public ServerConnection(Socket socket, RequestHandler requestHandler) { 22 super( "todo");26 super(socket.getInetAddress().getHostAddress(), "server connection"); 23 27 this.socket = socket; 24 28 this.requestHandler = requestHandler; 25 connected = true;26 29 // socket.setSoTimeout(500); 30 setupStreams(); 27 31 } 28 32 29 @Override30 public String toString() {31 return socket.getInetAddress().getHostAddress();32 }33 33 34 34 @Override 35 35 protected void receiverThreadRoutine() { 36 while (connected) { 37 processNextRequest(); 36 while (isRunning() && isConnected()) { 37 try { 38 processNextRequest(); 39 } catch (Exception e) { 40 log.log((isRunning() ? Level.ERROR : Level.DEBUG), "caught exception: ", e); 41 break; 42 } 38 43 } 44 interrupt(); 45 finish(); 39 46 } 40 47 … … 85 92 output.print(outId); 86 93 if (Strings.notEmpty(response.getComment())) { 87 output.print( ' ');94 output.print(" \""); 88 95 output.print(response.getComment()); 96 output.print('"'); 89 97 } 90 98 output.print('\n'); … … 96 104 97 105 protected void processNextRequest() { 98 String line = getLine(); 99 Pair<String, String> command = Strings.splitIntoPair(line, ' ', "\n"); 100 final Pair<Integer, String> rest = parseRest(command.second); 101 if (rest == null) { 102 respond(new Response(false, "\"invalid input\"", null), null); 106 final Holder<Integer> id = new Holder<>(); 107 final String line = getLine(); 108 try { 109 Pair<CharSequence, CharSequence> command = Request.takeIdentifier(line); 110 final Pair<Integer, CharSequence> rest = takeRequestId(command.second); 111 id.set(rest.first); 112 113 final Request request = Request.parse(command.first, rest.second); 114 115 if (log.isTraceEnabled()) { 116 log.trace("read request: " + request); 117 } 118 119 handleRequest(request, new ResponseCallback<ServerConnection>() { 120 @Override 121 public void process(Response response) { 122 respond(response, rest.first); 123 } 124 }); 125 } catch (FramsticksException e) { 126 e.arg("id", id.get()).arg("line", line); 127 log.error("error: ", e); 128 respond(new Response(false, "invalid input: " + e.getMsg(), null), id.get()); 103 129 return; 104 130 } 105 131 106 final Request request = Request.createRequestByTypeString(command.first);107 if (request == null) {108 respond(new Response(false, "\"invalid input\"", null), null);109 return;110 }111 request.parseRest(rest.second);112 if (log.isTraceEnabled()) {113 log.trace("read request: " + request);114 }115 116 handleRequest(request, new ResponseCallback<ServerConnection>() {117 @Override118 public void process(Response response) {119 respond(response, rest.first);120 }121 });122 }123 124 @Override125 protected void joinableStart() {126 // TODO Auto-generated method stub127 128 132 } 129 133 } -
java/main/src/main/java/com/framsticks/communication/StateCallback.java
r85 r96 1 1 package com.framsticks.communication; 2 2 3 import com.framsticks.util.FramsticksException; 3 4 import com.framsticks.util.StateFunctor; 4 5 … … 6 7 * @author Piotr Sniegowski 7 8 */ 8 public abstract class StateCallback<C> implements ResponseCallback<C>, StateFunctor { 9 public abstract class StateCallback<C> extends ResponseCallback<C> implements StateFunctor { 10 11 12 protected StateFunctor wrapped; 13 14 public StateCallback(StateFunctor wrapped) { 15 this.wrapped = wrapped; 16 } 17 18 public StateCallback() { 19 this.wrapped = null; 20 } 21 22 protected StateFunctor move() { 23 assert wrapped != null; 24 StateFunctor result = wrapped; 25 wrapped = null; 26 return result; 27 } 28 29 protected abstract void callImpl(); 30 31 @Override 32 public final void call() { 33 try { 34 callImpl(); 35 } catch (FramsticksException e) { 36 handle(e); 37 return; 38 } 39 if (wrapped != null) { 40 wrapped.call(); 41 } 42 } 43 44 @Override 45 public void handle(FramsticksException exception) { 46 if (wrapped != null) { 47 wrapped.handle(exception); 48 return; 49 } 50 throw exception; 51 } 52 9 53 @Override 10 54 public void process(Response response) { 11 call(response.getOk() ? null : new Exception(response.getComment())); 55 if (response.getOk()) { 56 call(); 57 } else { 58 handle(new FramsticksException().msg("non-ok response").arg("comment", response.getComment())); 59 } 12 60 } 13 61 } -
java/main/src/main/java/com/framsticks/communication/Subscription.java
r90 r96 7 7 import com.framsticks.util.dispatching.Dispatching; 8 8 import com.framsticks.util.dispatching.RunAt; 9 import com.framsticks.util.FramsticksException; 9 10 import com.framsticks.util.StateFunctor; 10 11 import org.apache.log4j.Logger; … … 52 53 if (!response.getOk()) { 53 54 log.error("failed to unsunscribe " + this + ": " + response.getComment()); 54 stateFunctor. call(new Exception(response.getComment()));55 stateFunctor.handle(new FramsticksException().msg("unsubscription failed").arg("comment", response.getComment())); 55 56 return; 56 57 } 57 58 assert response.hasFiles(); 58 59 log.debug("unsunscribed " + this); 59 stateFunctor.call( null);60 stateFunctor.call(); 60 61 } 61 62 }); -
java/main/src/main/java/com/framsticks/communication/queries/ApplicationRequest.java
r85 r96 2 2 3 3 import com.framsticks.communication.Request; 4 import com.framsticks.util.lang.Delimeted; 4 import com.framsticks.util.lang.Pair; 5 import com.framsticks.util.lang.Strings; 5 6 6 import java.util.Collection;7 7 8 8 /** … … 12 12 13 13 protected String path; 14 protected String fields;15 14 16 15 public ApplicationRequest path(String path) { 17 assert path != null;16 Strings.assureNotEmpty(path); 18 17 this.path = path; 19 18 return this; 20 19 } 21 22 public ApplicationRequest field(String field) {23 this.fields = field;24 return this;25 }26 27 public ApplicationRequest fields(Collection<String> fields) {28 Delimeted d = new Delimeted(",", "");29 for (String f : fields) {30 d.append(f);31 }32 return field(d.build());33 }34 35 20 36 21 public String getPath() { … … 38 23 } 39 24 25 40 26 @Override 41 27 protected StringBuilder construct(StringBuilder buffer) { 42 buffer.append(' ').append(path); 43 if (fields != null) { 44 buffer.append(' ').append(fields); 45 } 46 return buffer; 28 return buffer.append(path); 47 29 } 48 30 49 31 @Override 50 public void parseRest(String rest) { 51 path = rest; 32 public CharSequence parseRest(CharSequence rest) { 33 final Pair<CharSequence, CharSequence> p = takeIdentifier(rest); 34 path = p.first.toString(); 35 return p.second; 52 36 } 53 37 -
java/main/src/main/java/com/framsticks/communication/queries/CallRequest.java
r84 r96 1 1 package com.framsticks.communication.queries; 2 2 3 import com.framsticks.communication.Request; 3 import com.framsticks.util.Misc; 4 import com.framsticks.util.lang.Pair; 4 5 6 import java.util.ArrayList; 7 import java.util.Collection; 5 8 import java.util.List; 6 9 … … 10 13 public class CallRequest extends ApplicationRequest { 11 14 12 protected String arguments;13 protected String method;15 protected final List<Object> arguments = new ArrayList<>(); 16 protected String procedure; 14 17 15 public CallRequest setArguments(String arguments) {16 this.arguments = arguments;18 public CallRequest addArguments(String arguments) { 19 // this.arguments = arguments; 17 20 return this; 18 21 } 19 22 20 public CallRequest setArguments(List<String> arguments) { 21 StringBuilder buffer = new StringBuilder(); 22 for (String a : arguments) { 23 buffer.append(" "); 24 Request.quoteValue(buffer, a.trim()); 25 } 26 return this.setArguments(buffer.toString()); 23 /** 24 * @return the arguments 25 */ 26 public List<Object> getArguments() { 27 return arguments; 27 28 } 28 29 29 public CallRequest setMethod(String method) { 30 this.method = method; 30 /** 31 * @return the procedure 32 */ 33 public String getProcedure() { 34 return procedure; 35 } 36 37 /** 38 * @param arguments the arguments to set 39 */ 40 public CallRequest arguments(Collection<Object> arguments) { 41 this.arguments.clear(); 42 this.arguments.addAll(arguments); 43 return this; 44 } 45 46 public CallRequest argument(Object argument) { 47 arguments.add(argument); 48 return this; 49 } 50 51 public CallRequest procedure(String procedure) { 52 this.procedure = procedure; 31 53 return this; 32 54 } … … 35 57 protected StringBuilder construct(StringBuilder buffer) { 36 58 super.construct(buffer); 37 if (method != null) {38 buffer.append(" ").append(method);39 }40 if (arguments != null) {41 buffer.append(arguments);59 Misc.throwIfNull(procedure); 60 buffer.append(' ').append(procedure); 61 for (Object arg : arguments) { 62 buffer.append(' '); 63 quoteArgumentIfNeeded(buffer, arg); 42 64 } 43 65 return buffer; … … 49 71 } 50 72 73 @Override 74 public CharSequence parseRest(CharSequence rest) { 75 rest = super.parseRest(rest); 76 Pair<CharSequence, CharSequence> p = Misc.throwIfNull(takeIdentifier(rest)); 77 this.procedure = p.first.toString(); 78 while ((p = takeString(p.second)) != null) { 79 arguments.add(p.first); 80 } 81 return null; 82 } 83 51 84 } -
java/main/src/main/java/com/framsticks/communication/queries/GetRequest.java
r84 r96 1 1 package com.framsticks.communication.queries; 2 3 import java.util.ArrayList; 4 import java.util.List; 5 6 import com.framsticks.util.lang.Delimeted; 7 import com.framsticks.util.lang.Pair; 2 8 3 9 /** … … 5 11 */ 6 12 public class GetRequest extends ApplicationRequest { 13 protected final List<String> fields = new ArrayList<>(); 14 7 15 public GetRequest() { 16 } 17 18 public GetRequest fields(List<String> fields) { 19 this.fields.clear(); 20 this.fields.addAll(fields); 21 return this; 22 } 23 24 public GetRequest field(String field) { 25 this.fields.clear(); 26 this.fields.add(field); 27 return this; 8 28 } 9 29 … … 12 32 return "get"; 13 33 } 34 35 @Override 36 protected StringBuilder construct(StringBuilder buffer) { 37 super.construct(buffer); 38 if (!fields.isEmpty()) { 39 buffer.append(' ').append(new Delimeted<String>(",", "").append(fields.iterator())); 40 } 41 return buffer; 42 } 43 44 /** 45 * @return the fields 46 */ 47 public List<String> getFields() { 48 return fields; 49 } 50 51 @Override 52 public CharSequence parseRest(CharSequence rest) { 53 rest = super.parseRest(rest); 54 Pair<CharSequence, CharSequence> p = takeIdentifier(rest); 55 if (p != null) { 56 for (String a : p.first.toString().split(",")) { 57 fields.add(a); 58 } 59 } 60 return null; 61 } 14 62 } -
java/main/src/main/java/com/framsticks/communication/queries/SetRequest.java
r84 r96 1 1 package com.framsticks.communication.queries; 2 3 import com.framsticks.util.lang.Pair; 2 4 3 5 /** … … 5 7 */ 6 8 public class SetRequest extends ApplicationRequest { 9 10 protected String field; 7 11 protected String value; 8 12 9 13 public SetRequest() { 14 } 15 16 public SetRequest field(String field) { 17 this.field = field; 18 return this; 10 19 } 11 20 … … 17 26 @Override 18 27 protected StringBuilder construct(StringBuilder buffer) { 19 super.construct(buffer); 20 if (value != null) { 21 buffer.append(" \"").append(value).append("\""); 22 } 23 return buffer; 28 return quoteArgumentIfNeeded(super.construct(buffer).append(' ').append(field).append(' '), value); 24 29 } 30 25 31 @Override 26 32 public String getCommand() { 27 33 return "set"; 28 34 } 35 36 37 @Override 38 public CharSequence parseRest(CharSequence rest) { 39 final Pair<CharSequence, CharSequence> fp = takeString(super.parseRest(rest)); 40 field = fp.first.toString(); 41 final Pair<CharSequence, CharSequence> vp = takeString(fp.second); 42 value = vp.first.toString(); 43 44 return vp.second; 45 } 46 47 /** 48 * @return the field 49 */ 50 public String getField() { 51 return field; 52 } 53 54 /** 55 * @return the value 56 */ 57 public String getValue() { 58 return value; 59 } 29 60 } -
java/main/src/main/java/com/framsticks/communication/queries/UseRequest.java
r84 r96 1 1 package com.framsticks.communication.queries; 2 3 import com.framsticks.util.lang.Strings; 2 4 3 5 /** … … 19 21 @Override 20 22 protected StringBuilder construct(StringBuilder buffer) { 21 return buffer.append( ' ').append(feature);23 return buffer.append(feature); 22 24 } 23 25 24 26 @Override 25 public void parseRest(String rest) { 26 feature = rest; 27 public CharSequence parseRest(CharSequence rest) { 28 feature = rest.toString(); 29 Strings.assureNotEmpty(feature); 30 return null; 27 31 } 28 32 -
java/main/src/main/java/com/framsticks/communication/queries/VersionRequest.java
r84 r96 23 23 24 24 @Override 25 public void parseRest(String rest) { 26 version = Numbers.parse(rest, Integer.class); 25 public CharSequence parseRest(CharSequence rest) { 26 version = Numbers.parse(rest.toString(), Integer.class); 27 return null; 27 28 } 28 29 29 30 @Override 30 31 protected StringBuilder construct(StringBuilder buffer) { 31 return buffer.append( ' ').append(version);32 return buffer.append(version); 32 33 } 33 34 -
java/main/src/main/java/com/framsticks/communication/util/LoggingStateCallback.java
r85 r96 2 2 3 3 import com.framsticks.communication.StateCallback; 4 import com.framsticks.util.FramsticksException; 5 4 6 import org.apache.log4j.Logger; 5 7 … … 18 20 19 21 @Override 20 public void call(Exception e) { 21 if (e != null) { 22 logger.error("failed to " + message + " with " + e); 23 return; 24 } 22 public void handle(FramsticksException e) { 23 logger.error("failed to " + message + " with " + e); 24 } 25 26 @Override 27 public void callImpl() { 25 28 logger.debug(message); 26 29 } -
java/main/src/main/java/com/framsticks/core/Framsticks.java
r90 r96 3 3 import com.framsticks.params.annotations.FramsClassAnnotation; 4 4 import com.framsticks.parsers.XmlLoader; 5 import com.framsticks.util.dispatching.Joinable; 5 6 import com.framsticks.util.dispatching.JoinableCollection; 6 7 import com.framsticks.util.dispatching.Monitor; … … 15 16 */ 16 17 @FramsClassAnnotation 17 public class Framsticks extends JoinableCollection< Entity> {18 public class Framsticks extends JoinableCollection<Joinable> { 18 19 private static final Logger log = Logger.getLogger(Framsticks.class); 19 20 … … 28 29 public static void main(final String[] args) { 29 30 30 new Monitor(loadConfiguration(Framsticks.class.getResourceAsStream("/configs/framsticks.xml"))) 31 .use() 32 .waitFor() 33 .drop() 34 .join(); 31 new Monitor(loadConfiguration(Framsticks.class.getResourceAsStream("/configs/framsticks.xml"))).use().waitFor().drop().join(); 35 32 36 log. info("exiting main");33 log.debug("exiting main"); 37 34 } 38 35 -
java/main/src/main/java/com/framsticks/core/Instance.java
r90 r96 1 1 package com.framsticks.core; 2 3 import java.util.HashSet;4 import java.util.Iterator;5 import java.util.LinkedList;6 import java.util.List;7 import java.util.Set;8 2 9 3 import javax.annotation.Nonnull; 10 4 11 import org.apache.log4j.Logger;12 13 import com.framsticks.communication.File;14 5 import com.framsticks.params.AccessInterface; 15 6 import com.framsticks.params.CompositeParam; 16 import com.framsticks.params.ConstructionException;17 7 import com.framsticks.params.FramsClass; 18 import com.framsticks.params.ListAccess;19 import com.framsticks.params.Param;20 import com.framsticks.params.ParamsPackage;21 8 import com.framsticks.params.Registry; 22 9 import com.framsticks.params.ValueParam; 23 import com.framsticks.params.annotations.AutoAppendAnnotation;24 import com.framsticks.params.annotations.FramsClassAnnotation;25 import com.framsticks.params.types.ObjectParam;26 10 import com.framsticks.params.types.ProcedureParam; 27 import com.framsticks.parsers.Loaders;28 import com.framsticks.parsers.MultiParamLoader;29 import com.framsticks.util.FramsticksException;30 11 import com.framsticks.util.StateFunctor; 31 import com.framsticks.util.UnsupportedOperationException; 32 import com.framsticks.util.dispatching.Dispatching; 12 import com.framsticks.util.dispatching.Dispatcher; 33 13 import com.framsticks.util.dispatching.Future; 34 import com.framsticks.util.dispatching.RunAt; 35 import com.framsticks.util.dispatching.Thread; 36 import com.framsticks.util.lang.Casting; 14 import com.framsticks.util.dispatching.Joinable; 37 15 38 /** 39 * @author Piotr Sniegowski 40 */ 41 @FramsClassAnnotation 42 public abstract class Instance extends Thread<Instance> implements Entity { 16 public interface Instance extends Dispatcher<Instance>, Joinable { 43 17 44 private static final Logger log = Logger.getLogger(Instance.class.getName()); 18 public @Nonnull Node getRoot(); 19 public @Nonnull void setRoot(Node node); 45 20 46 private Node root; 21 public @Nonnull AccessInterface prepareAccess(CompositeParam param); 22 public void takeAllFrom(Registry source); 47 23 48 protected @Nonnull Node setRoot(CompositeParam param, Object object) { 49 // if (isRootAssigned()) { 50 // throw new FramsticksException().msg("root is already assigned"); 51 // } 52 // assert isActive(); 53 root = new Node(param, object); 54 return root; 55 } 24 public void addListener(InstanceListener listener); 25 public void removeListener(InstanceListener listener); 56 26 57 protected @Nonnull Node getRoot() { 58 // assert isActive(); 59 assert root != null; 60 return root; 61 } 27 public void notifyOfFetch(Path path); 62 28 63 public boolean isRootAssigned() { 64 // assert isActive(); 65 return root != null; 66 } 29 public FramsClass getInfoFromCache(String id); 67 30 68 p rotected Set<InstanceListener> listeners = new HashSet<InstanceListener>();31 public void putInfoIntoCache(FramsClass framclass); 69 32 70 public Instance() { 71 setName("entity"); 72 } 73 74 protected void fetchInfo(Path path, Future<FramsClass> future) { 75 future.result(null, new UnsupportedOperationException()); 76 } 77 78 public void resolve(Path path, Future<Path> future) { 79 assert isActive(); 80 assert path.isOwner(this); 81 if (path.getTop().getObject() != null) { 82 future.result(path, null); 83 return; 84 } 85 AccessInterface access = bindAccess(path.getUnder()); 86 Object object = access.get(path.getTop().getParam(), Object.class); 87 if (object == null) { 88 future.result(path, null); 89 return; 90 } 91 future.result(path.appendResolution(object), null); 92 } 33 public void resolve(Path path, Future<Path> future); 93 34 94 35 /** This is part of the Instance interface. 95 36 * 96 37 */ 97 public abstract void fetchValue(Path path,Param param, StateFunctor stateFunctor);38 public void fetchValue(Path path, ValueParam param, StateFunctor stateFunctor); 98 39 99 40 /** This is part of the Instance interface. 100 41 * 101 42 */ 102 public abstractvoid fetchValues(Path path, StateFunctor stateFunctor);43 public void fetchValues(Path path, StateFunctor stateFunctor); 103 44 104 45 /** This is part of the Instance interface. 105 46 * 106 47 */ 107 public abstract void call(Path path, ProcedureParam param, Object[] arguments, StateFunctor stateFunctor);48 public void call(Path path, ProcedureParam param, Object[] arguments, Future<Object> future); 108 49 109 p rotected void tryRegisterOnChangeEvents(Path path) {50 public void storeValue(Path path, ValueParam param, Object value, StateFunctor stateFunctor); 110 51 111 }52 public void fetchInfo(Path path, Future<FramsClass> future); 112 53 113 public void storeValue(Path path, Param param, Object value, final StateFunctor stateFunctor) { 114 assert isActive(); 115 dispatch(new RunAt<Instance>() { 116 @Override 117 public void run() { 118 stateFunctor.call(new UnsupportedOperationException()); 119 } 120 }); 121 } 122 123 protected void fireRun(Exception e) { 124 for (InstanceListener l : this.listeners) { 125 l.onRun(e); 126 } 127 } 128 129 protected void fireStop(Exception e) { 130 for (InstanceListener l : this.listeners) { 131 l.onStop(e); 132 } 133 } 134 135 public void addListener(final InstanceListener listener) { 136 assert Dispatching.isThreadSafe(); 137 Dispatching.dispatchIfNotActive(this, new RunAt<Instance>() { 138 @Override 139 public void run() { 140 listeners.add(listener); 141 } 142 }); 143 } 144 145 public void removeListener(final InstanceListener listener) { 146 assert Dispatching.isThreadSafe(); 147 Dispatching.dispatchIfNotActive(this, new RunAt<Instance>() { 148 @Override 149 public void run() { 150 listeners.remove(listener); 151 } 152 }); 153 } 154 155 protected void fireListChange(Path path, ListChange change) { 156 assert isActive(); 157 for (InstanceListener l : this.listeners) { 158 l.onListChange(path, change); 159 } 160 } 161 162 protected void fireFetch(Path path) { 163 assert isActive(); 164 for (InstanceListener l : this.listeners) { 165 l.onFetch(path); 166 } 167 } 168 169 public final FramsClass getInfoFromCache(Path path) { 170 return getInfoFromCache(path.getTop().getParam().getContainedTypeName()); 171 } 172 173 public FramsClass getInfoFromCache(String id) { 174 assert isActive(); 175 return registry.getFramsClass(id); 176 } 177 178 protected Registry registry = new Registry(); 179 180 public AccessInterface createAccess(String name) throws ConstructionException { 181 assert isActive(); 182 return registry.createAccess(name); 183 } 184 185 // TODO: make ValueParam 186 public <T> T get(Node node, Param childParam, Class<T> type) { 187 return bindAccess(node).get((ValueParam) childParam, type); 188 } 189 190 public void findInfo(final Path path, final Future<FramsClass> future) { 191 assert isActive(); 192 final String name = path.getTop().getParam().getContainedTypeName(); 193 final FramsClass framsClass = getInfoFromCache(name); 194 if (framsClass != null) { 195 log.trace("info for " + name + " found in cache"); 196 future.result(framsClass, null); 197 return; 198 } 199 fetchInfo(path, future); 200 } 201 202 public final AccessInterface bindAccess(String path) { 203 return bindAccess(getPath(path)); 204 } 205 206 public final AccessInterface bindAccess(Node node) { 207 assert isActive(); 208 assert node.getObject() != null; 209 210 try { 211 AccessInterface access = registry.prepareAccess(node.getParam()); 212 if (access == null) { 213 throw new FramsticksException().msg("failed to prepare access for param").arg("param", node.getParam()); 214 } 215 return access.select(node.getObject()); 216 } catch (ConstructionException e) { 217 log.error("failed to bind access for " + node.getParam() + ": " + e); 218 } 219 return null; 220 } 221 222 public final <T> T getParam(Path path, String id, Class<T> type) { 223 return Casting.tryCast(type, registry.prepareAccess(path.getTop().getParam()).getParam(id)); 224 } 225 226 public final AccessInterface bindAccess(Path path) { 227 path.assureResolved(); 228 return bindAccess(path.getTop()); 229 } 230 231 public void resolve(final String targetPath, final Future<Path> future) { 232 assert isActive(); 233 final Path path = getPath(targetPath); 234 resolve(path, new Future<Path>() { 235 @Override 236 public void result(Path result, Exception e) { 237 assert isActive(); 238 if (e != null) { 239 future.result(path, e); 240 return; 241 } 242 if (path.isResolved(targetPath)) { 243 future.result(path, null); 244 return; 245 } 246 if (path.isResolved()) { 247 future.result(path, new Exception("testing")); 248 return; 249 } 250 resolve(targetPath, future); 251 } 252 }); 253 } 254 255 public void resolveAndFetch(final String targetPath, final Future<Path> future) { 256 assert isActive(); 257 resolve(targetPath, new Future<Path>() { 258 @Override 259 public void result(final Path path, Exception e) { 260 if (e != null) { 261 future.result(path, e); 262 return; 263 } 264 assert path.isResolved(targetPath); 265 fetchValues(path, new StateFunctor() { 266 @Override 267 public void call(Exception e) { 268 future.result(path, e); 269 } 270 }); 271 } 272 }); 273 } 274 275 public Path createIfNeeded(String path) { 276 Path p; 277 while (!(p = getPath(path)).isResolved(path)) { 278 create(p); 279 } 280 return p; 281 } 282 283 public Path createIfNeeded(Path path) { 284 assert isActive(); 285 if (path.isResolved()) { 286 return path; 287 } 288 return create(path); 289 } 290 291 public Path create(Path path) { 292 assert isActive(); 293 assert !path.isResolved(); 294 Path resolved = path.tryFindResolution(); 295 if (!resolved.isResolved()) { 296 log.debug("creating: " + path); 297 AccessInterface access = registry.prepareAccess(path.getTop().getParam()); 298 assert access != null; 299 Object child = access.createAccessee(); 300 assert child != null; 301 if (path.size() == 1) { 302 setRoot(getRoot().getParam(), child); 303 } else { 304 bindAccess(path.getUnder()).set(path.getTop().getParam(), child); 305 } 306 resolved = path.appendResolution(child); 307 } 308 tryRegisterOnChangeEvents(resolved); 309 return resolved; 310 } 311 312 313 314 315 public @Nonnull FramsClass processFetchedInfo(File file) { 316 assert isActive(); 317 FramsClass framsClass = Loaders.loadFramsClass(file.getContent()); 318 if ("/".equals(file.getPath())) { 319 if (getRoot().getParam().getContainedTypeName() == null) { 320 setRoot(Param.build().name("Instance").id(getName()).type("o " + framsClass.getId()).finish(CompositeParam.class), getRoot().getObject()); 321 } 322 } 323 registry.putFramsClass(framsClass); 324 return framsClass; 325 } 326 327 public void processFetchedValues(Path path, List<File> files) { 328 assert isActive(); 329 assert files.size() == 1; 330 assert path.isTheSame(files.get(0).getPath()); 331 Node node = path.getTop(); 332 MultiParamLoader loader = new MultiParamLoader(); 333 loader.setNewSource(files.get(0).getContent()); 334 loader.addBreakCondition(MultiParamLoader.Status.AfterObject); 335 336 try { 337 if (node.getParam() instanceof ObjectParam) { 338 loader.addAccessInterface(bindAccess(node)); 339 loader.go(); 340 fireFetch(path); 341 return; 342 } 343 344 ListAccess listAccess = ((ListAccess)bindAccess(node)); 345 assert listAccess != null; 346 listAccess.clearValues(); 347 348 AccessInterface elementAccess = listAccess.getElementAccess(); 349 loader.addAccessInterface(elementAccess); 350 MultiParamLoader.Status status; 351 while ((status = loader.go()) != MultiParamLoader.Status.Finished) { 352 if (status == MultiParamLoader.Status.AfterObject) { 353 AccessInterface accessInterface = loader.getLastAccessInterface(); 354 355 String id = listAccess.computeIdentifierFor(accessInterface.getSelected()); 356 //TODO listAccessParam 357 Param param = Param.build().forAccess(accessInterface).id(id).finish(); 358 Object child = accessInterface.getSelected(); 359 accessInterface.select(null); 360 assert child != null; 361 bindAccess(node).set((ValueParam) param, child); 362 } 363 } 364 365 fireFetch(path); 366 } catch (Exception e) { 367 log.error("exception occurred while loading: " + e); 368 } 369 370 } 371 372 public static Iterator<String> splitPath(String path) { 373 List<String> list = new LinkedList<String>(); 374 for (String s : path.split("/")) { 375 if (!s.isEmpty()) { 376 list.add(s); 377 } 378 } 379 return list.iterator(); 380 } 381 382 public Registry getRegistry() { 383 return registry; 384 } 385 386 public Path getPath(String textual) { 387 return Path.build().resolve(this, textual).finish(); 388 } 389 390 public Path getRootPath() { 391 return getPath("/"); 392 } 393 394 @AutoAppendAnnotation 395 public void usePackage(ParamsPackage paramsPackage) { 396 log.debug("using package " + paramsPackage + " in instance " + this); 397 paramsPackage.register(registry); 398 } 399 400 @AutoAppendAnnotation 401 public void takeFromRegistry(Registry registry) { 402 log.debug("taking from registry " + registry + " in instance " + this); 403 this.registry.takeAllFrom(registry); 404 } 405 406 @Override 407 protected void joinableStart() { 408 dispatch(new RunAt<Instance>() { 409 @Override 410 public void run() { 411 if (!isRootAssigned()) { 412 setRoot(Param.build().name("Instance").id(getName()).type("o").finish(CompositeParam.class), null); 413 } 414 } 415 }); 416 super.joinableStart(); 417 } 418 54 public Path create(Path path); 419 55 } 420 -
java/main/src/main/java/com/framsticks/core/ObjectInstance.java
r90 r96 5 5 import com.framsticks.params.AccessInterface; 6 6 import com.framsticks.params.CompositeParam; 7 import com.framsticks.params.FramsClass; 7 8 import com.framsticks.params.Param; 9 import com.framsticks.params.ValueParam; 8 10 import com.framsticks.params.annotations.AutoAppendAnnotation; 9 11 import com.framsticks.params.annotations.FramsClassAnnotation; 12 import com.framsticks.util.UnsupportedOperationException; 10 13 import com.framsticks.params.types.ProcedureParam; 11 14 import com.framsticks.util.FramsticksException; 12 15 import com.framsticks.util.StateFunctor; 16 import com.framsticks.util.dispatching.Future; 17 // import static com.framsticks.core.InstanceUtils.*; 13 18 14 19 @FramsClassAnnotation 15 public class ObjectInstance extends Instance {20 public class ObjectInstance extends AbstractInstance { 16 21 private static final Logger log = Logger.getLogger(ObjectInstance.class); 17 22 … … 20 25 registry.registerAndBuild(object.getClass()); 21 26 AccessInterface access = registry.createAccess(object.getClass()); 22 setRoot( Param.build().forAccess(access).id(getName()).finish(CompositeParam.class), object);27 setRoot(new Node(Param.build().forAccess(access).id(getName()).finish(CompositeParam.class), object)); 23 28 } 24 29 … … 43 48 log.debug("requesting: " + path); 44 49 fireFetch(path); 45 stateFunctor.call( null);50 stateFunctor.call(); 46 51 } 47 52 48 53 @Override 49 public void fetchValue(Path path, Param param, StateFunctor stateFunctor) {54 public void fetchValue(Path path, ValueParam param, StateFunctor stateFunctor) { 50 55 assert isActive(); 51 56 fireFetch(path); 52 stateFunctor.call( null);57 stateFunctor.call(); 53 58 } 54 59 55 60 @Override 56 public void call(Path path, ProcedureParam param, Object[] arguments, StateFunctor stateFunctor) {61 public void call(Path path, ProcedureParam param, Object[] arguments, Future<Object> future) { 57 62 assert isActive(); 58 63 try { 59 bindAccess(path).call(param, arguments); 60 stateFunctor.call(null); 64 future.pass(InstanceUtils.bindAccess(path).call(param, arguments)); 61 65 } catch (FramsticksException e) { 62 stateFunctor.call(e);66 future.handle(e); 63 67 } 64 68 } 69 70 @Override 71 public void fetchInfo(Path path, Future<FramsClass> future) { 72 assert isActive(); 73 Path p = path.tryResolveIfNeeded(); 74 Class<?> javaClass = p.getTopObject().getClass(); 75 FramsClass framsClass = registry.registerReflectedIfNeeded(javaClass); 76 if (framsClass != null) { 77 future.pass(framsClass); 78 } else { 79 future.handle(new FramsticksException().msg("failed to find info for class").arg("java class", javaClass)); 80 } 81 } 82 83 @Override 84 public void resolve(Path path, Future<Path> future) { 85 assert isActive(); 86 assert path.isOwner(this); 87 if (path.getTop().getObject() != null) { 88 future.pass(path); 89 return; 90 } 91 AccessInterface access = InstanceUtils.bindAccess(this, path.getUnder()); 92 Object object = access.get(path.getTop().getParam(), Object.class); 93 if (object == null) { 94 future.pass(path); 95 return; 96 } 97 future.pass(path.appendResolution(object)); 98 } 99 100 @Override 101 public void storeValue(Path path, ValueParam param, Object value, final StateFunctor stateFunctor) { 102 assert isActive(); 103 stateFunctor.handle(new UnsupportedOperationException()); 104 } 105 106 @Override 107 public Path create(Path path) { 108 assert isActive(); 109 assert !path.isResolved(); 110 throw new UnsupportedOperationException(); 111 } 112 65 113 } -
java/main/src/main/java/com/framsticks/core/Path.java
r90 r96 11 11 import java.util.List; 12 12 13 import javax.annotation.Nonnull; 13 14 import javax.annotation.concurrent.Immutable; 14 15 … … 32 33 } 33 34 try { 34 instance. registry.prepareAccess(param);35 instance.prepareAccess(param); 35 36 return child; 36 37 } catch (FramsticksException e) { … … 119 120 } 120 121 121 public PathBuilder resolve(Instance instance, String textual) { 122 public static Iterator<String> splitPath(String path) { 123 List<String> list = new LinkedList<String>(); 124 for (String s : path.split("/")) { 125 if (!s.isEmpty()) { 126 list.add(s); 127 } 128 } 129 return list.iterator(); 130 } 131 132 public PathBuilder resolve(@Nonnull Instance instance, String textual) { 122 133 123 134 assert nodes.isEmpty(); … … 129 140 130 141 StringBuilder b = new StringBuilder(); 131 Iterator<String> i = Instance.splitPath(textual);142 Iterator<String> i = splitPath(textual); 132 143 while (i.hasNext() && current.getObject() != null) { 133 AccessInterface access = instance. registry.prepareAccess(current.getParam());144 AccessInterface access = instance.prepareAccess(current.getParam()); 134 145 if (access == null) { 135 146 break; … … 205 216 } 206 217 207 public final Instance getInstance() {218 public final @Nonnull Instance getInstance() { 208 219 assert Dispatching.isThreadSafe(); 209 220 return instance; 210 221 } 211 222 223 public Path tryResolveIfNeeded() { 224 if (isResolved()) { 225 return this; 226 } 227 return tryFindResolution(); 228 } 212 229 213 230 /** Attach resolution at end, if available. … … 221 238 return Path.build().resolve(instance, "/").finish();//appendResolution(instance.root.object); 222 239 } 223 Object child = getKnownChild(instance, instance.bindAccess(getUnder()), getTop().getParam());240 Object child = getKnownChild(instance, InstanceUtils.bindAccess(instance, getUnder()), getTop().getParam()); 224 241 if (child == null) { 225 242 return this; … … 266 283 } 267 284 } 285 286 public static Path to(@Nonnull Instance instance, String textual) { 287 return Path.build().resolve(instance, textual).finish(); 288 } 268 289 } 269 290 -
java/main/src/main/java/com/framsticks/diagnostics/Diagnostics.java
r88 r96 1 1 package com.framsticks.diagnostics; 2 3 2 4 3 import java.util.Date; … … 14 13 import com.framsticks.core.AbstractInstanceListener; 15 14 import com.framsticks.core.Instance; 15 import com.framsticks.core.Path; 16 16 import com.framsticks.dumping.PrintWriterSink; 17 17 import com.framsticks.dumping.SaveStream; 18 18 import com.framsticks.params.annotations.AutoAppendAnnotation; 19 19 import com.framsticks.remote.RecursiveFetcher; 20 import com.framsticks.util.FramsticksException; 20 21 import com.framsticks.util.Logging; 21 22 import com.framsticks.util.PeriodicTask; … … 28 29 */ 29 30 public class Diagnostics extends JoinableCollection<Instance> { 30 private static final Logger log = 31 Logger.getLogger(Diagnostics.class); 31 private static final Logger log = Logger.getLogger(Diagnostics.class); 32 32 33 33 … … 59 59 60 60 log.info("starting periodic dump"); 61 new RecursiveFetcher(instance, instance.getRootPath(), new StateFunctor() {61 new RecursiveFetcher(instance, Path.to(instance, "/"), new StateFunctor() { 62 62 @Override 63 public void call(Exception e) { 64 if (Logging.log(log, "recursively fetch", instance, e)) { 65 again(); 66 return; 67 } 63 public void handle(FramsticksException e) { 64 Logging.log(log, "recursively fetch", instance, e); 65 again(); 66 } 67 68 @Override 69 public void call() { 68 70 log.info("instance resolved, saving"); 69 71 try { 70 72 final String fileName = dumpsPath + "/" + instance + "_" + new SimpleDateFormat(dumpsFormat).format(new Date()) + ".param"; 71 73 File file = new File(fileName); 72 new SaveStream(new PrintWriterSink(new PrintWriter(new OutputStreamWriter(new FileOutputStream(file), Encoding.getFramsticksCharset()))), instance, instance.getRootPath(), new StateFunctor() {74 new SaveStream(new PrintWriterSink(new PrintWriter(new OutputStreamWriter(new FileOutputStream(file), Encoding.getFramsticksCharset()))), instance, Path.to(instance, "/"), new StateFunctor() { 73 75 @Override 74 public void call(Exception e) {76 public void handle(FramsticksException e) { 75 77 Logging.log(log, "periodic dump in " + fileName + " of", instance, e); 78 again(); 79 } 80 81 @Override 82 public void call() { 76 83 again(); 77 84 } -
java/main/src/main/java/com/framsticks/dumping/LoadStream.java
r84 r96 2 2 3 3 import com.framsticks.communication.File; 4 import com.framsticks.core.InstanceUtils; 4 5 import com.framsticks.core.Path; 5 6 import com.framsticks.params.ListSource; … … 19 20 * @author Piotr Sniegowski 20 21 */ 21 public class LoadStream {22 public class LoadStream extends Stream { 22 23 23 24 private final static Logger log = Logger.getLogger(LoadStream.class.getName()); … … 46 47 while ((line = stream.readLine()) != null) { 47 48 if (query == null) { 48 query = Strings.splitIntoPair(line, ' ', " \n");49 query = Strings.splitIntoPair(line, ' ', ""); 49 50 files = new LinkedList<File>(); 50 51 log.trace("loading " + line); … … 58 59 if (line.equals("ok")) { 59 60 if (query.first.equals("get")) { 60 Path path = instance.createIfNeeded(query.second);61 instance.processFetchedValues(path, files);61 Path path = InstanceUtils.createIfNeeded(instance, query.second); 62 InstanceUtils.processFetchedValues(path, files); 62 63 } else if (query.first.equals("info")) { 63 64 assert files.size() == 1; 64 instance.processFetchedInfo(files.get(0));65 InstanceUtils.processFetchedInfo(instance, files.get(0)); 65 66 } else { 66 67 assert false; … … 82 83 } catch (IOException e) { 83 84 log.error("failed to load: " + e); 84 future. result(null, e);85 future.handle(new FramsticksException().msg("failed to load stream").cause(e)); 85 86 return; 86 87 } 87 88 log.info("loaded in: " + stopwatch); 88 future. result(instance.getPath(mountPath.getTextual()), null);89 future.pass(Path.to(instance, mountPath.getTextual())); 89 90 } 90 91 -
java/main/src/main/java/com/framsticks/dumping/SaveStream.java
r90 r96 1 1 package com.framsticks.dumping; 2 2 3 import static com.framsticks.core.InstanceUtils.*; 3 4 import com.framsticks.core.Node; 4 5 import com.framsticks.core.Path; … … 22 23 * @author Piotr Sniegowski 23 24 */ 24 public class SaveStream {25 public class SaveStream extends Stream { 25 26 26 27 private final static Logger log = Logger.getLogger(SaveStream.class.getName()); … … 55 56 assert instance.isActive(); 56 57 log.info("stored in " + stopwatch); 57 stateFunctor.call( null);58 stateFunctor.call(); 58 59 } 59 60 … … 63 64 log.debug("path " + path + " is not resolved - skipping"); 64 65 } else { 65 AccessInterface access = instance.bindAccess(path);66 AccessInterface access = bindAccess(path); 66 67 assert access != null; 67 68 FramsClass framsClass = access.getFramsClass(); … … 85 86 for (CompositeParam p : filterInstanceof(access.getParams(), CompositeParam.class)) { 86 87 final Path childPath = path.appendNode(new Node(p, access.get(p, Object.class))); 87 if (childPath.isResolved() && instance.getInfoFromCache(childPath) != null) {88 if (childPath.isResolved() && getInfoFromCache(childPath) != null) { 88 89 dispatchWrite(childPath); 89 90 } -
java/main/src/main/java/com/framsticks/gui/Browser.java
r90 r96 5 5 import com.framsticks.params.annotations.FramsClassAnnotation; 6 6 import com.framsticks.params.annotations.ParamAnnotation; 7 import com.framsticks.util.Logging;8 7 import com.framsticks.util.dispatching.AbstractJoinable; 9 8 import com.framsticks.util.dispatching.Dispatcher; … … 22 21 import java.util.ArrayList; 23 22 import java.util.List; 24 import java.util.Map;25 23 import com.framsticks.util.dispatching.RunAt; 26 24 … … 29 27 */ 30 28 @FramsClassAnnotation 31 public class Browser extends AbstractJoinable implements Dispatcher<Browser>, Entity,JoinableParent {29 public class Browser extends AbstractJoinable implements Dispatcher<Browser>, JoinableParent { 32 30 33 31 private static final Logger log = Logger.getLogger(Browser.class.getName()); … … 72 70 @Override 73 71 public void run() { 74 i.resolveAndFetch(path, new Future<Path>() {72 InstanceUtils.resolveAndFetch(i, path, new Future<Path>(future) { 75 73 @Override 76 public void result(final Path p, Exception e) { 77 Logging.log(log, "auto resolve path", path, e); 78 if (future != null) { 79 future.result(p, e); 80 } 81 if (e == null) { 82 mainFrame.dispatch(new RunAt<Frame>() { 83 @Override 84 public void run() { 85 mainFrame.goTo(p); 86 } 87 }); 88 } 74 protected void result(final Path p) { 75 future.pass(p); 76 mainFrame.dispatch(new RunAt<Frame>() { 77 @Override 78 public void run() { 79 mainFrame.goTo(p); 80 } 81 }); 89 82 } 90 83 }); … … 132 125 @Override 133 126 public void run() { 134 final Path p = i.getRootPath();127 final Path p = Path.to(i, "/"); 135 128 dispatch(new RunAt<Browser>() { 136 129 @Override … … 194 187 * @return the instances 195 188 */ 196 public Map<String,Instance> getInstances() {197 return instances .getObservables();189 public JoinableCollection<Instance> getInstances() { 190 return instances; 198 191 } 199 192 … … 254 247 @Override 255 248 protected void joinableFinish() { 256 // TODO Auto-generated method stub257 249 258 250 } -
java/main/src/main/java/com/framsticks/gui/Frame.java
r90 r96 1 1 package com.framsticks.gui; 2 2 3 import com.framsticks.core.Entity;4 3 import com.framsticks.core.Instance; 5 4 import com.framsticks.core.Path; … … 32 31 */ 33 32 @SuppressWarnings("serial") 34 public class Frame extends JoinableCollection<Instance> implements Entity,Dispatcher<Frame> {33 public class Frame extends JoinableCollection<Instance> implements Dispatcher<Frame> { 35 34 36 35 private static final Logger log = Logger.getLogger(Frame.class.getName()); … … 82 81 public void windowClosing(WindowEvent e) { 83 82 log.info("received closing"); 84 joinableFinish();83 interrupt(); 85 84 } 86 85 }); … … 268 267 assert isActive(); 269 268 Instance instance = path.getInstance(); 270 assert browser.getInstances().contains Value(instance);269 assert browser.getInstances().contains(instance); 271 270 272 271 InstanceAtFrame e = new InstanceAtFrame(instance, this); -
java/main/src/main/java/com/framsticks/gui/TreeNode.java
r90 r96 5 5 import com.framsticks.communication.util.LoggingStateCallback; 6 6 import com.framsticks.core.Instance; 7 import com.framsticks.core.InstanceUtils; 7 8 import com.framsticks.core.ListChange; 8 9 import com.framsticks.core.Path; … … 15 16 import com.framsticks.remote.*; 16 17 import com.framsticks.util.lang.Casting; 18 import com.framsticks.util.lang.Holder; 17 19 import com.framsticks.util.swing.TooltipConstructor; 18 20 import com.framsticks.util.dispatching.Future; 21 import com.framsticks.util.AbstractStateFunctor; 19 22 import com.framsticks.util.Logging; 20 import com.framsticks.util.StateFunctor;21 23 import org.apache.log4j.Logger; 22 24 import com.framsticks.util.dispatching.RunAt; … … 29 31 import static com.framsticks.util.lang.Containers.filterInstanceof; 30 32 import com.framsticks.util.swing.TreeNodeUtils; 33 import static com.framsticks.core.InstanceUtils.*; 31 34 32 35 /** … … 73 76 assert p.getInstance().isActive(); 74 77 log.debug("fetching: " + p); 75 p.getInstance().fetchValues(p, new StateFunctor() { 76 @Override 77 public void call(Exception e) { 78 //TODO removing should stay here 78 p.getInstance().fetchValues(p, new AbstractStateFunctor() { 79 @Override 80 public void call() { 79 81 // reactForFetchResult(p, e); 80 82 } … … 140 142 assert p.getInstance().isActive(); 141 143 log.debug("updating children of " + this); 142 AccessInterface access = p.getInstance().bindAccess(p.getTop());144 AccessInterface access = InstanceUtils.bindAccess(p.getInstance(), p.getTop()); 143 145 if (access == null) { 144 146 return; … … 199 201 return; 200 202 } 201 p.getInstance().resolve(updated, new Future<Path>( ) {203 p.getInstance().resolve(updated, new Future<Path>(Logging.logger(log, "resolve and select", TreeNode.this)) { 202 204 @Override 203 public void result(final Path result, Exception e) { 204 if (Logging.log(log, "resolve and select", TreeNode.this, e)) { 205 return; 206 } 207 205 protected void result(Path result) { 208 206 fetch(result); 209 207 postUpdatePath(result); … … 231 229 return; 232 230 } 233 AccessInterface access = p.getInstance().bindAccess(p); 234 if (access == null) { 235 return; 236 } 231 AccessInterface access = InstanceUtils.bindAccess(p); 237 232 238 233 final String tooltip = new TooltipConstructor() … … 309 304 @Override 310 305 public void run() { 311 AccessInterface access = p.getInstance().bindAccess(p);306 AccessInterface access = InstanceUtils.bindAccess(p); 312 307 panel.pullValuesFromLocalToUser(access); 313 308 … … 501 496 return; 502 497 } 503 finalMap<ValueControl, Object> changes = localChanges;498 Map<ValueControl, Object> changes = localChanges; 504 499 localChanges = null; 505 instanceAtFrame.getInstance().dispatch(new RunAt<Instance>() { 506 @Override 507 public void run() { 508 for (Map.Entry<ValueControl, Object> e : changes.entrySet()) { 509 final ValueControl key = e.getKey(); 510 final Path p = path; 511 instanceAtFrame.getInstance().storeValue(p, e.getKey().getParam(), e.getValue(), new StateFunctor() { 500 final Holder<Integer> counter = new Holder<>(changes.size()); 501 final Path p = path; 502 503 for (Map.Entry<ValueControl, Object> e : localChanges.entrySet()) { 504 storeValue(p, e.getKey().getParam(), e.getValue(), new AbstractStateFunctor() { 505 @Override 506 public void call() { 507 counter.set(counter.get() - 1); 508 if (counter.get() != 0) { 509 return; 510 } 511 log.debug("applied changes for: " + p); 512 frame.dispatch(new RunAt<Frame>() { 512 513 @Override 513 public void call(Exception e) { 514 changes.remove(key); 515 if (!changes.isEmpty()) { 516 return; 517 } 518 log.debug("applied changes for: " + p); 519 frame.dispatch(new RunAt<Frame>() { 520 @Override 521 public void run() { 522 fillPanelWithValues(); 523 } 524 }); 514 public void run() { 515 fillPanelWithValues(); 525 516 } 526 517 }); 527 518 } 528 } 529 } );519 }); 520 } 530 521 } 531 522 } -
java/main/src/main/java/com/framsticks/gui/controls/ProcedureControl.java
r90 r96 8 8 import com.framsticks.params.ValueParam; 9 9 import com.framsticks.params.types.ProcedureParam; 10 import com.framsticks.util.FramsticksException; 10 11 import com.framsticks.util.Logging; 11 import com.framsticks.util. StateFunctor;12 import com.framsticks.util.dispatching.Future; 12 13 import com.framsticks.util.dispatching.RunAt; 13 14 … … 67 68 @Override 68 69 public void run() { 69 path.getInstance().call(path, getParam(), arguments.toArray(), new StateFunctor() { 70 path.getInstance().call(path, getParam(), arguments.toArray(), new Future<Object>() { 71 70 72 @Override 71 public void call(Exception e) {73 public void handle(FramsticksException e) { 72 74 Logging.log(log, "call procedure", path, e); 75 } 76 77 @Override 78 public void result(Object result) { 79 73 80 } 74 81 }); -
java/main/src/main/java/com/framsticks/gui/windows/console/ConsoleFrame.java
r85 r96 161 161 } 162 162 String commandText = commandLine.getText(); 163 Pair<String, String> command = Strings.splitIntoPair(commandText, ' ', " \n");163 Pair<String, String> command = Strings.splitIntoPair(commandText, ' ', ""); 164 164 Request request = Request.createRequestByTypeString(command.first); 165 165 if (request == null) { -
java/main/src/main/java/com/framsticks/hosting/InstanceClient.java
r90 r96 1 1 package com.framsticks.hosting; 2 3 import static com.framsticks.util.lang.Strings.assureNotEmpty; 2 4 3 5 import com.framsticks.communication.*; 4 6 import com.framsticks.communication.queries.ApplicationRequest; 7 import com.framsticks.communication.queries.CallRequest; 5 8 import com.framsticks.communication.queries.GetRequest; 6 9 import com.framsticks.communication.queries.InfoRequest; 10 import com.framsticks.communication.queries.SetRequest; 7 11 import com.framsticks.core.Instance; 12 import com.framsticks.core.InstanceUtils; 8 13 import com.framsticks.core.Path; 9 14 import com.framsticks.params.*; 15 import com.framsticks.params.types.ProcedureParam; 10 16 import com.framsticks.parsers.Savers; 11 import com.framsticks. core.LocalInstance;17 import com.framsticks.util.FramsticksException; 12 18 import com.framsticks.util.dispatching.AbstractJoinable; 13 19 import com.framsticks.util.dispatching.Dispatching; … … 16 22 import com.framsticks.util.dispatching.JoinableParent; 17 23 import com.framsticks.util.dispatching.JoinableState; 24 import static com.framsticks.core.InstanceUtils.*; 18 25 19 26 import java.net.Socket; 20 import java.util.ArrayList;21 27 import java.util.LinkedList; 22 28 import java.util.List; 23 import com.framsticks.util.dispatching.RunAt;24 29 25 30 /** … … 28 33 public class InstanceClient extends AbstractJoinable implements RequestHandler, JoinableParent { 29 34 30 protected final LocalInstance instance; 35 protected final Server server; 36 protected final Instance instance; 31 37 protected final ServerConnection connection; 32 38 33 public InstanceClient(LocalInstance instance, Socket socket) { 34 this.instance = instance; 35 connection = new ServerConnection(socket, this); 39 public InstanceClient(Server server, Socket socket) { 40 this.server = server; 41 this.instance = server.hosted; 42 this.connection = new ServerConnection(socket, this); 36 43 } 37 44 38 45 @Override 39 public String toString() {40 return instance + "|" + connection.toString();46 public String getName() { 47 return connection + " to " + server; 41 48 } 42 49 43 50 @Override 44 51 public void handle(final ApplicationRequest request, final ResponseCallback<?> responseCallback) { 45 instance.dispatch(new RunAt<Instance>() { 52 assureNotEmpty(request.getPath()); 53 54 resolve(instance, request.getPath(), new Future<Path>(responseCallback) { 46 55 @Override 47 public void run() { 48 final Path path = instance.getPath(request.getPath()); 49 if (!path.isResolved(request.getPath())) { 50 responseCallback.process(new Response(false, "\"invalid path\"", null)); 56 protected void result(final Path path) { 57 58 // final AccessInterface access = instance.prepareAccess(path); 59 final AccessInterface access = instance.prepareAccess(path.getTop().getParam()); 60 61 if (request instanceof SetRequest) { 62 SetRequest set = (SetRequest) request; 63 //TODO Proxy - here is break of chain, instance should have hosted 64 //hosted set 65 AccessInterface access2 = InstanceUtils.bindAccess(path); 66 int flag = access2.set(set.getField(), set.getValue()); 67 68 responseCallback.process(new Response(true, Flags.write(flag, null), null)); 51 69 return; 52 70 } 71 53 72 if (request instanceof GetRequest) { 54 instance.findInfo(path, new Future<FramsClass>() {73 InstanceUtils.findInfo(path, new Future<FramsClass>(responseCallback) { 55 74 @Override 56 p ublic void result(FramsClass result, Exception e) {75 protected void result(FramsClass result) { 57 76 if (result == null) { 58 responseCallback.process(new Response(false, "\"failed to find info for access bind\"", null)); 59 return; 77 throw new FramsticksException().msg("failed to find info for access bind"); 60 78 } 61 79 List<File> files = new LinkedList<File>(); 62 AccessInterface access = instance.bindAccess(path);80 AccessInterface access = bindAccess(path); 63 81 64 82 if (access == null) { 83 throw new FramsticksException().msg("failed to bind access"); 84 } 65 85 66 responseCallback.process(new Response(false, "\"failed to bind access\"", null));67 return;68 }69 86 ListSink sink = new ListSink(); 70 87 access.save(sink); … … 75 92 return; 76 93 } 77 if (request instanceof InfoRequest) { 78 instance.findInfo(path, new Future<FramsClass>() { 94 if (request instanceof CallRequest) { 95 final CallRequest callRequest = (CallRequest) request; 96 instance.call(path, access.getFramsClass().getParamEntry(callRequest.getProcedure(), ProcedureParam.class), callRequest.getArguments().toArray(), new Future<Object>(responseCallback) { 79 97 @Override 80 public void result(FramsClass result, Exception e) { 81 if (result == null) { 82 responseCallback.process(new Response(false, "\"info not found\"", null)); 83 return; 98 protected void result(Object result) { 99 ListSink sink = new ListSink(); 100 sink.print("Result:").breakLine(); 101 sink.print("value:").print("["); 102 if (result != null) { 103 sink.print(result); 84 104 } 85 ListSink sink = new ListSink(); 86 Savers.saveFramsClass(sink, result); 87 List<File> files = new ArrayList<File>(); 88 files.add(new File(path.getTextual(), new ListSource(sink.getOut()))); 89 responseCallback.process(new Response(true, null, files)); 105 sink.print("]"); 106 107 responseCallback.process(new Response(true, "", File.single(new File("", new ListSource(sink.getOut()))))); 90 108 } 91 109 }); 92 110 return; 93 111 } 94 responseCallback.process(new Response(false, "invalid", null)); 112 if (request instanceof InfoRequest) { 113 findInfo(path, new Future<FramsClass>(responseCallback) { 114 @Override 115 protected void result(FramsClass result) { 116 if (result == null) { 117 throw new FramsticksException().msg("info not found"); 118 } 119 responseCallback.process(new Response(true, null, File.single(new File(path.getTextual(), new ListSource(Savers.saveFramsClass(new ListSink(), result).getOut()))))); 120 } 121 }); 122 return; 123 } 124 125 throw new FramsticksException().msg("invalid request type: " + request.getCommand()); 95 126 } 96 127 }); … … 122 153 } 123 154 155 124 156 } -
java/main/src/main/java/com/framsticks/params/AccessInterface.java
r90 r96 75 75 FramsClass getFramsClass(); 76 76 77 booleantryAutoAppend(Object object);77 void tryAutoAppend(Object object); 78 78 79 79 -
java/main/src/main/java/com/framsticks/params/Flags.java
r85 r96 50 50 51 51 public static String write(int flags, String empty) { 52 Delimeted d = new Delimeted("+", empty);52 Delimeted<String> d = new Delimeted<String>("+", empty); 53 53 try { 54 54 for (Field f : Flags.class.getDeclaredFields()) { -
java/main/src/main/java/com/framsticks/params/FramsClass.java
r90 r96 130 130 } 131 131 132 public <T extends Param> T castedParam(@Nonnull final Param param, @Nonnull final Class<T> type, Object name) {132 public @Nonnull <T extends Param> T castedParam(@Nonnull final Param param, @Nonnull final Class<T> type, Object name) { 133 133 if (param == null) { 134 134 // return null; … … 149 149 * @return the param entry 150 150 */ 151 public <T extends Param> T getParamEntry(final int i, @Nonnull final Class<T> type) {151 public @Nonnull <T extends Param> T getParamEntry(final int i, @Nonnull final Class<T> type) { 152 152 return castedParam(getParam(i), type, i); 153 153 } … … 160 160 * @return the param entry 161 161 */ 162 public <T extends Param> T getParamEntry(@Nonnull final String id, @Nonnull final Class<T> type) {162 public @Nonnull <T extends Param> T getParamEntry(@Nonnull final String id, @Nonnull final Class<T> type) { 163 163 return castedParam(getParam(id), type, id); 164 164 } -
java/main/src/main/java/com/framsticks/params/FramsClassBuilder.java
r90 r96 22 22 import com.framsticks.parsers.Loaders; 23 23 import com.framsticks.util.Builder; 24 import com.framsticks.util.Misc; 24 25 import com.framsticks.util.lang.Containers; 25 26 import com.framsticks.util.lang.Strings; … … 78 79 // TODO: future support for enum 79 80 // if (cl.isEnum()) { 80 // 81 // 82 // 83 84 // 85 // 86 // 87 // 88 // 81 // Class<? extends Enum<?>> enumType = (Class<? extends Enum<?>>) cl; 82 // Enum<?>[] enums = enumType.getEnumConstants(); 83 // StringBuilder b = new StringBuilder(); 84 85 // b.append("d 0 ").append(enums.length - 1).append(" 0 "); 86 // for (Enum<?> e : enums) { 87 // b.append("~").append(e.name()); 88 // } 89 // return b.toString(); 89 90 // } 90 91 if (cl.equals(Integer.class) || cl.equals(int.class)) { … … 125 126 } 126 127 127 builder.resultType(induceParamType(Param.build(), method.getGenericReturnType()).finish(ValueParam.class)); 128 if (!method.getReturnType().equals(Void.TYPE)) { 129 builder.resultType(induceParamType(Param.build(), method.getGenericReturnType()).finish(ValueParam.class)); 130 } 128 131 129 132 List<ValueParam> arguments = new ArrayList<>(); … … 337 340 } 338 341 342 @Override 343 public String toString() { 344 return "FramsClassBuilder for " + Misc.returnNotNull(id, "<not yet known>"); 345 } 339 346 340 347 } -
java/main/src/main/java/com/framsticks/params/ListAccess.java
r90 r96 79 79 //TODO it could actually be used also 80 80 @Override 81 public booleantryAutoAppend(Object object) {82 return false;81 public void tryAutoAppend(Object object) { 82 throw new InvalidOperationException(); 83 83 } 84 84 -
java/main/src/main/java/com/framsticks/params/Param.java
r90 r96 17 17 */ 18 18 @Immutable 19 @FramsClassAnnotation(id = "prop", name = "prop" )19 @FramsClassAnnotation(id = "prop", name = "prop", order = {"id", "name", "type", "flags", "help", "group", "extra"}) 20 20 public abstract class Param { 21 21 … … 33 33 34 34 /** The getFlags stored as a bit sum. */ 35 protected final Integerflags;35 protected final int flags; 36 36 37 37 //TODO 38 38 /** The variable determining whether the parameter is an extra parameter. */ 39 protected final Integerextra;39 protected final int extra; 40 40 41 41 public Param(ParamBuilder builder) { … … 68 68 } 69 69 70 @ParamAnnotation 70 @ParamAnnotation(def = "0") 71 71 public Integer getFlags() { 72 72 return flags; 73 73 } 74 74 75 @ParamAnnotation(id = "type") 75 76 public abstract String getFramsTypeName(); 76 77 … … 92 93 93 94 public boolean hasFlag(int flag) { 94 return flags != null &&(flags & flag) != 0;95 return (flags & flag) != 0; 95 96 } 96 97 -
java/main/src/main/java/com/framsticks/params/ParamBuilder.java
r90 r96 6 6 import com.framsticks.util.Builder; 7 7 import com.framsticks.util.FramsticksException; 8 import com.framsticks.util.Misc; 8 9 import com.framsticks.util.lang.Strings; 9 10 … … 46 47 47 48 /** The flags stored as a bit sum. */ 48 private Integerflags = 0;49 private int flags = 0; 49 50 50 51 /** The parameter name. */ … … 63 64 private Object def; 64 65 65 private Integer extra;66 private int extra = 0; 66 67 67 68 String containedTypeName; … … 179 180 try { 180 181 if (paramType == null) { 181 throw new FramsticksException().msg("trying to finish incomplete param ");182 throw new FramsticksException().msg("trying to finish incomplete param while type is missing"); 182 183 } 183 184 return paramType.getConstructor(ParamBuilder.class).newInstance(this); … … 214 215 215 216 @ParamAnnotation 216 public ParamBuilder flags( Integerflags) {217 public ParamBuilder flags(int flags) { 217 218 this.flags = flags; 218 219 return this; … … 359 360 */ 360 361 @ParamAnnotation 361 public IntegergetFlags() {362 public int getFlags() { 362 363 return flags; 363 364 } … … 385 386 386 387 @ParamAnnotation(id = "xtra") 387 public IntegergetExtra() {388 public int getExtra() { 388 389 return extra; 389 390 } … … 397 398 398 399 @ParamAnnotation(id = "xtra") 399 public ParamBuilder extra( Integerextra) {400 public ParamBuilder extra(int extra) { 400 401 this.extra = extra; 401 402 return this; … … 517 518 } 518 519 String result = Strings.collapse(matcher.group(1)); 519 resultType = (result != null) ? parseProcedureTypePart(result, null) : null; 520 if (result != null) { 521 resultType = Param.build().type(result).finish(ValueParam.class); 522 } else { 523 resultType = null; 524 } 520 525 String arguments = matcher.group(2); 521 526 if (!Strings.notEmpty(arguments)) { … … 524 529 int number = 0; 525 530 for (String a : arguments.split(",")) { 531 ParamBuilder arg = Param.build(); 532 526 533 int space = a.indexOf(' '); 527 String type;528 String name;529 534 if (space == -1) { 530 type = a; 531 name = "arg" + number; 535 arg.type(a).id("arg" + number); 532 536 } else { 533 type = a.substring(0, space);534 name = a.substring(space + 1);535 } 536 argumentsType.add( parseProcedureTypePart(type, name));537 String name = a.substring(space + 1); 538 arg.type(a.substring(0, space)).id(name).name(name); 539 } 540 argumentsType.add(arg.finish(ValueParam.class)); 537 541 ++number; 538 542 } … … 546 550 return this; 547 551 } 552 553 @Override 554 public String toString() { 555 return "ParamBuilder for " + Misc.returnNotNull(id, "<not yet known>"); 556 } 548 557 } 549 558 -
java/main/src/main/java/com/framsticks/params/PropertiesAccess.java
r90 r96 91 91 92 92 @Override 93 public booleantryAutoAppend(Object object) {94 return false;93 public void tryAutoAppend(Object object) { 94 throw new InvalidOperationException(); 95 95 } 96 96 -
java/main/src/main/java/com/framsticks/params/ReflectionAccess.java
r90 r96 378 378 379 379 @Override 380 public booleantryAutoAppend(Object value) {380 public void tryAutoAppend(Object value) { 381 381 assert object != null; 382 for (Method m : backend.autoAppendMethods) { 383 if (m.getParameterTypes()[0].isAssignableFrom(value.getClass())) { 384 try { 385 log.trace("auto appending with value " + value + " with method " + m); 386 m.invoke(object, value); 387 return true; 388 } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException | FramsticksException e) { 389 throw new FramsticksException().msg("failed to auto append").cause(e).arg("value", value).arg("into object", object).arg("with method", m); 390 } 391 } 392 } 393 return false; 382 try { 383 for (Method m : backend.autoAppendMethods) { 384 if (m.getParameterTypes()[0].isAssignableFrom(value.getClass())) { 385 try { 386 log.trace("auto appending with value " + value + " with method " + m); 387 m.invoke(object, value); 388 return; 389 } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException | FramsticksException e) { 390 throw new FramsticksException().msg("failed to auto append").cause(e).arg("with method", m); 391 } 392 } 393 } 394 throw new FramsticksException().msg("no method found to append"); 395 } catch (FramsticksException e) { 396 throw e.arg("value", value).arg("into object", object); 397 } 398 394 399 } 395 400 -
java/main/src/main/java/com/framsticks/params/Registry.java
r90 r96 46 46 associate(javaClass, putFramsClass(FramsClass.build().forClass(javaClass))); 47 47 return this; 48 } 49 50 public FramsClass registerReflectedIfNeeded(Class<?> javaClass) { 51 if (!javaToFramsAssociation.containsKey(javaClass)) { 52 registerAndBuild(javaClass); 53 } 54 return javaToFramsAssociation.get(javaClass); 48 55 } 49 56 -
java/main/src/main/java/com/framsticks/params/SimpleAbstractAccess.java
r90 r96 7 7 8 8 import org.apache.log4j.Logger; 9 10 import com.framsticks.util.UnimplementedException; 9 11 10 12 /** … … 177 179 @Override 178 180 public void copyFrom(AccessInterface src) { 179 clearValues(); 181 throw new UnimplementedException(); 182 // clearValues(); 180 183 //TODO: iterate over self, and pull from src 181 184 /* … … 185 188 */ 186 189 } 187 188 189 190 190 191 191 @Override … … 195 195 for (PrimitiveParam<?> p : filterInstanceof(framsClass.getParamEntries(), PrimitiveParam.class)) { 196 196 Object value = get(p, Object.class); 197 if ( value == null) {197 if ((value == null) || value.equals(p.getDef(Object.class))) { 198 198 continue; 199 199 } -
java/main/src/main/java/com/framsticks/params/SinkInterface.java
r77 r96 5 5 */ 6 6 public interface SinkInterface { 7 8 9 10 7 SinkInterface print(String str); 8 SinkInterface print(Object obj); 9 void breakLine(); 10 void close(); 11 11 } -
java/main/src/main/java/com/framsticks/params/types/ProcedureParam.java
r90 r96 7 7 import java.util.List; 8 8 9 import javax.annotation.Nullable; 9 10 import javax.annotation.concurrent.Immutable; 10 11 … … 16 17 private final ValueParam resultType; 17 18 private final List<ValueParam> argumentsType; 19 private final String signatureString; 18 20 19 21 /** … … 24 26 resultType = builder.getResultType(); 25 27 argumentsType = builder.getArgumentsType(); 28 29 StringBuilder b = new StringBuilder().append("p"); 30 31 if (resultType != null) { 32 b.append(" ").append(resultType.getFramsTypeName()); 33 } 34 b.append("("); 35 boolean first = true; 36 for (ValueParam arg : argumentsType) { 37 if (first) { 38 first = false; 39 } else { 40 b.append(", "); 41 } 42 43 b.append(arg.getFramsTypeName()); 44 if (arg.getName() != null) { 45 b.append(" ").append(arg.getName()); 46 } 47 } 48 b.append(")"); 49 50 signatureString = b.toString(); 26 51 assert argumentsType != null; 27 52 } … … 32 57 } 33 58 34 public ValueParam getResultType() {59 public @Nullable ValueParam getResultType() { 35 60 return resultType; 36 61 } … … 42 67 @Override 43 68 public String getFramsTypeName() { 44 return "p";69 return signatureString; 45 70 } 46 71 -
java/main/src/main/java/com/framsticks/parsers/Loaders.java
r88 r96 32 32 return; 33 33 } 34 if (framsClassAccess.select(builder).tryAutoAppend(object)) { 35 return; 36 } 37 throw new ConstructionException().msg("failed to interpretate object").arg("object", object); 34 framsClassAccess.select(builder).tryAutoAppend(object); 35 // throw new ConstructionException().msg("failed to interpretate object").arg("object", object); 38 36 39 37 } -
java/main/src/main/java/com/framsticks/parsers/Savers.java
r86 r96 8 8 */ 9 9 public class Savers { 10 public static void saveFramsClass(SinkInterfacesink, FramsClass framsClass) {10 public static <S extends SinkInterface> S saveFramsClass(S sink, FramsClass framsClass) { 11 11 12 12 AccessInterface framsClassAccess = new ReflectionAccess(FramsClass.class); … … 18 18 paramAccess.save(sink); 19 19 } 20 return sink; 20 21 } 21 22 -
java/main/src/main/java/com/framsticks/parsers/XmlLoader.java
r90 r96 98 98 99 99 for (Object child : childrenObjects) { 100 if (!access.tryAutoAppend(child)) { 101 throw new FramsticksException().msg("failed to auto append").arg("child", child).arg("parent", object); 102 } 100 access.tryAutoAppend(child); 103 101 } 104 102 } -
java/main/src/main/java/com/framsticks/portals/Portal.java
r90 r96 4 4 import com.framsticks.core.AbstractInstanceListener; 5 5 import com.framsticks.core.Instance; 6 import com.framsticks.core.InstanceUtils; 6 7 import com.framsticks.core.Path; 7 8 import com.framsticks.params.annotations.FramsClassAnnotation; … … 61 62 @Override 62 63 public void run() { 63 instance.resolve(path, new Future<Path>() {64 InstanceUtils.resolve(instance, path, new Future<Path>(Logging.logger(log, "resolve", path)) { 64 65 @Override 65 public void result(Path result , Exception e) {66 Logging.log(log, "resolve", path, e);66 public void result(Path result) { 67 Logging.log(log, "resolve", path, null); 67 68 } 68 69 }); -
java/main/src/main/java/com/framsticks/remote/RecursiveFetcher.java
r90 r96 1 1 package com.framsticks.remote; 2 2 3 import static com.framsticks.core.InstanceUtils.*; 3 4 import com.framsticks.core.Node; 4 5 import com.framsticks.core.Path; … … 8 9 import com.framsticks.core.Instance; 9 10 import com.framsticks.util.dispatching.Future; 11 import com.framsticks.util.FramsticksException; 12 import com.framsticks.util.Logging; 10 13 import com.framsticks.util.StateFunctor; 11 14 import com.framsticks.util.Stopwatch; … … 36 39 assert instance.isActive(); 37 40 log.info("recursively fetched in " + stopwatch); 38 stateFunctor.call( null);41 stateFunctor.call(); 39 42 } 40 43 … … 44 47 log.warn("path " + path + " is not resolved - skipping"); 45 48 } else { 46 AccessInterface access = instance.bindAccess(path);49 AccessInterface access = bindAccess(path); 47 50 FramsClass framsClass = access.getFramsClass(); 48 51 assert framsClass != null; … … 50 53 Object child = access.get(p, Object.class); 51 54 final Path childPath = path.appendNode(new Node(p, child)); 52 if (childPath.isResolved() && instance.getInfoFromCache(childPath) != null) {55 if (childPath.isResolved() && getInfoFromCache(childPath) != null) { 53 56 ++dispatched; 54 57 instance.dispatch(new RunAt<Instance>() { … … 61 64 } 62 65 ++dispatched; 63 instance.resolve(childPath, new Future<Path>( ) {66 instance.resolve(childPath, new Future<Path>(Logging.logger(log, "resolve", RecursiveFetcher.this)) { 64 67 @Override 65 p ublic void result(Path result, Exception e) {68 protected void result(Path result) { 66 69 assert instance.isActive(); 67 if (e != null) {68 log.error(e);69 return;70 }71 70 fetch(result); 72 71 } … … 83 82 instance.fetchValues(path, new StateFunctor() { 84 83 @Override 85 public void call(Exception e) { 86 if (e != null) { 87 log.error("failed to fetch values for " + path + ": " + e); 88 process(null); 89 return; 90 } 84 public void handle(FramsticksException e) { 85 log.error("failed to fetch values for " + path + ": " + e); 86 process(null); 87 } 88 89 @Override 90 public void call() { 91 91 process(path); 92 92 } -
java/main/src/main/java/com/framsticks/remote/RemoteInstance.java
r90 r96 2 2 3 3 import com.framsticks.communication.*; 4 import com.framsticks.communication.queries.CallRequest; 4 5 import com.framsticks.communication.queries.GetRequest; 5 6 import com.framsticks.communication.queries.InfoRequest; 6 7 import com.framsticks.communication.queries.SetRequest; 7 import com.framsticks.communication.util.LoggingSubscriptionCallback; 8 import com.framsticks.core.AbstractInstance; 9 import com.framsticks.core.InstanceUtils; 8 10 import com.framsticks.core.ListChange; 11 import com.framsticks.core.Node; 9 12 import com.framsticks.core.Path; 10 13 import com.framsticks.params.*; … … 17 20 import com.framsticks.util.*; 18 21 import com.framsticks.util.dispatching.Dispatching; 22 import com.framsticks.util.dispatching.ExceptionResultHandler; 19 23 import com.framsticks.util.dispatching.Future; 20 24 import com.framsticks.util.dispatching.Joinable; … … 24 28 import com.framsticks.util.lang.Pair; 25 29 import com.framsticks.util.dispatching.RunAt; 30 import static com.framsticks.core.InstanceUtils.*; 26 31 27 32 import java.util.*; 33 34 import javax.annotation.Nonnull; 28 35 29 36 import org.apache.log4j.Logger; … … 33 40 */ 34 41 @FramsClassAnnotation 35 public class RemoteInstance extends Instance implements JoinableParent {42 public class RemoteInstance extends AbstractInstance implements JoinableParent { 36 43 37 44 private final static Logger log = Logger.getLogger(RemoteInstance.class.getName()); 38 45 39 protected Path simulator;40 46 protected ClientConnection connection; 41 47 … … 64 70 } 65 71 72 protected void onProtocolVersionNegotiated() { 73 } 74 75 66 76 public void setConnection(final ClientConnection connection) { 67 77 this.connection = connection; 68 this.connection.setConnectedFunctor(new StateFunctor() { 69 @Override 70 public void call(Exception e) { 71 if (e != null) { 72 fireRun(e); 73 return; 74 } 75 connection.negotiateProtocolVersion(new StateFunctor() { 78 final ExceptionResultHandler failure = new ExceptionResultHandler() { 79 @Override 80 public void handle(FramsticksException exception) { 81 log.fatal("failed to establish connection: ", exception); 82 // log.fatal("unsupported protocol version!\n minimal version is: " + "\nmanager protocol is: " + connection.getProtocolVersion()); 83 Dispatching.drop(connection, RemoteInstance.this); 84 fireRun(exception); 85 } 86 }; 87 88 this.connection.setConnectedFunctor(new AbstractStateFunctor(failure) { 89 @Override 90 public void call() { 91 connection.negotiateProtocolVersion(new AbstractStateFunctor(failure) { 76 92 @Override 77 public void call(Exception e) { 78 if (e != null) { 79 log.fatal("unsupported protocol version!\n minimal version is: " + "\nmanager protocol is: " + connection.getProtocolVersion()); 80 Dispatching.drop(connection, RemoteInstance.this); 81 fireRun(e); 82 return; 83 } 84 85 dispatch(new RunAt<Instance>() { 86 @Override 87 public void run() { 88 resolveAndFetch("/simulator", new Future<Path>() { 89 @Override 90 public void result(Path path, Exception e) { 91 if (e != null) { 92 log.fatal("failed to resolve simulator node"); 93 fireRun(e); 94 return; 95 } 96 assert isActive(); 97 simulator = path; 98 fireRun(null); 99 log.info("resolved simulator node"); 100 101 EventParam param = getParam(simulator, "running_changed", EventParam.class); 102 assert param != null; 103 connection.subscribe(simulator.getTextual() + "/" + param.getId(), RemoteInstance.this, new LoggingSubscriptionCallback<Instance>(log, "server running state change", new EventCallback() { 104 @Override 105 public void call(List<File> files) { 106 dispatch(new RunAt<Instance>() { 107 @Override 108 public void run() { 109 updateSimulationRunning(); 110 } 111 }); 112 } 113 })); 114 new PeriodicTask<Instance>(RemoteInstance.this, 1000) { 115 @Override 116 public void run() { 117 updateSimulationRunning(); 118 again(); 119 } 120 }; 121 } 122 }); 123 } 124 }); 93 public void call() { 94 onProtocolVersionNegotiated(); 125 95 } 126 96 }); 127 97 } 128 98 }); 129 130 99 } 131 100 … … 136 105 } 137 106 138 public void setRunning(final boolean running) {139 assert isActive();140 //simulator.call(simulator.getParam(running ? "start" : "stop", ProcedureParam.class), new LoggingStateCallback(log, (running ? "starting" : "stopping") + " server"));141 }142 143 protected final UnaryListenersSet<Boolean> simulationRunningListeners = new UnaryListenersSet<Boolean>();144 145 protected void updateSimulationRunning() {146 assert isActive();147 /*148 fetchValue(simulator, getParam(simulator, "running", Param.class), new StateFunctor() {149 @Override150 public void call(Exception e) {151 if (e != null) {152 log.fatal("failed to query simulator running status: " + e);153 return;154 }155 156 invokeLater(new Runnable() {157 @Override158 public void run() {159 boolean value = bindAccess(simulator).get("running", Boolean.class);160 log.trace("server running: " + value);161 simulationRunningListeners.call(value);162 }163 });164 165 }166 });167 */168 }169 170 public void addRunningStateListener(UnaryFunctor<Boolean, Boolean> listener) {171 assert isActive();172 simulationRunningListeners.add(listener);173 }174 175 // public void disconnect() {176 // assert isActive();177 // if (connection.isConnected()) {178 // Dispatching.stop(connection, this);179 // }180 // }181 182 107 public final ClientConnection getConnection() { 183 108 return connection; … … 185 110 186 111 @Override 187 public void fetchValue(final Path path, final Param param, final StateFunctor stateFunctor) {112 public void fetchValue(final Path path, final ValueParam param, final StateFunctor stateFunctor) { 188 113 assert isActive(); 189 114 assert param != null; … … 194 119 assert isActive(); 195 120 if (!response.getOk()) { 196 stateFunctor. call(new Exception(response.getComment()));121 stateFunctor.handle(new FramsticksException().msg("failed to fetch value").arg("comment", response.getComment())); 197 122 return; 198 123 } 199 124 try { 200 processFetchedValues(path, response.getFiles());201 stateFunctor.call( null);202 } catch ( Exception ex) {203 stateFunctor. call(ex);125 InstanceUtils.processFetchedValues(path, response.getFiles()); 126 stateFunctor.call(); 127 } catch (FramsticksException ex) { 128 stateFunctor.handle(ex); 204 129 } 205 130 } … … 209 134 protected final Map<String, Set<Future<FramsClass>>> infoRequests = new HashMap<String, Set<Future<FramsClass>>>(); 210 135 211 protected void finishInfoRequest(String id, FramsClass result, Exception e) {136 protected void finishInfoRequest(String id, FramsClass result, FramsticksException e) { 212 137 assert isActive(); 213 138 Set<Future<FramsClass>> futures = infoRequests.get(id); 214 139 infoRequests.remove(id); 215 140 for (Future<FramsClass> f : futures) { 216 f.result(result, e);217 } 218 } 219 220 @Override 221 p rotectedvoid fetchInfo(final Path path, final Future<FramsClass> future) {141 Future.passOrHandle(f, result, e); 142 } 143 } 144 145 @Override 146 public void fetchInfo(final Path path, final Future<FramsClass> future) { 222 147 223 148 final String name = path.getTop().getParam().getContainedTypeName(); … … 238 163 public void process(Response response) { 239 164 assert isActive(); 240 if (!response.getOk()) {241 finishInfoRequest(name, null, new Exception(response.getComment()));242 return;243 }244 245 assert response.getFiles().size() == 1;246 assert path.isTheSame(response.getFiles().get(0).getPath());247 FramsClass framsClass;248 165 try { 249 framsClass = processFetchedInfo(response.getFiles().get(0)); 250 } catch (ConstructionException e) { 251 log.fatal("could not read class info"); 252 finishInfoRequest(name, null, new Exception("could not read class info")); 253 return; 254 } 255 256 CompositeParam thisParam = path.getTop().getParam(); 257 if (!thisParam.isMatchingContainedName(framsClass.getId())) { 258 String mismatch = "class name mismatch: param=" + thisParam.getContainedTypeName() + " differs from fetched=" + framsClass.getId(); 259 log.error(mismatch); 260 finishInfoRequest(name, null, new Exception(mismatch)); 261 return; 262 } 263 finishInfoRequest(name, framsClass, null); 166 if (!response.getOk()) { 167 throw new FramsticksException().msg("invalid response").arg("comment", response.getComment()); 168 } 169 if (response.getFiles().size() != 1) { 170 throw new FramsticksException().msg("invalid number of files in response").arg("files", response.getFiles().size()); 171 } 172 if (!path.isTheSame(response.getFiles().get(0).getPath())) { 173 throw new FramsticksException().msg("path mismatch").arg("returned path", response.getFiles().get(0).getPath()); 174 } 175 FramsClass framsClass = InstanceUtils.processFetchedInfo(RemoteInstance.this, response.getFiles().get(0)); 176 177 CompositeParam thisParam = path.getTop().getParam(); 178 if (!thisParam.isMatchingContainedName(framsClass.getId())) { 179 throw new FramsticksException().msg("framsclass id mismatch").arg("request", thisParam.getContainedTypeName()).arg("fetched", framsClass.getId()); 180 } 181 182 finishInfoRequest(name, framsClass, null); 183 } catch (FramsticksException e) { 184 finishInfoRequest(name, null, e.arg("path", path)); 185 } 264 186 } 265 187 }); … … 276 198 public void process(Response response) { 277 199 assert isActive(); 278 if (!response.getOk()) {279 stateFunctor.call(new Exception(response.getComment()));280 return;281 }282 200 try { 283 processFetchedValues(path, response.getFiles()); 284 stateFunctor.call(null); 285 } catch (Exception ex) { 286 log.error("an exception occurred while loading: " + ex); 287 ex.printStackTrace(); 288 stateFunctor.call(ex); 201 if (!response.getOk()) { 202 throw new FramsticksException().msg("failed to fetch values").arg("comment", response.getComment()); 203 } 204 InstanceUtils.processFetchedValues(path, response.getFiles()); 205 stateFunctor.call(); 206 } catch (FramsticksException e) { 207 stateFunctor.handle(e); 289 208 } 290 209 } … … 294 213 @Override 295 214 public void resolve(final Path path, final Future<Path> future) { 296 assert isActive(); 297 if (path.getTop().getObject() != null) { 298 if (getInfoFromCache(path) != null) { 299 future.result(path, null); 300 return; 301 } 302 findInfo(path, new Future<FramsClass>() { 303 @Override 304 public void result(FramsClass result, Exception e) { 305 if (e != null) { 306 future.result(null, e); 307 return; 308 } 309 future.result(path, null); 310 } 311 }); 312 return; 313 } 314 findInfo(path, new Future<FramsClass>() { 315 @Override 316 public void result(FramsClass result, Exception e) { 317 assert isActive(); 318 if (e != null) { 319 future.result(null, e); 320 return; 321 } 322 assert path.getTop().getParam().isMatchingContainedName(result.getId()); 323 Path p = (path.getTop().getParam().getContainedTypeName() != null ? path : path.tryFindResolution()); 324 future.result(createIfNeeded(p), null); 325 } 326 }); 215 InstanceUtils.resolve(path, future); 327 216 } 328 217 … … 330 219 protected void tryRegisterOnChangeEvents(final Path path) { 331 220 assert isActive(); 332 AccessInterface access = bindAccess(path);221 AccessInterface access = InstanceUtils.bindAccess(path); 333 222 if (!(access instanceof ListAccess)) { 334 223 return; … … 396 285 } 397 286 287 protected Future<Path> futureListChanger(final ListChange listChange, final String path) { 288 return new Future<Path>(Logging.logger(log, "failed to " + listChange, path)) { 289 @Override 290 protected void result(Path result) { 291 log.debug(listChange + ": " + result); 292 fireListChange(result, listChange); 293 } 294 }; 295 } 296 398 297 protected void reactToChange(final Path path, final ListChange listChange) { 399 298 assert isActive(); 400 299 log.debug("reacting to change " + listChange + " in " + path); 401 AccessInterface access = bindAccess(path);300 AccessInterface access = InstanceUtils.bindAccess(path); 402 301 assert access != null; 403 302 404 303 if ((listChange.getAction() == ListChange.Action.Modify) && (listChange.getPosition() == -1)) { 405 304 final String p = path.getTextual(); 406 resolveAndFetch(p, new Future<Path>() { 407 @Override 408 public void result(Path result, Exception e) { 409 if (e != null) { 410 log.error("failed to modify " + p + ": " + e); 411 return; 412 } 413 fireListChange(path, listChange); 414 } 415 }); 305 InstanceUtils.resolveAndFetch(this, p, futureListChanger(listChange, p)); 416 306 return; 417 307 } … … 420 310 assert childParam != null; 421 311 switch (listChange.getAction()) { 422 case Add: { 423 final String p = path.getTextual() + "/" + childParam.getId(); 424 resolveAndFetch(p, new Future<Path>() { 425 @Override 426 public void result(Path result, Exception e) { 427 if (e != null) { 428 log.error("failed to add " + p + ": " + e); 429 return; 430 } 431 log.debug("added: " + result); 432 fireListChange(path, listChange); 433 } 434 }); 435 break; 436 } 437 case Remove: { 438 access.set(childParam, null); 439 fireListChange(path, listChange); 440 break; 441 } 442 case Modify: { 443 final String p = path.getTextual() + "/" + childParam.getId(); 444 resolveAndFetch(p, new Future<Path>() { 445 @Override 446 public void result(Path result, Exception e) { 447 if (e != null) { 448 log.error("failed to modify " + p + ": " + e); 449 return; 450 } 451 fireListChange(path, listChange); 452 } 453 }); 454 break; 455 } 456 } 457 } 458 459 //TODO ValueParam 460 @Override 461 public void storeValue(final Path path, final Param param, final Object value, final StateFunctor stateFunctor) { 312 case Add: { 313 final String p = path.getTextual() + "/" + childParam.getId(); 314 InstanceUtils.resolveAndFetch(this, p, futureListChanger(listChange, p)); 315 break; 316 } 317 case Remove: { 318 access.set(childParam, null); 319 fireListChange(path, listChange); 320 break; 321 } 322 case Modify: { 323 final String p = path.getTextual() + "/" + childParam.getId(); 324 InstanceUtils.resolveAndFetch(this, p, futureListChanger(listChange, p)); 325 break; 326 } 327 } 328 } 329 330 @Override 331 public void storeValue(final Path path, final ValueParam param, final Object value, StateFunctor stateFunctor) { 462 332 assert isActive(); 463 333 464 334 log.trace("storing value " + param + " for " + path); 465 connection.send(new SetRequest().value(value.toString()).field(param.getId()).path(path.getTextual()), this, new StateCallback<Instance>() { 466 @Override 467 public void call(Exception e) { 468 if (e == null) { 469 bindAccess(path).set((ValueParam) param, value); 470 } 471 stateFunctor.call(e); 335 connection.send(new SetRequest().value(value.toString()).field(param.getId()).path(path.getTextual()), this, new StateCallback<Instance>(stateFunctor) { 336 @Override 337 protected void callImpl() { 338 InstanceUtils.bindAccess(path).set((ValueParam) param, value); 472 339 } 473 340 }); … … 504 371 505 372 @Override 506 public void call(Path path, ProcedureParam param, Object[] arguments, StateFunctor stateFunctor) { 507 throw new UnimplementedException(); 373 public void call(@Nonnull final Path path, @Nonnull final ProcedureParam procedure, @Nonnull Object[] arguments, final Future<Object> future) { 374 assert isActive(); 375 assert path.isResolved(); 376 377 //TODO validate arguments type using params 378 connection.send(new CallRequest().procedure(procedure.getId()).arguments(Arrays.asList(arguments)).path(path.getTextual()), this, new ResponseCallback<Instance>() { 379 @Override 380 public void process(Response response) { 381 assert isActive(); 382 try { 383 if (!response.getOk()) { 384 throw new FramsticksException().msg("failed to call procedure").arg("procedure", procedure).arg("comment", response.getComment()); 385 } 386 // InstanceUtils.processFetchedValues(path, response.getFiles()); 387 future.pass(null); 388 } catch (FramsticksException ex) { 389 future.handle(ex); 390 } 391 } 392 }); 393 394 } 395 396 @Override 397 public Path create(Path path) { 398 assert isActive(); 399 assert !path.isResolved(); 400 Path resolved = path.tryFindResolution(); 401 if (!resolved.isResolved()) { 402 log.debug("creating: " + path); 403 AccessInterface access = registry.prepareAccess(path.getTop().getParam()); 404 assert access != null; 405 Object child = access.createAccessee(); 406 assert child != null; 407 if (path.size() == 1) { 408 setRoot(new Node(getRoot().getParam(), child)); 409 } else { 410 bindAccess(this, path.getUnder()).set(path.getTop().getParam(), child); 411 } 412 resolved = path.appendResolution(child); 413 } 414 tryRegisterOnChangeEvents(resolved); 415 return resolved; 508 416 } 509 417 -
java/main/src/main/java/com/framsticks/running/ExternalProcess.java
r90 r96 14 14 import org.apache.log4j.Logger; 15 15 16 import com.framsticks.core.Entity;17 16 import com.framsticks.params.annotations.AutoAppendAnnotation; 18 17 import com.framsticks.params.annotations.FramsClassAnnotation; … … 30 29 31 30 @FramsClassAnnotation 32 public class ExternalProcess extends AbstractJoinable implements JoinableParent , Entity{31 public class ExternalProcess extends AbstractJoinable implements JoinableParent { 33 32 private static final Logger log = Logger.getLogger(ExternalProcess.class); 34 33 -
java/main/src/main/java/com/framsticks/util/FramsticksException.java
r88 r96 35 35 } 36 36 37 @Override 38 public String getMessage() { 39 StringBuilder b = new StringBuilder(); 37 public void getShortMessage(StringBuilder b) { 40 38 if (message != null) { 41 39 b.append(message); 40 } else { 41 b.append("?"); 42 42 } 43 43 if (arguments != null) { … … 45 45 b.append(" "); 46 46 } 47 Delimeted d = new Delimeted(", ", "");47 Delimeted<Pair<String, Object>> d = new Delimeted<>(", ", ""); 48 48 d.append(arguments.iterator()); 49 49 50 50 b.append("(").append(d.build()).append(")"); 51 51 } 52 if (this.getCause() != null) { 53 b.append(" caused by: [").append(this.getCause().getMessage()).append("]"); 52 } 53 54 public String getMsg() { 55 return message; 56 } 57 58 @Override 59 public String getMessage() { 60 StringBuilder b = new StringBuilder(); 61 getShortMessage(b); 62 Throwable cause = this.getCause(); 63 while (cause != null) { 64 b.append(" caused by: [").append(cause.getClass().getCanonicalName()).append(": "); 65 if (cause instanceof FramsticksException) { 66 ((FramsticksException) cause).getShortMessage(b); 67 } else { 68 b.append(cause.getMessage()); 69 } 70 b.append("]"); 71 cause = cause.getCause(); 54 72 } 55 73 return b.toString(); -
java/main/src/main/java/com/framsticks/util/Logging.java
r90 r96 2 2 3 3 import org.apache.log4j.Logger; 4 5 import com.framsticks.util.dispatching.ExceptionResultHandler; 4 6 5 7 /** … … 17 19 return false; 18 20 } 21 22 public static ExceptionResultHandler logger(final Logger logger, final String action, final Object subject) { 23 return new ExceptionResultHandler() { 24 @Override 25 public void handle(FramsticksException e) { 26 Logging.log(logger, action, subject, e); 27 } 28 }; 29 } 19 30 } -
java/main/src/main/java/com/framsticks/util/PeriodicTask.java
r90 r96 21 21 22 22 public void again() { 23 dispatcher.dispatch(new Task<C>( System.currentTimeMillis() +period) {23 dispatcher.dispatch(new Task<C>(period) { 24 24 @Override 25 25 public void run() { -
java/main/src/main/java/com/framsticks/util/StateFunctor.java
r85 r96 1 1 package com.framsticks.util; 2 3 import com.framsticks.util.dispatching.ExceptionResultHandler; 2 4 3 5 /** 4 6 * @author Piotr Sniegowski 5 7 */ 6 public interface StateFunctor {8 public interface StateFunctor extends ExceptionResultHandler { 7 9 //TODO RunAt 8 public void call( Exception e);10 public void call(); 9 11 } -
java/main/src/main/java/com/framsticks/util/UnsupportedOperationException.java
r84 r96 4 4 * @author Piotr Sniegowski 5 5 */ 6 public class UnsupportedOperationException extends Exception {6 public class UnsupportedOperationException extends FramsticksException { 7 7 8 8 /** -
java/main/src/main/java/com/framsticks/util/dispatching/AbstractJoinable.java
r90 r96 14 14 import com.framsticks.util.FramsticksException; 15 15 16 17 18 16 public abstract class AbstractJoinable implements Joinable { 17 19 18 private static final Logger log = Logger.getLogger(AbstractJoinable.class); 20 21 19 22 20 protected final Set<JoinableParent> owners = new HashSet<JoinableParent>(); … … 25 23 protected static final Set<AbstractJoinable> joinablesRegistry = Collections.synchronizedSet(new HashSet<AbstractJoinable>()); 26 24 27 JoinableState state = JoinableState.INITILIAZED; 25 protected JoinableState state = JoinableState.INITILIAZED; 26 protected JoinableParent parent; 27 protected Monitor monitor; 28 28 29 29 /** … … 53 53 this.state = state; 54 54 55 synchronized (this) { 56 log.debug(this + " is notifying " + joinableListeners.size() + " parents"); 57 58 List<JoinableParent> parents = new LinkedList<>(); 59 CollectionUtils.addAll(parents, joinableListeners.iterator()); 60 61 for (JoinableParent p : parents) { 62 if (p != null) { 63 Dispatching.childChangedState(p, this, state); 64 } 65 } 66 this.notifyAll(); 67 } 55 log.debug(this + " is notifying " + joinableListeners.size() + " parents"); 56 57 List<JoinableParent> parents = new LinkedList<>(); 58 CollectionUtils.addAll(parents, joinableListeners.iterator()); 59 60 for (JoinableParent p : parents) { 61 if (p != null) { 62 Dispatching.childChangedState(p, this, state); 63 } 64 } 65 this.notifyAll(); 66 68 67 report(); 69 68 … … 145 144 } 146 145 if (start) { 146 assert monitor == null; 147 monitor = owner.getMonitor(); 147 148 return this.start(); 148 149 } … … 185 186 } 186 187 188 protected boolean isRunning() { 189 return state.equals(JoinableState.RUNNING); 190 } 191 192 @Override 193 public String toString() { 194 return getName(); 195 } 196 197 // @Override 198 public Monitor getMonitor() { 199 return monitor; 200 } 201 187 202 188 203 } -
java/main/src/main/java/com/framsticks/util/dispatching/Dispatching.java
r90 r96 3 3 import org.apache.log4j.Logger; 4 4 5 import com.framsticks.util.FramsticksException; 5 6 import com.framsticks.util.StateFunctor; 6 7 … … 28 29 @Override 29 30 public void run() { 30 stateFunctor.call( null);31 stateFunctor.call(); 31 32 } 32 33 }); … … 170 171 } 171 172 172 173 public static class Waiter { 174 protected boolean done = false; 175 176 protected final double timeOut; 177 178 /** 179 * @param timeOut 180 */ 181 public Waiter(double timeOut) { 182 this.timeOut = timeOut; 183 } 184 185 public synchronized void pass() { 186 done = true; 187 this.notify(); 188 } 189 190 public synchronized void waitFor() { 191 long end = System.currentTimeMillis() + (int)(timeOut * 1000); 192 while ((!done) && System.currentTimeMillis() < end) { 193 try { 194 this.wait(end - System.currentTimeMillis()); 195 } catch (InterruptedException e) { 196 break; 197 } 198 } 199 if (!done) { 200 throw new FramsticksException().msg("waiter timed out"); 201 } 202 } 203 } 204 205 206 public static <C> void synchronize(Dispatcher<C> dispatcher, double seconds) { 207 final Waiter waiter = new Waiter(seconds); 208 dispatcher.dispatch(new RunAt<C>() { 209 @Override 210 public void run() { 211 waiter.pass(); 212 } 213 }); 214 waiter.waitFor(); 215 } 173 216 174 217 } -
java/main/src/main/java/com/framsticks/util/dispatching/Future.java
r84 r96 1 1 package com.framsticks.util.dispatching; 2 3 import com.framsticks.util.FramsticksException; 2 4 3 5 /** 4 6 * @author Piotr Sniegowski 5 7 */ 6 public interface Future <T> { 7 void result(T result, Exception e); 8 public abstract class Future<T> implements ExceptionResultHandler { 9 10 protected final ExceptionResultHandler handler; 11 12 public Future(ExceptionResultHandler handler) { 13 this.handler = handler; 14 } 15 16 public Future() { 17 this.handler = null; 18 } 19 20 protected abstract void result(T result); 21 22 public final void pass(T result) { 23 try { 24 result(result); 25 } catch (FramsticksException e) { 26 handle(e); 27 } 28 } 29 30 public static <T> void passOrHandle(Future<T> future, T value, FramsticksException e) { 31 if (e != null) { 32 future.handle(e); 33 } else { 34 future.pass(value); 35 } 36 } 37 38 @Override 39 public void handle(FramsticksException exception) { 40 if (handler != null) { 41 handler.handle(exception); 42 return; 43 } 44 throw exception; 45 } 8 46 } -
java/main/src/main/java/com/framsticks/util/dispatching/Joinable.java
r88 r96 5 5 6 6 public interface Joinable { 7 8 /** The name of the joinable. 9 * 10 * It should never be empty, but it is not required to remain 11 * constant during lifetime of the object. 12 */ 13 public String getName(); 7 14 8 15 public boolean use(@Nonnull JoinableParent owner); -
java/main/src/main/java/com/framsticks/util/dispatching/JoinableCollection.java
r88 r96 2 2 3 3 import java.util.Collections; 4 import java.util.HashMap;5 4 import java.util.HashSet; 6 5 import java.util.Iterator; 7 import java.util.Map;8 6 import java.util.Set; 9 7 10 import com.framsticks.core.Entity;11 8 import com.framsticks.params.annotations.AutoAppendAnnotation; 12 9 import com.framsticks.params.annotations.FramsClassAnnotation; … … 19 16 20 17 protected final Set<T> joinables = new HashSet<T>(); 21 protected final Map<String, T> namedJoinables = new HashMap<>();22 18 23 19 protected boolean finishIfOne; … … 34 30 35 31 @AutoAppendAnnotation 36 public void add(T joinable) { 37 assert isInState(JoinableState.INITILIAZED); 32 public synchronized void add(T joinable) { 33 if (this.state.ordinal() > JoinableState.RUNNING.ordinal()) { 34 throw new FramsticksException().msg("failed to add joinable - collection is passed running state").arg("joinable", joinable).arg("collection", this); 35 } 38 36 39 37 if (joinables.contains(joinable)) { 40 38 throw new FramsticksException().msg("joinable is already observed").arg("joinable", joinable).arg("in", this); 41 39 } 42 // if (observables.containsKey(observable.getName())) { 43 // throw new FramsticksException().msg("observable with given name already exists").arg("name", observable.getName()).arg("in", this); 44 // } 40 joinables.add(joinable); 45 41 46 if (joinable instanceof Entity) { 47 Entity e = (Entity) joinable; 48 if (!namedJoinables.containsKey(e.getName())) { 49 namedJoinables.put(e.getName(), joinable); 50 } 42 if (this.state.equals(JoinableState.RUNNING)) { 43 Dispatching.use(joinable, this); 51 44 } 52 53 joinables.add(joinable);54 45 } 55 46 … … 107 98 public void childChangedState(Joinable joinable, JoinableState state) { 108 99 proceedToState(getNextState()); 109 110 100 } 111 101 … … 129 119 130 120 public T get(String name) { 131 return namedJoinables.get(name); 121 for (T j : joinables) { 122 if (j.getName().equals(name)) { 123 return j; 124 } 125 } 126 return null; 132 127 } 133 128 129 public int size() { 130 return joinables.size(); 131 } 134 132 135 public Map<String, T> getObservables() { 136 return Collections.unmodifiableMap(namedJoinables); 133 public boolean contains(T joinable) { 134 return joinables.contains(joinable); 135 } 136 137 @Override 138 public String getName() { 139 return observableName; 137 140 } 138 141 -
java/main/src/main/java/com/framsticks/util/dispatching/JoinableParent.java
r88 r96 4 4 5 5 public void childChangedState(Joinable joinable, JoinableState state); 6 public Monitor getMonitor(); 6 7 7 8 } -
java/main/src/main/java/com/framsticks/util/dispatching/Monitor.java
r90 r96 2 2 3 3 import org.apache.log4j.Logger; 4 // import edu.umd.cs.findbugs.annotations.SuppressWarnings;5 4 import com.framsticks.util.dispatching.Dispatching; 5 import java.lang.Thread; 6 6 7 7 public class Monitor implements JoinableParent { … … 10 10 11 11 protected final Joinable joinable; 12 protected final Thread shutdownHook; 12 13 13 14 /** … … 16 17 public Monitor(Joinable joinable) { 17 18 this.joinable = joinable; 19 20 shutdownHook = new Thread(new Runnable() { 21 @Override 22 public void run() { 23 log.debug("running shutdown hook"); 24 Monitor.this.drop().join(); 25 } 26 }); 27 } 28 29 public Monitor use() { 30 Runtime.getRuntime().addShutdownHook(shutdownHook); 31 32 log.debug(this + " is using"); 33 Dispatching.use(joinable, this); 34 return this; 18 35 } 19 36 … … 34 51 } 35 52 36 public Monitor use() {37 log.debug(this + " is using");38 Dispatching.use(joinable, this);39 return this;40 }41 53 42 54 public Monitor drop() { … … 50 62 Dispatching.joinAbsolutely(joinable); 51 63 log.debug(this + " is joined"); 64 65 try { 66 Runtime.getRuntime().removeShutdownHook(shutdownHook); 67 } catch (IllegalStateException e) { 68 /** In case IllegalStateException is caught, it means that JVM is in finalization stage */ 69 } 70 52 71 return this; 53 72 } … … 67 86 } 68 87 88 @Override 89 public Monitor getMonitor() { 90 return this; 91 } 92 93 protected ExceptionHandler taskExceptionHandler; 94 95 /** 96 * @return the taskExceptionHandler 97 */ 98 public ExceptionHandler getTaskExceptionHandler() { 99 return taskExceptionHandler; 100 } 101 102 /** 103 * @param taskExceptionHandler the taskExceptionHandler to set 104 */ 105 public void setTaskExceptionHandler(ExceptionHandler taskExceptionHandler) { 106 this.taskExceptionHandler = taskExceptionHandler; 107 } 108 69 109 } -
java/main/src/main/java/com/framsticks/util/dispatching/Task.java
r85 r96 13 13 14 14 public Task(long moment) { 15 this.moment = moment;15 this.moment = System.currentTimeMillis() + moment; 16 16 } 17 17 -
java/main/src/main/java/com/framsticks/util/dispatching/Thread.java
r90 r96 47 47 protected void routine() { 48 48 log.debug("starting thread " + this); 49 assert getMonitor() != null; 50 ExceptionHandler exceptionHandler = getMonitor().getTaskExceptionHandler(); 49 51 while (!java.lang.Thread.interrupted()) { 50 52 Task<? extends C> task; … … 73 75 task.run(); 74 76 } catch (Exception e) { 77 if (exceptionHandler != null) { 78 if (exceptionHandler.handle(this, e)) { 79 continue; 80 } 81 } 75 82 log.error("error in thread: ", e); 76 83 } -
java/main/src/main/java/com/framsticks/util/lang/Delimeted.java
r86 r96 3 3 import java.util.Iterator; 4 4 5 import org.apache.commons.collections.Closure;5 // import org.apache.commons.collections.Closure; 6 6 7 public class Delimeted implements Closure{7 public class Delimeted<T> { 8 8 9 9 protected final String delimeter; … … 19 19 } 20 20 21 public final Delimeted append(Objectobject) {21 public final Delimeted<T> append(T object) { 22 22 if (builder != null) { 23 23 builder.append(delimeter); … … 29 29 } 30 30 31 public final Delimeted append(Iterator<?> i) {31 public final Delimeted<T> append(Iterator<T> i) { 32 32 while (i.hasNext()) { 33 33 append(i.next()); … … 41 41 42 42 @Override 43 public void execute(Object input) {44 append(input);43 public String toString() { 44 return build(); 45 45 } 46 46 47 // @Override 48 // public void execute(Object input) { 49 // append(input); 50 // } 51 47 52 } -
java/main/src/main/java/com/framsticks/util/lang/Pair.java
r87 r96 24 24 } 25 25 Pair<?, ?> p = (Pair<?, ?>) obj; 26 // return first == p.first && second.equals(se)27 26 return first.equals(p.first) && second.equals(p.second); 28 27 } … … 33 32 } 34 33 34 public static <U1, U2> Pair<U1, U2> make(U1 first, U2 second) { 35 return new Pair<U1, U2>(first, second); 36 } 37 35 38 } -
java/main/src/main/java/com/framsticks/util/lang/Strings.java
r86 r96 1 1 package com.framsticks.util.lang; 2 3 import com.framsticks.util.FramsticksException; 2 4 3 5 /** … … 15 17 public static boolean notEmpty(String str) { 16 18 return str != null && !str.equals(""); 19 } 20 21 public static void assureNotEmpty(String str) { 22 if (!notEmpty(str)) { 23 throw new FramsticksException().msg("string is empty"); 24 } 17 25 } 18 26 … … 35 43 int pos = string.indexOf(separator); 36 44 if (pos == -1) { 37 return new Pair<String, String>(string.substring(0, 38 string.length() - 1), second); 45 return new Pair<String, String>(string, second); 39 46 } else { 40 return new Pair<String, String>(string.substring(0, pos), 41 string.substring(pos + 1)); 47 return new Pair<String, String>(string.substring(0, pos), string.substring(pos + 1)); 42 48 } 43 49 } -
java/main/src/main/resources/configs/framsticks.xml
r90 r96 3 3 <import class="com.framsticks.gui.Browser" /> 4 4 <import class="com.framsticks.remote.RemoteInstance" /> 5 <import class="com.framsticks.remote.SimulatorInstance" /> 5 6 <import class="com.framsticks.model.ModelPackage" /> 6 7 <import class="com.framsticks.model.ModelBuilder" /> 7 8 <import class="com.framsticks.model.f0.SchemaBuilder" /> 8 9 <import class="com.framsticks.core.ObjectInstance" /> 10 <import class="com.framsticks.hosting.Server" /> 9 11 <import class="com.framsticks.test.TestClass" /> 10 12 <Browser> 11 < RemoteInstance name="localhost:9009" address="localhost:9009">13 <SimulatorInstance name="localhost:9009" address="localhost:9009"> 12 14 <ModelPackage /> 13 </ RemoteInstance>15 </SimulatorInstance> 14 16 <ObjectInstance name="model"> 15 17 <ModelBuilder resource="/examples/f0_example.txt" /> … … 18 20 <SchemaBuilder /> 19 21 </ObjectInstance> 22 <RemoteInstance name="remote" address="localhost:9007" /> 23 </Browser> 24 <Server name="server" port="9007"> 20 25 <ObjectInstance name="test"> 21 26 <TestClass /> 22 27 </ObjectInstance> 23 </ Browser>28 </Server> 24 29 </Framsticks> -
java/main/src/main/resources/configs/log4j.properties
r90 r96 29 29 30 30 log4j.logger.com.framsticks=INFO 31 # log4j.logger.com.framsticks.core.Framsticks=DEBUG 32 # log4j.logger.com.framsticks.gui.Frame=DEBUG 31 33 # log4j.logger.com.framsticks.core.ObjectInstance=DEBUG 32 34 # log4j.logger.com.framsticks.core.Instance=DEBUG 33 log4j.logger.com.framsticks.gui.controls.ProcedureControl=DEBUG35 # log4j.logger.com.framsticks.gui.controls.ProcedureControl=DEBUG 34 36 # log4j.logger.com.framsticks.params.ReflectionAccess=TRACE 35 37 # log4j.logger.com.framsticks.util.dispatching.Dispatching=DEBUG -
java/main/src/test/java/com/framsticks/core/FramsticksTest.java
r88 r96 20 20 Framsticks framsticks = Framsticks.loadConfiguration(stream); 21 21 assertThat(framsticks).isNotNull(); 22 assertThat(framsticks. getObservables().size()).isEqualTo(1);23 assertThat(framsticks.get Observables().get("browser")).isInstanceOf(Browser.class);22 assertThat(framsticks.size()).isEqualTo(1); 23 assertThat(framsticks.get("browser")).isInstanceOf(Browser.class); 24 24 } 25 25 -
java/main/src/test/java/com/framsticks/core/ObjectInstanceTest.java
r90 r96 19 19 import com.framsticks.params.ReflectionAccess; 20 20 import com.framsticks.params.types.FloatParam; 21 22 import static com.framsticks.core.InstanceUtils.*; 23 21 24 22 25 import static org.fest.assertions.Assertions.*; … … 48 51 public void startInstance() { 49 52 instance = new ObjectInstance(); 50 instance. getRegistry().takeAllFrom(schema.getRegistry());53 instance.takeAllFrom(schema.getRegistry()); 51 54 52 55 instance.setRootObject(model); … … 62 65 })).isEqualTo("bla"); 63 66 64 assertDispatch(instance,new RunAt<Instance>() {67 instance.dispatch(new RunAt<Instance>() { 65 68 @Override 66 69 public void run() { 67 70 assertThat(instance.getRootObject(Model.class).getNeuroDefinitions().get(2).details).isEqualTo("G"); 68 71 69 Path path = instance.getPath("/");72 Path path = Path.to(instance, "/"); 70 73 assertThat(path.isResolved()); 71 AccessInterface access = instance.bindAccess(path);74 AccessInterface access = InstanceUtils.bindAccess(path); 72 75 assertThat(access.get("se", Double.class)).isEqualTo(1.0); 73 76 74 assertThat( instance.bindAccess("/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getDef(Double.class)).isEqualTo(1.0);75 assertThat( instance.bindAccess("/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getMax(Double.class)).isEqualTo(999.0);76 assertThat( instance.bindAccess("/parts/2")).isInstanceOf(ReflectionAccess.class);77 assertThat( instance.getPath("/neurodefs").getTopObject()).isInstanceOf(ArrayList.class);78 assertThat( instance.getPath("/joints/1").getTopObject()).isInstanceOf(Joint.class);79 assertThat( instance.bindAccess("/parts/2").get("i", String.class)).isEqualTo("bla");77 assertThat(bindAccess(instance, "/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getDef(Double.class)).isEqualTo(1.0); 78 assertThat(bindAccess(instance, "/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getMax(Double.class)).isEqualTo(999.0); 79 assertThat(bindAccess(instance, "/parts/2")).isInstanceOf(ReflectionAccess.class); 80 assertThat(Path.to(instance, "/neurodefs").getTopObject()).isInstanceOf(ArrayList.class); 81 assertThat(Path.to(instance, "/joints/1").getTopObject()).isInstanceOf(Joint.class); 82 assertThat(bindAccess(instance, "/parts/2").get("i", String.class)).isEqualTo("bla"); 80 83 } 81 84 }); -
java/main/src/test/java/com/framsticks/gui/BrowserBaseTest.java
r90 r96 9 9 import org.fest.swing.fixture.FrameFixture; 10 10 import org.fest.swing.fixture.JTreeFixture; 11 import org.testng.annotations.AfterClass;12 import org.testng.annotations.BeforeClass;13 11 import org.testng.annotations.Test; 14 12 15 import com.framsticks.test. TestConfiguration;16 import com.framsticks.util.dispatching. Monitor;13 import com.framsticks.test.MonitorBasedTest; 14 import com.framsticks.util.dispatching.Joinable; 17 15 18 16 import static org.fest.assertions.Assertions.assertThat; … … 22 20 23 21 @Test 24 public abstract class BrowserBaseTest extends TestConfiguration{22 public abstract class BrowserBaseTest extends MonitorBasedTest { 25 23 26 24 private static final Logger log = Logger.getLogger(BrowserTest.class); 27 25 28 protected Monitor monitor;29 26 protected Browser browser; 30 27 protected static Robot robot; … … 39 36 } 40 37 41 @BeforeClass(timeOut = 5000) 42 public void setUp() { 38 @Override 39 protected Joinable createSubject() { 40 configureBrowser(); 41 return browser; 42 } 43 43 44 configureBrowser(); 45 46 monitor = new Monitor(browser); 47 48 monitor.use(); 49 44 protected void setUpAfterUse() { 50 45 frame = new FrameFixture(robot, 51 46 GuiActionRunner.execute(new GuiQuery<JFrame>() { … … 57 52 58 53 tree = frame.tree("tree"); 54 59 55 log.debug("frame fixture done"); 60 56 } 57 61 58 62 59 protected abstract void configureBrowser(); … … 71 68 } 72 69 73 @AfterClass(timeOut = 5000)74 public void tearDown() {75 monitor.drop().join();76 }77 78 70 } -
java/main/src/test/java/com/framsticks/gui/BrowserTest.java
r90 r96 10 10 11 11 import com.framsticks.model.ModelPackage; 12 import com.framsticks.remote. RemoteInstance;12 import com.framsticks.remote.SimulatorInstance; 13 13 14 14 public class BrowserTest extends BrowserBaseTest { … … 16 16 private static final Logger log = Logger.getLogger(BrowserTest.class); 17 17 18 RemoteInstance localhost;18 SimulatorInstance localhost; 19 19 20 20 @Override … … 22 22 browser = new Browser(); 23 23 24 localhost = new RemoteInstance();24 localhost = new SimulatorInstance(); 25 25 localhost.setName("localhost"); 26 26 localhost.setAddress("localhost:9009"); -
java/main/src/test/java/com/framsticks/gui/ObjectInstanceBrowserTest.java
r90 r96 11 11 import com.framsticks.parsers.XmlLoader; 12 12 import com.framsticks.util.dispatching.RunAt; 13 14 import static com.framsticks.core.InstanceUtils.*; 13 15 14 16 @Test … … 29 31 @Test(timeOut = 10000) 30 32 public void testShow() { 31 assertDispatch(instance,new RunAt<Instance>() {33 instance.dispatch(new RunAt<Instance>() { 32 34 @Override 33 35 public void run() { … … 40 42 clickAndExpandPath("model/parts/2"); 41 43 42 assertDispatch(instance,new RunAt<Instance>() {44 instance.dispatch(new RunAt<Instance>() { 43 45 @Override 44 46 public void run() { 45 assertThat( instance.bindAccess("/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getMax(Double.class)).isEqualTo(999.0);47 assertThat(bindAccess(instance, "/parts/2").getFramsClass().getParamEntry("m", FloatParam.class).getMax(Double.class)).isEqualTo(999.0); 46 48 } 47 49 }); -
java/main/src/test/java/com/framsticks/gui/ProcedureBrowserTest.java
r90 r96 16 16 import com.framsticks.test.TestClass; 17 17 import com.framsticks.util.dispatching.RunAt; 18 import static com.framsticks.core.InstanceUtils.*; 18 19 19 20 @Test … … 34 35 @Test(timeOut = 10000) 35 36 public void testShow() { 36 assertDispatch(instance,new RunAt<Instance>() {37 instance.dispatch(new RunAt<Instance>() { 37 38 @Override 38 39 public void run() { … … 43 44 clickAndExpandPath("test"); 44 45 45 assertDispatch(instance,new RunAt<Instance>() {46 instance.dispatch(new RunAt<Instance>() { 46 47 @Override 47 48 public void run() { 48 assertThat( instance.bindAccess("/").getFramsClass().getParam("history")).isInstanceOf(StringParam.class);49 assertThat(bindAccess(instance, "/").getFramsClass().getParam("history")).isInstanceOf(StringParam.class); 49 50 } 50 51 }); … … 52 53 // monitor.useFor(4.0); 53 54 54 assertDispatch(instance,new RunAt<Instance>() {55 instance.dispatch(new RunAt<Instance>() { 55 56 @Override 56 57 public void run() { 57 AccessInterface access = instance.bindAccess("/");58 AccessInterface access = bindAccess(instance, "/"); 58 59 assertThat(access).isInstanceOf(ReflectionAccess.class); 59 60 FramsClass framsClass = access.getFramsClass(); … … 74 75 waitForIdle(); 75 76 76 assertDispatch(instance,new RunAt<Instance>() {77 instance.dispatch(new RunAt<Instance>() { 77 78 @Override 78 79 public void run() { 79 assertThat( instance.bindAccess("/").get("history", String.class)).isEqualTo("argument|");80 assertThat(bindAccess(instance, "/").get("history", String.class)).isEqualTo("argument|"); 80 81 } 81 82 }); … … 84 85 waitForIdle(); 85 86 86 assertDispatch(instance,new RunAt<Instance>() {87 instance.dispatch(new RunAt<Instance>() { 87 88 @Override 88 89 public void run() { 89 assertThat( instance.bindAccess("/").get("history", String.class)).isEqualTo("");90 assertThat(bindAccess(instance, "/").get("history", String.class)).isEqualTo(""); 90 91 } 91 92 }); -
java/main/src/test/java/com/framsticks/params/FramsClassBuilderTest.java
r90 r96 1 1 package com.framsticks.params; 2 2 3 import java.util.Arrays; 3 4 4 5 import org.testng.annotations.BeforeClass; … … 7 8 import com.framsticks.params.types.ProcedureParam; 8 9 import com.framsticks.params.types.StringParam; 10 import com.framsticks.parsers.Savers; 9 11 import com.framsticks.test.TestClass; 10 12 import com.framsticks.test.TestConfiguration; … … 17 19 ReflectionAccess access; 18 20 TestClass test; 19 20 21 21 22 @BeforeClass … … 36 37 assertThat(framsClass.getParam("appendHistory")).isInstanceOf(ProcedureParam.class); 37 38 assertThat(framsClass.getParam("resetHistory")).isInstanceOf(ProcedureParam.class); 39 38 40 ProcedureParam appendHistory = framsClass.getParamEntry("appendHistory", ProcedureParam.class); 39 41 assertThat(appendHistory.getArgumentsType().size()).isEqualTo(1); … … 42 44 43 45 @Test(dependsOnMethods = "checkProcedureParams") 46 public void print() { 47 assertThat(Savers.saveFramsClass(new ListSink(), framsClass).getOut()).isEqualTo( 48 Arrays.asList( 49 "class:", 50 "name:TestClass", 51 "id:TestClass", 52 "", 53 "prop:", 54 "id:name", 55 "name:Name", 56 "type:s", 57 "", 58 "prop:", 59 "id:history", 60 "name:History", 61 "type:s", 62 "", 63 "prop:", 64 "id:appendHistory", 65 "name:AppendHistory", 66 "type:p d(s arg0)", 67 "", 68 "prop:", 69 "id:resetHistory", 70 "name:ResetHistory", 71 "type:p()", 72 "" 73 ) 74 ); 75 } 76 77 78 @Test(dependsOnMethods = "print") 44 79 public void callProcedures() { 45 80 access = new ReflectionAccess(TestClass.class, framsClass); -
java/main/src/test/java/com/framsticks/params/ParamBuilderTest.java
r88 r96 23 23 assertThat(builderFramsClass.getName()).isEqualTo("prop"); 24 24 assertThat(builderFramsClass.getId()).isEqualTo("prop"); 25 assertThat(builderFramsClass.getParamEntry("flags", ValueParam.class).getDef(Object.class)).isEqualTo(new Integer(0)); 25 26 assertThat(builderFramsClass.getParamEntry("id", Param.class)).isInstanceOf(StringParam.class); 26 27 } -
java/main/src/test/java/com/framsticks/running/FramsServerTest.java
r90 r96 3 3 import org.testng.annotations.Test; 4 4 5 import com.framsticks.core.Framsticks; 6 import com.framsticks.test.TestConfiguration; 7 import com.framsticks.util.dispatching.Monitor; 5 import com.framsticks.core.XmlBasedTest; 8 6 9 7 import static org.fest.assertions.Assertions.*; 10 8 11 9 @Test 12 public class FramsServerTest extends TestConfiguration { 10 public class FramsServerTest extends XmlBasedTest { 11 12 @Override 13 protected String getConfigurationName() { 14 return "FramsServerTest.xml"; 15 } 13 16 14 17 @Test(timeOut = 3000) 15 18 public void runServer() { 16 Framsticks framsticks = Framsticks.loadConfiguration(FramsServerTest.class.getResourceAsStream("/configs/FramsServerTest.xml")); 19 assertThat(framsticks.size()).isEqualTo(1); 20 assertThat(framsticks.get("frams")).isInstanceOf(FramsServer.class); 17 21 18 assertThat(framsticks.getObservables().size()).isEqualTo(1); 19 assertThat(framsticks.getObservables().get("frams")).isInstanceOf(FramsServer.class); 20 // assertThat(framsticks.getObservables().get("remote")).isInstanceOf(RemoteInstance.class); 21 22 new Monitor(framsticks).use().useFor(1.0).drop().join(); 23 24 // monitor.use(); 25 26 // Dispatching.sleep(1000); 27 28 // // monitor.waitFor(); 29 // monitor.drop(); 30 // monitor.join(); 31 32 // framsticks.start(); 33 34 // framsticks.waitForObservables(); 35 22 monitor.useFor(1.0); 36 23 } 37 24 25 38 26 } -
java/main/src/test/java/com/framsticks/test/TestConfiguration.java
r90 r96 1 1 package com.framsticks.test; 2 2 3 import java.util.HashSet; 3 4 import java.util.LinkedList; 4 5 import java.util.List; 6 import java.util.Set; 5 7 6 8 import org.apache.log4j.Logger; … … 8 10 import org.testng.annotations.*; 9 11 12 import com.framsticks.util.FramsticksException; 10 13 import com.framsticks.util.dispatching.Dispatcher; 11 import com.framsticks.util.dispatching.RunAt; 14 import com.framsticks.util.dispatching.Dispatching; 15 import com.framsticks.util.dispatching.Dispatching.Waiter; 16 import com.framsticks.util.dispatching.ExceptionHandler; 17 import com.framsticks.util.dispatching.ExceptionResultHandler; 18 19 import static org.fest.assertions.Assertions.*; 12 20 13 21 public class TestConfiguration { … … 21 29 } 22 30 23 private final List<As yncAssert<?>> asyncAssertions = new LinkedList<AsyncAssert<?>>();31 private final List<AssertionError> asyncAssertions = new LinkedList<>(); 24 32 25 public class AsyncAssert<C> extends RunAt<C> { 26 final RunAt<? extends C> runnable; 27 boolean done = false; 28 AssertionError assertion; 33 public ExceptionHandler createExceptionHandler() { 34 return new ExceptionHandler() { 35 @Override 36 public boolean handle(Dispatcher<?> dispatcher, Throwable throwable) { 37 AssertionError ae; 38 if (AssertionError.class.isInstance(throwable)) { 39 ae = AssertionError.class.cast(throwable); 40 } else { 41 ae = new AssertionError(); 42 ae.initCause(throwable); 43 } 44 synchronized (asyncAssertions) { 45 asyncAssertions.add(ae); 46 } 47 return true; 48 } 49 }; 50 } 29 51 30 /** 31 * @param runnable 32 */ 33 public AsyncAssert(RunAt<? extends C> runnable) { 34 this.runnable = runnable; 35 } 36 37 @Override 38 public void run() { 52 @AfterMethod 53 public void waitForWaiters() { 54 for (Waiter w : waiters) { 39 55 try { 40 runnable.run(); 41 } catch (AssertionError e) { 42 assertion = e; 43 } 44 synchronized (this) { 45 done = true; 46 this.notifyAll(); 56 w.waitFor(); 57 } catch (FramsticksException e) { 58 AssertionError ae = new AssertionError(); 59 ae.initCause(e); 60 asyncAssertions.add(ae); 47 61 } 48 62 } 49 63 } 50 64 51 public <C> void assertDispatch(Dispatcher<C> dispatcher, RunAt<? extends C> runnable) {52 AsyncAssert<C> assertion = new AsyncAssert<C>(runnable);65 @AfterMethod(timeOut = 1000, dependsOnMethods = "waitForWaiters") 66 public void processAsyncAssertions() { 53 67 synchronized (asyncAssertions) { 54 asyncAssertions.add(assertion); 55 } 56 dispatcher.dispatch(assertion); 57 } 58 59 @BeforeMethod 60 public void clearAsyncAsserts() { 61 synchronized (asyncAssertions) { 62 asyncAssertions.clear(); 68 if (asyncAssertions.isEmpty()) { 69 return; 70 } 71 AssertionError a = asyncAssertions.get(0); 72 asyncAssertions.remove(0); 73 throw a; 63 74 } 64 75 } 65 76 66 @AfterMethod(timeOut = 5000) 67 public void waitForAsyncAsserts() { 68 while (true) { 69 AsyncAssert<?> assertion; 70 synchronized (asyncAssertions) { 71 if (asyncAssertions.isEmpty()) { 72 return; 73 } 74 assertion = asyncAssertions.get(0); 75 asyncAssertions.remove(0); 77 final Set<Waiter> waiters = new HashSet<>(); 78 79 @BeforeMethod 80 public void clearWaiters() { 81 waiters.clear(); 82 } 83 84 protected Dispatching.Waiter produceWaiter(double timeOut) { 85 Waiter waiter = new Waiter(timeOut); 86 waiters.add(waiter); 87 return waiter; 88 } 89 90 public static ExceptionResultHandler failOnException() { 91 return new ExceptionResultHandler() { 92 @Override 93 public void handle(FramsticksException e) { 94 assertThat(e).isNull(); 76 95 } 77 synchronized (assertion) { 78 while (!assertion.done) { 79 try { 80 assertion.wait(); 81 } catch (InterruptedException ignored) { 82 } 83 } 84 if (assertion.assertion != null) { 85 throw assertion.assertion; 86 } 87 } 88 } 96 }; 97 89 98 } 90 99 } -
java/main/src/test/resources/configs/test.xml
r88 r96 2 2 <Framsticks> 3 3 <import class="com.framsticks.gui.Browser" /> 4 <import class="com.framsticks.remote. RemoteInstance" />4 <import class="com.framsticks.remote.SimulatorInstance" /> 5 5 <Browser name="browser"> 6 < RemoteInstance name="localhost:9009" address="localhost:9009" />6 <SimulatorInstance name="localhost:9009" address="localhost:9009" /> 7 7 </Browser> 8 8 </Framsticks> -
java/main/src/test/resources/log4j.properties
r90 r96 27 27 28 28 log4j.logger.com.framsticks=INFO 29 # log4j.logger.com.framsticks.hosting.Server=DEBUG 30 # log4j.logger.com.framsticks.communication.ServerConnection=TRACE 31 # log4j.logger.com.framsticks.util.dispatching.AbstractJoinable=DEBUG 29 32 # log4j.logger.com.framsticks.parsers.F0Writer=TRACE 30 33 # log4j.logger.com.framsticks.core.ObjectInstance=DEBUG
Note: See TracChangeset
for help on using the changeset viewer.