feat(ui): wire file and database nest storage
This commit is contained in:
@@ -0,0 +1,45 @@
|
||||
using System.Linq;
|
||||
|
||||
namespace OpenNest.Data;
|
||||
|
||||
/// <summary>
|
||||
/// Builds the shareable <see cref="NestRecord"/> metadata from a live <see cref="Nest"/>.
|
||||
/// Counts are computed here (not carried on <see cref="Nest"/> itself) so every caller
|
||||
/// that saves to the nest server gets the same definition of "plate" and "part" counts.
|
||||
/// </summary>
|
||||
public static class NestRecordFactory
|
||||
{
|
||||
/// <summary>
|
||||
/// Builds a record for uploading <paramref name="nest"/>. <paramref name="id"/> is the
|
||||
/// client-tracked id: <see cref="System.Guid.Empty"/> for a first save (the server
|
||||
/// assigns one), or the previously returned id to update an existing record.
|
||||
/// <paramref name="fileSize"/> is the size of the serialized .nest archive being
|
||||
/// uploaded alongside this record; the server also recomputes it independently.
|
||||
/// </summary>
|
||||
public static NestRecord FromNest(Nest nest, System.Guid id, long fileSize)
|
||||
{
|
||||
ArgumentNullException.ThrowIfNull(nest);
|
||||
|
||||
return new NestRecord
|
||||
{
|
||||
Id = id,
|
||||
Name = nest.Name ?? "",
|
||||
Customer = nest.Customer ?? "",
|
||||
DateCreated = nest.DateCreated,
|
||||
DateModified = nest.DateLastModified,
|
||||
Material = nest.Material?.Name ?? "",
|
||||
Thickness = nest.Thickness,
|
||||
Status = nest.Status,
|
||||
PlateCount = nest.Plates.Count,
|
||||
PartCount = nest.Plates.Sum(CountNonCutoffParts),
|
||||
// Nest has no separate "comments" field; Notes is the closest analog
|
||||
// shown in the nest info dialog, so it round-trips as Comments here.
|
||||
Comments = nest.Notes ?? "",
|
||||
MadeBy = nest.MadeBy ?? "",
|
||||
FileSize = fileSize,
|
||||
};
|
||||
}
|
||||
|
||||
private static int CountNonCutoffParts(Plate plate) =>
|
||||
plate.Parts.Count(part => !part.BaseDrawing.IsCutOff);
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
namespace OpenNest.Data;
|
||||
|
||||
/// <summary>
|
||||
/// Tracks a document's database identity, bound to a particular server address.
|
||||
/// A failed upload leaves that identity untouched. Switching servers creates a new
|
||||
/// record rather than accidentally updating an unrelated record with the same id.
|
||||
/// </summary>
|
||||
public sealed class NestSaveSession
|
||||
{
|
||||
public Guid RemoteId { get; private set; }
|
||||
public string ServerUrl { get; private set; } = "";
|
||||
|
||||
public void Bind(Guid id, string serverUrl)
|
||||
{
|
||||
if (id == Guid.Empty)
|
||||
throw new ArgumentException("A saved nest needs a non-empty id.", nameof(id));
|
||||
RemoteId = id;
|
||||
ServerUrl = Normalize(serverUrl);
|
||||
}
|
||||
|
||||
public async Task<NestRecord> SaveAsync(
|
||||
INestRepository repository, string serverUrl, Nest nest, byte[] archive,
|
||||
bool saveCopy = false, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ArgumentNullException.ThrowIfNull(repository);
|
||||
ArgumentNullException.ThrowIfNull(nest);
|
||||
ArgumentNullException.ThrowIfNull(archive);
|
||||
|
||||
var normalizedUrl = Normalize(serverUrl);
|
||||
if (normalizedUrl.Length == 0)
|
||||
throw new ArgumentException("A database server URL is required.", nameof(serverUrl));
|
||||
|
||||
var id = !saveCopy && ServerUrl == normalizedUrl ? RemoteId : Guid.Empty;
|
||||
var record = NestRecordFactory.FromNest(nest, id, archive.LongLength);
|
||||
var saved = id == Guid.Empty
|
||||
? await repository.UploadAsync(archive, record, cancellationToken)
|
||||
: await repository.UpdateFileAsync(id, archive, record, cancellationToken);
|
||||
if (saved.Id == Guid.Empty || (id != Guid.Empty && saved.Id != id))
|
||||
throw new InvalidDataException("Server returned an invalid nest id.");
|
||||
|
||||
Bind(saved.Id, normalizedUrl);
|
||||
return saved;
|
||||
}
|
||||
|
||||
private static string Normalize(string? url) => (url ?? "").Trim().TrimEnd('/');
|
||||
}
|
||||
Reference in New Issue
Block a user