Microsoft Visual Studio Solution File, Format Version 12.00
-# Visual Studio Version 15
-VisualStudioVersion = 15.0.27527.1
+# Visual Studio Version 16
+VisualStudioVersion = 16.0.28803.352
MinimumVisualStudioVersion = 10.0.40219.1
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{5A29E8E3-A0FC-4C57-81DD-297B56D1A119}"
ProjectSection(SolutionItems) = preProject
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.NET.HostModel", "src\managed\Microsoft.NET.HostModel\Microsoft.NET.HostModel.csproj", "{325FB7F2-2E2E-422D-ADAA-F0B63E84CF24}"
EndProject
-Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.NET.HostModel.Tests", "src\test\Microsoft.NET.HostModel.Tests\Microsoft.NET.HostModel.Tests.csproj", "{3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}"
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AppHost.Bundle.Tests", "src\test\BundleTests\AppHost.Bundle.Tests\AppHost.Bundle.Tests.csproj", "{2745A51D-3425-4F68-8349-A8B8BC27DD87}"
+EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.NET.HostModel.Bundle.Tests", "src\test\BundleTests\Microsoft.NET.HostModel.Bundle.Tests\Microsoft.NET.HostModel.Bundle.Tests.csproj", "{1E76A78E-9E39-480D-8CD3-B7D0A858FECB}"
+EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "BundleHelper", "src\test\BundleTests\Helpers\BundleHelper.csproj", "{8116F946-FB24-4524-9028-43F5A3A80EE3}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
{325FB7F2-2E2E-422D-ADAA-F0B63E84CF24}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
{325FB7F2-2E2E-422D-ADAA-F0B63E84CF24}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
{325FB7F2-2E2E-422D-ADAA-F0B63E84CF24}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Debug|Any CPU.Build.0 = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Debug|x64.ActiveCfg = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Debug|x64.Build.0 = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.MinSizeRel|Any CPU.ActiveCfg = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.MinSizeRel|Any CPU.Build.0 = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.MinSizeRel|x64.ActiveCfg = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.MinSizeRel|x64.Build.0 = Debug|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Release|Any CPU.ActiveCfg = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Release|Any CPU.Build.0 = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Release|x64.ActiveCfg = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.Release|x64.Build.0 = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.RelWithDebInfo|Any CPU.ActiveCfg = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Debug|x64.Build.0 = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.MinSizeRel|Any CPU.ActiveCfg = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.MinSizeRel|Any CPU.Build.0 = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.MinSizeRel|x64.ActiveCfg = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.MinSizeRel|x64.Build.0 = Debug|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Release|Any CPU.Build.0 = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Release|x64.ActiveCfg = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.Release|x64.Build.0 = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.RelWithDebInfo|Any CPU.ActiveCfg = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Debug|x64.Build.0 = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.MinSizeRel|Any CPU.ActiveCfg = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.MinSizeRel|Any CPU.Build.0 = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.MinSizeRel|x64.ActiveCfg = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.MinSizeRel|x64.Build.0 = Debug|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Release|Any CPU.Build.0 = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Release|x64.ActiveCfg = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.Release|x64.Build.0 = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.RelWithDebInfo|Any CPU.ActiveCfg = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Debug|x64.Build.0 = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.MinSizeRel|Any CPU.ActiveCfg = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.MinSizeRel|Any CPU.Build.0 = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.MinSizeRel|x64.ActiveCfg = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.MinSizeRel|x64.Build.0 = Debug|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Release|Any CPU.Build.0 = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Release|x64.ActiveCfg = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.Release|x64.Build.0 = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.RelWithDebInfo|Any CPU.ActiveCfg = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
+ {8116F946-FB24-4524-9028-43F5A3A80EE3}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
{D86A859D-E6FA-4E73-A255-5776FC473A25} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
{D6676666-D14D-4DFA-88FB-76E3E823E2E1} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
{325FB7F2-2E2E-422D-ADAA-F0B63E84CF24} = {FAA448DA-7D1C-4481-915D-5765BF906332}
- {3D07933E-8A4B-4C9A-92FD-473B5C4F71E2} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
+ {2745A51D-3425-4F68-8349-A8B8BC27DD87} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
+ {1E76A78E-9E39-480D-8CD3-B7D0A858FECB} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
+ {8116F946-FB24-4524-9028-43F5A3A80EE3} = {5CE8410C-3100-4F41-8FA9-E6B4132D9703}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {28B9726D-802B-478D-AF7A-B9243B9E180B}
readonly string RuntimeConfigDevJson;
readonly Trace trace;
+ public readonly Manifest BundleManifest;
/// <summary>
/// Align embedded assemblies such that they can be loaded
EmbedPDBs = embedPDBs;
trace = new Trace(diagnosticOutput);
+ BundleManifest = new Manifest();
}
/// <summary>
{
trace.Log($"Bundler version {Version}");
- string bundlePath = Path.Combine(OutputDir, HostName);
- if (File.Exists(bundlePath))
+ if (fileSpecs.Any(x => !x.IsValid()))
{
- trace.Log($"Ovewriting existing File {bundlePath}");
+ throw new ArgumentException("Invalid input specification: Found entry with empty source-path or bundle-relative-path.");
}
string hostSource;
throw new ArgumentException("Input must uniquely specify the host binary");
}
+ string bundlePath = Path.Combine(OutputDir, HostName);
+ if (File.Exists(bundlePath))
+ {
+ trace.Log($"Ovewriting existing File {bundlePath}");
+ }
+
// Start with a copy of the host executable.
// Copy the file to preserve its permissions.
File.Copy(hostSource, bundlePath, overwrite: true);
using (BinaryWriter writer = new BinaryWriter(File.OpenWrite(bundlePath)))
{
- Manifest manifest = new Manifest();
Stream bundle = writer.BaseStream;
bundle.Position = bundle.Length;
FileType type = InferType(fileSpec.BundleRelativePath, file);
long startOffset = AddToBundle(bundle, file, type);
FileEntry entry = new FileEntry(type, fileSpec.BundleRelativePath, startOffset, file.Length);
- manifest.Files.Add(entry);
+ BundleManifest.Files.Add(entry);
trace.Log($"Embed: {entry}");
}
}
// Write the bundle manifest
- long manifestOffset = manifest.Write(writer);
+ long manifestOffset = BundleManifest.Write(writer);
trace.Log($"Manifest: Offset={manifestOffset}, Size={writer.BaseStream.Position - manifestOffset}");
trace.Log($"Bundle: Path={bundlePath} Size={bundle.Length}");
}
{
trace.Log($"Extract: {entry}");
- string fileRelativePath = entry.RelativePath.Replace(Manifest.DirectorySeparatorChar, Path.DirectorySeparatorChar);
+ string fileRelativePath = entry.RelativePath.Replace(FileEntry.DirectorySeparatorChar, Path.DirectorySeparatorChar);
string filePath = Path.Combine(OutputDir, fileRelativePath);
string fileDir = Path.GetDirectoryName(filePath);
/// </summary>
public class FileEntry
{
- public long Offset;
- public long Size;
- public FileType Type;
- public string RelativePath; // Path of an embedded file, relative to the Bundle source-directory.
+ public readonly long Offset;
+ public readonly long Size;
+ public readonly FileType Type;
+ public readonly string RelativePath; // Path of an embedded file, relative to the Bundle source-directory.
+
+ public const char DirectorySeparatorChar = '/';
public FileEntry(FileType fileType, string relativePath, long offset, long size)
{
Type = fileType;
- RelativePath = relativePath.Replace(Path.DirectorySeparatorChar, Manifest.DirectorySeparatorChar);
+ RelativePath = relativePath.Replace(Path.DirectorySeparatorChar, DirectorySeparatorChar);
Offset = offset;
Size = size;
}
/// </summary>
public struct FileSpec
{
- public string SourcePath;
- public string BundleRelativePath;
+ public readonly string SourcePath;
+ public readonly string BundleRelativePath;
public FileSpec(string sourcePath, string bundleRelativePath)
{
SourcePath = sourcePath;
BundleRelativePath = bundleRelativePath;
}
+
+ public bool IsValid()
+ {
+ return !string.IsNullOrWhiteSpace(SourcePath) &&
+ !string.IsNullOrWhiteSpace(BundleRelativePath);
+ }
}
}
public const string Signature = ".NetCoreBundle";
public const uint MajorVersion = 0;
public const uint MinorVersion = 1;
- public const char DirectorySeparatorChar = '/';
// Bundle ID is a string that is used to uniquely
// identify this bundle. It is choosen to be compatible
// with path-names so that the AppHost can use it in
// extraction path.
- string BundleID;
+ public readonly string BundleID;
public List<FileEntry> Files;
BundleID = Path.GetRandomFileName();
}
+ public Manifest(string bundleID)
+ {
+ Files = new List<FileEntry>();
+ BundleID = bundleID;
+ }
+
public long Write(BinaryWriter writer)
{
long startOffset = writer.BaseStream.Position;
public static Manifest Read(BinaryReader reader)
{
- Manifest manifest = new Manifest();
-
// Read the manifest footer
// signatureSize is one byte longer, for the length encoding.
uint majorVersion = reader.ReadUInt32();
uint minorVersion = reader.ReadUInt32();
int fileCount = reader.ReadInt32();
- manifest.BundleID = reader.ReadString(); // Bundle ID
+ string bundleID = reader.ReadString(); // Bundle ID
if (majorVersion != MajorVersion || minorVersion != MinorVersion)
{
}
// Read the manifest entries
+ Manifest manifest = new Manifest(bundleID);
for (long i = 0; i < fileCount; i++)
{
manifest.Files.Add(FileEntry.Read(reader));
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
- <TargetFramework>$(NETCoreAppFramework)</TargetFramework>
+ <TargetFramework>netcoreapp3.0</TargetFramework>
<OutputType>Exe</OutputType>
<RuntimeIdentifier>$(TestTargetRid)</RuntimeIdentifier>
<RuntimeFrameworkVersion>$(MNAVersion)</RuntimeFrameworkVersion>
<ItemGroup>
<FilesToCopy Include="$(MSBuildThisFileDirectory)\Sentence\**\*.*" />
</ItemGroup>
-
+
<Copy SourceFiles="@(FilesToCopy)" DestinationFolder="$(PublishDir)\Sentence\%(RecursiveDir)" SkipUnchangedFiles="true"/>
</Target>
using System.IO;
using System.Reflection;
-namespace StandaloneAppWithSubDirs
+namespace AppWithSubDirs
{
public static class Program
{
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
- <Description>Microsoft.NET.HostModel.Tests</Description>
+ <Description>Apphost Bundle Tests</Description>
<TargetFramework>netcoreapp2.0</TargetFramework>
- <AssemblyName>Microsoft.NET.HostModel.Tests</AssemblyName>
- <PackageId>Microsoft.NET.HostModel.Tests</PackageId>
+ <AssemblyName>AppHost.Bundle.Tests</AssemblyName>
+ <PackageId>AppHost.Bundle.Tests</PackageId>
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
</PropertyGroup>
<ItemGroup>
- <ProjectReference Include="..\TestUtils\TestUtils.csproj" />
+ <ProjectReference Include="..\..\TestUtils\TestUtils.csproj" />
+ <ProjectReference Include="..\..\..\managed\Microsoft.NET.HostModel\Microsoft.NET.HostModel.csproj" />
+ <ProjectReference Include="..\Helpers\BundleHelper.csproj" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.3.0" />
<PackageReference Include="xunit" Version="2.2.0" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.2.0" />
- <ProjectReference Include="..\..\managed\Microsoft.NET.HostModel\Microsoft.NET.HostModel.csproj" />
</ItemGroup>
</Project>
--- /dev/null
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.IO;
+using System.Threading;
+using Xunit;
+using Microsoft.DotNet.Cli.Build.Framework;
+using Microsoft.DotNet.CoreSetup.Test;
+using BundleTests.Helpers;
+
+namespace AppHost.Bundle.Tests
+{
+ public class BundleExtractToSpecificPath : IClassFixture<BundleExtractToSpecificPath.SharedTestState>
+ {
+ private SharedTestState sharedTestState;
+
+ public BundleExtractToSpecificPath(SharedTestState fixture)
+ {
+ sharedTestState = fixture;
+ }
+
+ [Fact]
+ private void Bundle_Extraction_To_Specific_Path_Succeeds()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+ var hostName = BundleHelper.GetHostName(fixture);
+ var appName = Path.GetFileNameWithoutExtension(hostName);
+ string publishPath = BundleHelper.GetPublishPath(fixture);
+
+ // Publish the bundle
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+ var bundler = new Microsoft.NET.HostModel.Bundle.Bundler(hostName, bundleDir.FullName);
+ string singleFile = bundler.GenerateBundle(publishPath);
+
+ // Compute bundled files
+ var bundledFiles = bundler.BundleManifest.Files.Select(file => file.RelativePath).ToList();
+
+ // Verify expected files in the bundle directory
+ bundleDir.Should().HaveFile(hostName);
+ bundleDir.Should().NotHaveFiles(bundledFiles);
+
+ // Create a directory for extraction.
+ var extractBaseDir = BundleHelper.GetExtractDir(fixture);
+ extractBaseDir.Should().NotHaveDirectory(appName);
+
+ // Run the bundled app for the first time, and extract files to
+ // $DOTNET_BUNDLE_EXTRACT_BASE_DIR/<app>/bundle-id
+ Command.Create(singleFile)
+ .CaptureStdErr()
+ .CaptureStdOut()
+ .EnvironmentVariable(BundleHelper.DotnetBundleExtractBaseEnvVariable, extractBaseDir.FullName)
+ .Execute()
+ .Should()
+ .Pass()
+ .And
+ .HaveStdOutContaining("Hello World");
+
+ string extractPath = Path.Combine(extractBaseDir.FullName, appName, bundler.BundleManifest.BundleID);
+ var extractDir = new DirectoryInfo(extractPath);
+ extractDir.Should().OnlyHaveFiles(bundledFiles);
+ extractDir.Should().NotHaveFile(hostName);
+ }
+
+ [Fact]
+ private void Bundle_extraction_is_reused()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+ var hostName = BundleHelper.GetHostName(fixture);
+ var appName = Path.GetFileNameWithoutExtension(hostName);
+ string publishPath = BundleHelper.GetPublishPath(fixture);
+
+ // Publish the bundle
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+ var bundler = new Microsoft.NET.HostModel.Bundle.Bundler(hostName, bundleDir.FullName);
+ string singleFile = bundler.GenerateBundle(publishPath);
+
+ // Create a directory for extraction.
+ var extractBaseDir = BundleHelper.GetExtractDir(fixture);
+
+ // Run the bunded app for the first time, and extract files to
+ // $DOTNET_BUNDLE_EXTRACT_BASE_DIR/<app>/bundle-id
+ Command.Create(singleFile)
+ .CaptureStdErr()
+ .CaptureStdOut()
+ .EnvironmentVariable(BundleHelper.DotnetBundleExtractBaseEnvVariable, extractBaseDir.FullName)
+ .Execute()
+ .Should()
+ .Pass()
+ .And
+ .HaveStdOutContaining("Hello World");
+
+ string extractPath = Path.Combine(extractBaseDir.FullName, appName, bundler.BundleManifest.BundleID);
+ var extractDir = new DirectoryInfo(extractPath);
+
+ extractDir.Refresh();
+ DateTime firstWriteTime = extractDir.LastWriteTimeUtc;
+
+ while (DateTime.Now == firstWriteTime)
+ {
+ Thread.Sleep(1);
+ }
+
+ // Run the bundled app again (reuse extracted files)
+ Command.Create(singleFile)
+ .CaptureStdErr()
+ .CaptureStdOut()
+ .EnvironmentVariable(BundleHelper.DotnetBundleExtractBaseEnvVariable, extractBaseDir.FullName)
+ .Execute()
+ .Should()
+ .Pass()
+ .And
+ .HaveStdOutContaining("Hello World");
+
+ extractDir.Should().NotBeModifiedAfter(firstWriteTime);
+ }
+
+
+ public class SharedTestState : IDisposable
+ {
+ public TestProjectFixture TestFixture { get; set; }
+ public RepoDirectoriesProvider RepoDirectories { get; set; }
+
+ public SharedTestState()
+ {
+ RepoDirectories = new RepoDirectoriesProvider();
+ TestFixture = new TestProjectFixture("StandaloneApp", RepoDirectories);
+ TestFixture
+ .EnsureRestoredForRid(TestFixture.CurrentRid, RepoDirectories.CorehostPackages)
+ .PublishProject(runtime: TestFixture.CurrentRid,
+ outputDirectory: BundleHelper.GetPublishPath(TestFixture));
+ }
+
+ public void Dispose()
+ {
+ TestFixture.Dispose();
+ }
+ }
+ }
+}
--- /dev/null
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System;
+using Xunit;
+using Microsoft.DotNet.Cli.Build.Framework;
+using BundleTests.Helpers;
+using Microsoft.DotNet.CoreSetup.Test;
+
+namespace AppHost.Bundle.Tests
+{
+ public class BundledAppWithSubDirs : IClassFixture<BundledAppWithSubDirs.SharedTestState>
+ {
+ private SharedTestState sharedTestState;
+
+ public BundledAppWithSubDirs(SharedTestState fixture)
+ {
+ sharedTestState = fixture;
+ }
+
+ private void RunTheApp(string path)
+ {
+ Command.Create(path)
+ .CaptureStdErr()
+ .CaptureStdOut()
+ .Execute()
+ .Should()
+ .Pass()
+ .And
+ .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
+ }
+
+ [Fact]
+ private void Bundled_Framework_dependent_App_Run_Succeeds()
+ {
+ var fixture = sharedTestState.TestFrameworkDependentFixture.Copy();
+ var singleFile = BundleHelper.BundleApp(fixture);
+
+ // Run the bundled app (extract files)
+ RunTheApp(singleFile);
+
+ // Run the bundled app again (reuse extracted files)
+ RunTheApp(singleFile);
+ }
+
+ [Fact]
+ private void Bundled_Self_Contained_App_Run_Succeeds()
+ {
+ var fixture = sharedTestState.TestSelfContainedFixture.Copy();
+ var singleFile = BundleHelper.BundleApp(fixture);
+
+ // Run the bundled app (extract files)
+ RunTheApp(singleFile);
+
+ // Run the bundled app again (reuse extracted files)
+ RunTheApp(singleFile);
+ }
+
+ public class SharedTestState : IDisposable
+ {
+ public TestProjectFixture TestFrameworkDependentFixture { get; set; }
+ public TestProjectFixture TestSelfContainedFixture { get; set; }
+ public RepoDirectoriesProvider RepoDirectories { get; set; }
+
+ public SharedTestState()
+ {
+ RepoDirectories = new RepoDirectoriesProvider();
+
+ TestFrameworkDependentFixture = new TestProjectFixture("AppWithSubDirs", RepoDirectories);
+ TestFrameworkDependentFixture
+ .EnsureRestoredForRid(TestFrameworkDependentFixture.CurrentRid, RepoDirectories.CorehostPackages)
+ .PublishProject(runtime: TestFrameworkDependentFixture.CurrentRid,
+ outputDirectory: BundleHelper.GetPublishPath(TestFrameworkDependentFixture));
+
+ TestSelfContainedFixture = new TestProjectFixture("AppWithSubDirs", RepoDirectories);
+ TestSelfContainedFixture
+ .EnsureRestoredForRid(TestSelfContainedFixture.CurrentRid, RepoDirectories.CorehostPackages)
+ .PublishProject(runtime: TestSelfContainedFixture.CurrentRid,
+ outputDirectory: BundleHelper.GetPublishPath(TestSelfContainedFixture));
+ }
+
+ public void Dispose()
+ {
+ TestFrameworkDependentFixture.Dispose();
+ TestSelfContainedFixture.Dispose();
+ }
+ }
+ }
+}
--- /dev/null
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System.IO;
+using Microsoft.DotNet.CoreSetup.Test;
+
+namespace BundleTests.Helpers
+{
+ public static class BundleHelper
+ {
+ public const string DotnetBundleExtractBaseEnvVariable = "DOTNET_BUNDLE_EXTRACT_BASE_DIR";
+ public static string GetHostName(TestProjectFixture fixture)
+ {
+ return Path.GetFileName(fixture.TestProject.AppExe);
+ }
+
+ public static string GetPublishPath(TestProjectFixture fixture)
+ {
+ return Path.Combine(fixture.TestProject.ProjectDirectory, "publish");
+ }
+
+ public static DirectoryInfo GetBundleDir(TestProjectFixture fixture)
+ {
+ return Directory.CreateDirectory(Path.Combine(fixture.TestProject.ProjectDirectory, "bundle"));
+ }
+
+ public static DirectoryInfo GetExtractDir(TestProjectFixture fixture)
+ {
+ return Directory.CreateDirectory(Path.Combine(fixture.TestProject.ProjectDirectory, "extract"));
+ }
+
+ // Bundle to a single-file
+ // This step should be removed in favor of publishing with /p:PublishSingleFile=true
+ // once core-setup tests use 3.0 SDK
+ public static string BundleApp(TestProjectFixture fixture)
+ {
+ var hostName = GetHostName(fixture);
+ string publishPath = GetPublishPath(fixture);
+ var bundleDir = GetBundleDir(fixture);
+
+ var bundler = new Microsoft.NET.HostModel.Bundle.Bundler(hostName, bundleDir.FullName);
+ string singleFile = bundler.GenerateBundle(publishPath);
+ return singleFile;
+ }
+
+ }
+}
--- /dev/null
+<Project Sdk="Microsoft.NET.Sdk">
+
+ <PropertyGroup>
+ <Description>Bundle Test Helpers</Description>
+ <TargetFramework>netcoreapp2.0</TargetFramework>
+ <AssemblyName>BundleHelper</AssemblyName>
+ <GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
+ </PropertyGroup>
+
+ <ItemGroup>
+ <ProjectReference Include="..\..\TestUtils\TestUtils.csproj" />
+ <ProjectReference Include="..\..\..\managed\Microsoft.NET.HostModel\Microsoft.NET.HostModel.csproj" />
+ </ItemGroup>
+
+ <ItemGroup>
+ <PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.3.0" />
+ </ItemGroup>
+
+</Project>
--- /dev/null
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System;
+using System.IO;
+using Xunit;
+using Microsoft.DotNet.Cli.Build.Framework;
+using Microsoft.DotNet.CoreSetup.Test;
+using Microsoft.NET.HostModel.Bundle;
+using BundleTests.Helpers;
+
+namespace Microsoft.NET.HostModel.Tests
+{
+ public class BundleExtractRun : IClassFixture<BundleExtractRun.SharedTestState>
+ {
+ private SharedTestState sharedTestState;
+
+ public BundleExtractRun(BundleExtractRun.SharedTestState fixture)
+ {
+ sharedTestState = fixture;
+ }
+
+ public void RunTheApp(string path)
+ {
+ Command.Create(path)
+ .CaptureStdErr()
+ .CaptureStdOut()
+ .Execute()
+ .Should()
+ .Pass()
+ .And
+ .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
+ }
+
+ private void BundleExtractAndRun(TestProjectFixture fixture, string publishDir, string singleFileDir)
+ {
+ var hostName = BundleHelper.GetHostName(fixture);
+
+ // Run the App normally
+ RunTheApp(Path.Combine(publishDir, hostName));
+
+ // Bundle to a single-file
+ Bundler bundler = new Bundler(hostName, singleFileDir);
+ string singleFile = bundler.GenerateBundle(publishDir);
+
+ // Extract the file
+ Extractor extractor = new Extractor(singleFile, singleFileDir);
+ extractor.ExtractFiles();
+
+ // Run the extracted app
+ RunTheApp(singleFile);
+ }
+
+ private string RelativePath(string path)
+ {
+ return Path.GetRelativePath(Directory.GetCurrentDirectory(), path)
+ .TrimEnd(Path.DirectorySeparatorChar);
+ }
+
+ [Fact]
+ public void TestWithAbsolutePaths()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ string publishDir = BundleHelper.GetPublishPath(fixture);
+ string outputDir = BundleHelper.GetBundleDir(fixture).FullName;
+
+ BundleExtractAndRun(fixture, publishDir, outputDir);
+ }
+
+ [Fact]
+ public void TestWithRelativePaths()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ string publishDir = RelativePath(BundleHelper.GetPublishPath(fixture));
+ string outputDir = RelativePath(BundleHelper.GetBundleDir(fixture).FullName);
+
+ BundleExtractAndRun(fixture, publishDir, outputDir);
+ }
+
+ [Fact]
+ public void TestWithRelativePathsDirSeparator()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ string publishDir = RelativePath(BundleHelper.GetPublishPath(fixture)) + Path.DirectorySeparatorChar;
+ string outputDir = RelativePath(BundleHelper.GetBundleDir(fixture).FullName) + Path.DirectorySeparatorChar;
+
+ BundleExtractAndRun(fixture, publishDir, outputDir);
+ }
+
+ public class SharedTestState : IDisposable
+ {
+ public TestProjectFixture TestFixture { get; set; }
+ public RepoDirectoriesProvider RepoDirectories { get; set; }
+
+ public SharedTestState()
+ {
+ RepoDirectories = new RepoDirectoriesProvider();
+
+ TestFixture = new TestProjectFixture("AppWithSubDirs", RepoDirectories);
+ TestFixture
+ .EnsureRestoredForRid(TestFixture.CurrentRid, RepoDirectories.CorehostPackages)
+ .PublishProject(runtime: TestFixture.CurrentRid,
+ outputDirectory: BundleHelper.GetPublishPath(TestFixture));
+ }
+
+ public void Dispose()
+ {
+ TestFixture.Dispose();
+ }
+ }
+ }
+}
--- /dev/null
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using Xunit;
+using Microsoft.DotNet.CoreSetup.Test;
+using Microsoft.NET.HostModel.Bundle;
+using BundleTests.Helpers;
+
+namespace Microsoft.NET.HostModel.Tests
+{
+ public class BundlerConsistencyTests : IClassFixture<BundlerConsistencyTests.SharedTestState>
+ {
+ private SharedTestState sharedTestState;
+
+ public BundlerConsistencyTests(SharedTestState fixture)
+ {
+ sharedTestState = fixture;
+ }
+
+ [Fact]
+ public void TestWithEmptySpecFails()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ var hostName = BundleHelper.GetHostName(fixture);
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+ Bundler bundler = new Bundler(hostName, bundleDir.FullName);
+
+ FileSpec[][] invalidSpecs =
+ {
+ new FileSpec[] {new FileSpec(hostName, null) },
+ new FileSpec[] {new FileSpec(hostName, "") },
+ new FileSpec[] {new FileSpec(hostName, " ") }
+ };
+
+ foreach (var invalidSpec in invalidSpecs)
+ {
+ Assert.Throws<ArgumentException>(() => bundler.GenerateBundle(invalidSpec));
+ }
+ }
+
+ [Fact]
+ public void TestWithoutSpecifyingHostFails()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ var hostName = BundleHelper.GetHostName(fixture);
+ var appName = Path.GetFileNameWithoutExtension(hostName);
+ string publishPath = BundleHelper.GetPublishPath(fixture);
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+
+ // Generate a file specification without the apphost
+ var fileSpecs = new List<FileSpec>();
+ string[] files = { $"{appName}.dll", $"{appName}.deps.json", $"{appName}.runtimeconfig.json" };
+ Array.ForEach(files, x => fileSpecs.Add(new FileSpec(x, x)));
+
+ Bundler bundler = new Bundler(hostName, bundleDir.FullName);
+
+ Assert.Throws<ArgumentException>(() => bundler.GenerateBundle(fileSpecs));
+ }
+
+ [InlineData(true)]
+ [InlineData(false)]
+ [Theory]
+ public void TestFilesNotBundled(bool embedPDBs)
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ var hostName = BundleHelper.GetHostName(fixture);
+ var appName = Path.GetFileNameWithoutExtension(hostName);
+ string publishPath = BundleHelper.GetPublishPath(fixture);
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+
+ // Make up a app.runtimeconfig.dev.json file in the publish directory.
+ File.Copy(Path.Combine(publishPath, $"{appName}.runtimeconfig.json"),
+ Path.Combine(publishPath, $"{appName}.runtimeconfig.dev.json"));
+
+ var singleFile = new Bundler(hostName, bundleDir.FullName, embedPDBs).GenerateBundle(publishPath);
+
+ bundleDir.Should().OnlyHaveFiles(new string[] { hostName });
+
+ new Extractor(singleFile, bundleDir.FullName).ExtractFiles();
+
+ bundleDir.Should().NotHaveFile($"{appName}.runtimeconfig.dev.json");
+ if (!embedPDBs)
+ {
+ bundleDir.Should().NotHaveFile($"{appName}.pdb");
+ }
+ }
+
+ [Fact]
+ public void ExtractingANonBundleFails()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ var hostName = BundleHelper.GetHostName(fixture);
+ var hostExe = Path.Combine(BundleHelper.GetPublishPath(fixture), hostName);
+
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+ Extractor extractor = new Extractor(hostExe, "extract");
+ Assert.Throws<BundleException>(() => extractor.ExtractFiles());
+ }
+
+ [Fact]
+ public void AllBundledFilesAreExtracted()
+ {
+ var fixture = sharedTestState.TestFixture.Copy();
+
+ var hostName = BundleHelper.GetHostName(fixture);
+ var bundleDir = BundleHelper.GetBundleDir(fixture);
+
+ var bundler = new Bundler(hostName, bundleDir.FullName);
+ string singleFile = bundler.GenerateBundle(BundleHelper.GetPublishPath(fixture));
+
+ var expectedFiles = new List<string>(bundler.BundleManifest.Files.Count);
+ expectedFiles.Add(hostName);
+ bundler.BundleManifest.Files.ForEach(file => expectedFiles.Add(file.RelativePath));
+
+ new Extractor(singleFile, bundleDir.FullName).ExtractFiles();
+ bundleDir.Should().OnlyHaveFiles(expectedFiles);
+ }
+
+ public class SharedTestState : IDisposable
+ {
+ public TestProjectFixture TestFixture { get; set; }
+ public RepoDirectoriesProvider RepoDirectories { get; set; }
+
+ public SharedTestState()
+ {
+ RepoDirectories = new RepoDirectoriesProvider();
+
+ TestFixture = new TestProjectFixture("StandaloneApp", RepoDirectories);
+ TestFixture
+ .EnsureRestoredForRid(TestFixture.CurrentRid, RepoDirectories.CorehostPackages)
+ .PublishProject(runtime: TestFixture.CurrentRid,
+ outputDirectory: BundleHelper.GetPublishPath(TestFixture));
+ }
+
+ public void Dispose()
+ {
+ TestFixture.Dispose();
+ }
+ }
+ }
+}
--- /dev/null
+<Project Sdk="Microsoft.NET.Sdk">
+
+ <PropertyGroup>
+ <Description>Microsoft.NET.HostModel.Bundle Tests</Description>
+ <TargetFramework>netcoreapp2.0</TargetFramework>
+ <AssemblyName>Microsoft.NET.HostModel.Bundle.Tests</AssemblyName>
+ <PackageId>Microsoft.NET.HostModel.Bundle.Tests</PackageId>
+ <GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
+ </PropertyGroup>
+
+ <ItemGroup>
+ <ProjectReference Include="..\..\TestUtils\TestUtils.csproj" />
+ <ProjectReference Include="..\..\..\managed\Microsoft.NET.HostModel\Microsoft.NET.HostModel.csproj" />
+ <ProjectReference Include="..\Helpers\BundleHelper.csproj" />
+ </ItemGroup>
+
+ <ItemGroup>
+ <PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.3.0" />
+ <PackageReference Include="xunit" Version="2.2.0" />
+ <PackageReference Include="xunit.runner.visualstudio" Version="2.2.0" />
+ </ItemGroup>
+
+</Project>
+++ /dev/null
-// Licensed to the .NET Foundation under one or more agreements.
-// The .NET Foundation licenses this file to you under the MIT license.
-// See the LICENSE file in the project root for more information.
-
-using System;
-using System.IO;
-using Xunit;
-using Microsoft.DotNet.Cli.Build.Framework;
-
-namespace Microsoft.DotNet.CoreSetup.Test.HostActivation
-{
- public class BundledAppWithSubDirs : IClassFixture<BundledAppWithSubDirs.SharedTestState>
- {
- private SharedTestState sharedTestState;
-
- public BundledAppWithSubDirs(SharedTestState fixture)
- {
- sharedTestState = fixture;
- }
-
- [Fact]
- private void Bundle_And_Run_App_With_Subdirs_Succeeds()
- {
- var fixture = sharedTestState.TestFixture.Copy();
- var hostName = Path.GetFileName(fixture.TestProject.AppExe);
-
- // Bundle to a single-file
- // This step should be removed in favor of publishing with /p:PublishSingleFile=true
- // once associated changes in SDK repo are checked in.
- string singleFileDir = Path.Combine(fixture.TestProject.ProjectDirectory, "oneExe");
- Directory.CreateDirectory(singleFileDir);
- var bundler = new Microsoft.NET.HostModel.Bundle.Bundler(hostName, singleFileDir);
- string singleFile = bundler.GenerateBundle(fixture.TestProject.OutputDirectory);
-
- // Run the bundled app (extract files)
- Command.Create(singleFile)
- .CaptureStdErr()
- .CaptureStdOut()
- .Execute()
- .Should()
- .Pass()
- .And
- .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
-
- // Run the bundled app again (reuse extracted files)
- Command.Create(singleFile)
- .CaptureStdErr()
- .CaptureStdOut()
- .Execute()
- .Should()
- .Pass()
- .And
- .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
- }
-
- public class SharedTestState : IDisposable
- {
- public TestProjectFixture TestFixture { get; set; }
- public RepoDirectoriesProvider RepoDirectories { get; set; }
-
- public SharedTestState()
- {
- RepoDirectories = new RepoDirectoriesProvider();
-
- TestFixture = new TestProjectFixture("StandaloneAppWithSubDirs", RepoDirectories);
- TestFixture
- .EnsureRestoredForRid(TestFixture.CurrentRid, RepoDirectories.CorehostPackages)
- .PublishProject(runtime: TestFixture.CurrentRid);
- }
-
- public void Dispose()
- {
- TestFixture.Dispose();
- }
- }
- }
-}
+++ /dev/null
-// Licensed to the .NET Foundation under one or more agreements.
-// The .NET Foundation licenses this file to you under the MIT license.
-// See the LICENSE file in the project root for more information.
-
-using System;
-using System.IO;
-using Xunit;
-using Microsoft.DotNet.Cli.Build.Framework;
-using Microsoft.NET.HostModel.Bundle;
-
-namespace Microsoft.DotNet.CoreSetup.Test.BundleTests.BundleExtract
-{
- public class BundleAndExtract : IClassFixture<BundleAndExtract.SharedTestState>
- {
- private SharedTestState sharedTestState;
-
- public BundleAndExtract(BundleAndExtract.SharedTestState fixture)
- {
- sharedTestState = fixture;
- }
-
- private void Run(TestProjectFixture fixture, string publishDir, string singleFileDir)
- {
- var dotnet = fixture.SdkDotnet;
- var hostName = Path.GetFileName(fixture.TestProject.AppExe);
-
- // Run the App normally
- Command.Create(Path.Combine(publishDir, hostName))
- .CaptureStdErr()
- .CaptureStdOut()
- .Execute()
- .Should()
- .Pass()
- .And
- .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
-
- // Bundle to a single-file
- Bundler bundler = new Bundler(hostName, singleFileDir);
- string singleFile = bundler.GenerateBundle(publishDir);
-
- // Extract the file
- Extractor extractor = new Extractor(singleFile, singleFileDir);
- extractor.ExtractFiles();
-
- // Run the extracted app
- Command.Create(singleFile)
- .CaptureStdErr()
- .CaptureStdOut()
- .Execute()
- .Should()
- .Pass()
- .And
- .HaveStdOutContaining("Wow! We now say hello to the big world and you.");
- }
-
- private string GetSingleFileDir(TestProjectFixture fixture)
- {
- // Create a directory for bundle/extraction output.
- // This directory shouldn't be within TestProject.OutputDirectory, since the bundler
- // will (attempt to) embed all files below the TestProject.OutputDirectory tree into one file.
-
- string singleFileDir = Path.Combine(fixture.TestProject.ProjectDirectory, "oneExe");
- Directory.CreateDirectory(singleFileDir);
-
- return singleFileDir;
- }
-
- private string RelativePath(string path)
- {
- return Path.GetRelativePath(Directory.GetCurrentDirectory(), path)
- .TrimEnd(Path.DirectorySeparatorChar);
- }
-
- [Fact]
- public void TestWithAbsolutePaths()
- {
- var fixture = sharedTestState.TestFixture
- .Copy();
-
- string publishDir = fixture.TestProject.OutputDirectory;
- string singleFileDir = GetSingleFileDir(fixture);
-
- Run(fixture, publishDir, singleFileDir);
- }
-
- [Fact]
- public void TestWithRelativePaths()
- {
- var fixture = sharedTestState.TestFixture
- .Copy();
-
- string publishDir = RelativePath(fixture.TestProject.OutputDirectory);
- string singleFileDir = RelativePath(GetSingleFileDir(fixture));
-
- Run(fixture, publishDir, singleFileDir);
- }
-
- [Fact]
- public void TestWithRelativePathsDirSeparator()
- {
- var fixture = sharedTestState.TestFixture
- .Copy();
-
- string publishDir = RelativePath(fixture.TestProject.OutputDirectory) + Path.DirectorySeparatorChar;
- string singleFileDir = RelativePath(GetSingleFileDir(fixture)) + Path.DirectorySeparatorChar;
-
- Run(fixture, publishDir, singleFileDir);
- }
-
- public class SharedTestState : IDisposable
- {
- public TestProjectFixture TestFixture { get; set; }
- public RepoDirectoriesProvider RepoDirectories { get; set; }
-
- public SharedTestState()
- {
- RepoDirectories = new RepoDirectoriesProvider();
-
- TestFixture = new TestProjectFixture("StandaloneAppWithSubDirs", RepoDirectories);
- TestFixture
- .EnsureRestoredForRid(TestFixture.CurrentRid, RepoDirectories.CorehostPackages)
- .PublishProject(runtime: TestFixture.CurrentRid);
- }
-
- public void Dispose()
- {
- TestFixture.Dispose();
- }
- }
- }
-}
return new AndConstraint<DirectoryInfoAssertions>(new DirectoryInfoAssertions(dir));
}
+ public AndConstraint<DirectoryInfoAssertions> NotHaveDirectory(string expectedDir)
+ {
+ var dir = _dirInfo.EnumerateDirectories(expectedDir, SearchOption.TopDirectoryOnly).SingleOrDefault();
+ Execute.Assertion.ForCondition(dir == null)
+ .FailWith("Directory {0} should not be found in found inside directory {1}.", expectedDir, _dirInfo.FullName);
+
+ return new AndConstraint<DirectoryInfoAssertions>(new DirectoryInfoAssertions(dir));
+ }
+
public AndConstraint<DirectoryInfoAssertions> OnlyHaveFiles(IEnumerable<string> expectedFiles)
{
var actualFiles = _dirInfo.EnumerateFiles("*", SearchOption.TopDirectoryOnly).Select(f => f.Name);
return new AndConstraint<DirectoryInfoAssertions>(this);
}
+
+ public AndConstraint<DirectoryInfoAssertions> NotBeModifiedAfter(DateTime timeUtc)
+ {
+ _dirInfo.Refresh();
+ DateTime writeTime = _dirInfo.LastWriteTimeUtc;
+
+ Execute.Assertion.ForCondition(writeTime <= timeUtc)
+ .FailWith("Directory {0} should not be modified after {1}, but is modified at {2}.", _dirInfo.FullName, timeUtc, writeTime);
+
+ return new AndConstraint<DirectoryInfoAssertions>(this);
+ }
+
}
}
DotNetCli dotnet = null,
string runtime = null,
string framework = null,
+ string selfContained = null,
string outputDirectory = null)
{
dotnet = dotnet ?? SdkDotnet;
publishArgs.Add($"/p:NETCoreAppFramework={framework}");
}
+ if (selfContained != null)
+ {
+ publishArgs.Add("--self-contained");
+ publishArgs.Add(selfContained);
+ }
+
if (outputDirectory != null)
{
publishArgs.Add("-o");
<ItemGroup>
<TestProjects Include="$(TestDir)/HostActivationTests/HostActivationTests.csproj" />
<TestProjects Include="$(TestDir)/Microsoft.Extensions.DependencyModel.Tests/Microsoft.Extensions.DependencyModel.Tests.csproj" />
- <TestProjects Include="$(TestDir)/Microsoft.NET.HostModel.Tests/Microsoft.NET.HostModel.Tests.csproj" />
+ <TestProjects Include="$(TestDir)/BundleTests/Microsoft.NET.HostModel.Bundle.Tests/Microsoft.NET.HostModel.Bundle.Tests.csproj" />
+ <TestProjects Include="$(TestDir)/BundleTests/AppHost.Bundle.Tests/AppHost.Bundle.Tests.csproj" />
</ItemGroup>
<ItemGroup>
<RestoreTestFallbackSource Include="$(CoreHostOutputDir.TrimEnd('/').TrimEnd('\'))" />