
org.integratedmodelling.utils.sexpr.FormReader Maven / Gradle / Ivy
/*******************************************************************************
* Copyright (C) 2007, 2014:
*
* - Ferdinando Villa
* - integratedmodelling.org
* - any other authors listed in @author annotations
*
* All rights reserved. This file is part of the k.LAB software suite,
* meant to enable modular, collaborative, integrated
* development of interoperable data and model components. For
* details, see http://integratedmodelling.org.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the Affero General Public License
* Version 3 or any later version.
*
* This program is distributed in the hope that it will be useful,
* but without any warranty; without even the implied warranty of
* merchantability or fitness for a particular purpose. See the
* Affero General Public License for more details.
*
* You should have received a copy of the Affero General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
* The license is also available at: https://www.gnu.org/licenses/agpl.html
*******************************************************************************/
package org.integratedmodelling.utils.sexpr;
import java.io.IOException;
import java.io.InputStream;
import org.integratedmodelling.exceptions.KlabException;
import org.integratedmodelling.exceptions.KlabIOException;
/**
* Wraps an InputStream and reads s-expr by s-expr, using Clojure (and I guess any
* Lisp's) reader conventions for strings and quotes. Allows "listening" to all
* forms in a stream.
*
* @author Ferdinando
*
*/
public class FormReader {
private boolean inDquote = false;
private boolean inSquote = false;
private boolean inEscape = false;
private boolean inComment = false;
private InputStream input = null;
private boolean isEof = false;
public interface FormListener {
public void onFormRead(String s) throws KlabException;
}
public FormReader(InputStream input) {
this.input = input;
}
public void close() throws KlabException {
try {
this.input.close();
} catch (IOException e) {
throw new KlabIOException(e);
}
}
private boolean quoted(int ch) {
boolean wasEscape = inEscape;
boolean wasInDquote = inDquote;
boolean wasInSquote = inSquote;
boolean wasComment = inComment;
if (wasComment && ch == '\n')
inComment = false;
if (wasEscape)
inEscape = false;
if (!wasEscape) {
if (wasInDquote && ch == '"') {
inDquote = false;
}
}
return wasInDquote || wasInSquote || wasEscape || wasComment;
}
/**
* Read a single form from input.
*/
public String readForm() throws KlabException {
StringBuffer ret = new StringBuffer(2048);
int plevel = -2;
for (;;) {
try {
int ch = this.input.read();
if (ch < 0) {
this.isEof = true;
break;
}
if (!quoted(ch)) {
switch (ch) {
case '(':
if (plevel == -2)
plevel = -1;
plevel++;
break;
case ')':
plevel--;
break;
case '"':
inDquote = true;
break;
// case '\'':
// inSquote = true;
// break;
case '\\':
inEscape = true;
break;
case ';':
inComment = true;
break;
}
}
ret.append((char) ch);
if (plevel == -1)
break;
} catch (IOException e) {
throw new KlabIOException(e);
}
}
return ret.toString();
}
public boolean isEof() {
return this.isEof;
}
public void read(FormListener listener) throws KlabException {
while (!isEof()) {
listener.onFormRead(readForm());
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy