Skip to content
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

Adding Integration Test project #2196

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<Project Sdk="Microsoft.NET.Sdk">

<Import Project=".\build\testing.targets" />

<PropertyGroup>
<TargetFramework>netcoreapp2.0</TargetFramework>
<IsPackable>false</IsPackable>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.5.0" />
<PackageReference Include="Shouldly" Version="2.8.3" />
<PackageReference Include="xunit" Version="2.3.1" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.3.1" />
<PackageReference Include="Microsoft.AspNetCore.TestHost" Version="2.0.0" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="2.0.0" PrivateAssets="All" />
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="2.0.0" PrivateAssets="All" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\Web-App\AllReady\AllReady.csproj" />
</ItemGroup>

</Project>
70 changes: 70 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/IntegrationTestStartup.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
using System;
using AllReady.DataAccess;
using AllReady.Models;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;

namespace AllReady.IntegrationTests
{
public class IntegrationTestStartup : Startup
{
public IntegrationTestStartup(IConfiguration configuration) : base(configuration)
{
}

protected override void AddDatabaseServices(IServiceCollection services)
{
services
.AddEntityFrameworkInMemoryDatabase()
.AddDbContext<AllReadyContext>(options =>
{
options.UseInMemoryDatabase("InMemory");
});
}

protected override void LoadSeedData(bool purgeRefreshSampleData, SampleDataGenerator sampleDataGenerator)
{
// tests will load their own data? Possibly have some default data instead
}

protected override void MigrateDatabase(bool purgeRefreshSampleData, IHostingEnvironment hostingEnvironment, AllReadyContext context)
{
// for now we load up a default set of data used by all tests - this works for now, but needs review

var campaign = new Campaign
{
EndDateTime = DateTimeOffset.UtcNow.AddDays(10),
Featured = true,
Published = true,
Locked = false,
Name = "Featured Campaign Name",
Description = "This is a featured campaign",
Headline = "This is a featured headline",
ManagingOrganization = new Organization
{
Name = "Test Organisation"
}
};

context.Campaigns.Add(campaign);

context.Events.Add(new Event { Campaign = campaign, Name = "Event Name 1", EndDateTime = DateTimeOffset.UtcNow.AddDays(2) });
context.Events.Add(new Event { Campaign = campaign, Name = "Event Name 2", EndDateTime = DateTimeOffset.UtcNow.AddDays(2) });

context.SaveChanges();
}

protected override void AddHangFire(IServiceCollection services)
{
// do nothing for now - may need to be added later in some form
}

protected override void RegisterHangFire(IApplicationBuilder app)
{
// do nothing for now - may need to be added later in some form
}
}
}
28 changes: 28 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/Pages/AboutTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using System.Net;
using System.Net.Http;
using System.Threading.Tasks;
using Shouldly;
using Xunit;

namespace AllReady.IntegrationTests.Pages
{
public class AboutTests : IClassFixture<TestFixture<IntegrationTestStartup>>
{
private readonly HttpClient _client;

public AboutTests(TestFixture<IntegrationTestStartup> fixture)
{
_client = fixture.Client;
}

[Fact]
public async Task CanGetAboutPage()
{
// Act
var response = await _client.GetAsync("/about");

// Assert
response.StatusCode.ShouldBe(HttpStatusCode.OK);
}
}
}
54 changes: 54 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/Pages/IndexTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
using System.Net;
using System.Net.Http;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using Shouldly;
using Xunit;

