//
// PacketStringEnumeratorTests.cs
//
// Copyright (c) František Boháček. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using NosSmooth.PacketSerializer.Abstractions;
using NosSmooth.PacketSerializer.Abstractions.Errors;
using Xunit;
namespace NosSmooth.Packets.Tests;
/// <summary>
/// Test for <see cref="PacketStringEnumerator"/>.
/// </summary>
public class PacketStringEnumeratorTests
{
/// <summary>
/// Test that array of complex types can be parsed.
/// </summary>
[Fact]
public void EnumeratorListComplexStringGivesCorrectResult()
{
var stringEnumerator = new PacketStringEnumerator("in 1 11.12.13|14.15.16|17.18.19");
var headerTokenResult = stringEnumerator.GetNextToken(out var packetToken);
Assert.True(headerTokenResult.IsSuccess);
Assert.False(packetToken.PacketEndReached);
Assert.NotNull(packetToken.IsLast);
Assert.NotNull(packetToken.EncounteredUpperLevel);
Assert.False(packetToken.IsLast);
Assert.False(packetToken.EncounteredUpperLevel);
Assert.Matches("in", packetToken.Token.ToString());
var firstToken = stringEnumerator.GetNextToken(out packetToken);
Assert.True(firstToken.IsSuccess);
Assert.False(packetToken.PacketEndReached);
Assert.NotNull(packetToken.IsLast);
Assert.NotNull(packetToken.EncounteredUpperLevel);
Assert.False(packetToken.IsLast);
Assert.False(packetToken.EncounteredUpperLevel);
Assert.Matches("1", packetToken.Token.ToString());
stringEnumerator.PushLevel('|');
stringEnumerator.PrepareLevel('.');
for (int i = 0; i < 3; i++)
{
stringEnumerator.PushPreparedLevel();
for (int j = 0; j < 3; j++)
{
string currentNum = (j + (i * 3) + 1 + 10).ToString();
var currentToken = stringEnumerator.GetNextToken(out packetToken);
Assert.True(currentToken.IsSuccess);
Assert.False(packetToken.PacketEndReached);
Assert.NotNull(packetToken.IsLast);
Assert.NotNull(packetToken.EncounteredUpperLevel);
if (j == 2 && i == 2)
{
Assert.True(packetToken.EncounteredUpperLevel);
}
else
{
Assert.False(packetToken.EncounteredUpperLevel);
}
if (j != 2)
{
Assert.False(packetToken.IsLast);
}
else
{
Assert.True(packetToken.IsLast);
}
Assert.Matches(currentNum, packetToken.Token.ToString());
}
Assert.True(stringEnumerator.IsOnLastToken());
stringEnumerator.PopLevel();
}
stringEnumerator.PopLevel();
Assert.True(stringEnumerator.IsOnLastToken());
}
/// <summary>
/// Test that over reaching the end is not allowed.
/// </summary>
[Fact]
public void EnumeratorDoesNotAllowOvereachingPacketEnd()
{
var stringEnumerator = new PacketStringEnumerator("in 1 2 3 4");
var tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // in
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // 1
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // 2
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // 3
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // 4
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.False(tokenResult.IsSuccess);
Assert.IsType<PacketEndReachedError>(tokenResult.Error);
}
/// <summary>
/// Test that over reaching the end of a list is not allowed.
/// </summary>
[Fact]
public void EnumeratorDoesNotAllowOvereachingListComplexTypeEnd()
{
var stringEnumerator = new PacketStringEnumerator("in 1|2.2|3.3|4.4|5");
var tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // in
stringEnumerator.PushLevel('.');
stringEnumerator.PushLevel('|');
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // 1
tokenResult = stringEnumerator.GetNextToken(out var packetToken);
Assert.True(tokenResult.IsSuccess); // 2
Assert.True(packetToken.IsLast);
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.False(tokenResult.IsSuccess);
Assert.IsType<PacketEndReachedError>(tokenResult.Error);
Assert.True(((PacketEndReachedError)tokenResult.Error!).LevelEnd);
}
/// <summary>
/// Test that over reaching the length of a list is not allowed.
/// </summary>
[Fact]
public void EnumeratorDoesNotAllowOvereachingListLength()
{
var stringEnumerator = new PacketStringEnumerator("in 1|2.2|3.3|4.4|5");
var tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // in
stringEnumerator.PushLevel('.', 2);
stringEnumerator.PushLevel('|');
// first item
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess);
tokenResult = stringEnumerator.GetNextToken(out var packetToken);
Assert.True(tokenResult.IsSuccess);
Assert.True(packetToken.IsLast);
stringEnumerator.PopLevel();
// second item
stringEnumerator.PushLevel('|');
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess);
stringEnumerator.GetNextToken(out packetToken);
Assert.True(tokenResult.IsSuccess);
Assert.True(packetToken.IsLast);
stringEnumerator.PopLevel();
// cannot reach third item
Assert.True(stringEnumerator.IsOnLastToken());
stringEnumerator.PushLevel('|');
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.False(tokenResult.IsSuccess);
Assert.IsType<PacketEndReachedError>(tokenResult.Error);
Assert.True(((PacketEndReachedError)tokenResult.Error!).LevelEnd);
}
/// <summary>
/// Test that EncounteredUpperLevel is returned if appropriate.
/// </summary>
[Fact]
public void EnumeratorReturnsEncounteredUpperLevel()
{
var stringEnumerator = new PacketStringEnumerator("in 1|2 1");
var tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess); // in
stringEnumerator.PushLevel('.');
stringEnumerator.PushLevel('|');
tokenResult = stringEnumerator.GetNextToken(out _);
Assert.True(tokenResult.IsSuccess);
tokenResult = stringEnumerator.GetNextToken(out var packetToken);
Assert.True(tokenResult.IsSuccess);
Assert.True(packetToken.IsLast);
Assert.True(packetToken.EncounteredUpperLevel);
}
}