1 29 30 package com.caucho.quercus.lib; 31 32 import com.caucho.quercus.env.*; 33 import com.caucho.util.URLUtil; 34 35 import java.lang.reflect.Method ; 36 import java.net.URI ; 37 import java.net.URISyntaxException ; 38 import java.util.ArrayList ; 39 import java.util.HashMap ; 40 41 45 public class UrlRewriterCallback extends CallbackFunction { 46 private StringBuilder _rewriterQuery = new StringBuilder (); 47 private ArrayList <String []> _rewriterVars = new ArrayList <String []>(); 48 49 public UrlRewriterCallback(Env env) 50 { 51 super(env, "URL-Rewriter"); 52 53 try { 54 Method rewriterMethod = 55 UrlRewriterCallback.class.getMethod("_internal_url_rewriter", 56 Env.class, String .class); 57 setFunction(new JavaMethod(env.getModuleContext(), rewriterMethod)); 58 } catch (NoSuchMethodException e) { 59 } catch (SecurityException e) { 60 } 61 } 62 63 66 public static UrlRewriterCallback getInstance(Env env) 67 { 68 OutputBuffer ob = env.getOutputBuffer(); 69 70 for (; ob != null; ob = ob.getNext()) { 71 Callback callback = ob.getCallback(); 72 73 if (callback instanceof UrlRewriterCallback) 74 return (UrlRewriterCallback)callback; 75 } 76 77 return null; 78 } 79 80 84 public void addRewriterVar(String var, String value) 85 { 86 if (_rewriterQuery.length() > 0) 87 _rewriterQuery.append("&"); 88 89 String encodedVar = URLUtil.encodeURL(var.replaceAll(" ", "+")); 90 String encodedValue = URLUtil.encodeURL(value.replaceAll(" ", "+")); 91 92 _rewriterQuery.append(encodedVar + "=" + encodedValue); 93 _rewriterVars.add(new String [] {encodedVar, encodedValue}); 94 } 95 96 100 public void resetRewriterVars() 101 { 102 _rewriterQuery = new StringBuilder (); 103 _rewriterVars.clear(); 104 } 105 106 109 public static Value _internal_url_rewriter(Env env, String buffer) 110 { 111 UrlRewriterCallback rewriter = getInstance(env); 112 113 if (rewriter == null) 116 return NullValue.NULL; 117 118 Parser parser = rewriter.new Parser(buffer, env); 119 return parser.parse(); 120 } 121 122 private class Parser { 123 private Env _env; 124 125 private boolean _includeSessionInfo = false; 126 private String _sessionName = null; 127 private String _sessionId = null; 128 private String _javaSessionName = null; 129 private String _javaSessionId = null; 130 131 private int _index; 132 private String _value; 133 private boolean _quoted; 134 135 private String _input; 136 private StringBuilderValue _output = new StringBuilderValue(); 137 138 public Parser(String input, Env env) 139 { 140 _input = input; 141 _env = env; 142 _index = 0; 143 } 144 145 public Value parse() 146 { 147 if (_env.getSession() != null && _env.getJavaSession() != null && 148 _env.getIni("session.use_trans_sid").toBoolean()) { 149 _includeSessionInfo = true; 150 151 _sessionName = _env.getIni("session.name").toString(); 152 _sessionId = _env.getSession().getId(); 153 154 _javaSessionName = _env.getQuercus().getCookieName(); 155 156 _javaSessionId = _env.getJavaSession().getId(); 157 } 158 159 if (_includeSessionInfo == false && _rewriterVars.isEmpty()) 160 return NullValue.NULL; 161 162 String [] tagPairs = 163 _env.getIni("url_rewriter.tags").toString().split(","); 164 HashMap <String ,String > tags = new HashMap <String ,String >(); 165 166 for (String tagPair : tagPairs) { 167 String [] tagAttribute = tagPair.split("="); 168 169 switch (tagAttribute.length) { 170 case 1: 171 tags.put(tagAttribute[0], null); 172 break; 173 174 case 2: 175 tags.put(tagAttribute[0], tagAttribute[1]); 176 break; 177 178 default: 179 break; 180 } 181 } 182 183 for (String tag = getNextTag(); tag != null; tag = getNextTag()) { 184 if (tags.containsKey(tag)) { 185 String attribute = tags.get(tag); 186 187 if (attribute == null) { 188 consumeToEndOfTag(); 189 190 if (_includeSessionInfo) { 191 String phpSessionInputTag = 192 "<input type=\"hidden\" name=\"" + _sessionName + "\"" + 193 " value=\"" + _sessionId + "\" />"; 194 195 _output.append(phpSessionInputTag ); 196 } 197 198 for (String [] entry : _rewriterVars) { 199 String inputTag = 200 "<input type=\"hidden\" name=\"" + entry[0] + "\"" + 201 " value=\"" + entry[1] + "\" />"; 202 _output.append(inputTag); 203 } 204 } else { 205 int valueEnd = 0; 206 207 for (valueEnd = getNextAttribute(attribute); 208 valueEnd == 0; 209 valueEnd = getNextAttribute(attribute)) 210 {} 211 212 if (valueEnd > 0) { 213 _output.append(rewriteUrl(_value)); 214 215 if (_quoted) 216 consumeOneCharacter(); 217 } 218 } 219 } 220 } 221 222 return _output; 223 } 224 225 228 private String getNextTag() 229 { 230 int tagStart = _input.indexOf('<', _index); 231 232 if (tagStart < 0) { 233 _output.append(_input.substring(_index)); 234 return null; 235 } 236 237 _output.append(_input.substring(_index, tagStart + 1)); 239 240 _index = tagStart + 1; 242 243 consumeNonWhiteSpace(); 244 245 return _input.substring(tagStart + 1, _index); 246 } 247 248 258 private int getNextAttribute(String attribute) 259 { 260 consumeWhiteSpace(); 261 262 int attributeStart = _index; 263 264 while (_index < _input.length() && 265 isValidAttributeCharacter(_input.charAt(_index))) 266 consumeOneCharacter(); 267 268 if (_index == attributeStart) 270 return -1; 271 272 String foundAttribute = _input.substring(attributeStart, _index); 273 274 consumeWhiteSpace(); 275 276 if (_input.length() <= _index || _input.charAt(_index) != '=') 278 return -1; 279 280 consumeOneCharacter(); 281 282 consumeWhiteSpace(); 283 284 char quote = ' '; 286 287 if (_input.charAt(_index) == '"' || _input.charAt(_index) == '\'') { 288 _quoted = true; 289 quote = _input.charAt(_index); 290 291 consumeOneCharacter(); 292 } 293 294 int valueEnd = _index; 295 296 if (_quoted) { 297 valueEnd = _input.indexOf(quote, _index); 298 299 int tagEnd = _input.indexOf('>', _index); 301 302 if (valueEnd < 0) { 303 if (tagEnd > 0) 304 valueEnd = tagEnd; 305 else 306 valueEnd = _input.length(); 307 } 308 } else { 309 for (valueEnd = _index; 311 valueEnd < _input.length() && 312 _input.charAt(valueEnd) != '/' && 313 _input.charAt(valueEnd) != '>' && 314 _input.charAt(valueEnd) != ' '; 315 valueEnd++) {} 316 } 317 318 if (foundAttribute.equals(attribute)) { 319 _value = _input.substring(_index, valueEnd); 320 321 _index = valueEnd; 322 323 return 1; 324 } else { 325 if (_quoted) 328 valueEnd += 1; 329 330 _output.append(_input.substring(_index, valueEnd)); 331 332 _index = valueEnd; 333 334 return 0; 335 } 336 } 337 338 private void consumeOneCharacter() 339 { 340 if (_index < _input.length()) { 341 _output.append(_input.charAt(_index)); 342 _index += 1; 343 } 344 } 345 346 private void consumeWhiteSpace() 347 { 348 while (_index < _input.length() && 349 Character.isWhitespace(_input.charAt(_index))) 350 consumeOneCharacter(); 351 } 352 353 private void consumeNonWhiteSpace() 354 { 355 while (_index < _input.length() && 356 !Character.isWhitespace(_input.charAt(_index))) 357 consumeOneCharacter(); 358 } 359 360 private void consumeToEndOfTag() 361 { 362 while (_input.charAt(_index) != '>') 363 consumeOneCharacter(); 364 365 consumeOneCharacter(); 367 } 368 369 private boolean isValidAttributeCharacter(char ch) 370 { 371 return Character.isLetterOrDigit(ch) || 372 (ch == '-') || (ch == '.') || (ch == '_') || (ch == ':'); 373 } 374 375 private String rewriteUrl(String urlString) 376 { 377 386 URI uri; 387 388 try { 389 uri = new URI (urlString); 390 } catch (URISyntaxException e) { 391 return urlString; 392 } 393 394 if ((uri.getScheme() != null) || (uri.getAuthority() != null)) { 395 return urlString; 396 } 397 398 StringBuilder query = new StringBuilder (); 399 400 if (uri.getQuery() != null) { 401 query.append("?"); 402 query.append(uri.getQuery()); 403 query.append("&"); 404 } 405 else 406 query.append("?"); 407 408 if (_includeSessionInfo) { 409 query.append(_sessionName); 410 query.append("="); 411 query.append(_sessionId); 412 } 413 414 if (_rewriterQuery.length() != 0) { 415 if (_includeSessionInfo) 416 query.append("&"); 417 418 query.append(_rewriterQuery); 419 } 420 421 StringBuilder newUri = new StringBuilder (); 422 423 if (uri.getPath() != null) 424 newUri.append(uri.getPath()); 425 426 newUri.append(query); 427 428 if (uri.getFragment() != null) { 429 newUri.append("#"); 430 newUri.append(uri.getFragment()); 431 } 432 433 return newUri.toString(); 434 } 435 } 436 } 437 | Popular Tags |