001
014
015 package com.liferay.portal.aspectj;
016
017 import com.liferay.portal.kernel.io.unsync.UnsyncByteArrayOutputStream;
018 import com.liferay.portal.kernel.log.Log;
019 import com.liferay.portal.kernel.log.LogFactoryUtil;
020 import com.liferay.portal.kernel.util.StreamUtil;
021
022 import java.io.File;
023 import java.io.FileOutputStream;
024 import java.io.IOException;
025 import java.io.InputStream;
026
027 import java.net.URL;
028 import java.net.URLClassLoader;
029
030 import java.security.ProtectionDomain;
031
032 import java.util.Arrays;
033
034
037 public class WeavingClassLoader extends URLClassLoader {
038
039 public WeavingClassLoader(
040 URL[] urls, Class<?>[] aspectClasses, File dumpDir) {
041
042 super(urls, null);
043
044 _dumpDir = dumpDir;
045
046 _urlWeavingAdaptor = new URLWeavingAdaptor(urls, aspectClasses);
047 }
048
049 @Override
050 protected Class<?> findClass(String name) throws ClassNotFoundException {
051 String resourcePath = name.replace('.', '/') + ".class";
052
053 InputStream inputStream = getResourceAsStream(resourcePath);
054
055 byte[] data = null;
056
057 try {
058 if (inputStream == null) {
059
060
061
062 data = _urlWeavingAdaptor.removeGeneratedClassDate(name);
063 }
064 else {
065 UnsyncByteArrayOutputStream unsyncByteArrayOutputStream =
066 new UnsyncByteArrayOutputStream();
067
068 StreamUtil.transfer(
069 inputStream, unsyncByteArrayOutputStream, true);
070
071 data = unsyncByteArrayOutputStream.toByteArray();
072 }
073
074 if (data == null) {
075 throw new ClassNotFoundException(name);
076 }
077
078 byte[] oldData = data;
079
080 data = _urlWeavingAdaptor.weaveClass(name, data, false);
081
082 if (Arrays.equals(oldData, data)) {
083 return _generateClass(name, data);
084 }
085
086 if (_dumpDir != null) {
087 File dumpFile = new File(_dumpDir, resourcePath);
088
089 File dumpDir = dumpFile.getParentFile();
090
091 dumpDir.mkdirs();
092
093 FileOutputStream fileOutputStream =
094 new FileOutputStream(dumpFile);
095
096 fileOutputStream.write(data);
097
098 fileOutputStream.close();
099
100 if (_log.isInfoEnabled()) {
101 _log.info(
102 "Woven class " + name + " result in " +
103 dumpFile.getCanonicalPath());
104 }
105 }
106 else {
107 if (_log.isInfoEnabled()) {
108 _log.info("Woven class " + name);
109 }
110 }
111
112 return _generateClass(name, data);
113 }
114 catch (IOException ioe) {
115 throw new ClassNotFoundException(name, ioe);
116 }
117 }
118
119 private Class<?> _generateClass(String name, byte[] data) {
120 Class<?> clazz = defineClass(
121 name, data, 0, data.length, (ProtectionDomain)null);
122
123 String packageName = null;
124
125 int index = name.lastIndexOf('.');
126
127 if (index != -1) {
128 packageName = name.substring(0, index);
129 }
130
131 if (packageName != null) {
132 Package pkg = getPackage(packageName);
133
134 if (pkg == null) {
135 definePackage(
136 packageName, null, null, null, null, null, null, null);
137 }
138 }
139
140 return clazz;
141 }
142
143 private static Log _log = LogFactoryUtil.getLog(WeavingClassLoader.class);
144
145 private File _dumpDir;
146 private URLWeavingAdaptor _urlWeavingAdaptor;
147
148 }