82 lines
3.0 KiB
C#
82 lines
3.0 KiB
C#
using Emby.Server.Implementations;
|
|
using Xunit;
|
|
|
|
namespace Jellyfin.Server.Implementations.Tests.Configuration;
|
|
|
|
/// <summary>
|
|
/// The decision <c>ApplicationHost.OnConfigurationUpdated</c> makes about a port change. The ports this
|
|
/// process bound are fixed for its lifetime and the pending-restart flag is per-process, so an instance
|
|
/// applying another instance's port change still has to notice its own binding went stale - while leaving
|
|
/// the authorization write, and the notice that follows it, to the instance that made the change.
|
|
/// </summary>
|
|
public static class ApplicationHostPortChangeTests
|
|
{
|
|
/// <summary>
|
|
/// The local case, unchanged: clear the authorization flag and report the pending restart.
|
|
/// </summary>
|
|
[Fact]
|
|
public static void LocalPortChange_ClearsAuthorizationAndRequiresRestart()
|
|
{
|
|
var outcome = ApplicationHost.EvaluatePortChange(8096, 8920, 9096, 8920, true, false);
|
|
|
|
Assert.True(outcome.RequiresRestart);
|
|
Assert.True(outcome.ClearsPortAuthorization);
|
|
}
|
|
|
|
/// <summary>
|
|
/// The cross-instance case: the peer wrote the new port and cleared the flag with it, so this
|
|
/// instance must not write, but it is still listening on the old port and has to say so.
|
|
/// </summary>
|
|
[Theory]
|
|
[InlineData(true)]
|
|
[InlineData(false)]
|
|
public static void RemotePortChange_RequiresRestartWithoutWriting(bool isPortAuthorized)
|
|
{
|
|
var outcome = ApplicationHost.EvaluatePortChange(8096, 8920, 9096, 8920, isPortAuthorized, true);
|
|
|
|
Assert.True(outcome.RequiresRestart);
|
|
Assert.False(outcome.ClearsPortAuthorization);
|
|
}
|
|
|
|
/// <summary>
|
|
/// A second update while a port change is already pending must not write the flag again, and the
|
|
/// binding is still stale.
|
|
/// </summary>
|
|
[Fact]
|
|
public static void LocalPortChange_WithAuthorizationAlreadyCleared_RequiresRestartWithoutWriting()
|
|
{
|
|
var outcome = ApplicationHost.EvaluatePortChange(8096, 8920, 9096, 8920, false, false);
|
|
|
|
Assert.True(outcome.RequiresRestart);
|
|
Assert.False(outcome.ClearsPortAuthorization);
|
|
}
|
|
|
|
/// <summary>
|
|
/// An update that leaves the ports alone is not a port change, whoever wrote it.
|
|
/// </summary>
|
|
[Theory]
|
|
[InlineData(false)]
|
|
[InlineData(true)]
|
|
public static void UnchangedPorts_DoNothing(bool isApplyingRemoteInvalidation)
|
|
{
|
|
var outcome = ApplicationHost.EvaluatePortChange(8096, 8920, 8096, 8920, true, isApplyingRemoteInvalidation);
|
|
|
|
Assert.False(outcome.RequiresRestart);
|
|
Assert.False(outcome.ClearsPortAuthorization);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Nothing is decided before the ports have been bound.
|
|
/// </summary>
|
|
[Theory]
|
|
[InlineData(0, 8920)]
|
|
[InlineData(8096, 0)]
|
|
public static void UnboundPorts_DoNothing(int boundHttpPort, int boundHttpsPort)
|
|
{
|
|
var outcome = ApplicationHost.EvaluatePortChange(boundHttpPort, boundHttpsPort, 9096, 9920, true, false);
|
|
|
|
Assert.False(outcome.RequiresRestart);
|
|
Assert.False(outcome.ClearsPortAuthorization);
|
|
}
|
|
}
|