/*
* Copyright 2008 biaoping.yin
*
* Licensed 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 org.frameworkset.spi.assemble.callback;
import java.io.File;
import java.io.FileFilter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.frameworkset.spi.assemble.AssembleUtil;
import org.frameworkset.spi.assemble.ManagerImport;
import org.frameworkset.util.AntPathMatcher;
import org.frameworkset.util.PathMatcher;
import com.frameworkset.util.SimpleStringUtil;
/**
* <p>Title: DefaultAssembleCallbackResolver.java</p>
* <p>Description: </p>
* <p>bboss workgroup</p>
* <p>Copyright (c) 2007</p>
* @Date 2010-10-3 下午11:04:59
* @author biaoping.yin
* @version 1.0
*/
public class DefaultAssembleCallbackResolver implements AssembleCallbackResolver{
private Map<String,AssembleCallback> docAssembleCallbacks = new HashMap<String,AssembleCallback>();
private final static PathMatcher pathMatcher = new AntPathMatcher();
public AssembleCallback resolverAssembleCallback(String docbasetype) {
AssembleCallback assembleCallback = docAssembleCallbacks.get(docbasetype);
return assembleCallback != null ? assembleCallback:AssembleUtil.defaultAssembleCallback;
}
public void registAssembleCallback(AssembleCallback assembleCallback)
{
docAssembleCallbacks.put(assembleCallback.getDocbaseType(), assembleCallback);
}
/**
* docbase:
* classpath::conf,相对于.
* web::/WEB-INF/
*
* @param docbaseImport
* @return
* @throws AssembleCallbackException
*/
public List<ManagerImport> getManagerImports(ManagerImport docbaseImport) throws AssembleCallbackException
{
String docbaseType = docbaseImport.isClasspathBase()?AssembleCallback.classpathprex:AssembleCallback.webprex;
String docbase = docbaseImport.getDocbase();
String contextFile = docbaseImport.getFile();
AssembleCallback assembleCallback = this.resolverAssembleCallback(docbaseImport.isClasspathBase()?AssembleCallback.classpathprex:AssembleCallback.webprex);
if(assembleCallback == null)
throw new AssembleCallbackException("GetManagerImports("+docbaseType+","+docbase+","+contextFile+"):获取docbaseType[" + docbaseType + "]失败,AssembleCallback is null.");
String absoluteParentPath = assembleCallback.getDocbasePath(docbase);
// System.out.println("~~~~~~~~~~~~~~~~~~~~~~~~~~assembleCallback.getRootPath():" + assembleCallback.getRootPath() + "," + assembleCallback.getClass().getName());
List<ManagerImport> managerImports = new ArrayList<ManagerImport>();
if(contextFile.indexOf("*") == -1 && contextFile.indexOf("?") == -1)
{
ManagerImport managerimport = new ManagerImport();
managerimport.setFile(contextFile);
managerimport.setRealPath(SimpleStringUtil.getRealPath(absoluteParentPath, contextFile));
managerimport.setWebbased(docbaseImport.isWebBase());
managerImports.add(managerimport);
return managerImports;
}
else
{
if(docbaseImport.isClasspathBase())
throw new AssembleCallbackException("GetManagerImports("+docbaseType+
","+docbase+","+contextFile+"):classpath上下文环境中的配置文件不能通过*,?进行批量配置导入.");
}
File parent = new File(absoluteParentPath);
if(!parent.exists())
throw new AssembleCallbackException("GetManagerImports("+docbaseType+","+docbase+","+contextFile+")失败:"+absoluteParentPath + " do not exist.");
// String docContextFilePattern = StringUtil.getRealPath(docbase, contextFile);
String docContextFilePattern = contextFile;
FileFilter fileFilter = docbaseImport.isWebBase()?
new WebContextFileFilter(managerImports,absoluteParentPath,docContextFilePattern):
new ClassPathContextFileFilter(managerImports,absoluteParentPath,docContextFilePattern);
getSubFolderManagerImports( parent,fileFilter);
return managerImports;
}
private void getSubFolderManagerImports(File parent,FileFilter fileFilter)
{
File[] files = parent.listFiles(fileFilter);
for(int i = 0; files != null && i < files.length; i ++)
{
File file = files[i];
getSubFolderManagerImports(file,fileFilter);
}
}
public List<ManagerImport> getManagerImports(String docbaseType,String docbase,String contextFile) throws AssembleCallbackException
{
ManagerImport docbaseImport = new ManagerImport();
if(docbase != null)
{
if(docbaseType == null)
{
docbaseImport.setDocbase(docbase);
}
else if(docbase.startsWith(docbaseType))
docbaseImport.setDocbase(docbase);
else
{
docbaseImport.setDocbase(docbaseType + docbase);
}
}
docbaseImport.setFile(contextFile);
return getManagerImports(docbaseImport);
}
static class WebContextFileFilter implements java.io.FileFilter
{
private String absoluteParentPathPattern;
private String[] contextFilePattern;
private String absoluteParentPath;
private String absoluteWEBINFPath;
List<ManagerImport> managerImports;
private String[] ignoreDirs = new String[]{".svn","classes"};
private String[] includeDirs = new String[]{"WEB-INF"};
private String[] includeFiles = new String[]{".xml"};
WebContextFileFilter(List<ManagerImport> managerImports,String absoluteParentPath,String contextFilePattern)
{
this.absoluteParentPathPattern = absoluteParentPath.endsWith("/")?absoluteParentPath + "*":absoluteParentPath + "/*";
// this.contextFilePattern = contextFilePattern;
String[] patterns = contextFilePattern.split(",");
this.contextFilePattern = new String[patterns.length];
int i = 0;
for(String pattern:patterns)
{
if(pattern.trim().startsWith("/"))
this.contextFilePattern[i] = pattern.trim().substring(1);
else
this.contextFilePattern[i] = pattern.trim();
i ++;
}
this.absoluteParentPath = absoluteParentPath;
this.absoluteWEBINFPath = SimpleStringUtil.getRealPath(absoluteParentPath, "WEB-INF");
this.managerImports = managerImports;
}
public boolean accept(File pathname) {
if(contextFilePattern == null || contextFilePattern.length == 0)
return false;
String path = pathname.getAbsolutePath();
path = path.replace('\\', '/');
if(pathname.isDirectory())
{
if(!path.startsWith(this.absoluteWEBINFPath))
return false;
if(SimpleStringUtil.containKey(ignoreDirs, pathname.getName()))
return false;
return true;
}
else
{
if(!pathname.getName().endsWith(".xml"))
{
return false;
}
}
String subpath = pathMatcher.extractPathWithinPattern(absoluteParentPathPattern, path);
for(String pattern:contextFilePattern)
{
if(pathMatcher.match(pattern, subpath))
{
ManagerImport managerimport = new ManagerImport();
managerimport.setFile(subpath);
managerimport.setRealPath(SimpleStringUtil.getRealPath(absoluteParentPath, subpath));
managerimport.setWebbased(true);
managerImports.add(managerimport);
break;
}
}
return false;
}
}
static class ClassPathContextFileFilter implements java.io.FileFilter
{
private String absoluteParentPathPattern;
private String[] contextFilePattern;
private String absoluteParentPath;
private String absoluteWEBINFPath;
List<ManagerImport> managerImports;
private String[] ignoreDirs = new String[]{".svn","classes"};
private String[] includeDirs = new String[]{"WEB-INF"};
private String[] includeFiles = new String[]{".xml"};
ClassPathContextFileFilter(List<ManagerImport> managerImports,String absoluteParentPath,String contextFilePattern)
{
this.absoluteParentPathPattern = absoluteParentPath.endsWith("/")?absoluteParentPath + "*":absoluteParentPath + "/*";
// this.contextFilePattern = contextFilePattern;
String[] patterns = contextFilePattern.split(",");
this.contextFilePattern = new String[patterns.length];
int i = 0;
for(String pattern:patterns)
{
if(pattern.trim().startsWith("/"))
this.contextFilePattern[i] = pattern.trim().substring(1);
else
this.contextFilePattern[i] = pattern.trim();
i ++;
}
this.absoluteParentPath = absoluteParentPath;
this.absoluteWEBINFPath = SimpleStringUtil.getRealPath(absoluteParentPath, "WEB-INF");
this.managerImports = managerImports;
}
public boolean accept(File pathname) {
if(contextFilePattern == null || contextFilePattern.length == 0)
return false;
String path = pathname.getAbsolutePath();
path = path.replace('\\', '/');
if(pathname.isDirectory())
{
if(SimpleStringUtil.containKey(ignoreDirs, pathname.getName()))
return false;
return false;
}
else
{
if(!pathname.getName().endsWith(".xml"))
{
return false;
}
}
String subpath = pathMatcher.extractPathWithinPattern(absoluteParentPathPattern, path);
for(String pattern:contextFilePattern)
{
if(pathMatcher.match(pattern, subpath))
{
ManagerImport managerimport = new ManagerImport();
managerimport.setFile(subpath);
managerimport.setRealPath(SimpleStringUtil.getRealPath(absoluteParentPath, subpath));
managerimport.setWebbased(true);
managerImports.add(managerimport);
break;
}
}
return false;
}
}
}