Skip to content
This repository was archived by the owner on Dec 24, 2022. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 5 additions & 3 deletions src/ServiceStack.Text/Support/TimeSpanConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,11 @@ public class TimeSpanConverter
{
public static string ToXsdDuration(TimeSpan timeSpan)
{
var sb = new StringBuilder("P");
var sb = new StringBuilder();

double ticks = timeSpan.Ticks;
sb.Append(timeSpan.Ticks < 0 ? "-P" : "P");

double ticks = Math.Abs(timeSpan.Ticks);
double totalSeconds = ticks / TimeSpan.TicksPerSecond;
int wholeSeconds = (int) totalSeconds;
int seconds = wholeSeconds;
Expand Down Expand Up @@ -55,6 +56,7 @@ public static TimeSpan FromXsdDuration(string xsdDuration)
int hours = 0;
int minutes = 0;
double seconds = 0;
var sign = (xsdDuration.StartsWith("-", StringComparison.Ordinal) ? -1 : 1);

string[] t = xsdDuration.Substring(1).SplitOnFirst('T'); //strip P

Expand Down Expand Up @@ -100,7 +102,7 @@ public static TimeSpan FromXsdDuration(string xsdDuration)
+ (minutes * 60)
+ (seconds);

var interval = (long) (totalSecs * TimeSpan.TicksPerSecond);
var interval = (long) (totalSecs * TimeSpan.TicksPerSecond * sign);

return TimeSpan.FromTicks(interval);
}
Expand Down
20 changes: 20 additions & 0 deletions tests/ServiceStack.Text.Tests/DateTimeOffsetAndTimeSpanTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,26 @@ public void Can_serialize_TimeSpan_field()
Serialize(model);
}

[Test]
public void Can_serialize_negative_TimeSpan_field()
{
var period = new TimeSpan(0, 0, -15, 0);

var model = new SampleModel { Id = 1, TimeSpan = period };
var json = JsonSerializer.SerializeToString(model);
Assert.That(json, Is.StringContaining("\"TimeSpan\":\"-PT15M\""));
}

[Test]
public void Can_deserialize_negative_TimeSpan_string()
{
var expectedTimeSpan = new TimeSpan(0, 0, -15, 0);
const string timeSpanString = @"-PT15M";

var timeSpan = JsonSerializer.DeserializeFromString<TimeSpan>(timeSpanString);
Assert.That(timeSpan, Is.EqualTo(expectedTimeSpan));
}

[Test]
public void Can_serialize_TimeSpan_field_with_StandardTimeSpanFormat()
{
Expand Down