Merged DEV/SWIFT to HEAD

25458: added OpenCMIS server
   25555: Don't initialize servlet context if it is not present


git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@28000 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
Derek Hulley
2011-05-24 02:23:57 +00:00
parent 0488757523
commit 00b8f4a002
76 changed files with 17777 additions and 32 deletions

View File

@@ -0,0 +1,414 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import org.alfresco.repo.search.impl.lucene.AnalysisMode;
import org.alfresco.repo.search.impl.parsers.CMIS_FTSLexer;
import org.alfresco.repo.search.impl.parsers.CMIS_FTSParser;
import org.alfresco.repo.search.impl.parsers.FTSQueryException;
import org.alfresco.repo.search.impl.querymodel.Argument;
import org.alfresco.repo.search.impl.querymodel.Column;
import org.alfresco.repo.search.impl.querymodel.Constraint;
import org.alfresco.repo.search.impl.querymodel.Function;
import org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext;
import org.alfresco.repo.search.impl.querymodel.LiteralArgument;
import org.alfresco.repo.search.impl.querymodel.QueryModelFactory;
import org.alfresco.repo.search.impl.querymodel.Selector;
import org.alfresco.repo.search.impl.querymodel.Constraint.Occur;
import org.alfresco.repo.search.impl.querymodel.QueryOptions.Connective;
import org.alfresco.repo.search.impl.querymodel.impl.functions.FTSPhrase;
import org.alfresco.repo.search.impl.querymodel.impl.functions.FTSTerm;
import org.alfresco.service.cmr.dictionary.DataTypeDefinition;
import org.antlr.runtime.ANTLRStringStream;
import org.antlr.runtime.CharStream;
import org.antlr.runtime.CommonTokenStream;
import org.antlr.runtime.RecognitionException;
import org.antlr.runtime.Token;
import org.antlr.runtime.tree.CommonTree;
import org.antlr.runtime.tree.Tree;
public class CMISFTSQueryParser
{
static public Constraint buildFTS(String ftsExpression, QueryModelFactory factory, FunctionEvaluationContext functionEvaluationContext, Selector selector,
Map<String, Column> columnMap, String defaultField)
{
// TODO: Decode sql escape for '' should do in CMIS layer
// parse templates to trees ...
CMIS_FTSParser parser = null;
try
{
CharStream cs = new ANTLRStringStream(ftsExpression);
CMIS_FTSLexer lexer = new CMIS_FTSLexer(cs);
CommonTokenStream tokens = new CommonTokenStream(lexer);
parser = new CMIS_FTSParser(tokens);
CommonTree ftsNode = (CommonTree) parser.cmisFtsQuery().getTree();
return buildFTSConnective(ftsNode, factory, functionEvaluationContext, selector, columnMap, defaultField);
}
catch (RecognitionException e)
{
if (parser != null)
{
String[] tokenNames = parser.getTokenNames();
String hdr = parser.getErrorHeader(e);
String msg = parser.getErrorMessage(e, tokenNames);
throw new FTSQueryException(hdr + "\n" + msg, e);
}
return null;
}
}
static private Constraint buildFTSConnective(CommonTree node, QueryModelFactory factory, FunctionEvaluationContext functionEvaluationContext,
Selector selector, Map<String, Column> columnMap, String defaultField)
{
Connective connective;
switch (node.getType())
{
case CMIS_FTSParser.DISJUNCTION:
connective = Connective.OR;
break;
case CMIS_FTSParser.CONJUNCTION:
connective = Connective.AND;
break;
default:
throw new FTSQueryException("Invalid connective ..." + node.getText());
}
List<Constraint> constraints = new ArrayList<Constraint>(node.getChildCount());
CommonTree testNode;
for (int i = 0; i < node.getChildCount(); i++)
{
CommonTree subNode = (CommonTree) node.getChild(i);
Constraint constraint;
switch (subNode.getType())
{
case CMIS_FTSParser.DISJUNCTION:
case CMIS_FTSParser.CONJUNCTION:
constraint = buildFTSConnective(subNode, factory, functionEvaluationContext, selector, columnMap, defaultField);
break;
case CMIS_FTSParser.DEFAULT:
testNode = (CommonTree) subNode.getChild(0);
constraint = buildFTSTest(testNode, factory, functionEvaluationContext, selector, columnMap, defaultField);
constraint.setOccur(Occur.DEFAULT);
break;
case CMIS_FTSParser.EXCLUDE:
testNode = (CommonTree) subNode.getChild(0);
constraint = buildFTSTest(testNode, factory, functionEvaluationContext, selector, columnMap, defaultField);
constraint.setOccur(Occur.EXCLUDE);
break;
default:
throw new FTSQueryException("Unsupported FTS option " + subNode.getText());
}
constraints.add(constraint);
}
if (constraints.size() == 1)
{
return constraints.get(0);
}
else
{
if (connective == Connective.OR)
{
return factory.createDisjunction(constraints);
}
else
{
return factory.createConjunction(constraints);
}
}
}
static private Constraint buildFTSTest(CommonTree argNode, QueryModelFactory factory, FunctionEvaluationContext functionEvaluationContext,
Selector selector, Map<String, Column> columnMap, String defaultField)
{
CommonTree testNode = argNode;
switch (testNode.getType())
{
case CMIS_FTSParser.DISJUNCTION:
case CMIS_FTSParser.CONJUNCTION:
return buildFTSConnective(testNode, factory, functionEvaluationContext, selector, columnMap, defaultField);
case CMIS_FTSParser.TERM:
return buildTerm(testNode, factory, functionEvaluationContext, selector, columnMap);
case CMIS_FTSParser.PHRASE:
return buildPhrase(testNode, factory, functionEvaluationContext, selector, columnMap);
default:
throw new FTSQueryException("Unsupported FTS option " + testNode.getText());
}
}
static private Constraint buildPhrase(CommonTree testNode, QueryModelFactory factory,
FunctionEvaluationContext functionEvaluationContext, Selector selector, Map<String, Column> columnMap)
{
String functionName = FTSPhrase.NAME;
Function function = factory.getFunction(functionName);
Map<String, Argument> functionArguments = new LinkedHashMap<String, Argument>();
LiteralArgument larg = factory.createLiteralArgument(FTSPhrase.ARG_PHRASE, DataTypeDefinition.TEXT, getText(testNode.getChild(0)));
functionArguments.put(larg.getName(), larg);
return factory.createFunctionalConstraint(function, functionArguments);
}
static private Constraint buildTerm(CommonTree testNode, QueryModelFactory factory, FunctionEvaluationContext functionEvaluationContext,
Selector selector, Map<String, Column> columnMap)
{
String functionName = FTSTerm.NAME;
Function function = factory.getFunction(functionName);
Map<String, Argument> functionArguments = new LinkedHashMap<String, Argument>();
LiteralArgument larg = factory.createLiteralArgument(FTSTerm.ARG_TERM, DataTypeDefinition.TEXT, getText(testNode.getChild(0)));
functionArguments.put(larg.getName(), larg);
larg = factory.createLiteralArgument(FTSTerm.ARG_TOKENISATION_MODE, DataTypeDefinition.ANY, AnalysisMode.DEFAULT);
functionArguments.put(larg.getName(), larg);
return factory.createFunctionalConstraint(function, functionArguments);
}
static class DisjunctionToken implements Token
{
public int getChannel()
{
return 0;
}
public int getCharPositionInLine()
{
return 0;
}
public CharStream getInputStream()
{
return null;
}
public int getLine()
{
return 0;
}
public String getText()
{
return null;
}
public int getTokenIndex()
{
return 0;
}
public int getType()
{
return CMIS_FTSParser.DISJUNCTION;
}
public void setChannel(int arg0)
{
}
public void setCharPositionInLine(int arg0)
{
}
public void setInputStream(CharStream arg0)
{
}
public void setLine(int arg0)
{
}
public void setText(String arg0)
{
}
public void setTokenIndex(int arg0)
{
}
public void setType(int arg0)
{
}
}
static class DefaultToken implements Token
{
public int getChannel()
{
return 0;
}
public int getCharPositionInLine()
{
return 0;
}
public CharStream getInputStream()
{
return null;
}
public int getLine()
{
return 0;
}
public String getText()
{
return null;
}
public int getTokenIndex()
{
return 0;
}
public int getType()
{
return CMIS_FTSParser.DEFAULT;
}
public void setChannel(int arg0)
{
}
public void setCharPositionInLine(int arg0)
{
}
public void setInputStream(CharStream arg0)
{
}
public void setLine(int arg0)
{
}
public void setText(String arg0)
{
}
public void setTokenIndex(int arg0)
{
}
public void setType(int arg0)
{
}
}
static private String getText(Tree node)
{
String text = node.getText();
int index;
switch (node.getType())
{
case CMIS_FTSParser.FTSWORD:
index = text.indexOf('\\');
if (index == -1)
{
return text;
}
else
{
return unescape(text);
}
case CMIS_FTSParser.FTSPHRASE:
String phrase = text.substring(1, text.length() - 1);
index = phrase.indexOf('\\');
if (index == -1)
{
return phrase;
}
else
{
return unescape(phrase);
}
default:
return text;
}
}
static private String unescape(String string)
{
StringBuilder builder = new StringBuilder(string.length());
boolean lastWasEscape = false;
for (int i = 0; i < string.length(); i++)
{
char c = string.charAt(i);
if (lastWasEscape)
{
if (c == 'u')
{
throw new UnsupportedOperationException(string);
}
else
{
builder.append(c);
}
lastWasEscape = false;
}
else
{
if (c == '\\')
{
lastWasEscape = true;
}
else
{
builder.append(c);
}
}
}
if (lastWasEscape)
{
throw new FTSQueryException("Escape character at end of string " + string);
}
return builder.toString();
}
}

