using Google.Protobuf.WellKnownTypes;
namespace DynamicCrud.Tests.Grpc;
///
/// Utilidades para desempacar el campo data de ,
/// que llega como un nativo de protobuf: un array de objetos en GetAll/Search,
/// o un objeto suelto en GetById.
///
internal static class CrudData
{
/// Interpreta la respuesta como lista de registros. Un objeto suelto cuenta como lista de uno.
internal static List> AsRecords(Value? data)
{
if (data is null) return new();
return data.KindCase switch
{
Value.KindOneofCase.ListValue => data.ListValue.Values
.Where(v => v.KindCase == Value.KindOneofCase.StructValue)
.Select(v => (IDictionary)v.StructValue.Fields)
.ToList(),
Value.KindOneofCase.StructValue =>
new() { data.StructValue.Fields },
_ => new(),
};
}
/// Interpreta la respuesta como un registro único (GetById).
internal static IDictionary? AsRecord(Value? data) =>
data?.KindCase == Value.KindOneofCase.StructValue ? data.StructValue.Fields : null;
///
/// Representación en texto de un valor, para comparar sin pelearse con el tipo.
/// Devuelve null cuando el valor es nulo en la base.
///
internal static string? Scalar(Value v) => v.KindCase switch
{
Value.KindOneofCase.StringValue => v.StringValue,
Value.KindOneofCase.NumberValue => v.NumberValue.ToString("0.####################"),
Value.KindOneofCase.BoolValue => v.BoolValue ? "true" : "false",
Value.KindOneofCase.NullValue => null,
_ => null,
};
/// Valor escalar de un campo del registro, o null si no existe o es nulo.
internal static string? Field(IDictionary record, string name) =>
record.TryGetValue(name, out var v) ? Scalar(v) : null;
}