package org.teiid.query.sql.lang;
import java.util.ArrayList;
import java.util.List;
import net.sf.saxon.sxpath.XPathExpression;
import org.teiid.core.TeiidProcessingException;
import org.teiid.core.types.DataTypeManager;
import org.teiid.core.util.EquivalenceUtil;
import org.teiid.query.sql.LanguageVisitor;
import org.teiid.query.sql.symbol.DerivedColumn;
import org.teiid.query.sql.symbol.Expression;
import org.teiid.query.sql.symbol.XMLNamespaces;
import org.teiid.query.xquery.saxon.SaxonXQueryExpression;
public class XMLTable extends TableFunctionReference {
public static class XMLColumn extends ProjectedColumn {
private boolean ordinal;
private String path;
private Expression defaultExpression;
private XPathExpression pathExpression;
public XMLColumn(String name) {
super(name, DataTypeManager.DefaultDataTypes.INTEGER);
this.ordinal = true;
}
public XMLColumn(String name, String type, String path, Expression defaultExpression) {
super(name, type);
this.path = path;
this.defaultExpression = defaultExpression;
}
protected XMLColumn() {
}
public Expression getDefaultExpression() {
return defaultExpression;
}
public void setDefaultExpression(Expression defaultExpression) {
this.defaultExpression = defaultExpression;
}
public String getPath() {
return path;
}
public void setPath(String path) {
this.path = path;
}
public boolean isOrdinal() {
return ordinal;
}
public void setOrdinal(boolean ordinal) {
this.ordinal = ordinal;
}
public void setPathExpression(XPathExpression pathExpression) {
this.pathExpression = pathExpression;
}
public XPathExpression getPathExpression() {
return pathExpression;
}
@Override
public boolean equals(Object obj) {
if (obj == this) {
return true;
}
if (!super.equals(obj) || !(obj instanceof XMLColumn)) {
return false;
}
XMLColumn other = (XMLColumn)obj;
return this.ordinal == other.ordinal
&& EquivalenceUtil.areEqual(this.path, other.path)
&& EquivalenceUtil.areEqual(this.defaultExpression, other.defaultExpression);
}
@Override
public XMLColumn clone() {
XMLColumn clone = new XMLColumn();
super.copyTo(clone);
clone.ordinal = this.ordinal;
clone.path = this.path;
if (this.defaultExpression != null) {
clone.defaultExpression = (Expression)this.defaultExpression.clone();
}
clone.pathExpression = this.pathExpression;
return clone;
}
}
private List<XMLColumn> columns = new ArrayList<XMLColumn>();
private XMLNamespaces namespaces;
private String xquery;
private List<DerivedColumn> passing = new ArrayList<DerivedColumn>();
private boolean usingDefaultColumn;
private SaxonXQueryExpression xqueryExpression;
public List<DerivedColumn> getPassing() {
return passing;
}
public void compileXqueryExpression() throws TeiidProcessingException {
this.xqueryExpression = new SaxonXQueryExpression(xquery, namespaces, passing, this.columns);
}
public SaxonXQueryExpression getXQueryExpression() {
return xqueryExpression;
}
public void setPassing(List<DerivedColumn> passing) {
this.passing = passing;
}
public String getXquery() {
return xquery;
}
public void setXquery(String xquery) {
this.xquery = xquery;
}
public List<XMLColumn> getColumns() {
return columns;
}
public void setColumns(List<XMLColumn> columns) {
if (columns.isEmpty()) {
usingDefaultColumn = true;
columns.add(new XMLColumn("OBJECT_VALUE", DataTypeManager.DefaultDataTypes.XML, ".", null)); //$NON-NLS-1$ //$NON-NLS-2$
}
this.columns = columns;
}
public boolean isUsingDefaultColumn() {
return usingDefaultColumn;
}
public XMLNamespaces getNamespaces() {
return namespaces;
}
public void setNamespaces(XMLNamespaces namespaces) {
this.namespaces = namespaces;
}
@Override
public void acceptVisitor(LanguageVisitor visitor) {
visitor.visit(this);
}
@Override
protected XMLTable cloneDirect() {
XMLTable clone = new XMLTable();
this.copy(clone);
for (XMLColumn column : columns) {
clone.getColumns().add(column.clone());
}
if (this.namespaces != null) {
clone.namespaces = this.namespaces.clone();
}
if (this.passing != null) {
for (DerivedColumn col : this.passing) {
clone.passing.add(col.clone());
}
}
clone.xquery = this.xquery;
if (this.xqueryExpression != null) {
clone.xqueryExpression = this.xqueryExpression.clone();
}
clone.usingDefaultColumn = usingDefaultColumn;
return clone;
}
@Override
public boolean equals(Object obj) {
if (obj == this) {
return true;
}
if (!super.equals(obj) || !(obj instanceof XMLTable)) {
return false;
}
XMLTable other = (XMLTable)obj;
return this.columns.equals(other.columns)
&& EquivalenceUtil.areEqual(this.namespaces, other.namespaces)
&& this.xquery.equals(other.xquery)
&& this.passing.equals(other.passing);
}
}