最近业务方面需要基于openCMS做一功能扩展
场景:
目前公司已基本openCMS做了几个网站(二级频道或专区活动网站),都是静态页面,openCMS导出后随即发布CDN网站。
缺点:每个页面都是静态的HTML,内容的维护依赖于设计人员,维护成本太高,且不容易维护;
现在,由于公司网站的活动、专区、频道页越来越多,故提出新需要如下:
1、页面上的经常变动的数据将由运维人员在后台管理系统维护,由后台系统提供API以XML或JSON形式出数据;
2、openCMS需要加载外部系统的XML或JSON数据,用于模板或JSP页面的显示;
3、定时导出这些JSP或模板页面(即按一定的规则导出需要导出,那些图片/JS/CSS/HTML无需要定时导出)
实现 :
1、后台运维系统增加推荐信息管理模块,负责维护和提供数据;
2、为了能加载外部数据,开发了一个JSP taglib,以http方式提供API并把取合的XML或JSON解释成为JAVA数据对象,这样在JSP页面或模板面就可以通过C标签来显示数据了;开发的标签以openCMS module形式发布;
3、由于openCMS自带的导出功能是根据全局的导出规则来导出数据,而且改规则也很麻烦,改完还要重启,所以修改覆盖了org.opencms.scheduler.jobs.CmsStaticExportJob这个类,并增加了一个org.opencms.staticexport.CmsAfterPublishStaticExportHandler类(继承自org.opencms.staticexport.CmsAfterPublishStaticExportHandler);这两个类的class文件都部署自己开发的module中,这样opemCMS启动后就可以覆盖opemCMS自已的CmsStaticExportJob,这样以避免直接去改openCMS的源码。
以上就我实现方案,希望对有类似需要的朋友所有帮助!
代码:
CmsStaticExportJob类 ============================================
/**
* 1、覆盖org.opencms.scheduler.jobs.CmsStaticExportJob类,所以包名和类名都与opencms源码
* 中的CmsStaticExportJob类一样,目地在于不去修改opencms的源代码;
* 2、新的CmsStaticExportJob增加读取任务参数mode、rule1、rule2、rule3....ruleN,当mode="
http://www.5umaimai.com"时,调用doCustomExport()按
* 自定义的导出规则导出资源;
* 3、doCustomExport()方法是新加出来的,目地在于读取自定义的导出规则,并用UleCmsAfterPublishStaticExportHandler类来导出资源
* @author jack_wu
*
*/
public class CmsStaticExportJob implements I_CmsScheduledJob {
public String launch(CmsObject cms, Map parameters) throws Exception {
I_CmsReport report = null;
try {
report = new CmsLogReport(cms.getRequestContext().getLocale(), CmsStaticExportJob.class);
/*
* 判断是哪种模式,如果是自定义模式则调用doCustomExport()方法导出资源;
* 反之则调用openCMS自己原始的导出方法(根据全局导出规则导出全部的资源)
*/
String mode = (String)parameters.get("mode");
if("
http://www.5umaimai.com".equals(mode)){
doCustomExport(cms, report, parameters);
}else{
OpenCms.getStaticExportManager().exportFullStaticRender(true, report);
}
Map eventData = new HashMap();
eventData.put("purge", Boolean.TRUE);
eventData.put(I_CmsEventListener.KEY_REPORT, report);
OpenCms.fireCmsEvent(new CmsEvent(I_CmsEventListener.EVENT_FULLSTATIC_EXPORT, eventData));
} catch (CmsException e) {
if (report != null) {
report.println(e);
}
} catch (IOException e) {
if (report != null) {
report.println(e);
}
} catch (ServletException e) {
if (report != null) {
report.println(e);
}
} finally {
// append runtime statistics to the report
if (report != null) {
report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_STAT_0));
report.println(org.opencms.report.Messages.get().container(
org.opencms.report.Messages.RPT_STAT_DURATION_1,
report.formatRuntime()));
report.println(Messages.get().container(Messages.RPT_STATICEXPORT_END_0), I_CmsReport.FORMAT_HEADLINE);
}
}
return null;
}
/**
* 自定义的导出方法,根据设置导出计划时设置的导出规则导出资源
* @param cms
* @param report
* @param parameters
* @throws Exception
*/
private void doCustomExport(CmsObject cms, I_CmsReport report, Map parameters) throws Exception{
String ruleStr = null;
List<Pattern> patternList = new ArrayList();
int n=1;
while((ruleStr=(String)parameters.get("rule"+ n++)) != null){
patternList.add(Pattern.compile(ruleStr));
}
List vfsResources = cms.readResources("/", CmsResourceFilter.ALL.addExcludeFlags(CmsResource.FLAG_INTERNAL));
CmsExportFolderMatcher matcher = OpenCms.getStaticExportManager().getExportFolderMatcher();
List resList = new ArrayList(vfsResources.size());
Iterator i = vfsResources.iterator();
while (i.hasNext()) {
CmsResource resource = (CmsResource)i.next();
if(resource.isFolder()){
continue;
}
if (!matcher.match(resource.getRootPath())) {
continue;
}
CmsPublishedResource pubRes = new CmsPublishedResource(resource);
resList.add(pubRes);
}
// do the export
CmsAfterPublishStaticExportHandler handler = null;
// handler = new CmsAfterPublishStaticExportHandler();
handler = new UleCmsAfterPublishStaticExportHandler(patternList);
handler.doExportAfterPublish(resList, report);
if (report.hasError()) {
report.println(Messages.get().container(Messages.ERR_EXPORT_NOT_SUCCESSFUL_0), I_CmsReport.FORMAT_WARNING);
}
}
UleCmsAfterPublishStaticExportHandler类 ============================================
/**
* 继续至CmsAfterPublishStaticExportHandler,用于按自定义的匹配规则导出资源
* 修改思想:
* 1、构造时传入导出规则
* 2、重载getRelatedResources()方法,过滤掉不需要的资源
* getRelatedResources
* @author jack_wu
*
*/
public class UleCmsAfterPublishStaticExportHandler extends
CmsAfterPublishStaticExportHandler {
private static final Log log = LogFactory.getLog(UleCmsAfterPublishStaticExportHandler.class);
private List<Pattern> exportRules;
public UleCmsAfterPublishStaticExportHandler(List<Pattern> exportRules){
super();
this.exportRules = exportRules;
}
@Override
protected List getRelatedResources(CmsObject cms, List publishedResources) throws CmsException {
List ls = super.getRelatedResources(cms, publishedResources);
CmsPublishedResource resource = null;
String fullVFileName = null;
List needExportResourcdList = new ArrayList();
//根据自定义的导出规则,过滤掉不需要的资源
for(int i=0; i<publishedResources.size(); i++){
resource = (CmsPublishedResource)publishedResources.get(i);
fullVFileName = resource.getRootPath();
if(exportRules != null){
for(Pattern pattern:exportRules){
if(pattern.matcher(fullVFileName).matches()){
needExportResourcdList.add(resource);
break;
}
}
}
}
return needExportResourcdList;
}
}