Basic integration tests for NodeServices (#8029)
This commit is contained in:
parent
f79f2e3b12
commit
18c1b994df
|
|
@ -267,6 +267,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.SpaSer
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.SpaServices.Extensions", "SpaServices.Extensions\src\Microsoft.AspNetCore.SpaServices.Extensions.csproj", "{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}"
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.SpaServices.Extensions", "SpaServices.Extensions\src\Microsoft.AspNetCore.SpaServices.Extensions.csproj", "{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}"
|
||||||
EndProject
|
EndProject
|
||||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.NodeServices.Tests", "NodeServices\test\Microsoft.AspNetCore.NodeServices.Tests.csproj", "{B04E9CB6-0D1C-4C21-B626-89B6926A491F}"
|
||||||
|
EndProject
|
||||||
Global
|
Global
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
Debug|Any CPU = Debug|Any CPU
|
Debug|Any CPU = Debug|Any CPU
|
||||||
|
|
@ -1465,6 +1467,18 @@ Global
|
||||||
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x64.Build.0 = Release|Any CPU
|
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x64.Build.0 = Release|Any CPU
|
||||||
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x86.ActiveCfg = Release|Any CPU
|
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x86.ActiveCfg = Release|Any CPU
|
||||||
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x86.Build.0 = Release|Any CPU
|
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07}.Release|x86.Build.0 = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|x64.Build.0 = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Debug|x86.Build.0 = Debug|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|x64.ActiveCfg = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|x64.Build.0 = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|x86.ActiveCfg = Release|Any CPU
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F}.Release|x86.Build.0 = Release|Any CPU
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
HideSolutionNode = FALSE
|
HideSolutionNode = FALSE
|
||||||
|
|
@ -1580,6 +1594,7 @@ Global
|
||||||
{121DFA13-E965-4C91-A175-19EF20DFD5AC} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
{121DFA13-E965-4C91-A175-19EF20DFD5AC} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
||||||
{D9D02772-1D53-45C3-B2CC-888F9978958C} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
{D9D02772-1D53-45C3-B2CC-888F9978958C} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
||||||
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
{5D5B7E54-9323-498A-8983-E9BDFA3B2D07} = {D6FA4ABE-E685-4EDD-8B06-D8777E76B472}
|
||||||
|
{B04E9CB6-0D1C-4C21-B626-89B6926A491F} = {17B409B3-7EC6-49D8-847E-CFAA319E01B5}
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||||
SolutionGuid = {83786312-A93B-4BB4-AB06-7C6913A59AFA}
|
SolutionGuid = {83786312-A93B-4BB4-AB06-7C6913A59AFA}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,13 @@
|
||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFramework>netcoreapp3.0</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<Reference Include="Microsoft.AspNetCore.NodeServices" />
|
||||||
|
<Reference Include="Microsoft.AspNetCore.TestHost" />
|
||||||
|
<Reference Include="Microsoft.Extensions.Logging.Testing" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
||||||
|
|
@ -0,0 +1,134 @@
|
||||||
|
// Copyright (c) .NET Foundation. All rights reserved.
|
||||||
|
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||||
|
|
||||||
|
using Microsoft.AspNetCore.NodeServices.HostingModels;
|
||||||
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
|
using System;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Xunit;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNetCore.NodeServices
|
||||||
|
{
|
||||||
|
public class NodeServicesTest : IDisposable
|
||||||
|
{
|
||||||
|
private readonly INodeServices _nodeServices;
|
||||||
|
|
||||||
|
public NodeServicesTest()
|
||||||
|
{
|
||||||
|
// In typical ASP.NET Core applications, INodeServices is made available
|
||||||
|
// through DI using services.AddNodeServices(). But for these tests we
|
||||||
|
// create our own INodeServices instance manually, since the tests are
|
||||||
|
// not about DI (and we might want different config for each test).
|
||||||
|
var serviceProvider = new ServiceCollection().BuildServiceProvider();
|
||||||
|
var options = new NodeServicesOptions(serviceProvider);
|
||||||
|
_nodeServices = NodeServicesFactory.CreateNodeServices(options);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanGetSuccessResult()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
var result = await _nodeServices.InvokeExportAsync<string>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"getFixedString");
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("test result", result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanGetErrorResult()
|
||||||
|
{
|
||||||
|
// Act/Assert
|
||||||
|
var ex = await Assert.ThrowsAsync<NodeInvocationException>(() =>
|
||||||
|
_nodeServices.InvokeExportAsync<string>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"raiseError"));
|
||||||
|
Assert.StartsWith("This is an error from Node", ex.Message);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanGetResultAsynchronously()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
// All the invocations are async, but this test shows we're not reliant
|
||||||
|
// on the response coming back immediately
|
||||||
|
var result = await _nodeServices.InvokeExportAsync<string>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"getFixedStringWithDelay");
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("delayed test result", result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanPassParameters()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
var result = await _nodeServices.InvokeExportAsync<string>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"echoSimpleParameters",
|
||||||
|
"Hey",
|
||||||
|
123);
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("Param0: Hey; Param1: 123", result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanPassParametersWithCamelCaseNameConversion()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
var result = await _nodeServices.InvokeExportAsync<string>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"echoComplexParameters",
|
||||||
|
new ComplexModel { StringProp = "Abc", IntProp = 123, BoolProp = true });
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("Received: [{\"stringProp\":\"Abc\",\"intProp\":123,\"boolProp\":true}]", result);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanReceiveComplexResultWithPascalCaseNameConversion()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
var result = await _nodeServices.InvokeExportAsync<ComplexModel>(
|
||||||
|
ModulePath("testCases"),
|
||||||
|
"getComplexObject");
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("Hi from Node", result.StringProp);
|
||||||
|
Assert.Equal(456, result.IntProp);
|
||||||
|
Assert.True(result.BoolProp);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task CanInvokeDefaultModuleExport()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
var result = await _nodeServices.InvokeAsync<string>(
|
||||||
|
ModulePath("moduleWithDefaultExport"),
|
||||||
|
"This is from .NET");
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Assert.Equal("Hello from the default export. You passed: This is from .NET", result);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static string ModulePath(string testModuleName)
|
||||||
|
=> $"../../../js/{testModuleName}";
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
_nodeServices.Dispose();
|
||||||
|
}
|
||||||
|
|
||||||
|
class ComplexModel
|
||||||
|
{
|
||||||
|
public string StringProp { get; set; }
|
||||||
|
|
||||||
|
public int IntProp { get; set; }
|
||||||
|
|
||||||
|
public bool BoolProp { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
module.exports = function (callback, message) {
|
||||||
|
callback(null, `Hello from the default export. You passed: ${message}`);
|
||||||
|
};
|
||||||
|
|
@ -0,0 +1,28 @@
|
||||||
|
// Function signatures follow Node conventions.
|
||||||
|
// i.e., parameters: (callback, arg0, arg1, ... etc ...)
|
||||||
|
// When done, functions must invoke 'callback', passing (errorInfo, result)
|
||||||
|
// where errorInfo should be null/undefined if there was no error.
|
||||||
|
|
||||||
|
exports.getFixedString = function (callback) {
|
||||||
|
callback(null, 'test result');
|
||||||
|
};
|
||||||
|
|
||||||
|
exports.getFixedStringWithDelay = function (callback) {
|
||||||
|
setTimeout(callback(null, 'delayed test result'), 100);
|
||||||
|
};
|
||||||
|
|
||||||
|
exports.raiseError = function (callback) {
|
||||||
|
callback('This is an error from Node');
|
||||||
|
};
|
||||||
|
|
||||||
|
exports.echoSimpleParameters = function (callback, param0, param1) {
|
||||||
|
callback(null, `Param0: ${param0}; Param1: ${param1}`);
|
||||||
|
};
|
||||||
|
|
||||||
|
exports.echoComplexParameters = function (callback, ...otherArgs) {
|
||||||
|
callback(null, `Received: ${JSON.stringify(otherArgs)}`);
|
||||||
|
};
|
||||||
|
|
||||||
|
exports.getComplexObject = function (callback) {
|
||||||
|
callback(null, { stringProp: 'Hi from Node', intProp: 456, boolProp: true });
|
||||||
|
};
|
||||||
Loading…
Reference in New Issue