1 package org.wings.resource; 2 3 import org.apache.commons.logging.Log; 4 import org.apache.commons.logging.LogFactory; 5 import org.wings.externalizer.ExternalizeManager; 6 7 import java.io.BufferedInputStream ; 8 import java.io.IOException ; 9 import java.io.InputStream ; 10 11 23 public class CssUrlFilterInputStream extends BufferedInputStream { 24 private final transient static Log log = LogFactory.getLog(CssUrlFilterInputStream.class); 25 26 private final static byte STATE_NONE = 0; 27 private final static byte STATE_U = 1; 28 private final static byte STATE_UR = 2; 29 private final static byte STATE_URL = 3; 30 private final static byte STATE_URL_DONE = 4; 31 private final static byte STATE_SUBST = 5; 32 private byte state = STATE_NONE; 33 34 private byte[] urlBuffer; 35 private int bufferPos; 36 37 42 private ExternalizeManager extManager; 43 44 49 public CssUrlFilterInputStream(InputStream in, ExternalizeManager extManager) { 50 super(in); 51 this.extManager = extManager; 52 } 53 54 57 public int read() throws IOException { 58 int result = 0; 59 if (state == STATE_SUBST) { 60 result = readFromUrlBuffer(); 61 } else { 62 result = super.read(); 63 if (result != -1) { 64 analyzeState(result); 65 if (state == STATE_URL_DONE) { 66 substitute(); 67 } 68 } 69 } 70 return result; 71 } 72 73 78 private void substitute() throws IOException { 79 StringBuffer classPathBuffer = new StringBuffer (); 80 int tempBuffer = super.read(); 81 while (tempBuffer != -1 && tempBuffer != ')') { 82 classPathBuffer.append((char)tempBuffer); 83 super.mark(2); 84 tempBuffer = super.read(); 85 } 86 super.reset(); 87 String classPath = strip(classPathBuffer.toString(), ' '); 88 classPath = strip(classPath, '\''); 89 classPath = strip(classPath, '"'); 90 String extension = null; 91 int dotIndex = classPath.lastIndexOf('.'); 92 if (dotIndex > -1) { 93 extension = classPath.substring(dotIndex + 1).toLowerCase(); 94 if ("jpg".equals(extension)) extension = "jpeg"; 95 96 } 97 bufferPos = 0; 98 urlBuffer = externalizeImage(classPath, "image/" + extension).getBytes(); 99 if (urlBuffer.length == 0) { 100 urlBuffer = classPathBuffer.toString().getBytes(); 102 } 103 state = STATE_SUBST; 104 } 105 106 111 private String externalizeImage(String classPath, String mimeType) { 112 ClasspathResource res = new ClasspathResource(classPath, mimeType); 113 if (res.getResourceStream() == null) { 114 log.debug("Could not find resource at classpath: " + classPath); 116 return ""; 117 } 118 StringBuffer imageUrl = new StringBuffer ("'"); 119 imageUrl.append(extManager.externalize(res, ExternalizeManager.GLOBAL)); 120 imageUrl.append("'"); 121 return imageUrl.toString(); 122 } 123 124 128 private int readFromUrlBuffer() { 129 int result = urlBuffer[bufferPos]; 130 bufferPos++; 131 if (bufferPos == urlBuffer.length) { 132 state = STATE_NONE; 133 } 134 return result; 135 } 136 137 140 public int read(byte[] b, int off, int len) throws IOException { 141 int i = 0; 142 for (i = off; i < (off+len);i++) { 143 byte tempByte = (byte)read(); 144 if (tempByte == -1) { 145 break; 146 } 147 b[i] = tempByte; 148 } 149 return i - off; 150 } 151 152 158 private String strip(String buffer, char character) { 159 if (buffer.charAt(0) == character) { 160 return strip(buffer.substring(1, buffer.length()), character); 161 } 162 if (buffer.charAt(buffer.length() - 1) == character) { 163 return strip(buffer.substring(0, buffer.length()-1), character); 164 } 165 return buffer; 166 } 167 168 171 public int read(byte[] b) throws IOException { 172 return read(b, 0, b.length); 173 } 174 175 180 private void analyzeState(int character) { 181 switch (character) { 182 case 'u': 183 if (state == STATE_NONE) { 184 state = STATE_U; 185 } else { 186 state = STATE_NONE; 187 } 188 break; 189 case 'r': 190 if (state == STATE_U) { 191 state = STATE_UR; 192 } else { 193 state = STATE_NONE; 194 } 195 break; 196 case 'l': 197 if (state == STATE_UR) { 198 state = STATE_URL; 199 } else { 200 state = STATE_NONE; 201 } 202 break; 203 case '(': 204 if (state == STATE_URL) { 205 state = STATE_URL_DONE; 206 } else { 207 state = STATE_NONE; 208 } 209 break; 210 default: 211 state = STATE_NONE; 212 break; 213 } 214 } 215 } 216 | Popular Tags |