Добавлен режим Sandbox для онлайн интерпретатора

This commit is contained in:
Victor 2016-11-25 12:16:01 +02:00
parent 92a2159e68
commit b8a2242272
5 changed files with 83 additions and 5 deletions

View File

@ -1,13 +1,16 @@
package com.annimon.ownlang;
import com.annimon.ownlang.lib.CallStack;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.PrintStream;
import java.io.UnsupportedEncodingException;
public class Console {
private static final String FILE_PREFIX = "tmp/";
public static boolean filePrefixEnabled = false;
public static String newline() {
return System.lineSeparator();
}
@ -39,7 +42,7 @@ public class Console {
public static void error(CharSequence value) {
System.err.println(value);
}
public static void handleException(Thread thread, Throwable throwable) {
final ByteArrayOutputStream baos = new ByteArrayOutputStream();
try(final PrintStream ps = new PrintStream(baos)) {
@ -57,4 +60,14 @@ public class Console {
error(baos.toString());
}
}
public static File fileInstance(String path) {
final String filepath;
if (filePrefixEnabled) {
filepath = FILE_PREFIX.concat(path);
} else {
filepath = path;
}
return new File(filepath);
}
}

View File

@ -11,6 +11,7 @@ import com.annimon.ownlang.parser.Token;
import com.annimon.ownlang.parser.ast.Statement;
import com.annimon.ownlang.parser.visitors.FunctionAdder;
import com.annimon.ownlang.utils.Repl;
import com.annimon.ownlang.utils.Sandbox;
import com.annimon.ownlang.utils.TimeMeasurement;
import java.io.IOException;
import java.util.List;
@ -112,6 +113,13 @@ public final class Main {
i++;
}
break;
case "--sandbox":
createOwnLangArgs(args, i + 1);
String[] newArgs = new String[ownlangArgs.length];
System.arraycopy(ownlangArgs, 0, newArgs, 0, ownlangArgs.length);
Sandbox.main(newArgs);
return;
default:
if (input == null) {

View File

@ -1,5 +1,6 @@
package com.annimon.ownlang.modules.files;
import com.annimon.ownlang.Console;
import com.annimon.ownlang.exceptions.ArgumentsMismatchException;
import com.annimon.ownlang.lib.*;
import com.annimon.ownlang.modules.Module;
@ -120,7 +121,7 @@ public final class files implements Module {
public Value execute(Value... args) {
Arguments.checkAtLeast(1, args.length);
final File file = new File(args[0].asString());
final File file = Console.fileInstance(args[0].asString());
try {
if (args.length > 1) {
return process(file, args[1].asString().toLowerCase());
@ -555,7 +556,7 @@ public final class files implements Module {
if (value.type() == Types.NUMBER) {
return files.get(value.asInt()).file;
}
return new File(value.asString());
return Console.fileInstance(value.asString());
}
private interface FileToBooleanFunction {

View File

@ -15,7 +15,7 @@ public final class SourceLoader {
return readAndCloseStream(is);
}
private static String readAndCloseStream(InputStream is) throws IOException {
public static String readAndCloseStream(InputStream is) throws IOException {
final ByteArrayOutputStream result = new ByteArrayOutputStream();
final int bufferSize = 1024;
final byte[] buffer = new byte[bufferSize];

View File

@ -0,0 +1,56 @@
package com.annimon.ownlang.utils;
import com.annimon.ownlang.Console;
import com.annimon.ownlang.exceptions.StoppedException;
import com.annimon.ownlang.lib.CallStack;
import com.annimon.ownlang.parser.Lexer;
import com.annimon.ownlang.parser.Parser;
import com.annimon.ownlang.parser.SourceLoader;
import com.annimon.ownlang.parser.Token;
import com.annimon.ownlang.parser.ast.Statement;
import com.annimon.ownlang.parser.visitors.FunctionAdder;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
public final class Sandbox {
public static void main(String[] args) throws IOException {
Console.filePrefixEnabled = true;
final String input = SourceLoader.readAndCloseStream(System.in);
dumpInputArguments(input, args);
final List<Token> tokens = Lexer.tokenize(input);
final Parser parser = new Parser(tokens);
final Statement program = parser.parse();
if (parser.getParseErrors().hasErrors()) {
System.out.print(parser.getParseErrors());
return;
}
program.accept(new FunctionAdder());
try {
program.execute();
} catch (StoppedException ex) {
// skip
} catch (Exception ex) {
// ownlang call stack to stdout
System.out.format("%s in %s%n", ex.getMessage(), Thread.currentThread().getName());
CallStack.getCalls().forEach(call -> System.out.format("\tat %s%n", call));
// java stack trace to stderr
Console.handleException(Thread.currentThread(), ex);
}
}
private static void dumpInputArguments(String source, String[] args) {
System.err.println();
System.err.println();
System.err.println(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
Arrays.stream(args).forEach(System.err::println);
System.err.println();
System.err.println(source);
}
}