Skip to content

Commit b3e8583

Browse files
committed
Update FormatModifer.
1 parent 328a11f commit b3e8583

File tree

6 files changed

+113
-158
lines changed

6 files changed

+113
-158
lines changed

.idea/inspectionProfiles/Project_Default.xml

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

httprpc-server/src/main/java/org/httprpc/io/TemplateEncoder.java

Lines changed: 104 additions & 125 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
import java.time.LocalTime;
3636
import java.time.format.DateTimeFormatter;
3737
import java.time.format.FormatStyle;
38+
import java.time.temporal.TemporalAccessor;
3839
import java.util.AbstractMap;
3940
import java.util.ArrayList;
4041
import java.util.HashMap;
@@ -99,6 +100,12 @@ private static class FormatModifier implements Modifier {
99100
static final String LONG_DATE_TIME = "longDateTime";
100101
static final String FULL_DATE_TIME = "fullDateTime";
101102

103+
enum DateTimeType {
104+
DATE,
105+
TIME,
106+
DATE_TIME
107+
}
108+
102109
@Override
103110
public Object apply(Object value, String argument, Locale locale, TimeZone timeZone) {
104111
if (argument == null) {
@@ -114,145 +121,52 @@ public Object apply(Object value, String argument, Locale locale, TimeZone timeZ
114121
return NumberFormat.getPercentInstance(locale).format(value);
115122
}
116123

117-
case SHORT_DATE:
118-
case MEDIUM_DATE:
119-
case LONG_DATE:
120-
case FULL_DATE: {
121-
if (value instanceof String) {
122-
value = LocalDate.parse((String)value);
123-
}
124-
125-
switch (argument) {
126-
case SHORT_DATE: {
127-
if (value instanceof LocalDate) {
128-
return ((LocalDate)value).format(DateTimeFormatter.ofLocalizedDate(FormatStyle.SHORT).withLocale(locale));
129-
} else {
130-
return getDateInstance(DateFormat.SHORT, locale, timeZone).format(value);
131-
}
132-
}
124+
case SHORT_DATE: {
125+
return format(value, FormatStyle.SHORT, DateTimeType.DATE, locale, timeZone);
126+
}
133127

134-
case MEDIUM_DATE: {
135-
if (value instanceof LocalDate) {
136-
return ((LocalDate)value).format(DateTimeFormatter.ofLocalizedDate(FormatStyle.MEDIUM).withLocale(locale));
137-
} else {
138-
return getDateInstance(DateFormat.MEDIUM, locale, timeZone).format(value);
139-
}
140-
}
128+
case MEDIUM_DATE: {
129+
return format(value, FormatStyle.MEDIUM, DateTimeType.DATE, locale, timeZone);
130+
}
141131

142-
case LONG_DATE: {
143-
if (value instanceof LocalDate) {
144-
return ((LocalDate)value).format(DateTimeFormatter.ofLocalizedDate(FormatStyle.LONG).withLocale(locale));
145-
} else {
146-
return getDateInstance(DateFormat.LONG, locale, timeZone).format(value);
147-
}
148-
}
132+
case LONG_DATE: {
133+
return format(value, FormatStyle.LONG, DateTimeType.DATE, locale, timeZone);
134+
}
149135

150-
case FULL_DATE: {
151-
if (value instanceof LocalDate) {
152-
return ((LocalDate)value).format(DateTimeFormatter.ofLocalizedDate(FormatStyle.FULL).withLocale(locale));
153-
} else {
154-
return getDateInstance(DateFormat.FULL, locale, timeZone).format(value);
155-
}
156-
}
136+
case FULL_DATE: {
137+
return format(value, FormatStyle.FULL, DateTimeType.DATE, locale, timeZone);
138+
}
157139

158-
default: {
159-
throw new UnsupportedOperationException();
160-
}
161-
}
140+
case SHORT_TIME: {
141+
return format(value, FormatStyle.SHORT, DateTimeType.TIME, locale, timeZone);
162142
}
163143

164-
case SHORT_TIME:
165-
case MEDIUM_TIME:
166-
case LONG_TIME:
167-
case FULL_TIME: {
168-
if (value instanceof String) {
169-
value = LocalTime.parse((String)value);
170-
}
144+
case MEDIUM_TIME: {
145+
return format(value, FormatStyle.MEDIUM, DateTimeType.TIME, locale, timeZone);
146+
}
171147

172-
switch (argument) {
173-
case SHORT_TIME: {
174-
if (value instanceof LocalTime) {
175-
return ((LocalTime)value).format(DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT).withLocale(locale));
176-
} else {
177-
return getTimeInstance(DateFormat.SHORT, locale, timeZone).format(value);
178-
}
179-
}
148+
case LONG_TIME: {
149+
return format(value, FormatStyle.LONG, DateTimeType.TIME, locale, timeZone);
150+
}
180151

181-
case MEDIUM_TIME: {
182-
if (value instanceof LocalTime) {
183-
return ((LocalTime)value).format(DateTimeFormatter.ofLocalizedTime(FormatStyle.MEDIUM).withLocale(locale));
184-
} else {
185-
return getTimeInstance(DateFormat.MEDIUM, locale, timeZone).format(value);
186-
}
187-
}
152+
case FULL_TIME: {
153+
return format(value, FormatStyle.FULL, DateTimeType.TIME, locale, timeZone);
154+
}
188155

189-
case LONG_TIME: {
190-
if (value instanceof LocalTime) {
191-
return ((LocalTime)value).format(DateTimeFormatter.ofLocalizedTime(FormatStyle.LONG).withLocale(locale));
192-
} else {
193-
return getTimeInstance(DateFormat.LONG, locale, timeZone).format(value);
194-
}
195-
}
156+
case SHORT_DATE_TIME: {
157+
return format(value, FormatStyle.SHORT, DateTimeType.DATE_TIME, locale, timeZone);
158+
}
196159

197-
case FULL_TIME: {
198-
if (value instanceof LocalTime) {
199-
return ((LocalTime)value).format(DateTimeFormatter.ofLocalizedTime(FormatStyle.FULL).withLocale(locale));
200-
} else {
201-
return getTimeInstance(DateFormat.FULL, locale, timeZone).format(value);
202-
}
203-
}
160+
case MEDIUM_DATE_TIME: {
161+
return format(value, FormatStyle.MEDIUM, DateTimeType.DATE_TIME, locale, timeZone);
162+
}
204163

205-
default: {
206-
throw new UnsupportedOperationException();
207-
}
208-
}
164+
case LONG_DATE_TIME: {
165+
return format(value, FormatStyle.LONG, DateTimeType.DATE_TIME, locale, timeZone);
209166
}
210167

211-
case SHORT_DATE_TIME:
212-
case MEDIUM_DATE_TIME:
213-
case LONG_DATE_TIME:
214168
case FULL_DATE_TIME: {
215-
if (value instanceof String) {
216-
value = LocalDateTime.parse((String)value);
217-
}
218-
219-
switch (argument) {
220-
case SHORT_DATE_TIME: {
221-
if (value instanceof LocalDateTime) {
222-
return ((LocalDateTime)value).format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.SHORT).withLocale(locale));
223-
} else {
224-
return getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT, locale, timeZone).format(value);
225-
}
226-
}
227-
228-
case MEDIUM_DATE_TIME: {
229-
if (value instanceof LocalDateTime) {
230-
return ((LocalDateTime)value).format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.MEDIUM).withLocale(locale));
231-
} else {
232-
return getDateTimeInstance(DateFormat.MEDIUM, DateFormat.MEDIUM, locale, timeZone).format(value);
233-
}
234-
}
235-
236-
case LONG_DATE_TIME: {
237-
if (value instanceof LocalDateTime) {
238-
return ((LocalDateTime)value).format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.LONG).withLocale(locale));
239-
} else {
240-
return getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale, timeZone).format(value);
241-
}
242-
}
243-
244-
case FULL_DATE_TIME: {
245-
if (value instanceof LocalDateTime) {
246-
return ((LocalDateTime)value).format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.FULL).withLocale(locale));
247-
} else {
248-
return getDateTimeInstance(DateFormat.FULL, DateFormat.FULL, locale, timeZone).format(value);
249-
}
250-
}
251-
252-
default: {
253-
throw new UnsupportedOperationException();
254-
}
255-
}
169+
return format(value, FormatStyle.FULL, DateTimeType.DATE_TIME, locale, timeZone);
256170
}
257171