namespace AllReady.IntegrationTests.Pages
{
public class IndexTests : IClassFixture<TestFixture<IntegrationTestStartup>>
{
private readonly HttpClient _client;

private const string FeaturedCampaignName = "Featured Campaign Name";

public IndexTests(TestFixture<IntegrationTestStartup> fixture)
{
_client = fixture.Client;
}

[Fact]
public async Task CanGetHomePage()
{
// Act
var response = await _client.GetAsync("/");

// Assert
response.StatusCode.ShouldBe(HttpStatusCode.OK);
}

[Fact]
public async Task IncludesFeaturedCampaign_WhenSet()
{
// Act
var response = await _client.GetAsync("/");
var content = await response.Content.ReadAsStringAsync();

// Assert
content.ShouldContain(FeaturedCampaignName);
}

[Fact]
public async Task IncludesExpectedNumberOfEvents()
{
// Act
var response = await _client.GetAsync("/");
var content = await response.Content.ReadAsStringAsync();

// Assert
var newLineFreeContent = Regex.Replace(content, @"\t|\n|\r|\s+", string.Empty);
Regex.Matches(newLineFreeContent, "</h4><p><b>Campaign:</b>").Count.ShouldBe(2);
}
}
}
28 changes: 28 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/Pages/PrivacyPolicyTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
using System.Net;
using System.Net.Http;
using System.Threading.Tasks;
using Shouldly;
using Xunit;

namespace AllReady.IntegrationTests.Pages
{
public class PrivacyPolicyTests : IClassFixture<TestFixture<IntegrationTestStartup>>
{
private readonly HttpClient _client;

public PrivacyPolicyTests(TestFixture<IntegrationTestStartup> fixture)
{
_client = fixture.Client;
}

[Fact]
public async Task CanGetAboutPage()
{
// Act
var response = await _client.GetAsync("/privacypolicy");

// Assert
response.StatusCode.ShouldBe(HttpStatusCode.OK);
}
}
}
83 changes: 83 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/TestFixture.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
using System;
using System.IO;
using System.Net.Http;
using System.Reflection;
using AllReady.Models;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Mvc.ApplicationParts;
using Microsoft.AspNetCore.Mvc.Controllers;
using Microsoft.AspNetCore.Mvc.ViewComponents;
using Microsoft.AspNetCore.TestHost;
using Microsoft.Extensions.DependencyInjection;

namespace AllReady.IntegrationTests
{
public class TestFixture<TStartup> : IDisposable
{
private readonly TestServer _server;

public TestFixture()
{
var startupAssembly = typeof(TStartup).GetTypeInfo().BaseType.Assembly;
var contentRoot = GetProjectPath(startupAssembly);

var builder = new WebHostBuilder()
.UseContentRoot(contentRoot)
.ConfigureServices(InitializeServices)
.UseEnvironment("Development")
.UseStartup(typeof(TStartup));

_server = new TestServer(builder);

DbContext = _server.Host.Services.GetService(typeof(AllReadyContext)) as AllReadyContext;

Client = _server.CreateClient();
Client.BaseAddress = new Uri("http://localhost");
}

public HttpClient Client { get; }

public AllReadyContext DbContext { get; }

public void Dispose()
{
Client.Dispose();
_server.Dispose();
}

protected virtual void InitializeServices(IServiceCollection services)
{
var startupAssembly = typeof(TStartup).GetTypeInfo().Assembly;
var manager = new ApplicationPartManager();
manager.ApplicationParts.Add(new AssemblyPart(startupAssembly));
manager.FeatureProviders.Add(new ControllerFeatureProvider());
manager.FeatureProviders.Add(new ViewComponentFeatureProvider());
services.AddSingleton(manager);
}

// Get the full path to the target project for testing
private static string GetProjectPath(Assembly startupAssembly)
{
var projectName = startupAssembly.GetName().Name;
var applicationBasePath = System.AppContext.BaseDirectory;
var directoryInfo = new DirectoryInfo(applicationBasePath);
do
{
directoryInfo = directoryInfo.Parent.Parent.Parent.Parent;

var projectDirectoryInfo = new DirectoryInfo(Path.Combine(directoryInfo.FullName, "Web-App"));
if (projectDirectoryInfo.Exists)
{
var projectFileInfo = new FileInfo(Path.Combine(projectDirectoryInfo.FullName, projectName, $"{projectName}.csproj"));
if (projectFileInfo.Exists)
{
return Path.Combine(projectDirectoryInfo.FullName, projectName);
}
}
}
while (directoryInfo.Parent != null);

throw new Exception($"Project root could not be located using the application root {applicationBasePath}.");
}
}
}
25 changes: 25 additions & 0 deletions AllReadyApp/AllReady.IntegrationTests/build/testing.targets
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">

