You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openjpa.apache.org by pp...@apache.org on 2010/05/25 06:28:31 UTC
svn commit: r947912 [1/5] - in
/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools: ./
ant/ converter/ parser/ util/
Author: ppoddar
Date: Tue May 25 04:28:30 2010
New Revision: 947912
URL: http://svn.apache.org/viewvc?rev=947912&view=rev
Log:
Add a Java2HTML conversion facility that we can tweak
Added:
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/parser/
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/parser/JavaLexer.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/parser/JavaParser.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/util/
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/util/TextProcessingUtility.java (with props)
openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/util/URIUtils.java (with props)
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java Tue May 25 04:28:30 2010
@@ -0,0 +1,357 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Processes options.
+ * <br>
+ * User can register a set of command options. Then this processor will parse a set of Strings to
+ * store the values for each of the registered options as well as optionally any unrecognized
+ * option values.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class CommandProcessor {
+ private final Map<Option, String> registeredOptions = new HashMap<Option,String>();
+ private final Set<Option> unregisteredOptions = new HashSet<Option>();
+ private boolean allowsUnregisteredOption = true;
+
+ /**
+ * Set the option values from the given arguments.
+ * All elements of the given array is <em>not</em> consumed,
+ * only till the index that appears to be a valid option.
+ *
+ * @see #lastIndex(String[])
+ *
+ * @param args an array of arguments.
+ *
+ * @return the array elements that are not consumed.
+ */
+ public String[] setFrom(String[] args) {
+ return setFrom(args, 0, args != null ? lastIndex(args) : 0);
+ }
+
+ /**
+ * Set the option values from the given arguments between the given indices.
+ *
+ * @see #lastIndex(String[])
+ *
+ * @param args an array of arguments.
+ *
+ * @return the array elements that are not consumed.
+ */
+ public String[] setFrom(String[] args, int from, int to) {
+ if (args == null)
+ return null;
+ if (args.length == 0)
+ return new String[0];
+ assertValidIndex(from, args, "Initial index " + from + " is an invalid index to " + Arrays.toString(args));
+ assertValidIndex(to, args, "Last index " + to + " is an invalid index to " + Arrays.toString(args));
+
+ int i = from;
+ for (; i < to; i++) {
+ String c = args[i];
+ Option command = findCommand(c);
+ if (command == null) {
+ throw new IllegalArgumentException(c + " is not a recongined option");
+ }
+ if (command.requiresInput()) {
+ i++;
+ }
+ if (i > to) {
+ throw new IllegalArgumentException("Command " + c + " requires a value, but no value is specified");
+ }
+ registeredOptions.put(command, args[i]);
+ }
+ String[] remaining = new String[args.length-to];
+ System.arraycopy(args, i, remaining, 0, remaining.length);
+ return remaining;
+ }
+
+ /**
+ * Gets the last index in the given array that can be processed as an option.
+ * The array elements are sequentially tested if they are a valid option name
+ * (i.e. starts with - character) and if valid then the next element is consumed
+ * as value, if the option requires a value. The search ends when either
+ * the array is exhausted or encounters elements that are not options.
+ *
+ * @param args an array of arguments
+ * @return the last index that will/can be consumed by this processor.
+ */
+ public int lastIndex(String[] args) {
+ int i = 0;
+ for (; i < args.length; i++) {
+ if (Option.isValidName(args[i])) {
+ Option cmd = findCommand(args[i]);
+ if (cmd != null) {
+ if (cmd.requiresInput()) {
+ i++;
+ }
+ continue;
+ }
+ }
+ break;
+ }
+ return i;
+ }
+
+ /**
+ * Register the given aliases as a command option.
+ *
+ * @param requiresValue if true then the option must be specified with a value.
+ * @param aliases strings to recognize this option. Each must begin with a dash character.
+ *
+ * @return the command that is registered
+ */
+ public Option register(boolean requiresValue, String...aliases) {
+ Option option = new Option(requiresValue, aliases);
+ registeredOptions.put(option, null);
+ return option;
+ }
+
+ /**
+ * Finds a command with the given name.
+ * If no command has been registered with the given name, but this processor
+ * allows unrecognized options, then as a result of this call, the
+ * unknown name is registered as an option.
+ *
+ * @param option a command alias.
+ *
+ * @return null if the given String is not a valid command option name.
+ *
+ */
+ public Option findCommand(String option) {
+ if (!Option.isValidName(option))
+ return null;
+ for (Option registeredOption : registeredOptions.keySet()) {
+ if (registeredOption.match(option))
+ return registeredOption;
+ }
+ for (Option unregisteredOption : unregisteredOptions) {
+ if (unregisteredOption.match(option))
+ return unregisteredOption;
+ }
+ if (allowsUnregisteredOption) {
+ Option cmd = new Option(option);
+ unregisteredOptions.add(cmd);
+ return cmd;
+ } else {
+ return null;
+ }
+ }
+
+ /**
+ * Gets all the unrecognized command options.
+ *
+ * @return empty set if no commands are unrecognized.
+ */
+ public Set<Option> getUnregisteredCommands() {
+ return Collections.unmodifiableSet(unregisteredOptions);
+ }
+
+ <T> void assertValidIndex(int i, T[] a, String message) {
+ if (i <0 || (a != null && i >= a.length))
+ throw new ArrayIndexOutOfBoundsException(message);
+ }
+
+ /**
+ * Gets value of the option matching the given alias.
+ *
+ * @param alias an alias.
+ *
+ * @return value of the given option.
+ */
+ public String getValue(String alias) {
+ Option cmd = findCommand(alias);
+ return getValue(cmd);
+ }
+
+ /**
+ * Gets value of the given option.
+ *
+ * @param opt an option.
+ *
+ * @return value of the given option.
+ */
+ String getValue(Option opt) {
+ String val = registeredOptions.get(opt);
+ if (val == null)
+ val = opt.getDefaultValue();
+ return val;
+ }
+
+ /**
+ * @return the allowsUnregisteredOption
+ */
+ public boolean getAllowsUnregisteredOption() {
+ return allowsUnregisteredOption;
+ }
+
+ /**
+ * @param allowsUnregisteredOption the allowsUnregisteredOption to set
+ */
+ public void setAllowsUnregisteredOption(boolean allowsUnregisteredOption) {
+ this.allowsUnregisteredOption = allowsUnregisteredOption;
+ }
+
+ /**
+ * A simple immutable object represents meta-data about a command option.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+ public static class Option {
+ private static final String DASH = "-";
+
+ /**
+ * Affirms if the given string can be a valid option name.
+ * An option name always starts with dash and must be followed by at least one character.
+ */
+ public static boolean isValidName(String s) {
+ return s != null && s.startsWith(DASH) && s.length() > 1;
+ }
+
+ /**
+ * Possible names of this command option.
+ * All aliases must start with a dash (<code>-</code>).
+ */
+ private String[] aliases;
+
+ /**
+ * Does the option require a value?
+ */
+ private boolean requiresInput;
+
+ /**
+ * A default value for this option.
+ */
+ private String defValue;
+
+ /**
+ * A description String.
+ */
+ private String _description = "";
+
+ /**
+ * Create a command with given aliases. This option requires a value.
+ *
+ * @param aliases strings each must start with a dash (<code>-</code>).
+ */
+ public Option(String... aliases) {
+ this(true, aliases);
+ }
+
+ /**
+ * Create a option with given aliases.
+ *
+ * @param requiresInput does it require a value?
+ * @param aliases strings each must start with a dash (<code>-</code>).
+ */
+ public Option(boolean requiresInput, String...aliases) {
+ super();
+ if (aliases == null || aliases.length == 0)
+ throw new IllegalArgumentException("Can not create command with null or empty aliases");
+ for (String alias : aliases) {
+ if (!isValidName(alias)) {
+ throw new IllegalArgumentException("Invalid alias [" + alias + "]. " +
+ "Aliases must start with - followded by at least one character");
+ }
+ }
+ this.aliases = aliases;
+ this.requiresInput = requiresInput;
+ }
+
+ /**
+ * Gets the first alias as the name.
+ */
+ public String getName() {
+ return aliases[0];
+ }
+
+ /**
+ * Sets the default value for this option.
+ *
+ * @param v a default value.
+ *
+ * @return this command itself.
+ *
+ * @exception IllegalStateException if this option does not require a value.
+ */
+ public Option setDefault(String v) {
+ if (!requiresInput)
+ throw new IllegalStateException(this + " does not require a value. Can not set default value [" + v + "]");
+ defValue = v;
+ return this;
+ }
+
+ public Option setDescription(String desc) {
+ if (desc != null) {
+ _description = desc;
+ }
+ return this;
+ }
+
+ public String getDescription() {
+ return _description;
+ }
+
+ /**
+ * Affirms if the given name any of the aliases.
+ * @param alias
+ * @return
+ */
+ public boolean match(String name) {
+ for (String alias : aliases) {
+ if (name.equals(alias))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Affirms if this option requires a value.
+ */
+ public boolean requiresInput() {
+ return requiresInput;
+ }
+
+ /**
+ * Gets the default value of this option.
+ *
+ * @return the default value. null if no default value has been set.
+ */
+ public String getDefaultValue() {
+ return defValue;
+ }
+
+ public String toString() {
+ return getName();
+ }
+ }
+
+
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/CommandProcessor.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java Tue May 25 04:28:30 2010
@@ -0,0 +1,239 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.ant;
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.List;
+
+import openbook.tools.converter.Java2HTMLConverter;
+
+import org.apache.tools.ant.BuildException;
+import org.apache.tools.ant.DirectoryScanner;
+import org.apache.tools.ant.taskdefs.MatchingTask;
+
+/**
+ * An ant task to run {@linkplain Java2HTMLConverter Java2HTML Converter}.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class Java2HTMLConverterTask extends MatchingTask {
+ private String sourcepath = ".";
+ private String destDir = ".";
+ private String extension = "";
+ private String stylesheet = "java.css";
+ private boolean showLineNumber = true;
+ private boolean anchorLineNumber = false;
+ private boolean addLineBreak = true;
+ private boolean addExplicitSpace = true;
+ private String lineNumberFormat = "%%0%4d";
+ private boolean verbose = false;
+
+ private List<Arg> _args = new ArrayList<Arg>();
+
+ public String getSourcepath() {
+ return sourcepath;
+ }
+
+ public void setSourcepath(String sourcepath) {
+ this.sourcepath = sourcepath;
+ }
+
+ @Override
+ public void execute() throws BuildException {
+ List<String> files = getFiles();
+ List<String> args = new ArrayList<String>();
+ args.add("-sourcepath"); args.add(sourcepath);
+ args.add("-d"); args.add(destDir);
+ args.add("-extension"); args.add(extension);
+ args.add("-verbose"); args.add(""+verbose);
+ args.add("-stylesheet"); args.add(stylesheet);
+ args.add("-showLineNumber"); args.add(""+showLineNumber);
+ args.add("-anchorLineNumber"); args.add(""+anchorLineNumber);
+ args.add("-addLineBreak"); args.add(""+addLineBreak);
+ args.add("-addExplicitSpace"); args.add(""+addExplicitSpace);
+ args.add("-lineNumberFormat"); args.add(lineNumberFormat);
+ args.add("-anchorLineNumber"); args.add(""+anchorLineNumber);
+
+ for (Arg a : _args) {
+ args.add(a.getName());
+ args.add(a.getValue());
+ }
+ for (String file : files) {
+ args.add(file.replace(File.separatorChar, '/'));
+ }
+ try {
+ Java2HTMLConverter.main(args.toArray(new String[args.size()]));
+ } catch (Exception e) {
+ throw new BuildException(e);
+ }
+ }
+
+ List<String> getFiles() {
+ List<String> list = new ArrayList<String>();
+ DirectoryScanner scanner = getDirectoryScanner(new File(getSourcepath()));
+ String[] files = scanner.getIncludedFiles();
+ for (String file : files) {
+ if (file.endsWith(".java")) {
+ list.add(file);
+ }
+ }
+ return list;
+ }
+
+ public Arg createArg() {
+ Arg arg = new Arg();
+ _args.add(arg);
+ return arg;
+ }
+
+
+ public String getDestDir() {
+ return destDir;
+ }
+
+ public void setDestDir(String destDir) {
+ this.destDir = destDir;
+ }
+
+ public boolean isVerbose() {
+ return verbose;
+ }
+
+ public void setVerbose(boolean verbose) {
+ this.verbose = verbose;
+ }
+
+ /**
+ * @return the extension
+ */
+ public String getExtension() {
+ return extension;
+ }
+
+ /**
+ * @param extension the extension to set
+ */
+ public void setExtension(String extension) {
+ this.extension = extension;
+ }
+
+ /**
+ * @return the stylesheet
+ */
+ public String getStylesheet() {
+ return stylesheet;
+ }
+
+ /**
+ * @param stylesheet the stylesheet to set
+ */
+ public void setStylesheet(String stylesheet) {
+ this.stylesheet = stylesheet;
+ }
+
+ /**
+ * @return the showLineNumber
+ */
+ public boolean isShowLineNumber() {
+ return showLineNumber;
+ }
+
+ /**
+ * @param showLineNumber the showLineNumber to set
+ */
+ public void setShowLineNumber(boolean showLineNumber) {
+ this.showLineNumber = showLineNumber;
+ }
+
+ /**
+ * @return the anchorLineNumber
+ */
+ public boolean isAnchorLineNumber() {
+ return anchorLineNumber;
+ }
+
+ /**
+ * @param anchorLineNumber the anchorLineNumber to set
+ */
+ public void setAnchorLineNumber(boolean anchorLineNumber) {
+ this.anchorLineNumber = anchorLineNumber;
+ }
+
+ /**
+ * @return the addLineBreak
+ */
+ public boolean isAddLineBreak() {
+ return addLineBreak;
+ }
+
+ /**
+ * @param addLineBreak the addLineBreak to set
+ */
+ public void setAddLineBreak(boolean addLineBreak) {
+ this.addLineBreak = addLineBreak;
+ }
+
+ /**
+ * @return the addExplicitSpace
+ */
+ public boolean isAddExplicitSpace() {
+ return addExplicitSpace;
+ }
+
+ /**
+ * @param addExplicitSpace the addExplicitSpace to set
+ */
+ public void setAddExplicitSpace(boolean addExplicitSpace) {
+ this.addExplicitSpace = addExplicitSpace;
+ }
+
+ /**
+ * @return the lineNumberFormat
+ */
+ public String getLineNumberFormat() {
+ return lineNumberFormat;
+ }
+
+ /**
+ * @param lineNumberFormat the lineNumberFormat to set
+ */
+ public void setLineNumberFormat(String lineNumberFormat) {
+ this.lineNumberFormat = lineNumberFormat;
+ }
+
+ public static class Arg {
+ String name;
+ String value;
+
+ public String getName() {
+ return name;
+ }
+ public void setName(String name) {
+ this.name = name;
+ }
+ public String getValue() {
+ return value;
+ }
+ public void setValue(String value) {
+ this.value = value;
+ }
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/ant/Java2HTMLConverterTask.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java Tue May 25 04:28:30 2010
@@ -0,0 +1,308 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import java.util.HashSet;
+import java.util.Set;
+
+import openbook.tools.parser.JavaParser;
+import openbook.tools.util.TextProcessingUtility;
+
+import org.antlr.runtime.Token;
+
+/**
+ * Renders Java source tokens as HTML tags.
+ * This renderer renders the parsed Java tokens with HTML styles.
+ * The styles of the tokens are determined by their types such as Java keywords, identifiers,
+ * comments etc. Moreover, an identifier can be a <em>custom</em> type if it matched a given
+ * list of identifiers. The actual HTML text is enclosed in <span id="style">token<\span>
+ * to apply the style. The styles are defined in a Cascaded Style Sheet (CSS).
+ * The cascaded style sheet by default is named <code>java.css</code>.
+ * <br>
+ * The rendering takes care of line breaks and white space in the following way to work
+ * around some limitations of Swing based HTML editor kit's usage of CSS attributes.
+ * <LI> Line Breaks: Swing Editor seems to require an explicit carriage return-line feed
+ * character to render in separate line. While a normal browser works with <br>
+ * tag alone.
+ * <LI> White space: The CSS property <code>white-space</code> is sufficient for browsers
+ * to preserve white space within <span> tags. But Swing Editor seems to require
+ * explicit <code>nbsp;</code> for white spaces within <span> tags.
+ * <br>
+ * Two boolean properties are provided to control these two properties.
+ * <br>
+ * <LI>Line Numbering: A boolean property controls whether line numbers will be printed.
+ * Line numbers are printed in 4 digits with leading zeros, by default.
+ * <LI>Line Number Anchoring: An anchor can be specified at every line. The anchor
+ * is <code>line.nnn</code> where <code>nnn</code> is the actual line number without
+ * any leading zero.
+ * <LI> JavaDoc comment : The JavaDoc comments can use characters that if reproduced
+ * exactly in HTML output can confuse the rendering process. On the other hand, the
+ * JavaDoc tags that define an anchor in the source code or creates a hyperlink should
+ * be preserved in the HTML output. The capacity and limitation of processing HTML tages
+ * inside JavaDoc comments are described in {@linkplain TextProcessingUtility here}.
+ *
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class HTMLTokenRenderer implements TokenRenderer {
+ private String stylesheet = "java.css";
+ private boolean showLineNumber = true;
+ private boolean anchorLineNumber = false;
+ private boolean addLineBreak = true;
+ private boolean addExplicitSpace = true;
+ private String lineNumberFormat = "%%0%4d ";
+
+ /**
+ * The CSS named styles.
+ */
+ public static final String CSS_CUSTOM = "custom";
+ public static final String CSS_KEYWORD = "keyword";
+ public static final String CSS_ANNOTATION = "annotation";
+ public static final String CSS_ENUM = "enum";
+ public static final String CSS_COMMENT = "comment";
+ public static final String CSS_LITERAL = "literal";
+ public static final String CSS_DECIMAL = "decimal";
+ public static final String CSS_LINE_NO = "lineno";
+
+ private Set<String> customIdentifiers = new HashSet<String>();
+
+ public static final String NEW_LINE = "\r\n";
+ public static final String HTML_BR_TAG = "<br>";
+ public static final String HTML_SPACE = " ";
+
+ /**
+ * Gets a end-of-line string: a HTML <br> tag followed by carriage return and line feed.
+ */
+ public String endLine(int line) {
+ return addLineBreak ? HTML_BR_TAG : HTML_BR_TAG + NEW_LINE;
+ }
+
+ /**
+ * Gets a string for beginning of a new line.
+ */
+ public String newLine(int line) {
+ String result = "";
+ if (showLineNumber) {
+ result = span(CSS_LINE_NO, fillWhiteSpace(String.format(lineNumberFormat, line)));
+ }
+ if (anchorLineNumber) {
+ result = "<A name=" + quote("line."+line) + ">" + result + "</A>";
+ }
+ return result;
+ }
+
+ @Override
+ public String render(int decision, Token token) {
+ String text = token.getText();
+ String result = "";
+ int type = token.getType();
+ switch (type) {
+ case JavaParser.Identifier:
+ case 73: // annotation symbol @
+ if (customIdentifiers.contains(text)) {
+ result = span(CSS_CUSTOM, text);
+ } else if (decision == 66 || decision == 14) {
+ result = span(CSS_ANNOTATION, text);
+ } else if (decision == 28) {
+ result = span(CSS_ENUM, text);
+ } else {
+ result = text;
+ }
+ break;
+ case JavaParser.COMMENT:
+ case JavaParser.LINE_COMMENT :
+ result = span(CSS_COMMENT, TextProcessingUtility.replaceHTMLSpecialCharacters(text));
+ break;
+ case JavaParser.StringLiteral :
+ case JavaParser.CharacterLiteral:
+ result = span(CSS_LITERAL, text);
+ break;
+ case JavaParser.DecimalLiteral:
+ case JavaParser.HexDigit:
+ case JavaParser.HexLiteral:
+ result = span(CSS_DECIMAL, text);
+ break;
+ default:
+ if (isWhiteSpace(text)) {
+ result = fillWhiteSpace(text);
+ } else if (text.length() == 1) {
+ if (text.charAt(0) == '>') {
+ result = ">";
+ } else if (text.charAt(0) == '<') {
+ result = "<";
+ } else {
+ result = text;
+ }
+ } else {
+ result = span(CSS_KEYWORD, text);
+ }
+ }
+ return result;
+ }
+
+ String span(String id, String txt) {
+ return "<span id=" + quote(id) + ">" + txt + "</span>";
+ }
+
+ String quote(String s) {
+ return "\""+s+"\"";
+ }
+
+ boolean isWhiteSpace(String txt) {
+ for (int i = 0; i < txt.length(); i++) {
+ if (!Character.isWhitespace(txt.charAt(i)))
+ return false;
+ }
+ return true;
+ }
+
+ String fillWhiteSpace(String txt) {
+ StringBuilder space = new StringBuilder();
+ for (int i = 0; i < txt.length(); i++) {
+ char ch = txt.charAt(i);
+ if (ch != '\r' && ch != '\n')
+ space.append(addExplicitSpace ? HTML_SPACE : ch);
+ }
+ return space.toString();
+ }
+
+
+ /**
+ * Gets the opening <BODY> and <HTML> tags and the <link type="stylesheet"> clause.
+ */
+ public String getPrologue() {
+ return insertLines(
+ "<HTML>",
+ "<HEAD>",
+ "<link rel="+ quote("stylesheet")+ " type=" + quote("text/css") + " href=" + quote(stylesheet) + ">",
+ "</HEAD>",
+ "<BODY>");
+ }
+
+ /**
+ * Gets the closing <BODY> and <HTML> tags
+ */
+ public String getEpilogue() {
+ return insertLines(" ", "</BODY>", "</HTML>");
+ }
+
+ private String insertLines(String...lines) {
+ StringBuilder buf = new StringBuilder();
+ for (String line : lines) {
+ if (buf.length() != 0) buf.append(NEW_LINE);
+ buf.append(line);
+ }
+ return buf.toString();
+ }
+
+ // Bean Style setters for auto-configuration
+
+ /**
+ * Gets the stylesheet to be linked at HTML output.
+ */
+ public String getStylesheet() {
+ return stylesheet;
+ }
+
+ /**
+ * Sets the stylesheet to be linked at the HTML output.
+ */
+ public void setStylesheet(String stylesheet) {
+ this.stylesheet = stylesheet;
+ }
+
+ /**
+ * Affirms if a line number will be added in HTML output.
+ */
+ public boolean getShowLineNumber() {
+ return showLineNumber;
+ }
+
+ /**
+ * Sets if a line number will be added in HTML output.
+ */
+ public void setShowLineNumber(boolean showLineNumber) {
+ this.showLineNumber = showLineNumber;
+ }
+
+ /**
+ * Affirms if an anchor will be created on every line.
+ */
+ public boolean getAnchorLineNumber() {
+ return anchorLineNumber;
+ }
+
+ /**
+ * Sets if an anchor will be created on every line.
+ */
+ public void setAnchorLineNumber(boolean anchorLineNumber) {
+ this.anchorLineNumber = anchorLineNumber;
+ }
+
+ /**
+ * Affirms if explicit line break (carriage return and line feed) will be added
+ * at the HTML output.
+ *
+ * @see #endLine(int)
+ */
+ public boolean getAddLineBreak() {
+ return addLineBreak;
+ }
+
+ /**
+ * Sets if explicit line break (carriage return and line feed) will be added
+ * at the HTML output.
+ *
+ * @see #endLine(int)
+ */
+ public void setAddLineBreak(boolean addLineBreak) {
+ this.addLineBreak = addLineBreak;
+ }
+
+ /**
+ * Affirms if explicit <code> </code> will be added at the HTML output.
+ */
+ public boolean getAddExplicitSpace() {
+ return addExplicitSpace;
+ }
+
+ /**
+ * Sets if explicit <code> </code> will be added at the HTML output.
+ */
+ public void setAddExplicitSpace(boolean addSpace) {
+ this.addExplicitSpace = addSpace;
+ }
+
+ /**
+ * Gets the format string to format line number such as <code>"%%0%4d"</code>
+ * for a 4-digit number with leading zeros.
+ */
+ public String getLineNumberFormat() {
+ return lineNumberFormat;
+ }
+
+ /**
+ * Sets the format string to format line number such as <code>"%%0%4d"</code>
+ * for a 4-digit number with leading zeros.
+ */
+ public void setLineNumberFormat(String lineNumberFormat) {
+ this.lineNumberFormat = lineNumberFormat;
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/HTMLTokenRenderer.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java Tue May 25 04:28:30 2010
@@ -0,0 +1,73 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import java.io.File;
+
+import openbook.tools.CommandProcessor;
+import openbook.tools.util.URIUtils;
+
+public class Java2HTMLConverter extends SourceRenderer {
+
+ private final HTMLTokenRenderer _renderer = new HTMLTokenRenderer();
+
+ public static void main(String[] args) throws Exception {
+ new Java2HTMLConverter().run(args);
+ }
+
+ @Override
+ public void registerOptions(CommandProcessor options) {
+ options.register(true, "-stylesheet").setDefault("java.css");
+ options.register(true, "-addLineBreak").setDefault("true");
+ options.register(true, "-addExplicitSpace").setDefault("true");
+ options.register(true, "-anchorLineNumber").setDefault("false");
+ options.register(true, "-showLineNumber").setDefault("true");
+ options.register(true, "-lineNumberFormat").setDefault("%%0%4d");
+ }
+
+ @Override
+ public TokenRenderer createRenderer(CommandProcessor options, File outFile) {
+ File styleFile = null;
+ styleFile = new File(getDestinationDirectory(), options.getValue("-stylesheet"));
+ if (!styleFile.exists()) {
+ throw new IllegalArgumentException("Stylesheet file " + styleFile.getAbsolutePath() +
+ " does not exist. Ensure that the file is available under destination directory" +
+ getDestinationDirectory().getAbsolutePath());
+ }
+ _renderer.setStylesheet(getRelativeStylesheet(styleFile, outFile));
+
+ _renderer.setAddLineBreak("true".equals(options.getValue("-addLineBreak")));
+ _renderer.setAddExplicitSpace("true".equals(options.getValue("-addExplicitSpace")));
+ _renderer.setAnchorLineNumber("true".equals(options.getValue("-anchorLineNumber")));
+ _renderer.setLineNumberFormat(options.getValue("-lineNumberFormat"));
+ _renderer.setShowLineNumber("true".equals(options.getValue("-showLineNumber")));
+ return _renderer;
+ }
+
+
+ String getRelativeStylesheet(File styleFile, File outFile) {
+ String stylesheetPath = styleFile.getAbsolutePath().replace(File.separatorChar, FORWARD_SLASH);
+ String outPath = outFile.getAbsolutePath().replace(File.separatorChar, FORWARD_SLASH);
+ verbose("stylesheet " + stylesheetPath);
+ verbose("output " + outPath);
+ String rstylesheet = URIUtils.getRelativePath(stylesheetPath, outPath, ""+FORWARD_SLASH);
+ verbose("stylesheet relative " + rstylesheet);
+ return rstylesheet;
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2HTMLConverter.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java Tue May 25 04:28:30 2010
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import java.io.File;
+
+import openbook.tools.CommandProcessor;
+
+/**
+ * Converts Java Source code to plain text with optional line number.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class Java2TextConverter extends SourceRenderer {
+
+ private final PlainTokenRenderer _renderer = new PlainTokenRenderer();
+
+ public static void main(String[] args) throws Exception {
+ new Java2TextConverter().run(args);
+ }
+
+ @Override
+ public void registerOptions(CommandProcessor options) {
+ options.register(true, "-showLineNumber").setDefault("true");
+ options.register(true, "-lineNumberFormat").setDefault("%%0%4d");
+ }
+
+ @Override
+ public TokenRenderer createRenderer(CommandProcessor options, File outFile) {
+ _renderer.setLineNumberFormat(options.getValue("-lineNumberFormat"));
+ _renderer.setShowLineNumber("true".equals(options.getValue("-showLineNumber")));
+ return _renderer;
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/Java2TextConverter.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java Tue May 25 04:28:30 2010
@@ -0,0 +1,142 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import java.io.PrintStream;
+import java.util.StringTokenizer;
+
+import openbook.tools.parser.JavaParser;
+
+import org.antlr.runtime.CommonToken;
+import org.antlr.runtime.Token;
+import org.antlr.runtime.debug.BlankDebugEventListener;
+
+/**
+ * A token processor to render the ANTLR tokens.
+ *
+ * This token processor is notified as ANTLR parses every token.
+ * This processor controls a {@linkplain TokenRenderer renderer}
+ * that renders the token.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class ParseTokenListener extends BlankDebugEventListener {
+ private int currentLine = 0;
+ private int backtracking = 0;
+ private int decision;
+ private TokenRenderer _renderer;
+ private PrintStream _stream;
+
+ /**
+ * By default, uses a {@linkplain PlainTokenRenderer}.
+ */
+ ParseTokenListener() {
+ this(new PlainTokenRenderer());
+ }
+
+ /**
+ * Uses the given renderer and outputs to System output.
+ *
+ * @param renderer a renderer to render the tokens.
+ */
+ ParseTokenListener(TokenRenderer renderer) {
+ this(renderer, System.out);
+ }
+
+ /**
+ * Uses the given renderer and given outputs stream.
+ *
+ * @param renderer a renderer to render the tokens.
+ * @param stream a output stream where the rendered strings are streamed.
+ */
+ ParseTokenListener(TokenRenderer renderer, PrintStream stream) {
+ _renderer = renderer;
+ _stream = stream;
+ }
+
+ @Override
+ public void enterDecision(int d) {
+ backtracking += 1;
+ decision = d;
+ }
+
+ @Override
+ public void exitDecision(int i) {
+ backtracking -= 1;
+ }
+
+ /**
+ * A regular token is delegated to the renderer for a string representation
+ * and the resultant string is sent to the output stream.
+ */
+ @Override
+ public void consumeToken(Token token) {
+ if (backtracking > 0) return;
+ changeLine(token.getLine());
+ _stream.print(_renderer.render(decision, token));
+ }
+
+ /**
+ * Hidden tokens are tokens that are not processed at lexical processing
+ * stage. The most important hidden token for rendering are the tokens
+ * that represent multi-line or single line comments. The multi-line
+ * comments must be broken into individual lines for line numbering to
+ * remain consistent.
+ *
+ */
+ @Override
+ public void consumeHiddenToken(Token token) {
+ if (this.backtracking > 0 && currentLine != 0) return;
+ int type = token.getType();
+ if (type == JavaParser.COMMENT) {
+// LineBreakIterator lines = new LineBreakIterator(token.getText());
+ StringTokenizer linebreaker = new StringTokenizer(token.getText(), "\r\n", false);
+ int i = 0;
+// for (String line : lines) {
+ while (linebreaker.hasMoreTokens()) {
+// Token dummy = new CommonToken(JavaParser.COMMENT, line);
+ Token dummy = new CommonToken(JavaParser.COMMENT, linebreaker.nextToken());
+ changeLine(token.getLine() + i);
+ _stream.print(_renderer.render(decision, dummy));
+ i++;
+ }
+ } else {
+ changeLine(token.getLine());
+ _stream.print(_renderer.render(decision, token));
+ }
+ }
+
+ /**
+ * If the given line is different than the current line, then asks the
+ * renderer to end the current line and start a new line. Otherwise, does nothing.
+ *
+ * @param newline
+ */
+ void changeLine(int newline) {
+ if (newline == currentLine)
+ return;
+ _stream.print(_renderer.endLine(currentLine));
+ _stream.print(_renderer.newLine(newline));
+ if (newline != currentLine+1) {
+ System.err.println("Error is line number processing. Line " + currentLine + " jumps to " + newline);
+ }
+ currentLine = newline;
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/ParseTokenListener.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java Tue May 25 04:28:30 2010
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+
+import org.antlr.runtime.Token;
+/**
+ * A default implementation of {@linkplain TokenRenderer} that simply prints the token.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public class PlainTokenRenderer implements TokenRenderer {
+ private static final String EMPTY = "";
+ private boolean showLineNumber;
+ private String lineNumberFormat = "%%0%4d :";
+
+ public String endLine(int line) {
+ return EMPTY;
+ }
+
+ public String newLine(int line) {
+ return showLineNumber ? String.format(lineNumberFormat, line) : EMPTY;
+ }
+
+ public String render(int decision, Token token) {
+ return token.getText();
+ }
+
+ public String getEpilogue() {
+ return EMPTY;
+ }
+
+ public String getPrologue() {
+ return EMPTY;
+ }
+
+ public boolean getShowLineNumber() {
+ return showLineNumber;
+ }
+
+ public void setShowLineNumber(boolean showLineNumber) {
+ this.showLineNumber = showLineNumber;
+ }
+
+ /**
+ * @return the lineNumberFormat
+ */
+ public String getLineNumberFormat() {
+ return lineNumberFormat;
+ }
+
+ /**
+ * @param lineNumberFormat the lineNumberFormat to set
+ */
+ public void setLineNumberFormat(String lineNumberFormat) {
+ this.lineNumberFormat = lineNumberFormat;
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/PlainTokenRenderer.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java Tue May 25 04:28:30 2010
@@ -0,0 +1,192 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.InputStream;
+import java.io.PrintStream;
+
+import openbook.tools.CommandProcessor;
+import openbook.tools.parser.JavaLexer;
+import openbook.tools.parser.JavaParser;
+
+import org.antlr.runtime.ANTLRInputStream;
+import org.antlr.runtime.CommonTokenStream;
+import org.antlr.runtime.debug.DebugEventListener;
+
+/**
+ * Renders Java Source Code.
+ *
+ * @author Pinaki Poddar
+ *
+ */
+public abstract class SourceRenderer {
+ public final static char FORWARD_SLASH = '/';
+ public final static String DOT = ".";
+ public final static String CURRENT_DIRECTORY = ".";
+
+ private File _sourceDir, _destinationDir;
+
+ boolean verbose = false;
+ /**
+ * Renders the given source files. The syntax of the command is
+ * <br>
+ * <pre> $ java SourceRenderer [options] files </pre>
+ * For example,
+ * <pre> $ java SourceRenderer -stylesheet mystyle.css -sourcepath test -d generated/html acme/foo/SomeClass.java</pre>
+ * <p>
+ *
+ * Recognized options are<br>
+ * <table>
+ * <TR><TD><pre>-format</pre></TD> <TD>the format of the converted output. Recognized monikers are
+ * <code>html</code> and <code>text</code>. A fully qualified class name that implements {@link TokenRenderer} is
+ * allowed. Default is <code>html</code></TD></tr>
+ * <TR><TD><pre>-sourcepath</pre><TD>the root of the source files. Default is the current directory</tr>
+ * <TR><TD><pre>-d</pre><TD>the root of the generated files. Default is the current directory</tr>
+ * </table>
+ * Besides these options, a renderer can accept more options. Any option <code>-someProperty</code>
+ * will configure the renderer if a bean-style setter method <code>setSomeProperty(String|boolean|int)</code>
+ * is available. See available documentation on the specific {@link HTMLTokenRenderer renderer}.
+ * <br>
+ * Stylesheet file must be under destination directory.
+ * <pre>-stylesheet</pre> is relative to destination directory.
+ *
+ * @param args command-line arguments.
+ *
+ * @throws Exception
+ */
+
+ protected final void run(String[] args) throws Exception {
+ CommandProcessor options = new CommandProcessor();
+ options.register(true, "-sourcepath").setDefault(CURRENT_DIRECTORY);
+ options.register(true, "-d").setDefault(CURRENT_DIRECTORY);
+ options.register(true, "-extension").setDefault("");
+ options.register(true, "-verbose").setDefault("false");
+ registerOptions(options);
+
+ String[] inputs = options.setFrom(args);
+
+ _sourceDir = new File(options.getValue("-sourcepath"));
+ _destinationDir = new File(options.getValue("-d"));
+ verbose = "true".equalsIgnoreCase(options.getValue("-verbose"));
+ for (String path : inputs) {
+ path = path.replace(File.separatorChar, FORWARD_SLASH);
+ InputStream fin = getInputStream(_sourceDir, path);
+ if (fin == null) {
+ continue;
+ }
+
+ File outFile = new File(_destinationDir, suffix(path, options.getValue("-extension")));
+ FileOutputStream fout = createOutput(outFile);
+ if (fout == null) {
+ continue;
+ }
+ PrintStream out = new PrintStream(fout);
+
+ TokenRenderer renderer = createRenderer(options, outFile);
+ if (renderer == null) {
+ continue;
+ }
+ out.print(renderer.getPrologue());
+ render(fin, renderer, out);
+ out.println(renderer.getEpilogue());
+ out.close();
+ }
+ }
+
+ public File getDestinationDirectory() {
+ return _destinationDir;
+ }
+ public File getSourceDirectory() {
+ return _sourceDir;
+ }
+ public abstract void registerOptions(CommandProcessor options);
+ public abstract TokenRenderer createRenderer(CommandProcessor options, File outFile);
+
+ private void render(InputStream is, TokenRenderer renderer, PrintStream out) throws Exception {
+ ANTLRInputStream input = new ANTLRInputStream(is);
+ JavaLexer lexer = new JavaLexer(input);
+ CommonTokenStream tokens = new CommonTokenStream(lexer);
+ DebugEventListener builder = new ParseTokenListener(renderer, out);
+ JavaParser parser = new JavaParser(tokens, builder);
+ // launch the parser starting at compilation unit
+ parser.compilationUnit();
+ }
+
+ /**
+ * Gets the input stream.
+ *
+ * @param srcDir the root source directory.
+ * @param path the path to input file.
+ * @return
+ */
+ protected InputStream getInputStream(File srcDir, String path) {
+ File file = new File(srcDir, path);
+ if (!file.exists()) {
+ warn("Input file " + file.getAbsolutePath() + " does not exist");
+ return null;
+ }
+ try {
+ return new FileInputStream(file);
+ } catch (Exception e) {
+ warn("Input file " + file.getAbsolutePath() + " failed due to " + e.toString());
+ }
+ return null;
+ }
+
+ /**
+ * Gets the output stream to write to.
+ * @param file
+ * @return
+ */
+ private FileOutputStream createOutput(File file) {
+ try {
+ file.getParentFile().mkdirs();
+ if (!file.exists())
+ file.createNewFile();
+ file.setWritable(true);
+ FileOutputStream out = new FileOutputStream(file);
+ verbose("Output " + file.toURI());
+ return out;
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ return null;
+ }
+
+
+ private String suffix(String s, String suffix) {
+ if (suffix == null || suffix.isEmpty())
+ return s;
+ if (suffix.startsWith("."))
+ return s + suffix;
+ return s + "." + suffix;
+ }
+
+ protected void verbose(String s) {
+ if (verbose)
+ System.err.println(s);
+ }
+
+ protected void warn(String s) {
+ System.err.println(s);
+ }
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/SourceRenderer.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java?rev=947912&view=auto
==============================================================================
--- openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java (added)
+++ openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java Tue May 25 04:28:30 2010
@@ -0,0 +1,103 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package openbook.tools.converter;
+
+import org.antlr.runtime.Token;
+import org.antlr.runtime.debug.DebugEventListener;
+
+/**
+ * Renders a runtime ANTLR token.
+ * {@linkplain ParseTokenListener} controls a renderer and streams the rendered Strings
+ * to appropriate output.
+ * <br>
+ * A renderer can define additional bean-style setter methods. They will be set before
+ * renderer is used.
+ * <br>
+ * A concrete renderer should have a no argument constructor.
+ * <br>
+ * {@linkplain ParseTokenListener} or the <em>framework</em> calls a renderer in following sequence:
+ * <pre>
+ * bean-style setter methods as per the user configured
+ * getPrologue()
+ * for each token {
+ * if (line is changing) {
+ * endLine()
+ * newLine()
+ * }
+ * render()
+ * }
+ * getEpilogue();
+ * </pre>
+
+ * @author Pinaki Poddar
+ *
+ */
+public interface TokenRenderer {
+ /**
+ * Gets a string to be added before token processing begins.
+ * <br>
+ * For example, a HTML renderer may return the opening HTML and BODY tags.
+ * A HTML render using a Cascaded Style Sheet may additionally specify
+ * the <HEAD> tag to include the style sheet.
+ */
+ public String getPrologue();
+
+ /**
+ * Gets a string to be added after token processing ends.
+ * For example, a HTML renderer may return the closing HTML and BODY tags.
+ *
+ */
+ public String getEpilogue();
+
+ /**
+ * Produce a string representation of the given token.
+ *
+ * @param decision the index of the decision (or the context) in which
+ * the current token is being processed. The index refers to ANTLR
+ * {@link DebugEventListener#enterDecision(int)}.
+ *
+ * @param token the token to be rendered. Can be a hidden token as well.
+ *
+ * @return a string representation of the given token.
+ */
+ public String render(int decision, Token token);
+
+ /**
+ * Produce a string to signal beginning of a line.
+ * <br>
+ * For example, a renderer printing line numbers can produce a String with the given line number.
+ *
+ * @param line the current line number
+ *
+ * @return a String can be a blank
+ */
+ public String newLine(int line);
+
+
+ /**
+ * Produce a string to signal end of a line.
+ * <br>
+ * For example, a renderer can produce a newline.
+ *
+ * @param line the line being ended
+ *
+ * @return a String can be a blank
+ */
+ public String endLine(int line);
+}
Propchange: openjpa/trunk/openjpa-examples/openbooks/src/main/java/openbook/tools/converter/TokenRenderer.java
------------------------------------------------------------------------------
svn:eol-style = native