C
C#14mo ago
SWEETPONY

✅ How to sum datetimeoffset and timespan?

I have following structure:
[JsonProperty( PropertyName = "timestamp" )]
[JsonRequired]
public DateTimeOffset Timestamp { get; set; }

[JsonProperty( PropertyName = "ttl" )]
public TimeSpan? Ttl { get; set; }

[JsonProperty( PropertyName = "expires_at" )]
public DateTime ExpiresAt { get; set; }
[JsonProperty( PropertyName = "timestamp" )]
[JsonRequired]
public DateTimeOffset Timestamp { get; set; }

[JsonProperty( PropertyName = "ttl" )]
public TimeSpan? Ttl { get; set; }

[JsonProperty( PropertyName = "expires_at" )]
public DateTime ExpiresAt { get; set; }
I would like to get expiration time by sum timestamp and ttl I tried this:
[JsonProperty( PropertyName = "expires_at" )]
public DateTime ExpiresAt => Ttl.HasValue
? DateTime.Now.Add( Ttl.Value )
: DateTime.MaxValue;
[JsonProperty( PropertyName = "expires_at" )]
public DateTime ExpiresAt => Ttl.HasValue
? DateTime.Now.Add( Ttl.Value )
: DateTime.MaxValue;
but it's not correct
18 Replies
Pobiega
Pobiega14mo ago
uhm you're using DateTime.Now in that example also why are you mixing datetimeoffset with datetime?
public class Fifth
{
public DateTimeOffset Timestamp { get; set; }

public TimeSpan? Ttl { get; set; }

public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
}
public class Fifth
{
public DateTimeOffset Timestamp { get; set; }

public TimeSpan? Ttl { get; set; }

public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
}
this works fine
SWEETPONY
SWEETPONYOP14mo ago
but I don't think that ExpiresAt should be DateTimeOffset, it should be local time
Pobiega
Pobiega14mo ago
public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.LocalDateTime.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.LocalDateTime.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
could turn this into DateTime if you don't want the offset shown
SWEETPONY
SWEETPONYOP14mo ago
the logic is following I get the dto with timestamp, then I add it to the database Once per hour (for example) I make a request to get all the objects that are already expired, and then I delete them The check takes place locally, so I don't need time zones
Pobiega
Pobiega14mo ago
But the timestamp is offset? ie, if you fetch an item from me, it'll be in my timezone, so +0200 it has a 3 hour ttl that means you need to take the offset into account when calculating the expire time, or convert it at the time of saving into database its FAR easier to just always use offsets
SWEETPONY
SWEETPONYOP14mo ago
"timestamp": "04/10/2023 7:23:57 PM -07:00",
"ttl": "1.02:30:15"
"timestamp": "04/10/2023 7:23:57 PM -07:00",
"ttl": "1.02:30:15"
let's say that this is values that I get from dto I should add this to database and remove after "04/10/2023 7:23:57 PM -07:00" + "1.02:30:15" So all I need is just 04/10/2023 7:23:57 PM -07:00.LocalDateTime.Add(1.02:30:15)?
Pobiega
Pobiega14mo ago
dont do the whole local conversion just keep it offset you want the object to live 1.02:30:15 after the timestamp, right?
SWEETPONY
SWEETPONYOP14mo ago
yes
Pobiega
Pobiega14mo ago
then you NEED to respect the offset it doesnt matter what local timezone the server is in
SWEETPONY
SWEETPONYOP14mo ago
ah and checking the time will be look like this: DateTime.Now > ExpiresAt - ExpiresAt.Offset idk
Pobiega
Pobiega14mo ago
use DateTimeOffset its literally just DateTimeOffset.Now > ExpiresAt offset is taken into account automatically here is an example
var now = DateTimeOffset.Now;

var dto = new Fifth()
{
Timestamp = CreateWithOffset(5),
Ttl = TimeSpan.FromHours(3)
};

var timeLeft = dto.ExpiresAt - now;

Console.WriteLine($"Now: {now}");
Console.WriteLine($"Expires at: {dto.ExpiresAt}");
Console.WriteLine($"Time left: {timeLeft}");

while (dto.ExpiresAt > now)
{
timeLeft = dto.ExpiresAt - now;
Console.WriteLine($"Time left: {timeLeft}");
Console.WriteLine("Dto has not expired, moving up an hour.");
now = now.AddHours(1);
}

Console.WriteLine($"It expired, time is now {now}");
var now = DateTimeOffset.Now;

var dto = new Fifth()
{
Timestamp = CreateWithOffset(5),
Ttl = TimeSpan.FromHours(3)
};

var timeLeft = dto.ExpiresAt - now;

Console.WriteLine($"Now: {now}");
Console.WriteLine($"Expires at: {dto.ExpiresAt}");
Console.WriteLine($"Time left: {timeLeft}");

while (dto.ExpiresAt > now)
{
timeLeft = dto.ExpiresAt - now;
Console.WriteLine($"Time left: {timeLeft}");
Console.WriteLine("Dto has not expired, moving up an hour.");
now = now.AddHours(1);
}

Console.WriteLine($"It expired, time is now {now}");
im in timezone 0200. Im creating a DTO that was created in 0500, and has a 3 hour time to live that means it should expire right away when I check it, because it was created exactly 3 hours ago
Now: 2023-10-06 12:24:33 +02:00
Expires at: 2023-10-06 15:24:33 +05:00
Time left: -00:00:00.9790660
It expired, time is now 2023-10-06 12:24:33 +02:00
Now: 2023-10-06 12:24:33 +02:00
Expires at: 2023-10-06 15:24:33 +05:00
Time left: -00:00:00.9790660
It expired, time is now 2023-10-06 12:24:33 +02:00
lets spice it up a bit. lets make it have a 10 hour time to live or 5 actually
Now: 2023-10-06 12:25:19 +02:00
Expires at: 2023-10-06 17:25:19 +05:00
Time left: 01:59:59.4297506
Time left: 01:59:59.4297506
Dto has not expired, moving up an hour.
Time left: 00:59:59.4297506
Dto has not expired, moving up an hour.
It expired, time is now 2023-10-06 14:25:19 +02:00
Now: 2023-10-06 12:25:19 +02:00
Expires at: 2023-10-06 17:25:19 +05:00
Time left: 01:59:59.4297506
Time left: 01:59:59.4297506
Dto has not expired, moving up an hour.
Time left: 00:59:59.4297506
Dto has not expired, moving up an hour.
It expired, time is now 2023-10-06 14:25:19 +02:00
so we see that when I start checking, it only has 2 hours left to live. That checks out, since it was created at 12:25 local time in +0500
SWEETPONY
SWEETPONYOP14mo ago
hm I get the idea of how to get expired objects from db (we use DateTimeOffset.Now > ExpiresAt)
Pobiega
Pobiega14mo ago
yes
SWEETPONY
SWEETPONYOP14mo ago
and to get ExpiresAt from datetimeoffset and timespan we just do sum(datetimeoffset , timespan)
Pobiega
Pobiega14mo ago
public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
public DateTimeOffset ExpiresAt
=> Ttl.HasValue
? Timestamp.Add(Ttl.Value)
: DateTimeOffset.MaxValue;
SWEETPONY
SWEETPONYOP14mo ago
yes, thanks for helping me!
Pobiega
Pobiega14mo ago
np
SWEETPONY
SWEETPONYOP14mo ago
now I understand
Want results from more Discord servers?
Add your server