<!--
Work around https://github.com/NuGet/Home/issues/4412. MVC uses DependencyContext.Load() which looks next to a .dll
for a .deps.json. Information isn't available elsewhere. Need the .deps.json file for all web site applications.
-->
<PropertyGroup>
<!--
The functional tests act as the host application for all test websites. Since the CLI copies all reference
assembly dependencies in websites to their corresponding bin/{config}/refs folder we need to re-calculate
reference assemblies for this project so there's a corresponding refs folder in our output. Without it
our websites deps files will fail to find their assembly references.
-->

<PreserveCompilationContext>true</PreserveCompilationContext>
</PropertyGroup>

<Target Name="CopyAditionalFiles" AfterTargets="Build" Condition="'$(TargetFramework)'!=''">
<ItemGroup>
<DepsFilePaths Include="$([System.IO.Path]::ChangeExtension('%(_ResolvedProjectReferencePaths.FullPath)', '.deps.json'))" />
</ItemGroup>

<Copy SourceFiles="%(DepsFilePaths.FullPath)" DestinationFolder="$(OutputPath)" Condition="Exists('%(DepsFilePaths.FullPath)')" />
</Target>
</Project>
15 changes: 11 additions & 4 deletions AllReadyApp/AllReadyWebOnly.sln
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 15
VisualStudioVersion = 15.0.26730.8
VisualStudioVersion = 15.0.27130.0
MinimumVisualStudioVersion = 10.0.40219.1
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Web", "Web", "{2C1DD2C4-73FF-4D1D-9E88-6B413317FC29}"
EndProject
Expand Down Expand Up @@ -32,6 +32,10 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Builds", "Builds", "{79E5CF
EndProject
Project("{F2A71F9B-5D33-465A-A702-920D77279786}") = "AllReady.ScenarioTest", "AllReady.IntegrationTest\AllReady.ScenarioTest.fsproj", "{44055C15-5757-4822-908B-C66B60251C54}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AllReady.IntegrationTests", "AllReady.IntegrationTests\AllReady.IntegrationTests.csproj", "{B45509F1-9C64-4A90-8143-C5D7CDB57904}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "build", "build", "{AECA1833-B3D9-4E87-B64C-042FDDBEFF7B}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand All @@ -58,6 +62,10 @@ Global
{44055C15-5757-4822-908B-C66B60251C54}.Debug|Any CPU.Build.0 = Debug|Any CPU
{44055C15-5757-4822-908B-C66B60251C54}.Release|Any CPU.ActiveCfg = Release|Any CPU
{44055C15-5757-4822-908B-C66B60251C54}.Release|Any CPU.Build.0 = Release|Any CPU
{B45509F1-9C64-4A90-8143-C5D7CDB57904}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{B45509F1-9C64-4A90-8143-C5D7CDB57904}.Debug|Any CPU.Build.0 = Debug|Any CPU
{B45509F1-9C64-4A90-8143-C5D7CDB57904}.Release|Any CPU.ActiveCfg = Release|Any CPU
{B45509F1-9C64-4A90-8143-C5D7CDB57904}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand All @@ -69,9 +77,8 @@ Global
{BFF4752B-274B-47E5-82FD-9B351792FF2D} = {CB31A2DF-9F47-41D5-AD0F-491C98A8D4CB}
{79E5CFB4-6FF7-4F89-B560-9342FFE91898} = {364DE571-98D2-4F69-8D93-F25F832E7D7A}
{44055C15-5757-4822-908B-C66B60251C54} = {1475C1FD-CE7D-4E6B-83B1-F7F82EA24FF8}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {645EFF42-0422-4249-B544-6038D44E3CDE}
{B45509F1-9C64-4A90-8143-C5D7CDB57904} = {1475C1FD-CE7D-4E6B-83B1-F7F82EA24FF8}
{AECA1833-B3D9-4E87-B64C-042FDDBEFF7B} = {1475C1FD-CE7D-4E6B-83B1-F7F82EA24FF8}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {FCAA194F-AD24-45C2-AA51-78C71433DCC0}
Expand Down
Loading