Fix date format in warning headers
This commit fixes the date format in warning headers. There is some confusion around whether or not RFC 1123 requires two-digit days. However, the warning header specification very clearly relies on a format that requires two-digit days. This commit removes the usage of RFC 1123 date/time format from Java 8, which allows for one-digit days, in favor of a format that forces two-digit days (it's otherwise identical to RFC 1123 format, it is just fixed width). Relates #23418
This commit is contained in:
parent
ee2f6ccf32
commit
7ce06aeb8c
|
@ -29,14 +29,26 @@ import org.elasticsearch.common.util.concurrent.ThreadContext;
|
||||||
import java.time.ZoneId;
|
import java.time.ZoneId;
|
||||||
import java.time.ZonedDateTime;
|
import java.time.ZonedDateTime;
|
||||||
import java.time.format.DateTimeFormatter;
|
import java.time.format.DateTimeFormatter;
|
||||||
|
import java.time.format.DateTimeFormatterBuilder;
|
||||||
|
import java.time.format.SignStyle;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.concurrent.CopyOnWriteArraySet;
|
import java.util.concurrent.CopyOnWriteArraySet;
|
||||||
import java.util.regex.Matcher;
|
import java.util.regex.Matcher;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
|
|
||||||
|
import static java.time.temporal.ChronoField.DAY_OF_MONTH;
|
||||||
|
import static java.time.temporal.ChronoField.DAY_OF_WEEK;
|
||||||
|
import static java.time.temporal.ChronoField.HOUR_OF_DAY;
|
||||||
|
import static java.time.temporal.ChronoField.MINUTE_OF_HOUR;
|
||||||
|
import static java.time.temporal.ChronoField.MONTH_OF_YEAR;
|
||||||
|
import static java.time.temporal.ChronoField.SECOND_OF_MINUTE;
|
||||||
|
import static java.time.temporal.ChronoField.YEAR;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A logger that logs deprecation notices.
|
* A logger that logs deprecation notices.
|
||||||
*/
|
*/
|
||||||
|
@ -128,6 +140,63 @@ public class DeprecationLogger {
|
||||||
Build.CURRENT.shortHash()) +
|
Build.CURRENT.shortHash()) +
|
||||||
"\"%s\" \"%s\"";
|
"\"%s\" \"%s\"";
|
||||||
|
|
||||||
|
/*
|
||||||
|
* RFC 7234 section 5.5 specifies that the warn-date is a quoted HTTP-date. HTTP-date is defined in RFC 7234 Appendix B as being from
|
||||||
|
* RFC 7231 section 7.1.1.1. RFC 7231 specifies an HTTP-date as an IMF-fixdate (or an obs-date referring to obsolete formats). The
|
||||||
|
* grammar for IMF-fixdate is specified as 'day-name "," SP date1 SP time-of-day SP GMT'. Here, day-name is
|
||||||
|
* (Mon|Tue|Wed|Thu|Fri|Sat|Sun). Then, date1 is 'day SP month SP year' where day is 2DIGIT, month is
|
||||||
|
* (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec), and year is 4DIGIT. Lastly, time-of-day is 'hour ":" minute ":" second' where
|
||||||
|
* hour is 2DIGIT, minute is 2DIGIT, and second is 2DIGIT. Finally, 2DIGIT and 4DIGIT have the obvious definitions.
|
||||||
|
*/
|
||||||
|
private static final DateTimeFormatter RFC_7231_DATE_TIME;
|
||||||
|
|
||||||
|
static {
|
||||||
|
final Map<Long, String> dow = new HashMap<>();
|
||||||
|
dow.put(1L, "Mon");
|
||||||
|
dow.put(2L, "Tue");
|
||||||
|
dow.put(3L, "Wed");
|
||||||
|
dow.put(4L, "Thu");
|
||||||
|
dow.put(5L, "Fri");
|
||||||
|
dow.put(6L, "Sat");
|
||||||
|
dow.put(7L, "Sun");
|
||||||
|
final Map<Long, String> moy = new HashMap<>();
|
||||||
|
moy.put(1L, "Jan");
|
||||||
|
moy.put(2L, "Feb");
|
||||||
|
moy.put(3L, "Mar");
|
||||||
|
moy.put(4L, "Apr");
|
||||||
|
moy.put(5L, "May");
|
||||||
|
moy.put(6L, "Jun");
|
||||||
|
moy.put(7L, "Jul");
|
||||||
|
moy.put(8L, "Aug");
|
||||||
|
moy.put(9L, "Sep");
|
||||||
|
moy.put(10L, "Oct");
|
||||||
|
moy.put(11L, "Nov");
|
||||||
|
moy.put(12L, "Dec");
|
||||||
|
RFC_7231_DATE_TIME = new DateTimeFormatterBuilder()
|
||||||
|
.parseCaseInsensitive()
|
||||||
|
.parseLenient()
|
||||||
|
.optionalStart()
|
||||||
|
.appendText(DAY_OF_WEEK, dow)
|
||||||
|
.appendLiteral(", ")
|
||||||
|
.optionalEnd()
|
||||||
|
.appendValue(DAY_OF_MONTH, 2, 2, SignStyle.NOT_NEGATIVE)
|
||||||
|
.appendLiteral(' ')
|
||||||
|
.appendText(MONTH_OF_YEAR, moy)
|
||||||
|
.appendLiteral(' ')
|
||||||
|
.appendValue(YEAR, 4)
|
||||||
|
.appendLiteral(' ')
|
||||||
|
.appendValue(HOUR_OF_DAY, 2)
|
||||||
|
.appendLiteral(':')
|
||||||
|
.appendValue(MINUTE_OF_HOUR, 2)
|
||||||
|
.optionalStart()
|
||||||
|
.appendLiteral(':')
|
||||||
|
.appendValue(SECOND_OF_MINUTE, 2)
|
||||||
|
.optionalEnd()
|
||||||
|
.appendLiteral(' ')
|
||||||
|
.appendOffset("+HHMM", "GMT")
|
||||||
|
.toFormatter(Locale.getDefault(Locale.Category.FORMAT));
|
||||||
|
}
|
||||||
|
|
||||||
private static final ZoneId GMT = ZoneId.of("GMT");
|
private static final ZoneId GMT = ZoneId.of("GMT");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -195,13 +264,13 @@ public class DeprecationLogger {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Format a warning string in the proper warning format by prepending a warn code, warn agent, wrapping the warning string in quotes,
|
* Format a warning string in the proper warning format by prepending a warn code, warn agent, wrapping the warning string in quotes,
|
||||||
* and appending the RFC 1123 date.
|
* and appending the RFC 7231 date.
|
||||||
*
|
*
|
||||||
* @param s the warning string to format
|
* @param s the warning string to format
|
||||||
* @return a warning value formatted according to RFC 7234
|
* @return a warning value formatted according to RFC 7234
|
||||||
*/
|
*/
|
||||||
public static String formatWarning(final String s) {
|
public static String formatWarning(final String s) {
|
||||||
return String.format(Locale.ROOT, WARNING_FORMAT, escape(s), DateTimeFormatter.RFC_1123_DATE_TIME.format(ZonedDateTime.now(GMT)));
|
return String.format(Locale.ROOT, WARNING_FORMAT, escape(s), RFC_7231_DATE_TIME.format(ZonedDateTime.now(GMT)));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -19,8 +19,6 @@
|
||||||
|
|
||||||
package org.elasticsearch.test.rest.yaml.section;
|
package org.elasticsearch.test.rest.yaml.section;
|
||||||
|
|
||||||
import org.elasticsearch.Version;
|
|
||||||
import org.elasticsearch.common.hash.MessageDigests;
|
|
||||||
import org.elasticsearch.common.logging.DeprecationLogger;
|
import org.elasticsearch.common.logging.DeprecationLogger;
|
||||||
import org.elasticsearch.common.xcontent.XContent;
|
import org.elasticsearch.common.xcontent.XContent;
|
||||||
import org.elasticsearch.common.xcontent.XContentLocation;
|
import org.elasticsearch.common.xcontent.XContentLocation;
|
||||||
|
@ -29,7 +27,6 @@ import org.elasticsearch.common.xcontent.yaml.YamlXContent;
|
||||||
import org.hamcrest.MatcherAssert;
|
import org.hamcrest.MatcherAssert;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue