001 /**
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements. See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License. You may obtain a copy of the License at
008 *
009 * http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017 package org.apache.camel.util;
018
019 import java.io.UnsupportedEncodingException;
020 import java.util.BitSet;
021
022 import org.apache.commons.logging.Log;
023 import org.apache.commons.logging.LogFactory;
024
025
026 public final class UnsafeUriCharactersEncoder {
027 static BitSet unsafeCharacters;
028 private static final transient Log LOG = LogFactory.getLog(UnsafeUriCharactersEncoder.class);
029 private static final char[] HEX_DIGITS = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C',
030 'D', 'E', 'F'};
031
032 static {
033 unsafeCharacters = new BitSet(256);
034 unsafeCharacters.set(' ');
035 unsafeCharacters.set('"');
036 unsafeCharacters.set('<');
037 unsafeCharacters.set('>');
038 unsafeCharacters.set('#');
039 unsafeCharacters.set('%');
040 unsafeCharacters.set('{');
041 unsafeCharacters.set('}');
042 unsafeCharacters.set('|');
043 unsafeCharacters.set('\\');
044 unsafeCharacters.set('^');
045 unsafeCharacters.set('~');
046 unsafeCharacters.set('[');
047 unsafeCharacters.set(']');
048 unsafeCharacters.set('`');
049 }
050
051
052 private UnsafeUriCharactersEncoder() {
053 // util class
054 }
055
056 public static String encode(String s) {
057 int n = s.length();
058 if (n == 0) {
059 return s;
060 }
061
062 // First check whether we actually need to encode
063
064 try {
065 byte[] bytes = s.getBytes("UTF8");
066 for (int i = 0;;) {
067 if (unsafeCharacters.get(bytes[i])) {
068 break;
069 }
070 if (++i >= bytes.length) {
071 return s;
072 }
073 }
074
075 StringBuffer sb = new StringBuffer();
076 for (byte b : bytes) {
077 if (unsafeCharacters.get(b)) {
078 appendEscape(sb, (byte)b);
079 } else {
080 sb.append((char)b);
081 }
082 }
083 return sb.toString();
084 } catch (UnsupportedEncodingException e) {
085 LOG.error("Can't encoding the uri: ", e);
086 return null;
087 }
088 }
089
090 private static void appendEscape(StringBuffer sb, byte b) {
091 sb.append('%');
092 sb.append(HEX_DIGITS[(b >> 4) & 0x0f]);
093 sb.append(HEX_DIGITS[(b >> 0) & 0x0f]);
094 }
095
096 }