258172
default: {
@@ -284,6 +198,71 @@ static DateFormat getDateTimeInstance(int dateStyle, int timeStyle, Locale local
284198

285199
return dateFormat;
286200
}
201+
202+
static String format(Object value, FormatStyle formatStyle, DateTimeType dateTimeType, Locale locale, TimeZone timeZone) {
203+
if (value instanceof TemporalAccessor) {
204+
TemporalAccessor temporalAccessor = (TemporalAccessor)value;
205+
206+
switch (dateTimeType) {
207+
case DATE: {
208+
return DateTimeFormatter.ofLocalizedDate(formatStyle).withLocale(locale).format(temporalAccessor);
209+
}
210+
211+
case TIME: {
212+
return DateTimeFormatter.ofLocalizedTime(formatStyle).withLocale(locale).format(temporalAccessor);
213+
}
214+
215+
case DATE_TIME: {
216+
return DateTimeFormatter.ofLocalizedDateTime(formatStyle).withLocale(locale).format(temporalAccessor);
217+
}
218+
219+
default: {
220+
throw new UnsupportedOperationException();
221+
}
222+
}
223+
} else {
224+
int style;
225+
switch (formatStyle) {
226+
case FULL:
227+
style = DateFormat.FULL;
228+
break;
229+
230+
case LONG:
231+
style = DateFormat.LONG;
232+
break;
233+
234+
case MEDIUM:
235+
style = DateFormat.MEDIUM;
236+
break;
237+
238+
case SHORT:
239+
style = DateFormat.SHORT;
240+
break;
241+
242+
default: {
243+
throw new UnsupportedOperationException();
244+
}
245+
}
246+
247+
switch (dateTimeType) {
248+
case DATE: {
249+
return getDateInstance(style, locale, timeZone).format(value);
250+
}
251+
252+
case TIME: {
253+
return getTimeInstance(style, locale, timeZone).format(value);
254+
}
255+
256+
case DATE_TIME: {
257+
return getDateTimeInstance(style, style, locale, timeZone).format(value);
258+
}
259+
260+
default: {
261+
throw new UnsupportedOperationException();
262+
}
263+
}
264+
}
265+
}
287266
}
288267

