1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.logging.log4j.core.pattern;
18
19 import org.apache.logging.log4j.core.LogEvent;
20 import org.apache.logging.log4j.core.config.plugins.Plugin;
21
22 import java.text.SimpleDateFormat;
23 import java.util.Date;
24 import java.util.TimeZone;
25
26
27
28
29
30 @Plugin(name = "DatePatternConverter", category = "Converter")
31 @ConverterKeys({"d", "date" })
32 public final class DatePatternConverter extends LogEventPatternConverter implements ArrayPatternConverter {
33
34
35
36
37 private static final String ABSOLUTE_FORMAT = "ABSOLUTE";
38
39
40
41
42 private static final String COMPACT_FORMAT = "COMPACT";
43
44
45
46
47 private static final String ABSOLUTE_TIME_PATTERN = "HH:mm:ss,SSS";
48
49
50
51
52 private static final String DATE_AND_TIME_FORMAT = "DATE";
53
54
55
56
57 private static final String DATE_AND_TIME_PATTERN = "dd MMM yyyy HH:mm:ss,SSS";
58
59
60
61
62 private static final String ISO8601_FORMAT = "ISO8601";
63
64
65
66
67 private static final String ISO8601_BASIC_FORMAT = "ISO8601_BASIC";
68
69
70
71
72 private static final String ISO8601_PATTERN = "yyyy-MM-dd HH:mm:ss,SSS";
73
74
75
76
77 private static final String ISO8601_BASIC_PATTERN = "yyyyMMdd HHmmss,SSS";
78
79
80
81
82 private static final String COMPACT_PATTERN = "yyyyMMddHHmmssSSS";
83
84
85
86
87 private String cachedDate;
88
89 private long lastTimestamp;
90
91 private final SimpleDateFormat simpleFormat;
92
93
94
95
96
97
98 private DatePatternConverter(final String[] options) {
99 super("Date", "date");
100
101 String patternOption;
102
103 if (options == null || options.length == 0) {
104
105
106 patternOption = null;
107 } else {
108 patternOption = options[0];
109 }
110
111 String pattern;
112
113 if (patternOption == null || patternOption.equalsIgnoreCase(ISO8601_FORMAT)) {
114 pattern = ISO8601_PATTERN;
115 } else if (patternOption.equalsIgnoreCase(ISO8601_BASIC_FORMAT)) {
116 pattern = ISO8601_BASIC_PATTERN;
117 } else if (patternOption.equalsIgnoreCase(ABSOLUTE_FORMAT)) {
118 pattern = ABSOLUTE_TIME_PATTERN;
119 } else if (patternOption.equalsIgnoreCase(DATE_AND_TIME_FORMAT)) {
120 pattern = DATE_AND_TIME_PATTERN;
121 } else if (patternOption.equalsIgnoreCase(COMPACT_FORMAT)) {
122 pattern = COMPACT_PATTERN;
123 } else {
124 pattern = patternOption;
125 }
126
127 SimpleDateFormat tempFormat;
128
129 try {
130 tempFormat = new SimpleDateFormat(pattern);
131 } catch (final IllegalArgumentException e) {
132 LOGGER.warn("Could not instantiate SimpleDateFormat with pattern " + patternOption, e);
133
134
135 tempFormat = new SimpleDateFormat(ISO8601_PATTERN);
136 }
137
138
139 if (options != null && options.length > 1) {
140 final TimeZone tz = TimeZone.getTimeZone(options[1]);
141 tempFormat.setTimeZone(tz);
142 }
143 simpleFormat = tempFormat;
144 }
145
146
147
148
149
150
151
152 public static DatePatternConverter newInstance(final String[] options) {
153 return new DatePatternConverter(options);
154 }
155
156
157
158
159 @Override
160 public void format(final LogEvent event, final StringBuilder output) {
161 final long timestamp = event.getMillis();
162
163 synchronized (this) {
164 if (timestamp != lastTimestamp) {
165 lastTimestamp = timestamp;
166 cachedDate = simpleFormat.format(timestamp);
167 }
168 }
169 output.append(cachedDate);
170 }
171
172 @Override
173 public void format(final StringBuilder toAppendTo, final Object... objects) {
174 for (final Object obj : objects) {
175 if (obj instanceof Date) {
176 format(obj, toAppendTo);
177 break;
178 }
179 }
180 }
181
182
183
184
185 @Override
186 public void format(final Object obj, final StringBuilder output) {
187 if (obj instanceof Date) {
188 format((Date) obj, output);
189 }
190
191 super.format(obj, output);
192 }
193
194
195
196
197
198
199
200 public void format(final Date date, final StringBuilder toAppendTo) {
201 synchronized (this) {
202 toAppendTo.append(simpleFormat.format(date.getTime()));
203 }
204 }
205
206 public String getPattern() {
207 return simpleFormat.toPattern();
208 }
209
210 }