Release 1.1.0: QR-Reportimport, Regal-Auswahlmodal, Einlagern/Auslagern-Verknuepfungen aus Reifenlager, Stabilitaetsfixes

This commit is contained in:
spaethf committed 2026-09-26 23:24:14 +02:00
1 parent cba9414e92
commit 3404fb9875
25 files changed
+5106 -744

No files matched your search

+116
View File
@@ -0,0 +1,116 @@
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace Lagerbestand.Models;
/// <summary>
/// Condition rating of a single tire as reported by the measurement device.
/// </summary>
public enum TireMeasureRating
{
Unknown = 0,
Ok = 1,
Warning = 2,
Critical = 3
}
/// <summary>
/// A tread depth / condition measurement for a tire stack, typically imported
/// from a Launch TTS01 report (QR code) during checkin.
/// </summary>
public class TireInspection
{
[Key]
public Guid Id { get; set; } = Guid.NewGuid();
public Guid TireStackId { get; set; }
[ForeignKey(nameof(TireStackId))]
[System.Text.Json.Serialization.JsonIgnore]
public TireStack? TireStack { get; set; }
[MaxLength(50)]
public string Source { get; set; } = "Launch TTS01";
[MaxLength(100)]
public string? RecordSn { get; set; }
[MaxLength(500)]
public string? ReportUrl { get; set; }
public DateTime? MeasuredAt { get; set; }
[MaxLength(20)]
public string? LicensePlate { get; set; }
public int? Mileage { get; set; }
[Column(TypeName = "decimal(5,2)")]
public decimal? TreadDepthFL { get; set; }
[Column(TypeName = "decimal(5,2)")]
public decimal? TreadDepthFR { get; set; }
[Column(TypeName = "decimal(5,2)")]
public decimal? TreadDepthRL { get; set; }
[Column(TypeName = "decimal(5,2)")]
public decimal? TreadDepthRR { get; set; }
public TireMeasureRating RatingFL { get; set; }
public TireMeasureRating RatingFR { get; set; }
public TireMeasureRating RatingRL { get; set; }
public TireMeasureRating RatingRR { get; set; }
[MaxLength(1000)]
public string? Recommendation { get; set; }
public string? RawJson { get; set; }
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
public Guid? CreatedByUserId { get; set; }
[NotMapped]
public decimal? MinTreadDepth
{
get
{
var values = new[] { TreadDepthFL, TreadDepthFR, TreadDepthRL, TreadDepthRR }.Where(v => v.HasValue).Select(v => v!.Value).ToList();
return values.Count == 0 ? null : values.Min();
}
}
[NotMapped]
public TireMeasureRating WorstRating
{
get
{
var ratings = new[] { RatingFL, RatingFR, RatingRL, RatingRR };
return ratings.Max();
}
}
[NotMapped]
public bool HasTreadData => TreadDepthFL.HasValue || TreadDepthFR.HasValue || TreadDepthRL.HasValue || TreadDepthRR.HasValue;
/// <summary>Legal minimum tread depth in Germany (mm).</summary>
public const decimal DefaultCriticalThreshold = 1.6m;
/// <summary>Common workshop recommendation threshold for replacement (mm).</summary>
public const decimal DefaultWarningThreshold = 3.0m;
/// <summary>
/// Derives a rating from a tread depth in mm. Values below <paramref name="critical"/>
/// are critical, values up to <paramref name="warning"/> are a warning.
/// </summary>
public static TireMeasureRating RateDepth(decimal? mm, decimal? critical = null, decimal? warning = null)
{
if (!mm.HasValue) return TireMeasureRating.Unknown;
var crit = critical ?? DefaultCriticalThreshold;
var warn = Math.Max(warning ?? DefaultWarningThreshold, crit);
if (mm.Value < crit) return TireMeasureRating.Critical;
if (mm.Value <= warn) return TireMeasureRating.Warning;
return TireMeasureRating.Ok;
}
}
+13 -1
View File
@@ -31,7 +31,13 @@ public enum TireStackStatus
/// <summary>
/// Tires are in inventory (shop stock, not customer-owned)
/// </summary>
Inventory = 4
Inventory = 4,
/// <summary>
/// Tires are currently mounted on the customer's vehicle (after a seasonal swap).
/// They can be re-stored later when swapping back.
/// </summary>
OnVehicle = 5
}
/// <summary>
@@ -96,6 +102,11 @@ public class TireStack
[ForeignKey(nameof(CatalogItemId))]
public CatalogItem? CatalogItem { get; set; }
/// <summary>
/// Tread depth / condition measurements (e.g. imported from QR report)
/// </summary>
public ICollection<TireInspection> Inspections { get; set; } = new List<TireInspection>();
/// <summary>
/// Current status of the tire stack
/// </summary>
@@ -234,6 +245,7 @@ public class TireStack
TireStackStatus.Disposed => "Entsorgt",
TireStackStatus.Reserved => "Reserviert",
TireStackStatus.Inventory => "Lagerbestand",
TireStackStatus.OnVehicle => "Montiert",
_ => "Unbekannt"
};