-
Notifications
You must be signed in to change notification settings - Fork 2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[STAThread] async Task hangs when executed with Test With > In-Proc (VS SDK) #110
Comments
@jcansdale I wouldn't expect hanging unless a WindowsFormsSynchronizationContext or DispatcherSynchronizationContext was installed; I'd just expect the rest of the method to execute on a non-STA thread. To help me make sure that I properly covered common deadlock situations (nunit/nunit#2776), can you let me know what the type of |
@jnm2, thanks for dropping by. 😄 This is actually a feature of TestDriven.Net that lets execute arbitrary methods inside the inside the VS process. The target assembly mustn't have any dependencies except for assemblies that are resolvable from inside VS. It therefore isn't using any particular test framework. I'm reusing the For example, I can reference
Unfortunately, it turned out the following would deadlock:
This is now fixed by executing the async method using I'm now struggling to test this code using NUnit. I've had some success using Here's an example project with a single test called It works fine with the
I'd be interested to know if there's a way to get it working with your NUnit PR? If you're curious, here's a recent build of TestDriven.Net: |
Oh, thanks for the explanation! 😃 What's going on at https://github.com/AArnott/Xunit.StaFact/tree/master/src/Xunit.StaFact looks eerily similar to the changes I've just made in NUnit. What happens if you try using https://ci.appveyor.com/api/buildjobs/rgabiufm7klv1lc0/artifacts/NUnit.3.11.0-ci-05551-jnm2-sta-sy.nupkg? I'm not quite gathering the steps I need to go through to reproduce the issue you're seeing. You're saying the issue is specific to using NUnit to test TestDriven.NET? |
Yes. It seems to work with Here is a repro: public class MyTests : JoinableTaskTestBase
{
//[StaFact]
[NUnit.Framework.Test]
[NUnit.Framework.Apartment(ApartmentState.STA)]
public void CanSwitchToStaThread()
{
SimulateUIThread(async () =>
{
var jtf = new JoinableTaskFactory(context);
await jtf.RunAsync(async () =>
{
// Get off the UI thread first so that we can transition (back) to it.
await TaskScheduler.Default;
Assert.Equal(ApartmentState.MTA, Thread.CurrentThread.GetApartmentState());
await jtf.SwitchToMainThreadAsync();
Assert.Equal(ApartmentState.STA, Thread.CurrentThread.GetApartmentState());
});
});
}
} You can find the example solution here (with the NUnit build you linked in the When I run with the version of NUnit you linked, I get: If I run the individual method using TestDriven.Net (without any test attributes), it also passes: Any idea why the |
Yes, it's because the fixture is constructed in a normal worker thread but the test method is executed on an STA worker thread. NUnit currently uses the same fixture instance for all test cases inside the fixture. I do have an issue somewhere for an option to construct a fixture per test case, but I'm not sure if we would end up executing the constructor on the same thread. In the meantime, the fix is to apply |
In fact, once you make sure the constructor and test method are running on the same thread by doing that, NUnit 3.10.1 passes the test. |
Thanks for investigating. I'd forgotten about the difference in fixture lifecycle between NUnit and xUnit. The difference in behavior makes sense now.
Does your deadlock mitigation install a message pump for the Main thread? Is there any special attribute required or is it simply a case of |
Yes. With the PR DLL you were testing against, NUnit installs a single-threaded message pump before executing STA tests, so you don't need any boilerplate. Everyone is so strapped for time recently at NUnit, I'm just waiting for someone to reapprove, but I'm confident it's going into 3.11 as-is. |
This PR turns out to be exactly what I need! For my tests to run as expected, I need the following to pass: [Test]
[Apartment(ApartmentState.STA)]
public async Task ApartmentStateAfterYield()
{
await Task.Yield();
Assert.That(Thread.CurrentThread.GetApartmentState(), Is.EqualTo(ApartmentState.STA));
} This passes with your PR, but not the most recent NUnit release.
I'll mention the above test as a comment on that PR. Thanks for your work on this. 👍 |
Yes, that is almost identical to one of the tests added in that PR. You are precisely who this PR is for! 😃 |
The following currently hangs when executed using
Test With > In-Proc (VS SDK)
.This is unfortunate because sometimes you want to do stuff on the Main thread between long running async operations.
Related
https://github.com/Microsoft/vs-threading/blob/master/doc/testing_vs.md
The text was updated successfully, but these errors were encountered: