Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 38 additions & 0 deletions .github/workflows/run-tests.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
name: Run Unit Tests

on:
pull_request:
branches:
- main
types:
- opened
- synchronize
- reopened

jobs:
test:
name: Build and run unit tests
runs-on: ubuntu-latest
steps:
- name: GitHub actions Workspace Cleaner
uses: jstone28/runner-workspace-cleaner@v1.0.0

- name: Checkout
uses: actions/checkout@v4

- name: Setup .NET
uses: actions/setup-dotnet@v4
with:
dotnet-version: "10.0.x"

- name: Restore dependencies
run: dotnet restore
working-directory: ./ThreeByte.LinkLib

- name: Build
run: dotnet build --configuration Release --no-restore
working-directory: ./ThreeByte.LinkLib

- name: Run tests
run: dotnet test --configuration Release --no-build --logger "trx;LogFileName=test-results.trx"
working-directory: ./ThreeByte.LinkLib
24 changes: 10 additions & 14 deletions ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.ComponentModel;
using System.Net;
using System.Net.Http;
using Microsoft.Extensions.Logging;
using ThreeByte.LinkLib.Shared.Logging;

Expand All @@ -11,12 +12,19 @@
{
private readonly string _ipAddress;
private readonly ILogger _logger;
private readonly HttpClient _httpClient;
private readonly Dictionary<int, bool> _powerStates = new Dictionary<int, bool>();

public NetBooterLink(string ipAddress)
{
_logger = LogFactory.Create<NetBooterLink>();
_ipAddress = ipAddress;

var handler = new HttpClientHandler
{
Credentials = new NetworkCredential("admin", "admin")
};
_httpClient = new HttpClient(handler);
}

public bool this[int port]
Expand All @@ -32,17 +40,15 @@
}
}

public event PropertyChangedEventHandler? PropertyChanged;

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and run unit tests

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used

Check warning on line 43 in ThreeByte.LinkLib/ThreeByte.LinkLib.NetBooter/NetBooterLink.cs

View workflow job for this annotation

GitHub Actions / Build and push Nuget package

The event 'NetBooterLink.PropertyChanged' is never used
public event EventHandler<Exception>? ErrorOccurred;

public void Power(int outlet, bool state)
{
try
{
var c = new WebClient();
c.Credentials = new NetworkCredential("admin", "admin");
var commandUri = string.Format("http://{0}/cmd.cgi?$A3 {1} {2}", _ipAddress, outlet, state ? 1 : 0);
var response = c.DownloadString(commandUri);
var response = _httpClient.GetStringAsync(commandUri).GetAwaiter().GetResult();
_logger.LogDebug("Response: {0}", response);
}
catch (Exception ex)
Expand All @@ -56,10 +62,8 @@
{
try
{
var c = new WebClient();
c.Credentials = new NetworkCredential("admin", "admin");
var commandUri = string.Format("http://{0}/cmd.cgi?$A5", _ipAddress);
var response = c.DownloadString(commandUri);
var response = _httpClient.GetStringAsync(commandUri).GetAwaiter().GetResult();

// Expected response: xxxx,cccc,tttt
// read right to left for each field, eg - 01 means port 1 is on
Expand All @@ -84,14 +88,6 @@
}
}

private void NotifyPropertyChanged(string info)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(info));
}
}

