2015-11-22 23:09:37 +03:00
|
|
|
using System;
|
2015-12-01 23:15:55 +03:00
|
|
|
using System.Threading;
|
|
|
|
using System.Threading.Tasks;
|
2022-06-23 18:19:04 +03:00
|
|
|
using Microsoft.Extensions.Logging;
|
2022-07-08 01:42:35 +03:00
|
|
|
using Orleans.Internal;
|
2016-06-18 00:16:52 +03:00
|
|
|
using Orleans.Runtime;
|
2016-10-20 06:33:02 +03:00
|
|
|
using TestExtensions;
|
2015-12-01 23:15:55 +03:00
|
|
|
using UnitTests.GrainInterfaces;
|
2016-01-16 02:37:48 +03:00
|
|
|
using Xunit;
|
2015-12-16 02:57:52 +03:00
|
|
|
|
2016-12-14 01:19:54 +03:00
|
|
|
namespace DefaultCluster.Tests.ActivationsLifeCycleTests
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2016-01-16 02:37:48 +03:00
|
|
|
public class GrainActivateDeactivateTests : HostedTestClusterEnsureDefaultStarted, IDisposable
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
|
|
|
private IActivateDeactivateWatcherGrain watcher;
|
|
|
|
|
2017-01-19 00:39:41 +03:00
|
|
|
public GrainActivateDeactivateTests(DefaultClusterFixture fixture) : base(fixture)
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2017-01-19 00:39:41 +03:00
|
|
|
watcher = this.GrainFactory.GetGrain<IActivateDeactivateWatcherGrain>(0);
|
2015-12-01 23:15:55 +03:00
|
|
|
watcher.Clear().Wait();
|
|
|
|
}
|
|
|
|
|
2019-06-28 01:34:08 +03:00
|
|
|
public virtual void Dispose()
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2016-01-16 02:37:48 +03:00
|
|
|
watcher.Clear().Wait();
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate"), TestCategory("GetGrain")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task WatcherGrain_GetGrain()
|
|
|
|
{
|
2017-01-19 00:39:41 +03:00
|
|
|
IActivateDeactivateWatcherGrain grain = this.GrainFactory.GetGrain<IActivateDeactivateWatcherGrain>(1);
|
2015-12-01 23:15:55 +03:00
|
|
|
await grain.Clear();
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Activate_Simple()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ISimpleActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ISimpleActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 0, activation, "After activation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Deactivate_Simple()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ISimpleActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ISimpleActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation, "After deactivation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Reactivate_Simple()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ISimpleActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ISimpleActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation, "After deactivation");
|
|
|
|
|
|
|
|
// Reactivate
|
|
|
|
string activation2 = await grain.DoSomething();
|
|
|
|
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.NotEqual(activation, activation2); // New activation created after re-activate
|
2015-12-01 23:15:55 +03:00
|
|
|
await CheckNumActivateDeactivateCalls(2, 1, new[] { activation, activation2 }, "After reactivation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Activate_TailCall()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ITailCallActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ITailCallActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 0, activation, "After activation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Deactivate_TailCall()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ITailCallActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ITailCallActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation, "After deactivation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Reactivate_TailCall()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ITailCallActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ITailCallActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation, "After deactivation");
|
|
|
|
|
|
|
|
// Reactivate
|
|
|
|
string activation2 = await grain.DoSomething();
|
|
|
|
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.NotEqual(activation, activation2); // New activation created after re-activate
|
2015-12-01 23:15:55 +03:00
|
|
|
await CheckNumActivateDeactivateCalls(2, 1, new[] { activation, activation2 }, "After reactivation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate"), TestCategory("Reentrancy")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task LongRunning_Deactivate()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ILongRunningActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ILongRunningActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 0, activation, "Before deactivation");
|
|
|
|
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation, "After deactivation");
|
|
|
|
|
|
|
|
// Reactivate
|
|
|
|
string activation2 = await grain.DoSomething();
|
|
|
|
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.NotEqual(activation, activation2); // New activation created after re-activate;
|
2015-12-16 02:57:52 +03:00
|
|
|
|
2015-12-01 23:15:55 +03:00
|
|
|
await CheckNumActivateDeactivateCalls(2, 1, new[] { activation, activation2 }, "After reactivation");
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task BadActivate_Await()
|
|
|
|
{
|
|
|
|
try
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
IBadActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<IBadActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
await grain.ThrowSomething();
|
|
|
|
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.True(false, "Expected ThrowSomething call to fail as unable to Activate grain");
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
2017-08-21 21:29:04 +03:00
|
|
|
catch (ApplicationException exc)
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2017-08-21 21:29:04 +03:00
|
|
|
Assert.Contains("Application-OnActivateAsync", exc.Message);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task BadActivate_GetValue()
|
|
|
|
{
|
|
|
|
try
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
IBadActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<IBadActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
long key = await grain.GetKey();
|
|
|
|
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.True(false, "Expected ThrowSomething call to fail as unable to Activate grain, but returned " + key);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
2017-08-21 21:29:04 +03:00
|
|
|
catch (ApplicationException exc)
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2017-08-21 21:29:04 +03:00
|
|
|
Assert.Contains("Application-OnActivateAsync", exc.Message);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task BadActivate_Await_ViaOtherGrain()
|
|
|
|
{
|
|
|
|
try
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ICreateGrainReferenceTestGrain grain = this.GrainFactory.GetGrain<ICreateGrainReferenceTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
2017-01-19 00:39:41 +03:00
|
|
|
await grain.ForwardCall(this.GrainFactory.GetGrain<IBadActivateDeactivateTestGrain>(id));
|
2015-12-01 23:15:55 +03:00
|
|
|
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.True(false, "Expected ThrowSomething call to fail as unable to Activate grain");
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
2017-08-21 21:29:04 +03:00
|
|
|
catch (ApplicationException exc)
|
2015-12-01 23:15:55 +03:00
|
|
|
{
|
2017-08-21 21:29:04 +03:00
|
|
|
Assert.Contains("Application-OnActivateAsync", exc.Message);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Constructor_Bad_Await()
|
|
|
|
{
|
|
|
|
try
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
IBadConstructorTestGrain grain = this.GrainFactory.GetGrain<IBadConstructorTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
await grain.DoSomething();
|
|
|
|
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.True(false, "Expected ThrowSomething call to fail as unable to Activate grain");
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
catch (TimeoutException te)
|
|
|
|
{
|
|
|
|
Console.WriteLine("Received timeout: " + te);
|
|
|
|
throw; // Fail test
|
|
|
|
}
|
|
|
|
catch (Exception exc)
|
|
|
|
{
|
2016-07-20 21:02:28 +03:00
|
|
|
AssertIsNotInvalidOperationException(exc, "Constructor");
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task Constructor_CreateGrainReference()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ICreateGrainReferenceTestGrain grain = this.GrainFactory.GetGrain<ICreateGrainReferenceTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
string activation = await grain.DoSomething();
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.NotNull(activation);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2015-12-01 23:15:55 +03:00
|
|
|
public async Task TaskAction_Deactivate()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
ITaskActionActivateDeactivateTestGrain grain = this.GrainFactory.GetGrain<ITaskActionActivateDeactivateTestGrain>(id);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
// Activate
|
|
|
|
string activation = await grain.DoSomething();
|
|
|
|
|
|
|
|
// Deactivate
|
|
|
|
await grain.DoDeactivate();
|
|
|
|
Thread.Sleep(TimeSpan.FromSeconds(2)); // Allow some time for deactivate to happen
|
|
|
|
|
|
|
|
await CheckNumActivateDeactivateCalls(1, 1, activation.ToString());
|
|
|
|
}
|
|
|
|
|
2019-10-03 00:11:51 +03:00
|
|
|
[Fact, TestCategory("BVT"), TestCategory("ActivateDeactivate")]
|
2016-01-23 04:42:14 +03:00
|
|
|
public async Task DeactivateOnIdleWhileActivate()
|
|
|
|
{
|
2022-07-08 01:42:35 +03:00
|
|
|
int id = ThreadSafeRandom.Next();
|
2017-01-19 00:39:41 +03:00
|
|
|
IDeactivatingWhileActivatingTestGrain grain = this.GrainFactory.GetGrain<IDeactivatingWhileActivatingTestGrain>(id);
|
2016-01-23 04:42:14 +03:00
|
|
|
|
|
|
|
try
|
|
|
|
{
|
|
|
|
string activation = await grain.DoSomething();
|
2016-05-26 00:03:26 +03:00
|
|
|
Assert.True(false, "Should have thrown.");
|
2016-01-23 04:42:14 +03:00
|
|
|
}
|
2017-08-21 21:29:04 +03:00
|
|
|
catch(InvalidOperationException exc)
|
2016-01-23 04:42:14 +03:00
|
|
|
{
|
2022-06-23 18:19:04 +03:00
|
|
|
this.Logger.LogInformation(exc, "Thrown as expected");
|
2017-08-21 21:29:04 +03:00
|
|
|
Assert.True(
|
|
|
|
exc.Message.Contains("DeactivateOnIdle from within OnActivateAsync"),
|
|
|
|
"Did not get expected exception message returned: " + exc.Message);
|
2016-01-23 04:42:14 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-12-01 23:15:55 +03:00
|
|
|
private async Task CheckNumActivateDeactivateCalls(
|
|
|
|
int expectedActivateCalls,
|
|
|
|
int expectedDeactivateCalls,
|
|
|
|
string forActivation,
|
|
|
|
string when = null)
|
|
|
|
{
|
|
|
|
await CheckNumActivateDeactivateCalls(
|
|
|
|
expectedActivateCalls,
|
|
|
|
expectedDeactivateCalls,
|
|
|
|
new string[] { forActivation },
|
|
|
|
when )
|
|
|
|
;
|
|
|
|
}
|
|
|
|
|
|
|
|
private async Task CheckNumActivateDeactivateCalls(
|
|
|
|
int expectedActivateCalls,
|
|
|
|
int expectedDeactivateCalls,
|
|
|
|
string[] forActivations,
|
|
|
|
string when = null)
|
|
|
|
{
|
|
|
|
string[] activateCalls = await watcher.GetActivateCalls();
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.Equal(expectedActivateCalls, activateCalls.Length);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
string[] deactivateCalls = await watcher.GetDeactivateCalls();
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.Equal(expectedDeactivateCalls, deactivateCalls.Length);
|
2015-12-01 23:15:55 +03:00
|
|
|
|
|
|
|
for (int i = 0; i < expectedActivateCalls; i++)
|
|
|
|
{
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.Equal(forActivations[i], activateCalls[i]);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
for (int i = 0; i < expectedDeactivateCalls; i++)
|
|
|
|
{
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.Equal(forActivations[i], deactivateCalls[i]);
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|
2016-05-30 20:34:26 +03:00
|
|
|
|
2016-07-20 21:02:28 +03:00
|
|
|
private static void AssertIsNotInvalidOperationException(Exception thrownException, string expectedMessageSubstring)
|
2016-05-30 20:34:26 +03:00
|
|
|
{
|
|
|
|
Console.WriteLine("Received exception: " + thrownException);
|
|
|
|
Exception e = thrownException.GetBaseException();
|
|
|
|
Console.WriteLine("Nested exception type: " + e.GetType().FullName);
|
|
|
|
Console.WriteLine("Nested exception message: " + e.Message);
|
|
|
|
|
|
|
|
Assert.IsAssignableFrom<Exception>(e);
|
2016-07-20 21:02:28 +03:00
|
|
|
Assert.False(e is InvalidOperationException);
|
2016-05-30 20:34:26 +03:00
|
|
|
Assert.True(e.Message.Contains(expectedMessageSubstring), "Did not get expected exception message returned: " + e.Message);
|
|
|
|
|
|
|
|
}
|
2015-12-01 23:15:55 +03:00
|
|
|
}
|
|
|
|
}
|