View File

@@ -0,0 +1,90 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.util.Locale;
import org.springframework.extensions.surf.util.I18NUtil;
import org.alfresco.repo.search.impl.querymodel.QueryOptions;
import org.alfresco.service.cmr.repository.StoreRef;
/**
* The options for a CMIS query
*
* @author andyh
*/
public class CMISQueryOptions extends QueryOptions
{
public enum CMISQueryMode
{
CMS_STRICT, CMS_WITH_ALFRESCO_EXTENSIONS;
}
private CMISQueryMode queryMode = CMISQueryMode.CMS_STRICT;
/**
* Create a CMISQueryOptions instance with the default options other than
* the query and store ref. The query will be run using the locale returned
* by I18NUtil.getLocale()
*
* @param query
* - the query to run
* @param storeRef
* - the store against which to run the query
*/
public CMISQueryOptions(String query, StoreRef storeRef)
{
this(query, storeRef, I18NUtil.getLocale());
}
/**
* Create a CMISQueryOptions instance with the default options other than
* the query, store ref and locale.
*
* @param query
* - the query to run
* @param storeRef
* - the store against which to run the query
*/
public CMISQueryOptions(String query, StoreRef storeRef, Locale locale)
{
super(query, storeRef, locale);
}
/**
* Get the query mode.
*
* @return the queryMode
*/
public CMISQueryMode getQueryMode()
{
return queryMode;
}
/**
* Set the query mode.
*
* @param queryMode
* the queryMode to set
*/
public void setQueryMode(CMISQueryMode queryMode)
{
this.queryMode = queryMode;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,20 @@
package org.alfresco.opencmis.search;
import org.alfresco.service.cmr.repository.StoreRef;
import org.apache.chemistry.opencmis.commons.enums.CapabilityJoin;
import org.apache.chemistry.opencmis.commons.enums.CapabilityQuery;
public interface CMISQueryService
{
CMISResultSet query(CMISQueryOptions options);
CMISResultSet query(String query, StoreRef storeRef);
boolean getPwcSearchable();
boolean getAllVersionsSearchable();
CapabilityQuery getQuerySupport();
CapabilityJoin getJoinSupport();
}

View File

@@ -0,0 +1,152 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import org.alfresco.opencmis.dictionary.CMISDictionaryService;
import org.alfresco.opencmis.search.CMISQueryOptions.CMISQueryMode;
import org.alfresco.repo.search.impl.querymodel.Query;
import org.alfresco.repo.search.impl.querymodel.QueryEngine;
import org.alfresco.repo.search.impl.querymodel.QueryEngineResults;
import org.alfresco.service.cmr.dictionary.DictionaryService;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.cmr.repository.StoreRef;
import org.alfresco.service.cmr.search.LimitBy;
import org.alfresco.service.cmr.search.ResultSet;
import org.apache.chemistry.opencmis.commons.enums.BaseTypeId;
import org.apache.chemistry.opencmis.commons.enums.CapabilityJoin;
import org.apache.chemistry.opencmis.commons.enums.CapabilityQuery;
/**
* @author andyh
*/
public class CMISQueryServiceImpl implements CMISQueryService
{
private CMISDictionaryService cmisDictionaryService;
private QueryEngine queryEngine;
private NodeService nodeService;
private DictionaryService alfrescoDictionaryService;
public void setOpenCMISDictionaryService(CMISDictionaryService cmisDictionaryService)
{
this.cmisDictionaryService = cmisDictionaryService;
}
/**
* @param queryEngine
* the queryEngine to set
*/
public void setQueryEngine(QueryEngine queryEngine)
{
this.queryEngine = queryEngine;
}
/**
* @param nodeService
* the nodeService to set
*/
public void setNodeService(NodeService nodeService)
{
this.nodeService = nodeService;
}
/**
* @param alfrescoDictionaryService
* the Alfresco Dictionary Service to set
*/
public void setAlfrescoDictionaryService(DictionaryService alfrescoDictionaryService)
{
this.alfrescoDictionaryService = alfrescoDictionaryService;
}
public CMISResultSet query(CMISQueryOptions options)
{
CapabilityJoin joinSupport = getJoinSupport();
if (options.getQueryMode() == CMISQueryOptions.CMISQueryMode.CMS_WITH_ALFRESCO_EXTENSIONS)
{
joinSupport = CapabilityJoin.INNERONLY;
}
// TODO: Refactor to avoid duplication of valid scopes here and in
// CMISQueryParser
BaseTypeId[] validScopes = (options.getQueryMode() == CMISQueryMode.CMS_STRICT) ? CmisFunctionEvaluationContext.STRICT_SCOPES
: CmisFunctionEvaluationContext.ALFRESCO_SCOPES;
CmisFunctionEvaluationContext functionContext = new CmisFunctionEvaluationContext();
functionContext.setCmisDictionaryService(cmisDictionaryService);
functionContext.setNodeService(nodeService);
functionContext.setValidScopes(validScopes);
CMISQueryParser parser = new CMISQueryParser(options, cmisDictionaryService, joinSupport);
Query query = parser.parse(queryEngine.getQueryModelFactory(), functionContext);
QueryEngineResults results = queryEngine.executeQuery(query, options, functionContext);
Map<String, ResultSet> wrapped = new HashMap<String, ResultSet>();
Map<Set<String>, ResultSet> map = results.getResults();
for (Set<String> group : map.keySet())
{
ResultSet current = map.get(group);
for (String selector : group)
{
wrapped.put(selector, current);
}
}
LimitBy limitBy = null;
if ((null != results.getResults()) && !results.getResults().isEmpty()
&& (null != results.getResults().values()) && !results.getResults().values().isEmpty())
{
limitBy = results.getResults().values().iterator().next().getResultSetMetaData().getLimitedBy();
}
CMISResultSet cmis = new CMISResultSet(wrapped, options, limitBy, nodeService, query, cmisDictionaryService,
alfrescoDictionaryService);
return cmis;
}
public CMISResultSet query(String query, StoreRef storeRef)
{
CMISQueryOptions options = new CMISQueryOptions(query, storeRef);
return query(options);
}
public boolean getPwcSearchable()
{
return true;
}
public boolean getAllVersionsSearchable()
{
return false;
}
public CapabilityQuery getQuerySupport()
{
return CapabilityQuery.BOTHCOMBINED;
}
public CapabilityJoin getJoinSupport()
{
return CapabilityJoin.NONE;
}
}

View File

@@ -0,0 +1,331 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.alfresco.opencmis.dictionary.CMISDictionaryService;
import org.alfresco.repo.search.impl.querymodel.Query;
import org.alfresco.service.cmr.dictionary.DictionaryService;
import org.alfresco.service.cmr.repository.ChildAssociationRef;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.cmr.search.LimitBy;
import org.alfresco.service.cmr.search.ResultSet;
import org.alfresco.service.cmr.search.ResultSetRow;
import org.alfresco.service.cmr.search.ResultSetSPI;
/**
* @author andyh
*/
public class CMISResultSet implements ResultSetSPI<CMISResultSetRow, CMISResultSetMetaData>, Serializable
{
private static final long serialVersionUID = 2014688399588268994L;
private Map<String, ResultSet> wrapped;
private LimitBy limitBy;
CMISQueryOptions options;
NodeService nodeService;
Query query;
CMISDictionaryService cmisDictionaryService;
DictionaryService alfrescoDictionaryService;
public CMISResultSet(Map<String, ResultSet> wrapped, CMISQueryOptions options, LimitBy limitBy,
NodeService nodeService, Query query, CMISDictionaryService cmisDictionaryService,
DictionaryService alfrescoDictionaryService)
{
this.wrapped = wrapped;
this.options = options;
this.limitBy = limitBy;
this.nodeService = nodeService;
this.query = query;
this.cmisDictionaryService = cmisDictionaryService;
this.alfrescoDictionaryService = alfrescoDictionaryService;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#close()
*/
public void close()
{
// results sets can be used for more than one selector so we need to
// keep track of what we have closed
Set<ResultSet> closed = new HashSet<ResultSet>();
for (ResultSet resultSet : wrapped.values())
{
if (!closed.contains(resultSet))
{
resultSet.close();
closed.add(resultSet);
}
}
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#getMetaData()
*/
public CMISResultSetMetaData getMetaData()
{
return new CMISResultSetMetaData(options, query, limitBy, cmisDictionaryService, alfrescoDictionaryService);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#getRow(int)
*/
public CMISResultSetRow getRow(int i)
{
return new CMISResultSetRow(this, i, getScores(i), nodeService, getNodeRefs(i), query, cmisDictionaryService);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#hasMore()
*/
public boolean hasMore()
{
for (ResultSet resultSet : wrapped.values())
{
if (resultSet.hasMore())
{
return true;
}
}
return false;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#length()
*/
public int getLength()
{
for (ResultSet resultSet : wrapped.values())
{
return resultSet.length();
}
throw new IllegalStateException();
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSet#start()
*/
public int getStart()
{
return options.getSkipCount();
}
/*
* (non-Javadoc)
*
* @see java.lang.Iterable#iterator()
*/
public Iterator<CMISResultSetRow> iterator()
{
return new CMISResultSetRowIterator(this);
}
private Map<String, NodeRef> getNodeRefs(int i)
{
HashMap<String, NodeRef> refs = new HashMap<String, NodeRef>();
for (String selector : wrapped.keySet())
{
ResultSet rs = wrapped.get(selector);
refs.put(selector, rs.getNodeRef(i));
}
return refs;
}
private Map<String, Float> getScores(int i)
{
HashMap<String, Float> scores = new HashMap<String, Float>();
for (String selector : wrapped.keySet())
{
ResultSet rs = wrapped.get(selector);
scores.put(selector, Float.valueOf(rs.getScore(i)));
}
return scores;
}
public ChildAssociationRef getChildAssocRef(int n)
{
NodeRef nodeRef = getNodeRef(n);
return nodeService.getPrimaryParent(nodeRef);
}
public List<ChildAssociationRef> getChildAssocRefs()
{
ArrayList<ChildAssociationRef> cars = new ArrayList<ChildAssociationRef>(length());
for (ResultSetRow row : this)
{
cars.add(row.getChildAssocRef());
}
return cars;
}
public NodeRef getNodeRef(int n)
{
Map<String, NodeRef> refs = getNodeRefs(n);
if (refs.size() == 1)
{
return refs.values().iterator().next();
} else if (allNodeRefsEqual(refs))
{
return refs.values().iterator().next();
} else
{
throw new IllegalStateException("Ambiguous selector");
}
}
private boolean allNodeRefsEqual(Map<String, NodeRef> selected)
{
NodeRef last = null;
for (NodeRef current : selected.values())
{
if (last == null)
{
last = current;
} else
{
if (!last.equals(current))
{
return false;
}
}
}
return true;
}
public List<NodeRef> getNodeRefs()
{
ArrayList<NodeRef> nodeRefs = new ArrayList<NodeRef>(length());
for (ResultSetRow row : this)
{
nodeRefs.add(row.getNodeRef());
}
return nodeRefs;
}
public CMISResultSetMetaData getResultSetMetaData()
{
return getMetaData();
}
public float getScore(int n)
{
Map<String, Float> scores = getScores(n);
if (scores.size() == 1)
{
return scores.values().iterator().next();
} else if (allScoresEqual(scores))
{
return scores.values().iterator().next();
} else
{
throw new IllegalStateException("Ambiguous selector");
}
}
private boolean allScoresEqual(Map<String, Float> scores)
{
Float last = null;
for (Float current : scores.values())
{
if (last == null)
{
last = current;
} else
{
if (!last.equals(current))
{
return false;
}
}
}
return true;
}
public int length()
{
return getLength();
}
/**
* Bulk fetch results in the cache - not supported here
*
* @param bulkFetch
*/
public boolean setBulkFetch(boolean bulkFetch)
{
return false;
}
/**
* Do we bulk fetch - not supported here
*
* @return - true if we do
*/
public boolean getBulkFetch()
{
return false;
}
/**
* Set the bulk fetch size
*
* @param bulkFetchSize
*/
public int setBulkFetchSize(int bulkFetchSize)
{
return 0;
}
/**
* Get the bulk fetch size.
*
* @return the fetch size
*/
public int getBulkFetchSize()
{
return 0;
}
}

View File

@@ -0,0 +1,77 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import org.alfresco.opencmis.dictionary.PropertyDefintionWrapper;
import org.alfresco.service.cmr.search.ResultSetColumn;
import org.alfresco.service.namespace.QName;
import org.apache.chemistry.opencmis.commons.enums.PropertyType;
/**
* @author andyh
*
*/
public class CMISResultSetColumn implements ResultSetColumn
{
private String name;
private PropertyDefintionWrapper propertyDefinition;
private PropertyType dataType;
private QName alfrescoPropertyQName;
private QName alfrescoDataTypeQName;
CMISResultSetColumn(String name, PropertyDefintionWrapper propertyDefinition, PropertyType dataType,
QName alfrescoPropertyQName, QName alfrescoDataTypeQName)
{
this.name = name;
this.propertyDefinition = propertyDefinition;
this.dataType = dataType;
this.alfrescoPropertyQName = alfrescoPropertyQName;
this.alfrescoDataTypeQName = alfrescoDataTypeQName;
}
public String getName()
{
return name;
}
public PropertyDefintionWrapper getCMISPropertyDefinition()
{
return propertyDefinition;
}
public PropertyType getCMISDataType()
{
return dataType;
}
public QName getDataType()
{
return alfrescoDataTypeQName;
}
public QName getPropertyType()
{
return alfrescoPropertyQName;
}
}

View File

@@ -0,0 +1,201 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.util.LinkedHashMap;
import java.util.Map;
import org.alfresco.opencmis.dictionary.CMISDictionaryService;
import org.alfresco.opencmis.dictionary.PropertyDefintionWrapper;
import org.alfresco.opencmis.dictionary.TypeDefinitionWrapper;
import org.alfresco.repo.search.impl.querymodel.Column;
import org.alfresco.repo.search.impl.querymodel.PropertyArgument;
import org.alfresco.repo.search.impl.querymodel.Query;
import org.alfresco.repo.search.impl.querymodel.Selector;
import org.alfresco.repo.search.impl.querymodel.impl.functions.PropertyAccessor;
import org.alfresco.service.cmr.dictionary.DictionaryService;
import org.alfresco.service.cmr.dictionary.PropertyDefinition;
import org.alfresco.service.cmr.search.LimitBy;
import org.alfresco.service.cmr.search.PermissionEvaluationMode;
import org.alfresco.service.cmr.search.ResultSetMetaData;
import org.alfresco.service.cmr.search.ResultSetType;
import org.alfresco.service.cmr.search.SearchParameters;
import org.alfresco.service.namespace.QName;
import org.apache.chemistry.opencmis.commons.enums.PropertyType;
/**
* @author andyh
*/
public class CMISResultSetMetaData implements ResultSetMetaData
{
private CMISQueryOptions options;
private SearchParameters searchParams;
private LimitBy limitBy;
private Map<String, CMISResultSetColumn> columnMetaData;
private Map<String, CMISResultSetSelector> selectorMetaData;
public CMISResultSetMetaData(CMISQueryOptions options, Query query, LimitBy limitBy,
CMISDictionaryService cmisDictionaryService, DictionaryService alfrescoDictionaryService)
{
this.options = options;
this.searchParams = new SearchParameters(options);
this.limitBy = limitBy;
Map<String, Selector> selectors = query.getSource().getSelectors();
selectorMetaData = new LinkedHashMap<String, CMISResultSetSelector>();
for (Selector selector : selectors.values())
{
TypeDefinitionWrapper type = cmisDictionaryService.findTypeForClass(selector.getType());
CMISResultSetSelector smd = new CMISResultSetSelector(selector.getAlias(), type);
selectorMetaData.put(smd.getName(), smd);
}
columnMetaData = new LinkedHashMap<String, CMISResultSetColumn>();
for (Column column : query.getColumns())
{
PropertyDefintionWrapper propertyDefinition = null;
PropertyType type = null;
QName alfrescoPropertyQName = null;
QName alfrescoDataTypeQName = null;
if (column.getFunction().getName().equals(PropertyAccessor.NAME))
{
PropertyArgument arg = (PropertyArgument) column.getFunctionArguments().get(
PropertyAccessor.ARG_PROPERTY);
String propertyName = arg.getPropertyName();
alfrescoPropertyQName = QName.createQName(propertyName);
PropertyDefinition alfPropDef = alfrescoDictionaryService.getProperty(alfrescoPropertyQName);
if (alfPropDef == null)
{
alfrescoPropertyQName = null;
} else
{
alfrescoDataTypeQName = alfPropDef.getDataType().getName();
}
propertyDefinition = cmisDictionaryService.findProperty(propertyName);
type = propertyDefinition.getPropertyDefinition().getPropertyType();
}
if (type == null)
{
type = cmisDictionaryService.findDataType(column.getFunction().getReturnType());
}
if (alfrescoDataTypeQName == null)
{
alfrescoDataTypeQName = cmisDictionaryService.findAlfrescoDataType(type);
}
CMISResultSetColumn cmd = new CMISResultSetColumn(column.getAlias(), propertyDefinition, type,
alfrescoPropertyQName, alfrescoDataTypeQName);
columnMetaData.put(cmd.getName(), cmd);
}
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetMetaData#getColumnNames()
*/
public String[] getColumnNames()
{
return columnMetaData.keySet().toArray(new String[0]);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetMetaData#getColumns()
*/
public CMISResultSetColumn[] getColumns()
{
return columnMetaData.values().toArray(new CMISResultSetColumn[0]);
}
/*
* (non-Javadoc)
*
* @see
* org.alfresco.cmis.search.CMISResultSetMetaData#getCoumn(java.lang.String)
*/
public CMISResultSetColumn getColumn(String name)
{
return columnMetaData.get(name);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetMetaData#getQueryOptions()
*/
public CMISQueryOptions getQueryOptions()
{
return options;
}
/*
* (non-Javadoc)
*
* @see
* org.alfresco.cmis.search.CMISResultSetMetaData#getSelector(java.lang.
* String)
*/
public CMISResultSetSelector getSelector(String name)
{
return selectorMetaData.get(name);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetMetaData#getSelectorNames()
*/
public String[] getSelectorNames()
{
return selectorMetaData.keySet().toArray(new String[0]);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetMetaData#getSelectors()
*/
public CMISResultSetSelector[] getSelectors()
{
return selectorMetaData.values().toArray(new CMISResultSetSelector[0]);
}
public LimitBy getLimitedBy()
{
return limitBy;
}
public PermissionEvaluationMode getPermissionEvaluationMode()
{
throw new UnsupportedOperationException();
}
public ResultSetType getResultSetType()
{
return ResultSetType.COLUMN_AND_NODE_REF;
}
public SearchParameters getSearchParameters()
{
return searchParams;
}
}

View File

@@ -0,0 +1,279 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.io.Serializable;
import java.util.LinkedHashMap;
import java.util.Map;
import org.alfresco.opencmis.dictionary.CMISDictionaryService;
import org.alfresco.repo.search.impl.querymodel.Column;
import org.alfresco.repo.search.impl.querymodel.PropertyArgument;
import org.alfresco.repo.search.impl.querymodel.Query;
import org.alfresco.repo.search.impl.querymodel.impl.functions.PropertyAccessor;
import org.alfresco.repo.search.results.ResultSetSPIWrapper;
import org.alfresco.service.cmr.repository.ChildAssociationRef;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.cmr.search.ResultSet;
import org.alfresco.service.cmr.search.ResultSetRow;
import org.alfresco.service.namespace.QName;
/**
* @author andyh
*/
public class CMISResultSetRow implements ResultSetRow
{
/**
* The containing result set
*/
private CMISResultSet resultSet;
/**
* The current position in the containing result set
*/
private int index;
private Map<String, Float> scores;
private NodeService nodeService;
private Map<String, NodeRef> nodeRefs;
private Query query;
private CMISDictionaryService cmisDictionaryService;
public CMISResultSetRow(CMISResultSet resultSet, int index, Map<String, Float> scores, NodeService nodeService,
Map<String, NodeRef> nodeRefs, Query query, CMISDictionaryService cmisDictionaryService)
{
this.resultSet = resultSet;
this.index = index;
this.scores = scores;
this.nodeService = nodeService;
this.nodeRefs = nodeRefs;
this.query = query;
this.cmisDictionaryService = cmisDictionaryService;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getIndex()
*/
public int getIndex()
{
return index;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getResultSet()
*/
public ResultSet getResultSet()
{
return new ResultSetSPIWrapper<CMISResultSetRow, CMISResultSetMetaData>(resultSet);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getScore()
*/
public float getScore()
{
float count = 0;
float overall = 0;
for (Float score : scores.values())
{
overall = (overall * (count / (count + 1.0f))) + (score / (count + 1.0f));
}
return overall;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getScore(java.lang.String)
*/
public float getScore(String selectorName)
{
return scores.get(selectorName);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getScores()
*/
public Map<String, Float> getScores()
{
return scores;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getScore(java.lang.String)
*/
public NodeRef getNodeRef(String selectorName)
{
return nodeRefs.get(selectorName);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getScores()
*/
public Map<String, NodeRef> getNodeRefs()
{
return nodeRefs;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getValue(java.lang.String)
*/
public Serializable getValue(String columnName)
{
CmisFunctionEvaluationContext context = new CmisFunctionEvaluationContext();
context.setCmisDictionaryService(cmisDictionaryService);
context.setNodeRefs(nodeRefs);
context.setNodeService(nodeService);
context.setScores(scores);
context.setScore(getScore());
for (Column column : query.getColumns())
{
if (column.getAlias().equals(columnName))
{
return column.getFunction().getValue(column.getFunctionArguments(), context);
}
// Special case for one selector - ignore any table aliases
// also allows look up direct and not by alias
// Perhaps we should add the duplicates instead
// TODO: check SQL 92 for single alias table behaviour for selectors
if (nodeRefs.size() == 1)
{
if (column.getFunction().getName().equals(PropertyAccessor.NAME))
{
PropertyArgument arg = (PropertyArgument) column.getFunctionArguments().get(
PropertyAccessor.ARG_PROPERTY);
String propertyName = arg.getPropertyName();
if (propertyName.equals(columnName))
{
return column.getFunction().getValue(column.getFunctionArguments(), context);
}
StringBuilder builder = new StringBuilder();
builder.append(arg.getSelector()).append(".").append(propertyName);
propertyName = builder.toString();
if (propertyName.equals(columnName))
{
return column.getFunction().getValue(column.getFunctionArguments(), context);
}
}
} else
{
if (column.getFunction().getName().equals(PropertyAccessor.NAME))
{
PropertyArgument arg = (PropertyArgument) column.getFunctionArguments().get(
PropertyAccessor.ARG_PROPERTY);
StringBuilder builder = new StringBuilder();
builder.append(arg.getSelector()).append(".").append(arg.getPropertyName());
String propertyName = builder.toString();
if (propertyName.equals(columnName))
{
return column.getFunction().getValue(column.getFunctionArguments(), context);
}
}
}
}
return null;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.cmis.search.CMISResultSetRow#getValues()
*/
public Map<String, Serializable> getValues()
{
LinkedHashMap<String, Serializable> answer = new LinkedHashMap<String, Serializable>();
for (String column : resultSet.getMetaData().getColumnNames())
{
answer.put(column, getValue(column));
}
return answer;
}
public CMISResultSet getCMISResultSet()
{
return resultSet;
}
public ChildAssociationRef getChildAssocRef()
{
NodeRef nodeRef = getNodeRef();
return nodeService.getPrimaryParent(nodeRef);
}
public NodeRef getNodeRef()
{
if (nodeRefs.size() == 1)
{
return nodeRefs.values().iterator().next();
} else if (allNodeRefsEqual(nodeRefs))
{
return nodeRefs.values().iterator().next();
}
throw new UnsupportedOperationException("Ambiguous selector");
}
private boolean allNodeRefsEqual(Map<String, NodeRef> selected)
{
NodeRef last = null;
for (NodeRef current : selected.values())
{
if (last == null)
{
last = current;
} else
{
if (!last.equals(current))
{
return false;
}
}
}
return true;
}
public QName getQName()
{
return getChildAssocRef().getQName();
}
public Serializable getValue(QName qname)
{
throw new UnsupportedOperationException();
}
}

View File

@@ -0,0 +1,130 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.util.ListIterator;
/**
* @author andyh
*/
public class CMISResultSetRowIterator implements ListIterator<CMISResultSetRow>
{
/**
* The result set
*/
private CMISResultSet resultSet;
/**
* The current position
*/
private int position = -1;
/**
* The maximum position
*/
private int max;
/**
* Create an iterator over the result set. Follows stadard ListIterator
* conventions
*
* @param resultSet
*/
public CMISResultSetRowIterator(CMISResultSet resultSet)
{
this.resultSet = resultSet;
this.max = resultSet.getLength();
}
public CMISResultSet getResultSet()
{
return resultSet;
}
/*
* ListIterator implementation
*/
public boolean hasNext()
{
return position < (max - 1);
}
public boolean allowsReverse()
{
return true;
}
public boolean hasPrevious()
{
return position > 0;
}
public CMISResultSetRow next()
{
return resultSet.getRow(moveToNextPosition());
}
protected int moveToNextPosition()
{
return ++position;
}
public CMISResultSetRow previous()
{
return resultSet.getRow(moveToPreviousPosition());
}
protected int moveToPreviousPosition()
{
return --position;
}
public int nextIndex()
{
return position + 1;
}
public int previousIndex()
{
return position - 1;
}
/*
* Mutation is not supported
*/
public void remove()
{
// TODO Auto-generated method stub
throw new UnsupportedOperationException();
}
public void set(CMISResultSetRow o)
{
// TODO Auto-generated method stub
throw new UnsupportedOperationException();
}
public void add(CMISResultSetRow o)
{
// TODO Auto-generated method stub
throw new UnsupportedOperationException();
}
}

View File

@@ -0,0 +1,56 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import org.alfresco.opencmis.dictionary.TypeDefinitionWrapper;
import org.alfresco.service.cmr.search.ResultSetSelector;
import org.alfresco.service.namespace.QName;
/**
* @author andyh
*
*/
public class CMISResultSetSelector implements ResultSetSelector
{
private String name;
private TypeDefinitionWrapper typeDefinition;
public CMISResultSetSelector(String name, TypeDefinitionWrapper typeDefinition)
{
this.name = name;
this.typeDefinition = typeDefinition;
}
public String getName()
{
return name;
}
public TypeDefinitionWrapper getTypeDefinition()
{
return typeDefinition;
}
public QName getType()
{
return typeDefinition.getAlfrescoName();
}
}

View File

@@ -0,0 +1,429 @@
/*
* Copyright (C) 2005-2010 Alfresco Software Limited.
*
* This file is part of Alfresco
*
* Alfresco is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Alfresco 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
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
*/
package org.alfresco.opencmis.search;
import java.io.Serializable;
import java.util.Collection;
import java.util.Map;
import org.alfresco.cmis.CMISDictionaryModel;
import org.alfresco.opencmis.dictionary.CMISDictionaryService;
import org.alfresco.opencmis.dictionary.PropertyDefintionWrapper;
import org.alfresco.opencmis.dictionary.TypeDefinitionWrapper;
import org.alfresco.repo.search.impl.lucene.LuceneFunction;
import org.alfresco.repo.search.impl.lucene.LuceneQueryParser;
import org.alfresco.repo.search.impl.querymodel.FunctionArgument;
import org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext;
import org.alfresco.repo.search.impl.querymodel.PredicateMode;
import org.alfresco.repo.search.impl.querymodel.QueryModelException;
import org.alfresco.repo.search.impl.querymodel.Selector;
import org.alfresco.repo.search.impl.querymodel.impl.functions.Lower;
import org.alfresco.repo.search.impl.querymodel.impl.functions.Upper;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
import org.apache.chemistry.opencmis.commons.enums.BaseTypeId;
import org.apache.chemistry.opencmis.commons.enums.Cardinality;
import org.apache.chemistry.opencmis.commons.exceptions.CmisInvalidArgumentException;
import org.apache.lucene.queryParser.ParseException;
import org.apache.lucene.search.Query;
/**
* @author andyh
*/
public class CmisFunctionEvaluationContext implements FunctionEvaluationContext
{
public static BaseTypeId[] STRICT_SCOPES = new BaseTypeId[] { BaseTypeId.CMIS_DOCUMENT, BaseTypeId.CMIS_FOLDER };
public static BaseTypeId[] ALFRESCO_SCOPES = new BaseTypeId[] { BaseTypeId.CMIS_DOCUMENT, BaseTypeId.CMIS_FOLDER,
BaseTypeId.CMIS_POLICY };
private Map<String, NodeRef> nodeRefs;
private Map<String, Float> scores;
private NodeService nodeService;
private CMISDictionaryService cmisDictionaryService;
private BaseTypeId[] validScopes;
private Float score;
/**
* @param nodeRefs
* the nodeRefs to set
*/
public void setNodeRefs(Map<String, NodeRef> nodeRefs)
{
this.nodeRefs = nodeRefs;
}
/**
* @param scores
* the scores to set
*/
public void setScores(Map<String, Float> scores)
{
this.scores = scores;
}
/**
* @param nodeService
* the nodeService to set
*/
public void setNodeService(NodeService nodeService)
{
this.nodeService = nodeService;
}
/**
* @param cmisDictionaryService
* the cmisDictionaryService to set
*/
public void setCmisDictionaryService(CMISDictionaryService cmisDictionaryService)
{
this.cmisDictionaryService = cmisDictionaryService;
}
/**
* @param validScopes
* the valid scopes to set
*/
public void setValidScopes(BaseTypeId[] validScopes)
{
this.validScopes = validScopes;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* getNodeRefs()
*/
public Map<String, NodeRef> getNodeRefs()
{
return nodeRefs;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* getNodeService()
*/
public NodeService getNodeService()
{
return nodeService;
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* getProperty(org.alfresco.service.cmr.repository.NodeRef,
* org.alfresco.service.namespace.QName)
*/
public Serializable getProperty(NodeRef nodeRef, String propertyName)
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyAccessor().getValue(nodeRef);
}
/*
* (non-Javadoc)
*
* @see
* org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#getScores
* ()
*/
public Map<String, Float> getScores()
{
return scores;
}
/**
* @return the score
*/
public Float getScore()
{
return score;
}
/**
* @param score
* the score to set
*/
public void setScore(Float score)
{
this.score = score;
}
public Query buildLuceneEquality(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneEquality(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneExists(org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.lang.Boolean)
*/
public Query buildLuceneExists(LuceneQueryParser lqp, String propertyName, Boolean not) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneExists(lqp, not);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneGreaterThan
* (org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneGreaterThan(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneGreaterThan(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneGreaterThanOrEquals
* (org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneGreaterThanOrEquals(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneGreaterThanOrEquals(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneIn(org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.util.Collection,
* java.lang.Boolean,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneIn(LuceneQueryParser lqp, String propertyName, Collection<Serializable> values,
Boolean not, PredicateMode mode) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneIn(lqp, values, not, mode);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneInequality
* (org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneInequality(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneInequality(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneLessThan
* (org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneLessThan(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneLessThan(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneLessThanOrEquals
* (org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* org.alfresco.repo.search.impl.querymodel.PredicateMode)
*/
public Query buildLuceneLessThanOrEquals(LuceneQueryParser lqp, String propertyName, Serializable value,
PredicateMode mode, LuceneFunction luceneFunction) throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneLessThanOrEquals(lqp, value, mode, luceneFunction);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* buildLuceneLike(org.alfresco.repo.search.impl.lucene.LuceneQueryParser,
* org.alfresco.service.namespace.QName, java.io.Serializable,
* java.lang.Boolean)
*/
public Query buildLuceneLike(LuceneQueryParser lqp, String propertyName, Serializable value, Boolean not)
throws ParseException
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().buildLuceneLike(lqp, value, not);
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* getLuceneSortField(org.alfresco.service.namespace.QName)
*/
public String getLuceneSortField(LuceneQueryParser lqp, String propertyName)
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
return propertyDef.getPropertyLuceneBuilder().getLuceneSortField(lqp);
}
public boolean isObjectId(String propertyName)
{
return CMISDictionaryModel.PROP_OBJECT_ID.equalsIgnoreCase(propertyName);
}
public boolean isOrderable(String fieldName)
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(fieldName);
if (propertyDef == null)
{
return false;
} else
{
return propertyDef.getPropertyDefinition().isOrderable();
}
}
public boolean isQueryable(String fieldName)
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(fieldName);
if (propertyDef == null)
{
return true;
} else
{
return propertyDef.getPropertyDefinition().isQueryable();
}
}
public String getLuceneFieldName(String propertyName)
{
PropertyDefintionWrapper propertyDef = cmisDictionaryService.findProperty(propertyName);
if (propertyDef != null)
{
return propertyDef.getPropertyLuceneBuilder().getLuceneFieldName();
} else
{
// TODO: restrict to supported "special" fields
return propertyName;
}
}
public LuceneFunction getLuceneFunction(FunctionArgument functionArgument)
{
if (functionArgument == null)
{
return LuceneFunction.FIELD;
} else
{
String functionName = functionArgument.getFunction().getName();
if (functionName.equals(Upper.NAME))
{
return LuceneFunction.UPPER;
} else if (functionName.equals(Lower.NAME))
{
return LuceneFunction.LOWER;
} else
{
throw new QueryModelException("Unsupported function: " + functionName);
}
}
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* checkFieldApplies(org.alfresco.service.namespace.QName, java.lang.String)
*/
public void checkFieldApplies(Selector selector, String propertyName)
{
PropertyDefintionWrapper propDef = cmisDictionaryService.findPropertyByQueryName(propertyName);
if (propDef == null)
{
throw new CmisInvalidArgumentException("Unknown column/property " + propertyName);
}
TypeDefinitionWrapper typeDef = cmisDictionaryService.findTypeForClass(selector.getType(), validScopes);
if (typeDef == null)
{
throw new CmisInvalidArgumentException("Type unsupported in CMIS queries: " + selector.getAlias());
}
// Check column/property applies to selector/type
if (typeDef.getPropertyById(propDef.getPropertyId()) == null)
{
throw new CmisInvalidArgumentException("Invalid column for "
+ typeDef.getTypeDefinition(false).getQueryName() + "." + propertyName);
}
}
/*
* (non-Javadoc)
*
* @see org.alfresco.repo.search.impl.querymodel.FunctionEvaluationContext#
* isMultiValued(java.lang.String)
*/
public boolean isMultiValued(String propertyName)
{
PropertyDefintionWrapper propDef = cmisDictionaryService.findPropertyByQueryName(propertyName);
if (propDef == null)
{
throw new CmisInvalidArgumentException("Unknown column/property " + propertyName);
}
return propDef.getPropertyDefinition().getCardinality() == Cardinality.MULTI;
}
}