Skip to content

Commit

Permalink
Fix DateOnly and TimeOnly Formatting using interpolated strings (#64398)
Browse files Browse the repository at this point in the history
  • Loading branch information
tarekgh authored Jan 28, 2022
1 parent 479ee51 commit f8f486b
Show file tree
Hide file tree
Showing 6 changed files with 30 additions and 12 deletions.
6 changes: 2 additions & 4 deletions src/libraries/System.Private.CoreLib/src/System/DateOnly.cs
Original file line number Diff line number Diff line change
Expand Up @@ -817,15 +817,13 @@ public string ToString(string? format, IFormatProvider? provider)
return DateTimeFormat.TryFormat(GetEquivalentDateTime(), destination, out charsWritten, format, provider);

default:
charsWritten = 0;
return false;
throw new FormatException(SR.Argument_BadFormatSpecifier);
}
}

if (!DateTimeFormat.IsValidCustomDateFormat(format, throwOnError: false))
{
charsWritten = 0;
return false;
throw new FormatException(SR.Format(SR.Format_DateTimeOnlyContainsNoneDateParts, format.ToString(), nameof(DateOnly)));
}

return DateTimeFormat.TryFormat(GetEquivalentDateTime(), destination, out charsWritten, format, provider);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,8 @@ Patterns Format Description Example
"M" "0" month w/o leading zero 2
"MM" "00" month with leading zero 02
"MMM" short month name (abbreviation) Feb
"MMMM" full month name Febuary
"MMMM*" full month name Febuary
"MMMM" full month name February
"MMMM*" full month name February
"y" "0" two digit year (year % 100) w/o leading zero 0
"yy" "00" two digit year (year % 100) with leading zero 00
Expand Down Expand Up @@ -734,7 +734,7 @@ private static StringBuilder FormatCustomized(
break;
case '\\':
// Escaped character. Can be used to insert a character into the format string.
// For exmple, "\d" will insert the character 'd' into the string.
// For example, "\d" will insert the character 'd' into the string.
//
// NOTENOTE : we can remove this format character if we enforce the enforced quote
// character rule.
Expand Down Expand Up @@ -966,7 +966,7 @@ private static string ExpandPredefinedFormat(ReadOnlySpan<char> format, ref Date
// This format is not supported by DateTimeOffset
throw new FormatException(SR.Format_InvalidString);
}
// Universal time is always in Greogrian calendar.
// Universal time is always in Gregorian calendar.
//
// Change the Calendar to be Gregorian Calendar.
//
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ public interface ISpanFormattable : IFormattable
/// <remarks>
/// An implementation of this interface should produce the same string of characters as an implementation of <see cref="IFormattable.ToString(string?, IFormatProvider?)"/>
/// on the same type.
/// TryFormat should return false only if there is not enough space in the destination buffer. Any other failures should throw an exception.
/// </remarks>
bool TryFormat(Span<char> destination, out int charsWritten, ReadOnlySpan<char> format, IFormatProvider? provider);
}
Expand Down
6 changes: 2 additions & 4 deletions src/libraries/System.Private.CoreLib/src/System/TimeOnly.cs
Original file line number Diff line number Diff line change
Expand Up @@ -892,15 +892,13 @@ public string ToString(string? format, IFormatProvider? provider)
return DateTimeFormat.TryFormat(ToDateTime(), destination, out charsWritten, format, provider);

default:
charsWritten = 0;
return false;
throw new FormatException(SR.Argument_BadFormatSpecifier);
}
}

if (!DateTimeFormat.IsValidCustomTimeFormat(format, throwOnError: false))
{
charsWritten = 0;
return false;
throw new FormatException(SR.Format(SR.Format_DateTimeOnlyContainsNoneDateParts, format.ToString(), nameof(TimeOnly)));
}

return DateTimeFormat.TryFormat(ToDateTime(), destination, out charsWritten, format, provider);
Expand Down
10 changes: 10 additions & 0 deletions src/libraries/System.Runtime/tests/System/DateOnlyTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -513,6 +513,16 @@ public static void TryFormatTest()
Assert.False(dateOnly.TryFormat(buffer.Slice(0, 3), out charsWritten));
Assert.False(dateOnly.TryFormat(buffer.Slice(0, 3), out charsWritten, "r"));
Assert.False(dateOnly.TryFormat(buffer.Slice(0, 3), out charsWritten, "O"));
Assert.Throws<FormatException>(() => {
Span<char> buff = stackalloc char[100];
dateOnly.TryFormat(buff, out charsWritten, "u");
});
Assert.Throws<FormatException>(() => {
Span<char> buff = stackalloc char[100];
dateOnly.TryFormat(buff, out charsWritten, "hh-ss");
});
Assert.Throws<FormatException>(() => $"{dateOnly:u}");
Assert.Throws<FormatException>(() => $"{dateOnly:hh-ss}");
}
}
}
11 changes: 11 additions & 0 deletions src/libraries/System.Runtime/tests/System/TimeOnlyTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -483,6 +483,17 @@ public static void TryFormatTest()
Assert.False(timeOnly.TryFormat(buffer.Slice(0, 3), out charsWritten));
Assert.False(timeOnly.TryFormat(buffer.Slice(0, 3), out charsWritten, "r"));
Assert.False(timeOnly.TryFormat(buffer.Slice(0, 3), out charsWritten, "O"));

Assert.Throws<FormatException>(() => {
Span<char> buff = stackalloc char[100];
timeOnly.TryFormat(buff, out charsWritten, "u");
});
Assert.Throws<FormatException>(() => {
Span<char> buff = stackalloc char[100];
timeOnly.TryFormat(buff, out charsWritten, "dd-yyyy");
});
Assert.Throws<FormatException>(() => $"{timeOnly:u}");
Assert.Throws<FormatException>(() => $"{timeOnly:dd-yyyy}");
}
}
}

0 comments on commit f8f486b

Please sign in to comment.