1
2
3
4
5
6
7
8
9
10
11
12
13
14 package ch.qos.logback.core.helpers;
15
16 import java.util.regex.Pattern;
17
18
19
20
21
22
23
24 public class Transform {
25 private static final String CDATA_START = "<![CDATA[";
26 private static final String CDATA_END = "]]>";
27 private static final String CDATA_PSEUDO_END = "]]>";
28 private static final String CDATA_EMBEDED_END = CDATA_END + CDATA_PSEUDO_END + CDATA_START;
29 private static final int CDATA_END_LEN = CDATA_END.length();
30 private static final Pattern UNSAFE_XML_CHARS = Pattern.compile("[\u0000-\u0008\u000b\u000c\u000e-\u001f<>&'\"]");
31
32
33
34
35
36
37
38
39 public static String escapeTags(final String input) {
40 if (input == null || input.length() == 0 || !UNSAFE_XML_CHARS.matcher(input).find()) {
41 return input;
42 }
43 StringBuffer buf = new StringBuffer(input);
44 return escapeTags(buf);
45 }
46
47
48
49
50
51
52
53
54
55 public static String escapeTags(final StringBuffer buf) {
56 for (int i = 0; i < buf.length(); i++) {
57 char ch = buf.charAt(i);
58 switch (ch) {
59 case '\t':
60 case '\n':
61 case '\r':
62
63 break;
64 case '&':
65 buf.replace(i, i + 1, "&");
66 break;
67 case '<':
68 buf.replace(i, i + 1, "<");
69 break;
70 case '>':
71 buf.replace(i, i + 1, ">");
72 break;
73 case '"':
74 buf.replace(i, i + 1, """);
75 break;
76 case '\'':
77 buf.replace(i, i + 1, "'");
78 break;
79 default:
80 if (ch < '\u0020') {
81
82
83 buf.replace(i, i + 1, "\uFFFD");
84 }
85 break;
86 }
87 }
88 return buf.toString();
89 }
90
91
92
93
94
95
96
97
98
99
100
101 public static void appendEscapingCDATA(StringBuilder output, String str) {
102 if (str == null) {
103 return;
104 }
105
106 int end = str.indexOf(CDATA_END);
107
108 if (end < 0) {
109 output.append(str);
110
111 return;
112 }
113
114 int start = 0;
115
116 while (end > -1) {
117 output.append(str.substring(start, end));
118 output.append(CDATA_EMBEDED_END);
119 start = end + CDATA_END_LEN;
120
121 if (start < str.length()) {
122 end = str.indexOf(CDATA_END, start);
123 } else {
124 return;
125 }
126 }
127
128 output.append(str.substring(start));
129 }
130 }