< Summary - Combined Code Coverage

Information
Class: NLightning.Bolt11.Models.TaggedFields.DescriptionTaggedField
Assembly: NLightning.Bolt11
File(s): /home/runner/work/nlightning/nlightning/src/NLightning.Bolt11/Models/TaggedFields/DescriptionTaggedField.cs
Tag: 36_15743069263
Line coverage
77%
Covered lines: 28
Uncovered lines: 8
Coverable lines: 36
Total lines: 109
Line coverage: 77.7%
Branch coverage
68%
Covered branches: 11
Total branches: 16
Branch coverage: 68.7%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
get_Type()100%11100%
get_Value()100%11100%
get_Length()100%11100%
.ctor(...)66.67%6.77672.22%
WriteToBitWriter(...)50%2.06275%
IsValid()50%2.06275%
FromBitReader(...)83.33%6.11685.71%

File(s)

/home/runner/work/nlightning/nlightning/src/NLightning.Bolt11/Models/TaggedFields/DescriptionTaggedField.cs

#LineLine coverage
 1using System.Text;
 2
 3namespace NLightning.Bolt11.Models.TaggedFields;
 4
 5using Domain.Utils;
 6using Enums;
 7using Interfaces;
 8
 9/// <summary>
 10/// Tagged field for the description
 11/// </summary>
 12/// <remarks>
 13/// The description is a UTF-8 encoded string that describes, in short, the purpose of payment
 14/// </remarks>
 15/// <seealso cref="ITaggedField"/>
 16internal sealed class DescriptionTaggedField : ITaggedField
 17{
 18    private const int MaxDescriptionBytes = 639;
 19    private readonly byte[] _data;
 20
 130821    public TaggedFieldTypes Type => TaggedFieldTypes.Description;
 72822    internal string Value { get; }
 20823    public short Length { get; }
 24
 25    /// <summary>
 26    /// Initializes a new instance of the <see cref="DescriptionTaggedField"/> class.
 27    /// </summary>
 28    /// <param name="value">The Description</param>
 21629    internal DescriptionTaggedField(string value)
 30    {
 21631        Value = value;
 32
 21633        if (string.IsNullOrEmpty(value))
 34        {
 035            _data = [];
 036            Length = 0;
 37        }
 38        else
 39        {
 40            // Add Padding if needed
 21641            var data = Encoding.UTF8.GetBytes(Value);
 21642            if (data.Length > MaxDescriptionBytes)
 043                throw new ArgumentException(
 044                    $"Description exceeds maximum length of {MaxDescriptionBytes} UTF-8 bytes. Current: {data.Length} by
 045                    nameof(value));
 46
 21647            var bitLength = data.Length * 8;
 21648            var totalBits = bitLength + (5 - bitLength % 5) % 5;
 21649            if (totalBits != bitLength)
 50            {
 19651                _data = new byte[data.Length + 1];
 19652                Array.Copy(data, _data, data.Length);
 53            }
 54            else
 55            {
 2056                _data = data;
 57            }
 58
 21659            Length = (short)(totalBits / 5);
 60        }
 21661    }
 62
 63    /// <inheritdoc/>
 64    public void WriteToBitWriter(BitWriter bitWriter)
 65    {
 5266        if (Length == 0)
 067            return;
 68
 69        // Write data
 5270        bitWriter.WriteBits(_data, Length * 5);
 5271    }
 72
 73    /// <inheritdoc/>
 74    public bool IsValid()
 75    {
 76        // Field-level validation
 15677        if (string.IsNullOrEmpty(Value))
 078            return true; // Empty description is valid
 79
 15680        var utf8Bytes = Encoding.UTF8.GetBytes(Value);
 15681        return utf8Bytes.Length <= MaxDescriptionBytes;
 82    }
 83
 84    /// <summary>
 85    /// Reads a DescriptionTaggedField from a BitReader
 86    /// </summary>
 87    /// <param name="bitReader">The BitReader to read from</param>
 88    /// <param name="length">The length of the field</param>
 89    /// <returns>The DescriptionTaggedField</returns>
 90    /// <exception cref="ArgumentException">Thrown when the length is invalid</exception>
 91    internal static DescriptionTaggedField FromBitReader(BitReader bitReader, short length)
 92    {
 93        switch (length)
 94        {
 95            case < 0:
 496                throw new ArgumentException(
 497                    $"Invalid length for {nameof(DescriptionTaggedField)}. Length must be greater or equal to 0",
 498                    nameof(length));
 99            case 0:
 0100                return new DescriptionTaggedField(string.Empty);
 101        }
 102
 103        // Read the data from the BitReader
 56104        var data = new byte[(length * 5 + 7) / 8];
 56105        bitReader.ReadBits(data, length * 5);
 106
 56107        return new DescriptionTaggedField(Encoding.UTF8.GetString(length * 5 % 8 > 0 ? data[..^1] : data));
 108    }
 109}