001
014
015 package com.liferay.util.freemarker;
016
017 import com.liferay.portal.kernel.cache.CacheRegistryItem;
018 import com.liferay.portal.kernel.cache.CacheRegistryUtil;
019 import com.liferay.portal.kernel.memory.FinalizeAction;
020 import com.liferay.portal.kernel.memory.FinalizeManager;
021 import com.liferay.portal.kernel.util.ContextPathUtil;
022
023 import freemarker.ext.jsp.TaglibFactory;
024
025 import freemarker.template.TemplateHashModel;
026 import freemarker.template.TemplateModel;
027 import freemarker.template.TemplateModelException;
028
029 import java.util.Map;
030 import java.util.concurrent.ConcurrentHashMap;
031
032 import javax.servlet.ServletContext;
033
034 import jodd.util.StringPool;
035
036
039 public class FreeMarkerTaglibFactoryUtil implements CacheRegistryItem {
040
041 public static TemplateHashModel createTaglibFactory(
042 ServletContext servletContext) {
043
044 return new TaglibFactoryCacheWrapper(servletContext);
045 }
046
047 public String getRegistryName() {
048 return _registryName;
049 }
050
051 public void invalidate() {
052 _templateModels.clear();
053 }
054
055 private static FreeMarkerTaglibFactoryUtil _getInstance(
056 ServletContext servletContext) {
057
058 if (_instance == null) {
059 synchronized(FreeMarkerTaglibFactoryUtil.class) {
060 if (_instance == null) {
061 String contextPath = ContextPathUtil.getContextPath(
062 servletContext);
063
064
065
066 _instance = new FreeMarkerTaglibFactoryUtil(contextPath);
067
068
069
070
071 CacheRegistryUtil.unregister(_instance._registryName);
072
073
074
075 CacheRegistryUtil.register(_instance);
076
077
078
079
080 final String name = _instance._registryName;
081
082
083
084
085 FinalizeManager.register(
086 servletContext,
087 new FinalizeAction() {
088
089 public void doFinalize() {
090 CacheRegistryUtil.unregister(name);
091 }
092
093 });
094 }
095 }
096 }
097
098 return _instance;
099 }
100
101 private FreeMarkerTaglibFactoryUtil(String contextPath) {
102 _contextPath = contextPath;
103 _registryName = FreeMarkerTaglibFactoryUtil.class.getName().concat(
104 StringPool.AT).concat(_contextPath);
105 }
106
107 private static volatile FreeMarkerTaglibFactoryUtil _instance;
108
109 private final String _contextPath;
110 private final String _registryName;
111 private Map<String, TemplateModel> _templateModels =
112 new ConcurrentHashMap<String, TemplateModel>();
113
114 private static class TaglibFactoryCacheWrapper
115 implements TemplateHashModel {
116
117 public TaglibFactoryCacheWrapper(ServletContext servletContext) {
118 FreeMarkerTaglibFactoryUtil freeMarkerTaglibFactoryUtil =
119 _getInstance(servletContext);
120
121 _templateModels = freeMarkerTaglibFactoryUtil._templateModels;
122 _taglibFactory = new TaglibFactory(servletContext);
123 }
124
125 public TemplateModel get(String uri) throws TemplateModelException {
126 TemplateModel templateModel = _templateModels.get(uri);
127
128 if (templateModel == null) {
129 templateModel = _taglibFactory.get(uri);
130
131 _templateModels.put(uri, templateModel);
132 }
133
134 return templateModel;
135 }
136
137 public boolean isEmpty() {
138 return false;
139 }
140
141 private TaglibFactory _taglibFactory;
142 private Map<String, TemplateModel> _templateModels;
143
144 }
145
146 }