120 lines
4.1 KiB
C#
120 lines
4.1 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Text.Json;
|
|
using MongoDB.Bson;
|
|
using MongoDB.Bson.Serialization.Attributes;
|
|
using StellaOps.Concelier.Core.Jobs;
|
|
|
|
namespace StellaOps.Concelier.Storage.Mongo;
|
|
|
|
[BsonIgnoreExtraElements]
|
|
public sealed class JobRunDocument
|
|
{
|
|
[BsonId]
|
|
public string Id { get; set; } = string.Empty;
|
|
|
|
[BsonElement("kind")]
|
|
public string Kind { get; set; } = string.Empty;
|
|
|
|
[BsonElement("status")]
|
|
public string Status { get; set; } = JobRunStatus.Pending.ToString();
|
|
|
|
[BsonElement("trigger")]
|
|
public string Trigger { get; set; } = string.Empty;
|
|
|
|
[BsonElement("parameters")]
|
|
public BsonDocument Parameters { get; set; } = new();
|
|
|
|
[BsonElement("parametersHash")]
|
|
[BsonIgnoreIfNull]
|
|
public string? ParametersHash { get; set; }
|
|
|
|
[BsonElement("createdAt")]
|
|
public DateTime CreatedAt { get; set; }
|
|
|
|
[BsonElement("startedAt")]
|
|
[BsonIgnoreIfNull]
|
|
public DateTime? StartedAt { get; set; }
|
|
|
|
[BsonElement("completedAt")]
|
|
[BsonIgnoreIfNull]
|
|
public DateTime? CompletedAt { get; set; }
|
|
|
|
[BsonElement("error")]
|
|
[BsonIgnoreIfNull]
|
|
public string? Error { get; set; }
|
|
|
|
[BsonElement("timeoutMs")]
|
|
[BsonIgnoreIfNull]
|
|
public long? TimeoutMs { get; set; }
|
|
|
|
[BsonElement("leaseMs")]
|
|
[BsonIgnoreIfNull]
|
|
public long? LeaseMs { get; set; }
|
|
}
|
|
|
|
internal static class JobRunDocumentExtensions
|
|
{
|
|
public static JobRunDocument FromRequest(JobRunCreateRequest request, Guid id)
|
|
{
|
|
return new JobRunDocument
|
|
{
|
|
Id = id.ToString(),
|
|
Kind = request.Kind,
|
|
Status = JobRunStatus.Pending.ToString(),
|
|
Trigger = request.Trigger,
|
|
Parameters = request.Parameters is { Count: > 0 }
|
|
? BsonDocument.Parse(JsonSerializer.Serialize(request.Parameters))
|
|
: new BsonDocument(),
|
|
ParametersHash = request.ParametersHash,
|
|
CreatedAt = request.CreatedAt.UtcDateTime,
|
|
TimeoutMs = request.Timeout?.MillisecondsFromTimespan(),
|
|
LeaseMs = request.LeaseDuration?.MillisecondsFromTimespan(),
|
|
};
|
|
}
|
|
|
|
public static JobRunSnapshot ToSnapshot(this JobRunDocument document)
|
|
{
|
|
var parameters = document.Parameters?.ToDictionary() ?? new Dictionary<string, object?>();
|
|
|
|
return new JobRunSnapshot(
|
|
Guid.Parse(document.Id),
|
|
document.Kind,
|
|
Enum.Parse<JobRunStatus>(document.Status, ignoreCase: true),
|
|
DateTime.SpecifyKind(document.CreatedAt, DateTimeKind.Utc),
|
|
document.StartedAt.HasValue ? DateTime.SpecifyKind(document.StartedAt.Value, DateTimeKind.Utc) : null,
|
|
document.CompletedAt.HasValue ? DateTime.SpecifyKind(document.CompletedAt.Value, DateTimeKind.Utc) : null,
|
|
document.Trigger,
|
|
document.ParametersHash,
|
|
document.Error,
|
|
document.TimeoutMs?.MillisecondsToTimespan(),
|
|
document.LeaseMs?.MillisecondsToTimespan(),
|
|
parameters);
|
|
}
|
|
|
|
public static Dictionary<string, object?> ToDictionary(this BsonDocument document)
|
|
{
|
|
return document.Elements.ToDictionary(
|
|
static element => element.Name,
|
|
static element => element.Value switch
|
|
{
|
|
BsonString s => (object?)s.AsString,
|
|
BsonBoolean b => b.AsBoolean,
|
|
BsonInt32 i => i.AsInt32,
|
|
BsonInt64 l => l.AsInt64,
|
|
BsonDouble d => d.AsDouble,
|
|
BsonNull => null,
|
|
BsonArray array => array.Select(v => v.IsBsonDocument ? ToDictionary(v.AsBsonDocument) : (object?)v.ToString()).ToArray(),
|
|
BsonDocument doc => ToDictionary(doc),
|
|
_ => element.Value.ToString(),
|
|
});
|
|
}
|
|
|
|
private static long MillisecondsFromTimespan(this TimeSpan timeSpan)
|
|
=> (long)timeSpan.TotalMilliseconds;
|
|
|
|
private static TimeSpan MillisecondsToTimespan(this long milliseconds)
|
|
=> TimeSpan.FromMilliseconds(milliseconds);
|
|
}
|