private void HandleError(Exception ex, string message)
{
_logger.LogError(ex, message);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@
{
public abstract class Command
{
public delegate void CommandResultHandler(Command sender, CommandResponse response);

protected CommandResponse _cmdResponse;

internal virtual string GetCommandString()
Expand Down
20 changes: 11 additions & 9 deletions ThreeByte.LinkLib/ThreeByte.LinkLib.ProjectorLink/Projector.cs
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
using Microsoft.Extensions.Logging;
using System;
using System.Net.Sockets;
using System.Security.Cryptography;
using System.Text;
using System.Security.Cryptography;
using ThreeByte.LinkLib.ProjectorLink.Commands;
using ThreeByte.LinkLib.Shared.Logging;

Expand Down Expand Up @@ -235,16 +235,18 @@ private void CloseConnection()

private string GetMD5Hash(string input)
{
MD5CryptoServiceProvider cryptoProvider = new MD5CryptoServiceProvider();
byte[] bs = Encoding.ASCII.GetBytes(input);
byte[] hash = cryptoProvider.ComputeHash(bs);

string toRet = "";
foreach (byte b in hash)
using (var md5 = MD5.Create())
{
toRet += b.ToString("x2");
byte[] bs = Encoding.ASCII.GetBytes(input);
byte[] hash = md5.ComputeHash(bs);

StringBuilder sb = new StringBuilder(hash.Length * 2);
foreach (byte b in hash)
{
sb.Append(b.ToString("x2"));
}
return sb.ToString();
}
return toRet;
}

private void HandleError(Exception ex, string message)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,10 @@
<None Include="..\icon.png" Pack="true" PackagePath="" />
</ItemGroup>

<ItemGroup>
<InternalsVisibleTo Include="ThreeByte.LinkLib.Tests" />
</ItemGroup>

<ItemGroup>
<PackageReference Include="Microsoft.Extensions.Logging" Version="10.0.5" />
</ItemGroup>
Expand Down
33 changes: 15 additions & 18 deletions ThreeByte.LinkLib/ThreeByte.LinkLib.SerialLink/FramedSerialLink.cs
Original file line number Diff line number Diff line change
Expand Up @@ -75,12 +75,12 @@ public void SendMessage(string message)
}

//Add the header and footer
byte[] header = new byte[0];
byte[] header = Array.Empty<byte>();
if (SendFrame != null && SendFrame.Header != null)
{
header = SendFrame.Header;
}
byte[] footer = new byte[0];
byte[] footer = Array.Empty<byte>();
if (SendFrame != null && SendFrame.Footer != null)
{
footer = SendFrame.Footer;
Expand All @@ -91,21 +91,18 @@ public void SendMessage(string message)
Encoding.UTF8.GetBytes(message, 0, message.Length, messageBytes, header.Length);
footer.CopyTo(messageBytes, message.Length + header.Length);

if (_serialLink != null)
try
{
try
{
_serialLink.SendData(messageBytes);
}
catch (ObjectDisposedException ode)
{
HandleError(ode, "Cannot send a message of disposed FramedSerialLink.");
}
catch (Exception ex)
{
//Also possible for the serial link to raise and UnauthorizedAccessException here
HandleError(ex, "SendMessage error.");
}
_serialLink.SendData(messageBytes);
}
catch (ObjectDisposedException ode)
{
HandleError(ode, "Cannot send a message of disposed FramedSerialLink.");
}
catch (Exception ex)
{
//Also possible for the serial link to raise and UnauthorizedAccessException here
HandleError(ex, "SendMessage error.");
}
}

Expand Down Expand Up @@ -162,13 +159,13 @@ private void OnDataReceived(object? sender, EventArgs e)
{
bool hasNewData = false;

byte[] header = new byte[0];
byte[] header = Array.Empty<byte>();
if (ReceiveFrame != null && ReceiveFrame.Header != null)
{
header = ReceiveFrame.Header;
}

byte[] footer = new byte[0];
byte[] footer = Array.Empty<byte>();
if (ReceiveFrame != null && ReceiveFrame.Footer != null)
{
footer = ReceiveFrame.Footer;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -178,7 +178,7 @@ private void SafeConnect()
_serialPort.Parity = _settings.Parity;
_serialPort.DataBits = _settings.DataBits;
_serialPort.StopBits = StopBits.One;
_serialPort.DataReceived += new SerialDataReceivedEventHandler(OnDataReceived);
_serialPort.DataReceived += OnDataReceived;
}

if (!_isConnected)
Expand Down
12 changes: 7 additions & 5 deletions ThreeByte.LinkLib/ThreeByte.LinkLib.Shared/Logging/LogFactory.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Microsoft.Extensions.Logging;
using System;
using Microsoft.Extensions.Logging;

namespace ThreeByte.LinkLib.Shared.Logging
{
Expand All @@ -7,11 +8,12 @@ namespace ThreeByte.LinkLib.Shared.Logging
/// </summary>
public class LogFactory
{
private static readonly Lazy<ILoggerFactory> Factory = new Lazy<ILoggerFactory>(() =>
LoggerFactory.Create(builder => { builder.AddConsole(); }));

public static ILogger Create<T>()
{
var factory = LoggerFactory.Create(builder => { builder.AddConsole(); });

return factory.CreateLogger<T>();
return Factory.Value.CreateLogger<T>();
}
}
}
}
13 changes: 12 additions & 1 deletion ThreeByte.LinkLib/ThreeByte.LinkLib.TcpLink/AsyncTcpLink.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.Net.Sockets;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.Extensions.Logging;
using ThreeByte.LinkLib.Shared.Logging;

Expand Down Expand Up @@ -384,7 +385,17 @@ private void ReadCallback(IAsyncResult asyncResult)
DataReceived(this, new EventArgs());
}

ReceiveData();
// When BeginRead completes synchronously the callback fires on the same
// thread, so a direct call to ReceiveData would recurse on the same stack
// and eventually overflow. Trampolining via the ThreadPool breaks the chain.
if (asyncResult.CompletedSynchronously)
{
ThreadPool.QueueUserWorkItem(_ => ReceiveData());
}
else
{
ReceiveData();
}
}

/// <summary>
Expand Down
Loading
Loading