| 1 | /*++ |
| 2 | |
| 3 | Copyright (c) Microsoft. All rights reserved. |
| 4 | |
| 5 | Module Name: |
| 6 | |
| 7 | WSLCE2EAliasTests.cpp |
| 8 | |
| 9 | Abstract: |
| 10 | |
| 11 | This file contains end-to-end tests for verifying the command alias functionality. |
| 12 | --*/ |
| 13 | |
| 14 | #include "precomp.h" |
| 15 | #include "windows/Common.h" |
| 16 | #include "WSLCExecutor.h" |
| 17 | |
| 18 | namespace WSLCE2ETests { |
| 19 | |
| 20 | namespace { |
| 21 | |
| 22 | inline std::wstring GetContainerExePath() |
| 23 | { |
| 24 | return (std::filesystem::path(wsl::windows::common::wslutil::GetMsiPackagePath().value()) / L"container.exe").wstring(); |
| 25 | } |
| 26 | |
| 27 | WSLCExecutionResult RunContainerExe(const std::wstring& commandLine) |
| 28 | { |
| 29 | auto cmd = L"\"" + GetContainerExePath() + L"\" " + commandLine; |
| 30 | wsl::windows::common::SubProcess process(nullptr, cmd.c_str()); |
| 31 | const auto output = process.RunAndCaptureOutput(); |
| 32 | return {.CommandLine = commandLine, .Stdout = output.Stdout, .Stderr = output.Stderr, .ExitCode = output.ExitCode}; |
| 33 | } |
| 34 | |
| 35 | } // namespace |
| 36 | |
| 37 | class WSLCE2EAliasTests |
| 38 | { |
| 39 | WSLC_TEST_CLASS(WSLCE2EAliasTests) |
| 40 | |
| 41 | TEST_CLASS_SETUP(TestClassSetup) |
| 42 | { |
| 43 | return true; |
| 44 | } |
| 45 | |
| 46 | TEST_CLASS_CLEANUP(TestClassCleanup) |
| 47 | { |
| 48 | return true; |
| 49 | } |
| 50 | |
| 51 | // Verify that container.exe exists on disk as the deployed alias for wslc.exe. |
| 52 | WSLC_TEST_METHOD(WSLCE2E_ContainerExe_IsDeployed) |
| 53 | { |
| 54 | const auto containerExePath = GetContainerExePath(); |
| 55 | VERIFY_IS_TRUE(std::filesystem::exists(containerExePath), (L"container.exe not found at: " + containerExePath).c_str()); |
| 56 | } |
| 57 | |
| 58 | // Verify that container.exe responds to --help identically to wslc.exe, |
| 59 | // confirming it is a functional alias and not just a placeholder. |
| 60 | WSLC_TEST_METHOD(WSLCE2E_ContainerExe_HelpCommand_MatchesWslc) |
| 61 | { |
| 62 | const auto wslcResult = RunWslc(L"--help"); |
| 63 | wslcResult.Verify({.Stderr = L"", .ExitCode = 0}); |
| 64 | |
| 65 | const auto containerResult = RunContainerExe(L"--help"); |
| 66 | containerResult.Verify({.Stderr = L"", .ExitCode = 0}); |
| 67 | |
| 68 | // Help output should be identical except the executable name in the usage line. |
| 69 | auto wslcOutput = wslcResult.Stdout.value(); |
| 70 | const std::wstring usageNeedle = L"Usage: wslc"; |
| 71 | const std::wstring usageReplacement = L"Usage: container"; |
| 72 | auto pos = wslcOutput.find(usageNeedle); |
| 73 | VERIFY_ARE_NOT_EQUAL(std::wstring::npos, pos); |
| 74 | wslcOutput.replace(pos, usageNeedle.size(), usageReplacement); |
| 75 | |
| 76 | VERIFY_ARE_EQUAL(wslcOutput, containerResult.Stdout.value()); |
| 77 | } |
| 78 | |
| 79 | WSLC_TEST_METHOD(WSLCE2E_CommandHelp_ListsFullInvocationAliases) |
| 80 | { |
| 81 | const std::wstring startAliases = L"Aliases:\r\n wslc container start, wslc start\r\n"; |
| 82 | |
| 83 | for (const auto commandLine : {L"container start --help", L"start --help"}) |
| 84 | { |
| 85 | const auto result = RunWslc(commandLine); |
| 86 | result.Verify({.Stderr = L"", .ExitCode = 0}); |
| 87 | VERIFY_IS_TRUE(result.StdoutContainsSubstring(startAliases)); |
| 88 | } |
| 89 | |
| 90 | const auto containerResult = RunContainerExe(L"start --help"); |
| 91 | containerResult.Verify({.Stderr = L"", .ExitCode = 0}); |
| 92 | VERIFY_IS_TRUE(containerResult.StdoutContainsSubstring(L"Aliases:\r\n container container start, container start\r\n")); |
| 93 | |
| 94 | const auto imageListResult = RunWslc(L"image list --help"); |
| 95 | imageListResult.Verify({.Stderr = L"", .ExitCode = 0}); |
| 96 | VERIFY_IS_TRUE(imageListResult.StdoutContainsSubstring(L"Aliases:\r\n wslc image list, wslc image ls, wslc images\r\n")); |
| 97 | |
| 98 | const auto volumeListResult = RunWslc(L"volume list --help"); |
| 99 | volumeListResult.Verify({.Stderr = L"", .ExitCode = 0}); |
| 100 | VERIFY_IS_TRUE(volumeListResult.StdoutContainsSubstring(L"Aliases:\r\n wslc volume list, wslc volume ls\r\n")); |
| 101 | } |
| 102 | }; |
| 103 | |
| 104 | } // namespace WSLCE2ETests |