Skip to content

Commit

Permalink
All RPC message handling methods have access to RemotingSession.Curre…
Browse files Browse the repository at this point in the history
…nt, close 99.
  • Loading branch information
yallie committed Dec 7, 2024
1 parent 30ee709 commit 081e2f3
Show file tree
Hide file tree
Showing 5 changed files with 119 additions and 18 deletions.
1 change: 1 addition & 0 deletions CoreRemoting.Tests/CoreRemoting.Tests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
</ItemGroup>

<ItemGroup>
<PackageReference Include="Microsoft.Bcl.AsyncInterfaces" Version="7.0.0" />
<PackageReference Include="System.Runtime.Serialization.Formatters" Version="9.0.0" Condition="'$(TargetFramework)' == 'net8.0'" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.7.2" />
Expand Down
57 changes: 57 additions & 0 deletions CoreRemoting.Tests/DisposableTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
using CoreRemoting.Toolbox;
using System.Threading.Tasks;
using Xunit;

namespace CoreRemoting.Tests
{
public class DisposableTests
{
[Fact]
public void Disposable_executes_action_on_Dispose()
{
var disposed = false;

void Dispose() =>
disposed = true;

using (Disposable.Create(Dispose))
Assert.False(disposed);

Assert.True(disposed);
}

[Fact]
public async Task AsyncDisposable_executes_action_on_DisposeAsync()
{
var disposed = false;

async Task DisposeTask()
{
await Task.Yield();
disposed = true;
}

await using (Disposable.Create(DisposeTask))
Assert.False(disposed);

Assert.True(disposed);
}

[Fact]
public async Task AsyncTaskDisposable_executes_action_on_DisposeAsync()
{
var disposed = false;

async ValueTask DisposeAsync()
{
await Task.Yield();
disposed = true;
}

await using (Disposable.Create(DisposeAsync))
Assert.False(disposed);

Assert.True(disposed);
}
}
}
8 changes: 4 additions & 4 deletions CoreRemoting/IRemotingServer.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,14 +27,14 @@ public interface IRemotingServer : IDisposable
event EventHandler<ServerRpcContext> AfterCall;

/// <summary>
/// Event: Fires if an error occurs.
/// Event: Fires when an RPC call is rejected before BeginCall event. .
/// </summary>
event EventHandler<Exception> Error;
event EventHandler<ServerRpcContext> RejectCall;

/// <summary>
/// Event: Fires when an RPC call is rejected before BeginCall event. .
/// Event: Fires if an error occurs.
/// </summary>
event EventHandler<ServerRpcContext> RejectCall;
event EventHandler<Exception> Error;

/// <summary>
/// Gets the unique name of this server instance.
Expand Down
19 changes: 5 additions & 14 deletions CoreRemoting/RemotingSession.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
using CoreRemoting.Encryption;
using CoreRemoting.Serialization;
using Serialize.Linq.Nodes;
using CoreRemoting.Toolbox;

namespace CoreRemoting
{
Expand Down Expand Up @@ -258,6 +259,8 @@ private void OnReceiveMessage(byte[] rawMessage)

_currentlyProcessedMessagesCounter.AddCount(1);

CurrentSession.Value = this;

try
{
var message = _server.Serializer.Deserialize<WireMessage>(rawMessage);
Expand Down Expand Up @@ -285,6 +288,8 @@ private void OnReceiveMessage(byte[] rawMessage)
finally
{
_currentlyProcessedMessagesCounter.Signal();

CurrentSession.Value = null;
}
});
}
Expand Down Expand Up @@ -424,8 +429,6 @@ private void ProcessRpcMessage(WireMessage request)

try
{
CurrentSession.Value = this;

if (_server.Config.AuthenticationRequired && !_isAuthenticated)
throw new NetworkException("Session is not authenticated.");

Expand Down Expand Up @@ -470,19 +473,13 @@ private void ProcessRpcMessage(WireMessage request)
serializedResult =
_server.Serializer.Serialize(serverRpcContext.Exception);
}
finally
{
CurrentSession.Value = null;
}

object result = null;

if (serverRpcContext.Exception == null)
{
try
{
CurrentSession.Value = this;

((RemotingServer)_server).OnBeforeCall(serverRpcContext);

result = method.Invoke(serverRpcContext.ServiceInstance,
Expand Down Expand Up @@ -543,10 +540,6 @@ private void ProcessRpcMessage(WireMessage request)
serializedResult =
_server.Serializer.Serialize(serverRpcContext.Exception);
}
finally
{
CurrentSession.Value = null;
}

if (!oneWay)
{
Expand Down Expand Up @@ -587,8 +580,6 @@ private void ProcessRpcMessage(WireMessage request)

_rawMessageTransport.SendMessage(
_server.Serializer.Serialize(methodResultMessage));

CurrentSession.Value = null;
}

private MethodInfo GetMethodInfo(MethodCallMessage callMessage, Type serviceInterfaceType, Type[] parameterTypes)
Expand Down
52 changes: 52 additions & 0 deletions CoreRemoting/Toolbox/Disposable.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
using System;
using System.Threading.Tasks;

namespace CoreRemoting.Toolbox
{
/// <summary>
/// Helper class to create disposable primitives.
/// </summary>
public static class Disposable
{
private class SyncDisposable(Action disposeAction) : IDisposable
{
void IDisposable.Dispose() =>
disposeAction?.Invoke();
}

/// <summary>
/// Creates a disposable object.
/// </summary>
/// <param name="disposeAction">An action to invoke on disposal.</param>
public static IDisposable Create(Action disposeAction) =>
new SyncDisposable(disposeAction);

private class AsyncDisposable(
Func<ValueTask> disposeAsync,
Func<Task> disposeTaskAsync) : IAsyncDisposable
{
async ValueTask IAsyncDisposable.DisposeAsync()
{
if (disposeAsync != null)
await disposeAsync();

if (disposeTaskAsync != null)
await disposeTaskAsync();
}
}

/// <summary>
/// Creates an asynchronous disposable object.
/// </summary>
/// <param name="disposeAsync">An action to invoke on disposal.</param>
public static IAsyncDisposable Create(Func<ValueTask> disposeAsync) =>
new AsyncDisposable(disposeAsync, null);

/// <summary>
/// Creates an asynchronous disposable object.
/// </summary>
/// <param name="disposeAsync">An action to invoke on disposal.</param>
public static IAsyncDisposable Create(Func<Task> disposeAsync) =>
new AsyncDisposable(null, disposeAsync);
}
}

0 comments on commit 081e2f3

Please sign in to comment.