Skip to content

Commit

Permalink
Cache redirect proxies (#67)
Browse files Browse the repository at this point in the history
  • Loading branch information
devodo committed Apr 8, 2023
1 parent 229c5f1 commit e760a8e
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 4 deletions.
7 changes: 5 additions & 2 deletions src/DivertR/DiverterSettings.cs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ public class DiverterSettings

public bool DefaultWithDummyRoot { get; }

public bool CacheRedirectProxies { get; }

public IDummyFactory DummyFactory { get; }

public ICallInvoker CallInvoker { get; }
Expand All @@ -41,18 +43,19 @@ public static DiverterSettings Global
}
}

public DiverterSettings(
IProxyFactory? proxyFactory = null,
public DiverterSettings(IProxyFactory? proxyFactory = null,
IDiverterProxyFactory? diverterProxyFactory = null,
IRedirectProxyDecorator? redirectProxyDecorator = null,
bool defaultWithDummyRoot = true,
bool cacheRedirectProxies = true,
IDummyFactory? dummyFactory = null,
ICallInvoker? callInvoker = null)
{
ProxyFactory = proxyFactory ?? new DispatchProxyFactory();
DiverterProxyFactory = diverterProxyFactory ?? new DiverterProxyFactory();
RedirectProxyDecorator = redirectProxyDecorator ?? new RedirectProxyDecorator();
DefaultWithDummyRoot = defaultWithDummyRoot;
CacheRedirectProxies = cacheRedirectProxies;
DummyFactory = dummyFactory ?? new DummyFactory();
CallInvoker = callInvoker ?? DefaultCallInvoker;
}
Expand Down
21 changes: 19 additions & 2 deletions src/DivertR/Redirect.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ public class Redirect<TTarget> : IRedirect<TTarget> where TTarget : class?
private readonly IProxyFactory _proxyFactory;
private readonly Relay<TTarget> _relay;
private readonly RedirectProxyCall<TTarget> _redirectProxyCall;
private readonly ConditionalWeakTable<TTarget, TTarget> _proxyCache = new();

public Redirect(string? name = null, DiverterSettings? diverterSettings = null, IRedirectRepository? redirectRepository = null)
: this(RedirectId.From<TTarget>(name), new RedirectSet(diverterSettings), redirectRepository)
Expand Down Expand Up @@ -102,9 +103,25 @@ public TTarget Proxy(object? root)
[return: NotNull]
public TTarget Proxy(TTarget? root)
{
var proxy = _proxyFactory.CreateProxy(_redirectProxyCall, root);
TTarget proxy;

return RedirectSet.Settings.RedirectProxyDecorator.Decorate(this, proxy);
if (root is null || !RedirectSet.Settings.CacheRedirectProxies)
{
proxy = _proxyFactory.CreateProxy(_redirectProxyCall, root);
RedirectSet.Settings.RedirectProxyDecorator.Decorate(this, proxy);
}
else
{
proxy = _proxyCache.GetValue(root, x =>
{
var createdProxy = _proxyFactory.CreateProxy(_redirectProxyCall, x);
RedirectSet.Settings.RedirectProxyDecorator.Decorate(this, createdProxy);

return createdProxy;
});
}

return proxy!;
}

/// <inheritdoc />
Expand Down
29 changes: 29 additions & 0 deletions test/DivertR.UnitTests/RedirectTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,35 @@ public void GivenInvalidRootObjectType_WhenCreateProxyObject_ShouldThrowArgument
// ASSERT
testAction.ShouldThrow<ArgumentException>();
}

[Fact]
public void GivenDefaultDiverterSettings_WhenCreateProxiesWithSameRootInstance_ShouldCache()
{
// ARRANGE
var foo = new Foo();
var proxy = _redirect.Proxy(foo);

// ACT
var testProxy = _redirect.Proxy(foo);

// ASSERT
testProxy.ShouldBeSameAs(proxy);
}

[Fact]
public void GivenCacheRedirectProxiesDisabled_WhenCreateProxiesWithSameRootInstance_ShouldNotCache()
{
// ARRANGE
var redirect = new Redirect<IFoo>(new DiverterSettings(cacheRedirectProxies: false));
var foo = new Foo();
var proxy = redirect.Proxy(foo);

// ACT
var testProxy = redirect.Proxy(foo);

// ASSERT
testProxy.ShouldNotBeSameAs(proxy);
}

[Fact]
public void GivenStrictModeWithNoVia_ShouldThrowException()
Expand Down

0 comments on commit e760a8e

Please sign in to comment.