/* VerySimpleTemplatesのパーザー */ import java.io.*; /* ハンドラのインターフェース */ interface VSTHandler { public void startTemplate(); public void endTemplate(); public void placeholder(String content); public void text(String text); public void error(String message); } /* デバッグ目的のデフォルト・ハンドラ */ class PrintHandler implements VSTHandler { public void startTemplate() { System.out.println("startTemplate"); } public void endTemplate() { System.out.println("endTemplate"); } public void placeholder(String content) { System.out.println("placeholder:" + content); } public void text(String text) { System.out.println("text:" + "'" + text + "'"); } public void error(String message) { System.out.println("error:" + message); } } /* パージング時の例外 */ class VSTParseException extends Exception { public VSTParseException(String msg) { super(msg); } } /* パーザー */ class VSTParser { private VSTHandler handler; public VSTParser() { handler = new PrintHandler(); } public void setHandler(VSTHandler handler) { this.handler = handler; } private void signalError(String msg) throws VSTParseException { handler.error(msg); throw new VSTParseException(msg); } public void parse(Reader input) throws IOException, VSTParseException { VSTLexer lexer = new VSTLexer(input); boolean withinPlaceholder = false; // 状態 StringBuilder placeholderContent = new StringBuilder(); // テキスト蓄積用 handler.startTemplate(); while (true) { VSTToken tok = lexer.nextToken(); switch (tok.kind) { case L_BRACE: if (withinPlaceholder) signalError("unexpected left-brace - nested placeholder."); withinPlaceholder = true; break; case R_BRACE: if (!withinPlaceholder) { handler.text("}"); // 単なるテキスト扱い } else { // withinPlaceholder if (placeholderContent.length() == 0) signalError("empty placeholder content."); handler.placeholder(placeholderContent.toString()); withinPlaceholder = false; // プレイスホルダー内容をクリア placeholderContent.delete(0, placeholderContent.length()); } break; case TEXT: if (withinPlaceholder) { placeholderContent.append(tok.value); // 蓄積 } else { handler.text(tok.value); } break; case EOF: if (withinPlaceholder) signalError("unexpected end-of-file - placeholder is not closed."); handler.endTemplate(); return; // 脱出・終了 default: assert false; // アリエナーイ } } } /* テスト用のmain */ public static void main(String[] args) { Reader input = null; if (args.length == 0) { input = new InputStreamReader(System.in); } else { try { input = new FileReader(args[0]); } catch (Exception e) { System.err.println(e); System.exit(1); } } VSTParser parser = new VSTParser(); try { parser.parse(input); } catch (Exception e) { System.out.println(e); System.exit(1); } System.exit(0); } }