289268
// URL escape modifier

httprpc-server/src/test/java/org/httprpc/io/TemplateEncoderTest.java

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -266,22 +266,16 @@ public void testDateFormatModifiers() throws IOException {
266266
entry("date", date),
267267
entry("dateInMilliseconds", date.getTime()),
268268
entry("localDate", localDate),
269-
entry("localDateAsString", localDate.toString()),
270269
entry("localTime", localTime),
271-
entry("localTimeAsString", localTime.toString()),
272-
entry("localDateTime", localDateTime),
273-
entry("localDateTimeAsString", localDateTime.toString())
270+
entry("localDateTime", localDateTime)
274271
), writer);
275272
result = writer.toString();
276273
}
277274

278275
assertEquals(DateFormat.getDateInstance(DateFormat.SHORT).format(date) + ",\n"
279276
+ DateFormat.getDateInstance(DateFormat.SHORT).format(date) + ",\n"
280277
+ localDate.format(DateTimeFormatter.ofLocalizedDate(FormatStyle.SHORT)) + ",\n"
281-
+ localDate.format(DateTimeFormatter.ofLocalizedDate(FormatStyle.SHORT)) + ",\n"
282-
+ localTime.format(DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT)) + ",\n"
283278
+ localTime.format(DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT)) + ",\n"
284-
+ localDateTime.format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.SHORT)) + ",\n"
285279
+ localDateTime.format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.SHORT)), result);
286280
}
287281

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,5 @@
11
{{date:format=shortDate}},
22
{{dateInMilliseconds:format=shortDate}},
33
{{localDate:format=shortDate}},
4-
{{localDateAsString:format=shortDate}},
54
{{localTime:format=shortTime}},
6-
{{localTimeAsString:format=shortTime}},
7-
{{localDateTime:format=shortDateTime}},
8-
{{localDateTimeAsString:format=shortDateTime}}
5+
{{localDateTime:format=shortDateTime}}

httprpc-server/src/test/resources/org/httprpc/io/format3.txt

Lines changed: 0 additions & 1 deletion
This file was deleted.

template-reference.md

Lines changed: 6 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -56,9 +56,9 @@ Applications may also define their own custom modifiers.
5656
#### Locale-Specific Formatting
5757
In addition to `printf()`-style formatting, the `format` modifier also supports the following arguments for locale-specific formatting of numbers and dates:
5858

59-
* `currency` - applies currency format
60-
* `percent` - applies percentage format
61-
* `shortDate` - applies short date format
59+
* `currency` - applies a currency format
60+
* `percent` - applies a percentage format
61+
* `shortDate` - applies a short date format
6262
* `mediumDate` - applies a medium date format
6363
* `longDate` - applies a long date format
6464
* `fullDate` - applies a full date format
@@ -77,26 +77,11 @@ For example, this marker transforms a date value into a localized medium-length
7777
{{date:format=mediumDate}}
7878
```
7979

80-
Date values may be represented by one of the following:
81-
82-
* an instance of `java.util.Date`
83-
* a `long` value representing epoch time in milliseconds
84-
* an instance of `java.util.time.LocalDate`
85-
* a string of the format `yyy-mm-dd`
86-
87-
Time values may be represented by one of the following:
88-
89-
* an instance of `java.util.Date`
90-
* a `long` value representing epoch time in milliseconds
91-
* an instance of `java.util.time.LocalTime`
92-
* a string of the format `hh:mm[:ss]`
93-
9480
Date/time values may be represented by one of the following:
9581

96-
* an instance of `java.util.Date`
97-
* a `long` value representing epoch time
98-
* an instance of `java.util.time.LocalDateTime`
99-
* a string of the format `yyy-mm-ddThh:mm[:ss]`
82+
* a `long` value representing epoch time in milliseconds
83+
* an instance of `java.util.Date`
84+
* an instance of `java.util.time.TemporalAccessor`
10085

10186
## Section Markers
10287
Section markers define a repeating section of content. The marker name must refer to an iterable value in the data dictionary (for example, an instance of `java.util.List`).

0 commit comments

Comments
 (0)