diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md index b4723cf34..d8771c0f0 100644 --- a/.github/ISSUE_TEMPLATE.md +++ b/.github/ISSUE_TEMPLATE.md @@ -1,10 +1,13 @@ ## Description > **IMPORTANT**: if the defect is reproduced only in a workflow from within the Visual Studio IDE then do not report the issue here - instead, please report it using Visual Studio's "Send Feedback" option that can be accessed from the Help menu OR using this link https://developercommunity.visualstudio.com. > +> **IMPORTANT**: Before posting an issue, please search the repository for similar ones. It might have been solved or reported already. +> > For a defect specific to the MSTest V2 test framework, describe the issue you've observed. ## Steps to reproduce > What steps can reproduce the defect? +> > Please share the setup, sample project, target platform (desktop, core, uap) ## Expected behavior @@ -15,5 +18,7 @@ ## Environment > Please share additional details about the test environment. -> Operating system, Build version of vstest.console, Package version of MSTest -> framework and adapter +> - Operating system +> - Build version of vstest.console +> - Package version of MSTest framework and adapter +> - Other installed packages and their versions on the test project diff --git a/.gitignore b/.gitignore index 2688b7eb7..7ef5c066f 100644 --- a/.gitignore +++ b/.gitignore @@ -88,6 +88,7 @@ ehthumbs.db packages artifacts Tools +.dotnet # =========================== # Tools diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md index 958979430..f9ba8cf65 100644 --- a/CODE_OF_CONDUCT.md +++ b/CODE_OF_CONDUCT.md @@ -1,2 +1,9 @@ -### Microsoft Open Source Code of Conduct -This project has adopted the [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/). For more information see the [Code of Conduct FAQ](https://opensource.microsoft.com/codeofconduct/faq/) or contact [opencode@microsoft.com](mailto:opencode@microsoft.com) with any additional questions or comments. +# Microsoft Open Source Code of Conduct + +This project has adopted the [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/). + +Resources: + +- [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/) +- [Microsoft Code of Conduct FAQ](https://opensource.microsoft.com/codeofconduct/faq/) +- Contact [opencode@microsoft.com](mailto:opencode@microsoft.com) with questions or concerns diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 0730c476c..757d10b19 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -2,13 +2,13 @@ Welcome, and thank you for your interest in contributing. There are many ways to contribute: - [Submit issues](https://github.com/Microsoft/testfx/issues) and help verify fixes as they are checked in. - Review the [source code changes](https://github.com/Microsoft/testfx/pulls). -- [Contribute features and fixes](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md). +- [Contribute features and fixes](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md). - Contribute to the [documentation](https://github.com/Microsoft/testfx-docs). ### Building If you want to understand how **testfx** works or want to debug an issue, you'll want to get the source, build it, and run it locally. **testfx** can be built from within Visual Studio or from the CLI. -- [Building with Visual Studio](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md#building-with-visual-studiovs) -- [Building with CLI](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md#building-with-command-linecli) +- [Building with Visual Studio](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md#building-with-visual-studiovs) +- [Building with CLI](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md#building-with-command-linecli) ### Thank You! Your contributions to open source, large or small, make projects like this possible. Thank you for taking the time to contribute. diff --git a/Directory.Build.props b/Directory.Build.props new file mode 100644 index 000000000..262a72352 --- /dev/null +++ b/Directory.Build.props @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/Directory.Build.targets b/Directory.Build.targets new file mode 100644 index 000000000..58e8fd573 --- /dev/null +++ b/Directory.Build.targets @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/Nuget.config b/NuGet.config similarity index 75% rename from Nuget.config rename to NuGet.config index bdab0c8cc..38283aac6 100644 --- a/Nuget.config +++ b/NuGet.config @@ -1,15 +1,21 @@ - + + + + - + + + + - - + + @@ -18,8 +24,8 @@ - - + + diff --git a/README.md b/README.md index bc5fbc253..5a15c2357 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,7 @@ This is a fully supported, open source and cross-platform implementation of the ### Build status -[![Build Status](https://dev.azure.com/dnceng/public/_apis/build/status/Microsoft/testfx/microsoft.testfx.ci?branchName=master)](https://dev.azure.com/dnceng/public/_build/latest?definitionId=937&branchName=master) +[![Build Status](https://dev.azure.com/dnceng/public/_apis/build/status/Microsoft/testfx/microsoft.testfx.ci?branchName=main)](https://dev.azure.com/dnceng/public/_build/latest?definitionId=937&branchName=main) ### Latest Builds | | Framework | Adapter | @@ -19,22 +19,22 @@ This is a fully supported, open source and cross-platform implementation of the There are many ways to contribute to testfx - [Submit issues](https://github.com/Microsoft/testfx/issues) and help verify fixes as they are checked in. - Review the [source code changes](https://github.com/Microsoft/testfx/pulls). -- [Contribute features and fixes](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md). +- [Contribute features and fixes](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md). - Contribute to the [documentation](https://github.com/Microsoft/testfx-docs). ### Building testfx can be built from within Visual Studio or from the CLI. -- [Building with Visual Studio](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md#building-with-visual-studiovs) -- [Building with CLI](https://github.com/Microsoft/testfx-docs/blob/master/docs/contribute.md#building-with-command-linecli) +- [Building with Visual Studio](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md#building-with-visual-studiovs) +- [Building with CLI](https://github.com/Microsoft/testfx-docs/blob/main/docs/contribute.md#building-with-command-linecli) ### Microsoft Open Source Code of Conduct This project has adopted the [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/). For more information see the [Code of Conduct FAQ](https://opensource.microsoft.com/codeofconduct/faq/) or contact [opencode@microsoft.com](mailto:opencode@microsoft.com) with any additional questions or comments. ### License -testfx platform is licensed under the [MIT license](https://github.com/Microsoft/testfx/blob/master/LICENSE) +testfx platform is licensed under the [MIT license](https://github.com/Microsoft/testfx/blob/main/LICENSE) ### Issue Tracking -Please see [issue tracking](https://github.com/Microsoft/testfx-docs/blob/master/issuetracking.md) for a description of the workflow we use to process issues. +Please see [issue tracking](https://github.com/Microsoft/testfx-docs/blob/main/issuetracking.md) for a description of the workflow we use to process issues. ### Roadmap -For information on shipped and upcoming features/enhancements please refer to our [Releases](https://github.com/Microsoft/testfx-docs/blob/master/docs/releases.md) and [Quarterly Checkin reports](https://github.com/Microsoft/testfx-docs/tree/master/Quarterly%20Checkins). +For information on shipped and upcoming features/enhancements please refer to our [Releases](https://github.com/Microsoft/testfx-docs/blob/main/docs/releases.md) and [Quarterly Checkin reports](https://github.com/Microsoft/testfx-docs/tree/main/Quarterly%20Checkins). diff --git a/TestFx.sln b/TestFx.sln index 183aebced..1d10ff71e 100644 --- a/TestFx.sln +++ b/TestFx.sln @@ -119,6 +119,10 @@ EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "PlatformServices.Portable.Unit.Tests", "test\UnitTests\PlatformServices.Portable.Unit.Tests\PlatformServices.Portable.Unit.Tests.csproj", "{E3C630FE-AF89-4C95-B1B9-2409B1107208}" EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "PlatformServices.Universal.Unit.Tests", "test\UnitTests\PlatformServices.Universal.Unit.Tests\PlatformServices.Universal.Unit.Tests.csproj", "{FA7C719F-A400-45AF-8091-7C23435617A8}" + ProjectSection(ProjectDependencies) = postProject + {DF131865-84EE-4540-8112-E88ACEBDEA09} = {DF131865-84EE-4540-8112-E88ACEBDEA09} + {5D153CAA-80C2-4551-9549-6C406FCEEFB1} = {5D153CAA-80C2-4551-9549-6C406FCEEFB1} + EndProjectSection EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MSTest.Core.Unit.Tests", "test\UnitTests\MSTest.Core.Unit.Tests\MSTest.Core.Unit.Tests.csproj", "{0A4A76DD-FEE1-4D04-926B-38E1A24A7ED2}" EndProject @@ -136,10 +140,9 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "stylecop", "stylecop", "{FE EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "targets", "targets", "{F60B647A-E14C-48AF-9BD6-89F44EB60115}" ProjectSection(SolutionItems) = preProject - scripts\build\TestFx.Loc.targets = scripts\build\TestFx.Loc.targets - scripts\build\TestFx.Settings.targets = scripts\build\TestFx.Settings.targets + scripts\build\TestFx.Loc.props = scripts\build\TestFx.Loc.props + scripts\build\TestFx.props = scripts\build\TestFx.props scripts\build\TestFx.targets = scripts\build\TestFx.targets - scripts\build\TestFx.Versions.targets = scripts\build\TestFx.Versions.targets EndProjectSection EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "scripts", "scripts", "{BCF525B1-E67F-486D-B091-06A8BB8A2793}" @@ -184,6 +187,20 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TimeoutTestProjectNetCore", EndProject Project("{6EC3EE1D-3C4E-46DD-8F32-0CC8E7565705}") = "FSharpTestProject", "test\E2ETests\TestAssets\FSharpTestProject\FSharpTestProject.fsproj", "{E5E58613-82FC-44CD-B75F-4F1C7ED52D0D}" EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DiscoveryAndExecutionTests", "test\E2ETests\DiscoveryAndExecutionTests\DiscoveryAndExecutionTests.csproj", "{EEE57613-6424-4A1C-9635-B73768F2146D}" + ProjectSection(ProjectDependencies) = postProject + {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D} = {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D} + {98BA6D2C-1F3D-4636-8E1D-D4932B7A253D} = {98BA6D2C-1F3D-4636-8E1D-D4932B7A253D} + {A7EA583B-A2B0-47DA-A058-458F247C7575} = {A7EA583B-A2B0-47DA-A058-458F247C7575} + {BBC99A6B-4490-49DD-9C12-AF2C1E95576E} = {BBC99A6B-4490-49DD-9C12-AF2C1E95576E} + {B0FCE474-14BC-449A-91EA-A433342C0D63} = {B0FCE474-14BC-449A-91EA-A433342C0D63} + {4004757A-0080-4410-B90A-6169B20F151B} = {4004757A-0080-4410-B90A-6169B20F151B} + {7FB80AAB-7123-4416-B6CD-8D3D69AA83F1} = {7FB80AAB-7123-4416-B6CD-8D3D69AA83F1} + {5A4967CD-B527-4D43-81C2-4CA90EE10222} = {5A4967CD-B527-4D43-81C2-4CA90EE10222} + {9C1219E0-E775-47F9-9236-63F03F774801} = {9C1219E0-E775-47F9-9236-63F03F774801} + {7252D9E3-267D-442C-96BC-C73AEF3241D6} = {7252D9E3-267D-442C-96BC-C73AEF3241D6} + EndProjectSection +EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Extension.WinUI", "src\TestFramework\Extension.WinUI\Extension.WinUI.csproj", "{23B9D9A2-4AEE-47E6-97B5-060DF21539FB}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "NetCore", "NetCore", "{D11C6664-1C4E-48F0-AA92-7F5BADC6F82C}" @@ -191,11 +208,21 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "NetCore", "NetCore", "{D11C src\Adapter\Build\NetCore\MSTest.TestAdapter.props = src\Adapter\Build\NetCore\MSTest.TestAdapter.props EndProjectSection EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "PlatformServices.WinUI", "src\Adapter\PlatformServices.WinUI\PlatformServices.WinUI.csproj", "{F4E2876F-6E42-4DCF-B629-041A9DF7C579}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "WinUI", "WinUI", "{35D010CC-CDF2-4115-BCFB-E2E3D21C1055}" + ProjectSection(SolutionItems) = preProject + src\Adapter\Build\WinUI\MSTest.TestAdapter.props = src\Adapter\Build\WinUI\MSTest.TestAdapter.props + src\Adapter\Build\WinUI\MSTest.TestAdapter.targets = src\Adapter\Build\WinUI\MSTest.TestAdapter.targets + EndProjectSection +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ReferencedProjectFromDataSourceTest", "test\E2ETests\TestAssets\ReferencedProjectFromDataSourceTest\ReferencedProjectFromDataSourceTest.csproj", "{6B4DE65C-4162-4C52-836A-8F9FA901814A}" +EndProject Global GlobalSection(SharedMSBuildProjectFiles) = preSolution src\Adapter\PlatformServices.Shared\PlatformServices.Shared.projitems*{2177c273-ae07-43b3-b87a-443e47a23c5a}*SharedItemsImports = 13 - src\TestFramework\Extension.Shared\Extension.Shared.projitems*{272ca5e1-8e81-4825-9e47-86cce02f700d}*SharedItemsImports = 13 src\TestFramework\Extension.Shared\Extension.Shared.projitems*{23b9d9a2-4aee-47e6-97b5-060df21539fb}*SharedItemsImports = 5 + src\TestFramework\Extension.Shared\Extension.Shared.projitems*{272ca5e1-8e81-4825-9e47-86cce02f700d}*SharedItemsImports = 13 src\TestFramework\Extension.Shared\Extension.Shared.projitems*{df131865-84ee-4540-8112-e88acebdea09}*SharedItemsImports = 4 EndGlobalSection GlobalSection(SolutionConfigurationPlatforms) = preSolution @@ -351,12 +378,12 @@ Global {B0FCE474-14BC-449A-91EA-A433342C0D63}.Debug|x86.Build.0 = Debug|Any CPU {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|Any CPU.ActiveCfg = Release|Any CPU {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|Any CPU.Build.0 = Release|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|ARM.ActiveCfg = Debug|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|ARM.Build.0 = Debug|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x64.ActiveCfg = Debug|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x64.Build.0 = Debug|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x86.ActiveCfg = Debug|Any CPU - {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x86.Build.0 = Debug|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|ARM.ActiveCfg = Release|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|ARM.Build.0 = Release|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x64.ActiveCfg = Release|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x64.Build.0 = Release|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x86.ActiveCfg = Release|Any CPU + {B0FCE474-14BC-449A-91EA-A433342C0D63}.Release|x86.Build.0 = Release|Any CPU {A7EA583B-A2B0-47DA-A058-458F247C7575}.Code Analysis Debug|Any CPU.ActiveCfg = Debug|Any CPU {A7EA583B-A2B0-47DA-A058-458F247C7575}.Code Analysis Debug|Any CPU.Build.0 = Debug|Any CPU {A7EA583B-A2B0-47DA-A058-458F247C7575}.Code Analysis Debug|ARM.ActiveCfg = Debug|Any CPU @@ -1173,6 +1200,30 @@ Global {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D}.Release|x64.Build.0 = Release|Any CPU {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D}.Release|x86.ActiveCfg = Release|Any CPU {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D}.Release|x86.Build.0 = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|Any CPU.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|Any CPU.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|ARM.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|ARM.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|x64.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|x64.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|x86.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Code Analysis Debug|x86.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|Any CPU.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|ARM.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|ARM.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|x64.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|x64.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|x86.ActiveCfg = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Debug|x86.Build.0 = Debug|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|Any CPU.ActiveCfg = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|Any CPU.Build.0 = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|ARM.ActiveCfg = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|ARM.Build.0 = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|x64.ActiveCfg = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|x64.Build.0 = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|x86.ActiveCfg = Release|Any CPU + {EEE57613-6424-4A1C-9635-B73768F2146D}.Release|x86.Build.0 = Release|Any CPU {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Code Analysis Debug|Any CPU.ActiveCfg = Debug|Any CPU {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Code Analysis Debug|Any CPU.Build.0 = Debug|Any CPU {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Code Analysis Debug|ARM.ActiveCfg = Debug|Any CPU @@ -1197,6 +1248,54 @@ Global {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Release|x64.Build.0 = Release|Any CPU {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Release|x86.ActiveCfg = Release|Any CPU {23B9D9A2-4AEE-47E6-97B5-060DF21539FB}.Release|x86.Build.0 = Release|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|Any CPU.ActiveCfg = Debug|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|Any CPU.Build.0 = Debug|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|ARM.ActiveCfg = Debug|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|ARM.Build.0 = Debug|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|x64.ActiveCfg = Debug|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|x64.Build.0 = Debug|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|x86.ActiveCfg = Debug|x86 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Code Analysis Debug|x86.Build.0 = Debug|x86 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|Any CPU.Build.0 = Debug|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|ARM.ActiveCfg = Debug|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|ARM.Build.0 = Debug|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|x64.ActiveCfg = Debug|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|x64.Build.0 = Debug|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|x86.ActiveCfg = Debug|x86 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Debug|x86.Build.0 = Debug|x86 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|Any CPU.ActiveCfg = Release|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|Any CPU.Build.0 = Release|Any CPU + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|ARM.ActiveCfg = Release|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|ARM.Build.0 = Release|ARM + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|x64.ActiveCfg = Release|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|x64.Build.0 = Release|x64 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|x86.ActiveCfg = Release|x86 + {F4E2876F-6E42-4DCF-B629-041A9DF7C579}.Release|x86.Build.0 = Release|x86 + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|Any CPU.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|Any CPU.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|ARM.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|ARM.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|x64.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|x64.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|x86.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Code Analysis Debug|x86.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|Any CPU.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|ARM.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|ARM.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|x64.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|x64.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|x86.ActiveCfg = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Debug|x86.Build.0 = Debug|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|Any CPU.ActiveCfg = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|Any CPU.Build.0 = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|ARM.ActiveCfg = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|ARM.Build.0 = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|x64.ActiveCfg = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|x64.Build.0 = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|x86.ActiveCfg = Release|Any CPU + {6B4DE65C-4162-4C52-836A-8F9FA901814A}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -1261,8 +1360,12 @@ Global {26F0B8EF-92D4-4A23-ACB4-D1B662F0EEBE} = {D53BD452-F69F-4FB3-8B98-386EDA28A4C8} {ED27A844-6870-4FE6-8FEF-3ABDD1ED6564} = {D53BD452-F69F-4FB3-8B98-386EDA28A4C8} {E5E58613-82FC-44CD-B75F-4F1C7ED52D0D} = {D53BD452-F69F-4FB3-8B98-386EDA28A4C8} + {EEE57613-6424-4A1C-9635-B73768F2146D} = {F1A27537-78D1-4BBD-8E76-ADB31BC0C2B4} {23B9D9A2-4AEE-47E6-97B5-060DF21539FB} = {E48AC786-E150-4F41-9A16-32F02E4493D8} {D11C6664-1C4E-48F0-AA92-7F5BADC6F82C} = {CA01DAF5-8D9D-496E-9AD3-94BB7FBB2D34} + {F4E2876F-6E42-4DCF-B629-041A9DF7C579} = {24088844-2107-4DB2-8F3F-CBCA94FC4B28} + {35D010CC-CDF2-4115-BCFB-E2E3D21C1055} = {CA01DAF5-8D9D-496E-9AD3-94BB7FBB2D34} + {6B4DE65C-4162-4C52-836A-8F9FA901814A} = {D53BD452-F69F-4FB3-8B98-386EDA28A4C8} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {31E0F4D5-975A-41CC-933E-545B2201FAF9} diff --git a/eng/Tools.props b/eng/Tools.props new file mode 100644 index 000000000..36a0f1248 --- /dev/null +++ b/eng/Tools.props @@ -0,0 +1,11 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/eng/Version.Details.xml b/eng/Version.Details.xml new file mode 100644 index 000000000..04eae2ce3 --- /dev/null +++ b/eng/Version.Details.xml @@ -0,0 +1,80 @@ + + + + + https://dev.azure.com/dnceng/internal/_git/dotnet-symuploader + 861806bc0dc685441cb3e8f6bd1ce5ed31e6b32b + + + https://dev.azure.com/dnceng/internal/_git/dotnet-symuploader + 165896e7efeecb70f01bd011257ead0f56d32c95 + + + https://github.com/microsoft/vstest + 7603cf3ff7a3b3002362e994b618b828a9250699 + + + + + https://github.com/dotnet/arcade + e97027cf100d2b532adce387e5cb93a373de93c9 + + + https://github.com/dotnet/arcade + e97027cf100d2b532adce387e5cb93a373de93c9 + + + https://github.com/dotnet/arcade + e97027cf100d2b532adce387e5cb93a373de93c9 + + + https://github.com/dotnet/arcade + e97027cf100d2b532adce387e5cb93a373de93c9 + + + https://github.com/dotnet/arcade + e97027cf100d2b532adce387e5cb93a373de93c9 + + + https://github.com/dotnet/arcade-services + 869869342f1ec338de96adcea6e003b61f195256 + + + https://github.com/dotnet/arcade-services + cac955fe259cb611f6a29d09209bd717deb69037 + + + https://github.com/dotnet/xharness + 2eef520188beb49e31460d0a7dbe040294428ff1 + + + https://github.com/dotnet/roslyn + 1e347d3e229cf388249d342c72a1222bff0b5fdd + + + https://github.com/mono/linker + 30f2498c2a3de1f7e236d5793f5f1aca6e5ba456 + + + https://github.com/dotnet/sourcelink + 4b584dbc392bb1aad49c2eb1ab84d8b489b6dccc + + + + https://github.com/dotnet/sourcelink + 4b584dbc392bb1aad49c2eb1ab84d8b489b6dccc + + + https://github.com/dotnet/symreader-converter + c5ba7c88f92e2dde156c324a8c8edc04d9fa4fe0 + + + https://github.com/dotnet/symreader-converter + c5ba7c88f92e2dde156c324a8c8edc04d9fa4fe0 + + + https://github.com/dotnet/xliff-tasks + f4bfde77fb60daf52d8fec738d96d1d54e37dd88 + + + diff --git a/eng/Versions.props b/eng/Versions.props new file mode 100644 index 000000000..e905dbc99 --- /dev/null +++ b/eng/Versions.props @@ -0,0 +1,119 @@ + + + + + 6.0.0 + beta + + false + 17.0.0-preview-20210719-01 + + 0.2.0 + 5.9.1 + 2.5.2 + 14.0.0 + + 1.1.0-beta2-21064-01 + 1.0.0-build-20170420-1 + 0.1.3 + 16.9.0-preview-4267359 + + + 4.3.0 + 4.3.0 + 4.3.0 + 4.3.0 + 4.3.0 + 4.3.0 + 4.3.0 + 4.3.0 + + 1.6.0 + 1.6.0 + + 5.3.0 + 0.8.0 + + 4.8.3 + 4.3.0 + 5.10.3 + 1.0.0 + + 15.7.0 + 1.2.0 + 1.2.0 + + 11.0 + + 2.2.1 + 1.0.2 + 1.10.1 + 0.25.2 + 2.0.10 + 4.3.4 + 12.3.0 + 2.16.0 + 3.0.0 + 1.3.1 + 0.1.0 + 15.7.179 + 15.7.179 + 15.7.179 + 15.7.179 + 2.6.3 + 2.9.0 + 3.8.0 + 3.17.2 + 2.3.13 + 2.1.0 + 2.1.1 + 2.1.1 + 2.0.0 + 2.1.1 + 2.1.0 + 4.0.0-1.21270.4 + 6.0.100-preview.5.21268.2 + 5.3.0.1 + 2.3.0 + 9.0.1 + 4.7.0 + 4.4.0 + 5.6.0-preview.2.6489 + 0.32.0 + 2.2.143 + 3.0.0 + 4.5.0 + 4.0.0 + 4.3.0 + 4.5.0 + 4.3.0 + 4.5.3 + 4.5.0 + 4.7.0 + 4.3.0 + 4.7.2 + 4.5.2 + 8.5.0 + 2.4.1 + 2.0.3 + 2.4.1 + 6.0.0-beta.21369.3 + 6.0.0-beta.21369.3 + 1.22.0 + 1.1.2 + 2.0.0 + 1.6.0 + 1.0.0 + 2.0.4 + 1.1.0-beta.20258.6 + 1.1.0-beta-21228-01 + 1.1.0-beta-21228-01 + 6.0.0-beta.21369.3 + 1.0.0-beta.21265.1 + 1.1.0-beta.21228.1 + 1.0.0-prerelease.21264.3 + 1.1.156402 + 1.1.152002 + 6.0.100-preview.5.21254.11 + + diff --git a/eng/common/CIBuild.cmd b/eng/common/CIBuild.cmd new file mode 100644 index 000000000..56c2f25ac --- /dev/null +++ b/eng/common/CIBuild.cmd @@ -0,0 +1,2 @@ +@echo off +powershell -ExecutionPolicy ByPass -NoProfile -command "& """%~dp0Build.ps1""" -restore -build -test -sign -pack -publish -ci %*" \ No newline at end of file diff --git a/eng/common/PSScriptAnalyzerSettings.psd1 b/eng/common/PSScriptAnalyzerSettings.psd1 new file mode 100644 index 000000000..4c1ea7c98 --- /dev/null +++ b/eng/common/PSScriptAnalyzerSettings.psd1 @@ -0,0 +1,11 @@ +@{ + IncludeRules=@('PSAvoidUsingCmdletAliases', + 'PSAvoidUsingWMICmdlet', + 'PSAvoidUsingPositionalParameters', + 'PSAvoidUsingInvokeExpression', + 'PSUseDeclaredVarsMoreThanAssignments', + 'PSUseCmdletCorrectly', + 'PSStandardDSCFunctionsInResource', + 'PSUseIdenticalMandatoryParametersForDSC', + 'PSUseIdenticalParametersForDSC') +} \ No newline at end of file diff --git a/eng/common/README.md b/eng/common/README.md new file mode 100644 index 000000000..ff49c3715 --- /dev/null +++ b/eng/common/README.md @@ -0,0 +1,28 @@ +# Don't touch this folder + + uuuuuuuuuuuuuuuuuuuu + u" uuuuuuuuuuuuuuuuuu "u + u" u$$$$$$$$$$$$$$$$$$$$u "u + u" u$$$$$$$$$$$$$$$$$$$$$$$$u "u + u" u$$$$$$$$$$$$$$$$$$$$$$$$$$$$u "u + u" u$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$u "u + u" u$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$u "u + $ $$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$ $ + $ $$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$ $ + $ $$$" ... "$... ...$" ... "$$$ ... "$$$ $ + $ $$$u `"$$$$$$$ $$$ $$$$$ $$ $$$ $$$ $ + $ $$$$$$uu "$$$$ $$$ $$$$$ $$ """ u$$$ $ + $ $$$""$$$ $$$$ $$$u "$$$" u$$ $$$$$$$$ $ + $ $$$$....,$$$$$..$$$$$....,$$$$..$$$$$$$$ $ + $ $$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$ $ + "u "$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$" u" + "u "$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$" u" + "u "$$$$$$$$$$$$$$$$$$$$$$$$$$$$" u" + "u "$$$$$$$$$$$$$$$$$$$$$$$$" u" + "u "$$$$$$$$$$$$$$$$$$$$" u" + "u """""""""""""""""" u" + """""""""""""""""""" + +!!! Changes made in this directory are subject to being overwritten by automation !!! + +The files in this directory are shared by all Arcade repos and managed by automation. If you need to make changes to these files, open an issue or submit a pull request to https://github.com/dotnet/arcade first. diff --git a/eng/common/SetupNugetSources.ps1 b/eng/common/SetupNugetSources.ps1 new file mode 100644 index 000000000..18823840b --- /dev/null +++ b/eng/common/SetupNugetSources.ps1 @@ -0,0 +1,167 @@ +# This file is a temporary workaround for internal builds to be able to restore from private AzDO feeds. +# This file should be removed as part of this issue: https://github.com/dotnet/arcade/issues/4080 +# +# What the script does is iterate over all package sources in the pointed NuGet.config and add a credential entry +# under for each Maestro managed private feed. Two additional credential +# entries are also added for the two private static internal feeds: dotnet3-internal and dotnet3-internal-transport. +# +# This script needs to be called in every job that will restore packages and which the base repo has +# private AzDO feeds in the NuGet.config. +# +# See example YAML call for this script below. Note the use of the variable `$(dn-bot-dnceng-artifact-feeds-rw)` +# from the AzureDevOps-Artifact-Feeds-Pats variable group. +# +# Any disabledPackageSources entries which start with "darc-int" will be re-enabled as part of this script executing +# +# - task: PowerShell@2 +# displayName: Setup Private Feeds Credentials +# condition: eq(variables['Agent.OS'], 'Windows_NT') +# inputs: +# filePath: $(Build.SourcesDirectory)/eng/common/SetupNugetSources.ps1 +# arguments: -ConfigFile $(Build.SourcesDirectory)/NuGet.config -Password $Env:Token +# env: +# Token: $(dn-bot-dnceng-artifact-feeds-rw) + +[CmdletBinding()] +param ( + [Parameter(Mandatory = $true)][string]$ConfigFile, + [Parameter(Mandatory = $true)][string]$Password +) + +$ErrorActionPreference = "Stop" +Set-StrictMode -Version 2.0 +[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 + +. $PSScriptRoot\tools.ps1 + +# Add source entry to PackageSources +function AddPackageSource($sources, $SourceName, $SourceEndPoint, $creds, $Username, $Password) { + $packageSource = $sources.SelectSingleNode("add[@key='$SourceName']") + + if ($packageSource -eq $null) + { + $packageSource = $doc.CreateElement("add") + $packageSource.SetAttribute("key", $SourceName) + $packageSource.SetAttribute("value", $SourceEndPoint) + $sources.AppendChild($packageSource) | Out-Null + } + else { + Write-Host "Package source $SourceName already present." + } + + AddCredential -Creds $creds -Source $SourceName -Username $Username -Password $Password +} + +# Add a credential node for the specified source +function AddCredential($creds, $source, $username, $password) { + # Looks for credential configuration for the given SourceName. Create it if none is found. + $sourceElement = $creds.SelectSingleNode($Source) + if ($sourceElement -eq $null) + { + $sourceElement = $doc.CreateElement($Source) + $creds.AppendChild($sourceElement) | Out-Null + } + + # Add the node to the credential if none is found. + $usernameElement = $sourceElement.SelectSingleNode("add[@key='Username']") + if ($usernameElement -eq $null) + { + $usernameElement = $doc.CreateElement("add") + $usernameElement.SetAttribute("key", "Username") + $sourceElement.AppendChild($usernameElement) | Out-Null + } + $usernameElement.SetAttribute("value", $Username) + + # Add the to the credential if none is found. + # Add it as a clear text because there is no support for encrypted ones in non-windows .Net SDKs. + # -> https://github.com/NuGet/Home/issues/5526 + $passwordElement = $sourceElement.SelectSingleNode("add[@key='ClearTextPassword']") + if ($passwordElement -eq $null) + { + $passwordElement = $doc.CreateElement("add") + $passwordElement.SetAttribute("key", "ClearTextPassword") + $sourceElement.AppendChild($passwordElement) | Out-Null + } + $passwordElement.SetAttribute("value", $Password) +} + +function InsertMaestroPrivateFeedCredentials($Sources, $Creds, $Username, $Password) { + $maestroPrivateSources = $Sources.SelectNodes("add[contains(@key,'darc-int')]") + + Write-Host "Inserting credentials for $($maestroPrivateSources.Count) Maestro's private feeds." + + ForEach ($PackageSource in $maestroPrivateSources) { + Write-Host "`tInserting credential for Maestro's feed:" $PackageSource.Key + AddCredential -Creds $creds -Source $PackageSource.Key -Username $Username -Password $Password + } +} + +function EnablePrivatePackageSources($DisabledPackageSources) { + $maestroPrivateSources = $DisabledPackageSources.SelectNodes("add[contains(@key,'darc-int')]") + ForEach ($DisabledPackageSource in $maestroPrivateSources) { + Write-Host "`tEnsuring private source '$($DisabledPackageSource.key)' is enabled by deleting it from disabledPackageSource" + # Due to https://github.com/NuGet/Home/issues/10291, we must actually remove the disabled entries + $DisabledPackageSources.RemoveChild($DisabledPackageSource) + } +} + +if (!(Test-Path $ConfigFile -PathType Leaf)) { + Write-PipelineTelemetryError -Category 'Build' -Message "Eng/common/SetupNugetSources.ps1 returned a non-zero exit code. Couldn't find the NuGet config file: $ConfigFile" + ExitWithExitCode 1 +} + +if (!$Password) { + Write-PipelineTelemetryError -Category 'Build' -Message 'Eng/common/SetupNugetSources.ps1 returned a non-zero exit code. Please supply a valid PAT' + ExitWithExitCode 1 +} + +# Load NuGet.config +$doc = New-Object System.Xml.XmlDocument +$filename = (Get-Item $ConfigFile).FullName +$doc.Load($filename) + +# Get reference to or create one if none exist already +$sources = $doc.DocumentElement.SelectSingleNode("packageSources") +if ($sources -eq $null) { + $sources = $doc.CreateElement("packageSources") + $doc.DocumentElement.AppendChild($sources) | Out-Null +} + +# Looks for a node. Create it if none is found. +$creds = $doc.DocumentElement.SelectSingleNode("packageSourceCredentials") +if ($creds -eq $null) { + $creds = $doc.CreateElement("packageSourceCredentials") + $doc.DocumentElement.AppendChild($creds) | Out-Null +} + +# Check for disabledPackageSources; we'll enable any darc-int ones we find there +$disabledSources = $doc.DocumentElement.SelectSingleNode("disabledPackageSources") +if ($disabledSources -ne $null) { + Write-Host "Checking for any darc-int disabled package sources in the disabledPackageSources node" + EnablePrivatePackageSources -DisabledPackageSources $disabledSources +} + +$userName = "dn-bot" + +# Insert credential nodes for Maestro's private feeds +InsertMaestroPrivateFeedCredentials -Sources $sources -Creds $creds -Username $userName -Password $Password + +$dotnet31Source = $sources.SelectSingleNode("add[@key='dotnet3.1']") +if ($dotnet31Source -ne $null) { + AddPackageSource -Sources $sources -SourceName "dotnet3.1-internal" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal/nuget/v2" -Creds $creds -Username $userName -Password $Password + AddPackageSource -Sources $sources -SourceName "dotnet3.1-internal-transport" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal-transport/nuget/v2" -Creds $creds -Username $userName -Password $Password +} + +$dotnet5Source = $sources.SelectSingleNode("add[@key='dotnet5']") +if ($dotnet5Source -ne $null) { + AddPackageSource -Sources $sources -SourceName "dotnet5-internal" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet5-internal/nuget/v2" -Creds $creds -Username $userName -Password $Password + AddPackageSource -Sources $sources -SourceName "dotnet5-internal-transport" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet5-internal-transport/nuget/v2" -Creds $creds -Username $userName -Password $Password +} + +$dotnet6Source = $sources.SelectSingleNode("add[@key='dotnet6']") +if ($dotnet6Source -ne $null) { + AddPackageSource -Sources $sources -SourceName "dotnet6-internal" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet6-internal/nuget/v2" -Creds $creds -Username $userName -Password $Password + AddPackageSource -Sources $sources -SourceName "dotnet6-internal-transport" -SourceEndPoint "https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet6-internal-transport/nuget/v2" -Creds $creds -Username $userName -Password $Password +} + +$doc.Save($filename) diff --git a/eng/common/SetupNugetSources.sh b/eng/common/SetupNugetSources.sh new file mode 100644 index 000000000..ad3fb74fd --- /dev/null +++ b/eng/common/SetupNugetSources.sh @@ -0,0 +1,191 @@ +#!/usr/bin/env bash + +# This file is a temporary workaround for internal builds to be able to restore from private AzDO feeds. +# This file should be removed as part of this issue: https://github.com/dotnet/arcade/issues/4080 +# +# What the script does is iterate over all package sources in the pointed NuGet.config and add a credential entry +# under for each Maestro's managed private feed. Two additional credential +# entries are also added for the two private static internal feeds: dotnet3-internal and dotnet3-internal-transport. +# +# This script needs to be called in every job that will restore packages and which the base repo has +# private AzDO feeds in the NuGet.config. +# +# See example YAML call for this script below. Note the use of the variable `$(dn-bot-dnceng-artifact-feeds-rw)` +# from the AzureDevOps-Artifact-Feeds-Pats variable group. +# +# Any disabledPackageSources entries which start with "darc-int" will be re-enabled as part of this script executing. +# +# - task: Bash@3 +# displayName: Setup Private Feeds Credentials +# inputs: +# filePath: $(Build.SourcesDirectory)/eng/common/SetupNugetSources.sh +# arguments: $(Build.SourcesDirectory)/NuGet.config $Token +# condition: ne(variables['Agent.OS'], 'Windows_NT') +# env: +# Token: $(dn-bot-dnceng-artifact-feeds-rw) + +ConfigFile=$1 +CredToken=$2 +NL='\n' +TB=' ' + +source="${BASH_SOURCE[0]}" + +# resolve $source until the file is no longer a symlink +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. "$scriptroot/tools.sh" + +if [ ! -f "$ConfigFile" ]; then + Write-PipelineTelemetryError -Category 'Build' "Error: Eng/common/SetupNugetSources.sh returned a non-zero exit code. Couldn't find the NuGet config file: $ConfigFile" + ExitWithExitCode 1 +fi + +if [ -z "$CredToken" ]; then + Write-PipelineTelemetryError -category 'Build' "Error: Eng/common/SetupNugetSources.sh returned a non-zero exit code. Please supply a valid PAT" + ExitWithExitCode 1 +fi + +if [[ `uname -s` == "Darwin" ]]; then + NL=$'\\\n' + TB='' +fi + +# Ensure there is a ... section. +grep -i "" $ConfigFile +if [ "$?" != "0" ]; then + echo "Adding ... section." + ConfigNodeHeader="" + PackageSourcesTemplate="${TB}${NL}${TB}" + + sed -i.bak "s|$ConfigNodeHeader|$ConfigNodeHeader${NL}$PackageSourcesTemplate|" $ConfigFile +fi + +# Ensure there is a ... section. +grep -i "" $ConfigFile +if [ "$?" != "0" ]; then + echo "Adding ... section." + + PackageSourcesNodeFooter="" + PackageSourceCredentialsTemplate="${TB}${NL}${TB}" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourcesNodeFooter${NL}$PackageSourceCredentialsTemplate|" $ConfigFile +fi + +PackageSources=() + +# Ensure dotnet3.1-internal and dotnet3.1-internal-transport are in the packageSources if the public dotnet3.1 feeds are present +grep -i "" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet3.1-internal') + + grep -i "" $ConfigFile + if [ "$?" != "0" ]; then + echo "Adding dotnet3.1-internal-transport to the packageSources." + PackageSourcesNodeFooter="" + PackageSourceTemplate="${TB}" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet3.1-internal-transport') +fi + +# Ensure dotnet5-internal and dotnet5-internal-transport are in the packageSources if the public dotnet5 feeds are present +grep -i "" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet5-internal') + + grep -i "" $ConfigFile + if [ "$?" != "0" ]; then + echo "Adding dotnet5-internal-transport to the packageSources." + PackageSourcesNodeFooter="" + PackageSourceTemplate="${TB}" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet5-internal-transport') +fi + +# Ensure dotnet6-internal and dotnet6-internal-transport are in the packageSources if the public dotnet6 feeds are present +grep -i "" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet6-internal') + + grep -i "" $ConfigFile + if [ "$?" != "0" ]; then + echo "Adding dotnet6-internal-transport to the packageSources." + PackageSourcesNodeFooter="" + PackageSourceTemplate="${TB}" + + sed -i.bak "s|$PackageSourcesNodeFooter|$PackageSourceTemplate${NL}$PackageSourcesNodeFooter|" $ConfigFile + fi + PackageSources+=('dotnet6-internal-transport') +fi + +# I want things split line by line +PrevIFS=$IFS +IFS=$'\n' +PackageSources+="$IFS" +PackageSources+=$(grep -oh '"darc-int-[^"]*"' $ConfigFile | tr -d '"') +IFS=$PrevIFS + +for FeedName in ${PackageSources[@]} ; do + # Check if there is no existing credential for this FeedName + grep -i "<$FeedName>" $ConfigFile + if [ "$?" != "0" ]; then + echo "Adding credentials for $FeedName." + + PackageSourceCredentialsNodeFooter="" + NewCredential="${TB}${TB}<$FeedName>${NL}${NL}${NL}" + + sed -i.bak "s|$PackageSourceCredentialsNodeFooter|$NewCredential${NL}$PackageSourceCredentialsNodeFooter|" $ConfigFile + fi +done + +# Re-enable any entries in disabledPackageSources where the feed name contains darc-int +grep -i "" $ConfigFile +if [ "$?" == "0" ]; then + DisabledDarcIntSources=() + echo "Re-enabling any disabled \"darc-int\" package sources in $ConfigFile" + DisabledDarcIntSources+=$(grep -oh '"darc-int-[^"]*" value="true"' $ConfigFile | tr -d '"') + for DisabledSourceName in ${DisabledDarcIntSources[@]} ; do + if [[ $DisabledSourceName == darc-int* ]] + then + OldDisableValue="" + NewDisableValue="" + sed -i.bak "s|$OldDisableValue|$NewDisableValue|" $ConfigFile + echo "Neutralized disablePackageSources entry for '$DisabledSourceName'" + fi + done +fi diff --git a/eng/common/build.ps1 b/eng/common/build.ps1 new file mode 100644 index 000000000..8943da242 --- /dev/null +++ b/eng/common/build.ps1 @@ -0,0 +1,161 @@ +[CmdletBinding(PositionalBinding=$false)] +Param( + [string][Alias('c')]$configuration = "Debug", + [string]$platform = $null, + [string] $projects, + [string][Alias('v')]$verbosity = "minimal", + [string] $msbuildEngine = $null, + [bool] $warnAsError = $true, + [bool] $nodeReuse = $true, + [switch][Alias('r')]$restore, + [switch] $deployDeps, + [switch][Alias('b')]$build, + [switch] $rebuild, + [switch] $deploy, + [switch][Alias('t')]$test, + [switch] $integrationTest, + [switch] $performanceTest, + [switch] $sign, + [switch] $pack, + [switch] $publish, + [switch] $clean, + [switch][Alias('bl')]$binaryLog, + [switch][Alias('nobl')]$excludeCIBinarylog, + [switch] $ci, + [switch] $prepareMachine, + [string] $runtimeSourceFeed = '', + [string] $runtimeSourceFeedKey = '', + [switch] $excludePrereleaseVS, + [switch] $help, + [Parameter(ValueFromRemainingArguments=$true)][String[]]$properties +) + +# Unset 'Platform' environment variable to avoid unwanted collision in InstallDotNetCore.targets file +# some computer has this env var defined (e.g. Some HP) +if($env:Platform) { + $env:Platform="" +} +function Print-Usage() { + Write-Host "Common settings:" + Write-Host " -configuration Build configuration: 'Debug' or 'Release' (short: -c)" + Write-Host " -platform Platform configuration: 'x86', 'x64' or any valid Platform value to pass to msbuild" + Write-Host " -verbosity Msbuild verbosity: q[uiet], m[inimal], n[ormal], d[etailed], and diag[nostic] (short: -v)" + Write-Host " -binaryLog Output binary log (short: -bl)" + Write-Host " -help Print help and exit" + Write-Host "" + + Write-Host "Actions:" + Write-Host " -restore Restore dependencies (short: -r)" + Write-Host " -build Build solution (short: -b)" + Write-Host " -rebuild Rebuild solution" + Write-Host " -deploy Deploy built VSIXes" + Write-Host " -deployDeps Deploy dependencies (e.g. VSIXes for integration tests)" + Write-Host " -test Run all unit tests in the solution (short: -t)" + Write-Host " -integrationTest Run all integration tests in the solution" + Write-Host " -performanceTest Run all performance tests in the solution" + Write-Host " -pack Package build outputs into NuGet packages and Willow components" + Write-Host " -sign Sign build outputs" + Write-Host " -publish Publish artifacts (e.g. symbols)" + Write-Host " -clean Clean the solution" + Write-Host "" + + Write-Host "Advanced settings:" + Write-Host " -projects Semi-colon delimited list of sln/proj's to build. Globbing is supported (*.sln)" + Write-Host " -ci Set when running on CI server" + Write-Host " -excludeCIBinarylog Don't output binary log (short: -nobl)" + Write-Host " -prepareMachine Prepare machine for CI run, clean up processes after build" + Write-Host " -warnAsError Sets warnaserror msbuild parameter ('true' or 'false')" + Write-Host " -msbuildEngine Msbuild engine to use to run build ('dotnet', 'vs', or unspecified)." + Write-Host " -excludePrereleaseVS Set to exclude build engines in prerelease versions of Visual Studio" + Write-Host "" + + Write-Host "Command line arguments not listed above are passed thru to msbuild." + Write-Host "The above arguments can be shortened as much as to be unambiguous (e.g. -co for configuration, -t for test, etc.)." +} + +. $PSScriptRoot\tools.ps1 + +function InitializeCustomToolset { + if (-not $restore) { + return + } + + $script = Join-Path $EngRoot 'restore-toolset.ps1' + + if (Test-Path $script) { + . $script + } +} + +function Build { + $toolsetBuildProj = InitializeToolset + InitializeCustomToolset + + $bl = if ($binaryLog) { '/bl:' + (Join-Path $LogDir 'Build.binlog') } else { '' } + $platformArg = if ($platform) { "/p:Platform=$platform" } else { '' } + + if ($projects) { + # Re-assign properties to a new variable because PowerShell doesn't let us append properties directly for unclear reasons. + # Explicitly set the type as string[] because otherwise PowerShell would make this char[] if $properties is empty. + [string[]] $msbuildArgs = $properties + + # Resolve relative project paths into full paths + $projects = ($projects.Split(';').ForEach({Resolve-Path $_}) -join ';') + + $msbuildArgs += "/p:Projects=$projects" + $properties = $msbuildArgs + } + + MSBuild $toolsetBuildProj ` + $bl ` + $platformArg ` + /p:Configuration=$configuration ` + /p:RepoRoot=$RepoRoot ` + /p:Restore=$restore ` + /p:DeployDeps=$deployDeps ` + /p:Build=$build ` + /p:Rebuild=$rebuild ` + /p:Deploy=$deploy ` + /p:Test=$test ` + /p:Pack=$pack ` + /p:IntegrationTest=$integrationTest ` + /p:PerformanceTest=$performanceTest ` + /p:Sign=$sign ` + /p:Publish=$publish ` + @properties +} + +try { + if ($clean) { + if (Test-Path $ArtifactsDir) { + Remove-Item -Recurse -Force $ArtifactsDir + Write-Host 'Artifacts directory deleted.' + } + exit 0 + } + + if ($help -or (($null -ne $properties) -and ($properties.Contains('/help') -or $properties.Contains('/?')))) { + Print-Usage + exit 0 + } + + if ($ci) { + if (-not $excludeCIBinarylog) { + $binaryLog = $true + } + $nodeReuse = $false + } + + if ($restore) { + InitializeNativeTools + } + + Build +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message $_ + ExitWithExitCode 1 +} + +ExitWithExitCode 0 diff --git a/eng/common/build.sh b/eng/common/build.sh new file mode 100644 index 000000000..55b298f16 --- /dev/null +++ b/eng/common/build.sh @@ -0,0 +1,232 @@ +#!/usr/bin/env bash + +# Stop script if unbound variable found (use ${var:-} if intentional) +set -u + +# Stop script if command returns non-zero exit code. +# Prevents hidden errors caused by missing error code propagation. +set -e + +usage() +{ + echo "Common settings:" + echo " --configuration Build configuration: 'Debug' or 'Release' (short: -c)" + echo " --verbosity Msbuild verbosity: q[uiet], m[inimal], n[ormal], d[etailed], and diag[nostic] (short: -v)" + echo " --binaryLog Create MSBuild binary log (short: -bl)" + echo " --help Print help and exit (short: -h)" + echo "" + + echo "Actions:" + echo " --restore Restore dependencies (short: -r)" + echo " --build Build solution (short: -b)" + echo " --rebuild Rebuild solution" + echo " --test Run all unit tests in the solution (short: -t)" + echo " --integrationTest Run all integration tests in the solution" + echo " --performanceTest Run all performance tests in the solution" + echo " --pack Package build outputs into NuGet packages and Willow components" + echo " --sign Sign build outputs" + echo " --publish Publish artifacts (e.g. symbols)" + echo " --clean Clean the solution" + echo "" + + echo "Advanced settings:" + echo " --projects Project or solution file(s) to build" + echo " --ci Set when running on CI server" + echo " --excludeCIBinarylog Don't output binary log (short: -nobl)" + echo " --prepareMachine Prepare machine for CI run, clean up processes after build" + echo " --nodeReuse Sets nodereuse msbuild parameter ('true' or 'false')" + echo " --warnAsError Sets warnaserror msbuild parameter ('true' or 'false')" + echo "" + echo "Command line arguments not listed above are passed thru to msbuild." + echo "Arguments can also be passed in with a single hyphen." +} + +source="${BASH_SOURCE[0]}" + +# resolve $source until the file is no longer a symlink +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +restore=false +build=false +rebuild=false +test=false +integration_test=false +performance_test=false +pack=false +publish=false +sign=false +public=false +ci=false +clean=false + +warn_as_error=true +node_reuse=true +binary_log=false +exclude_ci_binary_log=false +pipelines_log=false + +projects='' +configuration='Debug' +prepare_machine=false +verbosity='minimal' +runtime_source_feed='' +runtime_source_feed_key='' + +properties='' +while [[ $# > 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -help|-h) + usage + exit 0 + ;; + -clean) + clean=true + ;; + -configuration|-c) + configuration=$2 + shift + ;; + -verbosity|-v) + verbosity=$2 + shift + ;; + -binarylog|-bl) + binary_log=true + ;; + -excludeCIBinarylog|-nobl) + exclude_ci_binary_log=true + ;; + -pipelineslog|-pl) + pipelines_log=true + ;; + -restore|-r) + restore=true + ;; + -build|-b) + build=true + ;; + -rebuild) + rebuild=true + ;; + -pack) + pack=true + ;; + -test|-t) + test=true + ;; + -integrationtest) + integration_test=true + ;; + -performancetest) + performance_test=true + ;; + -sign) + sign=true + ;; + -publish) + publish=true + ;; + -preparemachine) + prepare_machine=true + ;; + -projects) + projects=$2 + shift + ;; + -ci) + ci=true + ;; + -warnaserror) + warn_as_error=$2 + shift + ;; + -nodereuse) + node_reuse=$2 + shift + ;; + -runtimesourcefeed) + runtime_source_feed=$2 + shift + ;; + -runtimesourcefeedkey) + runtime_source_feed_key=$2 + shift + ;; + *) + properties="$properties $1" + ;; + esac + + shift +done + +if [[ "$ci" == true ]]; then + pipelines_log=true + node_reuse=false + if [[ "$exclude_ci_binary_log" == false ]]; then + binary_log=true + fi +fi + +. "$scriptroot/tools.sh" + +function InitializeCustomToolset { + local script="$eng_root/restore-toolset.sh" + + if [[ -a "$script" ]]; then + . "$script" + fi +} + +function Build { + InitializeToolset + InitializeCustomToolset + + if [[ ! -z "$projects" ]]; then + properties="$properties /p:Projects=$projects" + fi + + local bl="" + if [[ "$binary_log" == true ]]; then + bl="/bl:\"$log_dir/Build.binlog\"" + fi + + MSBuild $_InitializeToolset \ + $bl \ + /p:Configuration=$configuration \ + /p:RepoRoot="$repo_root" \ + /p:Restore=$restore \ + /p:Build=$build \ + /p:Rebuild=$rebuild \ + /p:Test=$test \ + /p:Pack=$pack \ + /p:IntegrationTest=$integration_test \ + /p:PerformanceTest=$performance_test \ + /p:Sign=$sign \ + /p:Publish=$publish \ + $properties + + ExitWithExitCode 0 +} + +if [[ "$clean" == true ]]; then + if [ -d "$artifacts_dir" ]; then + rm -rf $artifacts_dir + echo "Artifacts directory deleted." + fi + exit 0 +fi + +if [[ "$restore" == true ]]; then + InitializeNativeTools +fi + +Build diff --git a/eng/common/cibuild.sh b/eng/common/cibuild.sh new file mode 100644 index 000000000..1a02c0dec --- /dev/null +++ b/eng/common/cibuild.sh @@ -0,0 +1,16 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" + +# resolve $SOURCE until the file is no longer a symlink +while [[ -h $source ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + + # if $source was a relative symlink, we need to resolve it relative to the path where + # the symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. "$scriptroot/build.sh" --restore --build --test --pack --publish --ci $@ \ No newline at end of file diff --git a/eng/common/cross/arm/sources.list.bionic b/eng/common/cross/arm/sources.list.bionic new file mode 100644 index 000000000..210955740 --- /dev/null +++ b/eng/common/cross/arm/sources.list.bionic @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse diff --git a/eng/common/cross/arm/sources.list.jessie b/eng/common/cross/arm/sources.list.jessie new file mode 100644 index 000000000..4d142ac9b --- /dev/null +++ b/eng/common/cross/arm/sources.list.jessie @@ -0,0 +1,3 @@ +# Debian (sid) # UNSTABLE +deb http://ftp.debian.org/debian/ sid main contrib non-free +deb-src http://ftp.debian.org/debian/ sid main contrib non-free diff --git a/eng/common/cross/arm/sources.list.trusty b/eng/common/cross/arm/sources.list.trusty new file mode 100644 index 000000000..07d8f88d8 --- /dev/null +++ b/eng/common/cross/arm/sources.list.trusty @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ trusty main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-security main restricted universe multiverse \ No newline at end of file diff --git a/eng/common/cross/arm/sources.list.xenial b/eng/common/cross/arm/sources.list.xenial new file mode 100644 index 000000000..eacd86b7d --- /dev/null +++ b/eng/common/cross/arm/sources.list.xenial @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ xenial main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-security main restricted universe multiverse \ No newline at end of file diff --git a/eng/common/cross/arm/sources.list.zesty b/eng/common/cross/arm/sources.list.zesty new file mode 100644 index 000000000..ea2c14a78 --- /dev/null +++ b/eng/common/cross/arm/sources.list.zesty @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ zesty main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-security main restricted universe multiverse diff --git a/eng/common/cross/arm/trusty-lttng-2.4.patch b/eng/common/cross/arm/trusty-lttng-2.4.patch new file mode 100644 index 000000000..8e4dd7ae7 --- /dev/null +++ b/eng/common/cross/arm/trusty-lttng-2.4.patch @@ -0,0 +1,71 @@ +From e72c9d7ead60e3317bd6d1fade995c07021c947b Mon Sep 17 00:00:00 2001 +From: Mathieu Desnoyers +Date: Thu, 7 May 2015 13:25:04 -0400 +Subject: [PATCH] Fix: building probe providers with C++ compiler + +Robert Daniels wrote: +> > I'm attempting to use lttng userspace tracing with a C++ application +> > on an ARM platform. I'm using GCC 4.8.4 on Linux 3.14 with the 2.6 +> > release of lttng. I've compiled lttng-modules, lttng-ust, and +> > lttng-tools and have been able to get a simple test working with C +> > code. When I attempt to run the hello.cxx test on my target it will +> > segfault. +> +> +> I spent a little time digging into this issue and finally discovered the +> cause of my segfault with ARM C++ tracepoints. +> +> There is a struct called 'lttng_event' in ust-events.h which contains an +> empty union 'u'. This was the cause of my issue. Under C, this empty union +> compiles to a zero byte member while under C++ it compiles to a one byte +> member, and in my case was four-byte aligned which caused my C++ code to +> have the 'cds_list_head node' offset incorrectly by four bytes. This lead +> to an incorrect linked list structure which caused my issue. +> +> Since this union is empty, I simply removed it from the struct and everything +> worked correctly. +> +> I don't know the history or purpose behind this empty union so I'd like to +> know if this is a safe fix. If it is I can submit a patch with the union +> removed. + +That's a very nice catch! + +We do not support building tracepoint probe provider with +g++ yet, as stated in lttng-ust(3): + +"- Note for C++ support: although an application instrumented with + tracepoints can be compiled with g++, tracepoint probes should be + compiled with gcc (only tested with gcc so far)." + +However, if it works fine with this fix, then I'm tempted to take it, +especially because removing the empty union does not appear to affect +the layout of struct lttng_event as seen from liblttng-ust, which must +be compiled with a C compiler, and from probe providers compiled with +a C compiler. So all we are changing is the layout of a probe provider +compiled with a C++ compiler, which is anyway buggy at the moment, +because it is not compatible with the layout expected by liblttng-ust +compiled with a C compiler. + +Reported-by: Robert Daniels +Signed-off-by: Mathieu Desnoyers +--- + include/lttng/ust-events.h | 2 -- + 1 file changed, 2 deletions(-) + +diff --git a/usr/include/lttng/ust-events.h b/usr/include/lttng/ust-events.h +index 328a875..3d7a274 100644 +--- a/usr/include/lttng/ust-events.h ++++ b/usr/include/lttng/ust-events.h +@@ -407,8 +407,6 @@ struct lttng_event { + void *_deprecated1; + struct lttng_ctx *ctx; + enum lttng_ust_instrumentation instrumentation; +- union { +- } u; + struct cds_list_head node; /* Event list in session */ + struct cds_list_head _deprecated2; + void *_deprecated3; +-- +2.7.4 + diff --git a/eng/common/cross/arm/trusty.patch b/eng/common/cross/arm/trusty.patch new file mode 100644 index 000000000..2f2972f8e --- /dev/null +++ b/eng/common/cross/arm/trusty.patch @@ -0,0 +1,97 @@ +diff -u -r a/usr/include/urcu/uatomic/generic.h b/usr/include/urcu/uatomic/generic.h +--- a/usr/include/urcu/uatomic/generic.h 2014-03-28 06:04:42.000000000 +0900 ++++ b/usr/include/urcu/uatomic/generic.h 2017-02-13 10:35:21.189927116 +0900 +@@ -65,17 +65,17 @@ + switch (len) { + #ifdef UATOMIC_HAS_ATOMIC_BYTE + case 1: +- return __sync_val_compare_and_swap_1(addr, old, _new); ++ return __sync_val_compare_and_swap_1((uint8_t *) addr, old, _new); + #endif + #ifdef UATOMIC_HAS_ATOMIC_SHORT + case 2: +- return __sync_val_compare_and_swap_2(addr, old, _new); ++ return __sync_val_compare_and_swap_2((uint16_t *) addr, old, _new); + #endif + case 4: +- return __sync_val_compare_and_swap_4(addr, old, _new); ++ return __sync_val_compare_and_swap_4((uint32_t *) addr, old, _new); + #if (CAA_BITS_PER_LONG == 64) + case 8: +- return __sync_val_compare_and_swap_8(addr, old, _new); ++ return __sync_val_compare_and_swap_8((uint64_t *) addr, old, _new); + #endif + } + _uatomic_link_error(); +@@ -100,20 +100,20 @@ + switch (len) { + #ifdef UATOMIC_HAS_ATOMIC_BYTE + case 1: +- __sync_and_and_fetch_1(addr, val); ++ __sync_and_and_fetch_1((uint8_t *) addr, val); + return; + #endif + #ifdef UATOMIC_HAS_ATOMIC_SHORT + case 2: +- __sync_and_and_fetch_2(addr, val); ++ __sync_and_and_fetch_2((uint16_t *) addr, val); + return; + #endif + case 4: +- __sync_and_and_fetch_4(addr, val); ++ __sync_and_and_fetch_4((uint32_t *) addr, val); + return; + #if (CAA_BITS_PER_LONG == 64) + case 8: +- __sync_and_and_fetch_8(addr, val); ++ __sync_and_and_fetch_8((uint64_t *) addr, val); + return; + #endif + } +@@ -139,20 +139,20 @@ + switch (len) { + #ifdef UATOMIC_HAS_ATOMIC_BYTE + case 1: +- __sync_or_and_fetch_1(addr, val); ++ __sync_or_and_fetch_1((uint8_t *) addr, val); + return; + #endif + #ifdef UATOMIC_HAS_ATOMIC_SHORT + case 2: +- __sync_or_and_fetch_2(addr, val); ++ __sync_or_and_fetch_2((uint16_t *) addr, val); + return; + #endif + case 4: +- __sync_or_and_fetch_4(addr, val); ++ __sync_or_and_fetch_4((uint32_t *) addr, val); + return; + #if (CAA_BITS_PER_LONG == 64) + case 8: +- __sync_or_and_fetch_8(addr, val); ++ __sync_or_and_fetch_8((uint64_t *) addr, val); + return; + #endif + } +@@ -180,17 +180,17 @@ + switch (len) { + #ifdef UATOMIC_HAS_ATOMIC_BYTE + case 1: +- return __sync_add_and_fetch_1(addr, val); ++ return __sync_add_and_fetch_1((uint8_t *) addr, val); + #endif + #ifdef UATOMIC_HAS_ATOMIC_SHORT + case 2: +- return __sync_add_and_fetch_2(addr, val); ++ return __sync_add_and_fetch_2((uint16_t *) addr, val); + #endif + case 4: +- return __sync_add_and_fetch_4(addr, val); ++ return __sync_add_and_fetch_4((uint32_t *) addr, val); + #if (CAA_BITS_PER_LONG == 64) + case 8: +- return __sync_add_and_fetch_8(addr, val); ++ return __sync_add_and_fetch_8((uint64_t *) addr, val); + #endif + } + _uatomic_link_error(); diff --git a/eng/common/cross/arm64/sources.list.bionic b/eng/common/cross/arm64/sources.list.bionic new file mode 100644 index 000000000..210955740 --- /dev/null +++ b/eng/common/cross/arm64/sources.list.bionic @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse diff --git a/eng/common/cross/arm64/sources.list.buster b/eng/common/cross/arm64/sources.list.buster new file mode 100644 index 000000000..7194ac64a --- /dev/null +++ b/eng/common/cross/arm64/sources.list.buster @@ -0,0 +1,11 @@ +deb http://deb.debian.org/debian buster main +deb-src http://deb.debian.org/debian buster main + +deb http://deb.debian.org/debian-security/ buster/updates main +deb-src http://deb.debian.org/debian-security/ buster/updates main + +deb http://deb.debian.org/debian buster-updates main +deb-src http://deb.debian.org/debian buster-updates main + +deb http://deb.debian.org/debian buster-backports main contrib non-free +deb-src http://deb.debian.org/debian buster-backports main contrib non-free diff --git a/eng/common/cross/arm64/sources.list.stretch b/eng/common/cross/arm64/sources.list.stretch new file mode 100644 index 000000000..0e1215774 --- /dev/null +++ b/eng/common/cross/arm64/sources.list.stretch @@ -0,0 +1,12 @@ +deb http://deb.debian.org/debian stretch main +deb-src http://deb.debian.org/debian stretch main + +deb http://deb.debian.org/debian-security/ stretch/updates main +deb-src http://deb.debian.org/debian-security/ stretch/updates main + +deb http://deb.debian.org/debian stretch-updates main +deb-src http://deb.debian.org/debian stretch-updates main + +deb http://deb.debian.org/debian stretch-backports main contrib non-free +deb-src http://deb.debian.org/debian stretch-backports main contrib non-free + diff --git a/eng/common/cross/arm64/sources.list.trusty b/eng/common/cross/arm64/sources.list.trusty new file mode 100644 index 000000000..07d8f88d8 --- /dev/null +++ b/eng/common/cross/arm64/sources.list.trusty @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ trusty main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ trusty-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ trusty-security main restricted universe multiverse \ No newline at end of file diff --git a/eng/common/cross/arm64/sources.list.xenial b/eng/common/cross/arm64/sources.list.xenial new file mode 100644 index 000000000..eacd86b7d --- /dev/null +++ b/eng/common/cross/arm64/sources.list.xenial @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ xenial main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ xenial-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ xenial-security main restricted universe multiverse \ No newline at end of file diff --git a/eng/common/cross/arm64/sources.list.zesty b/eng/common/cross/arm64/sources.list.zesty new file mode 100644 index 000000000..ea2c14a78 --- /dev/null +++ b/eng/common/cross/arm64/sources.list.zesty @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ zesty main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ zesty-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ zesty-security main restricted universe multiverse diff --git a/eng/common/cross/arm64/tizen-build-rootfs.sh b/eng/common/cross/arm64/tizen-build-rootfs.sh new file mode 100644 index 000000000..13bfddb5e --- /dev/null +++ b/eng/common/cross/arm64/tizen-build-rootfs.sh @@ -0,0 +1,35 @@ +#!/usr/bin/env bash +set -e + +__CrossDir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) +__TIZEN_CROSSDIR="$__CrossDir/tizen" + +if [[ -z "$ROOTFS_DIR" ]]; then + echo "ROOTFS_DIR is not defined." + exit 1; +fi + +TIZEN_TMP_DIR=$ROOTFS_DIR/tizen_tmp +mkdir -p $TIZEN_TMP_DIR + +# Download files +echo ">>Start downloading files" +VERBOSE=1 $__CrossDir/tizen-fetch.sh $TIZEN_TMP_DIR +echo "<>Start constructing Tizen rootfs" +TIZEN_RPM_FILES=`ls $TIZEN_TMP_DIR/*.rpm` +cd $ROOTFS_DIR +for f in $TIZEN_RPM_FILES; do + rpm2cpio $f | cpio -idm --quiet +done +echo "<>Start configuring Tizen rootfs" +ln -sfn asm-arm64 ./usr/include/asm +patch -p1 < $__TIZEN_CROSSDIR/tizen.patch +echo "</dev/null; then + VERBOSE=0 +fi + +Log() +{ + if [ $VERBOSE -ge $1 ]; then + echo ${@:2} + fi +} + +Inform() +{ + Log 1 -e "\x1B[0;34m$@\x1B[m" +} + +Debug() +{ + Log 2 -e "\x1B[0;32m$@\x1B[m" +} + +Error() +{ + >&2 Log 0 -e "\x1B[0;31m$@\x1B[m" +} + +Fetch() +{ + URL=$1 + FILE=$2 + PROGRESS=$3 + if [ $VERBOSE -ge 1 ] && [ $PROGRESS ]; then + CURL_OPT="--progress-bar" + else + CURL_OPT="--silent" + fi + curl $CURL_OPT $URL > $FILE +} + +hash curl 2> /dev/null || { Error "Require 'curl' Aborting."; exit 1; } +hash xmllint 2> /dev/null || { Error "Require 'xmllint' Aborting."; exit 1; } +hash sha256sum 2> /dev/null || { Error "Require 'sha256sum' Aborting."; exit 1; } + +TMPDIR=$1 +if [ ! -d $TMPDIR ]; then + TMPDIR=./tizen_tmp + Debug "Create temporary directory : $TMPDIR" + mkdir -p $TMPDIR +fi + +TIZEN_URL=http://download.tizen.org/snapshots/tizen/ +BUILD_XML=build.xml +REPOMD_XML=repomd.xml +PRIMARY_XML=primary.xml +TARGET_URL="http://__not_initialized" + +Xpath_get() +{ + XPATH_RESULT='' + XPATH=$1 + XML_FILE=$2 + RESULT=$(xmllint --xpath $XPATH $XML_FILE) + if [[ -z ${RESULT// } ]]; then + Error "Can not find target from $XML_FILE" + Debug "Xpath = $XPATH" + exit 1 + fi + XPATH_RESULT=$RESULT +} + +fetch_tizen_pkgs_init() +{ + TARGET=$1 + PROFILE=$2 + Debug "Initialize TARGET=$TARGET, PROFILE=$PROFILE" + + TMP_PKG_DIR=$TMPDIR/tizen_${PROFILE}_pkgs + if [ -d $TMP_PKG_DIR ]; then rm -rf $TMP_PKG_DIR; fi + mkdir -p $TMP_PKG_DIR + + PKG_URL=$TIZEN_URL/$PROFILE/latest + + BUILD_XML_URL=$PKG_URL/$BUILD_XML + TMP_BUILD=$TMP_PKG_DIR/$BUILD_XML + TMP_REPOMD=$TMP_PKG_DIR/$REPOMD_XML + TMP_PRIMARY=$TMP_PKG_DIR/$PRIMARY_XML + TMP_PRIMARYGZ=${TMP_PRIMARY}.gz + + Fetch $BUILD_XML_URL $TMP_BUILD + + Debug "fetch $BUILD_XML_URL to $TMP_BUILD" + + TARGET_XPATH="//build/buildtargets/buildtarget[@name=\"$TARGET\"]/repo[@type=\"binary\"]/text()" + Xpath_get $TARGET_XPATH $TMP_BUILD + TARGET_PATH=$XPATH_RESULT + TARGET_URL=$PKG_URL/$TARGET_PATH + + REPOMD_URL=$TARGET_URL/repodata/repomd.xml + PRIMARY_XPATH='string(//*[local-name()="data"][@type="primary"]/*[local-name()="location"]/@href)' + + Fetch $REPOMD_URL $TMP_REPOMD + + Debug "fetch $REPOMD_URL to $TMP_REPOMD" + + Xpath_get $PRIMARY_XPATH $TMP_REPOMD + PRIMARY_XML_PATH=$XPATH_RESULT + PRIMARY_URL=$TARGET_URL/$PRIMARY_XML_PATH + + Fetch $PRIMARY_URL $TMP_PRIMARYGZ + + Debug "fetch $PRIMARY_URL to $TMP_PRIMARYGZ" + + gunzip $TMP_PRIMARYGZ + + Debug "unzip $TMP_PRIMARYGZ to $TMP_PRIMARY" +} + +fetch_tizen_pkgs() +{ + ARCH=$1 + PACKAGE_XPATH_TPL='string(//*[local-name()="metadata"]/*[local-name()="package"][*[local-name()="name"][text()="_PKG_"]][*[local-name()="arch"][text()="_ARCH_"]]/*[local-name()="location"]/@href)' + + PACKAGE_CHECKSUM_XPATH_TPL='string(//*[local-name()="metadata"]/*[local-name()="package"][*[local-name()="name"][text()="_PKG_"]][*[local-name()="arch"][text()="_ARCH_"]]/*[local-name()="checksum"]/text())' + + for pkg in ${@:2} + do + Inform "Fetching... $pkg" + XPATH=${PACKAGE_XPATH_TPL/_PKG_/$pkg} + XPATH=${XPATH/_ARCH_/$ARCH} + Xpath_get $XPATH $TMP_PRIMARY + PKG_PATH=$XPATH_RESULT + + XPATH=${PACKAGE_CHECKSUM_XPATH_TPL/_PKG_/$pkg} + XPATH=${XPATH/_ARCH_/$ARCH} + Xpath_get $XPATH $TMP_PRIMARY + CHECKSUM=$XPATH_RESULT + + PKG_URL=$TARGET_URL/$PKG_PATH + PKG_FILE=$(basename $PKG_PATH) + PKG_PATH=$TMPDIR/$PKG_FILE + + Debug "Download $PKG_URL to $PKG_PATH" + Fetch $PKG_URL $PKG_PATH true + + echo "$CHECKSUM $PKG_PATH" | sha256sum -c - > /dev/null + if [ $? -ne 0 ]; then + Error "Fail to fetch $PKG_URL to $PKG_PATH" + Debug "Checksum = $CHECKSUM" + exit 1 + fi + done +} + +Inform "Initialize arm base" +fetch_tizen_pkgs_init standard base +Inform "fetch common packages" +fetch_tizen_pkgs aarch64 gcc glibc glibc-devel libicu libicu-devel libatomic linux-glibc-devel keyutils keyutils-devel libkeyutils +Inform "fetch coreclr packages" +fetch_tizen_pkgs aarch64 lldb lldb-devel libgcc libstdc++ libstdc++-devel libunwind libunwind-devel lttng-ust-devel lttng-ust userspace-rcu-devel userspace-rcu +Inform "fetch corefx packages" +fetch_tizen_pkgs aarch64 libcom_err libcom_err-devel zlib zlib-devel libopenssl11 libopenssl1.1-devel krb5 krb5-devel + +Inform "Initialize standard unified" +fetch_tizen_pkgs_init standard unified +Inform "fetch corefx packages" +fetch_tizen_pkgs aarch64 gssdp gssdp-devel tizen-release + diff --git a/eng/common/cross/arm64/tizen/tizen.patch b/eng/common/cross/arm64/tizen/tizen.patch new file mode 100644 index 000000000..af7c8be05 --- /dev/null +++ b/eng/common/cross/arm64/tizen/tizen.patch @@ -0,0 +1,9 @@ +diff -u -r a/usr/lib/libc.so b/usr/lib/libc.so +--- a/usr/lib64/libc.so 2016-12-30 23:00:08.284951863 +0900 ++++ b/usr/lib64/libc.so 2016-12-30 23:00:32.140951815 +0900 +@@ -2,4 +2,4 @@ + Use the shared library, but some functions are only in + the static library, so try that secondarily. */ + OUTPUT_FORMAT(elf64-littleaarch64) +-GROUP ( /lib64/libc.so.6 /usr/lib64/libc_nonshared.a AS_NEEDED ( /lib/ld-linux-aarch64.so.1 ) ) ++GROUP ( libc.so.6 libc_nonshared.a AS_NEEDED ( ld-linux-aarch64.so.1 ) ) diff --git a/eng/common/cross/armel/armel.jessie.patch b/eng/common/cross/armel/armel.jessie.patch new file mode 100644 index 000000000..2d2615619 --- /dev/null +++ b/eng/common/cross/armel/armel.jessie.patch @@ -0,0 +1,43 @@ +diff -u -r a/usr/include/urcu/uatomic/generic.h b/usr/include/urcu/uatomic/generic.h +--- a/usr/include/urcu/uatomic/generic.h 2014-10-22 15:00:58.000000000 -0700 ++++ b/usr/include/urcu/uatomic/generic.h 2020-10-30 21:38:28.550000000 -0700 +@@ -69,10 +69,10 @@ + #endif + #ifdef UATOMIC_HAS_ATOMIC_SHORT + case 2: +- return __sync_val_compare_and_swap_2(addr, old, _new); ++ return __sync_val_compare_and_swap_2((uint16_t*) addr, old, _new); + #endif + case 4: +- return __sync_val_compare_and_swap_4(addr, old, _new); ++ return __sync_val_compare_and_swap_4((uint32_t*) addr, old, _new); + #if (CAA_BITS_PER_LONG == 64) + case 8: + return __sync_val_compare_and_swap_8(addr, old, _new); +@@ -109,7 +109,7 @@ + return; + #endif + case 4: +- __sync_and_and_fetch_4(addr, val); ++ __sync_and_and_fetch_4((uint32_t*) addr, val); + return; + #if (CAA_BITS_PER_LONG == 64) + case 8: +@@ -148,7 +148,7 @@ + return; + #endif + case 4: +- __sync_or_and_fetch_4(addr, val); ++ __sync_or_and_fetch_4((uint32_t*) addr, val); + return; + #if (CAA_BITS_PER_LONG == 64) + case 8: +@@ -187,7 +187,7 @@ + return __sync_add_and_fetch_2(addr, val); + #endif + case 4: +- return __sync_add_and_fetch_4(addr, val); ++ return __sync_add_and_fetch_4((uint32_t*) addr, val); + #if (CAA_BITS_PER_LONG == 64) + case 8: + return __sync_add_and_fetch_8(addr, val); diff --git a/eng/common/cross/armel/sources.list.jessie b/eng/common/cross/armel/sources.list.jessie new file mode 100644 index 000000000..3d9c3059d --- /dev/null +++ b/eng/common/cross/armel/sources.list.jessie @@ -0,0 +1,3 @@ +# Debian (jessie) # Stable +deb http://ftp.debian.org/debian/ jessie main contrib non-free +deb-src http://ftp.debian.org/debian/ jessie main contrib non-free diff --git a/eng/common/cross/armel/tizen-build-rootfs.sh b/eng/common/cross/armel/tizen-build-rootfs.sh new file mode 100644 index 000000000..9a4438af6 --- /dev/null +++ b/eng/common/cross/armel/tizen-build-rootfs.sh @@ -0,0 +1,35 @@ +#!/usr/bin/env bash +set -e + +__ARM_SOFTFP_CrossDir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) +__TIZEN_CROSSDIR="$__ARM_SOFTFP_CrossDir/tizen" + +if [[ -z "$ROOTFS_DIR" ]]; then + echo "ROOTFS_DIR is not defined." + exit 1; +fi + +TIZEN_TMP_DIR=$ROOTFS_DIR/tizen_tmp +mkdir -p $TIZEN_TMP_DIR + +# Download files +echo ">>Start downloading files" +VERBOSE=1 $__ARM_SOFTFP_CrossDir/tizen-fetch.sh $TIZEN_TMP_DIR +echo "<>Start constructing Tizen rootfs" +TIZEN_RPM_FILES=`ls $TIZEN_TMP_DIR/*.rpm` +cd $ROOTFS_DIR +for f in $TIZEN_RPM_FILES; do + rpm2cpio $f | cpio -idm --quiet +done +echo "<>Start configuring Tizen rootfs" +ln -sfn asm-arm ./usr/include/asm +patch -p1 < $__TIZEN_CROSSDIR/tizen.patch +echo "</dev/null; then + VERBOSE=0 +fi + +Log() +{ + if [ $VERBOSE -ge $1 ]; then + echo ${@:2} + fi +} + +Inform() +{ + Log 1 -e "\x1B[0;34m$@\x1B[m" +} + +Debug() +{ + Log 2 -e "\x1B[0;32m$@\x1B[m" +} + +Error() +{ + >&2 Log 0 -e "\x1B[0;31m$@\x1B[m" +} + +Fetch() +{ + URL=$1 + FILE=$2 + PROGRESS=$3 + if [ $VERBOSE -ge 1 ] && [ $PROGRESS ]; then + CURL_OPT="--progress-bar" + else + CURL_OPT="--silent" + fi + curl $CURL_OPT $URL > $FILE +} + +hash curl 2> /dev/null || { Error "Require 'curl' Aborting."; exit 1; } +hash xmllint 2> /dev/null || { Error "Require 'xmllint' Aborting."; exit 1; } +hash sha256sum 2> /dev/null || { Error "Require 'sha256sum' Aborting."; exit 1; } + +TMPDIR=$1 +if [ ! -d $TMPDIR ]; then + TMPDIR=./tizen_tmp + Debug "Create temporary directory : $TMPDIR" + mkdir -p $TMPDIR +fi + +TIZEN_URL=http://download.tizen.org/snapshots/tizen +BUILD_XML=build.xml +REPOMD_XML=repomd.xml +PRIMARY_XML=primary.xml +TARGET_URL="http://__not_initialized" + +Xpath_get() +{ + XPATH_RESULT='' + XPATH=$1 + XML_FILE=$2 + RESULT=$(xmllint --xpath $XPATH $XML_FILE) + if [[ -z ${RESULT// } ]]; then + Error "Can not find target from $XML_FILE" + Debug "Xpath = $XPATH" + exit 1 + fi + XPATH_RESULT=$RESULT +} + +fetch_tizen_pkgs_init() +{ + TARGET=$1 + PROFILE=$2 + Debug "Initialize TARGET=$TARGET, PROFILE=$PROFILE" + + TMP_PKG_DIR=$TMPDIR/tizen_${PROFILE}_pkgs + if [ -d $TMP_PKG_DIR ]; then rm -rf $TMP_PKG_DIR; fi + mkdir -p $TMP_PKG_DIR + + PKG_URL=$TIZEN_URL/$PROFILE/latest + + BUILD_XML_URL=$PKG_URL/$BUILD_XML + TMP_BUILD=$TMP_PKG_DIR/$BUILD_XML + TMP_REPOMD=$TMP_PKG_DIR/$REPOMD_XML + TMP_PRIMARY=$TMP_PKG_DIR/$PRIMARY_XML + TMP_PRIMARYGZ=${TMP_PRIMARY}.gz + + Fetch $BUILD_XML_URL $TMP_BUILD + + Debug "fetch $BUILD_XML_URL to $TMP_BUILD" + + TARGET_XPATH="//build/buildtargets/buildtarget[@name=\"$TARGET\"]/repo[@type=\"binary\"]/text()" + Xpath_get $TARGET_XPATH $TMP_BUILD + TARGET_PATH=$XPATH_RESULT + TARGET_URL=$PKG_URL/$TARGET_PATH + + REPOMD_URL=$TARGET_URL/repodata/repomd.xml + PRIMARY_XPATH='string(//*[local-name()="data"][@type="primary"]/*[local-name()="location"]/@href)' + + Fetch $REPOMD_URL $TMP_REPOMD + + Debug "fetch $REPOMD_URL to $TMP_REPOMD" + + Xpath_get $PRIMARY_XPATH $TMP_REPOMD + PRIMARY_XML_PATH=$XPATH_RESULT + PRIMARY_URL=$TARGET_URL/$PRIMARY_XML_PATH + + Fetch $PRIMARY_URL $TMP_PRIMARYGZ + + Debug "fetch $PRIMARY_URL to $TMP_PRIMARYGZ" + + gunzip $TMP_PRIMARYGZ + + Debug "unzip $TMP_PRIMARYGZ to $TMP_PRIMARY" +} + +fetch_tizen_pkgs() +{ + ARCH=$1 + PACKAGE_XPATH_TPL='string(//*[local-name()="metadata"]/*[local-name()="package"][*[local-name()="name"][text()="_PKG_"]][*[local-name()="arch"][text()="_ARCH_"]]/*[local-name()="location"]/@href)' + + PACKAGE_CHECKSUM_XPATH_TPL='string(//*[local-name()="metadata"]/*[local-name()="package"][*[local-name()="name"][text()="_PKG_"]][*[local-name()="arch"][text()="_ARCH_"]]/*[local-name()="checksum"]/text())' + + for pkg in ${@:2} + do + Inform "Fetching... $pkg" + XPATH=${PACKAGE_XPATH_TPL/_PKG_/$pkg} + XPATH=${XPATH/_ARCH_/$ARCH} + Xpath_get $XPATH $TMP_PRIMARY + PKG_PATH=$XPATH_RESULT + + XPATH=${PACKAGE_CHECKSUM_XPATH_TPL/_PKG_/$pkg} + XPATH=${XPATH/_ARCH_/$ARCH} + Xpath_get $XPATH $TMP_PRIMARY + CHECKSUM=$XPATH_RESULT + + PKG_URL=$TARGET_URL/$PKG_PATH + PKG_FILE=$(basename $PKG_PATH) + PKG_PATH=$TMPDIR/$PKG_FILE + + Debug "Download $PKG_URL to $PKG_PATH" + Fetch $PKG_URL $PKG_PATH true + + echo "$CHECKSUM $PKG_PATH" | sha256sum -c - > /dev/null + if [ $? -ne 0 ]; then + Error "Fail to fetch $PKG_URL to $PKG_PATH" + Debug "Checksum = $CHECKSUM" + exit 1 + fi + done +} + +Inform "Initialize arm base" +fetch_tizen_pkgs_init standard base +Inform "fetch common packages" +fetch_tizen_pkgs armv7l gcc gcc-devel-static glibc glibc-devel libicu libicu-devel libatomic linux-glibc-devel keyutils keyutils-devel libkeyutils +Inform "fetch coreclr packages" +fetch_tizen_pkgs armv7l lldb lldb-devel libgcc libstdc++ libstdc++-devel libunwind libunwind-devel lttng-ust-devel lttng-ust userspace-rcu-devel userspace-rcu +Inform "fetch corefx packages" +fetch_tizen_pkgs armv7l libcom_err libcom_err-devel zlib zlib-devel libopenssl11 libopenssl1.1-devel krb5 krb5-devel + +Inform "Initialize standard unified" +fetch_tizen_pkgs_init standard unified +Inform "fetch corefx packages" +fetch_tizen_pkgs armv7l gssdp gssdp-devel tizen-release + diff --git a/eng/common/cross/armel/tizen/tizen-dotnet.ks b/eng/common/cross/armel/tizen/tizen-dotnet.ks new file mode 100644 index 000000000..506d455bd --- /dev/null +++ b/eng/common/cross/armel/tizen/tizen-dotnet.ks @@ -0,0 +1,50 @@ +lang en_US.UTF-8 +keyboard us +timezone --utc Asia/Seoul + +part / --fstype="ext4" --size=3500 --ondisk=mmcblk0 --label rootfs --fsoptions=defaults,noatime + +rootpw tizen +desktop --autologinuser=root +user --name root --groups audio,video --password 'tizen' + +repo --name=standard --baseurl=http://download.tizen.org/releases/milestone/tizen/unified/latest/repos/standard/packages/ --ssl_verify=no +repo --name=base --baseurl=http://download.tizen.org/releases/milestone/tizen/base/latest/repos/standard/packages/ --ssl_verify=no + +%packages +tar +gzip + +sed +grep +gawk +perl + +binutils +findutils +util-linux +lttng-ust +userspace-rcu +procps-ng +tzdata +ca-certificates + + +### Core FX +libicu +libunwind +iputils +zlib +krb5 +libcurl +libopenssl + +%end + +%post + +### Update /tmp privilege +chmod 777 /tmp +#################################### + +%end diff --git a/eng/common/cross/armel/tizen/tizen.patch b/eng/common/cross/armel/tizen/tizen.patch new file mode 100644 index 000000000..ca7c7c1ff --- /dev/null +++ b/eng/common/cross/armel/tizen/tizen.patch @@ -0,0 +1,9 @@ +diff -u -r a/usr/lib/libc.so b/usr/lib/libc.so +--- a/usr/lib/libc.so 2016-12-30 23:00:08.284951863 +0900 ++++ b/usr/lib/libc.so 2016-12-30 23:00:32.140951815 +0900 +@@ -2,4 +2,4 @@ + Use the shared library, but some functions are only in + the static library, so try that secondarily. */ + OUTPUT_FORMAT(elf32-littlearm) +-GROUP ( /lib/libc.so.6 /usr/lib/libc_nonshared.a AS_NEEDED ( /lib/ld-linux.so.3 ) ) ++GROUP ( libc.so.6 libc_nonshared.a AS_NEEDED ( ld-linux.so.3 ) ) diff --git a/eng/common/cross/build-android-rootfs.sh b/eng/common/cross/build-android-rootfs.sh new file mode 100644 index 000000000..42516bbee --- /dev/null +++ b/eng/common/cross/build-android-rootfs.sh @@ -0,0 +1,131 @@ +#!/usr/bin/env bash +set -e +__NDK_Version=r21 + +usage() +{ + echo "Creates a toolchain and sysroot used for cross-compiling for Android." + echo. + echo "Usage: $0 [BuildArch] [ApiLevel]" + echo. + echo "BuildArch is the target architecture of Android. Currently only arm64 is supported." + echo "ApiLevel is the target Android API level. API levels usually match to Android releases. See https://source.android.com/source/build-numbers.html" + echo. + echo "By default, the toolchain and sysroot will be generated in cross/android-rootfs/toolchain/[BuildArch]. You can change this behavior" + echo "by setting the TOOLCHAIN_DIR environment variable" + echo. + echo "By default, the NDK will be downloaded into the cross/android-rootfs/android-ndk-$__NDK_Version directory. If you already have an NDK installation," + echo "you can set the NDK_DIR environment variable to have this script use that installation of the NDK." + echo "By default, this script will generate a file, android_platform, in the root of the ROOTFS_DIR directory that contains the RID for the supported and tested Android build: android.28-arm64. This file is to replace '/etc/os-release', which is not available for Android." + exit 1 +} + +__ApiLevel=28 # The minimum platform for arm64 is API level 21 but the minimum version that support glob(3) is 28. See $ANDROID_NDK/toolchains/llvm/prebuilt/linux-x86_64/sysroot/usr/include/glob.h +__BuildArch=arm64 +__AndroidArch=aarch64 +__AndroidToolchain=aarch64-linux-android + +for i in "$@" + do + lowerI="$(echo $i | tr "[:upper:]" "[:lower:]")" + case $lowerI in + -?|-h|--help) + usage + exit 1 + ;; + arm64) + __BuildArch=arm64 + __AndroidArch=aarch64 + __AndroidToolchain=aarch64-linux-android + ;; + arm) + __BuildArch=arm + __AndroidArch=arm + __AndroidToolchain=arm-linux-androideabi + ;; + *[0-9]) + __ApiLevel=$i + ;; + *) + __UnprocessedBuildArgs="$__UnprocessedBuildArgs $i" + ;; + esac +done + +# Obtain the location of the bash script to figure out where the root of the repo is. +__ScriptBaseDir="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" + +__CrossDir="$__ScriptBaseDir/../../../.tools/android-rootfs" + +if [[ ! -f "$__CrossDir" ]]; then + mkdir -p "$__CrossDir" +fi + +# Resolve absolute path to avoid `../` in build logs +__CrossDir="$( cd "$__CrossDir" && pwd )" + +__NDK_Dir="$__CrossDir/android-ndk-$__NDK_Version" +__lldb_Dir="$__CrossDir/lldb" +__ToolchainDir="$__CrossDir/android-ndk-$__NDK_Version" + +if [[ -n "$TOOLCHAIN_DIR" ]]; then + __ToolchainDir=$TOOLCHAIN_DIR +fi + +if [[ -n "$NDK_DIR" ]]; then + __NDK_Dir=$NDK_DIR +fi + +echo "Target API level: $__ApiLevel" +echo "Target architecture: $__BuildArch" +echo "NDK location: $__NDK_Dir" +echo "Target Toolchain location: $__ToolchainDir" + +# Download the NDK if required +if [ ! -d $__NDK_Dir ]; then + echo Downloading the NDK into $__NDK_Dir + mkdir -p $__NDK_Dir + wget -q --progress=bar:force:noscroll --show-progress https://dl.google.com/android/repository/android-ndk-$__NDK_Version-linux-x86_64.zip -O $__CrossDir/android-ndk-$__NDK_Version-linux-x86_64.zip + unzip -q $__CrossDir/android-ndk-$__NDK_Version-linux-x86_64.zip -d $__CrossDir +fi + +if [ ! -d $__lldb_Dir ]; then + mkdir -p $__lldb_Dir + echo Downloading LLDB into $__lldb_Dir + wget -q --progress=bar:force:noscroll --show-progress https://dl.google.com/android/repository/lldb-2.3.3614996-linux-x86_64.zip -O $__CrossDir/lldb-2.3.3614996-linux-x86_64.zip + unzip -q $__CrossDir/lldb-2.3.3614996-linux-x86_64.zip -d $__lldb_Dir +fi + +echo "Download dependencies..." +__TmpDir=$__CrossDir/tmp/$__BuildArch/ +mkdir -p "$__TmpDir" + +# combined dependencies for coreclr, installer and libraries +__AndroidPackages="libicu" +__AndroidPackages+=" libandroid-glob" +__AndroidPackages+=" liblzma" +__AndroidPackages+=" krb5" +__AndroidPackages+=" openssl" + +for path in $(wget -qO- http://termux.net/dists/stable/main/binary-$__AndroidArch/Packages |\ + grep -A15 "Package: \(${__AndroidPackages// /\\|}\)" | grep -v "static\|tool" | grep Filename); do + + if [[ "$path" != "Filename:" ]]; then + echo "Working on: $path" + wget -qO- http://termux.net/$path | dpkg -x - "$__TmpDir" + fi +done + +cp -R "$__TmpDir/data/data/com.termux/files/usr/"* "$__ToolchainDir/sysroot/usr/" + +# Generate platform file for build.sh script to assign to __DistroRid +echo "Generating platform file..." +echo "RID=android.${__ApiLevel}-${__BuildArch}" > $__ToolchainDir/sysroot/android_platform + +echo "Now to build coreclr, libraries and installers; run:" +echo ROOTFS_DIR=\$\(realpath $__ToolchainDir/sysroot\) ./build.sh --cross --arch $__BuildArch \ + --subsetCategory coreclr +echo ROOTFS_DIR=\$\(realpath $__ToolchainDir/sysroot\) ./build.sh --cross --arch $__BuildArch \ + --subsetCategory libraries +echo ROOTFS_DIR=\$\(realpath $__ToolchainDir/sysroot\) ./build.sh --cross --arch $__BuildArch \ + --subsetCategory installer diff --git a/eng/common/cross/build-rootfs.sh b/eng/common/cross/build-rootfs.sh new file mode 100644 index 000000000..735a4c828 --- /dev/null +++ b/eng/common/cross/build-rootfs.sh @@ -0,0 +1,385 @@ +#!/usr/bin/env bash + +set -e + +usage() +{ + echo "Usage: $0 [BuildArch] [CodeName] [lldbx.y] [--skipunmount] --rootfsdir ]" + echo "BuildArch can be: arm(default), armel, arm64, x86" + echo "CodeName - optional, Code name for Linux, can be: trusty, xenial(default), zesty, bionic, alpine, alpine3.9 or alpine3.13. If BuildArch is armel, LinuxCodeName is jessie(default) or tizen." + echo " for FreeBSD can be: freebsd11 or freebsd12." + echo " for illumos can be: illumos." + echo "lldbx.y - optional, LLDB version, can be: lldb3.9(default), lldb4.0, lldb5.0, lldb6.0 no-lldb. Ignored for alpine and FReeBSD" + echo "--skipunmount - optional, will skip the unmount of rootfs folder." + echo "--use-mirror - optional, use mirror URL to fetch resources, when available." + exit 1 +} + +__CodeName=xenial +__CrossDir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) +__InitialDir=$PWD +__BuildArch=arm +__AlpineArch=armv7 +__QEMUArch=arm +__UbuntuArch=armhf +__UbuntuRepo="http://ports.ubuntu.com/" +__LLDB_Package="liblldb-3.9-dev" +__SkipUnmount=0 + +# base development support +__UbuntuPackages="build-essential" + +__AlpinePackages="alpine-base" +__AlpinePackages+=" build-base" +__AlpinePackages+=" linux-headers" +__AlpinePackagesEdgeCommunity=" lldb-dev" +__AlpinePackagesEdgeMain+=" python3" +__AlpinePackagesEdgeMain+=" libedit" + +# symlinks fixer +__UbuntuPackages+=" symlinks" + +# CoreCLR and CoreFX dependencies +__UbuntuPackages+=" libicu-dev" +__UbuntuPackages+=" liblttng-ust-dev" +__UbuntuPackages+=" libunwind8-dev" + +__AlpinePackages+=" gettext-dev" +__AlpinePackages+=" icu-dev" +__AlpinePackages+=" libunwind-dev" +__AlpinePackages+=" lttng-ust-dev" + +# CoreFX dependencies +__UbuntuPackages+=" libcurl4-openssl-dev" +__UbuntuPackages+=" libkrb5-dev" +__UbuntuPackages+=" libssl-dev" +__UbuntuPackages+=" zlib1g-dev" + +__AlpinePackages+=" curl-dev" +__AlpinePackages+=" krb5-dev" +__AlpinePackages+=" openssl-dev" +__AlpinePackages+=" zlib-dev" + +__FreeBSDBase="12.1-RELEASE" +__FreeBSDPkg="1.12.0" +__FreeBSDPackages="libunwind" +__FreeBSDPackages+=" icu" +__FreeBSDPackages+=" libinotify" +__FreeBSDPackages+=" lttng-ust" +__FreeBSDPackages+=" krb5" + +__IllumosPackages="icu-64.2nb2" +__IllumosPackages+=" mit-krb5-1.16.2nb4" +__IllumosPackages+=" openssl-1.1.1e" +__IllumosPackages+=" zlib-1.2.11" + +# ML.NET dependencies +__UbuntuPackages+=" libomp5" +__UbuntuPackages+=" libomp-dev" + +__UseMirror=0 + +__UnprocessedBuildArgs= +while :; do + if [ $# -le 0 ]; then + break + fi + + lowerI="$(echo $1 | tr "[:upper:]" "[:lower:]")" + case $lowerI in + -?|-h|--help) + usage + exit 1 + ;; + arm) + __BuildArch=arm + __UbuntuArch=armhf + __AlpineArch=armv7 + __QEMUArch=arm + ;; + arm64) + __BuildArch=arm64 + __UbuntuArch=arm64 + __AlpineArch=aarch64 + __QEMUArch=aarch64 + ;; + armel) + __BuildArch=armel + __UbuntuArch=armel + __UbuntuRepo="http://ftp.debian.org/debian/" + __CodeName=jessie + ;; + s390x) + __BuildArch=s390x + __UbuntuArch=s390x + __UbuntuRepo="http://ports.ubuntu.com/ubuntu-ports/" + __UbuntuPackages=$(echo ${__UbuntuPackages} | sed 's/ libunwind8-dev//') + __UbuntuPackages=$(echo ${__UbuntuPackages} | sed 's/ libomp-dev//') + __UbuntuPackages=$(echo ${__UbuntuPackages} | sed 's/ libomp5//') + unset __LLDB_Package + ;; + x86) + __BuildArch=x86 + __UbuntuArch=i386 + __UbuntuRepo="http://archive.ubuntu.com/ubuntu/" + ;; + lldb3.6) + __LLDB_Package="lldb-3.6-dev" + ;; + lldb3.8) + __LLDB_Package="lldb-3.8-dev" + ;; + lldb3.9) + __LLDB_Package="liblldb-3.9-dev" + ;; + lldb4.0) + __LLDB_Package="liblldb-4.0-dev" + ;; + lldb5.0) + __LLDB_Package="liblldb-5.0-dev" + ;; + lldb6.0) + __LLDB_Package="liblldb-6.0-dev" + ;; + no-lldb) + unset __LLDB_Package + ;; + trusty) # Ubuntu 14.04 + if [ "$__CodeName" != "jessie" ]; then + __CodeName=trusty + fi + ;; + xenial) # Ubuntu 16.04 + if [ "$__CodeName" != "jessie" ]; then + __CodeName=xenial + fi + ;; + zesty) # Ubuntu 17.04 + if [ "$__CodeName" != "jessie" ]; then + __CodeName=zesty + fi + ;; + bionic) # Ubuntu 18.04 + if [ "$__CodeName" != "jessie" ]; then + __CodeName=bionic + fi + ;; + jessie) # Debian 8 + __CodeName=jessie + __UbuntuRepo="http://ftp.debian.org/debian/" + ;; + stretch) # Debian 9 + __CodeName=stretch + __UbuntuRepo="http://ftp.debian.org/debian/" + __LLDB_Package="liblldb-6.0-dev" + ;; + buster) # Debian 10 + __CodeName=buster + __UbuntuRepo="http://ftp.debian.org/debian/" + __LLDB_Package="liblldb-6.0-dev" + ;; + tizen) + if [ "$__BuildArch" != "armel" ] && [ "$__BuildArch" != "arm64" ]; then + echo "Tizen is available only for armel and arm64." + usage; + exit 1; + fi + __CodeName= + __UbuntuRepo= + __Tizen=tizen + ;; + alpine|alpine3.9) + __CodeName=alpine + __UbuntuRepo= + __AlpineVersion=3.9 + __AlpinePackagesEdgeMain+=" llvm11-libs" + __AlpinePackagesEdgeMain+=" clang-libs" + ;; + alpine3.13) + __CodeName=alpine + __UbuntuRepo= + __AlpineVersion=3.13 + # Alpine 3.13 has all the packages we need in the 3.13 repository + __AlpinePackages+=$__AlpinePackagesEdgeCommunity + __AlpinePackagesEdgeCommunity= + __AlpinePackages+=$__AlpinePackagesEdgeMain + __AlpinePackagesEdgeMain= + __AlpinePackages+=" llvm10-libs" + ;; + freebsd11) + __FreeBSDBase="11.3-RELEASE" + ;& + freebsd12) + __CodeName=freebsd + __BuildArch=x64 + __SkipUnmount=1 + ;; + illumos) + __CodeName=illumos + __BuildArch=x64 + __SkipUnmount=1 + ;; + --skipunmount) + __SkipUnmount=1 + ;; + --rootfsdir|-rootfsdir) + shift + __RootfsDir=$1 + ;; + --use-mirror) + __UseMirror=1 + ;; + *) + __UnprocessedBuildArgs="$__UnprocessedBuildArgs $1" + ;; + esac + + shift +done + +if [ "$__BuildArch" == "armel" ]; then + __LLDB_Package="lldb-3.5-dev" +fi +__UbuntuPackages+=" ${__LLDB_Package:-}" + +if [ -z "$__RootfsDir" ] && [ ! -z "$ROOTFS_DIR" ]; then + __RootfsDir=$ROOTFS_DIR +fi + +if [ -z "$__RootfsDir" ]; then + __RootfsDir="$__CrossDir/../../../.tools/rootfs/$__BuildArch" +fi + +if [ -d "$__RootfsDir" ]; then + if [ $__SkipUnmount == 0 ]; then + umount $__RootfsDir/* || true + fi + rm -rf $__RootfsDir +fi + +mkdir -p $__RootfsDir +__RootfsDir="$( cd "$__RootfsDir" && pwd )" + +if [[ "$__CodeName" == "alpine" ]]; then + __ApkToolsVersion=2.9.1 + __ApkToolsDir=$(mktemp -d) + wget https://github.com/alpinelinux/apk-tools/releases/download/v$__ApkToolsVersion/apk-tools-$__ApkToolsVersion-x86_64-linux.tar.gz -P $__ApkToolsDir + tar -xf $__ApkToolsDir/apk-tools-$__ApkToolsVersion-x86_64-linux.tar.gz -C $__ApkToolsDir + mkdir -p $__RootfsDir/usr/bin + cp -v /usr/bin/qemu-$__QEMUArch-static $__RootfsDir/usr/bin + + $__ApkToolsDir/apk-tools-$__ApkToolsVersion/apk \ + -X http://dl-cdn.alpinelinux.org/alpine/v$__AlpineVersion/main \ + -X http://dl-cdn.alpinelinux.org/alpine/v$__AlpineVersion/community \ + -U --allow-untrusted --root $__RootfsDir --arch $__AlpineArch --initdb \ + add $__AlpinePackages + + if [[ -n "$__AlpinePackagesEdgeMain" ]]; then + $__ApkToolsDir/apk-tools-$__ApkToolsVersion/apk \ + -X http://dl-cdn.alpinelinux.org/alpine/edge/main \ + -U --allow-untrusted --root $__RootfsDir --arch $__AlpineArch --initdb \ + add $__AlpinePackagesEdgeMain + fi + + if [[ -n "$__AlpinePackagesEdgeCommunity" ]]; then + $__ApkToolsDir/apk-tools-$__ApkToolsVersion/apk \ + -X http://dl-cdn.alpinelinux.org/alpine/edge/community \ + -U --allow-untrusted --root $__RootfsDir --arch $__AlpineArch --initdb \ + add $__AlpinePackagesEdgeCommunity + fi + + rm -r $__ApkToolsDir +elif [[ "$__CodeName" == "freebsd" ]]; then + mkdir -p $__RootfsDir/usr/local/etc + wget -O - https://download.freebsd.org/ftp/releases/amd64/${__FreeBSDBase}/base.txz | tar -C $__RootfsDir -Jxf - ./lib ./usr/lib ./usr/libdata ./usr/include ./usr/share/keys ./etc ./bin/freebsd-version + # For now, ask for 11 ABI even on 12. This can be revisited later. + echo "ABI = \"FreeBSD:11:amd64\"; FINGERPRINTS = \"${__RootfsDir}/usr/share/keys\"; REPOS_DIR = [\"${__RootfsDir}/etc/pkg\"]; REPO_AUTOUPDATE = NO; RUN_SCRIPTS = NO;" > ${__RootfsDir}/usr/local/etc/pkg.conf + echo "FreeBSD: { url: "pkg+http://pkg.FreeBSD.org/\${ABI}/quarterly", mirror_type: \"srv\", signature_type: \"fingerprints\", fingerprints: \"${__RootfsDir}/usr/share/keys/pkg\", enabled: yes }" > ${__RootfsDir}/etc/pkg/FreeBSD.conf + mkdir -p $__RootfsDir/tmp + # get and build package manager + wget -O - https://github.com/freebsd/pkg/archive/${__FreeBSDPkg}.tar.gz | tar -C $__RootfsDir/tmp -zxf - + cd $__RootfsDir/tmp/pkg-${__FreeBSDPkg} + # needed for install to succeed + mkdir -p $__RootfsDir/host/etc + ./autogen.sh && ./configure --prefix=$__RootfsDir/host && make && make install + rm -rf $__RootfsDir/tmp/pkg-${__FreeBSDPkg} + # install packages we need. + INSTALL_AS_USER=$(whoami) $__RootfsDir/host/sbin/pkg -r $__RootfsDir -C $__RootfsDir/usr/local/etc/pkg.conf update + INSTALL_AS_USER=$(whoami) $__RootfsDir/host/sbin/pkg -r $__RootfsDir -C $__RootfsDir/usr/local/etc/pkg.conf install --yes $__FreeBSDPackages +elif [[ "$__CodeName" == "illumos" ]]; then + mkdir "$__RootfsDir/tmp" + pushd "$__RootfsDir/tmp" + JOBS="$(getconf _NPROCESSORS_ONLN)" + echo "Downloading sysroot." + wget -O - https://github.com/illumos/sysroot/releases/download/20181213-de6af22ae73b-v1/illumos-sysroot-i386-20181213-de6af22ae73b-v1.tar.gz | tar -C "$__RootfsDir" -xzf - + echo "Building binutils. Please wait.." + wget -O - https://ftp.gnu.org/gnu/binutils/binutils-2.33.1.tar.bz2 | tar -xjf - + mkdir build-binutils && cd build-binutils + ../binutils-2.33.1/configure --prefix="$__RootfsDir" --target="x86_64-sun-solaris2.10" --program-prefix="x86_64-illumos-" --with-sysroot="$__RootfsDir" + make -j "$JOBS" && make install && cd .. + echo "Building gcc. Please wait.." + wget -O - https://ftp.gnu.org/gnu/gcc/gcc-8.4.0/gcc-8.4.0.tar.xz | tar -xJf - + CFLAGS="-fPIC" + CXXFLAGS="-fPIC" + CXXFLAGS_FOR_TARGET="-fPIC" + CFLAGS_FOR_TARGET="-fPIC" + export CFLAGS CXXFLAGS CXXFLAGS_FOR_TARGET CFLAGS_FOR_TARGET + mkdir build-gcc && cd build-gcc + ../gcc-8.4.0/configure --prefix="$__RootfsDir" --target="x86_64-sun-solaris2.10" --program-prefix="x86_64-illumos-" --with-sysroot="$__RootfsDir" --with-gnu-as \ + --with-gnu-ld --disable-nls --disable-libgomp --disable-libquadmath --disable-libssp --disable-libvtv --disable-libcilkrts --disable-libada --disable-libsanitizer \ + --disable-libquadmath-support --disable-shared --enable-tls + make -j "$JOBS" && make install && cd .. + BaseUrl=https://pkgsrc.joyent.com + if [[ "$__UseMirror" == 1 ]]; then + BaseUrl=http://pkgsrc.smartos.skylime.net + fi + BaseUrl="$BaseUrl"/packages/SmartOS/2020Q1/x86_64/All + echo "Downloading dependencies." + read -ra array <<<"$__IllumosPackages" + for package in "${array[@]}"; do + echo "Installing $package..." + wget "$BaseUrl"/"$package".tgz + ar -x "$package".tgz + tar --skip-old-files -xzf "$package".tmp.tgz -C "$__RootfsDir" 2>/dev/null + done + echo "Cleaning up temporary files." + popd + rm -rf "$__RootfsDir"/{tmp,+*} + mkdir -p "$__RootfsDir"/usr/include/net + mkdir -p "$__RootfsDir"/usr/include/netpacket + wget -P "$__RootfsDir"/usr/include/net https://raw.githubusercontent.com/illumos/illumos-gate/master/usr/src/uts/common/io/bpf/net/bpf.h + wget -P "$__RootfsDir"/usr/include/net https://raw.githubusercontent.com/illumos/illumos-gate/master/usr/src/uts/common/io/bpf/net/dlt.h + wget -P "$__RootfsDir"/usr/include/netpacket https://raw.githubusercontent.com/illumos/illumos-gate/master/usr/src/uts/common/inet/sockmods/netpacket/packet.h + wget -P "$__RootfsDir"/usr/include/sys https://raw.githubusercontent.com/illumos/illumos-gate/master/usr/src/uts/common/sys/sdt.h +elif [[ -n $__CodeName ]]; then + qemu-debootstrap --arch $__UbuntuArch $__CodeName $__RootfsDir $__UbuntuRepo + cp $__CrossDir/$__BuildArch/sources.list.$__CodeName $__RootfsDir/etc/apt/sources.list + chroot $__RootfsDir apt-get update + chroot $__RootfsDir apt-get -f -y install + chroot $__RootfsDir apt-get -y install $__UbuntuPackages + chroot $__RootfsDir symlinks -cr /usr + chroot $__RootfsDir apt-get clean + + if [ $__SkipUnmount == 0 ]; then + umount $__RootfsDir/* || true + fi + + if [[ "$__BuildArch" == "arm" && "$__CodeName" == "trusty" ]]; then + pushd $__RootfsDir + patch -p1 < $__CrossDir/$__BuildArch/trusty.patch + patch -p1 < $__CrossDir/$__BuildArch/trusty-lttng-2.4.patch + popd + fi + + if [[ "$__BuildArch" == "armel" && "$__CodeName" == "jessie" ]]; then + pushd $__RootfsDir + patch -p1 < $__CrossDir/$__BuildArch/armel.jessie.patch + popd + fi +elif [[ "$__Tizen" == "tizen" ]]; then + ROOTFS_DIR=$__RootfsDir $__CrossDir/$__BuildArch/tizen-build-rootfs.sh +else + echo "Unsupported target platform." + usage; + exit 1 +fi diff --git a/eng/common/cross/s390x/sources.list.bionic b/eng/common/cross/s390x/sources.list.bionic new file mode 100644 index 000000000..210955740 --- /dev/null +++ b/eng/common/cross/s390x/sources.list.bionic @@ -0,0 +1,11 @@ +deb http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-updates main restricted universe + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-backports main restricted + +deb http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse +deb-src http://ports.ubuntu.com/ubuntu-ports/ bionic-security main restricted universe multiverse diff --git a/eng/common/cross/toolchain.cmake b/eng/common/cross/toolchain.cmake new file mode 100644 index 000000000..fc11001aa --- /dev/null +++ b/eng/common/cross/toolchain.cmake @@ -0,0 +1,242 @@ +set(CROSS_ROOTFS $ENV{ROOTFS_DIR}) + +set(TARGET_ARCH_NAME $ENV{TARGET_BUILD_ARCH}) +if(EXISTS ${CROSS_ROOTFS}/bin/freebsd-version) + set(CMAKE_SYSTEM_NAME FreeBSD) +elseif(EXISTS ${CROSS_ROOTFS}/usr/platform/i86pc) + set(CMAKE_SYSTEM_NAME SunOS) + set(ILLUMOS 1) +else() + set(CMAKE_SYSTEM_NAME Linux) +endif() +set(CMAKE_SYSTEM_VERSION 1) + +if(TARGET_ARCH_NAME STREQUAL "armel") + set(CMAKE_SYSTEM_PROCESSOR armv7l) + set(TOOLCHAIN "arm-linux-gnueabi") + if("$ENV{__DistroRid}" MATCHES "tizen.*") + set(TIZEN_TOOLCHAIN "armv7l-tizen-linux-gnueabi/9.2.0") + endif() +elseif(TARGET_ARCH_NAME STREQUAL "arm") + set(CMAKE_SYSTEM_PROCESSOR armv7l) + if(EXISTS ${CROSS_ROOTFS}/usr/lib/gcc/armv7-alpine-linux-musleabihf) + set(TOOLCHAIN "armv7-alpine-linux-musleabihf") + elseif(EXISTS ${CROSS_ROOTFS}/usr/lib/gcc/armv6-alpine-linux-musleabihf) + set(TOOLCHAIN "armv6-alpine-linux-musleabihf") + else() + set(TOOLCHAIN "arm-linux-gnueabihf") + endif() +elseif(TARGET_ARCH_NAME STREQUAL "arm64") + set(CMAKE_SYSTEM_PROCESSOR aarch64) + if(EXISTS ${CROSS_ROOTFS}/usr/lib/gcc/aarch64-alpine-linux-musl) + set(TOOLCHAIN "aarch64-alpine-linux-musl") + else() + set(TOOLCHAIN "aarch64-linux-gnu") + endif() + if("$ENV{__DistroRid}" MATCHES "tizen.*") + set(TIZEN_TOOLCHAIN "aarch64-tizen-linux-gnu/9.2.0") + endif() +elseif(TARGET_ARCH_NAME STREQUAL "s390x") + set(CMAKE_SYSTEM_PROCESSOR s390x) + set(TOOLCHAIN "s390x-linux-gnu") +elseif(TARGET_ARCH_NAME STREQUAL "x86") + set(CMAKE_SYSTEM_PROCESSOR i686) + set(TOOLCHAIN "i686-linux-gnu") +elseif (CMAKE_SYSTEM_NAME STREQUAL "FreeBSD") + set(CMAKE_SYSTEM_PROCESSOR "x86_64") + set(triple "x86_64-unknown-freebsd11") +elseif (ILLUMOS) + set(CMAKE_SYSTEM_PROCESSOR "x86_64") + set(TOOLCHAIN "x86_64-illumos") +else() + message(FATAL_ERROR "Arch is ${TARGET_ARCH_NAME}. Only armel, arm, arm64, s390x and x86 are supported!") +endif() + +if(DEFINED ENV{TOOLCHAIN}) + set(TOOLCHAIN $ENV{TOOLCHAIN}) +endif() + +# Specify include paths +if(DEFINED TIZEN_TOOLCHAIN) + if(TARGET_ARCH_NAME STREQUAL "armel") + include_directories(SYSTEM ${CROSS_ROOTFS}/usr/lib/gcc/${TIZEN_TOOLCHAIN}/include/c++/) + include_directories(SYSTEM ${CROSS_ROOTFS}/usr/lib/gcc/${TIZEN_TOOLCHAIN}/include/c++/armv7l-tizen-linux-gnueabi) + endif() + if(TARGET_ARCH_NAME STREQUAL "arm64") + include_directories(SYSTEM ${CROSS_ROOTFS}/usr/lib64/gcc/${TIZEN_TOOLCHAIN}/include/c++/) + include_directories(SYSTEM ${CROSS_ROOTFS}/usr/lib64/gcc/${TIZEN_TOOLCHAIN}/include/c++/aarch64-tizen-linux-gnu) + endif() +endif() + +if("$ENV{__DistroRid}" MATCHES "android.*") + if(TARGET_ARCH_NAME STREQUAL "arm") + set(ANDROID_ABI armeabi-v7a) + elseif(TARGET_ARCH_NAME STREQUAL "arm64") + set(ANDROID_ABI arm64-v8a) + endif() + + # extract platform number required by the NDK's toolchain + string(REGEX REPLACE ".*\\.([0-9]+)-.*" "\\1" ANDROID_PLATFORM "$ENV{__DistroRid}") + + set(ANDROID_TOOLCHAIN clang) + set(FEATURE_EVENT_TRACE 0) # disable event trace as there is no lttng-ust package in termux repository + set(CMAKE_SYSTEM_LIBRARY_PATH "${CROSS_ROOTFS}/usr/lib") + set(CMAKE_SYSTEM_INCLUDE_PATH "${CROSS_ROOTFS}/usr/include") + + # include official NDK toolchain script + include(${CROSS_ROOTFS}/../build/cmake/android.toolchain.cmake) +elseif(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD") + # we cross-compile by instructing clang + set(CMAKE_C_COMPILER_TARGET ${triple}) + set(CMAKE_CXX_COMPILER_TARGET ${triple}) + set(CMAKE_ASM_COMPILER_TARGET ${triple}) + set(CMAKE_SYSROOT "${CROSS_ROOTFS}") +elseif(ILLUMOS) + set(CMAKE_SYSROOT "${CROSS_ROOTFS}") + + include_directories(SYSTEM ${CROSS_ROOTFS}/include) + + set(TOOLSET_PREFIX ${TOOLCHAIN}-) + function(locate_toolchain_exec exec var) + string(TOUPPER ${exec} EXEC_UPPERCASE) + if(NOT "$ENV{CLR_${EXEC_UPPERCASE}}" STREQUAL "") + set(${var} "$ENV{CLR_${EXEC_UPPERCASE}}" PARENT_SCOPE) + return() + endif() + + find_program(EXEC_LOCATION_${exec} + NAMES + "${TOOLSET_PREFIX}${exec}${CLR_CMAKE_COMPILER_FILE_NAME_VERSION}" + "${TOOLSET_PREFIX}${exec}") + + if (EXEC_LOCATION_${exec} STREQUAL "EXEC_LOCATION_${exec}-NOTFOUND") + message(FATAL_ERROR "Unable to find toolchain executable. Name: ${exec}, Prefix: ${TOOLSET_PREFIX}.") + endif() + set(${var} ${EXEC_LOCATION_${exec}} PARENT_SCOPE) + endfunction() + + set(CMAKE_SYSTEM_PREFIX_PATH "${CROSS_ROOTFS}") + + locate_toolchain_exec(gcc CMAKE_C_COMPILER) + locate_toolchain_exec(g++ CMAKE_CXX_COMPILER) + + set(CMAKE_C_STANDARD_LIBRARIES "${CMAKE_C_STANDARD_LIBRARIES} -lssp") + set(CMAKE_CXX_STANDARD_LIBRARIES "${CMAKE_CXX_STANDARD_LIBRARIES} -lssp") +else() + set(CMAKE_SYSROOT "${CROSS_ROOTFS}") + + set(CMAKE_C_COMPILER_EXTERNAL_TOOLCHAIN "${CROSS_ROOTFS}/usr") + set(CMAKE_CXX_COMPILER_EXTERNAL_TOOLCHAIN "${CROSS_ROOTFS}/usr") + set(CMAKE_ASM_COMPILER_EXTERNAL_TOOLCHAIN "${CROSS_ROOTFS}/usr") +endif() + +# Specify link flags + +function(add_toolchain_linker_flag Flag) + set(Config "${ARGV1}") + set(CONFIG_SUFFIX "") + if (NOT Config STREQUAL "") + set(CONFIG_SUFFIX "_${Config}") + endif() + set("CMAKE_EXE_LINKER_FLAGS${CONFIG_SUFFIX}" "${CMAKE_EXE_LINKER_FLAGS${CONFIG_SUFFIX}} ${Flag}" PARENT_SCOPE) + set("CMAKE_SHARED_LINKER_FLAGS${CONFIG_SUFFIX}" "${CMAKE_SHARED_LINKER_FLAGS${CONFIG_SUFFIX}} ${Flag}" PARENT_SCOPE) +endfunction() + +if(CMAKE_SYSTEM_NAME STREQUAL "Linux") + add_toolchain_linker_flag("-Wl,--rpath-link=${CROSS_ROOTFS}/lib/${TOOLCHAIN}") + add_toolchain_linker_flag("-Wl,--rpath-link=${CROSS_ROOTFS}/usr/lib/${TOOLCHAIN}") +endif() + +if(TARGET_ARCH_NAME STREQUAL "armel") + if(DEFINED TIZEN_TOOLCHAIN) # For Tizen only + add_toolchain_linker_flag("-B${CROSS_ROOTFS}/usr/lib/gcc/${TIZEN_TOOLCHAIN}") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/lib") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/usr/lib") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/usr/lib/gcc/${TIZEN_TOOLCHAIN}") + endif() +elseif(TARGET_ARCH_NAME STREQUAL "arm64") + if(DEFINED TIZEN_TOOLCHAIN) # For Tizen only + add_toolchain_linker_flag("-B${CROSS_ROOTFS}/usr/lib64/gcc/${TIZEN_TOOLCHAIN}") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/lib64") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/usr/lib64") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/usr/lib64/gcc/${TIZEN_TOOLCHAIN}") + + add_toolchain_linker_flag("-Wl,--rpath-link=${CROSS_ROOTFS}/lib64") + add_toolchain_linker_flag("-Wl,--rpath-link=${CROSS_ROOTFS}/usr/lib64") + add_toolchain_linker_flag("-Wl,--rpath-link=${CROSS_ROOTFS}/usr/lib64/gcc/${TIZEN_TOOLCHAIN}") + endif() +elseif(TARGET_ARCH_NAME STREQUAL "x86") + add_toolchain_linker_flag(-m32) +elseif(ILLUMOS) + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/lib/amd64") + add_toolchain_linker_flag("-L${CROSS_ROOTFS}/usr/amd64/lib") +endif() + +# Specify compile options + +if((TARGET_ARCH_NAME MATCHES "^(arm|armel|arm64|s390x)$" AND NOT "$ENV{__DistroRid}" MATCHES "android.*") OR ILLUMOS) + set(CMAKE_C_COMPILER_TARGET ${TOOLCHAIN}) + set(CMAKE_CXX_COMPILER_TARGET ${TOOLCHAIN}) + set(CMAKE_ASM_COMPILER_TARGET ${TOOLCHAIN}) +endif() + +if(TARGET_ARCH_NAME MATCHES "^(arm|armel)$") + add_compile_options(-mthumb) + if (NOT DEFINED CLR_ARM_FPU_TYPE) + set (CLR_ARM_FPU_TYPE vfpv3) + endif (NOT DEFINED CLR_ARM_FPU_TYPE) + + add_compile_options (-mfpu=${CLR_ARM_FPU_TYPE}) + if (NOT DEFINED CLR_ARM_FPU_CAPABILITY) + set (CLR_ARM_FPU_CAPABILITY 0x7) + endif (NOT DEFINED CLR_ARM_FPU_CAPABILITY) + + add_definitions (-DCLR_ARM_FPU_CAPABILITY=${CLR_ARM_FPU_CAPABILITY}) + + if(TARGET_ARCH_NAME STREQUAL "armel") + add_compile_options(-mfloat-abi=softfp) + endif() +elseif(TARGET_ARCH_NAME STREQUAL "x86") + add_compile_options(-m32) + add_compile_options(-Wno-error=unused-command-line-argument) +endif() + +if(DEFINED TIZEN_TOOLCHAIN) + if(TARGET_ARCH_NAME MATCHES "^(armel|arm64)$") + add_compile_options(-Wno-deprecated-declarations) # compile-time option + add_compile_options(-D__extern_always_inline=inline) # compile-time option + endif() +endif() + +# Set LLDB include and library paths for builds that need lldb. +if(TARGET_ARCH_NAME MATCHES "^(arm|armel|x86)$") + if(TARGET_ARCH_NAME STREQUAL "x86") + set(LLVM_CROSS_DIR "$ENV{LLVM_CROSS_HOME}") + else() # arm/armel case + set(LLVM_CROSS_DIR "$ENV{LLVM_ARM_HOME}") + endif() + if(LLVM_CROSS_DIR) + set(WITH_LLDB_LIBS "${LLVM_CROSS_DIR}/lib/" CACHE STRING "") + set(WITH_LLDB_INCLUDES "${LLVM_CROSS_DIR}/include" CACHE STRING "") + set(LLDB_H "${WITH_LLDB_INCLUDES}" CACHE STRING "") + set(LLDB "${LLVM_CROSS_DIR}/lib/liblldb.so" CACHE STRING "") + else() + if(TARGET_ARCH_NAME STREQUAL "x86") + set(WITH_LLDB_LIBS "${CROSS_ROOTFS}/usr/lib/i386-linux-gnu" CACHE STRING "") + set(CHECK_LLVM_DIR "${CROSS_ROOTFS}/usr/lib/llvm-3.8/include") + if(EXISTS "${CHECK_LLVM_DIR}" AND IS_DIRECTORY "${CHECK_LLVM_DIR}") + set(WITH_LLDB_INCLUDES "${CHECK_LLVM_DIR}") + else() + set(WITH_LLDB_INCLUDES "${CROSS_ROOTFS}/usr/lib/llvm-3.6/include") + endif() + else() # arm/armel case + set(WITH_LLDB_LIBS "${CROSS_ROOTFS}/usr/lib/${TOOLCHAIN}" CACHE STRING "") + set(WITH_LLDB_INCLUDES "${CROSS_ROOTFS}/usr/lib/llvm-3.6/include" CACHE STRING "") + endif() + endif() +endif() + +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY) diff --git a/eng/common/cross/x86/sources.list.bionic b/eng/common/cross/x86/sources.list.bionic new file mode 100644 index 000000000..a71ccadcf --- /dev/null +++ b/eng/common/cross/x86/sources.list.bionic @@ -0,0 +1,11 @@ +deb http://archive.ubuntu.com/ubuntu/ bionic main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ bionic main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ bionic-updates main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ bionic-updates main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ bionic-backports main restricted +deb-src http://archive.ubuntu.com/ubuntu/ bionic-backports main restricted + +deb http://archive.ubuntu.com/ubuntu/ bionic-security main restricted universe multiverse +deb-src http://archive.ubuntu.com/ubuntu/ bionic-security main restricted universe multiverse diff --git a/eng/common/cross/x86/sources.list.trusty b/eng/common/cross/x86/sources.list.trusty new file mode 100644 index 000000000..9b3085436 --- /dev/null +++ b/eng/common/cross/x86/sources.list.trusty @@ -0,0 +1,11 @@ +deb http://archive.ubuntu.com/ubuntu/ trusty main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ trusty main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ trusty-updates main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ trusty-updates main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ trusty-backports main restricted +deb-src http://archive.ubuntu.com/ubuntu/ trusty-backports main restricted + +deb http://archive.ubuntu.com/ubuntu/ trusty-security main restricted universe multiverse +deb-src http://archive.ubuntu.com/ubuntu/ trusty-security main restricted universe multiverse diff --git a/eng/common/cross/x86/sources.list.xenial b/eng/common/cross/x86/sources.list.xenial new file mode 100644 index 000000000..ad9c5a014 --- /dev/null +++ b/eng/common/cross/x86/sources.list.xenial @@ -0,0 +1,11 @@ +deb http://archive.ubuntu.com/ubuntu/ xenial main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ xenial main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ xenial-updates main restricted universe +deb-src http://archive.ubuntu.com/ubuntu/ xenial-updates main restricted universe + +deb http://archive.ubuntu.com/ubuntu/ xenial-backports main restricted +deb-src http://archive.ubuntu.com/ubuntu/ xenial-backports main restricted + +deb http://archive.ubuntu.com/ubuntu/ xenial-security main restricted universe multiverse +deb-src http://archive.ubuntu.com/ubuntu/ xenial-security main restricted universe multiverse diff --git a/eng/common/darc-init.ps1 b/eng/common/darc-init.ps1 new file mode 100644 index 000000000..435e76413 --- /dev/null +++ b/eng/common/darc-init.ps1 @@ -0,0 +1,47 @@ +param ( + $darcVersion = $null, + $versionEndpoint = 'https://maestro-prod.westus2.cloudapp.azure.com/api/assets/darc-version?api-version=2019-01-16', + $verbosity = 'minimal', + $toolpath = $null +) + +. $PSScriptRoot\tools.ps1 + +function InstallDarcCli ($darcVersion, $toolpath) { + $darcCliPackageName = 'microsoft.dotnet.darc' + + $dotnetRoot = InitializeDotNetCli -install:$true + $dotnet = "$dotnetRoot\dotnet.exe" + $toolList = & "$dotnet" tool list -g + + if ($toolList -like "*$darcCliPackageName*") { + & "$dotnet" tool uninstall $darcCliPackageName -g + } + + # If the user didn't explicitly specify the darc version, + # query the Maestro API for the correct version of darc to install. + if (-not $darcVersion) { + $darcVersion = $(Invoke-WebRequest -Uri $versionEndpoint -UseBasicParsing).Content + } + + $arcadeServicesSource = 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + + Write-Host "Installing Darc CLI version $darcVersion..." + Write-Host 'You may need to restart your command window if this is the first dotnet tool you have installed.' + if (-not $toolpath) { + Write-Host "'$dotnet' tool install $darcCliPackageName --version $darcVersion --add-source '$arcadeServicesSource' -v $verbosity -g" + & "$dotnet" tool install $darcCliPackageName --version $darcVersion --add-source "$arcadeServicesSource" -v $verbosity -g + }else { + Write-Host "'$dotnet' tool install $darcCliPackageName --version $darcVersion --add-source '$arcadeServicesSource' -v $verbosity --tool-path '$toolpath'" + & "$dotnet" tool install $darcCliPackageName --version $darcVersion --add-source "$arcadeServicesSource" -v $verbosity --tool-path "$toolpath" + } +} + +try { + InstallDarcCli $darcVersion $toolpath +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'Darc' -Message $_ + ExitWithExitCode 1 +} \ No newline at end of file diff --git a/eng/common/darc-init.sh b/eng/common/darc-init.sh new file mode 100644 index 000000000..39abdbecd --- /dev/null +++ b/eng/common/darc-init.sh @@ -0,0 +1,82 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" +darcVersion='' +versionEndpoint='https://maestro-prod.westus2.cloudapp.azure.com/api/assets/darc-version?api-version=2019-01-16' +verbosity='minimal' + +while [[ $# > 0 ]]; do + opt="$(echo "$1" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + --darcversion) + darcVersion=$2 + shift + ;; + --versionendpoint) + versionEndpoint=$2 + shift + ;; + --verbosity) + verbosity=$2 + shift + ;; + --toolpath) + toolpath=$2 + shift + ;; + *) + echo "Invalid argument: $1" + usage + exit 1 + ;; + esac + + shift +done + +# resolve $source until the file is no longer a symlink +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. "$scriptroot/tools.sh" + +if [ -z "$darcVersion" ]; then + darcVersion=$(curl -X GET "$versionEndpoint" -H "accept: text/plain") +fi + +function InstallDarcCli { + local darc_cli_package_name="microsoft.dotnet.darc" + + InitializeDotNetCli + local dotnet_root=$_InitializeDotNetCli + + if [ -z "$toolpath" ]; then + local tool_list=$($dotnet_root/dotnet tool list -g) + if [[ $tool_list = *$darc_cli_package_name* ]]; then + echo $($dotnet_root/dotnet tool uninstall $darc_cli_package_name -g) + fi + else + local tool_list=$($dotnet_root/dotnet tool list --tool-path "$toolpath") + if [[ $tool_list = *$darc_cli_package_name* ]]; then + echo $($dotnet_root/dotnet tool uninstall $darc_cli_package_name --tool-path "$toolpath") + fi + fi + + local arcadeServicesSource="https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json" + + echo "Installing Darc CLI version $darcVersion..." + echo "You may need to restart your command shell if this is the first dotnet tool you have installed." + if [ -z "$toolpath" ]; then + echo $($dotnet_root/dotnet tool install $darc_cli_package_name --version $darcVersion --add-source "$arcadeServicesSource" -v $verbosity -g) + else + echo $($dotnet_root/dotnet tool install $darc_cli_package_name --version $darcVersion --add-source "$arcadeServicesSource" -v $verbosity --tool-path "$toolpath") + fi +} + +InstallDarcCli diff --git a/eng/common/dotnet-install.cmd b/eng/common/dotnet-install.cmd new file mode 100644 index 000000000..b1c2642e7 --- /dev/null +++ b/eng/common/dotnet-install.cmd @@ -0,0 +1,2 @@ +@echo off +powershell -ExecutionPolicy ByPass -NoProfile -command "& """%~dp0dotnet-install.ps1""" %*" \ No newline at end of file diff --git a/eng/common/dotnet-install.ps1 b/eng/common/dotnet-install.ps1 new file mode 100644 index 000000000..811f0f717 --- /dev/null +++ b/eng/common/dotnet-install.ps1 @@ -0,0 +1,28 @@ +[CmdletBinding(PositionalBinding=$false)] +Param( + [string] $verbosity = 'minimal', + [string] $architecture = '', + [string] $version = 'Latest', + [string] $runtime = 'dotnet', + [string] $RuntimeSourceFeed = '', + [string] $RuntimeSourceFeedKey = '' +) + +. $PSScriptRoot\tools.ps1 + +$dotnetRoot = Join-Path $RepoRoot '.dotnet' + +$installdir = $dotnetRoot +try { + if ($architecture -and $architecture.Trim() -eq 'x86') { + $installdir = Join-Path $installdir 'x86' + } + InstallDotNet $installdir $version $architecture $runtime $true -RuntimeSourceFeed $RuntimeSourceFeed -RuntimeSourceFeedKey $RuntimeSourceFeedKey +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message $_ + ExitWithExitCode 1 +} + +ExitWithExitCode 0 diff --git a/eng/common/dotnet-install.sh b/eng/common/dotnet-install.sh new file mode 100644 index 000000000..fdfeea66e --- /dev/null +++ b/eng/common/dotnet-install.sh @@ -0,0 +1,84 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" +# resolve $source until the file is no longer a symlink +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. "$scriptroot/tools.sh" + +version='Latest' +architecture='' +runtime='dotnet' +runtimeSourceFeed='' +runtimeSourceFeedKey='' +while [[ $# > 0 ]]; do + opt="$(echo "$1" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -version|-v) + shift + version="$1" + ;; + -architecture|-a) + shift + architecture="$1" + ;; + -runtime|-r) + shift + runtime="$1" + ;; + -runtimesourcefeed) + shift + runtimeSourceFeed="$1" + ;; + -runtimesourcefeedkey) + shift + runtimeSourceFeedKey="$1" + ;; + *) + Write-PipelineTelemetryError -Category 'Build' -Message "Invalid argument: $1" + exit 1 + ;; + esac + shift +done + +# Use uname to determine what the CPU is, see https://en.wikipedia.org/wiki/Uname#Examples +cpuname=$(uname -m) +case $cpuname in + aarch64) + buildarch=arm64 + ;; + amd64|x86_64) + buildarch=x64 + ;; + armv*l) + buildarch=arm + ;; + i686) + buildarch=x86 + ;; + *) + echo "Unknown CPU $cpuname detected, treating it as x64" + buildarch=x64 + ;; +esac + +dotnetRoot="${repo_root}.dotnet" +if [[ $architecture != "" ]] && [[ $architecture != $buildarch ]]; then + dotnetRoot="$dotnetRoot/$architecture" +fi + +InstallDotNet $dotnetRoot $version "$architecture" $runtime true $runtimeSourceFeed $runtimeSourceFeedKey || { + local exit_code=$? + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "dotnet-install.sh failed (exit code '$exit_code')." >&2 + ExitWithExitCode $exit_code +} + +ExitWithExitCode 0 diff --git a/eng/common/enable-cross-org-publishing.ps1 b/eng/common/enable-cross-org-publishing.ps1 new file mode 100644 index 000000000..da09da4f1 --- /dev/null +++ b/eng/common/enable-cross-org-publishing.ps1 @@ -0,0 +1,13 @@ +param( + [string] $token +) + + +. $PSScriptRoot\pipeline-logging-functions.ps1 + +# Write-PipelineSetVariable will no-op if a variable named $ci is not defined +# Since this script is only ever called in AzDO builds, just universally set it +$ci = $true + +Write-PipelineSetVariable -Name 'VSS_NUGET_ACCESSTOKEN' -Value $token -IsMultiJobVariable $false +Write-PipelineSetVariable -Name 'VSS_NUGET_URI_PREFIXES' -Value 'https://dnceng.pkgs.visualstudio.com/;https://pkgs.dev.azure.com/dnceng/;https://devdiv.pkgs.visualstudio.com/;https://pkgs.dev.azure.com/devdiv/' -IsMultiJobVariable $false diff --git a/eng/common/generate-graph-files.ps1 b/eng/common/generate-graph-files.ps1 new file mode 100644 index 000000000..0728b1a8b --- /dev/null +++ b/eng/common/generate-graph-files.ps1 @@ -0,0 +1,86 @@ +Param( + [Parameter(Mandatory=$true)][string] $barToken, # Token generated at https://maestro-prod.westus2.cloudapp.azure.com/Account/Tokens + [Parameter(Mandatory=$true)][string] $gitHubPat, # GitHub personal access token from https://github.com/settings/tokens (no auth scopes needed) + [Parameter(Mandatory=$true)][string] $azdoPat, # Azure Dev Ops tokens from https://dev.azure.com/dnceng/_details/security/tokens (code read scope needed) + [Parameter(Mandatory=$true)][string] $outputFolder, # Where the graphviz.txt file will be created + [string] $darcVersion, # darc's version + [string] $graphvizVersion = '2.38', # GraphViz version + [switch] $includeToolset # Whether the graph should include toolset dependencies or not. i.e. arcade, optimization. For more about + # toolset dependencies see https://github.com/dotnet/arcade/blob/master/Documentation/Darc.md#toolset-vs-product-dependencies +) + +function CheckExitCode ([string]$stage) +{ + $exitCode = $LASTEXITCODE + if ($exitCode -ne 0) { + Write-PipelineTelemetryError -Category 'Arcade' -Message "Something failed in stage: '$stage'. Check for errors above. Exiting now..." + ExitWithExitCode $exitCode + } +} + +try { + $ErrorActionPreference = 'Stop' + . $PSScriptRoot\tools.ps1 + + Import-Module -Name (Join-Path $PSScriptRoot 'native\CommonLibrary.psm1') + + Push-Location $PSScriptRoot + + Write-Host 'Installing darc...' + . .\darc-init.ps1 -darcVersion $darcVersion + CheckExitCode 'Running darc-init' + + $engCommonBaseDir = Join-Path $PSScriptRoot 'native\' + $graphvizInstallDir = CommonLibrary\Get-NativeInstallDirectory + $nativeToolBaseUri = 'https://netcorenativeassets.blob.core.windows.net/resource-packages/external' + $installBin = Join-Path $graphvizInstallDir 'bin' + + Write-Host 'Installing dot...' + .\native\install-tool.ps1 -ToolName graphviz -InstallPath $installBin -BaseUri $nativeToolBaseUri -CommonLibraryDirectory $engCommonBaseDir -Version $graphvizVersion -Verbose + + $darcExe = "$env:USERPROFILE\.dotnet\tools" + $darcExe = Resolve-Path "$darcExe\darc.exe" + + Create-Directory $outputFolder + + # Generate 3 graph descriptions: + # 1. Flat with coherency information + # 2. Graphviz (dot) file + # 3. Standard dependency graph + $graphVizFilePath = "$outputFolder\graphviz.txt" + $graphVizImageFilePath = "$outputFolder\graph.png" + $normalGraphFilePath = "$outputFolder\graph-full.txt" + $flatGraphFilePath = "$outputFolder\graph-flat.txt" + $baseOptions = @( '--github-pat', "$gitHubPat", '--azdev-pat', "$azdoPat", '--password', "$barToken" ) + + if ($includeToolset) { + Write-Host 'Toolsets will be included in the graph...' + $baseOptions += @( '--include-toolset' ) + } + + Write-Host 'Generating standard dependency graph...' + & "$darcExe" get-dependency-graph @baseOptions --output-file $normalGraphFilePath + CheckExitCode 'Generating normal dependency graph' + + Write-Host 'Generating flat dependency graph and graphviz file...' + & "$darcExe" get-dependency-graph @baseOptions --flat --coherency --graphviz $graphVizFilePath --output-file $flatGraphFilePath + CheckExitCode 'Generating flat and graphviz dependency graph' + + Write-Host "Generating graph image $graphVizFilePath" + $dotFilePath = Join-Path $installBin "graphviz\$graphvizVersion\release\bin\dot.exe" + & "$dotFilePath" -Tpng -o"$graphVizImageFilePath" "$graphVizFilePath" + CheckExitCode 'Generating graphviz image' + + Write-Host "'$graphVizFilePath', '$flatGraphFilePath', '$normalGraphFilePath' and '$graphVizImageFilePath' created!" +} +catch { + if (!$includeToolset) { + Write-Host 'This might be a toolset repo which includes only toolset dependencies. ' -NoNewline -ForegroundColor Yellow + Write-Host 'Since -includeToolset is not set there is no graph to create. Include -includeToolset and try again...' -ForegroundColor Yellow + } + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'Arcade' -Message $_ + ExitWithExitCode 1 +} finally { + Pop-Location +} \ No newline at end of file diff --git a/eng/common/generate-locproject.ps1 b/eng/common/generate-locproject.ps1 new file mode 100644 index 000000000..25e97ac00 --- /dev/null +++ b/eng/common/generate-locproject.ps1 @@ -0,0 +1,117 @@ +Param( + [Parameter(Mandatory=$true)][string] $SourcesDirectory, # Directory where source files live; if using a Localize directory it should live in here + [string] $LanguageSet = 'VS_Main_Languages', # Language set to be used in the LocProject.json + [switch] $UseCheckedInLocProjectJson, # When set, generates a LocProject.json and compares it to one that already exists in the repo; otherwise just generates one + [switch] $CreateNeutralXlfs # Creates neutral xlf files. Only set to false when running locally +) + +# Generates LocProject.json files for the OneLocBuild task. OneLocBuildTask is described here: +# https://ceapex.visualstudio.com/CEINTL/_wiki/wikis/CEINTL.wiki/107/Localization-with-OneLocBuild-Task + +Set-StrictMode -Version 2.0 +$ErrorActionPreference = "Stop" +. $PSScriptRoot\tools.ps1 + +Import-Module -Name (Join-Path $PSScriptRoot 'native\CommonLibrary.psm1') + +$exclusionsFilePath = "$SourcesDirectory\eng\Localize\LocExclusions.json" +$exclusions = @{ Exclusions = @() } +if (Test-Path -Path $exclusionsFilePath) +{ + $exclusions = Get-Content "$exclusionsFilePath" | ConvertFrom-Json +} + +Push-Location "$SourcesDirectory" # push location for Resolve-Path -Relative to work + +# Template files +$jsonFiles = @() +$jsonTemplateFiles = Get-ChildItem -Recurse -Path "$SourcesDirectory" | Where-Object { $_.FullName -Match "\.template\.config\\localize\\.+\.en\.json" } # .NET templating pattern +$jsonTemplateFiles | ForEach-Object { + $null = $_.Name -Match "(.+)\.[\w-]+\.json" # matches '[filename].[langcode].json + + $destinationFile = "$($_.Directory.FullName)\$($Matches.1).json" + $jsonFiles += Copy-Item "$($_.FullName)" -Destination $destinationFile -PassThru +} + +$jsonWinformsTemplateFiles = Get-ChildItem -Recurse -Path "$SourcesDirectory" | Where-Object { $_.FullName -Match "en\\strings\.json" } # current winforms pattern + +$xlfFiles = @() + +$allXlfFiles = Get-ChildItem -Recurse -Path "$SourcesDirectory\*\*.xlf" +$langXlfFiles = @() +if ($allXlfFiles) { + $null = $allXlfFiles[0].FullName -Match "\.([\w-]+)\.xlf" # matches '[langcode].xlf' + $firstLangCode = $Matches.1 + $langXlfFiles = Get-ChildItem -Recurse -Path "$SourcesDirectory\*\*.$firstLangCode.xlf" +} +$langXlfFiles | ForEach-Object { + $null = $_.Name -Match "(.+)\.[\w-]+\.xlf" # matches '[filename].[langcode].xlf + + $destinationFile = "$($_.Directory.FullName)\$($Matches.1).xlf" + $xlfFiles += Copy-Item "$($_.FullName)" -Destination $destinationFile -PassThru +} + +$locFiles = $jsonFiles + $jsonWinformsTemplateFiles + $xlfFiles + +$locJson = @{ + Projects = @( + @{ + LanguageSet = $LanguageSet + LocItems = @( + $locFiles | ForEach-Object { + $outputPath = "$(($_.DirectoryName | Resolve-Path -Relative) + "\")" + $continue = $true + foreach ($exclusion in $exclusions.Exclusions) { + if ($outputPath.Contains($exclusion)) + { + $continue = $false + } + } + $sourceFile = ($_.FullName | Resolve-Path -Relative) + if (!$CreateNeutralXlfs -and $_.Extension -eq '.xlf') { + Remove-Item -Path $sourceFile + } + if ($continue) + { + if ($_.Directory.Name -eq 'en' -and $_.Extension -eq '.json') { + return @{ + SourceFile = $sourceFile + CopyOption = "LangIDOnPath" + OutputPath = "$($_.Directory.Parent.FullName | Resolve-Path -Relative)\" + } + } + else { + return @{ + SourceFile = $sourceFile + CopyOption = "LangIDOnName" + OutputPath = $outputPath + } + } + } + } + ) + } + ) +} + +$json = ConvertTo-Json $locJson -Depth 5 +Write-Host "LocProject.json generated:`n`n$json`n`n" +Pop-Location + +if (!$UseCheckedInLocProjectJson) { + New-Item "$SourcesDirectory\eng\Localize\LocProject.json" -Force # Need this to make sure the Localize directory is created + Set-Content "$SourcesDirectory\eng\Localize\LocProject.json" $json +} +else { + New-Item "$SourcesDirectory\eng\Localize\LocProject-generated.json" -Force # Need this to make sure the Localize directory is created + Set-Content "$SourcesDirectory\eng\Localize\LocProject-generated.json" $json + + if ((Get-FileHash "$SourcesDirectory\eng\Localize\LocProject-generated.json").Hash -ne (Get-FileHash "$SourcesDirectory\eng\Localize\LocProject.json").Hash) { + Write-PipelineTelemetryError -Category "OneLocBuild" -Message "Existing LocProject.json differs from generated LocProject.json. Download LocProject-generated.json and compare them." + + exit 1 + } + else { + Write-Host "Generated LocProject.json and current LocProject.json are identical." + } +} \ No newline at end of file diff --git a/eng/common/helixpublish.proj b/eng/common/helixpublish.proj new file mode 100644 index 000000000..d7f185856 --- /dev/null +++ b/eng/common/helixpublish.proj @@ -0,0 +1,26 @@ + + + + msbuild + + + + + %(Identity) + + + + + + $(WorkItemDirectory) + $(WorkItemCommand) + $(WorkItemTimeout) + + + + + + + + + diff --git a/eng/common/init-tools-native.cmd b/eng/common/init-tools-native.cmd new file mode 100644 index 000000000..438cd548c --- /dev/null +++ b/eng/common/init-tools-native.cmd @@ -0,0 +1,3 @@ +@echo off +powershell -NoProfile -NoLogo -ExecutionPolicy ByPass -command "& """%~dp0init-tools-native.ps1""" %*" +exit /b %ErrorLevel% \ No newline at end of file diff --git a/eng/common/init-tools-native.ps1 b/eng/common/init-tools-native.ps1 new file mode 100644 index 000000000..db830c00a --- /dev/null +++ b/eng/common/init-tools-native.ps1 @@ -0,0 +1,152 @@ +<# +.SYNOPSIS +Entry point script for installing native tools + +.DESCRIPTION +Reads $RepoRoot\global.json file to determine native assets to install +and executes installers for those tools + +.PARAMETER BaseUri +Base file directory or Url from which to acquire tool archives + +.PARAMETER InstallDirectory +Directory to install native toolset. This is a command-line override for the default +Install directory precedence order: +- InstallDirectory command-line override +- NETCOREENG_INSTALL_DIRECTORY environment variable +- (default) %USERPROFILE%/.netcoreeng/native + +.PARAMETER Clean +Switch specifying to not install anything, but cleanup native asset folders + +.PARAMETER Force +Clean and then install tools + +.PARAMETER DownloadRetries +Total number of retry attempts + +.PARAMETER RetryWaitTimeInSeconds +Wait time between retry attempts in seconds + +.PARAMETER GlobalJsonFile +File path to global.json file + +.NOTES +#> +[CmdletBinding(PositionalBinding=$false)] +Param ( + [string] $BaseUri = 'https://netcorenativeassets.blob.core.windows.net/resource-packages/external', + [string] $InstallDirectory, + [switch] $Clean = $False, + [switch] $Force = $False, + [int] $DownloadRetries = 5, + [int] $RetryWaitTimeInSeconds = 30, + [string] $GlobalJsonFile +) + +if (!$GlobalJsonFile) { + $GlobalJsonFile = Join-Path (Get-Item $PSScriptRoot).Parent.Parent.FullName 'global.json' +} + +Set-StrictMode -version 2.0 +$ErrorActionPreference='Stop' + +. $PSScriptRoot\pipeline-logging-functions.ps1 +Import-Module -Name (Join-Path $PSScriptRoot 'native\CommonLibrary.psm1') + +try { + # Define verbose switch if undefined + $Verbose = $VerbosePreference -Eq 'Continue' + + $EngCommonBaseDir = Join-Path $PSScriptRoot 'native\' + $NativeBaseDir = $InstallDirectory + if (!$NativeBaseDir) { + $NativeBaseDir = CommonLibrary\Get-NativeInstallDirectory + } + $Env:CommonLibrary_NativeInstallDir = $NativeBaseDir + $InstallBin = Join-Path $NativeBaseDir 'bin' + $InstallerPath = Join-Path $EngCommonBaseDir 'install-tool.ps1' + + # Process tools list + Write-Host "Processing $GlobalJsonFile" + If (-Not (Test-Path $GlobalJsonFile)) { + Write-Host "Unable to find '$GlobalJsonFile'" + exit 0 + } + $NativeTools = Get-Content($GlobalJsonFile) -Raw | + ConvertFrom-Json | + Select-Object -Expand 'native-tools' -ErrorAction SilentlyContinue + if ($NativeTools) { + $NativeTools.PSObject.Properties | ForEach-Object { + $ToolName = $_.Name + $ToolVersion = $_.Value + $LocalInstallerArguments = @{ ToolName = "$ToolName" } + $LocalInstallerArguments += @{ InstallPath = "$InstallBin" } + $LocalInstallerArguments += @{ BaseUri = "$BaseUri" } + $LocalInstallerArguments += @{ CommonLibraryDirectory = "$EngCommonBaseDir" } + $LocalInstallerArguments += @{ Version = "$ToolVersion" } + + if ($Verbose) { + $LocalInstallerArguments += @{ Verbose = $True } + } + if (Get-Variable 'Force' -ErrorAction 'SilentlyContinue') { + if($Force) { + $LocalInstallerArguments += @{ Force = $True } + } + } + if ($Clean) { + $LocalInstallerArguments += @{ Clean = $True } + } + + Write-Verbose "Installing $ToolName version $ToolVersion" + Write-Verbose "Executing '$InstallerPath $($LocalInstallerArguments.Keys.ForEach({"-$_ '$($LocalInstallerArguments.$_)'"}) -join ' ')'" + & $InstallerPath @LocalInstallerArguments + if ($LASTEXITCODE -Ne "0") { + $errMsg = "$ToolName installation failed" + if ((Get-Variable 'DoNotAbortNativeToolsInstallationOnFailure' -ErrorAction 'SilentlyContinue') -and $DoNotAbortNativeToolsInstallationOnFailure) { + $showNativeToolsWarning = $true + if ((Get-Variable 'DoNotDisplayNativeToolsInstallationWarnings' -ErrorAction 'SilentlyContinue') -and $DoNotDisplayNativeToolsInstallationWarnings) { + $showNativeToolsWarning = $false + } + if ($showNativeToolsWarning) { + Write-Warning $errMsg + } + $toolInstallationFailure = $true + } else { + # We cannot change this to Write-PipelineTelemetryError because of https://github.com/dotnet/arcade/issues/4482 + Write-Host $errMsg + exit 1 + } + } + } + + if ((Get-Variable 'toolInstallationFailure' -ErrorAction 'SilentlyContinue') -and $toolInstallationFailure) { + # We cannot change this to Write-PipelineTelemetryError because of https://github.com/dotnet/arcade/issues/4482 + Write-Host 'Native tools bootstrap failed' + exit 1 + } + } + else { + Write-Host 'No native tools defined in global.json' + exit 0 + } + + if ($Clean) { + exit 0 + } + if (Test-Path $InstallBin) { + Write-Host 'Native tools are available from ' (Convert-Path -Path $InstallBin) + Write-Host "##vso[task.prependpath]$(Convert-Path -Path $InstallBin)" + return $InstallBin + } + else { + Write-PipelineTelemetryError -Category 'NativeToolsBootstrap' -Message 'Native tools install directory does not exist, installation failed' + exit 1 + } + exit 0 +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'NativeToolsBootstrap' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/init-tools-native.sh b/eng/common/init-tools-native.sh new file mode 100644 index 000000000..5bd205b5d --- /dev/null +++ b/eng/common/init-tools-native.sh @@ -0,0 +1,238 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +base_uri='https://netcorenativeassets.blob.core.windows.net/resource-packages/external' +install_directory='' +clean=false +force=false +download_retries=5 +retry_wait_time_seconds=30 +global_json_file="$(dirname "$(dirname "${scriptroot}")")/global.json" +declare -A native_assets + +. $scriptroot/pipeline-logging-functions.sh +. $scriptroot/native/common-library.sh + +while (($# > 0)); do + lowerI="$(echo $1 | tr "[:upper:]" "[:lower:]")" + case $lowerI in + --baseuri) + base_uri=$2 + shift 2 + ;; + --installdirectory) + install_directory=$2 + shift 2 + ;; + --clean) + clean=true + shift 1 + ;; + --force) + force=true + shift 1 + ;; + --donotabortonfailure) + donotabortonfailure=true + shift 1 + ;; + --donotdisplaywarnings) + donotdisplaywarnings=true + shift 1 + ;; + --downloadretries) + download_retries=$2 + shift 2 + ;; + --retrywaittimeseconds) + retry_wait_time_seconds=$2 + shift 2 + ;; + --help) + echo "Common settings:" + echo " --installdirectory Directory to install native toolset." + echo " This is a command-line override for the default" + echo " Install directory precedence order:" + echo " - InstallDirectory command-line override" + echo " - NETCOREENG_INSTALL_DIRECTORY environment variable" + echo " - (default) %USERPROFILE%/.netcoreeng/native" + echo "" + echo " --clean Switch specifying not to install anything, but cleanup native asset folders" + echo " --donotabortonfailure Switch specifiying whether to abort native tools installation on failure" + echo " --donotdisplaywarnings Switch specifiying whether to display warnings during native tools installation on failure" + echo " --force Clean and then install tools" + echo " --help Print help and exit" + echo "" + echo "Advanced settings:" + echo " --baseuri Base URI for where to download native tools from" + echo " --downloadretries Number of times a download should be attempted" + echo " --retrywaittimeseconds Wait time between download attempts" + echo "" + exit 0 + ;; + esac +done + +function ReadGlobalJsonNativeTools { + # happy path: we have a proper JSON parsing tool `jq(1)` in PATH! + if command -v jq &> /dev/null; then + + # jq: read each key/value pair under "native-tools" entry and emit: + # KEY="" VALUE="" + # followed by a null byte. + # + # bash: read line with null byte delimeter and push to array (for later `eval`uation). + + while IFS= read -rd '' line; do + native_assets+=("$line") + done < <(jq -r '. | + select(has("native-tools")) | + ."native-tools" | + keys[] as $k | + @sh "KEY=\($k) VALUE=\(.[$k])\u0000"' "$global_json_file") + + return + fi + + # Warning: falling back to manually parsing JSON, which is not recommended. + + # Following routine matches the output and escaping logic of jq(1)'s @sh formatter used above. + # It has been tested with several weird strings with escaped characters in entries (key and value) + # and results were compared with the output of jq(1) in binary representation using xxd(1); + # just before the assignment to 'native_assets' array (above and below). + + # try to capture the section under "native-tools". + if [[ ! "$(cat "$global_json_file")" =~ \"native-tools\"[[:space:]\:\{]*([^\}]+) ]]; then + return + fi + + section="${BASH_REMATCH[1]}" + + parseStarted=0 + possibleEnd=0 + escaping=0 + escaped=0 + isKey=1 + + for (( i=0; i<${#section}; i++ )); do + char="${section:$i:1}" + if ! ((parseStarted)) && [[ "$char" =~ [[:space:],:] ]]; then continue; fi + + if ! ((escaping)) && [[ "$char" == "\\" ]]; then + escaping=1 + elif ((escaping)) && ! ((escaped)); then + escaped=1 + fi + + if ! ((parseStarted)) && [[ "$char" == "\"" ]]; then + parseStarted=1 + possibleEnd=0 + elif [[ "$char" == "'" ]]; then + token="$token'\\\''" + possibleEnd=0 + elif ((escaping)) || [[ "$char" != "\"" ]]; then + token="$token$char" + possibleEnd=1 + fi + + if ((possibleEnd)) && ! ((escaping)) && [[ "$char" == "\"" ]]; then + # Use printf to unescape token to match jq(1)'s @sh formatting rules. + # do not use 'token="$(printf "$token")"' syntax, as $() eats the trailing linefeed. + printf -v token "'$token'" + + if ((isKey)); then + KEY="$token" + isKey=0 + else + line="KEY=$KEY VALUE=$token" + native_assets+=("$line") + isKey=1 + fi + + # reset for next token + parseStarted=0 + token= + elif ((escaping)) && ((escaped)); then + escaping=0 + escaped=0 + fi + done +} + +native_base_dir=$install_directory +if [[ -z $install_directory ]]; then + native_base_dir=$(GetNativeInstallDirectory) +fi + +install_bin="${native_base_dir}/bin" +installed_any=false + +ReadGlobalJsonNativeTools + +if [[ ${#native_assets[@]} -eq 0 ]]; then + echo "No native tools defined in global.json" + exit 0; +else + native_installer_dir="$scriptroot/native" + for index in "${!native_assets[@]}"; do + eval "${native_assets["$index"]}" + + installer_path="$native_installer_dir/install-$KEY.sh" + installer_command="$installer_path" + installer_command+=" --baseuri $base_uri" + installer_command+=" --installpath $install_bin" + installer_command+=" --version $VALUE" + echo $installer_command + + if [[ $force = true ]]; then + installer_command+=" --force" + fi + + if [[ $clean = true ]]; then + installer_command+=" --clean" + fi + + if [[ -a $installer_path ]]; then + $installer_command + if [[ $? != 0 ]]; then + if [[ $donotabortonfailure = true ]]; then + if [[ $donotdisplaywarnings != true ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Execution Failed" + fi + else + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Execution Failed" + exit 1 + fi + else + $installed_any = true + fi + else + if [[ $donotabortonfailure == true ]]; then + if [[ $donotdisplaywarnings != true ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Execution Failed: no install script" + fi + else + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Execution Failed: no install script" + exit 1 + fi + fi + done +fi + +if [[ $clean = true ]]; then + exit 0 +fi + +if [[ -d $install_bin ]]; then + echo "Native tools are available from $install_bin" + echo "##vso[task.prependpath]$install_bin" +else + if [[ $installed_any = true ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Native tools install directory does not exist, installation failed" + exit 1 + fi +fi + +exit 0 diff --git a/eng/common/internal-feed-operations.ps1 b/eng/common/internal-feed-operations.ps1 new file mode 100644 index 000000000..92b77347d --- /dev/null +++ b/eng/common/internal-feed-operations.ps1 @@ -0,0 +1,132 @@ +param( + [Parameter(Mandatory=$true)][string] $Operation, + [string] $AuthToken, + [string] $CommitSha, + [string] $RepoName, + [switch] $IsFeedPrivate +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 +. $PSScriptRoot\tools.ps1 + +# Sets VSS_NUGET_EXTERNAL_FEED_ENDPOINTS based on the "darc-int-*" feeds defined in NuGet.config. This is needed +# in build agents by CredProvider to authenticate the restore requests to internal feeds as specified in +# https://github.com/microsoft/artifacts-credprovider/blob/0f53327cd12fd893d8627d7b08a2171bf5852a41/README.md#environment-variables. This should ONLY be called from identified +# internal builds +function SetupCredProvider { + param( + [string] $AuthToken + ) + + # Install the Cred Provider NuGet plugin + Write-Host 'Setting up Cred Provider NuGet plugin in the agent...' + Write-Host "Getting 'installcredprovider.ps1' from 'https://github.com/microsoft/artifacts-credprovider'..." + + $url = 'https://raw.githubusercontent.com/microsoft/artifacts-credprovider/master/helpers/installcredprovider.ps1' + + Write-Host "Writing the contents of 'installcredprovider.ps1' locally..." + Invoke-WebRequest $url -OutFile installcredprovider.ps1 + + Write-Host 'Installing plugin...' + .\installcredprovider.ps1 -Force + + Write-Host "Deleting local copy of 'installcredprovider.ps1'..." + Remove-Item .\installcredprovider.ps1 + + if (-Not("$env:USERPROFILE\.nuget\plugins\netcore")) { + Write-PipelineTelemetryError -Category 'Arcade' -Message 'CredProvider plugin was not installed correctly!' + ExitWithExitCode 1 + } + else { + Write-Host 'CredProvider plugin was installed correctly!' + } + + # Then, we set the 'VSS_NUGET_EXTERNAL_FEED_ENDPOINTS' environment variable to restore from the stable + # feeds successfully + + $nugetConfigPath = Join-Path $RepoRoot "NuGet.config" + + if (-Not (Test-Path -Path $nugetConfigPath)) { + Write-PipelineTelemetryError -Category 'Build' -Message 'NuGet.config file not found in repo root!' + ExitWithExitCode 1 + } + + $endpoints = New-Object System.Collections.ArrayList + $nugetConfigPackageSources = Select-Xml -Path $nugetConfigPath -XPath "//packageSources/add[contains(@key, 'darc-int-')]/@value" | foreach{$_.Node.Value} + + if (($nugetConfigPackageSources | Measure-Object).Count -gt 0 ) { + foreach ($stableRestoreResource in $nugetConfigPackageSources) { + $trimmedResource = ([string]$stableRestoreResource).Trim() + [void]$endpoints.Add(@{endpoint="$trimmedResource"; password="$AuthToken"}) + } + } + + if (($endpoints | Measure-Object).Count -gt 0) { + $endpointCredentials = @{endpointCredentials=$endpoints} | ConvertTo-Json -Compress + + # Create the environment variables the AzDo way + Write-LoggingCommand -Area 'task' -Event 'setvariable' -Data $endpointCredentials -Properties @{ + 'variable' = 'VSS_NUGET_EXTERNAL_FEED_ENDPOINTS' + 'issecret' = 'false' + } + + # We don't want sessions cached since we will be updating the endpoints quite frequently + Write-LoggingCommand -Area 'task' -Event 'setvariable' -Data 'False' -Properties @{ + 'variable' = 'NUGET_CREDENTIALPROVIDER_SESSIONTOKENCACHE_ENABLED' + 'issecret' = 'false' + } + } + else + { + Write-Host 'No internal endpoints found in NuGet.config' + } +} + +#Workaround for https://github.com/microsoft/msbuild/issues/4430 +function InstallDotNetSdkAndRestoreArcade { + $dotnetTempDir = Join-Path $RepoRoot "dotnet" + $dotnetSdkVersion="2.1.507" # After experimentation we know this version works when restoring the SDK (compared to 3.0.*) + $dotnet = "$dotnetTempDir\dotnet.exe" + $restoreProjPath = "$PSScriptRoot\restore.proj" + + Write-Host "Installing dotnet SDK version $dotnetSdkVersion to restore Arcade SDK..." + InstallDotNetSdk "$dotnetTempDir" "$dotnetSdkVersion" + + '' | Out-File "$restoreProjPath" + + & $dotnet restore $restoreProjPath + + Write-Host 'Arcade SDK restored!' + + if (Test-Path -Path $restoreProjPath) { + Remove-Item $restoreProjPath + } + + if (Test-Path -Path $dotnetTempDir) { + Remove-Item $dotnetTempDir -Recurse + } +} + +try { + Push-Location $PSScriptRoot + + if ($Operation -like 'setup') { + SetupCredProvider $AuthToken + } + elseif ($Operation -like 'install-restore') { + InstallDotNetSdkAndRestoreArcade + } + else { + Write-PipelineTelemetryError -Category 'Arcade' -Message "Unknown operation '$Operation'!" + ExitWithExitCode 1 + } +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'Arcade' -Message $_ + ExitWithExitCode 1 +} +finally { + Pop-Location +} diff --git a/eng/common/internal-feed-operations.sh b/eng/common/internal-feed-operations.sh new file mode 100644 index 000000000..9378223ba --- /dev/null +++ b/eng/common/internal-feed-operations.sh @@ -0,0 +1,141 @@ +#!/usr/bin/env bash + +set -e + +# Sets VSS_NUGET_EXTERNAL_FEED_ENDPOINTS based on the "darc-int-*" feeds defined in NuGet.config. This is needed +# in build agents by CredProvider to authenticate the restore requests to internal feeds as specified in +# https://github.com/microsoft/artifacts-credprovider/blob/0f53327cd12fd893d8627d7b08a2171bf5852a41/README.md#environment-variables. +# This should ONLY be called from identified internal builds +function SetupCredProvider { + local authToken=$1 + + # Install the Cred Provider NuGet plugin + echo "Setting up Cred Provider NuGet plugin in the agent..."... + echo "Getting 'installcredprovider.ps1' from 'https://github.com/microsoft/artifacts-credprovider'..." + + local url="https://raw.githubusercontent.com/microsoft/artifacts-credprovider/master/helpers/installcredprovider.sh" + + echo "Writing the contents of 'installcredprovider.ps1' locally..." + local installcredproviderPath="installcredprovider.sh" + if command -v curl > /dev/null; then + curl $url > "$installcredproviderPath" + else + wget -q -O "$installcredproviderPath" "$url" + fi + + echo "Installing plugin..." + . "$installcredproviderPath" + + echo "Deleting local copy of 'installcredprovider.sh'..." + rm installcredprovider.sh + + if [ ! -d "$HOME/.nuget/plugins" ]; then + Write-PipelineTelemetryError -category 'Build' 'CredProvider plugin was not installed correctly!' + ExitWithExitCode 1 + else + echo "CredProvider plugin was installed correctly!" + fi + + # Then, we set the 'VSS_NUGET_EXTERNAL_FEED_ENDPOINTS' environment variable to restore from the stable + # feeds successfully + + local nugetConfigPath="{$repo_root}NuGet.config" + + if [ ! "$nugetConfigPath" ]; then + Write-PipelineTelemetryError -category 'Build' "NuGet.config file not found in repo's root!" + ExitWithExitCode 1 + fi + + local endpoints='[' + local nugetConfigPackageValues=`cat "$nugetConfigPath" | grep "key=\"darc-int-"` + local pattern="value=\"(.*)\"" + + for value in $nugetConfigPackageValues + do + if [[ $value =~ $pattern ]]; then + local endpoint="${BASH_REMATCH[1]}" + endpoints+="{\"endpoint\": \"$endpoint\", \"password\": \"$authToken\"}," + fi + done + + endpoints=${endpoints%?} + endpoints+=']' + + if [ ${#endpoints} -gt 2 ]; then + local endpointCredentials="{\"endpointCredentials\": "$endpoints"}" + + echo "##vso[task.setvariable variable=VSS_NUGET_EXTERNAL_FEED_ENDPOINTS]$endpointCredentials" + echo "##vso[task.setvariable variable=NUGET_CREDENTIALPROVIDER_SESSIONTOKENCACHE_ENABLED]False" + else + echo "No internal endpoints found in NuGet.config" + fi +} + +# Workaround for https://github.com/microsoft/msbuild/issues/4430 +function InstallDotNetSdkAndRestoreArcade { + local dotnetTempDir="$repo_root/dotnet" + local dotnetSdkVersion="2.1.507" # After experimentation we know this version works when restoring the SDK (compared to 3.0.*) + local restoreProjPath="$repo_root/eng/common/restore.proj" + + echo "Installing dotnet SDK version $dotnetSdkVersion to restore Arcade SDK..." + echo "" > "$restoreProjPath" + + InstallDotNetSdk "$dotnetTempDir" "$dotnetSdkVersion" + + local res=`$dotnetTempDir/dotnet restore $restoreProjPath` + echo "Arcade SDK restored!" + + # Cleanup + if [ "$restoreProjPath" ]; then + rm "$restoreProjPath" + fi + + if [ "$dotnetTempDir" ]; then + rm -r $dotnetTempDir + fi +} + +source="${BASH_SOURCE[0]}" +operation='' +authToken='' +repoName='' + +while [[ $# > 0 ]]; do + opt="$(echo "$1" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + --operation) + operation=$2 + shift + ;; + --authtoken) + authToken=$2 + shift + ;; + *) + echo "Invalid argument: $1" + usage + exit 1 + ;; + esac + + shift +done + +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. "$scriptroot/tools.sh" + +if [ "$operation" = "setup" ]; then + SetupCredProvider $authToken +elif [ "$operation" = "install-restore" ]; then + InstallDotNetSdkAndRestoreArcade +else + echo "Unknown operation '$operation'!" +fi diff --git a/eng/common/internal/Directory.Build.props b/eng/common/internal/Directory.Build.props new file mode 100644 index 000000000..dbf99d82a --- /dev/null +++ b/eng/common/internal/Directory.Build.props @@ -0,0 +1,4 @@ + + + + diff --git a/eng/common/internal/Tools.csproj b/eng/common/internal/Tools.csproj new file mode 100644 index 000000000..f46d5efe2 --- /dev/null +++ b/eng/common/internal/Tools.csproj @@ -0,0 +1,28 @@ + + + + + net472 + false + false + + + + + + + + + + + https://devdiv.pkgs.visualstudio.com/_packaging/dotnet-core-internal-tooling/nuget/v3/index.json; + + + $(RestoreSources); + https://devdiv.pkgs.visualstudio.com/_packaging/VS/nuget/v3/index.json; + + + + + + diff --git a/eng/common/msbuild.ps1 b/eng/common/msbuild.ps1 new file mode 100644 index 000000000..eea19cd84 --- /dev/null +++ b/eng/common/msbuild.ps1 @@ -0,0 +1,27 @@ +[CmdletBinding(PositionalBinding=$false)] +Param( + [string] $verbosity = 'minimal', + [bool] $warnAsError = $true, + [bool] $nodeReuse = $true, + [switch] $ci, + [switch] $prepareMachine, + [switch] $excludePrereleaseVS, + [Parameter(ValueFromRemainingArguments=$true)][String[]]$extraArgs +) + +. $PSScriptRoot\tools.ps1 + +try { + if ($ci) { + $nodeReuse = $false + } + + MSBuild @extraArgs +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'Build' -Message $_ + ExitWithExitCode 1 +} + +ExitWithExitCode 0 \ No newline at end of file diff --git a/eng/common/msbuild.sh b/eng/common/msbuild.sh new file mode 100644 index 000000000..20d3dad54 --- /dev/null +++ b/eng/common/msbuild.sh @@ -0,0 +1,58 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" + +# resolve $source until the file is no longer a symlink +while [[ -h "$source" ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +verbosity='minimal' +warn_as_error=true +node_reuse=true +prepare_machine=false +extra_args='' + +while (($# > 0)); do + lowerI="$(echo $1 | tr "[:upper:]" "[:lower:]")" + case $lowerI in + --verbosity) + verbosity=$2 + shift 2 + ;; + --warnaserror) + warn_as_error=$2 + shift 2 + ;; + --nodereuse) + node_reuse=$2 + shift 2 + ;; + --ci) + ci=true + shift 1 + ;; + --preparemachine) + prepare_machine=true + shift 1 + ;; + *) + extra_args="$extra_args $1" + shift 1 + ;; + esac +done + +. "$scriptroot/tools.sh" + +if [[ "$ci" == true ]]; then + node_reuse=false +fi + +MSBuild $extra_args +ExitWithExitCode 0 diff --git a/eng/common/native/CommonLibrary.psm1 b/eng/common/native/CommonLibrary.psm1 new file mode 100644 index 000000000..adf707c8f --- /dev/null +++ b/eng/common/native/CommonLibrary.psm1 @@ -0,0 +1,399 @@ +<# +.SYNOPSIS +Helper module to install an archive to a directory + +.DESCRIPTION +Helper module to download and extract an archive to a specified directory + +.PARAMETER Uri +Uri of artifact to download + +.PARAMETER InstallDirectory +Directory to extract artifact contents to + +.PARAMETER Force +Force download / extraction if file or contents already exist. Default = False + +.PARAMETER DownloadRetries +Total number of retry attempts. Default = 5 + +.PARAMETER RetryWaitTimeInSeconds +Wait time between retry attempts in seconds. Default = 30 + +.NOTES +Returns False if download or extraction fail, True otherwise +#> +function DownloadAndExtract { + [CmdletBinding(PositionalBinding=$false)] + Param ( + [Parameter(Mandatory=$True)] + [string] $Uri, + [Parameter(Mandatory=$True)] + [string] $InstallDirectory, + [switch] $Force = $False, + [int] $DownloadRetries = 5, + [int] $RetryWaitTimeInSeconds = 30 + ) + # Define verbose switch if undefined + $Verbose = $VerbosePreference -Eq "Continue" + + $TempToolPath = CommonLibrary\Get-TempPathFilename -Path $Uri + + # Download native tool + $DownloadStatus = CommonLibrary\Get-File -Uri $Uri ` + -Path $TempToolPath ` + -DownloadRetries $DownloadRetries ` + -RetryWaitTimeInSeconds $RetryWaitTimeInSeconds ` + -Force:$Force ` + -Verbose:$Verbose + + if ($DownloadStatus -Eq $False) { + Write-Error "Download failed from $Uri" + return $False + } + + # Extract native tool + $UnzipStatus = CommonLibrary\Expand-Zip -ZipPath $TempToolPath ` + -OutputDirectory $InstallDirectory ` + -Force:$Force ` + -Verbose:$Verbose + + if ($UnzipStatus -Eq $False) { + # Retry Download one more time with Force=true + $DownloadRetryStatus = CommonLibrary\Get-File -Uri $Uri ` + -Path $TempToolPath ` + -DownloadRetries 1 ` + -RetryWaitTimeInSeconds $RetryWaitTimeInSeconds ` + -Force:$True ` + -Verbose:$Verbose + + if ($DownloadRetryStatus -Eq $False) { + Write-Error "Last attempt of download failed as well" + return $False + } + + # Retry unzip again one more time with Force=true + $UnzipRetryStatus = CommonLibrary\Expand-Zip -ZipPath $TempToolPath ` + -OutputDirectory $InstallDirectory ` + -Force:$True ` + -Verbose:$Verbose + if ($UnzipRetryStatus -Eq $False) + { + Write-Error "Last attempt of unzip failed as well" + # Clean up partial zips and extracts + if (Test-Path $TempToolPath) { + Remove-Item $TempToolPath -Force + } + if (Test-Path $InstallDirectory) { + Remove-Item $InstallDirectory -Force -Recurse + } + return $False + } + } + + return $True +} + +<# +.SYNOPSIS +Download a file, retry on failure + +.DESCRIPTION +Download specified file and retry if attempt fails + +.PARAMETER Uri +Uri of file to download. If Uri is a local path, the file will be copied instead of downloaded + +.PARAMETER Path +Path to download or copy uri file to + +.PARAMETER Force +Overwrite existing file if present. Default = False + +.PARAMETER DownloadRetries +Total number of retry attempts. Default = 5 + +.PARAMETER RetryWaitTimeInSeconds +Wait time between retry attempts in seconds Default = 30 + +#> +function Get-File { + [CmdletBinding(PositionalBinding=$false)] + Param ( + [Parameter(Mandatory=$True)] + [string] $Uri, + [Parameter(Mandatory=$True)] + [string] $Path, + [int] $DownloadRetries = 5, + [int] $RetryWaitTimeInSeconds = 30, + [switch] $Force = $False + ) + $Attempt = 0 + + if ($Force) { + if (Test-Path $Path) { + Remove-Item $Path -Force + } + } + if (Test-Path $Path) { + Write-Host "File '$Path' already exists, skipping download" + return $True + } + + $DownloadDirectory = Split-Path -ErrorAction Ignore -Path "$Path" -Parent + if (-Not (Test-Path $DownloadDirectory)) { + New-Item -path $DownloadDirectory -force -itemType "Directory" | Out-Null + } + + $TempPath = "$Path.tmp" + if (Test-Path -IsValid -Path $Uri) { + Write-Verbose "'$Uri' is a file path, copying temporarily to '$TempPath'" + Copy-Item -Path $Uri -Destination $TempPath + Write-Verbose "Moving temporary file to '$Path'" + Move-Item -Path $TempPath -Destination $Path + return $? + } + else { + Write-Verbose "Downloading $Uri" + # Don't display the console progress UI - it's a huge perf hit + $ProgressPreference = 'SilentlyContinue' + while($Attempt -Lt $DownloadRetries) + { + try { + Invoke-WebRequest -UseBasicParsing -Uri $Uri -OutFile $TempPath + Write-Verbose "Downloaded to temporary location '$TempPath'" + Move-Item -Path $TempPath -Destination $Path + Write-Verbose "Moved temporary file to '$Path'" + return $True + } + catch { + $Attempt++ + if ($Attempt -Lt $DownloadRetries) { + $AttemptsLeft = $DownloadRetries - $Attempt + Write-Warning "Download failed, $AttemptsLeft attempts remaining, will retry in $RetryWaitTimeInSeconds seconds" + Start-Sleep -Seconds $RetryWaitTimeInSeconds + } + else { + Write-Error $_ + Write-Error $_.Exception + } + } + } + } + + return $False +} + +<# +.SYNOPSIS +Generate a shim for a native tool + +.DESCRIPTION +Creates a wrapper script (shim) that passes arguments forward to native tool assembly + +.PARAMETER ShimName +The name of the shim + +.PARAMETER ShimDirectory +The directory where shims are stored + +.PARAMETER ToolFilePath +Path to file that shim forwards to + +.PARAMETER Force +Replace shim if already present. Default = False + +.NOTES +Returns $True if generating shim succeeds, $False otherwise +#> +function New-ScriptShim { + [CmdletBinding(PositionalBinding=$false)] + Param ( + [Parameter(Mandatory=$True)] + [string] $ShimName, + [Parameter(Mandatory=$True)] + [string] $ShimDirectory, + [Parameter(Mandatory=$True)] + [string] $ToolFilePath, + [Parameter(Mandatory=$True)] + [string] $BaseUri, + [switch] $Force + ) + try { + Write-Verbose "Generating '$ShimName' shim" + + if (-Not (Test-Path $ToolFilePath)){ + Write-Error "Specified tool file path '$ToolFilePath' does not exist" + return $False + } + + # WinShimmer is a small .NET Framework program that creates .exe shims to bootstrapped programs + # Many of the checks for installed programs expect a .exe extension for Windows tools, rather + # than a .bat or .cmd file. + # Source: https://github.com/dotnet/arcade/tree/master/src/WinShimmer + if (-Not (Test-Path "$ShimDirectory\WinShimmer\winshimmer.exe")) { + $InstallStatus = DownloadAndExtract -Uri "$BaseUri/windows/winshimmer/WinShimmer.zip" ` + -InstallDirectory $ShimDirectory\WinShimmer ` + -Force:$Force ` + -DownloadRetries 2 ` + -RetryWaitTimeInSeconds 5 ` + -Verbose:$Verbose + } + + if ((Test-Path (Join-Path $ShimDirectory "$ShimName.exe"))) { + Write-Host "$ShimName.exe already exists; replacing..." + Remove-Item (Join-Path $ShimDirectory "$ShimName.exe") + } + + & "$ShimDirectory\WinShimmer\winshimmer.exe" $ShimName $ToolFilePath $ShimDirectory + return $True + } + catch { + Write-Host $_ + Write-Host $_.Exception + return $False + } +} + +<# +.SYNOPSIS +Returns the machine architecture of the host machine + +.NOTES +Returns 'x64' on 64 bit machines + Returns 'x86' on 32 bit machines +#> +function Get-MachineArchitecture { + $ProcessorArchitecture = $Env:PROCESSOR_ARCHITECTURE + $ProcessorArchitectureW6432 = $Env:PROCESSOR_ARCHITEW6432 + if($ProcessorArchitecture -Eq "X86") + { + if(($ProcessorArchitectureW6432 -Eq "") -Or + ($ProcessorArchitectureW6432 -Eq "X86")) { + return "x86" + } + $ProcessorArchitecture = $ProcessorArchitectureW6432 + } + if (($ProcessorArchitecture -Eq "AMD64") -Or + ($ProcessorArchitecture -Eq "IA64") -Or + ($ProcessorArchitecture -Eq "ARM64")) { + return "x64" + } + return "x86" +} + +<# +.SYNOPSIS +Get the name of a temporary folder under the native install directory +#> +function Get-TempDirectory { + return Join-Path (Get-NativeInstallDirectory) "temp/" +} + +function Get-TempPathFilename { + [CmdletBinding(PositionalBinding=$false)] + Param ( + [Parameter(Mandatory=$True)] + [string] $Path + ) + $TempDir = CommonLibrary\Get-TempDirectory + $TempFilename = Split-Path $Path -leaf + $TempPath = Join-Path $TempDir $TempFilename + return $TempPath +} + +<# +.SYNOPSIS +Returns the base directory to use for native tool installation + +.NOTES +Returns the value of the NETCOREENG_INSTALL_DIRECTORY if that environment variable +is set, or otherwise returns an install directory under the %USERPROFILE% +#> +function Get-NativeInstallDirectory { + $InstallDir = $Env:NETCOREENG_INSTALL_DIRECTORY + if (!$InstallDir) { + $InstallDir = Join-Path $Env:USERPROFILE ".netcoreeng/native/" + } + return $InstallDir +} + +<# +.SYNOPSIS +Unzip an archive + +.DESCRIPTION +Powershell module to unzip an archive to a specified directory + +.PARAMETER ZipPath (Required) +Path to archive to unzip + +.PARAMETER OutputDirectory (Required) +Output directory for archive contents + +.PARAMETER Force +Overwrite output directory contents if they already exist + +.NOTES +- Returns True and does not perform an extraction if output directory already exists but Overwrite is not True. +- Returns True if unzip operation is successful +- Returns False if Overwrite is True and it is unable to remove contents of OutputDirectory +- Returns False if unable to extract zip archive +#> +function Expand-Zip { + [CmdletBinding(PositionalBinding=$false)] + Param ( + [Parameter(Mandatory=$True)] + [string] $ZipPath, + [Parameter(Mandatory=$True)] + [string] $OutputDirectory, + [switch] $Force + ) + + Write-Verbose "Extracting '$ZipPath' to '$OutputDirectory'" + try { + if ((Test-Path $OutputDirectory) -And (-Not $Force)) { + Write-Host "Directory '$OutputDirectory' already exists, skipping extract" + return $True + } + if (Test-Path $OutputDirectory) { + Write-Verbose "'Force' is 'True', but '$OutputDirectory' exists, removing directory" + Remove-Item $OutputDirectory -Force -Recurse + if ($? -Eq $False) { + Write-Error "Unable to remove '$OutputDirectory'" + return $False + } + } + + $TempOutputDirectory = Join-Path "$(Split-Path -Parent $OutputDirectory)" "$(Split-Path -Leaf $OutputDirectory).tmp" + if (Test-Path $TempOutputDirectory) { + Remove-Item $TempOutputDirectory -Force -Recurse + } + New-Item -Path $TempOutputDirectory -Force -ItemType "Directory" | Out-Null + + Add-Type -assembly "system.io.compression.filesystem" + [io.compression.zipfile]::ExtractToDirectory("$ZipPath", "$TempOutputDirectory") + if ($? -Eq $False) { + Write-Error "Unable to extract '$ZipPath'" + return $False + } + + Move-Item -Path $TempOutputDirectory -Destination $OutputDirectory + } + catch { + Write-Host $_ + Write-Host $_.Exception + + return $False + } + return $True +} + +export-modulemember -function DownloadAndExtract +export-modulemember -function Expand-Zip +export-modulemember -function Get-File +export-modulemember -function Get-MachineArchitecture +export-modulemember -function Get-NativeInstallDirectory +export-modulemember -function Get-TempDirectory +export-modulemember -function Get-TempPathFilename +export-modulemember -function New-ScriptShim diff --git a/eng/common/native/common-library.sh b/eng/common/native/common-library.sh new file mode 100644 index 000000000..bf272dcf5 --- /dev/null +++ b/eng/common/native/common-library.sh @@ -0,0 +1,168 @@ +#!/usr/bin/env bash + +function GetNativeInstallDirectory { + local install_dir + + if [[ -z $NETCOREENG_INSTALL_DIRECTORY ]]; then + install_dir=$HOME/.netcoreeng/native/ + else + install_dir=$NETCOREENG_INSTALL_DIRECTORY + fi + + echo $install_dir + return 0 +} + +function GetTempDirectory { + + echo $(GetNativeInstallDirectory)temp/ + return 0 +} + +function ExpandZip { + local zip_path=$1 + local output_directory=$2 + local force=${3:-false} + + echo "Extracting $zip_path to $output_directory" + if [[ -d $output_directory ]] && [[ $force = false ]]; then + echo "Directory '$output_directory' already exists, skipping extract" + return 0 + fi + + if [[ -d $output_directory ]]; then + echo "'Force flag enabled, but '$output_directory' exists. Removing directory" + rm -rf $output_directory + if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Unable to remove '$output_directory'" + return 1 + fi + fi + + echo "Creating directory: '$output_directory'" + mkdir -p $output_directory + + echo "Extracting archive" + tar -xf $zip_path -C $output_directory + if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Unable to extract '$zip_path'" + return 1 + fi + + return 0 +} + +function GetCurrentOS { + local unameOut="$(uname -s)" + case $unameOut in + Linux*) echo "Linux";; + Darwin*) echo "MacOS";; + esac + return 0 +} + +function GetFile { + local uri=$1 + local path=$2 + local force=${3:-false} + local download_retries=${4:-5} + local retry_wait_time_seconds=${5:-30} + + if [[ -f $path ]]; then + if [[ $force = false ]]; then + echo "File '$path' already exists. Skipping download" + return 0 + else + rm -rf $path + fi + fi + + if [[ -f $uri ]]; then + echo "'$uri' is a file path, copying file to '$path'" + cp $uri $path + return $? + fi + + echo "Downloading $uri" + # Use curl if available, otherwise use wget + if command -v curl > /dev/null; then + curl "$uri" -sSL --retry $download_retries --retry-delay $retry_wait_time_seconds --create-dirs -o "$path" --fail + else + wget -q -O "$path" "$uri" --tries="$download_retries" + fi + + return $? +} + +function GetTempPathFileName { + local path=$1 + + local temp_dir=$(GetTempDirectory) + local temp_file_name=$(basename $path) + echo $temp_dir$temp_file_name + return 0 +} + +function DownloadAndExtract { + local uri=$1 + local installDir=$2 + local force=${3:-false} + local download_retries=${4:-5} + local retry_wait_time_seconds=${5:-30} + + local temp_tool_path=$(GetTempPathFileName $uri) + + echo "downloading to: $temp_tool_path" + + # Download file + GetFile "$uri" "$temp_tool_path" $force $download_retries $retry_wait_time_seconds + if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Failed to download '$uri' to '$temp_tool_path'." + return 1 + fi + + # Extract File + echo "extracting from $temp_tool_path to $installDir" + ExpandZip "$temp_tool_path" "$installDir" $force $download_retries $retry_wait_time_seconds + if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Failed to extract '$temp_tool_path' to '$installDir'." + return 1 + fi + + return 0 +} + +function NewScriptShim { + local shimpath=$1 + local tool_file_path=$2 + local force=${3:-false} + + echo "Generating '$shimpath' shim" + if [[ -f $shimpath ]]; then + if [[ $force = false ]]; then + echo "File '$shimpath' already exists." >&2 + return 1 + else + rm -rf $shimpath + fi + fi + + if [[ ! -f $tool_file_path ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' "Specified tool file path:'$tool_file_path' does not exist" + return 1 + fi + + local shim_contents=$'#!/usr/bin/env bash\n' + shim_contents+="SHIMARGS="$'$1\n' + shim_contents+="$tool_file_path"$' $SHIMARGS\n' + + # Write shim file + echo "$shim_contents" > $shimpath + + chmod +x $shimpath + + echo "Finished generating shim '$shimpath'" + + return $? +} + diff --git a/eng/common/native/find-native-compiler.sh b/eng/common/native/find-native-compiler.sh new file mode 100644 index 000000000..aed19d07d --- /dev/null +++ b/eng/common/native/find-native-compiler.sh @@ -0,0 +1,121 @@ +#!/usr/bin/env bash +# +# This file locates the native compiler with the given name and version and sets the environment variables to locate it. +# + +source="${BASH_SOURCE[0]}" + +# resolve $SOURCE until the file is no longer a symlink +while [[ -h $source ]]; do + scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + source="$(readlink "$source")" + + # if $source was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $source != /* ]] && source="$scriptroot/$source" +done +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +if [ $# -lt 0 ] +then + echo "Usage..." + echo "find-native-compiler.sh " + echo "Specify the name of compiler (clang or gcc)." + echo "Specify the major version of compiler." + echo "Specify the minor version of compiler." + exit 1 +fi + +. $scriptroot/../pipeline-logging-functions.sh + +compiler="$1" +cxxCompiler="$compiler++" +majorVersion="$2" +minorVersion="$3" + +if [ "$compiler" = "gcc" ]; then cxxCompiler="g++"; fi + +check_version_exists() { + desired_version=-1 + + # Set up the environment to be used for building with the desired compiler. + if command -v "$compiler-$1.$2" > /dev/null; then + desired_version="-$1.$2" + elif command -v "$compiler$1$2" > /dev/null; then + desired_version="$1$2" + elif command -v "$compiler-$1$2" > /dev/null; then + desired_version="-$1$2" + fi + + echo "$desired_version" +} + +if [ -z "$CLR_CC" ]; then + + # Set default versions + if [ -z "$majorVersion" ]; then + # note: gcc (all versions) and clang versions higher than 6 do not have minor version in file name, if it is zero. + if [ "$compiler" = "clang" ]; then versions=( 9 8 7 6.0 5.0 4.0 3.9 3.8 3.7 3.6 3.5 ) + elif [ "$compiler" = "gcc" ]; then versions=( 9 8 7 6 5 4.9 ); fi + + for version in "${versions[@]}"; do + parts=(${version//./ }) + desired_version="$(check_version_exists "${parts[0]}" "${parts[1]}")" + if [ "$desired_version" != "-1" ]; then majorVersion="${parts[0]}"; break; fi + done + + if [ -z "$majorVersion" ]; then + if command -v "$compiler" > /dev/null; then + if [ "$(uname)" != "Darwin" ]; then + Write-PipelineTelemetryError -category "Build" -type "warning" "Specific version of $compiler not found, falling back to use the one in PATH." + fi + export CC="$(command -v "$compiler")" + export CXX="$(command -v "$cxxCompiler")" + else + Write-PipelineTelemetryError -category "Build" "No usable version of $compiler found." + exit 1 + fi + else + if [ "$compiler" = "clang" ] && [ "$majorVersion" -lt 5 ]; then + if [ "$build_arch" = "arm" ] || [ "$build_arch" = "armel" ]; then + if command -v "$compiler" > /dev/null; then + Write-PipelineTelemetryError -category "Build" -type "warning" "Found clang version $majorVersion which is not supported on arm/armel architectures, falling back to use clang from PATH." + export CC="$(command -v "$compiler")" + export CXX="$(command -v "$cxxCompiler")" + else + Write-PipelineTelemetryError -category "Build" "Found clang version $majorVersion which is not supported on arm/armel architectures, and there is no clang in PATH." + exit 1 + fi + fi + fi + fi + else + desired_version="$(check_version_exists "$majorVersion" "$minorVersion")" + if [ "$desired_version" = "-1" ]; then + Write-PipelineTelemetryError -category "Build" "Could not find specific version of $compiler: $majorVersion $minorVersion." + exit 1 + fi + fi + + if [ -z "$CC" ]; then + export CC="$(command -v "$compiler$desired_version")" + export CXX="$(command -v "$cxxCompiler$desired_version")" + if [ -z "$CXX" ]; then export CXX="$(command -v "$cxxCompiler")"; fi + fi +else + if [ ! -f "$CLR_CC" ]; then + Write-PipelineTelemetryError -category "Build" "CLR_CC is set but path '$CLR_CC' does not exist" + exit 1 + fi + export CC="$CLR_CC" + export CXX="$CLR_CXX" +fi + +if [ -z "$CC" ]; then + Write-PipelineTelemetryError -category "Build" "Unable to find $compiler." + exit 1 +fi + +export CCC_CC="$CC" +export CCC_CXX="$CXX" +export SCAN_BUILD_COMMAND="$(command -v "scan-build$desired_version")" diff --git a/eng/common/native/install-cmake-test.sh b/eng/common/native/install-cmake-test.sh new file mode 100644 index 000000000..8a5e7cf0d --- /dev/null +++ b/eng/common/native/install-cmake-test.sh @@ -0,0 +1,117 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. $scriptroot/common-library.sh + +base_uri= +install_path= +version= +clean=false +force=false +download_retries=5 +retry_wait_time_seconds=30 + +while (($# > 0)); do + lowerI="$(echo $1 | tr "[:upper:]" "[:lower:]")" + case $lowerI in + --baseuri) + base_uri=$2 + shift 2 + ;; + --installpath) + install_path=$2 + shift 2 + ;; + --version) + version=$2 + shift 2 + ;; + --clean) + clean=true + shift 1 + ;; + --force) + force=true + shift 1 + ;; + --downloadretries) + download_retries=$2 + shift 2 + ;; + --retrywaittimeseconds) + retry_wait_time_seconds=$2 + shift 2 + ;; + --help) + echo "Common settings:" + echo " --baseuri Base file directory or Url wrom which to acquire tool archives" + echo " --installpath Base directory to install native tool to" + echo " --clean Don't install the tool, just clean up the current install of the tool" + echo " --force Force install of tools even if they previously exist" + echo " --help Print help and exit" + echo "" + echo "Advanced settings:" + echo " --downloadretries Total number of retry attempts" + echo " --retrywaittimeseconds Wait time between retry attempts in seconds" + echo "" + exit 0 + ;; + esac +done + +tool_name="cmake-test" +tool_os=$(GetCurrentOS) +tool_folder="$(echo $tool_os | tr "[:upper:]" "[:lower:]")" +tool_arch="x86_64" +tool_name_moniker="$tool_name-$version-$tool_os-$tool_arch" +tool_install_directory="$install_path/$tool_name/$version" +tool_file_path="$tool_install_directory/$tool_name_moniker/bin/$tool_name" +shim_path="$install_path/$tool_name.sh" +uri="${base_uri}/$tool_folder/$tool_name/$tool_name_moniker.tar.gz" + +# Clean up tool and installers +if [[ $clean = true ]]; then + echo "Cleaning $tool_install_directory" + if [[ -d $tool_install_directory ]]; then + rm -rf $tool_install_directory + fi + + echo "Cleaning $shim_path" + if [[ -f $shim_path ]]; then + rm -rf $shim_path + fi + + tool_temp_path=$(GetTempPathFileName $uri) + echo "Cleaning $tool_temp_path" + if [[ -f $tool_temp_path ]]; then + rm -rf $tool_temp_path + fi + + exit 0 +fi + +# Install tool +if [[ -f $tool_file_path ]] && [[ $force = false ]]; then + echo "$tool_name ($version) already exists, skipping install" + exit 0 +fi + +DownloadAndExtract $uri $tool_install_directory $force $download_retries $retry_wait_time_seconds + +if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' 'Installation failed' + exit 1 +fi + +# Generate Shim +# Always rewrite shims so that we are referencing the expected version +NewScriptShim $shim_path $tool_file_path true + +if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' 'Shim generation failed' + exit 1 +fi + +exit 0 diff --git a/eng/common/native/install-cmake.sh b/eng/common/native/install-cmake.sh new file mode 100644 index 000000000..de496beeb --- /dev/null +++ b/eng/common/native/install-cmake.sh @@ -0,0 +1,117 @@ +#!/usr/bin/env bash + +source="${BASH_SOURCE[0]}" +scriptroot="$( cd -P "$( dirname "$source" )" && pwd )" + +. $scriptroot/common-library.sh + +base_uri= +install_path= +version= +clean=false +force=false +download_retries=5 +retry_wait_time_seconds=30 + +while (($# > 0)); do + lowerI="$(echo $1 | tr "[:upper:]" "[:lower:]")" + case $lowerI in + --baseuri) + base_uri=$2 + shift 2 + ;; + --installpath) + install_path=$2 + shift 2 + ;; + --version) + version=$2 + shift 2 + ;; + --clean) + clean=true + shift 1 + ;; + --force) + force=true + shift 1 + ;; + --downloadretries) + download_retries=$2 + shift 2 + ;; + --retrywaittimeseconds) + retry_wait_time_seconds=$2 + shift 2 + ;; + --help) + echo "Common settings:" + echo " --baseuri Base file directory or Url wrom which to acquire tool archives" + echo " --installpath Base directory to install native tool to" + echo " --clean Don't install the tool, just clean up the current install of the tool" + echo " --force Force install of tools even if they previously exist" + echo " --help Print help and exit" + echo "" + echo "Advanced settings:" + echo " --downloadretries Total number of retry attempts" + echo " --retrywaittimeseconds Wait time between retry attempts in seconds" + echo "" + exit 0 + ;; + esac +done + +tool_name="cmake" +tool_os=$(GetCurrentOS) +tool_folder="$(echo $tool_os | tr "[:upper:]" "[:lower:]")" +tool_arch="x86_64" +tool_name_moniker="$tool_name-$version-$tool_os-$tool_arch" +tool_install_directory="$install_path/$tool_name/$version" +tool_file_path="$tool_install_directory/$tool_name_moniker/bin/$tool_name" +shim_path="$install_path/$tool_name.sh" +uri="${base_uri}/$tool_folder/$tool_name/$tool_name_moniker.tar.gz" + +# Clean up tool and installers +if [[ $clean = true ]]; then + echo "Cleaning $tool_install_directory" + if [[ -d $tool_install_directory ]]; then + rm -rf $tool_install_directory + fi + + echo "Cleaning $shim_path" + if [[ -f $shim_path ]]; then + rm -rf $shim_path + fi + + tool_temp_path=$(GetTempPathFileName $uri) + echo "Cleaning $tool_temp_path" + if [[ -f $tool_temp_path ]]; then + rm -rf $tool_temp_path + fi + + exit 0 +fi + +# Install tool +if [[ -f $tool_file_path ]] && [[ $force = false ]]; then + echo "$tool_name ($version) already exists, skipping install" + exit 0 +fi + +DownloadAndExtract $uri $tool_install_directory $force $download_retries $retry_wait_time_seconds + +if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' 'Installation failed' + exit 1 +fi + +# Generate Shim +# Always rewrite shims so that we are referencing the expected version +NewScriptShim $shim_path $tool_file_path true + +if [[ $? != 0 ]]; then + Write-PipelineTelemetryError -category 'NativeToolsBootstrap' 'Shim generation failed' + exit 1 +fi + +exit 0 diff --git a/eng/common/native/install-tool.ps1 b/eng/common/native/install-tool.ps1 new file mode 100644 index 000000000..78f2d84a4 --- /dev/null +++ b/eng/common/native/install-tool.ps1 @@ -0,0 +1,132 @@ +<# +.SYNOPSIS +Install native tool + +.DESCRIPTION +Install cmake native tool from Azure blob storage + +.PARAMETER InstallPath +Base directory to install native tool to + +.PARAMETER BaseUri +Base file directory or Url from which to acquire tool archives + +.PARAMETER CommonLibraryDirectory +Path to folder containing common library modules + +.PARAMETER Force +Force install of tools even if they previously exist + +.PARAMETER Clean +Don't install the tool, just clean up the current install of the tool + +.PARAMETER DownloadRetries +Total number of retry attempts + +.PARAMETER RetryWaitTimeInSeconds +Wait time between retry attempts in seconds + +.NOTES +Returns 0 if install succeeds, 1 otherwise +#> +[CmdletBinding(PositionalBinding=$false)] +Param ( + [Parameter(Mandatory=$True)] + [string] $ToolName, + [Parameter(Mandatory=$True)] + [string] $InstallPath, + [Parameter(Mandatory=$True)] + [string] $BaseUri, + [Parameter(Mandatory=$True)] + [string] $Version, + [string] $CommonLibraryDirectory = $PSScriptRoot, + [switch] $Force = $False, + [switch] $Clean = $False, + [int] $DownloadRetries = 5, + [int] $RetryWaitTimeInSeconds = 30 +) + +. $PSScriptRoot\..\pipeline-logging-functions.ps1 + +# Import common library modules +Import-Module -Name (Join-Path $CommonLibraryDirectory "CommonLibrary.psm1") + +try { + # Define verbose switch if undefined + $Verbose = $VerbosePreference -Eq "Continue" + + $Arch = CommonLibrary\Get-MachineArchitecture + $ToolOs = "win64" + if($Arch -Eq "x32") { + $ToolOs = "win32" + } + $ToolNameMoniker = "$ToolName-$Version-$ToolOs-$Arch" + $ToolInstallDirectory = Join-Path $InstallPath "$ToolName\$Version\" + $Uri = "$BaseUri/windows/$ToolName/$ToolNameMoniker.zip" + $ShimPath = Join-Path $InstallPath "$ToolName.exe" + + if ($Clean) { + Write-Host "Cleaning $ToolInstallDirectory" + if (Test-Path $ToolInstallDirectory) { + Remove-Item $ToolInstallDirectory -Force -Recurse + } + Write-Host "Cleaning $ShimPath" + if (Test-Path $ShimPath) { + Remove-Item $ShimPath -Force + } + $ToolTempPath = CommonLibrary\Get-TempPathFilename -Path $Uri + Write-Host "Cleaning $ToolTempPath" + if (Test-Path $ToolTempPath) { + Remove-Item $ToolTempPath -Force + } + exit 0 + } + + # Install tool + if ((Test-Path $ToolInstallDirectory) -And (-Not $Force)) { + Write-Verbose "$ToolName ($Version) already exists, skipping install" + } + else { + $InstallStatus = CommonLibrary\DownloadAndExtract -Uri $Uri ` + -InstallDirectory $ToolInstallDirectory ` + -Force:$Force ` + -DownloadRetries $DownloadRetries ` + -RetryWaitTimeInSeconds $RetryWaitTimeInSeconds ` + -Verbose:$Verbose + + if ($InstallStatus -Eq $False) { + Write-PipelineTelemetryError "Installation failed" -Category "NativeToolsetBootstrapping" + exit 1 + } + } + + $ToolFilePath = Get-ChildItem $ToolInstallDirectory -Recurse -Filter "$ToolName.exe" | % { $_.FullName } + if (@($ToolFilePath).Length -Gt 1) { + Write-Error "There are multiple copies of $ToolName in $($ToolInstallDirectory): `n$(@($ToolFilePath | out-string))" + exit 1 + } elseif (@($ToolFilePath).Length -Lt 1) { + Write-Host "$ToolName was not found in $ToolInstallDirectory." + exit 1 + } + + # Generate shim + # Always rewrite shims so that we are referencing the expected version + $GenerateShimStatus = CommonLibrary\New-ScriptShim -ShimName $ToolName ` + -ShimDirectory $InstallPath ` + -ToolFilePath "$ToolFilePath" ` + -BaseUri $BaseUri ` + -Force:$Force ` + -Verbose:$Verbose + + if ($GenerateShimStatus -Eq $False) { + Write-PipelineTelemetryError "Generate shim failed" -Category "NativeToolsetBootstrapping" + return 1 + } + + exit 0 +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category "NativeToolsetBootstrapping" -Message $_ + exit 1 +} diff --git a/eng/common/pipeline-logging-functions.ps1 b/eng/common/pipeline-logging-functions.ps1 new file mode 100644 index 000000000..8e422c561 --- /dev/null +++ b/eng/common/pipeline-logging-functions.ps1 @@ -0,0 +1,260 @@ +# Source for this file was taken from https://github.com/microsoft/azure-pipelines-task-lib/blob/11c9439d4af17e6475d9fe058e6b2e03914d17e6/powershell/VstsTaskSdk/LoggingCommandFunctions.ps1 and modified. + +# NOTE: You should not be calling these method directly as they are likely to change. Instead you should be calling the Write-Pipeline* functions defined in tools.ps1 + +$script:loggingCommandPrefix = '##vso[' +$script:loggingCommandEscapeMappings = @( # TODO: WHAT ABOUT "="? WHAT ABOUT "%"? + New-Object psobject -Property @{ Token = ';' ; Replacement = '%3B' } + New-Object psobject -Property @{ Token = "`r" ; Replacement = '%0D' } + New-Object psobject -Property @{ Token = "`n" ; Replacement = '%0A' } + New-Object psobject -Property @{ Token = "]" ; Replacement = '%5D' } +) +# TODO: BUG: Escape % ??? +# TODO: Add test to verify don't need to escape "=". + +# Specify "-Force" to force pipeline formatted output even if "$ci" is false or not set +function Write-PipelineTelemetryError { + [CmdletBinding()] + param( + [Parameter(Mandatory = $true)] + [string]$Category, + [Parameter(Mandatory = $true)] + [string]$Message, + [Parameter(Mandatory = $false)] + [string]$Type = 'error', + [string]$ErrCode, + [string]$SourcePath, + [string]$LineNumber, + [string]$ColumnNumber, + [switch]$AsOutput, + [switch]$Force) + + $PSBoundParameters.Remove('Category') | Out-Null + + if ($Force -Or ((Test-Path variable:ci) -And $ci)) { + $Message = "(NETCORE_ENGINEERING_TELEMETRY=$Category) $Message" + } + $PSBoundParameters.Remove('Message') | Out-Null + $PSBoundParameters.Add('Message', $Message) + Write-PipelineTaskError @PSBoundParameters +} + +# Specify "-Force" to force pipeline formatted output even if "$ci" is false or not set +function Write-PipelineTaskError { + [CmdletBinding()] + param( + [Parameter(Mandatory = $true)] + [string]$Message, + [Parameter(Mandatory = $false)] + [string]$Type = 'error', + [string]$ErrCode, + [string]$SourcePath, + [string]$LineNumber, + [string]$ColumnNumber, + [switch]$AsOutput, + [switch]$Force + ) + + if (!$Force -And (-Not (Test-Path variable:ci) -Or !$ci)) { + if ($Type -eq 'error') { + Write-Host $Message -ForegroundColor Red + return + } + elseif ($Type -eq 'warning') { + Write-Host $Message -ForegroundColor Yellow + return + } + } + + if (($Type -ne 'error') -and ($Type -ne 'warning')) { + Write-Host $Message + return + } + $PSBoundParameters.Remove('Force') | Out-Null + if (-not $PSBoundParameters.ContainsKey('Type')) { + $PSBoundParameters.Add('Type', 'error') + } + Write-LogIssue @PSBoundParameters +} + +function Write-PipelineSetVariable { + [CmdletBinding()] + param( + [Parameter(Mandatory = $true)] + [string]$Name, + [string]$Value, + [switch]$Secret, + [switch]$AsOutput, + [bool]$IsMultiJobVariable = $true) + + if ((Test-Path variable:ci) -And $ci) { + Write-LoggingCommand -Area 'task' -Event 'setvariable' -Data $Value -Properties @{ + 'variable' = $Name + 'isSecret' = $Secret + 'isOutput' = $IsMultiJobVariable + } -AsOutput:$AsOutput + } +} + +function Write-PipelinePrependPath { + [CmdletBinding()] + param( + [Parameter(Mandatory = $true)] + [string]$Path, + [switch]$AsOutput) + + if ((Test-Path variable:ci) -And $ci) { + Write-LoggingCommand -Area 'task' -Event 'prependpath' -Data $Path -AsOutput:$AsOutput + } +} + +function Write-PipelineSetResult { + [CmdletBinding()] + param( + [ValidateSet("Succeeded", "SucceededWithIssues", "Failed", "Cancelled", "Skipped")] + [Parameter(Mandatory = $true)] + [string]$Result, + [string]$Message) + if ((Test-Path variable:ci) -And $ci) { + Write-LoggingCommand -Area 'task' -Event 'complete' -Data $Message -Properties @{ + 'result' = $Result + } + } +} + +<######################################## +# Private functions. +########################################> +function Format-LoggingCommandData { + [CmdletBinding()] + param([string]$Value, [switch]$Reverse) + + if (!$Value) { + return '' + } + + if (!$Reverse) { + foreach ($mapping in $script:loggingCommandEscapeMappings) { + $Value = $Value.Replace($mapping.Token, $mapping.Replacement) + } + } + else { + for ($i = $script:loggingCommandEscapeMappings.Length - 1 ; $i -ge 0 ; $i--) { + $mapping = $script:loggingCommandEscapeMappings[$i] + $Value = $Value.Replace($mapping.Replacement, $mapping.Token) + } + } + + return $Value +} + +function Format-LoggingCommand { + [CmdletBinding()] + param( + [Parameter(Mandatory = $true)] + [string]$Area, + [Parameter(Mandatory = $true)] + [string]$Event, + [string]$Data, + [hashtable]$Properties) + + # Append the preamble. + [System.Text.StringBuilder]$sb = New-Object -TypeName System.Text.StringBuilder + $null = $sb.Append($script:loggingCommandPrefix).Append($Area).Append('.').Append($Event) + + # Append the properties. + if ($Properties) { + $first = $true + foreach ($key in $Properties.Keys) { + [string]$value = Format-LoggingCommandData $Properties[$key] + if ($value) { + if ($first) { + $null = $sb.Append(' ') + $first = $false + } + else { + $null = $sb.Append(';') + } + + $null = $sb.Append("$key=$value") + } + } + } + + # Append the tail and output the value. + $Data = Format-LoggingCommandData $Data + $sb.Append(']').Append($Data).ToString() +} + +function Write-LoggingCommand { + [CmdletBinding(DefaultParameterSetName = 'Parameters')] + param( + [Parameter(Mandatory = $true, ParameterSetName = 'Parameters')] + [string]$Area, + [Parameter(Mandatory = $true, ParameterSetName = 'Parameters')] + [string]$Event, + [Parameter(ParameterSetName = 'Parameters')] + [string]$Data, + [Parameter(ParameterSetName = 'Parameters')] + [hashtable]$Properties, + [Parameter(Mandatory = $true, ParameterSetName = 'Object')] + $Command, + [switch]$AsOutput) + + if ($PSCmdlet.ParameterSetName -eq 'Object') { + Write-LoggingCommand -Area $Command.Area -Event $Command.Event -Data $Command.Data -Properties $Command.Properties -AsOutput:$AsOutput + return + } + + $command = Format-LoggingCommand -Area $Area -Event $Event -Data $Data -Properties $Properties + if ($AsOutput) { + $command + } + else { + Write-Host $command + } +} + +function Write-LogIssue { + [CmdletBinding()] + param( + [ValidateSet('warning', 'error')] + [Parameter(Mandatory = $true)] + [string]$Type, + [string]$Message, + [string]$ErrCode, + [string]$SourcePath, + [string]$LineNumber, + [string]$ColumnNumber, + [switch]$AsOutput) + + $command = Format-LoggingCommand -Area 'task' -Event 'logissue' -Data $Message -Properties @{ + 'type' = $Type + 'code' = $ErrCode + 'sourcepath' = $SourcePath + 'linenumber' = $LineNumber + 'columnnumber' = $ColumnNumber + } + if ($AsOutput) { + return $command + } + + if ($Type -eq 'error') { + $foregroundColor = $host.PrivateData.ErrorForegroundColor + $backgroundColor = $host.PrivateData.ErrorBackgroundColor + if ($foregroundColor -isnot [System.ConsoleColor] -or $backgroundColor -isnot [System.ConsoleColor]) { + $foregroundColor = [System.ConsoleColor]::Red + $backgroundColor = [System.ConsoleColor]::Black + } + } + else { + $foregroundColor = $host.PrivateData.WarningForegroundColor + $backgroundColor = $host.PrivateData.WarningBackgroundColor + if ($foregroundColor -isnot [System.ConsoleColor] -or $backgroundColor -isnot [System.ConsoleColor]) { + $foregroundColor = [System.ConsoleColor]::Yellow + $backgroundColor = [System.ConsoleColor]::Black + } + } + + Write-Host $command -ForegroundColor $foregroundColor -BackgroundColor $backgroundColor +} diff --git a/eng/common/pipeline-logging-functions.sh b/eng/common/pipeline-logging-functions.sh new file mode 100644 index 000000000..6a0b2255e --- /dev/null +++ b/eng/common/pipeline-logging-functions.sh @@ -0,0 +1,206 @@ +#!/usr/bin/env bash + +function Write-PipelineTelemetryError { + local telemetry_category='' + local force=false + local function_args=() + local message='' + while [[ $# -gt 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -category|-c) + telemetry_category=$2 + shift + ;; + -force|-f) + force=true + ;; + -*) + function_args+=("$1 $2") + shift + ;; + *) + message=$* + ;; + esac + shift + done + + if [[ $force != true ]] && [[ "$ci" != true ]]; then + echo "$message" >&2 + return + fi + + if [[ $force == true ]]; then + function_args+=("-force") + fi + message="(NETCORE_ENGINEERING_TELEMETRY=$telemetry_category) $message" + function_args+=("$message") + Write-PipelineTaskError ${function_args[@]} +} + +function Write-PipelineTaskError { + local message_type="error" + local sourcepath='' + local linenumber='' + local columnnumber='' + local error_code='' + local force=false + + while [[ $# -gt 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -type|-t) + message_type=$2 + shift + ;; + -sourcepath|-s) + sourcepath=$2 + shift + ;; + -linenumber|-ln) + linenumber=$2 + shift + ;; + -columnnumber|-cn) + columnnumber=$2 + shift + ;; + -errcode|-e) + error_code=$2 + shift + ;; + -force|-f) + force=true + ;; + *) + break + ;; + esac + + shift + done + + if [[ $force != true ]] && [[ "$ci" != true ]]; then + echo "$@" >&2 + return + fi + + local message="##vso[task.logissue" + + message="$message type=$message_type" + + if [ -n "$sourcepath" ]; then + message="$message;sourcepath=$sourcepath" + fi + + if [ -n "$linenumber" ]; then + message="$message;linenumber=$linenumber" + fi + + if [ -n "$columnnumber" ]; then + message="$message;columnnumber=$columnnumber" + fi + + if [ -n "$error_code" ]; then + message="$message;code=$error_code" + fi + + message="$message]$*" + echo "$message" +} + +function Write-PipelineSetVariable { + if [[ "$ci" != true ]]; then + return + fi + + local name='' + local value='' + local secret=false + local as_output=false + local is_multi_job_variable=true + + while [[ $# -gt 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -name|-n) + name=$2 + shift + ;; + -value|-v) + value=$2 + shift + ;; + -secret|-s) + secret=true + ;; + -as_output|-a) + as_output=true + ;; + -is_multi_job_variable|-i) + is_multi_job_variable=$2 + shift + ;; + esac + shift + done + + value=${value/;/%3B} + value=${value/\\r/%0D} + value=${value/\\n/%0A} + value=${value/]/%5D} + + local message="##vso[task.setvariable variable=$name;isSecret=$secret;isOutput=$is_multi_job_variable]$value" + + if [[ "$as_output" == true ]]; then + $message + else + echo "$message" + fi +} + +function Write-PipelinePrependPath { + local prepend_path='' + + while [[ $# -gt 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -path|-p) + prepend_path=$2 + shift + ;; + esac + shift + done + + export PATH="$prepend_path:$PATH" + + if [[ "$ci" == true ]]; then + echo "##vso[task.prependpath]$prepend_path" + fi +} + +function Write-PipelineSetResult { + local result='' + local message='' + + while [[ $# -gt 0 ]]; do + opt="$(echo "${1/#--/-}" | tr "[:upper:]" "[:lower:]")" + case "$opt" in + -result|-r) + result=$2 + shift + ;; + -message|-m) + message=$2 + shift + ;; + esac + shift + done + + if [[ "$ci" == true ]]; then + echo "##vso[task.complete result=$result;]$message" + fi +} diff --git a/eng/common/post-build/add-build-to-channel.ps1 b/eng/common/post-build/add-build-to-channel.ps1 new file mode 100644 index 000000000..de2d95792 --- /dev/null +++ b/eng/common/post-build/add-build-to-channel.ps1 @@ -0,0 +1,48 @@ +param( + [Parameter(Mandatory=$true)][int] $BuildId, + [Parameter(Mandatory=$true)][int] $ChannelId, + [Parameter(Mandatory=$true)][string] $MaestroApiAccessToken, + [Parameter(Mandatory=$false)][string] $MaestroApiEndPoint = 'https://maestro-prod.westus2.cloudapp.azure.com', + [Parameter(Mandatory=$false)][string] $MaestroApiVersion = '2019-01-16' +) + +try { + . $PSScriptRoot\post-build-utils.ps1 + + # Check that the channel we are going to promote the build to exist + $channelInfo = Get-MaestroChannel -ChannelId $ChannelId + + if (!$channelInfo) { + Write-PipelineTelemetryCategory -Category 'PromoteBuild' -Message "Channel with BAR ID $ChannelId was not found in BAR!" + ExitWithExitCode 1 + } + + # Get info about which channel(s) the build has already been promoted to + $buildInfo = Get-MaestroBuild -BuildId $BuildId + + if (!$buildInfo) { + Write-PipelineTelemetryError -Category 'PromoteBuild' -Message "Build with BAR ID $BuildId was not found in BAR!" + ExitWithExitCode 1 + } + + # Find whether the build is already assigned to the channel or not + if ($buildInfo.channels) { + foreach ($channel in $buildInfo.channels) { + if ($channel.Id -eq $ChannelId) { + Write-Host "The build with BAR ID $BuildId is already on channel $ChannelId!" + ExitWithExitCode 0 + } + } + } + + Write-Host "Promoting build '$BuildId' to channel '$ChannelId'." + + Assign-BuildToChannel -BuildId $BuildId -ChannelId $ChannelId + + Write-Host 'done.' +} +catch { + Write-Host $_ + Write-PipelineTelemetryError -Category 'PromoteBuild' -Message "There was an error while trying to promote build '$BuildId' to channel '$ChannelId'" + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/check-channel-consistency.ps1 b/eng/common/post-build/check-channel-consistency.ps1 new file mode 100644 index 000000000..63f3464c9 --- /dev/null +++ b/eng/common/post-build/check-channel-consistency.ps1 @@ -0,0 +1,40 @@ +param( + [Parameter(Mandatory=$true)][string] $PromoteToChannels, # List of channels that the build should be promoted to + [Parameter(Mandatory=$true)][array] $AvailableChannelIds # List of channel IDs available in the YAML implementation +) + +try { + . $PSScriptRoot\post-build-utils.ps1 + + if ($PromoteToChannels -eq "") { + Write-PipelineTaskError -Type 'warning' -Message "This build won't publish assets as it's not configured to any Maestro channel. If that wasn't intended use Darc to configure a default channel using add-default-channel for this branch or to promote it to a channel using add-build-to-channel. See https://github.com/dotnet/arcade/blob/master/Documentation/Darc.md#assigning-an-individual-build-to-a-channel for more info." + ExitWithExitCode 0 + } + + # Check that every channel that Maestro told to promote the build to + # is available in YAML + $PromoteToChannelsIds = $PromoteToChannels -split "\D" | Where-Object { $_ } + + $hasErrors = $false + + foreach ($id in $PromoteToChannelsIds) { + if (($id -ne 0) -and ($id -notin $AvailableChannelIds)) { + Write-PipelineTaskError -Message "Channel $id is not present in the post-build YAML configuration! This is an error scenario. Please contact @dnceng." + $hasErrors = $true + } + } + + # The `Write-PipelineTaskError` doesn't error the script and we might report several errors + # in the previous lines. The check below makes sure that we return an error state from the + # script if we reported any validation error + if ($hasErrors) { + ExitWithExitCode 1 + } + + Write-Host 'done.' +} +catch { + Write-Host $_ + Write-PipelineTelemetryError -Category 'CheckChannelConsistency' -Message "There was an error while trying to check consistency of Maestro default channels for the build and post-build YAML configuration." + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/nuget-validation.ps1 b/eng/common/post-build/nuget-validation.ps1 new file mode 100644 index 000000000..dab3534ab --- /dev/null +++ b/eng/common/post-build/nuget-validation.ps1 @@ -0,0 +1,24 @@ +# This script validates NuGet package metadata information using this +# tool: https://github.com/NuGet/NuGetGallery/tree/jver-verify/src/VerifyMicrosoftPackage + +param( + [Parameter(Mandatory=$true)][string] $PackagesPath, # Path to where the packages to be validated are + [Parameter(Mandatory=$true)][string] $ToolDestinationPath # Where the validation tool should be downloaded to +) + +try { + . $PSScriptRoot\post-build-utils.ps1 + + $url = 'https://raw.githubusercontent.com/NuGet/NuGetGallery/3e25ad135146676bcab0050a516939d9958bfa5d/src/VerifyMicrosoftPackage/verify.ps1' + + New-Item -ItemType 'directory' -Path ${ToolDestinationPath} -Force + + Invoke-WebRequest $url -OutFile ${ToolDestinationPath}\verify.ps1 + + & ${ToolDestinationPath}\verify.ps1 ${PackagesPath}\*.nupkg +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'NuGetValidation' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/post-build-utils.ps1 b/eng/common/post-build/post-build-utils.ps1 new file mode 100644 index 000000000..534f6988d --- /dev/null +++ b/eng/common/post-build/post-build-utils.ps1 @@ -0,0 +1,91 @@ +# Most of the functions in this file require the variables `MaestroApiEndPoint`, +# `MaestroApiVersion` and `MaestroApiAccessToken` to be globally available. + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 + +# `tools.ps1` checks $ci to perform some actions. Since the post-build +# scripts don't necessarily execute in the same agent that run the +# build.ps1/sh script this variable isn't automatically set. +$ci = $true +$disableConfigureToolsetImport = $true +. $PSScriptRoot\..\tools.ps1 + +function Create-MaestroApiRequestHeaders([string]$ContentType = 'application/json') { + Validate-MaestroVars + + $headers = New-Object 'System.Collections.Generic.Dictionary[[String],[String]]' + $headers.Add('Accept', $ContentType) + $headers.Add('Authorization',"Bearer $MaestroApiAccessToken") + return $headers +} + +function Get-MaestroChannel([int]$ChannelId) { + Validate-MaestroVars + + $apiHeaders = Create-MaestroApiRequestHeaders + $apiEndpoint = "$MaestroApiEndPoint/api/channels/${ChannelId}?api-version=$MaestroApiVersion" + + $result = try { Invoke-WebRequest -Method Get -Uri $apiEndpoint -Headers $apiHeaders | ConvertFrom-Json } catch { Write-Host "Error: $_" } + return $result +} + +function Get-MaestroBuild([int]$BuildId) { + Validate-MaestroVars + + $apiHeaders = Create-MaestroApiRequestHeaders -AuthToken $MaestroApiAccessToken + $apiEndpoint = "$MaestroApiEndPoint/api/builds/${BuildId}?api-version=$MaestroApiVersion" + + $result = try { return Invoke-WebRequest -Method Get -Uri $apiEndpoint -Headers $apiHeaders | ConvertFrom-Json } catch { Write-Host "Error: $_" } + return $result +} + +function Get-MaestroSubscriptions([string]$SourceRepository, [int]$ChannelId) { + Validate-MaestroVars + + $SourceRepository = [System.Web.HttpUtility]::UrlEncode($SourceRepository) + $apiHeaders = Create-MaestroApiRequestHeaders -AuthToken $MaestroApiAccessToken + $apiEndpoint = "$MaestroApiEndPoint/api/subscriptions?sourceRepository=$SourceRepository&channelId=$ChannelId&api-version=$MaestroApiVersion" + + $result = try { Invoke-WebRequest -Method Get -Uri $apiEndpoint -Headers $apiHeaders | ConvertFrom-Json } catch { Write-Host "Error: $_" } + return $result +} + +function Assign-BuildToChannel([int]$BuildId, [int]$ChannelId) { + Validate-MaestroVars + + $apiHeaders = Create-MaestroApiRequestHeaders -AuthToken $MaestroApiAccessToken + $apiEndpoint = "$MaestroApiEndPoint/api/channels/${ChannelId}/builds/${BuildId}?api-version=$MaestroApiVersion" + Invoke-WebRequest -Method Post -Uri $apiEndpoint -Headers $apiHeaders | Out-Null +} + +function Trigger-Subscription([string]$SubscriptionId) { + Validate-MaestroVars + + $apiHeaders = Create-MaestroApiRequestHeaders -AuthToken $MaestroApiAccessToken + $apiEndpoint = "$MaestroApiEndPoint/api/subscriptions/$SubscriptionId/trigger?api-version=$MaestroApiVersion" + Invoke-WebRequest -Uri $apiEndpoint -Headers $apiHeaders -Method Post | Out-Null +} + +function Validate-MaestroVars { + try { + Get-Variable MaestroApiEndPoint | Out-Null + Get-Variable MaestroApiVersion | Out-Null + Get-Variable MaestroApiAccessToken | Out-Null + + if (!($MaestroApiEndPoint -Match '^http[s]?://maestro-(int|prod).westus2.cloudapp.azure.com$')) { + Write-PipelineTelemetryError -Category 'MaestroVars' -Message "MaestroApiEndPoint is not a valid Maestro URL. '$MaestroApiEndPoint'" + ExitWithExitCode 1 + } + + if (!($MaestroApiVersion -Match '^[0-9]{4}-[0-9]{2}-[0-9]{2}$')) { + Write-PipelineTelemetryError -Category 'MaestroVars' -Message "MaestroApiVersion does not match a version string in the format yyyy-MM-DD. '$MaestroApiVersion'" + ExitWithExitCode 1 + } + } + catch { + Write-PipelineTelemetryError -Category 'MaestroVars' -Message 'Error: Variables `MaestroApiEndPoint`, `MaestroApiVersion` and `MaestroApiAccessToken` are required while using this script.' + Write-Host $_ + ExitWithExitCode 1 + } +} diff --git a/eng/common/post-build/publish-using-darc.ps1 b/eng/common/post-build/publish-using-darc.ps1 new file mode 100644 index 000000000..2427ca6b6 --- /dev/null +++ b/eng/common/post-build/publish-using-darc.ps1 @@ -0,0 +1,80 @@ +param( + [Parameter(Mandatory=$true)][int] $BuildId, + [Parameter(Mandatory=$true)][int] $PublishingInfraVersion, + [Parameter(Mandatory=$true)][string] $AzdoToken, + [Parameter(Mandatory=$true)][string] $MaestroToken, + [Parameter(Mandatory=$false)][string] $MaestroApiEndPoint = 'https://maestro-prod.westus2.cloudapp.azure.com', + [Parameter(Mandatory=$true)][string] $WaitPublishingFinish, + [Parameter(Mandatory=$false)][string] $EnableSourceLinkValidation, + [Parameter(Mandatory=$false)][string] $EnableSigningValidation, + [Parameter(Mandatory=$false)][string] $EnableNugetValidation, + [Parameter(Mandatory=$false)][string] $PublishInstallersAndChecksums, + [Parameter(Mandatory=$false)][string] $ArtifactsPublishingAdditionalParameters, + [Parameter(Mandatory=$false)][string] $SymbolPublishingAdditionalParameters, + [Parameter(Mandatory=$false)][string] $SigningValidationAdditionalParameters +) + +try { + . $PSScriptRoot\post-build-utils.ps1 + + $darc = Get-Darc + + $optionalParams = [System.Collections.ArrayList]::new() + + if ("" -ne $ArtifactsPublishingAdditionalParameters) { + $optionalParams.Add("--artifact-publishing-parameters") | Out-Null + $optionalParams.Add($ArtifactsPublishingAdditionalParameters) | Out-Null + } + + if ("" -ne $SymbolPublishingAdditionalParameters) { + $optionalParams.Add("--symbol-publishing-parameters") | Out-Null + $optionalParams.Add($SymbolPublishingAdditionalParameters) | Out-Null + } + + if ("false" -eq $WaitPublishingFinish) { + $optionalParams.Add("--no-wait") | Out-Null + } + + if ("false" -ne $PublishInstallersAndChecksums) { + $optionalParams.Add("--publish-installers-and-checksums") | Out-Null + } + + if ("true" -eq $EnableNugetValidation) { + $optionalParams.Add("--validate-nuget") | Out-Null + } + + if ("true" -eq $EnableSourceLinkValidation) { + $optionalParams.Add("--validate-sourcelinkchecksums") | Out-Null + } + + if ("true" -eq $EnableSigningValidation) { + $optionalParams.Add("--validate-signingchecksums") | Out-Null + + if ("" -ne $SigningValidationAdditionalParameters) { + $optionalParams.Add("--signing-validation-parameters") | Out-Null + $optionalParams.Add($SigningValidationAdditionalParameters) | Out-Null + } + } + + & $darc add-build-to-channel ` + --id $buildId ` + --publishing-infra-version $PublishingInfraVersion ` + --default-channels ` + --source-branch main ` + --azdev-pat $AzdoToken ` + --bar-uri $MaestroApiEndPoint ` + --password $MaestroToken ` + @optionalParams + + if ($LastExitCode -ne 0) { + Write-Host "Problems using Darc to promote build ${buildId} to default channels. Stopping execution..." + exit 1 + } + + Write-Host 'done.' +} +catch { + Write-Host $_ + Write-PipelineTelemetryError -Category 'PromoteBuild' -Message "There was an error while trying to publish build '$BuildId' to default channels." + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/sourcelink-validation.ps1 b/eng/common/post-build/sourcelink-validation.ps1 new file mode 100644 index 000000000..85c898617 --- /dev/null +++ b/eng/common/post-build/sourcelink-validation.ps1 @@ -0,0 +1,303 @@ +param( + [Parameter(Mandatory=$true)][string] $InputPath, # Full path to directory where Symbols.NuGet packages to be checked are stored + [Parameter(Mandatory=$true)][string] $ExtractPath, # Full path to directory where the packages will be extracted during validation + [Parameter(Mandatory=$false)][string] $GHRepoName, # GitHub name of the repo including the Org. E.g., dotnet/arcade + [Parameter(Mandatory=$false)][string] $GHCommit, # GitHub commit SHA used to build the packages + [Parameter(Mandatory=$true)][string] $SourcelinkCliVersion # Version of SourceLink CLI to use +) + +. $PSScriptRoot\post-build-utils.ps1 + +# Cache/HashMap (File -> Exist flag) used to consult whether a file exist +# in the repository at a specific commit point. This is populated by inserting +# all files present in the repo at a specific commit point. +$global:RepoFiles = @{} + +# Maximum number of jobs to run in parallel +$MaxParallelJobs = 16 + +$MaxRetries = 5 + +# Wait time between check for system load +$SecondsBetweenLoadChecks = 10 + +$ValidatePackage = { + param( + [string] $PackagePath # Full path to a Symbols.NuGet package + ) + + . $using:PSScriptRoot\..\tools.ps1 + + # Ensure input file exist + if (!(Test-Path $PackagePath)) { + Write-Host "Input file does not exist: $PackagePath" + return [pscustomobject]@{ + result = 1 + packagePath = $PackagePath + } + } + + # Extensions for which we'll look for SourceLink information + # For now we'll only care about Portable & Embedded PDBs + $RelevantExtensions = @('.dll', '.exe', '.pdb') + + Write-Host -NoNewLine 'Validating ' ([System.IO.Path]::GetFileName($PackagePath)) '...' + + $PackageId = [System.IO.Path]::GetFileNameWithoutExtension($PackagePath) + $ExtractPath = Join-Path -Path $using:ExtractPath -ChildPath $PackageId + $FailedFiles = 0 + + Add-Type -AssemblyName System.IO.Compression.FileSystem + + [System.IO.Directory]::CreateDirectory($ExtractPath) | Out-Null + + try { + $zip = [System.IO.Compression.ZipFile]::OpenRead($PackagePath) + + $zip.Entries | + Where-Object {$RelevantExtensions -contains [System.IO.Path]::GetExtension($_.Name)} | + ForEach-Object { + $FileName = $_.FullName + $Extension = [System.IO.Path]::GetExtension($_.Name) + $FakeName = -Join((New-Guid), $Extension) + $TargetFile = Join-Path -Path $ExtractPath -ChildPath $FakeName + + # We ignore resource DLLs + if ($FileName.EndsWith('.resources.dll')) { + return [pscustomobject]@{ + result = 0 + packagePath = $PackagePath + } + } + + [System.IO.Compression.ZipFileExtensions]::ExtractToFile($_, $TargetFile, $true) + + $ValidateFile = { + param( + [string] $FullPath, # Full path to the module that has to be checked + [string] $RealPath, + [ref] $FailedFiles + ) + + $sourcelinkExe = "$env:USERPROFILE\.dotnet\tools" + $sourcelinkExe = Resolve-Path "$sourcelinkExe\sourcelink.exe" + $SourceLinkInfos = & $sourcelinkExe print-urls $FullPath | Out-String + + if ($LASTEXITCODE -eq 0 -and -not ([string]::IsNullOrEmpty($SourceLinkInfos))) { + $NumFailedLinks = 0 + + # We only care about Http addresses + $Matches = (Select-String '(http[s]?)(:\/\/)([^\s,]+)' -Input $SourceLinkInfos -AllMatches).Matches + + if ($Matches.Count -ne 0) { + $Matches.Value | + ForEach-Object { + $Link = $_ + $CommitUrl = "https://raw.githubusercontent.com/${using:GHRepoName}/${using:GHCommit}/" + + $FilePath = $Link.Replace($CommitUrl, "") + $Status = 200 + $Cache = $using:RepoFiles + + $totalRetries = 0 + + while ($totalRetries -lt $using:MaxRetries) { + if ( !($Cache.ContainsKey($FilePath)) ) { + try { + $Uri = $Link -as [System.URI] + + # Only GitHub links are valid + if ($Uri.AbsoluteURI -ne $null -and ($Uri.Host -match 'github' -or $Uri.Host -match 'githubusercontent')) { + $Status = (Invoke-WebRequest -Uri $Link -UseBasicParsing -Method HEAD -TimeoutSec 5).StatusCode + } + else { + # If it's not a github link, we want to break out of the loop and not retry. + $Status = 0 + $totalRetries = $using:MaxRetries + } + } + catch { + Write-Host $_ + $Status = 0 + } + } + + if ($Status -ne 200) { + $totalRetries++ + + if ($totalRetries -ge $using:MaxRetries) { + if ($NumFailedLinks -eq 0) { + if ($FailedFiles.Value -eq 0) { + Write-Host + } + + Write-Host "`tFile $RealPath has broken links:" + } + + Write-Host "`t`tFailed to retrieve $Link" + + $NumFailedLinks++ + } + } + else { + break + } + } + } + } + + if ($NumFailedLinks -ne 0) { + $FailedFiles.value++ + $global:LASTEXITCODE = 1 + } + } + } + + &$ValidateFile $TargetFile $FileName ([ref]$FailedFiles) + } + } + catch { + Write-Host $_ + } + finally { + $zip.Dispose() + } + + if ($FailedFiles -eq 0) { + Write-Host 'Passed.' + return [pscustomobject]@{ + result = 0 + packagePath = $PackagePath + } + } + else { + Write-PipelineTelemetryError -Category 'SourceLink' -Message "$PackagePath has broken SourceLink links." + return [pscustomobject]@{ + result = 1 + packagePath = $PackagePath + } + } +} + +function CheckJobResult( + $result, + $packagePath, + [ref]$ValidationFailures, + [switch]$logErrors) { + if ($result -ne '0') { + if ($logErrors) { + Write-PipelineTelemetryError -Category 'SourceLink' -Message "$packagePath has broken SourceLink links." + } + $ValidationFailures.Value++ + } +} + +function ValidateSourceLinkLinks { + if ($GHRepoName -ne '' -and !($GHRepoName -Match '^[^\s\/]+/[^\s\/]+$')) { + if (!($GHRepoName -Match '^[^\s-]+-[^\s]+$')) { + Write-PipelineTelemetryError -Category 'SourceLink' -Message "GHRepoName should be in the format / or -. '$GHRepoName'" + ExitWithExitCode 1 + } + else { + $GHRepoName = $GHRepoName -replace '^([^\s-]+)-([^\s]+)$', '$1/$2'; + } + } + + if ($GHCommit -ne '' -and !($GHCommit -Match '^[0-9a-fA-F]{40}$')) { + Write-PipelineTelemetryError -Category 'SourceLink' -Message "GHCommit should be a 40 chars hexadecimal string. '$GHCommit'" + ExitWithExitCode 1 + } + + if ($GHRepoName -ne '' -and $GHCommit -ne '') { + $RepoTreeURL = -Join('http://api.github.com/repos/', $GHRepoName, '/git/trees/', $GHCommit, '?recursive=1') + $CodeExtensions = @('.cs', '.vb', '.fs', '.fsi', '.fsx', '.fsscript') + + try { + # Retrieve the list of files in the repo at that particular commit point and store them in the RepoFiles hash + $Data = Invoke-WebRequest $RepoTreeURL -UseBasicParsing | ConvertFrom-Json | Select-Object -ExpandProperty tree + + foreach ($file in $Data) { + $Extension = [System.IO.Path]::GetExtension($file.path) + + if ($CodeExtensions.Contains($Extension)) { + $RepoFiles[$file.path] = 1 + } + } + } + catch { + Write-Host "Problems downloading the list of files from the repo. Url used: $RepoTreeURL . Execution will proceed without caching." + } + } + elseif ($GHRepoName -ne '' -or $GHCommit -ne '') { + Write-Host 'For using the http caching mechanism both GHRepoName and GHCommit should be informed.' + } + + if (Test-Path $ExtractPath) { + Remove-Item $ExtractPath -Force -Recurse -ErrorAction SilentlyContinue + } + + $ValidationFailures = 0 + + # Process each NuGet package in parallel + Get-ChildItem "$InputPath\*.symbols.nupkg" | + ForEach-Object { + Write-Host "Starting $($_.FullName)" + Start-Job -ScriptBlock $ValidatePackage -ArgumentList $_.FullName | Out-Null + $NumJobs = @(Get-Job -State 'Running').Count + + while ($NumJobs -ge $MaxParallelJobs) { + Write-Host "There are $NumJobs validation jobs running right now. Waiting $SecondsBetweenLoadChecks seconds to check again." + sleep $SecondsBetweenLoadChecks + $NumJobs = @(Get-Job -State 'Running').Count + } + + foreach ($Job in @(Get-Job -State 'Completed')) { + $jobResult = Wait-Job -Id $Job.Id | Receive-Job + CheckJobResult $jobResult.result $jobResult.packagePath ([ref]$ValidationFailures) -LogErrors + Remove-Job -Id $Job.Id + } + } + + foreach ($Job in @(Get-Job)) { + $jobResult = Wait-Job -Id $Job.Id | Receive-Job + CheckJobResult $jobResult.result $jobResult.packagePath ([ref]$ValidationFailures) + Remove-Job -Id $Job.Id + } + if ($ValidationFailures -gt 0) { + Write-PipelineTelemetryError -Category 'SourceLink' -Message "$ValidationFailures package(s) failed validation." + ExitWithExitCode 1 + } +} + +function InstallSourcelinkCli { + $sourcelinkCliPackageName = 'sourcelink' + + $dotnetRoot = InitializeDotNetCli -install:$true + $dotnet = "$dotnetRoot\dotnet.exe" + $toolList = & "$dotnet" tool list --global + + if (($toolList -like "*$sourcelinkCliPackageName*") -and ($toolList -like "*$sourcelinkCliVersion*")) { + Write-Host "SourceLink CLI version $sourcelinkCliVersion is already installed." + } + else { + Write-Host "Installing SourceLink CLI version $sourcelinkCliVersion..." + Write-Host 'You may need to restart your command window if this is the first dotnet tool you have installed.' + & "$dotnet" tool install $sourcelinkCliPackageName --version $sourcelinkCliVersion --verbosity "minimal" --global + } +} + +try { + InstallSourcelinkCli + + foreach ($Job in @(Get-Job)) { + Remove-Job -Id $Job.Id + } + + ValidateSourceLinkLinks +} +catch { + Write-Host $_.Exception + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'SourceLink' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/symbols-validation.ps1 b/eng/common/post-build/symbols-validation.ps1 new file mode 100644 index 000000000..a5af041ba --- /dev/null +++ b/eng/common/post-build/symbols-validation.ps1 @@ -0,0 +1,316 @@ +param( + [Parameter(Mandatory = $true)][string] $InputPath, # Full path to directory where NuGet packages to be checked are stored + [Parameter(Mandatory = $true)][string] $ExtractPath, # Full path to directory where the packages will be extracted during validation + [Parameter(Mandatory = $true)][string] $DotnetSymbolVersion, # Version of dotnet symbol to use + [Parameter(Mandatory = $false)][switch] $CheckForWindowsPdbs, # If we should check for the existence of windows pdbs in addition to portable PDBs + [Parameter(Mandatory = $false)][switch] $ContinueOnError, # If we should keep checking symbols after an error + [Parameter(Mandatory = $false)][switch] $Clean # Clean extracted symbols directory after checking symbols +) + +# Maximum number of jobs to run in parallel +$MaxParallelJobs = 16 + +# Max number of retries +$MaxRetry = 5 + +# Wait time between check for system load +$SecondsBetweenLoadChecks = 10 + +# Set error codes +Set-Variable -Name "ERROR_BADEXTRACT" -Option Constant -Value -1 +Set-Variable -Name "ERROR_FILEDOESNOTEXIST" -Option Constant -Value -2 + +$WindowsPdbVerificationParam = "" +if ($CheckForWindowsPdbs) { + $WindowsPdbVerificationParam = "--windows-pdbs" +} + +$CountMissingSymbols = { + param( + [string] $PackagePath, # Path to a NuGet package + [string] $WindowsPdbVerificationParam # If we should check for the existence of windows pdbs in addition to portable PDBs + ) + + . $using:PSScriptRoot\..\tools.ps1 + + Add-Type -AssemblyName System.IO.Compression.FileSystem + + Write-Host "Validating $PackagePath " + + # Ensure input file exist + if (!(Test-Path $PackagePath)) { + Write-PipelineTaskError "Input file does not exist: $PackagePath" + return [pscustomobject]@{ + result = $using:ERROR_FILEDOESNOTEXIST + packagePath = $PackagePath + } + } + + # Extensions for which we'll look for symbols + $RelevantExtensions = @('.dll', '.exe', '.so', '.dylib') + + # How many files are missing symbol information + $MissingSymbols = 0 + + $PackageId = [System.IO.Path]::GetFileNameWithoutExtension($PackagePath) + $PackageGuid = New-Guid + $ExtractPath = Join-Path -Path $using:ExtractPath -ChildPath $PackageGuid + $SymbolsPath = Join-Path -Path $ExtractPath -ChildPath 'Symbols' + + try { + [System.IO.Compression.ZipFile]::ExtractToDirectory($PackagePath, $ExtractPath) + } + catch { + Write-Host "Something went wrong extracting $PackagePath" + Write-Host $_ + return [pscustomobject]@{ + result = $using:ERROR_BADEXTRACT + packagePath = $PackagePath + } + } + + Get-ChildItem -Recurse $ExtractPath | + Where-Object { $RelevantExtensions -contains $_.Extension } | + ForEach-Object { + $FileName = $_.FullName + if ($FileName -Match '\\ref\\') { + Write-Host "`t Ignoring reference assembly file " $FileName + return + } + + $FirstMatchingSymbolDescriptionOrDefault = { + param( + [string] $FullPath, # Full path to the module that has to be checked + [string] $TargetServerParam, # Parameter to pass to `Symbol Tool` indicating the server to lookup for symbols + [string] $WindowsPdbVerificationParam, # Parameter to pass to potential check for windows-pdbs. + [string] $SymbolsPath + ) + + $FileName = [System.IO.Path]::GetFileName($FullPath) + $Extension = [System.IO.Path]::GetExtension($FullPath) + + # Those below are potential symbol files that the `dotnet symbol` might + # return. Which one will be returned depend on the type of file we are + # checking and which type of file was uploaded. + + # The file itself is returned + $SymbolPath = $SymbolsPath + '\' + $FileName + + # PDB file for the module + $PdbPath = $SymbolPath.Replace($Extension, '.pdb') + + # PDB file for R2R module (created by crossgen) + $NGenPdb = $SymbolPath.Replace($Extension, '.ni.pdb') + + # DBG file for a .so library + $SODbg = $SymbolPath.Replace($Extension, '.so.dbg') + + # DWARF file for a .dylib + $DylibDwarf = $SymbolPath.Replace($Extension, '.dylib.dwarf') + + $dotnetSymbolExe = "$env:USERPROFILE\.dotnet\tools" + $dotnetSymbolExe = Resolve-Path "$dotnetSymbolExe\dotnet-symbol.exe" + + $totalRetries = 0 + + while ($totalRetries -lt $using:MaxRetry) { + + # Save the output and get diagnostic output + $output = & $dotnetSymbolExe --symbols --modules $WindowsPdbVerificationParam $TargetServerParam $FullPath -o $SymbolsPath --diagnostics | Out-String + + if (Test-Path $PdbPath) { + return 'PDB' + } + elseif (Test-Path $NGenPdb) { + return 'NGen PDB' + } + elseif (Test-Path $SODbg) { + return 'DBG for SO' + } + elseif (Test-Path $DylibDwarf) { + return 'Dwarf for Dylib' + } + elseif (Test-Path $SymbolPath) { + return 'Module' + } + else + { + $totalRetries++ + } + } + + return $null + } + + $FileGuid = New-Guid + $ExpandedSymbolsPath = Join-Path -Path $SymbolsPath -ChildPath $FileGuid + + $SymbolsOnMSDL = & $FirstMatchingSymbolDescriptionOrDefault ` + -FullPath $FileName ` + -TargetServerParam '--microsoft-symbol-server' ` + -SymbolsPath "$ExpandedSymbolsPath-msdl" ` + -WindowsPdbVerificationParam $WindowsPdbVerificationParam + $SymbolsOnSymWeb = & $FirstMatchingSymbolDescriptionOrDefault ` + -FullPath $FileName ` + -TargetServerParam '--internal-server' ` + -SymbolsPath "$ExpandedSymbolsPath-symweb" ` + -WindowsPdbVerificationParam $WindowsPdbVerificationParam + + Write-Host -NoNewLine "`t Checking file " $FileName "... " + + if ($SymbolsOnMSDL -ne $null -and $SymbolsOnSymWeb -ne $null) { + Write-Host "Symbols found on MSDL ($SymbolsOnMSDL) and SymWeb ($SymbolsOnSymWeb)" + } + else { + $MissingSymbols++ + + if ($SymbolsOnMSDL -eq $null -and $SymbolsOnSymWeb -eq $null) { + Write-Host 'No symbols found on MSDL or SymWeb!' + } + else { + if ($SymbolsOnMSDL -eq $null) { + Write-Host 'No symbols found on MSDL!' + } + else { + Write-Host 'No symbols found on SymWeb!' + } + } + } + } + + if ($using:Clean) { + Remove-Item $ExtractPath -Recurse -Force + } + + Pop-Location + + return [pscustomobject]@{ + result = $MissingSymbols + packagePath = $PackagePath + } +} + +function CheckJobResult( + $result, + $packagePath, + [ref]$DupedSymbols, + [ref]$TotalFailures) { + if ($result -eq $ERROR_BADEXTRACT) { + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message "$packagePath has duplicated symbol files" + $DupedSymbols.Value++ + } + elseif ($result -eq $ERROR_FILEDOESNOTEXIST) { + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message "$packagePath does not exist" + $TotalFailures.Value++ + } + elseif ($result -gt '0') { + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message "Missing symbols for $result modules in the package $packagePath" + $TotalFailures.Value++ + } + else { + Write-Host "All symbols verified for package $packagePath" + } +} + +function CheckSymbolsAvailable { + if (Test-Path $ExtractPath) { + Remove-Item $ExtractPath -Force -Recurse -ErrorAction SilentlyContinue + } + + $TotalPackages = 0 + $TotalFailures = 0 + $DupedSymbols = 0 + + Get-ChildItem "$InputPath\*.nupkg" | + ForEach-Object { + $FileName = $_.Name + $FullName = $_.FullName + + # These packages from Arcade-Services include some native libraries that + # our current symbol uploader can't handle. Below is a workaround until + # we get issue: https://github.com/dotnet/arcade/issues/2457 sorted. + if ($FileName -Match 'Microsoft\.DotNet\.Darc\.') { + Write-Host "Ignoring Arcade-services file: $FileName" + Write-Host + return + } + elseif ($FileName -Match 'Microsoft\.DotNet\.Maestro\.Tasks\.') { + Write-Host "Ignoring Arcade-services file: $FileName" + Write-Host + return + } + + $TotalPackages++ + + Start-Job -ScriptBlock $CountMissingSymbols -ArgumentList @($FullName,$WindowsPdbVerificationParam) | Out-Null + + $NumJobs = @(Get-Job -State 'Running').Count + + while ($NumJobs -ge $MaxParallelJobs) { + Write-Host "There are $NumJobs validation jobs running right now. Waiting $SecondsBetweenLoadChecks seconds to check again." + sleep $SecondsBetweenLoadChecks + $NumJobs = @(Get-Job -State 'Running').Count + } + + foreach ($Job in @(Get-Job -State 'Completed')) { + $jobResult = Wait-Job -Id $Job.Id | Receive-Job + CheckJobResult $jobResult.result $jobResult.packagePath ([ref]$DupedSymbols) ([ref]$TotalFailures) + Remove-Job -Id $Job.Id + } + Write-Host + } + + foreach ($Job in @(Get-Job)) { + $jobResult = Wait-Job -Id $Job.Id | Receive-Job + CheckJobResult $jobResult.result $jobResult.packagePath ([ref]$DupedSymbols) ([ref]$TotalFailures) + } + + if ($TotalFailures -gt 0 -or $DupedSymbols -gt 0) { + if ($TotalFailures -gt 0) { + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message "Symbols missing for $TotalFailures/$TotalPackages packages" + } + + if ($DupedSymbols -gt 0) { + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message "$DupedSymbols/$TotalPackages packages had duplicated symbol files and could not be extracted" + } + + ExitWithExitCode 1 + } + else { + Write-Host "All symbols validated!" + } +} + +function InstallDotnetSymbol { + $dotnetSymbolPackageName = 'dotnet-symbol' + + $dotnetRoot = InitializeDotNetCli -install:$true + $dotnet = "$dotnetRoot\dotnet.exe" + $toolList = & "$dotnet" tool list --global + + if (($toolList -like "*$dotnetSymbolPackageName*") -and ($toolList -like "*$dotnetSymbolVersion*")) { + Write-Host "dotnet-symbol version $dotnetSymbolVersion is already installed." + } + else { + Write-Host "Installing dotnet-symbol version $dotnetSymbolVersion..." + Write-Host 'You may need to restart your command window if this is the first dotnet tool you have installed.' + & "$dotnet" tool install $dotnetSymbolPackageName --version $dotnetSymbolVersion --verbosity "minimal" --global + } +} + +try { + . $PSScriptRoot\post-build-utils.ps1 + + InstallDotnetSymbol + + foreach ($Job in @(Get-Job)) { + Remove-Job -Id $Job.Id + } + + CheckSymbolsAvailable +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'CheckSymbols' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/post-build/trigger-subscriptions.ps1 b/eng/common/post-build/trigger-subscriptions.ps1 new file mode 100644 index 000000000..55dea518a --- /dev/null +++ b/eng/common/post-build/trigger-subscriptions.ps1 @@ -0,0 +1,64 @@ +param( + [Parameter(Mandatory=$true)][string] $SourceRepo, + [Parameter(Mandatory=$true)][int] $ChannelId, + [Parameter(Mandatory=$true)][string] $MaestroApiAccessToken, + [Parameter(Mandatory=$false)][string] $MaestroApiEndPoint = 'https://maestro-prod.westus2.cloudapp.azure.com', + [Parameter(Mandatory=$false)][string] $MaestroApiVersion = '2019-01-16' +) + +try { + . $PSScriptRoot\post-build-utils.ps1 + + # Get all the $SourceRepo subscriptions + $normalizedSourceRepo = $SourceRepo.Replace('dnceng@', '') + $subscriptions = Get-MaestroSubscriptions -SourceRepository $normalizedSourceRepo -ChannelId $ChannelId + + if (!$subscriptions) { + Write-PipelineTelemetryError -Category 'TriggerSubscriptions' -Message "No subscriptions found for source repo '$normalizedSourceRepo' in channel '$ChannelId'" + ExitWithExitCode 0 + } + + $subscriptionsToTrigger = New-Object System.Collections.Generic.List[string] + $failedTriggeredSubscription = $false + + # Get all enabled subscriptions that need dependency flow on 'everyBuild' + foreach ($subscription in $subscriptions) { + if ($subscription.enabled -and $subscription.policy.updateFrequency -like 'everyBuild' -and $subscription.channel.id -eq $ChannelId) { + Write-Host "Should trigger this subscription: ${$subscription.id}" + [void]$subscriptionsToTrigger.Add($subscription.id) + } + } + + foreach ($subscriptionToTrigger in $subscriptionsToTrigger) { + try { + Write-Host "Triggering subscription '$subscriptionToTrigger'." + + Trigger-Subscription -SubscriptionId $subscriptionToTrigger + + Write-Host 'done.' + } + catch + { + Write-Host "There was an error while triggering subscription '$subscriptionToTrigger'" + Write-Host $_ + Write-Host $_.ScriptStackTrace + $failedTriggeredSubscription = $true + } + } + + if ($subscriptionsToTrigger.Count -eq 0) { + Write-Host "No subscription matched source repo '$normalizedSourceRepo' and channel ID '$ChannelId'." + } + elseif ($failedTriggeredSubscription) { + Write-PipelineTelemetryError -Category 'TriggerSubscriptions' -Message 'At least one subscription failed to be triggered...' + ExitWithExitCode 1 + } + else { + Write-Host 'All subscriptions were triggered successfully!' + } +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'TriggerSubscriptions' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/sdk-task.ps1 b/eng/common/sdk-task.ps1 new file mode 100644 index 000000000..b1bca63ab --- /dev/null +++ b/eng/common/sdk-task.ps1 @@ -0,0 +1,97 @@ +[CmdletBinding(PositionalBinding=$false)] +Param( + [string] $configuration = 'Debug', + [string] $task, + [string] $verbosity = 'minimal', + [string] $msbuildEngine = $null, + [switch] $restore, + [switch] $prepareMachine, + [switch] $help, + [Parameter(ValueFromRemainingArguments=$true)][String[]]$properties +) + +$ci = $true +$binaryLog = $true +$warnAsError = $true + +. $PSScriptRoot\tools.ps1 + +function Print-Usage() { + Write-Host "Common settings:" + Write-Host " -task Name of Arcade task (name of a project in SdkTasks directory of the Arcade SDK package)" + Write-Host " -restore Restore dependencies" + Write-Host " -verbosity Msbuild verbosity: q[uiet], m[inimal], n[ormal], d[etailed], and diag[nostic]" + Write-Host " -help Print help and exit" + Write-Host "" + + Write-Host "Advanced settings:" + Write-Host " -prepareMachine Prepare machine for CI run" + Write-Host " -msbuildEngine Msbuild engine to use to run build ('dotnet', 'vs', or unspecified)." + Write-Host "" + Write-Host "Command line arguments not listed above are passed thru to msbuild." +} + +function Build([string]$target) { + $logSuffix = if ($target -eq 'Execute') { '' } else { ".$target" } + $log = Join-Path $LogDir "$task$logSuffix.binlog" + $outputPath = Join-Path $ToolsetDir "$task\" + + MSBuild $taskProject ` + /bl:$log ` + /t:$target ` + /p:Configuration=$configuration ` + /p:RepoRoot=$RepoRoot ` + /p:BaseIntermediateOutputPath=$outputPath ` + /v:$verbosity ` + @properties +} + +try { + if ($help -or (($null -ne $properties) -and ($properties.Contains('/help') -or $properties.Contains('/?')))) { + Print-Usage + exit 0 + } + + if ($task -eq "") { + Write-PipelineTelemetryError -Category 'Build' -Message "Missing required parameter '-task '" + Print-Usage + ExitWithExitCode 1 + } + + if( $msbuildEngine -eq "vs") { + # Ensure desktop MSBuild is available for sdk tasks. + if( -not ($GlobalJson.tools.PSObject.Properties.Name -contains "vs" )) { + $GlobalJson.tools | Add-Member -Name "vs" -Value (ConvertFrom-Json "{ `"version`": `"16.5`" }") -MemberType NoteProperty + } + if( -not ($GlobalJson.tools.PSObject.Properties.Name -match "xcopy-msbuild" )) { + $GlobalJson.tools | Add-Member -Name "xcopy-msbuild" -Value "16.10.0-preview2" -MemberType NoteProperty + } + if ($GlobalJson.tools."xcopy-msbuild".Trim() -ine "none") { + $xcopyMSBuildToolsFolder = InitializeXCopyMSBuild $GlobalJson.tools."xcopy-msbuild" -install $true + } + if ($xcopyMSBuildToolsFolder -eq $null) { + throw 'Unable to get xcopy downloadable version of msbuild' + } + + $global:_MSBuildExe = "$($xcopyMSBuildToolsFolder)\MSBuild\Current\Bin\MSBuild.exe" + } + + $taskProject = GetSdkTaskProject $task + if (!(Test-Path $taskProject)) { + Write-PipelineTelemetryError -Category 'Build' -Message "Unknown task: $task" + ExitWithExitCode 1 + } + + if ($restore) { + Build 'Restore' + } + + Build 'Execute' +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'Build' -Message $_ + ExitWithExitCode 1 +} + +ExitWithExitCode 0 diff --git a/eng/common/sdl/NuGet.config b/eng/common/sdl/NuGet.config new file mode 100644 index 000000000..0c5451c11 --- /dev/null +++ b/eng/common/sdl/NuGet.config @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/eng/common/sdl/configure-sdl-tool.ps1 b/eng/common/sdl/configure-sdl-tool.ps1 new file mode 100644 index 000000000..4999c3070 --- /dev/null +++ b/eng/common/sdl/configure-sdl-tool.ps1 @@ -0,0 +1,109 @@ +Param( + [string] $GuardianCliLocation, + [string] $WorkingDirectory, + [string] $TargetDirectory, + [string] $GdnFolder, + # The list of Guardian tools to configure. For each object in the array: + # - If the item is a [hashtable], it must contain these entries: + # - Name = The tool name as Guardian knows it. + # - Scenario = (Optional) Scenario-specific name for this configuration entry. It must be unique + # among all tool entries with the same Name. + # - Args = (Optional) Array of Guardian tool configuration args, like '@("Target > C:\temp")' + # - If the item is a [string] $v, it is treated as '@{ Name="$v" }' + [object[]] $ToolsList, + [string] $GuardianLoggerLevel='Standard', + # Optional: Additional params to add to any tool using CredScan. + [string[]] $CrScanAdditionalRunConfigParams, + # Optional: Additional params to add to any tool using PoliCheck. + [string[]] $PoliCheckAdditionalRunConfigParams +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 +$disableConfigureToolsetImport = $true +$global:LASTEXITCODE = 0 + +try { + # `tools.ps1` checks $ci to perform some actions. Since the SDL + # scripts don't necessarily execute in the same agent that run the + # build.ps1/sh script this variable isn't automatically set. + $ci = $true + . $PSScriptRoot\..\tools.ps1 + + # Normalize tools list: all in [hashtable] form with defined values for each key. + $ToolsList = $ToolsList | + ForEach-Object { + if ($_ -is [string]) { + $_ = @{ Name = $_ } + } + + if (-not ($_['Scenario'])) { $_.Scenario = "" } + if (-not ($_['Args'])) { $_.Args = @() } + $_ + } + + Write-Host "List of tools to configure:" + $ToolsList | ForEach-Object { $_ | Out-String | Write-Host } + + # We store config files in the r directory of .gdn + $gdnConfigPath = Join-Path $GdnFolder 'r' + $ValidPath = Test-Path $GuardianCliLocation + + if ($ValidPath -eq $False) + { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message "Invalid Guardian CLI Location." + ExitWithExitCode 1 + } + + foreach ($tool in $ToolsList) { + # Put together the name and scenario to make a unique key. + $toolConfigName = $tool.Name + if ($tool.Scenario) { + $toolConfigName += "_" + $tool.Scenario + } + + Write-Host "=== Configuring $toolConfigName..." + + $gdnConfigFile = Join-Path $gdnConfigPath "$toolConfigName-configure.gdnconfig" + + # For some tools, add default and automatic args. + if ($tool.Name -eq 'credscan') { + if ($targetDirectory) { + $tool.Args += "TargetDirectory < $TargetDirectory" + } + $tool.Args += "OutputType < pre" + $tool.Args += $CrScanAdditionalRunConfigParams + } elseif ($tool.Name -eq 'policheck') { + if ($targetDirectory) { + $tool.Args += "Target < $TargetDirectory" + } + $tool.Args += $PoliCheckAdditionalRunConfigParams + } + + # Create variable pointing to the args array directly so we can use splat syntax later. + $toolArgs = $tool.Args + + # Configure the tool. If args array is provided or the current tool has some default arguments + # defined, add "--args" and splat each element on the end. Arg format is "{Arg id} < {Value}", + # one per parameter. Doc page for "guardian configure": + # https://dev.azure.com/securitytools/SecurityIntegration/_wiki/wikis/Guardian/1395/configure + Exec-BlockVerbosely { + & $GuardianCliLocation configure ` + --working-directory $WorkingDirectory ` + --tool $tool.Name ` + --output-path $gdnConfigFile ` + --logger-level $GuardianLoggerLevel ` + --noninteractive ` + --force ` + $(if ($toolArgs) { "--args" }) @toolArgs + Exit-IfNZEC "Sdl" + } + + Write-Host "Created '$toolConfigName' configuration file: $gdnConfigFile" + } +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/sdl/execute-all-sdl-tools.ps1 b/eng/common/sdl/execute-all-sdl-tools.ps1 new file mode 100644 index 000000000..1157151f4 --- /dev/null +++ b/eng/common/sdl/execute-all-sdl-tools.ps1 @@ -0,0 +1,163 @@ +Param( + [string] $GuardianPackageName, # Required: the name of guardian CLI package (not needed if GuardianCliLocation is specified) + [string] $NugetPackageDirectory, # Required: directory where NuGet packages are installed (not needed if GuardianCliLocation is specified) + [string] $GuardianCliLocation, # Optional: Direct location of Guardian CLI executable if GuardianPackageName & NugetPackageDirectory are not specified + [string] $Repository=$env:BUILD_REPOSITORY_NAME, # Required: the name of the repository (e.g. dotnet/arcade) + [string] $BranchName=$env:BUILD_SOURCEBRANCH, # Optional: name of branch or version of gdn settings; defaults to master + [string] $SourceDirectory=$env:BUILD_SOURCESDIRECTORY, # Required: the directory where source files are located + [string] $ArtifactsDirectory = (Join-Path $env:BUILD_ARTIFACTSTAGINGDIRECTORY ('artifacts')), # Required: the directory where build artifacts are located + [string] $AzureDevOpsAccessToken, # Required: access token for dnceng; should be provided via KeyVault + + # Optional: list of SDL tools to run on source code. See 'configure-sdl-tool.ps1' for tools list + # format. + [object[]] $SourceToolsList, + # Optional: list of SDL tools to run on built artifacts. See 'configure-sdl-tool.ps1' for tools + # list format. + [object[]] $ArtifactToolsList, + # Optional: list of SDL tools to run without automatically specifying a target directory. See + # 'configure-sdl-tool.ps1' for tools list format. + [object[]] $CustomToolsList, + + [bool] $TsaPublish=$False, # Optional: true will publish results to TSA; only set to true after onboarding to TSA; TSA is the automated framework used to upload test results as bugs. + [string] $TsaBranchName=$env:BUILD_SOURCEBRANCH, # Optional: required for TSA publish; defaults to $(Build.SourceBranchName); TSA is the automated framework used to upload test results as bugs. + [string] $TsaRepositoryName=$env:BUILD_REPOSITORY_NAME, # Optional: TSA repository name; will be generated automatically if not submitted; TSA is the automated framework used to upload test results as bugs. + [string] $BuildNumber=$env:BUILD_BUILDNUMBER, # Optional: required for TSA publish; defaults to $(Build.BuildNumber) + [bool] $UpdateBaseline=$False, # Optional: if true, will update the baseline in the repository; should only be run after fixing any issues which need to be fixed + [bool] $TsaOnboard=$False, # Optional: if true, will onboard the repository to TSA; should only be run once; TSA is the automated framework used to upload test results as bugs. + [string] $TsaInstanceUrl, # Optional: only needed if TsaOnboard or TsaPublish is true; the instance-url registered with TSA; TSA is the automated framework used to upload test results as bugs. + [string] $TsaCodebaseName, # Optional: only needed if TsaOnboard or TsaPublish is true; the name of the codebase registered with TSA; TSA is the automated framework used to upload test results as bugs. + [string] $TsaProjectName, # Optional: only needed if TsaOnboard or TsaPublish is true; the name of the project registered with TSA; TSA is the automated framework used to upload test results as bugs. + [string] $TsaNotificationEmail, # Optional: only needed if TsaOnboard is true; the email(s) which will receive notifications of TSA bug filings (e.g. alias@microsoft.com); TSA is the automated framework used to upload test results as bugs. + [string] $TsaCodebaseAdmin, # Optional: only needed if TsaOnboard is true; the aliases which are admins of the TSA codebase (e.g. DOMAIN\alias); TSA is the automated framework used to upload test results as bugs. + [string] $TsaBugAreaPath, # Optional: only needed if TsaOnboard is true; the area path where TSA will file bugs in AzDO; TSA is the automated framework used to upload test results as bugs. + [string] $TsaIterationPath, # Optional: only needed if TsaOnboard is true; the iteration path where TSA will file bugs in AzDO; TSA is the automated framework used to upload test results as bugs. + [string] $GuardianLoggerLevel='Standard', # Optional: the logger level for the Guardian CLI; options are Trace, Verbose, Standard, Warning, and Error + [string[]] $CrScanAdditionalRunConfigParams, # Optional: Additional Params to custom build a CredScan run config in the format @("xyz:abc","sdf:1") + [string[]] $PoliCheckAdditionalRunConfigParams, # Optional: Additional Params to custom build a Policheck run config in the format @("xyz:abc","sdf:1") + [bool] $BreakOnFailure=$False # Optional: Fail the build if there were errors during the run +) + +try { + $ErrorActionPreference = 'Stop' + Set-StrictMode -Version 2.0 + $disableConfigureToolsetImport = $true + $global:LASTEXITCODE = 0 + + # `tools.ps1` checks $ci to perform some actions. Since the SDL + # scripts don't necessarily execute in the same agent that run the + # build.ps1/sh script this variable isn't automatically set. + $ci = $true + . $PSScriptRoot\..\tools.ps1 + + #Replace repo names to the format of org/repo + if (!($Repository.contains('/'))) { + $RepoName = $Repository -replace '(.*?)-(.*)', '$1/$2'; + } + else{ + $RepoName = $Repository; + } + + if ($GuardianPackageName) { + $guardianCliLocation = Join-Path $NugetPackageDirectory (Join-Path $GuardianPackageName (Join-Path 'tools' 'guardian.cmd')) + } else { + $guardianCliLocation = $GuardianCliLocation + } + + $workingDirectory = (Split-Path $SourceDirectory -Parent) + $ValidPath = Test-Path $guardianCliLocation + + if ($ValidPath -eq $False) + { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message 'Invalid Guardian CLI Location.' + ExitWithExitCode 1 + } + + Exec-BlockVerbosely { + & $(Join-Path $PSScriptRoot 'init-sdl.ps1') -GuardianCliLocation $guardianCliLocation -Repository $RepoName -BranchName $BranchName -WorkingDirectory $workingDirectory -AzureDevOpsAccessToken $AzureDevOpsAccessToken -GuardianLoggerLevel $GuardianLoggerLevel + } + $gdnFolder = Join-Path $workingDirectory '.gdn' + + if ($TsaOnboard) { + if ($TsaCodebaseName -and $TsaNotificationEmail -and $TsaCodebaseAdmin -and $TsaBugAreaPath) { + Exec-BlockVerbosely { + & $guardianCliLocation tsa-onboard --codebase-name "$TsaCodebaseName" --notification-alias "$TsaNotificationEmail" --codebase-admin "$TsaCodebaseAdmin" --instance-url "$TsaInstanceUrl" --project-name "$TsaProjectName" --area-path "$TsaBugAreaPath" --iteration-path "$TsaIterationPath" --working-directory $workingDirectory --logger-level $GuardianLoggerLevel + } + if ($LASTEXITCODE -ne 0) { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message "Guardian tsa-onboard failed with exit code $LASTEXITCODE." + ExitWithExitCode $LASTEXITCODE + } + } else { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message 'Could not onboard to TSA -- not all required values ($TsaCodebaseName, $TsaNotificationEmail, $TsaCodebaseAdmin, $TsaBugAreaPath) were specified.' + ExitWithExitCode 1 + } + } + + # Configure a list of tools with a default target directory. Populates the ".gdn/r" directory. + function Configure-ToolsList([object[]] $tools, [string] $targetDirectory) { + if ($tools -and $tools.Count -gt 0) { + Exec-BlockVerbosely { + & $(Join-Path $PSScriptRoot 'configure-sdl-tool.ps1') ` + -GuardianCliLocation $guardianCliLocation ` + -WorkingDirectory $workingDirectory ` + -TargetDirectory $targetDirectory ` + -GdnFolder $gdnFolder ` + -ToolsList $tools ` + -AzureDevOpsAccessToken $AzureDevOpsAccessToken ` + -GuardianLoggerLevel $GuardianLoggerLevel ` + -CrScanAdditionalRunConfigParams $CrScanAdditionalRunConfigParams ` + -PoliCheckAdditionalRunConfigParams $PoliCheckAdditionalRunConfigParams + if ($BreakOnFailure) { + Exit-IfNZEC "Sdl" + } + } + } + } + + # Configure Artifact and Source tools with default Target directories. + Configure-ToolsList $ArtifactToolsList $ArtifactsDirectory + Configure-ToolsList $SourceToolsList $SourceDirectory + # Configure custom tools with no default Target directory. + Configure-ToolsList $CustomToolsList $null + + # At this point, all tools are configured in the ".gdn" directory. Run them all in a single call. + # (If we used "run" multiple times, each run would overwrite data from earlier runs.) + Exec-BlockVerbosely { + & $(Join-Path $PSScriptRoot 'run-sdl.ps1') ` + -GuardianCliLocation $guardianCliLocation ` + -WorkingDirectory $workingDirectory ` + -UpdateBaseline $UpdateBaseline ` + -GdnFolder $gdnFolder + } + + if ($TsaPublish) { + if ($TsaBranchName -and $BuildNumber) { + if (-not $TsaRepositoryName) { + $TsaRepositoryName = "$($Repository)-$($BranchName)" + } + Exec-BlockVerbosely { + & $guardianCliLocation tsa-publish --all-tools --repository-name "$TsaRepositoryName" --branch-name "$TsaBranchName" --build-number "$BuildNumber" --onboard $True --codebase-name "$TsaCodebaseName" --notification-alias "$TsaNotificationEmail" --codebase-admin "$TsaCodebaseAdmin" --instance-url "$TsaInstanceUrl" --project-name "$TsaProjectName" --area-path "$TsaBugAreaPath" --iteration-path "$TsaIterationPath" --working-directory $workingDirectory --logger-level $GuardianLoggerLevel + } + if ($LASTEXITCODE -ne 0) { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message "Guardian tsa-publish failed with exit code $LASTEXITCODE." + ExitWithExitCode $LASTEXITCODE + } + } else { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message 'Could not publish to TSA -- not all required values ($TsaBranchName, $BuildNumber) were specified.' + ExitWithExitCode 1 + } + } + + if ($BreakOnFailure) { + Write-Host "Failing the build in case of breaking results..." + Exec-BlockVerbosely { + & $guardianCliLocation break --working-directory $workingDirectory --logger-level $GuardianLoggerLevel + } + } else { + Write-Host "Letting the build pass even if there were breaking results..." + } +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + exit 1 +} diff --git a/eng/common/sdl/extract-artifact-archives.ps1 b/eng/common/sdl/extract-artifact-archives.ps1 new file mode 100644 index 000000000..68da4fbf2 --- /dev/null +++ b/eng/common/sdl/extract-artifact-archives.ps1 @@ -0,0 +1,63 @@ +# This script looks for each archive file in a directory and extracts it into the target directory. +# For example, the file "$InputPath/bin.tar.gz" extracts to "$ExtractPath/bin.tar.gz.extracted/**". +# Uses the "tar" utility added to Windows 10 / Windows 2019 that supports tar.gz and zip. +param( + # Full path to directory where archives are stored. + [Parameter(Mandatory=$true)][string] $InputPath, + # Full path to directory to extract archives into. May be the same as $InputPath. + [Parameter(Mandatory=$true)][string] $ExtractPath +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 + +$disableConfigureToolsetImport = $true + +try { + # `tools.ps1` checks $ci to perform some actions. Since the SDL + # scripts don't necessarily execute in the same agent that run the + # build.ps1/sh script this variable isn't automatically set. + $ci = $true + . $PSScriptRoot\..\tools.ps1 + + Measure-Command { + $jobs = @() + + # Find archive files for non-Windows and Windows builds. + $archiveFiles = @( + Get-ChildItem (Join-Path $InputPath "*.tar.gz") + Get-ChildItem (Join-Path $InputPath "*.zip") + ) + + foreach ($targzFile in $archiveFiles) { + $jobs += Start-Job -ScriptBlock { + $file = $using:targzFile + $fileName = [System.IO.Path]::GetFileName($file) + $extractDir = Join-Path $using:ExtractPath "$fileName.extracted" + + New-Item $extractDir -ItemType Directory -Force | Out-Null + + Write-Host "Extracting '$file' to '$extractDir'..." + + # Pipe errors to stdout to prevent PowerShell detecting them and quitting the job early. + # This type of quit skips the catch, so we wouldn't be able to tell which file triggered the + # error. Save output so it can be stored in the exception string along with context. + $output = tar -xf $file -C $extractDir 2>&1 + # Handle NZEC manually rather than using Exit-IfNZEC: we are in a background job, so we + # don't have access to the outer scope. + if ($LASTEXITCODE -ne 0) { + throw "Error extracting '$file': non-zero exit code ($LASTEXITCODE). Output: '$output'" + } + + Write-Host "Extracted to $extractDir" + } + } + + Receive-Job $jobs -Wait + } +} +catch { + Write-Host $_ + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/sdl/extract-artifact-packages.ps1 b/eng/common/sdl/extract-artifact-packages.ps1 new file mode 100644 index 000000000..7f28d9c59 --- /dev/null +++ b/eng/common/sdl/extract-artifact-packages.ps1 @@ -0,0 +1,80 @@ +param( + [Parameter(Mandatory=$true)][string] $InputPath, # Full path to directory where artifact packages are stored + [Parameter(Mandatory=$true)][string] $ExtractPath # Full path to directory where the packages will be extracted +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 + +$disableConfigureToolsetImport = $true + +function ExtractArtifacts { + if (!(Test-Path $InputPath)) { + Write-Host "Input Path does not exist: $InputPath" + ExitWithExitCode 0 + } + $Jobs = @() + Get-ChildItem "$InputPath\*.nupkg" | + ForEach-Object { + $Jobs += Start-Job -ScriptBlock $ExtractPackage -ArgumentList $_.FullName + } + + foreach ($Job in $Jobs) { + Wait-Job -Id $Job.Id | Receive-Job + } +} + +try { + # `tools.ps1` checks $ci to perform some actions. Since the SDL + # scripts don't necessarily execute in the same agent that run the + # build.ps1/sh script this variable isn't automatically set. + $ci = $true + . $PSScriptRoot\..\tools.ps1 + + $ExtractPackage = { + param( + [string] $PackagePath # Full path to a NuGet package + ) + + if (!(Test-Path $PackagePath)) { + Write-PipelineTelemetryError -Category 'Build' -Message "Input file does not exist: $PackagePath" + ExitWithExitCode 1 + } + + $RelevantExtensions = @('.dll', '.exe', '.pdb') + Write-Host -NoNewLine 'Extracting ' ([System.IO.Path]::GetFileName($PackagePath)) '...' + + $PackageId = [System.IO.Path]::GetFileNameWithoutExtension($PackagePath) + $ExtractPath = Join-Path -Path $using:ExtractPath -ChildPath $PackageId + + Add-Type -AssemblyName System.IO.Compression.FileSystem + + [System.IO.Directory]::CreateDirectory($ExtractPath); + + try { + $zip = [System.IO.Compression.ZipFile]::OpenRead($PackagePath) + + $zip.Entries | + Where-Object {$RelevantExtensions -contains [System.IO.Path]::GetExtension($_.Name)} | + ForEach-Object { + $TargetFile = Join-Path -Path $ExtractPath -ChildPath $_.Name + + [System.IO.Compression.ZipFileExtensions]::ExtractToFile($_, $TargetFile, $true) + } + } + catch { + Write-Host $_ + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 + } + finally { + $zip.Dispose() + } + } + Measure-Command { ExtractArtifacts } +} +catch { + Write-Host $_ + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/sdl/init-sdl.ps1 b/eng/common/sdl/init-sdl.ps1 new file mode 100644 index 000000000..3ac1d92b3 --- /dev/null +++ b/eng/common/sdl/init-sdl.ps1 @@ -0,0 +1,55 @@ +Param( + [string] $GuardianCliLocation, + [string] $Repository, + [string] $BranchName='master', + [string] $WorkingDirectory, + [string] $AzureDevOpsAccessToken, + [string] $GuardianLoggerLevel='Standard' +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 +$disableConfigureToolsetImport = $true +$global:LASTEXITCODE = 0 + +# `tools.ps1` checks $ci to perform some actions. Since the SDL +# scripts don't necessarily execute in the same agent that run the +# build.ps1/sh script this variable isn't automatically set. +$ci = $true +. $PSScriptRoot\..\tools.ps1 + +# Don't display the console progress UI - it's a huge perf hit +$ProgressPreference = 'SilentlyContinue' + +# Construct basic auth from AzDO access token; construct URI to the repository's gdn folder stored in that repository; construct location of zip file +$encodedPat = [Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes(":$AzureDevOpsAccessToken")) +$escapedRepository = [Uri]::EscapeDataString("/$Repository/$BranchName/.gdn") +$uri = "https://dev.azure.com/dnceng/internal/_apis/git/repositories/sdl-tool-cfg/Items?path=$escapedRepository&versionDescriptor[versionOptions]=0&`$format=zip&api-version=5.0" +$zipFile = "$WorkingDirectory/gdn.zip" + +Add-Type -AssemblyName System.IO.Compression.FileSystem +$gdnFolder = (Join-Path $WorkingDirectory '.gdn') + +try { + # if the folder does not exist, we'll do a guardian init and push it to the remote repository + Write-Host 'Initializing Guardian...' + Write-Host "$GuardianCliLocation init --working-directory $WorkingDirectory --logger-level $GuardianLoggerLevel" + & $GuardianCliLocation init --working-directory $WorkingDirectory --logger-level $GuardianLoggerLevel + if ($LASTEXITCODE -ne 0) { + Write-PipelineTelemetryError -Force -Category 'Build' -Message "Guardian init failed with exit code $LASTEXITCODE." + ExitWithExitCode $LASTEXITCODE + } + # We create the mainbaseline so it can be edited later + Write-Host "$GuardianCliLocation baseline --working-directory $WorkingDirectory --name mainbaseline" + & $GuardianCliLocation baseline --working-directory $WorkingDirectory --name mainbaseline + if ($LASTEXITCODE -ne 0) { + Write-PipelineTelemetryError -Force -Category 'Build' -Message "Guardian baseline failed with exit code $LASTEXITCODE." + ExitWithExitCode $LASTEXITCODE + } + ExitWithExitCode 0 +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/sdl/packages.config b/eng/common/sdl/packages.config new file mode 100644 index 000000000..3bd8b29eb --- /dev/null +++ b/eng/common/sdl/packages.config @@ -0,0 +1,4 @@ + + + + diff --git a/eng/common/sdl/run-sdl.ps1 b/eng/common/sdl/run-sdl.ps1 new file mode 100644 index 000000000..2eac8c78f --- /dev/null +++ b/eng/common/sdl/run-sdl.ps1 @@ -0,0 +1,49 @@ +Param( + [string] $GuardianCliLocation, + [string] $WorkingDirectory, + [string] $GdnFolder, + [string] $UpdateBaseline, + [string] $GuardianLoggerLevel='Standard' +) + +$ErrorActionPreference = 'Stop' +Set-StrictMode -Version 2.0 +$disableConfigureToolsetImport = $true +$global:LASTEXITCODE = 0 + +try { + # `tools.ps1` checks $ci to perform some actions. Since the SDL + # scripts don't necessarily execute in the same agent that run the + # build.ps1/sh script this variable isn't automatically set. + $ci = $true + . $PSScriptRoot\..\tools.ps1 + + # We store config files in the r directory of .gdn + $gdnConfigPath = Join-Path $GdnFolder 'r' + $ValidPath = Test-Path $GuardianCliLocation + + if ($ValidPath -eq $False) + { + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message "Invalid Guardian CLI Location." + ExitWithExitCode 1 + } + + $gdnConfigFiles = Get-ChildItem $gdnConfigPath -Recurse -Include '*.gdnconfig' + Write-Host "Discovered Guardian config files:" + $gdnConfigFiles | Out-String | Write-Host + + Exec-BlockVerbosely { + & $GuardianCliLocation run ` + --working-directory $WorkingDirectory ` + --baseline mainbaseline ` + --update-baseline $UpdateBaseline ` + --logger-level $GuardianLoggerLevel ` + --config @gdnConfigFiles + Exit-IfNZEC "Sdl" + } +} +catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Force -Category 'Sdl' -Message $_ + ExitWithExitCode 1 +} diff --git a/eng/common/templates/job/execute-sdl.yml b/eng/common/templates/job/execute-sdl.yml new file mode 100644 index 000000000..69eb67849 --- /dev/null +++ b/eng/common/templates/job/execute-sdl.yml @@ -0,0 +1,185 @@ +parameters: + enable: 'false' # Whether the SDL validation job should execute or not + overrideParameters: '' # Optional: to override values for parameters. + additionalParameters: '' # Optional: parameters that need user specific values eg: '-SourceToolsList @("abc","def") -ArtifactToolsList @("ghi","jkl")' + # Optional: if specified, restore and use this version of Guardian instead of the default. + overrideGuardianVersion: '' + # Optional: if true, publish the '.gdn' folder as a pipeline artifact. This can help with in-depth + # diagnosis of problems with specific tool configurations. + publishGuardianDirectoryToPipeline: false + # The script to run to execute all SDL tools. Use this if you want to use a script to define SDL + # parameters rather than relying on YAML. It may be better to use a local script, because you can + # reproduce results locally without piecing together a command based on the YAML. + executeAllSdlToolsScript: 'eng/common/sdl/execute-all-sdl-tools.ps1' + # There is some sort of bug (has been reported) in Azure DevOps where if this parameter is named + # 'continueOnError', the parameter value is not correctly picked up. + # This can also be remedied by the caller (post-build.yml) if it does not use a nested parameter + sdlContinueOnError: false # optional: determines whether to continue the build if the step errors; + # optional: determines if build artifacts should be downloaded. + downloadArtifacts: true + # optional: determines if this job should search the directory of downloaded artifacts for + # 'tar.gz' and 'zip' archive files and extract them before running SDL validation tasks. + extractArchiveArtifacts: false + dependsOn: '' # Optional: dependencies of the job + artifactNames: '' # Optional: patterns supplied to DownloadBuildArtifacts + # Usage: + # artifactNames: + # - 'BlobArtifacts' + # - 'Artifacts_Windows_NT_Release' + # Optional: download a list of pipeline artifacts. 'downloadArtifacts' controls build artifacts, + # not pipeline artifacts, so doesn't affect the use of this parameter. + pipelineArtifactNames: [] + # Optional: location and ID of the AzDO build that the build/pipeline artifacts should be + # downloaded from. By default, uses runtime expressions to decide based on the variables set by + # the 'setupMaestroVars' dependency. Overriding this parameter is necessary if SDL tasks are + # running without Maestro++/BAR involved, or to download artifacts from a specific existing build + # to iterate quickly on SDL changes. + AzDOProjectName: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + AzDOPipelineId: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + AzDOBuildId: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + +jobs: +- job: Run_SDL + dependsOn: ${{ parameters.dependsOn }} + displayName: Run SDL tool + condition: eq( ${{ parameters.enable }}, 'true') + variables: + - group: DotNet-VSTS-Bot + - name: AzDOProjectName + value: ${{ parameters.AzDOProjectName }} + - name: AzDOPipelineId + value: ${{ parameters.AzDOPipelineId }} + - name: AzDOBuildId + value: ${{ parameters.AzDOBuildId }} + # The Guardian version specified in 'eng/common/sdl/packages.config'. This value must be kept in + # sync with the packages.config file. + - name: DefaultGuardianVersion + value: 0.53.3 + - name: GuardianVersion + value: ${{ coalesce(parameters.overrideGuardianVersion, '$(DefaultGuardianVersion)') }} + - name: GuardianPackagesConfigFile + value: $(Build.SourcesDirectory)\eng\common\sdl\packages.config + pool: + # To extract archives (.tar.gz, .zip), we need access to "tar", added in Windows 10/2019. + ${{ if eq(parameters.extractArchiveArtifacts, 'false') }}: + name: Hosted VS2017 + ${{ if ne(parameters.extractArchiveArtifacts, 'false') }}: + vmImage: windows-2019 + steps: + - checkout: self + clean: true + + - ${{ if ne(parameters.downloadArtifacts, 'false')}}: + - ${{ if ne(parameters.artifactNames, '') }}: + - ${{ each artifactName in parameters.artifactNames }}: + - task: DownloadBuildArtifacts@0 + displayName: Download Build Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: ${{ artifactName }} + downloadPath: $(Build.ArtifactStagingDirectory)\artifacts + checkDownloadedFiles: true + - ${{ if eq(parameters.artifactNames, '') }}: + - task: DownloadBuildArtifacts@0 + displayName: Download Build Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: specific files + itemPattern: "**" + downloadPath: $(Build.ArtifactStagingDirectory)\artifacts + checkDownloadedFiles: true + + - ${{ each artifactName in parameters.pipelineArtifactNames }}: + - task: DownloadPipelineArtifact@2 + displayName: Download Pipeline Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: ${{ artifactName }} + downloadPath: $(Build.ArtifactStagingDirectory)\artifacts + checkDownloadedFiles: true + + - powershell: eng/common/sdl/extract-artifact-packages.ps1 + -InputPath $(Build.ArtifactStagingDirectory)\artifacts\BlobArtifacts + -ExtractPath $(Build.ArtifactStagingDirectory)\artifacts\BlobArtifacts + displayName: Extract Blob Artifacts + continueOnError: ${{ parameters.sdlContinueOnError }} + + - powershell: eng/common/sdl/extract-artifact-packages.ps1 + -InputPath $(Build.ArtifactStagingDirectory)\artifacts\PackageArtifacts + -ExtractPath $(Build.ArtifactStagingDirectory)\artifacts\PackageArtifacts + displayName: Extract Package Artifacts + continueOnError: ${{ parameters.sdlContinueOnError }} + + - ${{ if ne(parameters.extractArchiveArtifacts, 'false') }}: + - powershell: eng/common/sdl/extract-artifact-archives.ps1 + -InputPath $(Build.ArtifactStagingDirectory)\artifacts + -ExtractPath $(Build.ArtifactStagingDirectory)\artifacts + displayName: Extract Archive Artifacts + continueOnError: ${{ parameters.sdlContinueOnError }} + + - ${{ if ne(parameters.overrideGuardianVersion, '') }}: + - powershell: | + $content = Get-Content $(GuardianPackagesConfigFile) + + Write-Host "packages.config content was:`n$content" + + $content = $content.Replace('$(DefaultGuardianVersion)', '$(GuardianVersion)') + $content | Set-Content $(GuardianPackagesConfigFile) + + Write-Host "packages.config content updated to:`n$content" + displayName: Use overridden Guardian version ${{ parameters.overrideGuardianVersion }} + + - task: NuGetToolInstaller@1 + displayName: 'Install NuGet.exe' + - task: NuGetCommand@2 + displayName: 'Install Guardian' + inputs: + restoreSolution: $(Build.SourcesDirectory)\eng\common\sdl\packages.config + feedsToUse: config + nugetConfigPath: $(Build.SourcesDirectory)\eng\common\sdl\NuGet.config + externalFeedCredentials: GuardianConnect + restoreDirectory: $(Build.SourcesDirectory)\.packages + + - ${{ if ne(parameters.overrideParameters, '') }}: + - powershell: ${{ parameters.executeAllSdlToolsScript }} ${{ parameters.overrideParameters }} + displayName: Execute SDL + continueOnError: ${{ parameters.sdlContinueOnError }} + - ${{ if eq(parameters.overrideParameters, '') }}: + - powershell: ${{ parameters.executeAllSdlToolsScript }} + -GuardianPackageName Microsoft.Guardian.Cli.$(GuardianVersion) + -NugetPackageDirectory $(Build.SourcesDirectory)\.packages + -AzureDevOpsAccessToken $(dn-bot-dotnet-build-rw-code-rw) + ${{ parameters.additionalParameters }} + displayName: Execute SDL + continueOnError: ${{ parameters.sdlContinueOnError }} + + - ${{ if ne(parameters.publishGuardianDirectoryToPipeline, 'false') }}: + # We want to publish the Guardian results and configuration for easy diagnosis. However, the + # '.gdn' dir is a mix of configuration, results, extracted dependencies, and Guardian default + # tooling files. Some of these files are large and aren't useful during an investigation, so + # exclude them by simply deleting them before publishing. (As of writing, there is no documented + # way to selectively exclude a dir from the pipeline artifact publish task.) + - task: DeleteFiles@1 + displayName: Delete Guardian dependencies to avoid uploading + inputs: + SourceFolder: $(Agent.BuildDirectory)/.gdn + Contents: | + c + i + condition: succeededOrFailed() + - publish: $(Agent.BuildDirectory)/.gdn + artifact: GuardianConfiguration + displayName: Publish GuardianConfiguration + condition: succeededOrFailed() diff --git a/eng/common/templates/job/generate-graph-files.yml b/eng/common/templates/job/generate-graph-files.yml new file mode 100644 index 000000000..e54ce956f --- /dev/null +++ b/eng/common/templates/job/generate-graph-files.yml @@ -0,0 +1,48 @@ +parameters: + # Optional: dependencies of the job + dependsOn: '' + + # Optional: A defined YAML pool - https://docs.microsoft.com/en-us/azure/devops/pipelines/yaml-schema?view=vsts&tabs=schema#pool + pool: {} + + # Optional: Include toolset dependencies in the generated graph files + includeToolset: false + +jobs: +- job: Generate_Graph_Files + + dependsOn: ${{ parameters.dependsOn }} + + displayName: Generate Graph Files + + pool: ${{ parameters.pool }} + + variables: + # Publish-Build-Assets provides: MaestroAccessToken, BotAccount-dotnet-maestro-bot-PAT + # DotNet-AllOrgs-Darc-Pats provides: dn-bot-devdiv-dnceng-rw-code-pat + - group: Publish-Build-Assets + - group: DotNet-AllOrgs-Darc-Pats + - name: _GraphArguments + value: -gitHubPat $(BotAccount-dotnet-maestro-bot-PAT) + -azdoPat $(dn-bot-devdiv-dnceng-rw-code-pat) + -barToken $(MaestroAccessToken) + -outputFolder '$(Build.StagingDirectory)/GraphFiles/' + - ${{ if ne(parameters.includeToolset, 'false') }}: + - name: _GraphArguments + value: ${{ variables._GraphArguments }} -includeToolset + + steps: + - task: PowerShell@2 + displayName: Generate Graph Files + inputs: + filePath: eng\common\generate-graph-files.ps1 + arguments: $(_GraphArguments) + continueOnError: true + - task: PublishBuildArtifacts@1 + displayName: Publish Graph to Artifacts + inputs: + PathtoPublish: '$(Build.StagingDirectory)/GraphFiles' + PublishLocation: Container + ArtifactName: GraphFiles + continueOnError: true + condition: always() diff --git a/eng/common/templates/job/job.yml b/eng/common/templates/job/job.yml new file mode 100644 index 000000000..866967934 --- /dev/null +++ b/eng/common/templates/job/job.yml @@ -0,0 +1,244 @@ +# Internal resources (telemetry, microbuild) can only be accessed from non-public projects, +# and some (Microbuild) should only be applied to non-PR cases for internal builds. + +parameters: +# Job schema parameters - https://docs.microsoft.com/en-us/azure/devops/pipelines/yaml-schema?view=vsts&tabs=schema#job + cancelTimeoutInMinutes: '' + condition: '' + container: '' + continueOnError: false + dependsOn: '' + displayName: '' + pool: '' + steps: [] + strategy: '' + timeoutInMinutes: '' + variables: [] + workspace: '' + +# Job base template specific parameters + # See schema documentation - https://github.com/dotnet/arcade/blob/master/Documentation/AzureDevOps/TemplateSchema.md + artifacts: '' + enableMicrobuild: false + enablePublishBuildArtifacts: false + enablePublishBuildAssets: false + enablePublishTestResults: false + enablePublishUsingPipelines: false + mergeTestResults: false + testRunTitle: '' + testResultsFormat: '' + name: '' + preSteps: [] + runAsPublic: false + +jobs: +- job: ${{ parameters.name }} + + ${{ if ne(parameters.cancelTimeoutInMinutes, '') }}: + cancelTimeoutInMinutes: ${{ parameters.cancelTimeoutInMinutes }} + + ${{ if ne(parameters.condition, '') }}: + condition: ${{ parameters.condition }} + + ${{ if ne(parameters.container, '') }}: + container: ${{ parameters.container }} + + ${{ if ne(parameters.continueOnError, '') }}: + continueOnError: ${{ parameters.continueOnError }} + + ${{ if ne(parameters.dependsOn, '') }}: + dependsOn: ${{ parameters.dependsOn }} + + ${{ if ne(parameters.displayName, '') }}: + displayName: ${{ parameters.displayName }} + + ${{ if ne(parameters.pool, '') }}: + pool: ${{ parameters.pool }} + + ${{ if ne(parameters.strategy, '') }}: + strategy: ${{ parameters.strategy }} + + ${{ if ne(parameters.timeoutInMinutes, '') }}: + timeoutInMinutes: ${{ parameters.timeoutInMinutes }} + + variables: + - ${{ if ne(parameters.enableTelemetry, 'false') }}: + - name: DOTNET_CLI_TELEMETRY_PROFILE + value: '$(Build.Repository.Uri)' + - ${{ if eq(parameters.enableRichCodeNavigation, 'true') }}: + - name: EnableRichCodeNavigation + value: 'true' + - ${{ each variable in parameters.variables }}: + # handle name-value variable syntax + # example: + # - name: [key] + # value: [value] + - ${{ if ne(variable.name, '') }}: + - name: ${{ variable.name }} + value: ${{ variable.value }} + + # handle variable groups + - ${{ if ne(variable.group, '') }}: + - group: ${{ variable.group }} + + # handle key-value variable syntax. + # example: + # - [key]: [value] + - ${{ if and(eq(variable.name, ''), eq(variable.group, '')) }}: + - ${{ each pair in variable }}: + - name: ${{ pair.key }} + value: ${{ pair.value }} + + # DotNet-HelixApi-Access provides 'HelixApiAccessToken' for internal builds + - ${{ if and(eq(parameters.enableTelemetry, 'true'), eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - group: DotNet-HelixApi-Access + + ${{ if ne(parameters.workspace, '') }}: + workspace: ${{ parameters.workspace }} + + steps: + - ${{ if ne(parameters.preSteps, '') }}: + - ${{ each preStep in parameters.preSteps }}: + - ${{ preStep }} + + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - ${{ if eq(parameters.enableMicrobuild, 'true') }}: + - task: MicroBuildSigningPlugin@2 + displayName: Install MicroBuild plugin + inputs: + signType: $(_SignType) + zipSources: false + feedSource: https://dnceng.pkgs.visualstudio.com/_packaging/MicroBuildToolset/nuget/v3/index.json + env: + TeamName: $(_TeamName) + continueOnError: ${{ parameters.continueOnError }} + condition: and(succeeded(), in(variables['_SignType'], 'real', 'test'), eq(variables['Agent.Os'], 'Windows_NT')) + + - task: NuGetAuthenticate@0 + + - ${{ if or(eq(parameters.artifacts.download, 'true'), ne(parameters.artifacts.download, '')) }}: + - task: DownloadPipelineArtifact@2 + inputs: + buildType: current + artifactName: ${{ coalesce(parameters.artifacts.download.name, 'Artifacts_$(Agent.OS)_$(_BuildConfig)') }} + targetPath: ${{ coalesce(parameters.artifacts.download.path, 'artifacts') }} + itemPattern: ${{ coalesce(parameters.artifacts.download.pattern, '**') }} + + - ${{ each step in parameters.steps }}: + - ${{ step }} + + - ${{ if eq(parameters.enableRichCodeNavigation, true) }}: + - task: RichCodeNavIndexer@0 + displayName: RichCodeNav Upload + inputs: + languages: ${{ coalesce(parameters.richCodeNavigationLanguage, 'csharp') }} + environment: ${{ coalesce(parameters.richCodeNavigationEnvironment, 'production') }} + richNavLogOutputDirectory: $(Build.SourcesDirectory)/artifacts/bin + continueOnError: true + + - ${{ if eq(parameters.enableMicrobuild, 'true') }}: + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: MicroBuildCleanup@1 + displayName: Execute Microbuild cleanup tasks + condition: and(always(), in(variables['_SignType'], 'real', 'test'), eq(variables['Agent.Os'], 'Windows_NT')) + continueOnError: ${{ parameters.continueOnError }} + env: + TeamName: $(_TeamName) + + - ${{ if ne(parameters.artifacts.publish, '') }}: + - ${{ if or(eq(parameters.artifacts.publish.artifacts, 'true'), ne(parameters.artifacts.publish.artifacts, '')) }}: + - task: CopyFiles@2 + displayName: Gather binaries for publish to artifacts + inputs: + SourceFolder: 'artifacts/bin' + Contents: '**' + TargetFolder: '$(Build.ArtifactStagingDirectory)/artifacts/bin' + - task: CopyFiles@2 + displayName: Gather packages for publish to artifacts + inputs: + SourceFolder: 'artifacts/packages' + Contents: '**' + TargetFolder: '$(Build.ArtifactStagingDirectory)/artifacts/packages' + - task: PublishBuildArtifacts@1 + displayName: Publish pipeline artifacts + inputs: + PathtoPublish: '$(Build.ArtifactStagingDirectory)/artifacts' + PublishLocation: Container + ArtifactName: ${{ coalesce(parameters.artifacts.publish.artifacts.name , 'Artifacts_$(Agent.Os)_$(_BuildConfig)') }} + continueOnError: true + condition: always() + - ${{ if or(eq(parameters.artifacts.publish.logs, 'true'), ne(parameters.artifacts.publish.logs, '')) }}: + - publish: artifacts/log + artifact: ${{ coalesce(parameters.artifacts.publish.logs.name, 'Logs_Build_$(Agent.Os)_$(_BuildConfig)') }} + displayName: Publish logs + continueOnError: true + condition: always() + - ${{ if or(eq(parameters.artifacts.publish.manifests, 'true'), ne(parameters.artifacts.publish.manifests, '')) }}: + - ${{ if and(ne(parameters.enablePublishUsingPipelines, 'true'), eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: CopyFiles@2 + displayName: Gather Asset Manifests + inputs: + SourceFolder: '$(Build.SourcesDirectory)/artifacts/log/$(_BuildConfig)/AssetManifest' + TargetFolder: '$(Build.ArtifactStagingDirectory)/AssetManifests' + continueOnError: ${{ parameters.continueOnError }} + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) + + - task: PublishBuildArtifacts@1 + displayName: Push Asset Manifests + inputs: + PathtoPublish: '$(Build.ArtifactStagingDirectory)/AssetManifests' + PublishLocation: Container + ArtifactName: AssetManifests + continueOnError: ${{ parameters.continueOnError }} + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) + + - ${{ if ne(parameters.enablePublishBuildArtifacts, 'false') }}: + - task: PublishBuildArtifacts@1 + displayName: Publish Logs + inputs: + PathtoPublish: '$(Build.SourcesDirectory)/artifacts/log/$(_BuildConfig)' + PublishLocation: Container + ArtifactName: ${{ coalesce(parameters.enablePublishBuildArtifacts.artifactName, '$(Agent.Os)_$(Agent.JobName)' ) }} + continueOnError: true + condition: always() + + - ${{ if or(and(eq(parameters.enablePublishTestResults, 'true'), eq(parameters.testResultsFormat, '')), eq(parameters.testResultsFormat, 'xunit')) }}: + - task: PublishTestResults@2 + displayName: Publish XUnit Test Results + inputs: + testResultsFormat: 'xUnit' + testResultsFiles: '*.xml' + searchFolder: '$(Build.SourcesDirectory)/artifacts/TestResults/$(_BuildConfig)' + testRunTitle: ${{ coalesce(parameters.testRunTitle, parameters.name, '$(System.JobName)') }}-xunit + mergeTestResults: ${{ parameters.mergeTestResults }} + continueOnError: true + condition: always() + - ${{ if or(and(eq(parameters.enablePublishTestResults, 'true'), eq(parameters.testResultsFormat, '')), eq(parameters.testResultsFormat, 'vstest')) }}: + - task: PublishTestResults@2 + displayName: Publish TRX Test Results + inputs: + testResultsFormat: 'VSTest' + testResultsFiles: '*.trx' + searchFolder: '$(Build.SourcesDirectory)/artifacts/TestResults/$(_BuildConfig)' + testRunTitle: ${{ coalesce(parameters.testRunTitle, parameters.name, '$(System.JobName)') }}-trx + mergeTestResults: ${{ parameters.mergeTestResults }} + continueOnError: true + condition: always() + + - ${{ if and(eq(parameters.enablePublishBuildAssets, true), ne(parameters.enablePublishUsingPipelines, 'true'), eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: CopyFiles@2 + displayName: Gather Asset Manifests + inputs: + SourceFolder: '$(Build.SourcesDirectory)/artifacts/log/$(_BuildConfig)/AssetManifest' + TargetFolder: '$(Build.StagingDirectory)/AssetManifests' + continueOnError: ${{ parameters.continueOnError }} + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) + + - task: PublishBuildArtifacts@1 + displayName: Push Asset Manifests + inputs: + PathtoPublish: '$(Build.StagingDirectory)/AssetManifests' + PublishLocation: Container + ArtifactName: AssetManifests + continueOnError: ${{ parameters.continueOnError }} + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) diff --git a/eng/common/templates/job/onelocbuild.yml b/eng/common/templates/job/onelocbuild.yml new file mode 100644 index 000000000..e8bc77d2e --- /dev/null +++ b/eng/common/templates/job/onelocbuild.yml @@ -0,0 +1,93 @@ +parameters: + # Optional: dependencies of the job + dependsOn: '' + + # Optional: A defined YAML pool - https://docs.microsoft.com/en-us/azure/devops/pipelines/yaml-schema?view=vsts&tabs=schema#pool + pool: + vmImage: vs2017-win2016 + + CeapexPat: $(dn-bot-ceapex-package-r) # PAT for the loc AzDO instance https://dev.azure.com/ceapex + GithubPat: $(BotAccount-dotnet-bot-repo-PAT) + + SourcesDirectory: $(Build.SourcesDirectory) + CreatePr: true + AutoCompletePr: false + UseLfLineEndings: true + UseCheckedInLocProjectJson: false + LanguageSet: VS_Main_Languages + LclSource: lclFilesInRepo + LclPackageId: '' + RepoType: gitHub + GitHubOrg: dotnet + MirrorRepo: '' + MirrorBranch: main + condition: '' + +jobs: +- job: OneLocBuild + + dependsOn: ${{ parameters.dependsOn }} + + displayName: OneLocBuild + + pool: ${{ parameters.pool }} + + variables: + - group: OneLocBuildVariables # Contains the CeapexPat and GithubPat + - name: _GenerateLocProjectArguments + value: -SourcesDirectory ${{ parameters.SourcesDirectory }} + -LanguageSet "${{ parameters.LanguageSet }}" + -CreateNeutralXlfs + - ${{ if eq(parameters.UseCheckedInLocProjectJson, 'true') }}: + - name: _GenerateLocProjectArguments + value: ${{ variables._GenerateLocProjectArguments }} -UseCheckedInLocProjectJson + + + steps: + - task: Powershell@2 + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/generate-locproject.ps1 + arguments: $(_GenerateLocProjectArguments) + displayName: Generate LocProject.json + condition: ${{ parameters.condition }} + + - task: OneLocBuild@2 + displayName: OneLocBuild + env: + SYSTEM_ACCESSTOKEN: $(System.AccessToken) + inputs: + locProj: eng/Localize/LocProject.json + outDir: $(Build.ArtifactStagingDirectory) + lclSource: ${{ parameters.LclSource }} + lclPackageId: ${{ parameters.LclPackageId }} + isCreatePrSelected: ${{ parameters.CreatePr }} + ${{ if eq(parameters.CreatePr, true) }}: + isAutoCompletePrSelected: ${{ parameters.AutoCompletePr }} + isUseLfLineEndingsSelected: ${{ parameters.UseLfLineEndings }} + packageSourceAuth: patAuth + patVariable: ${{ parameters.CeapexPat }} + ${{ if eq(parameters.RepoType, 'gitHub') }}: + repoType: ${{ parameters.RepoType }} + gitHubPatVariable: "${{ parameters.GithubPat }}" + ${{ if ne(parameters.MirrorRepo, '') }}: + isMirrorRepoSelected: true + gitHubOrganization: ${{ parameters.GitHubOrg }} + mirrorRepo: ${{ parameters.MirrorRepo }} + mirrorBranch: ${{ parameters.MirrorBranch }} + condition: ${{ parameters.condition }} + + - task: PublishBuildArtifacts@1 + displayName: Publish Localization Files + inputs: + PathtoPublish: '$(Build.ArtifactStagingDirectory)/loc' + PublishLocation: Container + ArtifactName: Loc + condition: ${{ parameters.condition }} + + - task: PublishBuildArtifacts@1 + displayName: Publish LocProject.json + inputs: + PathtoPublish: '$(Build.SourcesDirectory)/eng/Localize/' + PublishLocation: Container + ArtifactName: Loc + condition: ${{ parameters.condition }} \ No newline at end of file diff --git a/eng/common/templates/job/publish-build-assets.yml b/eng/common/templates/job/publish-build-assets.yml new file mode 100644 index 000000000..3b9e2524f --- /dev/null +++ b/eng/common/templates/job/publish-build-assets.yml @@ -0,0 +1,101 @@ +parameters: + configuration: 'Debug' + + # Optional: condition for the job to run + condition: '' + + # Optional: 'true' if future jobs should run even if this job fails + continueOnError: false + + # Optional: dependencies of the job + dependsOn: '' + + # Optional: Include PublishBuildArtifacts task + enablePublishBuildArtifacts: false + + # Optional: A defined YAML pool - https://docs.microsoft.com/en-us/azure/devops/pipelines/yaml-schema?view=vsts&tabs=schema#pool + pool: {} + + # Optional: should run as a public build even in the internal project + # if 'true', the build won't run any of the internal only steps, even if it is running in non-public projects. + runAsPublic: false + + # Optional: whether the build's artifacts will be published using release pipelines or direct feed publishing + publishUsingPipelines: false + +jobs: +- job: Asset_Registry_Publish + + dependsOn: ${{ parameters.dependsOn }} + + displayName: Publish to Build Asset Registry + + pool: ${{ parameters.pool }} + + variables: + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - name: _BuildConfig + value: ${{ parameters.configuration }} + - group: Publish-Build-Assets + - group: AzureDevOps-Artifact-Feeds-Pats + # Skip component governance and codesign validation for SDL. These jobs + # create no content. + - name: skipComponentGovernanceDetection + value: true + - name: runCodesignValidationInjection + value: false + + steps: + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: DownloadBuildArtifacts@0 + displayName: Download artifact + inputs: + artifactName: AssetManifests + downloadPath: '$(Build.StagingDirectory)/Download' + checkDownloadedFiles: true + condition: ${{ parameters.condition }} + continueOnError: ${{ parameters.continueOnError }} + + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: NuGetAuthenticate@0 + + - task: PowerShell@2 + displayName: Enable cross-org NuGet feed authentication + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-all-orgs-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish Build Assets + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishBuildAssets -restore -msbuildEngine dotnet + /p:ManifestsPath='$(Build.StagingDirectory)/Download/AssetManifests' + /p:BuildAssetRegistryToken=$(MaestroAccessToken) + /p:MaestroApiEndpoint=https://maestro-prod.westus2.cloudapp.azure.com + /p:PublishUsingPipelines=${{ parameters.publishUsingPipelines }} + /p:Configuration=$(_BuildConfig) + /p:OfficialBuildId=$(Build.BuildNumber) + condition: ${{ parameters.condition }} + continueOnError: ${{ parameters.continueOnError }} + + - task: powershell@2 + displayName: Create ReleaseConfigs Artifact + inputs: + targetType: inline + script: | + Add-Content -Path "$(Build.StagingDirectory)/ReleaseConfigs.txt" -Value $(BARBuildId) + Add-Content -Path "$(Build.StagingDirectory)/ReleaseConfigs.txt" -Value "$(DefaultChannels)" + Add-Content -Path "$(Build.StagingDirectory)/ReleaseConfigs.txt" -Value $(IsStableBuild) + + - task: PublishBuildArtifacts@1 + displayName: Publish ReleaseConfigs Artifact + inputs: + PathtoPublish: '$(Build.StagingDirectory)/ReleaseConfigs.txt' + PublishLocation: Container + ArtifactName: ReleaseConfigs + + - ${{ if eq(parameters.enablePublishBuildArtifacts, 'true') }}: + - template: /eng/common/templates/steps/publish-logs.yml + parameters: + JobLabel: 'Publish_Artifacts_Logs' diff --git a/eng/common/templates/job/source-build.yml b/eng/common/templates/job/source-build.yml new file mode 100644 index 000000000..5023d36dc --- /dev/null +++ b/eng/common/templates/job/source-build.yml @@ -0,0 +1,60 @@ +parameters: + # This template adds arcade-powered source-build to CI. The template produces a server job with a + # default ID 'Source_Build_Complete' to put in a dependency list if necessary. + + # Specifies the prefix for source-build jobs added to pipeline. Use this if disambiguation needed. + jobNamePrefix: 'Source_Build' + + # Defines the platform on which to run the job. By default, a linux-x64 machine, suitable for + # managed-only repositories. This is an object with these properties: + # + # name: '' + # The name of the job. This is included in the job ID. + # targetRID: '' + # The name of the target RID to use, instead of the one auto-detected by Arcade. + # nonPortable: false + # Enables non-portable mode. This means a more specific RID (e.g. fedora.32-x64 rather than + # linux-x64), and compiling against distro-provided packages rather than portable ones. + # skipPublishValidation: false + # Disables publishing validation. By default, a check is performed to ensure no packages are + # published by source-build. + # container: '' + # A container to use. Runs in docker. + # pool: {} + # A pool to use. Runs directly on an agent. + # buildScript: '' + # Specifies the build script to invoke to perform the build in the repo. The default + # './build.sh' should work for typical Arcade repositories, but this is customizable for + # difficult situations. + # jobProperties: {} + # A list of job properties to inject at the top level, for potential extensibility beyond + # container and pool. + platform: {} + + # The default VM host AzDO pool. This should be capable of running Docker containers: almost all + # source-build builds run in Docker, including the default managed platform. + defaultContainerHostPool: + vmImage: ubuntu-20.04 + +jobs: +- job: ${{ parameters.jobNamePrefix }}_${{ parameters.platform.name }} + displayName: Source-Build (${{ parameters.platform.name }}) + + ${{ each property in parameters.platform.jobProperties }}: + ${{ property.key }}: ${{ property.value }} + + ${{ if ne(parameters.platform.container, '') }}: + container: ${{ parameters.platform.container }} + + ${{ if eq(parameters.platform.pool, '') }}: + pool: ${{ parameters.defaultContainerHostPool }} + ${{ if ne(parameters.platform.pool, '') }}: + pool: ${{ parameters.platform.pool }} + + workspace: + clean: all + + steps: + - template: /eng/common/templates/steps/source-build.yml + parameters: + platform: ${{ parameters.platform }} diff --git a/eng/common/templates/job/source-index-stage1.yml b/eng/common/templates/job/source-index-stage1.yml new file mode 100644 index 000000000..b58d42364 --- /dev/null +++ b/eng/common/templates/job/source-index-stage1.yml @@ -0,0 +1,62 @@ +parameters: + runAsPublic: false + sourceIndexPackageVersion: 1.0.1-20210614.1 + sourceIndexPackageSource: https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json + sourceIndexBuildCommand: powershell -NoLogo -NoProfile -ExecutionPolicy Bypass -Command "eng/common/build.ps1 -restore -build -binarylog -ci" + preSteps: [] + binlogPath: artifacts/log/Debug/Build.binlog + pool: + vmImage: vs2017-win2016 + condition: '' + dependsOn: '' + +jobs: +- job: SourceIndexStage1 + dependsOn: ${{ parameters.dependsOn }} + condition: ${{ parameters.condition }} + variables: + - name: SourceIndexPackageVersion + value: ${{ parameters.sourceIndexPackageVersion }} + - name: SourceIndexPackageSource + value: ${{ parameters.sourceIndexPackageSource }} + - name: BinlogPath + value: ${{ parameters.binlogPath }} + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - group: source-dot-net stage1 variables + + pool: ${{ parameters.pool }} + steps: + - ${{ each preStep in parameters.preSteps }}: + - ${{ preStep }} + + - task: UseDotNet@2 + displayName: Use .NET Core sdk 3.1 + inputs: + packageType: sdk + version: 3.1.x + + - task: UseDotNet@2 + displayName: Use .NET Core sdk + inputs: + useGlobalJson: true + + - script: | + dotnet tool install BinLogToSln --version $(SourceIndexPackageVersion) --add-source $(SourceIndexPackageSource) --tool-path .source-index/tools + dotnet tool install UploadIndexStage1 --version $(SourceIndexPackageVersion) --add-source $(SourceIndexPackageSource) --tool-path .source-index/tools + echo ##vso[task.prependpath]$(Build.SourcesDirectory)/.source-index/tools + displayName: Download Tools + + - script: ${{ parameters.sourceIndexBuildCommand }} + displayName: Build Repository + + - script: BinLogToSln -i $(BinlogPath) -r $(Build.SourcesDirectory) -n $(Build.Repository.Name) -o .source-index/stage1output + displayName: Process Binlog into indexable sln + env: + DOTNET_ROLL_FORWARD_ON_NO_CANDIDATE_FX: 2 + + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - script: UploadIndexStage1 -i .source-index/stage1output -n $(Build.Repository.Name) + displayName: Upload stage1 artifacts to source index + env: + BLOB_CONTAINER_URL: $(source-dot-net-stage1-blob-container-url) + DOTNET_ROLL_FORWARD_ON_NO_CANDIDATE_FX: 2 diff --git a/eng/common/templates/jobs/jobs.yml b/eng/common/templates/jobs/jobs.yml new file mode 100644 index 000000000..a1f8fce96 --- /dev/null +++ b/eng/common/templates/jobs/jobs.yml @@ -0,0 +1,99 @@ +parameters: + # See schema documentation in /Documentation/AzureDevOps/TemplateSchema.md + continueOnError: false + + # Optional: Include PublishBuildArtifacts task + enablePublishBuildArtifacts: false + + # Optional: Enable publishing using release pipelines + enablePublishUsingPipelines: false + + # Optional: Enable running the source-build jobs to build repo from source + enableSourceBuild: false + + # Optional: Parameters for source-build template. + # See /eng/common/templates/jobs/source-build.yml for options + sourceBuildParameters: [] + + graphFileGeneration: + # Optional: Enable generating the graph files at the end of the build + enabled: false + # Optional: Include toolset dependencies in the generated graph files + includeToolset: false + + # Required: A collection of jobs to run - https://docs.microsoft.com/en-us/azure/devops/pipelines/yaml-schema?view=vsts&tabs=schema#job + jobs: [] + + # Optional: Override automatically derived dependsOn value for "publish build assets" job + publishBuildAssetsDependsOn: '' + + # Optional: should run as a public build even in the internal project + # if 'true', the build won't run any of the internal only steps, even if it is running in non-public projects. + runAsPublic: false + + enableSourceIndex: false + sourceIndexParams: {} + +# Internal resources (telemetry, microbuild) can only be accessed from non-public projects, +# and some (Microbuild) should only be applied to non-PR cases for internal builds. + +jobs: +- ${{ each job in parameters.jobs }}: + - template: ../job/job.yml + parameters: + # pass along parameters + ${{ each parameter in parameters }}: + ${{ if ne(parameter.key, 'jobs') }}: + ${{ parameter.key }}: ${{ parameter.value }} + + # pass along job properties + ${{ each property in job }}: + ${{ if ne(property.key, 'job') }}: + ${{ property.key }}: ${{ property.value }} + + name: ${{ job.job }} + +- ${{ if eq(parameters.enableSourceBuild, true) }}: + - template: /eng/common/templates/jobs/source-build.yml + parameters: + allCompletedJobId: Source_Build_Complete + ${{ each parameter in parameters.sourceBuildParameters }}: + ${{ parameter.key }}: ${{ parameter.value }} + +- ${{ if eq(parameters.enableSourceIndex, 'true') }}: + - template: ../job/source-index-stage1.yml + parameters: + runAsPublic: ${{ parameters.runAsPublic }} + ${{ each parameter in parameters.sourceIndexParams }}: + ${{ parameter.key }}: ${{ parameter.value }} + +- ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + + - ${{ if or(eq(parameters.enablePublishBuildAssets, true), eq(parameters.artifacts.publish.manifests, 'true'), ne(parameters.artifacts.publish.manifests, '')) }}: + - template: ../job/publish-build-assets.yml + parameters: + continueOnError: ${{ parameters.continueOnError }} + dependsOn: + - ${{ if ne(parameters.publishBuildAssetsDependsOn, '') }}: + - ${{ each job in parameters.publishBuildAssetsDependsOn }}: + - ${{ job.job }} + - ${{ if eq(parameters.publishBuildAssetsDependsOn, '') }}: + - ${{ each job in parameters.jobs }}: + - ${{ job.job }} + - ${{ if eq(parameters.enableSourceBuild, true) }}: + - Source_Build_Complete + pool: + vmImage: vs2017-win2016 + runAsPublic: ${{ parameters.runAsPublic }} + publishUsingPipelines: ${{ parameters.enablePublishUsingPipelines }} + enablePublishBuildArtifacts: ${{ parameters.enablePublishBuildArtifacts }} + + - ${{ if eq(parameters.graphFileGeneration.enabled, true) }}: + - template: ../job/generate-graph-files.yml + parameters: + continueOnError: ${{ parameters.continueOnError }} + includeToolset: ${{ parameters.graphFileGeneration.includeToolset }} + dependsOn: + - Asset_Registry_Publish + pool: + vmImage: vs2017-win2016 diff --git a/eng/common/templates/jobs/source-build.yml b/eng/common/templates/jobs/source-build.yml new file mode 100644 index 000000000..00aa98eb3 --- /dev/null +++ b/eng/common/templates/jobs/source-build.yml @@ -0,0 +1,46 @@ +parameters: + # This template adds arcade-powered source-build to CI. A job is created for each platform, as + # well as an optional server job that completes when all platform jobs complete. + + # The name of the "join" job for all source-build platforms. If set to empty string, the job is + # not included. Existing repo pipelines can use this job depend on all source-build jobs + # completing without maintaining a separate list of every single job ID: just depend on this one + # server job. By default, not included. Recommended name if used: 'Source_Build_Complete'. + allCompletedJobId: '' + + # See /eng/common/templates/job/source-build.yml + jobNamePrefix: 'Source_Build' + + # This is the default platform provided by Arcade, intended for use by a managed-only repo. + defaultManagedPlatform: + name: 'Managed' + container: 'mcr.microsoft.com/dotnet-buildtools/prereqs:centos-7-3e800f1-20190501005343' + + # Defines the platforms on which to run build jobs. One job is created for each platform, and the + # object in this array is sent to the job template as 'platform'. If no platforms are specified, + # one job runs on 'defaultManagedPlatform'. + platforms: [] + +jobs: + +- ${{ if ne(parameters.allCompletedJobId, '') }}: + - job: ${{ parameters.allCompletedJobId }} + displayName: Source-Build Complete + pool: server + dependsOn: + - ${{ each platform in parameters.platforms }}: + - ${{ parameters.jobNamePrefix }}_${{ platform.name }} + - ${{ if eq(length(parameters.platforms), 0) }}: + - ${{ parameters.jobNamePrefix }}_${{ parameters.defaultManagedPlatform.name }} + +- ${{ each platform in parameters.platforms }}: + - template: /eng/common/templates/job/source-build.yml + parameters: + jobNamePrefix: ${{ parameters.jobNamePrefix }} + platform: ${{ platform }} + +- ${{ if eq(length(parameters.platforms), 0) }}: + - template: /eng/common/templates/job/source-build.yml + parameters: + jobNamePrefix: ${{ parameters.jobNamePrefix }} + platform: ${{ parameters.defaultManagedPlatform }} diff --git a/eng/common/templates/phases/base.yml b/eng/common/templates/phases/base.yml new file mode 100644 index 000000000..0123cf43b --- /dev/null +++ b/eng/common/templates/phases/base.yml @@ -0,0 +1,130 @@ +parameters: + # Optional: Clean sources before building + clean: true + + # Optional: Git fetch depth + fetchDepth: '' + + # Optional: name of the phase (not specifying phase name may cause name collisions) + name: '' + # Optional: display name of the phase + displayName: '' + + # Optional: condition for the job to run + condition: '' + + # Optional: dependencies of the phase + dependsOn: '' + + # Required: A defined YAML queue + queue: {} + + # Required: build steps + steps: [] + + # Optional: variables + variables: {} + + # Optional: should run as a public build even in the internal project + # if 'true', the build won't run any of the internal only steps, even if it is running in non-public projects. + runAsPublic: false + + ## Telemetry variables + + # Optional: enable sending telemetry + # if 'true', these "variables" must be specified in the variables object or as part of the queue matrix + # _HelixBuildConfig - differentiate between Debug, Release, other + # _HelixSource - Example: build/product + # _HelixType - Example: official/dotnet/arcade/$(Build.SourceBranch) + enableTelemetry: false + + # Optional: Enable installing Microbuild plugin + # if 'true', these "variables" must be specified in the variables object or as part of the queue matrix + # _TeamName - the name of your team + # _SignType - 'test' or 'real' + enableMicrobuild: false + +# Internal resources (telemetry, microbuild) can only be accessed from non-public projects, +# and some (Microbuild) should only be applied to non-PR cases for internal builds. + +phases: +- phase: ${{ parameters.name }} + + ${{ if ne(parameters.displayName, '') }}: + displayName: ${{ parameters.displayName }} + + ${{ if ne(parameters.condition, '') }}: + condition: ${{ parameters.condition }} + + ${{ if ne(parameters.dependsOn, '') }}: + dependsOn: ${{ parameters.dependsOn }} + + queue: ${{ parameters.queue }} + + ${{ if ne(parameters.variables, '') }}: + variables: + ${{ insert }}: ${{ parameters.variables }} + + steps: + - checkout: self + clean: ${{ parameters.clean }} + ${{ if ne(parameters.fetchDepth, '') }}: + fetchDepth: ${{ parameters.fetchDepth }} + + - ${{ if eq(parameters.enableTelemetry, 'true') }}: + - template: /eng/common/templates/steps/telemetry-start.yml + parameters: + buildConfig: $(_HelixBuildConfig) + helixSource: $(_HelixSource) + helixType: $(_HelixType) + runAsPublic: ${{ parameters.runAsPublic }} + + - ${{ if eq(parameters.enableMicrobuild, 'true') }}: + # Internal only resource, and Microbuild signing shouldn't be applied to PRs. + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: MicroBuildSigningPlugin@2 + displayName: Install MicroBuild plugin + inputs: + signType: $(_SignType) + zipSources: false + feedSource: https://dnceng.pkgs.visualstudio.com/_packaging/MicroBuildToolset/nuget/v3/index.json + + env: + TeamName: $(_TeamName) + continueOnError: false + condition: and(succeeded(), in(variables['_SignType'], 'real', 'test'), eq(variables['Agent.Os'], 'Windows_NT')) + + # Run provided build steps + - ${{ parameters.steps }} + + - ${{ if eq(parameters.enableMicrobuild, 'true') }}: + # Internal only resources + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: MicroBuildCleanup@1 + displayName: Execute Microbuild cleanup tasks + condition: and(always(), in(variables['_SignType'], 'real', 'test'), eq(variables['Agent.Os'], 'Windows_NT')) + env: + TeamName: $(_TeamName) + + - ${{ if eq(parameters.enableTelemetry, 'true') }}: + - template: /eng/common/templates/steps/telemetry-end.yml + parameters: + helixSource: $(_HelixSource) + helixType: $(_HelixType) + + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: CopyFiles@2 + displayName: Gather Asset Manifests + inputs: + SourceFolder: '$(Build.SourcesDirectory)/artifacts/log/$(_BuildConfig)/AssetManifest' + TargetFolder: '$(Build.StagingDirectory)/AssetManifests' + continueOnError: false + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) + - task: PublishBuildArtifacts@1 + displayName: Push Asset Manifests + inputs: + PathtoPublish: '$(Build.StagingDirectory)/AssetManifests' + PublishLocation: Container + ArtifactName: AssetManifests + continueOnError: false + condition: and(succeeded(), eq(variables['_DotNetPublishToBlobFeed'], 'true')) diff --git a/eng/common/templates/phases/publish-build-assets.yml b/eng/common/templates/phases/publish-build-assets.yml new file mode 100644 index 000000000..4e51e472e --- /dev/null +++ b/eng/common/templates/phases/publish-build-assets.yml @@ -0,0 +1,52 @@ +parameters: + dependsOn: '' + queue: {} + configuration: 'Debug' + condition: succeeded() + continueOnError: false + runAsPublic: false + publishUsingPipelines: false +phases: + - phase: Asset_Registry_Publish + displayName: Publish to Build Asset Registry + dependsOn: ${{ parameters.dependsOn }} + queue: ${{ parameters.queue }} + variables: + _BuildConfig: ${{ parameters.configuration }} + steps: + - ${{ if and(eq(parameters.runAsPublic, 'false'), ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}: + - task: DownloadBuildArtifacts@0 + displayName: Download artifact + inputs: + artifactName: AssetManifests + downloadPath: '$(Build.StagingDirectory)/Download' + checkDownloadedFiles: true + condition: ${{ parameters.condition }} + continueOnError: ${{ parameters.continueOnError }} + - task: AzureKeyVault@1 + inputs: + azureSubscription: 'DotNet-Engineering-Services_KeyVault' + KeyVaultName: EngKeyVault + SecretsFilter: 'MaestroAccessToken' + condition: ${{ parameters.condition }} + continueOnError: ${{ parameters.continueOnError }} + - task: PowerShell@2 + displayName: Publish Build Assets + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishBuildAssets -restore -msbuildEngine dotnet + /p:ManifestsPath='$(Build.StagingDirectory)/Download/AssetManifests' + /p:BuildAssetRegistryToken=$(MaestroAccessToken) + /p:MaestroApiEndpoint=https://maestro-prod.westus2.cloudapp.azure.com + /p:PublishUsingPipelines=${{ parameters.publishUsingPipelines }} + /p:Configuration=$(_BuildConfig) + condition: ${{ parameters.condition }} + continueOnError: ${{ parameters.continueOnError }} + - task: PublishBuildArtifacts@1 + displayName: Publish Logs to VSTS + inputs: + PathtoPublish: '$(Build.SourcesDirectory)/artifacts/log/$(_BuildConfig)' + PublishLocation: Container + ArtifactName: $(Agent.Os)_Asset_Registry_Publish + continueOnError: true + condition: always() diff --git a/eng/common/templates/post-build/channels/generic-internal-channel.yml b/eng/common/templates/post-build/channels/generic-internal-channel.yml new file mode 100644 index 000000000..8990dfc8c --- /dev/null +++ b/eng/common/templates/post-build/channels/generic-internal-channel.yml @@ -0,0 +1,190 @@ +parameters: + BARBuildId: '' + PromoteToChannelIds: '' + artifactsPublishingAdditionalParameters: '' + dependsOn: + - Validate + publishInstallersAndChecksums: true + symbolPublishingAdditionalParameters: '' + stageName: '' + channelName: '' + channelId: '' + transportFeed: '' + shippingFeed: '' + symbolsFeed: '' + +stages: +- stage: ${{ parameters.stageName }} + dependsOn: ${{ parameters.dependsOn }} + variables: + - template: ../common-variables.yml + displayName: ${{ parameters.channelName }} Publishing + jobs: + - template: ../setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - job: publish_symbols + displayName: Symbol Publishing + dependsOn: setupMaestroVars + condition: contains(dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'], format('[{0}]', ${{ parameters.channelId }} )) + variables: + - group: DotNet-Symbol-Server-Pats + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - script: echo "##vso[task.logissue type=warning]Going forward, v2 Arcade publishing is no longer supported. Please read https://github.com/dotnet/arcade/blob/main/Documentation/CorePackages/Publishing.md for details, then contact dnceng if you have further questions." + displayName: Warn about v2 Arcade Publishing Usage + + # This is necessary whenever we want to publish/restore to an AzDO private feed + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + PdbArtifacts/** + BlobArtifacts/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + checkDownloadedFiles: true + + # This is necessary whenever we want to publish/restore to an AzDO private feed + # Since sdk-task.ps1 tries to restore packages we need to do this authentication here + # otherwise it'll complain about accessing a private feed. + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: eng\common\enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishToSymbolServers -restore -msbuildEngine dotnet + /p:DotNetSymbolServerTokenMsdl=$(microsoft-symbol-server-pat) + /p:DotNetSymbolServerTokenSymWeb=$(symweb-symbol-server-pat) + /p:PDBArtifactsDirectory='$(Build.ArtifactStagingDirectory)/PDBArtifacts/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:SymbolPublishingExclusionsFile='$(Build.SourcesDirectory)/eng/SymbolPublishingExclusionsFile.txt' + /p:Configuration=Release + /p:PublishToMSDL=false + ${{ parameters.symbolPublishingAdditionalParameters }} + + - template: ../../steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'SymbolPublishing' + + - job: publish_assets + displayName: Publish Assets + dependsOn: setupMaestroVars + timeoutInMinutes: 120 + variables: + - name: BARBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.BARBuildId'] ] + - name: IsStableBuild + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.IsStableBuild'] ] + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + condition: contains(dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'], format('[{0}]', ${{ parameters.channelId }} )) + pool: + vmImage: 'windows-2019' + steps: + - script: echo "##vso[task.logissue type=warning]Going forward, v2 Arcade publishing is no longer supported. Please read https://github.com/dotnet/arcade/blob/main/Documentation/CorePackages/Publishing.md for details, then contact dnceng if you have further questions." + displayName: Warn about v2 Arcade Publishing Usage + + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + PackageArtifacts/** + BlobArtifacts/** + AssetManifests/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + checkDownloadedFiles: true + + - task: NuGetToolInstaller@1 + displayName: 'Install NuGet.exe' + + # This is necessary whenever we want to publish/restore to an AzDO private feed + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: eng\common\enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish Assets + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishArtifactsInManifest -restore -msbuildEngine dotnet + /p:PublishingInfraVersion=2 + /p:IsStableBuild=$(IsStableBuild) + /p:IsInternalBuild=$(IsInternalBuild) + /p:RepositoryName=$(Build.Repository.Name) + /p:CommitSha=$(Build.SourceVersion) + /p:NugetPath=$(NuGetExeToolPath) + /p:AzdoTargetFeedPAT='$(dn-bot-dnceng-universal-packages-rw)' + /p:AzureStorageTargetFeedPAT='$(dotnetfeed-storage-access-key-1)' + /p:BARBuildId=$(BARBuildId) + /p:MaestroApiEndpoint='$(MaestroApiEndPoint)' + /p:BuildAssetRegistryToken='$(MaestroApiAccessToken)' + /p:ManifestsBasePath='$(Build.ArtifactStagingDirectory)/AssetManifests/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:PackageBasePath='$(Build.ArtifactStagingDirectory)/PackageArtifacts/' + /p:Configuration=Release + /p:PublishInstallersAndChecksums=${{ parameters.publishInstallersAndChecksums }} + /p:ChecksumsTargetStaticFeed=$(InternalChecksumsBlobFeedUrl) + /p:ChecksumsAzureAccountKey=$(InternalChecksumsBlobFeedKey) + /p:InstallersTargetStaticFeed=$(InternalInstallersBlobFeedUrl) + /p:InstallersAzureAccountKey=$(InternalInstallersBlobFeedKey) + /p:AzureDevOpsStaticShippingFeed='${{ parameters.shippingFeed }}' + /p:AzureDevOpsStaticShippingFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:AzureDevOpsStaticTransportFeed='${{ parameters.transportFeed }}' + /p:AzureDevOpsStaticTransportFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:AzureDevOpsStaticSymbolsFeed='${{ parameters.symbolsFeed }}' + /p:AzureDevOpsStaticSymbolsFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:PublishToMSDL=false + ${{ parameters.artifactsPublishingAdditionalParameters }} + + - template: ../../steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'AssetsPublishing' + + - template: ../../steps/add-build-to-channel.yml + parameters: + ChannelId: ${{ parameters.channelId }} diff --git a/eng/common/templates/post-build/channels/generic-public-channel.yml b/eng/common/templates/post-build/channels/generic-public-channel.yml new file mode 100644 index 000000000..3220c6a4f --- /dev/null +++ b/eng/common/templates/post-build/channels/generic-public-channel.yml @@ -0,0 +1,192 @@ +parameters: + BARBuildId: '' + PromoteToChannelIds: '' + artifactsPublishingAdditionalParameters: '' + dependsOn: + - Validate + publishInstallersAndChecksums: true + symbolPublishingAdditionalParameters: '' + stageName: '' + channelName: '' + channelId: '' + transportFeed: '' + shippingFeed: '' + symbolsFeed: '' + # If the channel name is empty, no links will be generated + akaMSChannelName: '' + +stages: +- stage: ${{ parameters.stageName }} + dependsOn: ${{ parameters.dependsOn }} + variables: + - template: ../common-variables.yml + displayName: ${{ parameters.channelName }} Publishing + jobs: + - template: ../setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - job: publish_symbols + displayName: Symbol Publishing + dependsOn: setupMaestroVars + condition: contains(dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'], format('[{0}]', ${{ parameters.channelId }} )) + variables: + - group: DotNet-Symbol-Server-Pats + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - script: echo "##vso[task.logissue type=warning]Going forward, v2 Arcade publishing is no longer supported. Please read https://github.com/dotnet/arcade/blob/main/Documentation/CorePackages/Publishing.md for details, then contact dnceng if you have further questions." + displayName: Warn about v2 Arcade Publishing Usage + + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + PdbArtifacts/** + BlobArtifacts/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + checkDownloadedFiles: true + + # This is necessary whenever we want to publish/restore to an AzDO private feed + # Since sdk-task.ps1 tries to restore packages we need to do this authentication here + # otherwise it'll complain about accessing a private feed. + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: eng\common\enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishToSymbolServers -restore -msbuildEngine dotnet + /p:DotNetSymbolServerTokenMsdl=$(microsoft-symbol-server-pat) + /p:DotNetSymbolServerTokenSymWeb=$(symweb-symbol-server-pat) + /p:PDBArtifactsDirectory='$(Build.ArtifactStagingDirectory)/PDBArtifacts/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:SymbolPublishingExclusionsFile='$(Build.SourcesDirectory)/eng/SymbolPublishingExclusionsFile.txt' + /p:Configuration=Release + ${{ parameters.symbolPublishingAdditionalParameters }} + + - template: ../../steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'SymbolPublishing' + + - job: publish_assets + displayName: Publish Assets + dependsOn: setupMaestroVars + timeoutInMinutes: 120 + variables: + - name: BARBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.BARBuildId'] ] + - name: IsStableBuild + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.IsStableBuild'] ] + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + - name: ArtifactsCategory + value: ${{ coalesce(variables._DotNetArtifactsCategory, '.NETCore') }} + condition: contains(dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'], format('[{0}]', ${{ parameters.channelId }} )) + pool: + vmImage: 'windows-2019' + steps: + - script: echo "##vso[task.logissue type=warning]Going forward, v2 Arcade publishing is no longer supported. Please read https://github.com/dotnet/arcade/blob/main/Documentation/CorePackages/Publishing.md for details, then contact dnceng if you have further questions." + displayName: Warn about v2 Arcade Publishing Usage + + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + PackageArtifacts/** + BlobArtifacts/** + AssetManifests/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + checkDownloadedFiles: true + + - task: NuGetToolInstaller@1 + displayName: 'Install NuGet.exe' + + # This is necessary whenever we want to publish/restore to an AzDO private feed + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: eng\common\enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish Assets + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task PublishArtifactsInManifest -restore -msbuildEngine dotnet + /p:PublishingInfraVersion=2 + /p:ArtifactsCategory=$(ArtifactsCategory) + /p:IsStableBuild=$(IsStableBuild) + /p:IsInternalBuild=$(IsInternalBuild) + /p:RepositoryName=$(Build.Repository.Name) + /p:CommitSha=$(Build.SourceVersion) + /p:NugetPath=$(NuGetExeToolPath) + /p:AzdoTargetFeedPAT='$(dn-bot-dnceng-universal-packages-rw)' + /p:AzureStorageTargetFeedPAT='$(dotnetfeed-storage-access-key-1)' + /p:BARBuildId=$(BARBuildId) + /p:MaestroApiEndpoint='$(MaestroApiEndPoint)' + /p:BuildAssetRegistryToken='$(MaestroApiAccessToken)' + /p:ManifestsBasePath='$(Build.ArtifactStagingDirectory)/AssetManifests/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:PackageBasePath='$(Build.ArtifactStagingDirectory)/PackageArtifacts/' + /p:Configuration=Release + /p:PublishInstallersAndChecksums=${{ parameters.publishInstallersAndChecksums }} + /p:InstallersTargetStaticFeed=$(InstallersBlobFeedUrl) + /p:InstallersAzureAccountKey=$(dotnetcli-storage-key) + /p:ChecksumsTargetStaticFeed=$(ChecksumsBlobFeedUrl) + /p:ChecksumsAzureAccountKey=$(dotnetclichecksums-storage-key) + /p:AzureDevOpsStaticShippingFeed='${{ parameters.shippingFeed }}' + /p:AzureDevOpsStaticShippingFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:AzureDevOpsStaticTransportFeed='${{ parameters.transportFeed }}' + /p:AzureDevOpsStaticTransportFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:AzureDevOpsStaticSymbolsFeed='${{ parameters.symbolsFeed }}' + /p:AzureDevOpsStaticSymbolsFeedKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:LatestLinkShortUrlPrefix=dotnet/'${{ parameters.akaMSChannelName }}' + /p:AkaMSClientId=$(akams-client-id) + /p:AkaMSClientSecret=$(akams-client-secret) + ${{ parameters.artifactsPublishingAdditionalParameters }} + + - template: ../../steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'AssetsPublishing' + + - template: ../../steps/add-build-to-channel.yml + parameters: + ChannelId: ${{ parameters.channelId }} diff --git a/eng/common/templates/post-build/common-variables.yml b/eng/common/templates/post-build/common-variables.yml new file mode 100644 index 000000000..c99fd7503 --- /dev/null +++ b/eng/common/templates/post-build/common-variables.yml @@ -0,0 +1,99 @@ +variables: + - group: AzureDevOps-Artifact-Feeds-Pats + - group: DotNet-Blob-Feed + - group: DotNet-DotNetCli-Storage + - group: DotNet-MSRC-Storage + - group: Publish-Build-Assets + + # .NET Core 3.1 Dev + - name: PublicDevRelease_31_Channel_Id + value: 128 + + # .NET 5 Dev + - name: Net_5_Dev_Channel_Id + value: 131 + + # .NET Eng - Validation + - name: Net_Eng_Validation_Channel_Id + value: 9 + + # .NET Eng - Latest + - name: Net_Eng_Latest_Channel_Id + value: 2 + + # .NET 3 Eng - Validation + - name: NET_3_Eng_Validation_Channel_Id + value: 390 + + # .NET 3 Eng + - name: NetCore_3_Tools_Channel_Id + value: 344 + + # .NET Core 3.0 Internal Servicing + - name: InternalServicing_30_Channel_Id + value: 184 + + # .NET Core 3.0 Release + - name: PublicRelease_30_Channel_Id + value: 19 + + # .NET Core 3.1 Release + - name: PublicRelease_31_Channel_Id + value: 129 + + # General Testing + - name: GeneralTesting_Channel_Id + value: 529 + + # .NET Core 3.1 Blazor Features + - name: NetCore_31_Blazor_Features_Channel_Id + value: 531 + + # .NET Core Experimental + - name: NetCore_Experimental_Channel_Id + value: 562 + + # Whether the build is internal or not + - name: IsInternalBuild + value: ${{ and(ne(variables['System.TeamProject'], 'public'), contains(variables['Build.SourceBranch'], 'internal')) }} + + # Default Maestro++ API Endpoint and API Version + - name: MaestroApiEndPoint + value: "https://maestro-prod.westus2.cloudapp.azure.com" + - name: MaestroApiAccessToken + value: $(MaestroAccessToken) + - name: MaestroApiVersion + value: "2020-02-20" + + - name: SourceLinkCLIVersion + value: 3.0.0 + - name: SymbolToolVersion + value: 1.0.1 + + # Feed Configurations + # These should include the suffix "/index.json" + + # Default locations for Installers and checksums + # Public Locations + - name: ChecksumsBlobFeedUrl + value: https://dotnetclichecksums.blob.core.windows.net/dotnet/index.json + - name: InstallersBlobFeedUrl + value: https://dotnetcli.blob.core.windows.net/dotnet/index.json + + # Private Locations + - name: InternalChecksumsBlobFeedUrl + value: https://dotnetclichecksumsmsrc.blob.core.windows.net/dotnet/index.json + - name: InternalChecksumsBlobFeedKey + value: $(dotnetclichecksumsmsrc-storage-key) + + - name: InternalInstallersBlobFeedUrl + value: https://dotnetclimsrc.blob.core.windows.net/dotnet/index.json + - name: InternalInstallersBlobFeedKey + value: $(dotnetclimsrc-access-key) + + # Skip component governance and codesign validation for SDL. These jobs + # create no content. + - name: skipComponentGovernanceDetection + value: true + - name: runCodesignValidationInjection + value: false diff --git a/eng/common/templates/post-build/post-build.yml b/eng/common/templates/post-build/post-build.yml new file mode 100644 index 000000000..4f79cf0f3 --- /dev/null +++ b/eng/common/templates/post-build/post-build.yml @@ -0,0 +1,589 @@ +parameters: + # Which publishing infra should be used. THIS SHOULD MATCH THE VERSION ON THE BUILD MANIFEST. + # Publishing V2 accepts optionally outlining the publishing stages - default is inline. + # Publishing V3 DOES NOT accept inlining the publishing stages. + publishingInfraVersion: 2 + # When set to true the publishing templates from the repo will be used + # otherwise Darc add-build-to-channel will be used to trigger the promotion pipeline + inline: true + + # Only used if inline==false. When set to true will stall the current build until + # the Promotion Pipeline build finishes. Otherwise, the current build will continue + # execution concurrently with the promotion build. + waitPublishingFinish: true + + BARBuildId: '' + PromoteToChannelIds: '' + + enableSourceLinkValidation: false + enableSigningValidation: true + enableSymbolValidation: false + enableNugetValidation: true + publishInstallersAndChecksums: true + SDLValidationParameters: + enable: false + continueOnError: false + params: '' + artifactNames: '' + downloadArtifacts: true + + # These parameters let the user customize the call to sdk-task.ps1 for publishing + # symbols & general artifacts as well as for signing validation + symbolPublishingAdditionalParameters: '' + artifactsPublishingAdditionalParameters: '' + signingValidationAdditionalParameters: '' + + # Which stages should finish execution before post-build stages start + validateDependsOn: + - build + publishDependsOn: + - Validate + + # Channel ID's instantiated in this file. + # When adding a new channel implementation the call to `check-channel-consistency.ps1` + # needs to be updated with the new channel ID + NetEngLatestChannelId: 2 + NetEngValidationChannelId: 9 + NetDev5ChannelId: 131 + NetDev6ChannelId: 1296 + GeneralTestingChannelId: 529 + NETCoreToolingDevChannelId: 548 + NETCoreToolingReleaseChannelId: 549 + NETInternalToolingChannelId: 551 + NETCoreExperimentalChannelId: 562 + NetEngServicesIntChannelId: 678 + NetEngServicesProdChannelId: 679 + NetCoreSDK313xxChannelId: 759 + NetCoreSDK313xxInternalChannelId: 760 + NetCoreSDK314xxChannelId: 921 + NetCoreSDK314xxInternalChannelId: 922 + VS166ChannelId: 1010 + VS167ChannelId: 1011 + VS168ChannelId: 1154 + VSMasterChannelId: 1012 + VS169ChannelId: 1473 + VS1610ChannelId: 1692 + +stages: +- ${{ if or(and(le(parameters.publishingInfraVersion, 2), eq(parameters.inline, 'true')), eq( parameters.enableNugetValidation, 'true'), eq(parameters.enableSigningValidation, 'true'), eq(parameters.enableSourceLinkValidation, 'true'), eq(parameters.SDLValidationParameters.enable, 'true')) }}: + - stage: Validate + dependsOn: ${{ parameters.validateDependsOn }} + displayName: Validate Build Assets + variables: + - template: common-variables.yml + jobs: + - template: setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - ${{ if and(le(parameters.publishingInfraVersion, 2), eq(parameters.inline, 'true')) }}: + - job: + displayName: Post-build Checks + dependsOn: setupMaestroVars + variables: + - name: TargetChannels + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: PowerShell@2 + displayName: Maestro Channels Consistency + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/check-channel-consistency.ps1 + arguments: -PromoteToChannels "$(TargetChannels)" + -AvailableChannelIds ${{parameters.NetEngLatestChannelId}},${{parameters.NetEngValidationChannelId}},${{parameters.NetDev5ChannelId}},${{parameters.NetDev6ChannelId}},${{parameters.GeneralTestingChannelId}},${{parameters.NETCoreToolingDevChannelId}},${{parameters.NETCoreToolingReleaseChannelId}},${{parameters.NETInternalToolingChannelId}},${{parameters.NETCoreExperimentalChannelId}},${{parameters.NetEngServicesIntChannelId}},${{parameters.NetEngServicesProdChannelId}},${{parameters.NetCoreSDK313xxChannelId}},${{parameters.NetCoreSDK313xxInternalChannelId}},${{parameters.NetCoreSDK314xxChannelId}},${{parameters.NetCoreSDK314xxInternalChannelId}},${{parameters.VS166ChannelId}},${{parameters.VS167ChannelId}},${{parameters.VS168ChannelId}},${{parameters.VSMasterChannelId}},${{parameters.VS169ChannelId}},${{parameters.VS1610ChannelId}} + + - job: + displayName: NuGet Validation + dependsOn: setupMaestroVars + condition: eq( ${{ parameters.enableNugetValidation }}, 'true') + pool: + vmImage: 'windows-2019' + variables: + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Package Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: PackageArtifacts + checkDownloadedFiles: true + + - task: PowerShell@2 + displayName: Validate + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/nuget-validation.ps1 + arguments: -PackagesPath $(Build.ArtifactStagingDirectory)/PackageArtifacts/ + -ToolDestinationPath $(Agent.BuildDirectory)/Extract/ + + - job: + displayName: Signing Validation + dependsOn: setupMaestroVars + condition: and( eq( ${{ parameters.enableSigningValidation }}, 'true'), ne( variables['PostBuildSign'], 'true')) + variables: + - template: common-variables.yml + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Package Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: PackageArtifacts + checkDownloadedFiles: true + itemPattern: | + ** + !**/Microsoft.SourceBuild.Intermediate.*.nupkg + + # This is necessary whenever we want to publish/restore to an AzDO private feed + # Since sdk-task.ps1 tries to restore packages we need to do this authentication here + # otherwise it'll complain about accessing a private feed. + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: eng\common\enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + # Signing validation will optionally work with the buildmanifest file which is downloaded from + # Azure DevOps above. + - task: PowerShell@2 + displayName: Validate + inputs: + filePath: eng\common\sdk-task.ps1 + arguments: -task SigningValidation -restore -msbuildEngine vs + /p:PackageBasePath='$(Build.ArtifactStagingDirectory)/PackageArtifacts' + /p:SignCheckExclusionsFile='$(Build.SourcesDirectory)/eng/SignCheckExclusionsFile.txt' + ${{ parameters.signingValidationAdditionalParameters }} + + - template: ../steps/publish-logs.yml + parameters: + StageLabel: 'Validation' + JobLabel: 'Signing' + + - job: + displayName: SourceLink Validation + dependsOn: setupMaestroVars + condition: eq( ${{ parameters.enableSourceLinkValidation }}, 'true') + variables: + - template: common-variables.yml + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Blob Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: BlobArtifacts + checkDownloadedFiles: true + + - task: PowerShell@2 + displayName: Validate + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/sourcelink-validation.ps1 + arguments: -InputPath $(Build.ArtifactStagingDirectory)/BlobArtifacts/ + -ExtractPath $(Agent.BuildDirectory)/Extract/ + -GHRepoName $(Build.Repository.Name) + -GHCommit $(Build.SourceVersion) + -SourcelinkCliVersion $(SourceLinkCLIVersion) + continueOnError: true + + - template: /eng/common/templates/job/execute-sdl.yml + parameters: + enable: ${{ parameters.SDLValidationParameters.enable }} + dependsOn: setupMaestroVars + additionalParameters: ${{ parameters.SDLValidationParameters.params }} + continueOnError: ${{ parameters.SDLValidationParameters.continueOnError }} + artifactNames: ${{ parameters.SDLValidationParameters.artifactNames }} + downloadArtifacts: ${{ parameters.SDLValidationParameters.downloadArtifacts }} + +- ${{ if or(ge(parameters.publishingInfraVersion, 3), eq(parameters.inline, 'false')) }}: + - stage: publish_using_darc + ${{ if or(eq(parameters.enableNugetValidation, 'true'), eq(parameters.enableSigningValidation, 'true'), eq(parameters.enableSourceLinkValidation, 'true'), eq(parameters.SDLValidationParameters.enable, 'true')) }}: + dependsOn: ${{ parameters.publishDependsOn }} + ${{ if and(ne(parameters.enableNugetValidation, 'true'), ne(parameters.enableSigningValidation, 'true'), ne(parameters.enableSourceLinkValidation, 'true'), ne(parameters.SDLValidationParameters.enable, 'true')) }}: + dependsOn: ${{ parameters.validateDependsOn }} + displayName: Publish using Darc + variables: + - template: common-variables.yml + jobs: + - template: setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - job: + displayName: Publish Using Darc + dependsOn: setupMaestroVars + timeoutInMinutes: 120 + variables: + - name: BARBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.BARBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: PowerShell@2 + displayName: Publish Using Darc + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/publish-using-darc.ps1 + arguments: -BuildId $(BARBuildId) + -PublishingInfraVersion ${{ parameters.PublishingInfraVersion }} + -AzdoToken '$(publishing-dnceng-devdiv-code-r-build-re)' + -MaestroToken '$(MaestroApiAccessToken)' + -WaitPublishingFinish ${{ parameters.waitPublishingFinish }} + -PublishInstallersAndChecksums ${{ parameters.publishInstallersAndChecksums }} + -ArtifactsPublishingAdditionalParameters '${{ parameters.artifactsPublishingAdditionalParameters }}' + -SymbolPublishingAdditionalParameters '${{ parameters.symbolPublishingAdditionalParameters }}' + +- ${{ if and(le(parameters.publishingInfraVersion, 2), eq(parameters.inline, 'true')) }}: + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NetCore_Dev5_Publish' + channelName: '.NET 5 Dev' + akaMSChannelName: 'net5/dev' + channelId: ${{ parameters.NetDev5ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet5-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet5/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet5-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NetCore_Dev6_Publish' + channelName: '.NET 6 Dev' + akaMSChannelName: 'net6/dev' + channelId: ${{ parameters.NetDev6ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet6-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet6/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet6-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'Net_Eng_Latest_Publish' + channelName: '.NET Eng - Latest' + akaMSChannelName: 'eng/daily' + channelId: ${{ parameters.NetEngLatestChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'Net_Eng_Validation_Publish' + channelName: '.NET Eng - Validation' + akaMSChannelName: 'eng/validation' + channelId: ${{ parameters.NetEngValidationChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'General_Testing_Publish' + channelName: 'General Testing' + akaMSChannelName: 'generaltesting' + channelId: ${{ parameters.GeneralTestingChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/general-testing/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/general-testing/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/general-testing-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_Tooling_Dev_Publishing' + channelName: '.NET Core Tooling Dev' + channelId: ${{ parameters.NETCoreToolingDevChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_Tooling_Release_Publishing' + channelName: '.NET Core Tooling Release' + channelId: ${{ parameters.NETCoreToolingReleaseChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-internal-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NET_Internal_Tooling_Publishing' + channelName: '.NET Internal Tooling' + channelId: ${{ parameters.NETInternalToolingChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-tools-internal/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-tools-internal/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/internal/_packaging/dotnet-tools-internal-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_Experimental_Publishing' + channelName: '.NET Core Experimental' + channelId: ${{ parameters.NETCoreExperimentalChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-experimental/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-experimental/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-experimental-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'Net_Eng_Services_Int_Publish' + channelName: '.NET Eng Services - Int' + channelId: ${{ parameters.NetEngServicesIntChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'Net_Eng_Services_Prod_Publish' + channelName: '.NET Eng Services - Prod' + channelId: ${{ parameters.NetEngServicesProdChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_SDK_314xx_Publishing' + channelName: '.NET Core SDK 3.1.4xx' + channelId: ${{ parameters.NetCoreSDK314xxChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-internal-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_SDK_314xx_Internal_Publishing' + channelName: '.NET Core SDK 3.1.4xx Internal' + channelId: ${{ parameters.NetCoreSDK314xxInternalChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_SDK_313xx_Publishing' + channelName: '.NET Core SDK 3.1.3xx' + channelId: ${{ parameters.NetCoreSDK313xxChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet3.1-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-internal-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'NETCore_SDK_313xx_Internal_Publishing' + channelName: '.NET Core SDK 3.1.3xx Internal' + channelId: ${{ parameters.NetCoreSDK313xxInternalChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/_packaging/dotnet3.1-internal-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS16_6_Publishing' + channelName: 'VS 16.6' + channelId: ${{ parameters.VS166ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS16_7_Publishing' + channelName: 'VS 16.7' + channelId: ${{ parameters.VS167ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS16_8_Publishing' + channelName: 'VS 16.8' + channelId: ${{ parameters.VS168ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS_Master_Publishing' + channelName: 'VS Master' + channelId: ${{ parameters.VSMasterChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS_16_9_Publishing' + channelName: 'VS 16.9' + channelId: ${{ parameters.VS169ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' + + - template: \eng\common\templates\post-build\channels\generic-public-channel.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + dependsOn: ${{ parameters.publishDependsOn }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + symbolPublishingAdditionalParameters: ${{ parameters.symbolPublishingAdditionalParameters }} + stageName: 'VS_16_10_Publishing' + channelName: 'VS 16.10' + channelId: ${{ parameters.VS1610ChannelId }} + transportFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-transport/nuget/v3/index.json' + shippingFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json' + symbolsFeed: 'https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools-symbols/nuget/v3/index.json' diff --git a/eng/common/templates/post-build/setup-maestro-vars.yml b/eng/common/templates/post-build/setup-maestro-vars.yml new file mode 100644 index 000000000..4a22b2e6f --- /dev/null +++ b/eng/common/templates/post-build/setup-maestro-vars.yml @@ -0,0 +1,78 @@ +parameters: + BARBuildId: '' + PromoteToChannelIds: '' + +jobs: +- job: setupMaestroVars + displayName: Setup Maestro Vars + variables: + - template: common-variables.yml + pool: + vmImage: 'windows-2019' + steps: + - checkout: none + + - ${{ if eq(coalesce(parameters.PromoteToChannelIds, 0), 0) }}: + - task: DownloadBuildArtifacts@0 + displayName: Download Release Configs + inputs: + buildType: current + artifactName: ReleaseConfigs + checkDownloadedFiles: true + + - task: PowerShell@2 + name: setReleaseVars + displayName: Set Release Configs Vars + inputs: + targetType: inline + script: | + try { + if (!$Env:PromoteToMaestroChannels -or $Env:PromoteToMaestroChannels.Trim() -eq '') { + $Content = Get-Content $(Build.StagingDirectory)/ReleaseConfigs/ReleaseConfigs.txt + + $BarId = $Content | Select -Index 0 + $Channels = $Content | Select -Index 1 + $IsStableBuild = $Content | Select -Index 2 + + $AzureDevOpsProject = $Env:System_TeamProject + $AzureDevOpsBuildDefinitionId = $Env:System_DefinitionId + $AzureDevOpsBuildId = $Env:Build_BuildId + } + else { + $buildApiEndpoint = "${Env:MaestroApiEndPoint}/api/builds/${Env:BARBuildId}?api-version=${Env:MaestroApiVersion}" + + $apiHeaders = New-Object 'System.Collections.Generic.Dictionary[[String],[String]]' + $apiHeaders.Add('Accept', 'application/json') + $apiHeaders.Add('Authorization',"Bearer ${Env:MAESTRO_API_TOKEN}") + + $buildInfo = try { Invoke-WebRequest -Method Get -Uri $buildApiEndpoint -Headers $apiHeaders | ConvertFrom-Json } catch { Write-Host "Error: $_" } + + $BarId = $Env:BARBuildId + $Channels = $Env:PromoteToMaestroChannels -split "," + $Channels = $Channels -join "][" + $Channels = "[$Channels]" + + $IsStableBuild = $buildInfo.stable + $AzureDevOpsProject = $buildInfo.azureDevOpsProject + $AzureDevOpsBuildDefinitionId = $buildInfo.azureDevOpsBuildDefinitionId + $AzureDevOpsBuildId = $buildInfo.azureDevOpsBuildId + } + + Write-Host "##vso[task.setvariable variable=BARBuildId;isOutput=true]$BarId" + Write-Host "##vso[task.setvariable variable=TargetChannels;isOutput=true]$Channels" + Write-Host "##vso[task.setvariable variable=IsStableBuild;isOutput=true]$IsStableBuild" + + Write-Host "##vso[task.setvariable variable=AzDOProjectName;isOutput=true]$AzureDevOpsProject" + Write-Host "##vso[task.setvariable variable=AzDOPipelineId;isOutput=true]$AzureDevOpsBuildDefinitionId" + Write-Host "##vso[task.setvariable variable=AzDOBuildId;isOutput=true]$AzureDevOpsBuildId" + } + catch { + Write-Host $_ + Write-Host $_.Exception + Write-Host $_.ScriptStackTrace + exit 1 + } + env: + MAESTRO_API_TOKEN: $(MaestroApiAccessToken) + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToMaestroChannels: ${{ parameters.PromoteToChannelIds }} diff --git a/eng/common/templates/post-build/trigger-subscription.yml b/eng/common/templates/post-build/trigger-subscription.yml new file mode 100644 index 000000000..da669030d --- /dev/null +++ b/eng/common/templates/post-build/trigger-subscription.yml @@ -0,0 +1,13 @@ +parameters: + ChannelId: 0 + +steps: +- task: PowerShell@2 + displayName: Triggering subscriptions + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/trigger-subscriptions.ps1 + arguments: -SourceRepo $(Build.Repository.Uri) + -ChannelId ${{ parameters.ChannelId }} + -MaestroApiAccessToken $(MaestroAccessToken) + -MaestroApiEndPoint $(MaestroApiEndPoint) + -MaestroApiVersion $(MaestroApiVersion) diff --git a/eng/common/templates/steps/add-build-to-channel.yml b/eng/common/templates/steps/add-build-to-channel.yml new file mode 100644 index 000000000..f67a210d6 --- /dev/null +++ b/eng/common/templates/steps/add-build-to-channel.yml @@ -0,0 +1,13 @@ +parameters: + ChannelId: 0 + +steps: +- task: PowerShell@2 + displayName: Add Build to Channel + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/add-build-to-channel.ps1 + arguments: -BuildId $(BARBuildId) + -ChannelId ${{ parameters.ChannelId }} + -MaestroApiAccessToken $(MaestroApiAccessToken) + -MaestroApiEndPoint $(MaestroApiEndPoint) + -MaestroApiVersion $(MaestroApiVersion) diff --git a/eng/common/templates/steps/build-reason.yml b/eng/common/templates/steps/build-reason.yml new file mode 100644 index 000000000..eba58109b --- /dev/null +++ b/eng/common/templates/steps/build-reason.yml @@ -0,0 +1,12 @@ +# build-reason.yml +# Description: runs steps if build.reason condition is valid. conditions is a string of valid build reasons +# to include steps (',' separated). +parameters: + conditions: '' + steps: [] + +steps: + - ${{ if and( not(startsWith(parameters.conditions, 'not')), contains(parameters.conditions, variables['build.reason'])) }}: + - ${{ parameters.steps }} + - ${{ if and( startsWith(parameters.conditions, 'not'), not(contains(parameters.conditions, variables['build.reason']))) }}: + - ${{ parameters.steps }} diff --git a/eng/common/templates/steps/publish-logs.yml b/eng/common/templates/steps/publish-logs.yml new file mode 100644 index 000000000..88f238f36 --- /dev/null +++ b/eng/common/templates/steps/publish-logs.yml @@ -0,0 +1,23 @@ +parameters: + StageLabel: '' + JobLabel: '' + +steps: +- task: Powershell@2 + displayName: Prepare Binlogs to Upload + inputs: + targetType: inline + script: | + New-Item -ItemType Directory $(Build.SourcesDirectory)/PostBuildLogs/${{parameters.StageLabel}}/${{parameters.JobLabel}}/ + Move-Item -Path $(Build.SourcesDirectory)/artifacts/log/Debug/* $(Build.SourcesDirectory)/PostBuildLogs/${{parameters.StageLabel}}/${{parameters.JobLabel}}/ + continueOnError: true + condition: always() + +- task: PublishBuildArtifacts@1 + displayName: Publish Logs + inputs: + PathtoPublish: '$(Build.SourcesDirectory)/PostBuildLogs' + PublishLocation: Container + ArtifactName: PostBuildLogs + continueOnError: true + condition: always() diff --git a/eng/common/templates/steps/run-on-unix.yml b/eng/common/templates/steps/run-on-unix.yml new file mode 100644 index 000000000..e1733814f --- /dev/null +++ b/eng/common/templates/steps/run-on-unix.yml @@ -0,0 +1,7 @@ +parameters: + agentOs: '' + steps: [] + +steps: +- ${{ if ne(parameters.agentOs, 'Windows_NT') }}: + - ${{ parameters.steps }} diff --git a/eng/common/templates/steps/run-on-windows.yml b/eng/common/templates/steps/run-on-windows.yml new file mode 100644 index 000000000..73e7e9c27 --- /dev/null +++ b/eng/common/templates/steps/run-on-windows.yml @@ -0,0 +1,7 @@ +parameters: + agentOs: '' + steps: [] + +steps: +- ${{ if eq(parameters.agentOs, 'Windows_NT') }}: + - ${{ parameters.steps }} diff --git a/eng/common/templates/steps/run-script-ifequalelse.yml b/eng/common/templates/steps/run-script-ifequalelse.yml new file mode 100644 index 000000000..3d1242f55 --- /dev/null +++ b/eng/common/templates/steps/run-script-ifequalelse.yml @@ -0,0 +1,33 @@ +parameters: + # if parameter1 equals parameter 2, run 'ifScript' command, else run 'elsescript' command + parameter1: '' + parameter2: '' + ifScript: '' + elseScript: '' + + # name of script step + name: Script + + # display name of script step + displayName: If-Equal-Else Script + + # environment + env: {} + + # conditional expression for step execution + condition: '' + +steps: +- ${{ if and(ne(parameters.ifScript, ''), eq(parameters.parameter1, parameters.parameter2)) }}: + - script: ${{ parameters.ifScript }} + name: ${{ parameters.name }} + displayName: ${{ parameters.displayName }} + env: ${{ parameters.env }} + condition: ${{ parameters.condition }} + +- ${{ if and(ne(parameters.elseScript, ''), ne(parameters.parameter1, parameters.parameter2)) }}: + - script: ${{ parameters.elseScript }} + name: ${{ parameters.name }} + displayName: ${{ parameters.displayName }} + env: ${{ parameters.env }} + condition: ${{ parameters.condition }} \ No newline at end of file diff --git a/eng/common/templates/steps/send-to-helix.yml b/eng/common/templates/steps/send-to-helix.yml new file mode 100644 index 000000000..cd02ae160 --- /dev/null +++ b/eng/common/templates/steps/send-to-helix.yml @@ -0,0 +1,94 @@ +# Please remember to update the documentation if you make changes to these parameters! +parameters: + HelixSource: 'pr/default' # required -- sources must start with pr/, official/, prodcon/, or agent/ + HelixType: 'tests/default/' # required -- Helix telemetry which identifies what type of data this is; should include "test" for clarity and must end in '/' + HelixBuild: $(Build.BuildNumber) # required -- the build number Helix will use to identify this -- automatically set to the AzDO build number + HelixTargetQueues: '' # required -- semicolon delimited list of Helix queues to test on; see https://helix.dot.net/ for a list of queues + HelixAccessToken: '' # required -- access token to make Helix API requests; should be provided by the appropriate variable group + HelixConfiguration: '' # optional -- additional property attached to a job + HelixPreCommands: '' # optional -- commands to run before Helix work item execution + HelixPostCommands: '' # optional -- commands to run after Helix work item execution + WorkItemDirectory: '' # optional -- a payload directory to zip up and send to Helix; requires WorkItemCommand; incompatible with XUnitProjects + WorkItemCommand: '' # optional -- a command to execute on the payload; requires WorkItemDirectory; incompatible with XUnitProjects + WorkItemTimeout: '' # optional -- a timeout in TimeSpan.Parse-ready value (e.g. 00:02:00) for the work item command; requires WorkItemDirectory; incompatible with XUnitProjects + CorrelationPayloadDirectory: '' # optional -- a directory to zip up and send to Helix as a correlation payload + XUnitProjects: '' # optional -- semicolon delimited list of XUnitProjects to parse and send to Helix; requires XUnitRuntimeTargetFramework, XUnitPublishTargetFramework, XUnitRunnerVersion, and IncludeDotNetCli=true + XUnitWorkItemTimeout: '' # optional -- the workitem timeout in seconds for all workitems created from the xUnit projects specified by XUnitProjects + XUnitPublishTargetFramework: '' # optional -- framework to use to publish your xUnit projects + XUnitRuntimeTargetFramework: '' # optional -- framework to use for the xUnit console runner + XUnitRunnerVersion: '' # optional -- version of the xUnit nuget package you wish to use on Helix; required for XUnitProjects + IncludeDotNetCli: false # optional -- true will download a version of the .NET CLI onto the Helix machine as a correlation payload; requires DotNetCliPackageType and DotNetCliVersion + DotNetCliPackageType: '' # optional -- either 'sdk', 'runtime' or 'aspnetcore-runtime'; determines whether the sdk or runtime will be sent to Helix; see https://raw.githubusercontent.com/dotnet/core/main/release-notes/releases-index.json + DotNetCliVersion: '' # optional -- version of the CLI to send to Helix; based on this: https://raw.githubusercontent.com/dotnet/core/main/release-notes/releases-index.json + EnableXUnitReporter: false # optional -- true enables XUnit result reporting to Mission Control + WaitForWorkItemCompletion: true # optional -- true will make the task wait until work items have been completed and fail the build if work items fail. False is "fire and forget." + IsExternal: false # [DEPRECATED] -- doesn't do anything, jobs are external if HelixAccessToken is empty and Creator is set + HelixBaseUri: 'https://helix.dot.net/' # optional -- sets the Helix API base URI (allows targeting int) + Creator: '' # optional -- if the build is external, use this to specify who is sending the job + DisplayNamePrefix: 'Run Tests' # optional -- rename the beginning of the displayName of the steps in AzDO + condition: succeeded() # optional -- condition for step to execute; defaults to succeeded() + continueOnError: false # optional -- determines whether to continue the build if the step errors; defaults to false + +steps: + - powershell: 'powershell "$env:BUILD_SOURCESDIRECTORY\eng\common\msbuild.ps1 $env:BUILD_SOURCESDIRECTORY\eng\common\helixpublish.proj /restore /t:Test /bl:$env:BUILD_SOURCESDIRECTORY\artifacts\log\$env:BuildConfig\SendToHelix.binlog"' + displayName: ${{ parameters.DisplayNamePrefix }} (Windows) + env: + BuildConfig: $(_BuildConfig) + HelixSource: ${{ parameters.HelixSource }} + HelixType: ${{ parameters.HelixType }} + HelixBuild: ${{ parameters.HelixBuild }} + HelixConfiguration: ${{ parameters.HelixConfiguration }} + HelixTargetQueues: ${{ parameters.HelixTargetQueues }} + HelixAccessToken: ${{ parameters.HelixAccessToken }} + HelixPreCommands: ${{ parameters.HelixPreCommands }} + HelixPostCommands: ${{ parameters.HelixPostCommands }} + WorkItemDirectory: ${{ parameters.WorkItemDirectory }} + WorkItemCommand: ${{ parameters.WorkItemCommand }} + WorkItemTimeout: ${{ parameters.WorkItemTimeout }} + CorrelationPayloadDirectory: ${{ parameters.CorrelationPayloadDirectory }} + XUnitProjects: ${{ parameters.XUnitProjects }} + XUnitWorkItemTimeout: ${{ parameters.XUnitWorkItemTimeout }} + XUnitPublishTargetFramework: ${{ parameters.XUnitPublishTargetFramework }} + XUnitRuntimeTargetFramework: ${{ parameters.XUnitRuntimeTargetFramework }} + XUnitRunnerVersion: ${{ parameters.XUnitRunnerVersion }} + IncludeDotNetCli: ${{ parameters.IncludeDotNetCli }} + DotNetCliPackageType: ${{ parameters.DotNetCliPackageType }} + DotNetCliVersion: ${{ parameters.DotNetCliVersion }} + EnableXUnitReporter: ${{ parameters.EnableXUnitReporter }} + WaitForWorkItemCompletion: ${{ parameters.WaitForWorkItemCompletion }} + HelixBaseUri: ${{ parameters.HelixBaseUri }} + Creator: ${{ parameters.Creator }} + SYSTEM_ACCESSTOKEN: $(System.AccessToken) + condition: and(${{ parameters.condition }}, eq(variables['Agent.Os'], 'Windows_NT')) + continueOnError: ${{ parameters.continueOnError }} + - script: $BUILD_SOURCESDIRECTORY/eng/common/msbuild.sh $BUILD_SOURCESDIRECTORY/eng/common/helixpublish.proj /restore /t:Test /bl:$BUILD_SOURCESDIRECTORY/artifacts/log/$BuildConfig/SendToHelix.binlog + displayName: ${{ parameters.DisplayNamePrefix }} (Unix) + env: + BuildConfig: $(_BuildConfig) + HelixSource: ${{ parameters.HelixSource }} + HelixType: ${{ parameters.HelixType }} + HelixBuild: ${{ parameters.HelixBuild }} + HelixConfiguration: ${{ parameters.HelixConfiguration }} + HelixTargetQueues: ${{ parameters.HelixTargetQueues }} + HelixAccessToken: ${{ parameters.HelixAccessToken }} + HelixPreCommands: ${{ parameters.HelixPreCommands }} + HelixPostCommands: ${{ parameters.HelixPostCommands }} + WorkItemDirectory: ${{ parameters.WorkItemDirectory }} + WorkItemCommand: ${{ parameters.WorkItemCommand }} + WorkItemTimeout: ${{ parameters.WorkItemTimeout }} + CorrelationPayloadDirectory: ${{ parameters.CorrelationPayloadDirectory }} + XUnitProjects: ${{ parameters.XUnitProjects }} + XUnitWorkItemTimeout: ${{ parameters.XUnitWorkItemTimeout }} + XUnitPublishTargetFramework: ${{ parameters.XUnitPublishTargetFramework }} + XUnitRuntimeTargetFramework: ${{ parameters.XUnitRuntimeTargetFramework }} + XUnitRunnerVersion: ${{ parameters.XUnitRunnerVersion }} + IncludeDotNetCli: ${{ parameters.IncludeDotNetCli }} + DotNetCliPackageType: ${{ parameters.DotNetCliPackageType }} + DotNetCliVersion: ${{ parameters.DotNetCliVersion }} + EnableXUnitReporter: ${{ parameters.EnableXUnitReporter }} + WaitForWorkItemCompletion: ${{ parameters.WaitForWorkItemCompletion }} + HelixBaseUri: ${{ parameters.HelixBaseUri }} + Creator: ${{ parameters.Creator }} + SYSTEM_ACCESSTOKEN: $(System.AccessToken) + condition: and(${{ parameters.condition }}, ne(variables['Agent.Os'], 'Windows_NT')) + continueOnError: ${{ parameters.continueOnError }} diff --git a/eng/common/templates/steps/source-build.yml b/eng/common/templates/steps/source-build.yml new file mode 100644 index 000000000..e20637ed6 --- /dev/null +++ b/eng/common/templates/steps/source-build.yml @@ -0,0 +1,71 @@ +parameters: + # This template adds arcade-powered source-build to CI. + + # This is a 'steps' template, and is intended for advanced scenarios where the existing build + # infra has a careful build methodology that must be followed. For example, a repo + # (dotnet/runtime) might choose to clone the GitHub repo only once and store it as a pipeline + # artifact for all subsequent jobs to use, to reduce dependence on a strong network connection to + # GitHub. Using this steps template leaves room for that infra to be included. + + # Defines the platform on which to run the steps. See 'eng/common/templates/job/source-build.yml' + # for details. The entire object is described in the 'job' template for simplicity, even though + # the usage of the properties on this object is split between the 'job' and 'steps' templates. + platform: {} + +steps: +# Build. Keep it self-contained for simple reusability. (No source-build-specific job variables.) +- script: | + set -x + df -h + + buildConfig=Release + # Check if AzDO substitutes in a build config from a variable, and use it if so. + if [ '$(_BuildConfig)' != '$''(_BuildConfig)' ]; then + buildConfig='$(_BuildConfig)' + fi + + officialBuildArgs= + if [ '${{ and(ne(variables['System.TeamProject'], 'public'), notin(variables['Build.Reason'], 'PullRequest')) }}' = 'True' ]; then + officialBuildArgs='/p:DotNetPublishUsingPipelines=true /p:OfficialBuildId=$(BUILD.BUILDNUMBER)' + fi + + targetRidArgs= + if [ '${{ parameters.platform.targetRID }}' != '' ]; then + targetRidArgs='/p:TargetRid=${{ parameters.platform.targetRID }}' + fi + + publishArgs= + if [ '${{ parameters.platform.skipPublishValidation }}' != 'true' ]; then + publishArgs='--publish' + fi + + ${{ coalesce(parameters.platform.buildScript, './build.sh') }} --ci \ + --configuration $buildConfig \ + --restore --build --pack $publishArgs -bl \ + $officialBuildArgs \ + $targetRidArgs \ + /p:SourceBuildNonPortable=${{ parameters.platform.nonPortable }} \ + /p:ArcadeBuildFromSource=true + displayName: Build + +# Upload build logs for diagnosis. +- task: CopyFiles@2 + displayName: Prepare BuildLogs staging directory + inputs: + SourceFolder: '$(Build.SourcesDirectory)' + Contents: | + **/*.log + **/*.binlog + artifacts/source-build/self/prebuilt-report/** + TargetFolder: '$(Build.StagingDirectory)/BuildLogs' + CleanTargetFolder: true + continueOnError: true + condition: succeededOrFailed() + +- task: PublishPipelineArtifact@1 + displayName: Publish BuildLogs + inputs: + targetPath: '$(Build.StagingDirectory)/BuildLogs' + artifactName: BuildLogs_SourceBuild_${{ parameters.platform.name }}_Attempt$(System.JobAttempt) + continueOnError: true + condition: succeededOrFailed() diff --git a/eng/common/templates/steps/telemetry-end.yml b/eng/common/templates/steps/telemetry-end.yml new file mode 100644 index 000000000..fadc04ca1 --- /dev/null +++ b/eng/common/templates/steps/telemetry-end.yml @@ -0,0 +1,102 @@ +parameters: + maxRetries: 5 + retryDelay: 10 # in seconds + +steps: +- bash: | + if [ "$AGENT_JOBSTATUS" = "Succeeded" ] || [ "$AGENT_JOBSTATUS" = "PartiallySucceeded" ]; then + errorCount=0 + else + errorCount=1 + fi + warningCount=0 + + curlStatus=1 + retryCount=0 + # retry loop to harden against spotty telemetry connections + # we don't retry successes and 4xx client errors + until [[ $curlStatus -eq 0 || ( $curlStatus -ge 400 && $curlStatus -le 499 ) || $retryCount -ge $MaxRetries ]] + do + if [ $retryCount -gt 0 ]; then + echo "Failed to send telemetry to Helix; waiting $RetryDelay seconds before retrying..." + sleep $RetryDelay + fi + + # create a temporary file for curl output + res=`mktemp` + + curlResult=` + curl --verbose --output $res --write-out "%{http_code}"\ + -H 'Content-Type: application/json' \ + -H "X-Helix-Job-Token: $Helix_JobToken" \ + -H 'Content-Length: 0' \ + -X POST -G "https://helix.dot.net/api/2018-03-14/telemetry/job/build/$Helix_WorkItemId/finish" \ + --data-urlencode "errorCount=$errorCount" \ + --data-urlencode "warningCount=$warningCount"` + curlStatus=$? + + if [ $curlStatus -eq 0 ]; then + if [ $curlResult -gt 299 ] || [ $curlResult -lt 200 ]; then + curlStatus=$curlResult + fi + fi + + let retryCount++ + done + + if [ $curlStatus -ne 0 ]; then + echo "Failed to Send Build Finish information after $retryCount retries" + vstsLogOutput="vso[task.logissue type=error;sourcepath=templates/steps/telemetry-end.yml;code=1;]Failed to Send Build Finish information: $curlStatus" + echo "##$vstsLogOutput" + exit 1 + fi + displayName: Send Unix Build End Telemetry + env: + # defined via VSTS variables in start-job.sh + Helix_JobToken: $(Helix_JobToken) + Helix_WorkItemId: $(Helix_WorkItemId) + MaxRetries: ${{ parameters.maxRetries }} + RetryDelay: ${{ parameters.retryDelay }} + condition: and(always(), ne(variables['Agent.Os'], 'Windows_NT')) +- powershell: | + if (($env:Agent_JobStatus -eq 'Succeeded') -or ($env:Agent_JobStatus -eq 'PartiallySucceeded')) { + $ErrorCount = 0 + } else { + $ErrorCount = 1 + } + $WarningCount = 0 + + # Basic retry loop to harden against server flakiness + $retryCount = 0 + while ($retryCount -lt $env:MaxRetries) { + try { + Invoke-RestMethod -Uri "https://helix.dot.net/api/2018-03-14/telemetry/job/build/$env:Helix_WorkItemId/finish?errorCount=$ErrorCount&warningCount=$WarningCount" -Method Post -ContentType "application/json" -Body "" ` + -Headers @{ 'X-Helix-Job-Token'=$env:Helix_JobToken } + break + } + catch { + $statusCode = $_.Exception.Response.StatusCode.value__ + if ($statusCode -ge 400 -and $statusCode -le 499) { + Write-Host "##vso[task.logissue]error Failed to send telemetry to Helix (status code $statusCode); not retrying (4xx client error)" + Write-Host "##vso[task.logissue]error ", $_.Exception.GetType().FullName, $_.Exception.Message + exit 1 + } + Write-Host "Failed to send telemetry to Helix (status code $statusCode); waiting $env:RetryDelay seconds before retrying..." + $retryCount++ + sleep $env:RetryDelay + continue + } + } + + if ($retryCount -ge $env:MaxRetries) { + Write-Host "##vso[task.logissue]error Failed to send telemetry to Helix after $retryCount retries." + exit 1 + } + displayName: Send Windows Build End Telemetry + env: + # defined via VSTS variables in start-job.ps1 + Helix_JobToken: $(Helix_JobToken) + Helix_WorkItemId: $(Helix_WorkItemId) + MaxRetries: ${{ parameters.maxRetries }} + RetryDelay: ${{ parameters.retryDelay }} + condition: and(always(),eq(variables['Agent.Os'], 'Windows_NT')) diff --git a/eng/common/templates/steps/telemetry-start.yml b/eng/common/templates/steps/telemetry-start.yml new file mode 100644 index 000000000..32c01ef0b --- /dev/null +++ b/eng/common/templates/steps/telemetry-start.yml @@ -0,0 +1,241 @@ +parameters: + helixSource: 'undefined_defaulted_in_telemetry.yml' + helixType: 'undefined_defaulted_in_telemetry.yml' + buildConfig: '' + runAsPublic: false + maxRetries: 5 + retryDelay: 10 # in seconds + +steps: +- ${{ if and(eq(parameters.runAsPublic, 'false'), not(eq(variables['System.TeamProject'], 'public'))) }}: + - task: AzureKeyVault@1 + inputs: + azureSubscription: 'HelixProd_KeyVault' + KeyVaultName: HelixProdKV + SecretsFilter: 'HelixApiAccessToken' + condition: always() +- bash: | + # create a temporary file + jobInfo=`mktemp` + + # write job info content to temporary file + cat > $jobInfo < powershell invocations +# as dot sourcing isn't possible. +function InitializeDotNetCli([bool]$install, [bool]$createSdkLocationFile) { + if (Test-Path variable:global:_DotNetInstallDir) { + return $global:_DotNetInstallDir + } + + # Don't resolve runtime, shared framework, or SDK from other locations to ensure build determinism + $env:DOTNET_MULTILEVEL_LOOKUP=0 + + # Disable first run since we do not need all ASP.NET packages restored. + $env:DOTNET_SKIP_FIRST_TIME_EXPERIENCE=1 + + # Disable telemetry on CI. + if ($ci) { + $env:DOTNET_CLI_TELEMETRY_OPTOUT=1 + } + + # Source Build uses DotNetCoreSdkDir variable + if ($env:DotNetCoreSdkDir -ne $null) { + $env:DOTNET_INSTALL_DIR = $env:DotNetCoreSdkDir + } + + # Find the first path on %PATH% that contains the dotnet.exe + if ($useInstalledDotNetCli -and (-not $globalJsonHasRuntimes) -and ($env:DOTNET_INSTALL_DIR -eq $null)) { + $dotnetExecutable = GetExecutableFileName 'dotnet' + $dotnetCmd = Get-Command $dotnetExecutable -ErrorAction SilentlyContinue + + if ($dotnetCmd -ne $null) { + $env:DOTNET_INSTALL_DIR = Split-Path $dotnetCmd.Path -Parent + } + } + + $dotnetSdkVersion = $GlobalJson.tools.dotnet + + # Use dotnet installation specified in DOTNET_INSTALL_DIR if it contains the required SDK version, + # otherwise install the dotnet CLI and SDK to repo local .dotnet directory to avoid potential permission issues. + if ((-not $globalJsonHasRuntimes) -and (-not [string]::IsNullOrEmpty($env:DOTNET_INSTALL_DIR)) -and (Test-Path(Join-Path $env:DOTNET_INSTALL_DIR "sdk\$dotnetSdkVersion"))) { + $dotnetRoot = $env:DOTNET_INSTALL_DIR + } else { + $dotnetRoot = Join-Path $RepoRoot '.dotnet' + + if (-not (Test-Path(Join-Path $dotnetRoot "sdk\$dotnetSdkVersion"))) { + if ($install) { + InstallDotNetSdk $dotnetRoot $dotnetSdkVersion + } else { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Unable to find dotnet with SDK version '$dotnetSdkVersion'" + ExitWithExitCode 1 + } + } + + $env:DOTNET_INSTALL_DIR = $dotnetRoot + } + + # Creates a temporary file under the toolset dir. + # The following code block is protecting against concurrent access so that this function can + # be called in parallel. + if ($createSdkLocationFile) { + do { + $sdkCacheFileTemp = Join-Path $ToolsetDir $([System.IO.Path]::GetRandomFileName()) + } + until (!(Test-Path $sdkCacheFileTemp)) + Set-Content -Path $sdkCacheFileTemp -Value $dotnetRoot + + try { + Move-Item -Force $sdkCacheFileTemp (Join-Path $ToolsetDir 'sdk.txt') + } catch { + # Somebody beat us + Remove-Item -Path $sdkCacheFileTemp + } + } + + # Add dotnet to PATH. This prevents any bare invocation of dotnet in custom + # build steps from using anything other than what we've downloaded. + # It also ensures that VS msbuild will use the downloaded sdk targets. + $env:PATH = "$dotnetRoot;$env:PATH" + + # Make Sure that our bootstrapped dotnet cli is available in future steps of the Azure Pipelines build + Write-PipelinePrependPath -Path $dotnetRoot + + Write-PipelineSetVariable -Name 'DOTNET_MULTILEVEL_LOOKUP' -Value '0' + Write-PipelineSetVariable -Name 'DOTNET_SKIP_FIRST_TIME_EXPERIENCE' -Value '1' + + return $global:_DotNetInstallDir = $dotnetRoot +} + +function Retry($downloadBlock, $maxRetries = 5) { + $retries = 1 + + while($true) { + try { + & $downloadBlock + break + } + catch { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message $_ + } + + if (++$retries -le $maxRetries) { + $delayInSeconds = [math]::Pow(2, $retries) - 1 # Exponential backoff + Write-Host "Retrying. Waiting for $delayInSeconds seconds before next attempt ($retries of $maxRetries)." + Start-Sleep -Seconds $delayInSeconds + } + else { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Unable to download file in $maxRetries attempts." + break + } + + } +} + +function GetDotNetInstallScript([string] $dotnetRoot) { + $installScript = Join-Path $dotnetRoot 'dotnet-install.ps1' + if (!(Test-Path $installScript)) { + Create-Directory $dotnetRoot + $ProgressPreference = 'SilentlyContinue' # Don't display the console progress UI - it's a huge perf hit + $uri = "https://dotnet.microsoft.com/download/dotnet/scripts/$dotnetInstallScriptVersion/dotnet-install.ps1" + + Retry({ + Write-Host "GET $uri" + Invoke-WebRequest $uri -OutFile $installScript + }) + } + + return $installScript +} + +function InstallDotNetSdk([string] $dotnetRoot, [string] $version, [string] $architecture = '', [switch] $noPath) { + InstallDotNet $dotnetRoot $version $architecture '' $false $runtimeSourceFeed $runtimeSourceFeedKey -noPath:$noPath +} + +function InstallDotNet([string] $dotnetRoot, + [string] $version, + [string] $architecture = '', + [string] $runtime = '', + [bool] $skipNonVersionedFiles = $false, + [string] $runtimeSourceFeed = '', + [string] $runtimeSourceFeedKey = '', + [switch] $noPath) { + + $installScript = GetDotNetInstallScript $dotnetRoot + $installParameters = @{ + Version = $version + InstallDir = $dotnetRoot + } + + if ($architecture) { $installParameters.Architecture = $architecture } + if ($runtime) { $installParameters.Runtime = $runtime } + if ($skipNonVersionedFiles) { $installParameters.SkipNonVersionedFiles = $skipNonVersionedFiles } + if ($noPath) { $installParameters.NoPath = $True } + + try { + & $installScript @installParameters + } + catch { + if ($runtimeSourceFeed -or $runtimeSourceFeedKey) { + Write-Host "Failed to install dotnet from public location. Trying from '$runtimeSourceFeed'" + if ($runtimeSourceFeed) { $installParameters.AzureFeed = $runtimeSourceFeed } + + if ($runtimeSourceFeedKey) { + $decodedBytes = [System.Convert]::FromBase64String($runtimeSourceFeedKey) + $decodedString = [System.Text.Encoding]::UTF8.GetString($decodedBytes) + $installParameters.FeedCredential = $decodedString + } + + try { + & $installScript @installParameters + } + catch { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Failed to install dotnet from custom location '$runtimeSourceFeed'." + ExitWithExitCode 1 + } + } else { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Failed to install dotnet from public location." + ExitWithExitCode 1 + } + } +} + +# +# Locates Visual Studio MSBuild installation. +# The preference order for MSBuild to use is as follows: +# +# 1. MSBuild from an active VS command prompt +# 2. MSBuild from a compatible VS installation +# 3. MSBuild from the xcopy tool package +# +# Returns full path to msbuild.exe. +# Throws on failure. +# +function InitializeVisualStudioMSBuild([bool]$install, [object]$vsRequirements = $null) { + if (-not (IsWindowsPlatform)) { + throw "Cannot initialize Visual Studio on non-Windows" + } + + if (Test-Path variable:global:_MSBuildExe) { + return $global:_MSBuildExe + } + + # Minimum VS version to require. + $vsMinVersionReqdStr = '16.8' + $vsMinVersionReqd = [Version]::new($vsMinVersionReqdStr) + + # If the version of msbuild is going to be xcopied, + # use this version. Version matches a package here: + # https://dev.azure.com/dnceng/public/_packaging?_a=package&feed=dotnet-eng&package=RoslynTools.MSBuild&protocolType=NuGet&version=16.10.0-preview2&view=overview + $defaultXCopyMSBuildVersion = '16.10.0-preview2' + + if (!$vsRequirements) { $vsRequirements = $GlobalJson.tools.vs } + $vsMinVersionStr = if ($vsRequirements.version) { $vsRequirements.version } else { $vsMinVersionReqdStr } + $vsMinVersion = [Version]::new($vsMinVersionStr) + + # Try msbuild command available in the environment. + if ($env:VSINSTALLDIR -ne $null) { + $msbuildCmd = Get-Command 'msbuild.exe' -ErrorAction SilentlyContinue + if ($msbuildCmd -ne $null) { + # Workaround for https://github.com/dotnet/roslyn/issues/35793 + # Due to this issue $msbuildCmd.Version returns 0.0.0.0 for msbuild.exe 16.2+ + $msbuildVersion = [Version]::new((Get-Item $msbuildCmd.Path).VersionInfo.ProductVersion.Split([char[]]@('-', '+'))[0]) + + if ($msbuildVersion -ge $vsMinVersion) { + return $global:_MSBuildExe = $msbuildCmd.Path + } + + # Report error - the developer environment is initialized with incompatible VS version. + throw "Developer Command Prompt for VS $($env:VisualStudioVersion) is not recent enough. Please upgrade to $vsMinVersionStr or build from a plain CMD window" + } + } + + # Locate Visual Studio installation or download x-copy msbuild. + $vsInfo = LocateVisualStudio $vsRequirements + if ($vsInfo -ne $null) { + $vsInstallDir = $vsInfo.installationPath + $vsMajorVersion = $vsInfo.installationVersion.Split('.')[0] + + InitializeVisualStudioEnvironmentVariables $vsInstallDir $vsMajorVersion + } else { + + if (Get-Member -InputObject $GlobalJson.tools -Name 'xcopy-msbuild') { + $xcopyMSBuildVersion = $GlobalJson.tools.'xcopy-msbuild' + $vsMajorVersion = $xcopyMSBuildVersion.Split('.')[0] + } else { + #if vs version provided in global.json is incompatible (too low) then use the default version for xcopy msbuild download + if($vsMinVersion -lt $vsMinVersionReqd){ + Write-Host "Using xcopy-msbuild version of $defaultXCopyMSBuildVersion since VS version $vsMinVersionStr provided in global.json is not compatible" + $xcopyMSBuildVersion = $defaultXCopyMSBuildVersion + } + else{ + # If the VS version IS compatible, look for an xcopy msbuild package + # with a version matching VS. + # Note: If this version does not exist, then an explicit version of xcopy msbuild + # can be specified in global.json. This will be required for pre-release versions of msbuild. + $vsMajorVersion = $vsMinVersion.Major + $vsMinorVersion = $vsMinVersion.Minor + $xcopyMSBuildVersion = "$vsMajorVersion.$vsMinorVersion.0" + } + } + + $vsInstallDir = $null + if ($xcopyMSBuildVersion.Trim() -ine "none") { + $vsInstallDir = InitializeXCopyMSBuild $xcopyMSBuildVersion $install + if ($vsInstallDir -eq $null) { + throw "Could not xcopy msbuild. Please check that package 'RoslynTools.MSBuild @ $xcopyMSBuildVersion' exists on feed 'dotnet-eng'." + } + } + if ($vsInstallDir -eq $null) { + throw 'Unable to find Visual Studio that has required version and components installed' + } + } + + $msbuildVersionDir = if ([int]$vsMajorVersion -lt 16) { "$vsMajorVersion.0" } else { "Current" } + + $local:BinFolder = Join-Path $vsInstallDir "MSBuild\$msbuildVersionDir\Bin" + $local:Prefer64bit = if (Get-Member -InputObject $vsRequirements -Name 'Prefer64bit') { $vsRequirements.Prefer64bit } else { $false } + if ($local:Prefer64bit -and (Test-Path(Join-Path $local:BinFolder "amd64"))) { + $global:_MSBuildExe = Join-Path $local:BinFolder "amd64\msbuild.exe" + } else { + $global:_MSBuildExe = Join-Path $local:BinFolder "msbuild.exe" + } + + return $global:_MSBuildExe +} + +function InitializeVisualStudioEnvironmentVariables([string] $vsInstallDir, [string] $vsMajorVersion) { + $env:VSINSTALLDIR = $vsInstallDir + Set-Item "env:VS$($vsMajorVersion)0COMNTOOLS" (Join-Path $vsInstallDir "Common7\Tools\") + + $vsSdkInstallDir = Join-Path $vsInstallDir "VSSDK\" + if (Test-Path $vsSdkInstallDir) { + Set-Item "env:VSSDK$($vsMajorVersion)0Install" $vsSdkInstallDir + $env:VSSDKInstall = $vsSdkInstallDir + } +} + +function InstallXCopyMSBuild([string]$packageVersion) { + return InitializeXCopyMSBuild $packageVersion -install $true +} + +function InitializeXCopyMSBuild([string]$packageVersion, [bool]$install) { + $packageName = 'RoslynTools.MSBuild' + $packageDir = Join-Path $ToolsDir "msbuild\$packageVersion" + $packagePath = Join-Path $packageDir "$packageName.$packageVersion.nupkg" + + if (!(Test-Path $packageDir)) { + if (!$install) { + return $null + } + + Create-Directory $packageDir + + Write-Host "Downloading $packageName $packageVersion" + $ProgressPreference = 'SilentlyContinue' # Don't display the console progress UI - it's a huge perf hit + Retry({ + Invoke-WebRequest "https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-eng/nuget/v3/flat2/$packageName/$packageVersion/$packageName.$packageVersion.nupkg" -OutFile $packagePath + }) + + Unzip $packagePath $packageDir + } + + return Join-Path $packageDir 'tools' +} + +# +# Locates Visual Studio instance that meets the minimal requirements specified by tools.vs object in global.json. +# +# The following properties of tools.vs are recognized: +# "version": "{major}.{minor}" +# Two part minimal VS version, e.g. "15.9", "16.0", etc. +# "components": ["componentId1", "componentId2", ...] +# Array of ids of workload components that must be available in the VS instance. +# See e.g. https://docs.microsoft.com/en-us/visualstudio/install/workload-component-id-vs-enterprise?view=vs-2017 +# +# Returns JSON describing the located VS instance (same format as returned by vswhere), +# or $null if no instance meeting the requirements is found on the machine. +# +function LocateVisualStudio([object]$vsRequirements = $null){ + if (-not (IsWindowsPlatform)) { + throw "Cannot run vswhere on non-Windows platforms." + } + + if (Get-Member -InputObject $GlobalJson.tools -Name 'vswhere') { + $vswhereVersion = $GlobalJson.tools.vswhere + } else { + $vswhereVersion = '2.5.2' + } + + $vsWhereDir = Join-Path $ToolsDir "vswhere\$vswhereVersion" + $vsWhereExe = Join-Path $vsWhereDir 'vswhere.exe' + + if (!(Test-Path $vsWhereExe)) { + Create-Directory $vsWhereDir + Write-Host 'Downloading vswhere' + Retry({ + Invoke-WebRequest "https://netcorenativeassets.blob.core.windows.net/resource-packages/external/windows/vswhere/$vswhereVersion/vswhere.exe" -OutFile $vswhereExe + }) + } + + if (!$vsRequirements) { $vsRequirements = $GlobalJson.tools.vs } + $args = @('-latest', '-format', 'json', '-requires', 'Microsoft.Component.MSBuild', '-products', '*') + + if (!$excludePrereleaseVS) { + $args += '-prerelease' + } + + if (Get-Member -InputObject $vsRequirements -Name 'version') { + $args += '-version' + $args += $vsRequirements.version + } + + if (Get-Member -InputObject $vsRequirements -Name 'components') { + foreach ($component in $vsRequirements.components) { + $args += '-requires' + $args += $component + } + } + + $vsInfo =& $vsWhereExe $args | ConvertFrom-Json + + if ($lastExitCode -ne 0) { + return $null + } + + # use first matching instance + return $vsInfo[0] +} + +function InitializeBuildTool() { + if (Test-Path variable:global:_BuildTool) { + # If the requested msbuild parameters do not match, clear the cached variables. + if($global:_BuildTool.Contains('ExcludePrereleaseVS') -and $global:_BuildTool.ExcludePrereleaseVS -ne $excludePrereleaseVS) { + Remove-Item variable:global:_BuildTool + Remove-Item variable:global:_MSBuildExe + } else { + return $global:_BuildTool + } + } + + if (-not $msbuildEngine) { + $msbuildEngine = GetDefaultMSBuildEngine + } + + # Initialize dotnet cli if listed in 'tools' + $dotnetRoot = $null + if (Get-Member -InputObject $GlobalJson.tools -Name 'dotnet') { + $dotnetRoot = InitializeDotNetCli -install:$restore + } + + if ($msbuildEngine -eq 'dotnet') { + if (!$dotnetRoot) { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "/global.json must specify 'tools.dotnet'." + ExitWithExitCode 1 + } + $dotnetPath = Join-Path $dotnetRoot (GetExecutableFileName 'dotnet') + $buildTool = @{ Path = $dotnetPath; Command = 'msbuild'; Tool = 'dotnet'; Framework = 'netcoreapp3.1' } + } elseif ($msbuildEngine -eq "vs") { + try { + $msbuildPath = InitializeVisualStudioMSBuild -install:$restore + } catch { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message $_ + ExitWithExitCode 1 + } + + $buildTool = @{ Path = $msbuildPath; Command = ""; Tool = "vs"; Framework = "net472"; ExcludePrereleaseVS = $excludePrereleaseVS } + } else { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Unexpected value of -msbuildEngine: '$msbuildEngine'." + ExitWithExitCode 1 + } + + return $global:_BuildTool = $buildTool +} + +function GetDefaultMSBuildEngine() { + # Presence of tools.vs indicates the repo needs to build using VS msbuild on Windows. + if (Get-Member -InputObject $GlobalJson.tools -Name 'vs') { + return 'vs' + } + + if (Get-Member -InputObject $GlobalJson.tools -Name 'dotnet') { + return 'dotnet' + } + + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "-msbuildEngine must be specified, or /global.json must specify 'tools.dotnet' or 'tools.vs'." + ExitWithExitCode 1 +} + +function GetNuGetPackageCachePath() { + if ($env:NUGET_PACKAGES -eq $null) { + # Use local cache on CI to ensure deterministic build. + # Avoid using the http cache as workaround for https://github.com/NuGet/Home/issues/3116 + # use global cache in dev builds to avoid cost of downloading packages. + # For directory normalization, see also: https://github.com/NuGet/Home/issues/7968 + if ($useGlobalNuGetCache) { + $env:NUGET_PACKAGES = Join-Path $env:UserProfile '.nuget\packages\' + } else { + $env:NUGET_PACKAGES = Join-Path $RepoRoot '.packages\' + $env:RESTORENOCACHE = $true + } + } + + return $env:NUGET_PACKAGES +} + +# Returns a full path to an Arcade SDK task project file. +function GetSdkTaskProject([string]$taskName) { + return Join-Path (Split-Path (InitializeToolset) -Parent) "SdkTasks\$taskName.proj" +} + +function InitializeNativeTools() { + if (-Not (Test-Path variable:DisableNativeToolsetInstalls) -And (Get-Member -InputObject $GlobalJson -Name "native-tools")) { + $nativeArgs= @{} + if ($ci) { + $nativeArgs = @{ + InstallDirectory = "$ToolsDir" + } + } + & "$PSScriptRoot/init-tools-native.ps1" @nativeArgs + } +} + +function InitializeToolset() { + if (Test-Path variable:global:_ToolsetBuildProj) { + return $global:_ToolsetBuildProj + } + + $nugetCache = GetNuGetPackageCachePath + + $toolsetVersion = $GlobalJson.'msbuild-sdks'.'Microsoft.DotNet.Arcade.Sdk' + $toolsetLocationFile = Join-Path $ToolsetDir "$toolsetVersion.txt" + + if (Test-Path $toolsetLocationFile) { + $path = Get-Content $toolsetLocationFile -TotalCount 1 + if (Test-Path $path) { + return $global:_ToolsetBuildProj = $path + } + } + + if (-not $restore) { + Write-PipelineTelemetryError -Category 'InitializeToolset' -Message "Toolset version $toolsetVersion has not been restored." + ExitWithExitCode 1 + } + + $buildTool = InitializeBuildTool + + $proj = Join-Path $ToolsetDir 'restore.proj' + $bl = if ($binaryLog) { '/bl:' + (Join-Path $LogDir 'ToolsetRestore.binlog') } else { '' } + + '' | Set-Content $proj + + MSBuild-Core $proj $bl /t:__WriteToolsetLocation /clp:ErrorsOnly`;NoSummary /p:__ToolsetLocationOutputFile=$toolsetLocationFile + + $path = Get-Content $toolsetLocationFile -Encoding UTF8 -TotalCount 1 + if (!(Test-Path $path)) { + throw "Invalid toolset path: $path" + } + + return $global:_ToolsetBuildProj = $path +} + +function ExitWithExitCode([int] $exitCode) { + if ($ci -and $prepareMachine) { + Stop-Processes + } + exit $exitCode +} + +# Check if $LASTEXITCODE is a nonzero exit code (NZEC). If so, print a Azure Pipeline error for +# diagnostics, then exit the script with the $LASTEXITCODE. +function Exit-IfNZEC([string] $category = "General") { + Write-Host "Exit code $LASTEXITCODE" + if ($LASTEXITCODE -ne 0) { + $message = "Last command failed with exit code $LASTEXITCODE." + Write-PipelineTelemetryError -Force -Category $category -Message $message + ExitWithExitCode $LASTEXITCODE + } +} + +function Stop-Processes() { + Write-Host 'Killing running build processes...' + foreach ($processName in $processesToStopOnExit) { + Get-Process -Name $processName -ErrorAction SilentlyContinue | Stop-Process + } +} + +# +# Executes msbuild (or 'dotnet msbuild') with arguments passed to the function. +# The arguments are automatically quoted. +# Terminates the script if the build fails. +# +function MSBuild() { + if ($pipelinesLog) { + $buildTool = InitializeBuildTool + + if ($ci -and $buildTool.Tool -eq 'dotnet') { + $env:NUGET_PLUGIN_HANDSHAKE_TIMEOUT_IN_SECONDS = 20 + $env:NUGET_PLUGIN_REQUEST_TIMEOUT_IN_SECONDS = 20 + Write-PipelineSetVariable -Name 'NUGET_PLUGIN_HANDSHAKE_TIMEOUT_IN_SECONDS' -Value '20' + Write-PipelineSetVariable -Name 'NUGET_PLUGIN_REQUEST_TIMEOUT_IN_SECONDS' -Value '20' + } + + $toolsetBuildProject = InitializeToolset + $basePath = Split-Path -parent $toolsetBuildProject + $possiblePaths = @( + # new scripts need to work with old packages, so we need to look for the old names/versions + (Join-Path $basePath (Join-Path $buildTool.Framework 'Microsoft.DotNet.ArcadeLogging.dll')), + (Join-Path $basePath (Join-Path $buildTool.Framework 'Microsoft.DotNet.Arcade.Sdk.dll')), + (Join-Path $basePath (Join-Path netcoreapp2.1 'Microsoft.DotNet.ArcadeLogging.dll')), + (Join-Path $basePath (Join-Path netcoreapp2.1 'Microsoft.DotNet.Arcade.Sdk.dll')) + ) + $selectedPath = $null + foreach ($path in $possiblePaths) { + if (Test-Path $path -PathType Leaf) { + $selectedPath = $path + break + } + } + if (-not $selectedPath) { + Write-PipelineTelemetryError -Category 'Build' -Message 'Unable to find arcade sdk logger assembly.' + ExitWithExitCode 1 + } + $args += "/logger:$selectedPath" + } + + MSBuild-Core @args +} + +# +# Executes msbuild (or 'dotnet msbuild') with arguments passed to the function. +# The arguments are automatically quoted. +# Terminates the script if the build fails. +# +function MSBuild-Core() { + if ($ci) { + if (!$binaryLog -and !$excludeCIBinarylog) { + Write-PipelineTelemetryError -Category 'Build' -Message 'Binary log must be enabled in CI build, or explicitly opted-out from with the -excludeCIBinarylog switch.' + ExitWithExitCode 1 + } + + if ($nodeReuse) { + Write-PipelineTelemetryError -Category 'Build' -Message 'Node reuse must be disabled in CI build.' + ExitWithExitCode 1 + } + } + + $buildTool = InitializeBuildTool + + $cmdArgs = "$($buildTool.Command) /m /nologo /clp:Summary /v:$verbosity /nr:$nodeReuse /p:ContinuousIntegrationBuild=$ci" + + if ($warnAsError) { + $cmdArgs += ' /warnaserror /p:TreatWarningsAsErrors=true' + } + else { + $cmdArgs += ' /p:TreatWarningsAsErrors=false' + } + + foreach ($arg in $args) { + if ($null -ne $arg -and $arg.Trim() -ne "") { + if ($arg.EndsWith('\')) { + $arg = $arg + "\" + } + $cmdArgs += " `"$arg`"" + } + } + + $env:ARCADE_BUILD_TOOL_COMMAND = "$($buildTool.Path) $cmdArgs" + + $exitCode = Exec-Process $buildTool.Path $cmdArgs + + if ($exitCode -ne 0) { + # We should not Write-PipelineTaskError here because that message shows up in the build summary + # The build already logged an error, that's the reason it failed. Producing an error here only adds noise. + Write-Host "Build failed with exit code $exitCode. Check errors above." -ForegroundColor Red + + $buildLog = GetMSBuildBinaryLogCommandLineArgument $args + if ($null -ne $buildLog) { + Write-Host "See log: $buildLog" -ForegroundColor DarkGray + } + + if ($ci) { + Write-PipelineSetResult -Result "Failed" -Message "msbuild execution failed." + # Exiting with an exit code causes the azure pipelines task to log yet another "noise" error + # The above Write-PipelineSetResult will cause the task to be marked as failure without adding yet another error + ExitWithExitCode 0 + } else { + ExitWithExitCode $exitCode + } + } +} + +function GetMSBuildBinaryLogCommandLineArgument($arguments) { + foreach ($argument in $arguments) { + if ($argument -ne $null) { + $arg = $argument.Trim() + if ($arg.StartsWith('/bl:', "OrdinalIgnoreCase")) { + return $arg.Substring('/bl:'.Length) + } + + if ($arg.StartsWith('/binaryLogger:', 'OrdinalIgnoreCase')) { + return $arg.Substring('/binaryLogger:'.Length) + } + } + } + + return $null +} + +function GetExecutableFileName($baseName) { + if (IsWindowsPlatform) { + return "$baseName.exe" + } + else { + return $baseName + } +} + +function IsWindowsPlatform() { + return [environment]::OSVersion.Platform -eq [PlatformID]::Win32NT +} + +function Get-Darc($version) { + $darcPath = "$TempDir\darc\$(New-Guid)" + if ($version -ne $null) { + & $PSScriptRoot\darc-init.ps1 -toolpath $darcPath -darcVersion $version | Out-Host + } else { + & $PSScriptRoot\darc-init.ps1 -toolpath $darcPath | Out-Host + } + return "$darcPath\darc.exe" +} + +. $PSScriptRoot\pipeline-logging-functions.ps1 + +$RepoRoot = Resolve-Path (Join-Path $PSScriptRoot '..\..\') +$EngRoot = Resolve-Path (Join-Path $PSScriptRoot '..') +$ArtifactsDir = Join-Path $RepoRoot 'artifacts' +$ToolsetDir = Join-Path $ArtifactsDir 'toolset' +$ToolsDir = Join-Path $RepoRoot '.tools' +$LogDir = Join-Path (Join-Path $ArtifactsDir 'log') $configuration +$TempDir = Join-Path (Join-Path $ArtifactsDir 'tmp') $configuration +$GlobalJson = Get-Content -Raw -Path (Join-Path $RepoRoot 'global.json') | ConvertFrom-Json +# true if global.json contains a "runtimes" section +$globalJsonHasRuntimes = if ($GlobalJson.tools.PSObject.Properties.Name -Match 'runtimes') { $true } else { $false } + +Create-Directory $ToolsetDir +Create-Directory $TempDir +Create-Directory $LogDir + +Write-PipelineSetVariable -Name 'Artifacts' -Value $ArtifactsDir +Write-PipelineSetVariable -Name 'Artifacts.Toolset' -Value $ToolsetDir +Write-PipelineSetVariable -Name 'Artifacts.Log' -Value $LogDir +Write-PipelineSetVariable -Name 'TEMP' -Value $TempDir +Write-PipelineSetVariable -Name 'TMP' -Value $TempDir + +# Import custom tools configuration, if present in the repo. +# Note: Import in global scope so that the script set top-level variables without qualification. +if (!$disableConfigureToolsetImport) { + $configureToolsetScript = Join-Path $EngRoot 'configure-toolset.ps1' + if (Test-Path $configureToolsetScript) { + . $configureToolsetScript + if ((Test-Path variable:failOnConfigureToolsetError) -And $failOnConfigureToolsetError) { + if ((Test-Path variable:LastExitCode) -And ($LastExitCode -ne 0)) { + Write-PipelineTelemetryError -Category 'Build' -Message 'configure-toolset.ps1 returned a non-zero exit code' + ExitWithExitCode $LastExitCode + } + } + } +} diff --git a/eng/common/tools.sh b/eng/common/tools.sh new file mode 100644 index 000000000..828119be4 --- /dev/null +++ b/eng/common/tools.sh @@ -0,0 +1,535 @@ +#!/usr/bin/env bash + +# Initialize variables if they aren't already defined. + +# CI mode - set to true on CI server for PR validation build or official build. +ci=${ci:-false} + +# Set to true to use the pipelines logger which will enable Azure logging output. +# https://github.com/Microsoft/azure-pipelines-tasks/blob/master/docs/authoring/commands.md +# This flag is meant as a temporary opt-opt for the feature while validate it across +# our consumers. It will be deleted in the future. +if [[ "$ci" == true ]]; then + pipelines_log=${pipelines_log:-true} +else + pipelines_log=${pipelines_log:-false} +fi + +# Build configuration. Common values include 'Debug' and 'Release', but the repository may use other names. +configuration=${configuration:-'Debug'} + +# Set to true to opt out of outputting binary log while running in CI +exclude_ci_binary_log=${exclude_ci_binary_log:-false} + +if [[ "$ci" == true && "$exclude_ci_binary_log" == false ]]; then + binary_log_default=true +else + binary_log_default=false +fi + +# Set to true to output binary log from msbuild. Note that emitting binary log slows down the build. +binary_log=${binary_log:-$binary_log_default} + +# Turns on machine preparation/clean up code that changes the machine state (e.g. kills build processes). +prepare_machine=${prepare_machine:-false} + +# True to restore toolsets and dependencies. +restore=${restore:-true} + +# Adjusts msbuild verbosity level. +verbosity=${verbosity:-'minimal'} + +# Set to true to reuse msbuild nodes. Recommended to not reuse on CI. +if [[ "$ci" == true ]]; then + node_reuse=${node_reuse:-false} +else + node_reuse=${node_reuse:-true} +fi + +# Configures warning treatment in msbuild. +warn_as_error=${warn_as_error:-true} + +# True to attempt using .NET Core already that meets requirements specified in global.json +# installed on the machine instead of downloading one. +use_installed_dotnet_cli=${use_installed_dotnet_cli:-true} + +# Enable repos to use a particular version of the on-line dotnet-install scripts. +# default URL: https://dotnet.microsoft.com/download/dotnet/scripts/v1/dotnet-install.sh +dotnetInstallScriptVersion=${dotnetInstallScriptVersion:-'v1'} + +# True to use global NuGet cache instead of restoring packages to repository-local directory. +if [[ "$ci" == true ]]; then + use_global_nuget_cache=${use_global_nuget_cache:-false} +else + use_global_nuget_cache=${use_global_nuget_cache:-true} +fi + +# Used when restoring .NET SDK from alternative feeds +runtime_source_feed=${runtime_source_feed:-''} +runtime_source_feed_key=${runtime_source_feed_key:-''} + +# Resolve any symlinks in the given path. +function ResolvePath { + local path=$1 + + while [[ -h $path ]]; do + local dir="$( cd -P "$( dirname "$path" )" && pwd )" + path="$(readlink "$path")" + + # if $path was a relative symlink, we need to resolve it relative to the path where the + # symlink file was located + [[ $path != /* ]] && path="$dir/$path" + done + + # return value + _ResolvePath="$path" +} + +# ReadVersionFromJson [json key] +function ReadGlobalVersion { + local key=$1 + + if command -v jq &> /dev/null; then + _ReadGlobalVersion="$(jq -r ".[] | select(has(\"$key\")) | .\"$key\"" "$global_json_file")" + elif [[ "$(cat "$global_json_file")" =~ \"$key\"[[:space:]\:]*\"([^\"]+) ]]; then + _ReadGlobalVersion=${BASH_REMATCH[1]} + fi + + if [[ -z "$_ReadGlobalVersion" ]]; then + Write-PipelineTelemetryError -category 'Build' "Error: Cannot find \"$key\" in $global_json_file" + ExitWithExitCode 1 + fi +} + +function InitializeDotNetCli { + if [[ -n "${_InitializeDotNetCli:-}" ]]; then + return + fi + + local install=$1 + + # Don't resolve runtime, shared framework, or SDK from other locations to ensure build determinism + export DOTNET_MULTILEVEL_LOOKUP=0 + + # Disable first run since we want to control all package sources + export DOTNET_SKIP_FIRST_TIME_EXPERIENCE=1 + + # Disable telemetry on CI + if [[ $ci == true ]]; then + export DOTNET_CLI_TELEMETRY_OPTOUT=1 + fi + + # LTTNG is the logging infrastructure used by Core CLR. Need this variable set + # so it doesn't output warnings to the console. + export LTTNG_HOME="$HOME" + + # Source Build uses DotNetCoreSdkDir variable + if [[ -n "${DotNetCoreSdkDir:-}" ]]; then + export DOTNET_INSTALL_DIR="$DotNetCoreSdkDir" + fi + + # Find the first path on $PATH that contains the dotnet.exe + if [[ "$use_installed_dotnet_cli" == true && $global_json_has_runtimes == false && -z "${DOTNET_INSTALL_DIR:-}" ]]; then + local dotnet_path=`command -v dotnet` + if [[ -n "$dotnet_path" ]]; then + ResolvePath "$dotnet_path" + export DOTNET_INSTALL_DIR=`dirname "$_ResolvePath"` + fi + fi + + ReadGlobalVersion "dotnet" + local dotnet_sdk_version=$_ReadGlobalVersion + local dotnet_root="" + + # Use dotnet installation specified in DOTNET_INSTALL_DIR if it contains the required SDK version, + # otherwise install the dotnet CLI and SDK to repo local .dotnet directory to avoid potential permission issues. + if [[ $global_json_has_runtimes == false && -n "${DOTNET_INSTALL_DIR:-}" && -d "$DOTNET_INSTALL_DIR/sdk/$dotnet_sdk_version" ]]; then + dotnet_root="$DOTNET_INSTALL_DIR" + else + dotnet_root="$repo_root/.dotnet" + + export DOTNET_INSTALL_DIR="$dotnet_root" + + if [[ ! -d "$DOTNET_INSTALL_DIR/sdk/$dotnet_sdk_version" ]]; then + if [[ "$install" == true ]]; then + InstallDotNetSdk "$dotnet_root" "$dotnet_sdk_version" + else + Write-PipelineTelemetryError -category 'InitializeToolset' "Unable to find dotnet with SDK version '$dotnet_sdk_version'" + ExitWithExitCode 1 + fi + fi + fi + + # Add dotnet to PATH. This prevents any bare invocation of dotnet in custom + # build steps from using anything other than what we've downloaded. + Write-PipelinePrependPath -path "$dotnet_root" + + Write-PipelineSetVariable -name "DOTNET_MULTILEVEL_LOOKUP" -value "0" + Write-PipelineSetVariable -name "DOTNET_SKIP_FIRST_TIME_EXPERIENCE" -value "1" + + # return value + _InitializeDotNetCli="$dotnet_root" +} + +function InstallDotNetSdk { + local root=$1 + local version=$2 + local architecture="unset" + if [[ $# -ge 3 ]]; then + architecture=$3 + fi + InstallDotNet "$root" "$version" $architecture 'sdk' 'false' $runtime_source_feed $runtime_source_feed_key +} + +function InstallDotNet { + local root=$1 + local version=$2 + + GetDotNetInstallScript "$root" + local install_script=$_GetDotNetInstallScript + + local archArg='' + if [[ -n "${3:-}" ]] && [ "$3" != 'unset' ]; then + archArg="--architecture $3" + fi + local runtimeArg='' + if [[ -n "${4:-}" ]] && [ "$4" != 'sdk' ]; then + runtimeArg="--runtime $4" + fi + local skipNonVersionedFilesArg="" + if [[ "$#" -ge "5" ]] && [[ "$5" != 'false' ]]; then + skipNonVersionedFilesArg="--skip-non-versioned-files" + fi + bash "$install_script" --version $version --install-dir "$root" $archArg $runtimeArg $skipNonVersionedFilesArg || { + local exit_code=$? + echo "Failed to install dotnet SDK from public location (exit code '$exit_code')." + + local runtimeSourceFeed='' + if [[ -n "${6:-}" ]]; then + runtimeSourceFeed="--azure-feed $6" + fi + + local runtimeSourceFeedKey='' + if [[ -n "${7:-}" ]]; then + # The 'base64' binary on alpine uses '-d' and doesn't support '--decode' + # '-d'. To work around this, do a simple detection and switch the parameter + # accordingly. + decodeArg="--decode" + if base64 --help 2>&1 | grep -q "BusyBox"; then + decodeArg="-d" + fi + decodedFeedKey=`echo $7 | base64 $decodeArg` + runtimeSourceFeedKey="--feed-credential $decodedFeedKey" + fi + + if [[ -n "$runtimeSourceFeed" || -n "$runtimeSourceFeedKey" ]]; then + bash "$install_script" --version $version --install-dir "$root" $archArg $runtimeArg $skipNonVersionedFilesArg $runtimeSourceFeed $runtimeSourceFeedKey || { + local exit_code=$? + Write-PipelineTelemetryError -category 'InitializeToolset' "Failed to install dotnet SDK from custom location '$runtimeSourceFeed' (exit code '$exit_code')." + ExitWithExitCode $exit_code + } + else + if [[ $exit_code != 0 ]]; then + Write-PipelineTelemetryError -category 'InitializeToolset' "Failed to install dotnet SDK from public location (exit code '$exit_code')." + fi + ExitWithExitCode $exit_code + fi + } +} + +function with_retries { + local maxRetries=5 + local retries=1 + echo "Trying to run '$@' for maximum of $maxRetries attempts." + while [[ $((retries++)) -le $maxRetries ]]; do + "$@" + + if [[ $? == 0 ]]; then + echo "Ran '$@' successfully." + return 0 + fi + + timeout=$((3**$retries-1)) + echo "Failed to execute '$@'. Waiting $timeout seconds before next attempt ($retries out of $maxRetries)." 1>&2 + sleep $timeout + done + + echo "Failed to execute '$@' for $maxRetries times." 1>&2 + + return 1 +} + +function GetDotNetInstallScript { + local root=$1 + local install_script="$root/dotnet-install.sh" + local install_script_url="https://dotnet.microsoft.com/download/dotnet/scripts/$dotnetInstallScriptVersion/dotnet-install.sh" + + if [[ ! -a "$install_script" ]]; then + mkdir -p "$root" + + echo "Downloading '$install_script_url'" + + # Use curl if available, otherwise use wget + if command -v curl > /dev/null; then + # first, try directly, if this fails we will retry with verbose logging + curl "$install_script_url" -sSL --retry 10 --create-dirs -o "$install_script" || { + if command -v openssl &> /dev/null; then + echo "Curl failed; dumping some information about dotnet.microsoft.com for later investigation" + echo | openssl s_client -showcerts -servername dotnet.microsoft.com -connect dotnet.microsoft.com:443 + fi + echo "Will now retry the same URL with verbose logging." + with_retries curl "$install_script_url" -sSL --verbose --retry 10 --create-dirs -o "$install_script" || { + local exit_code=$? + Write-PipelineTelemetryError -category 'InitializeToolset' "Failed to acquire dotnet install script (exit code '$exit_code')." + ExitWithExitCode $exit_code + } + } + else + with_retries wget -v -O "$install_script" "$install_script_url" || { + local exit_code=$? + Write-PipelineTelemetryError -category 'InitializeToolset' "Failed to acquire dotnet install script (exit code '$exit_code')." + ExitWithExitCode $exit_code + } + fi + fi + # return value + _GetDotNetInstallScript="$install_script" +} + +function InitializeBuildTool { + if [[ -n "${_InitializeBuildTool:-}" ]]; then + return + fi + + InitializeDotNetCli $restore + + # return values + _InitializeBuildTool="$_InitializeDotNetCli/dotnet" + _InitializeBuildToolCommand="msbuild" + _InitializeBuildToolFramework="netcoreapp3.1" +} + +# Set RestoreNoCache as a workaround for https://github.com/NuGet/Home/issues/3116 +function GetNuGetPackageCachePath { + if [[ -z ${NUGET_PACKAGES:-} ]]; then + if [[ "$use_global_nuget_cache" == true ]]; then + export NUGET_PACKAGES="$HOME/.nuget/packages" + else + export NUGET_PACKAGES="$repo_root/.packages" + export RESTORENOCACHE=true + fi + fi + + # return value + _GetNuGetPackageCachePath=$NUGET_PACKAGES +} + +function InitializeNativeTools() { + if [[ -n "${DisableNativeToolsetInstalls:-}" ]]; then + return + fi + if grep -Fq "native-tools" $global_json_file + then + local nativeArgs="" + if [[ "$ci" == true ]]; then + nativeArgs="--installDirectory $tools_dir" + fi + "$_script_dir/init-tools-native.sh" $nativeArgs + fi +} + +function InitializeToolset { + if [[ -n "${_InitializeToolset:-}" ]]; then + return + fi + + GetNuGetPackageCachePath + + ReadGlobalVersion "Microsoft.DotNet.Arcade.Sdk" + + local toolset_version=$_ReadGlobalVersion + local toolset_location_file="$toolset_dir/$toolset_version.txt" + + if [[ -a "$toolset_location_file" ]]; then + local path=`cat "$toolset_location_file"` + if [[ -a "$path" ]]; then + # return value + _InitializeToolset="$path" + return + fi + fi + + if [[ "$restore" != true ]]; then + Write-PipelineTelemetryError -category 'InitializeToolset' "Toolset version $toolset_version has not been restored." + ExitWithExitCode 2 + fi + + local proj="$toolset_dir/restore.proj" + + local bl="" + if [[ "$binary_log" == true ]]; then + bl="/bl:$log_dir/ToolsetRestore.binlog" + fi + + echo '' > "$proj" + MSBuild-Core "$proj" $bl /t:__WriteToolsetLocation /clp:ErrorsOnly\;NoSummary /p:__ToolsetLocationOutputFile="$toolset_location_file" + + local toolset_build_proj=`cat "$toolset_location_file"` + + if [[ ! -a "$toolset_build_proj" ]]; then + Write-PipelineTelemetryError -category 'Build' "Invalid toolset path: $toolset_build_proj" + ExitWithExitCode 3 + fi + + # return value + _InitializeToolset="$toolset_build_proj" +} + +function ExitWithExitCode { + if [[ "$ci" == true && "$prepare_machine" == true ]]; then + StopProcesses + fi + exit $1 +} + +function StopProcesses { + echo "Killing running build processes..." + pkill -9 "dotnet" || true + pkill -9 "vbcscompiler" || true + return 0 +} + +function MSBuild { + local args=$@ + if [[ "$pipelines_log" == true ]]; then + InitializeBuildTool + InitializeToolset + + if [[ "$ci" == true ]]; then + export NUGET_PLUGIN_HANDSHAKE_TIMEOUT_IN_SECONDS=20 + export NUGET_PLUGIN_REQUEST_TIMEOUT_IN_SECONDS=20 + Write-PipelineSetVariable -name "NUGET_PLUGIN_HANDSHAKE_TIMEOUT_IN_SECONDS" -value "20" + Write-PipelineSetVariable -name "NUGET_PLUGIN_REQUEST_TIMEOUT_IN_SECONDS" -value "20" + fi + + local toolset_dir="${_InitializeToolset%/*}" + # new scripts need to work with old packages, so we need to look for the old names/versions + local selectedPath= + local possiblePaths=() + possiblePaths+=( "$toolset_dir/$_InitializeBuildToolFramework/Microsoft.DotNet.ArcadeLogging.dll" ) + possiblePaths+=( "$toolset_dir/$_InitializeBuildToolFramework/Microsoft.DotNet.Arcade.Sdk.dll" ) + possiblePaths+=( "$toolset_dir/netcoreapp2.1/Microsoft.DotNet.ArcadeLogging.dll" ) + possiblePaths+=( "$toolset_dir/netcoreapp2.1/Microsoft.DotNet.Arcade.Sdk.dll" ) + for path in "${possiblePaths[@]}"; do + if [[ -f $path ]]; then + selectedPath=$path + break + fi + done + if [[ -z "$selectedPath" ]]; then + Write-PipelineTelemetryError -category 'Build' "Unable to find arcade sdk logger assembly." + ExitWithExitCode 1 + fi + args+=( "-logger:$selectedPath" ) + fi + + MSBuild-Core ${args[@]} +} + +function MSBuild-Core { + if [[ "$ci" == true ]]; then + if [[ "$binary_log" != true && "$exclude_ci_binary_log" != true ]]; then + Write-PipelineTelemetryError -category 'Build' "Binary log must be enabled in CI build, or explicitly opted-out from with the -noBinaryLog switch." + ExitWithExitCode 1 + fi + + if [[ "$node_reuse" == true ]]; then + Write-PipelineTelemetryError -category 'Build' "Node reuse must be disabled in CI build." + ExitWithExitCode 1 + fi + fi + + InitializeBuildTool + + local warnaserror_switch="" + if [[ $warn_as_error == true ]]; then + warnaserror_switch="/warnaserror" + fi + + function RunBuildTool { + export ARCADE_BUILD_TOOL_COMMAND="$_InitializeBuildTool $@" + + "$_InitializeBuildTool" "$@" || { + local exit_code=$? + # We should not Write-PipelineTaskError here because that message shows up in the build summary + # The build already logged an error, that's the reason it failed. Producing an error here only adds noise. + echo "Build failed with exit code $exit_code. Check errors above." + if [[ "$ci" == "true" ]]; then + Write-PipelineSetResult -result "Failed" -message "msbuild execution failed." + # Exiting with an exit code causes the azure pipelines task to log yet another "noise" error + # The above Write-PipelineSetResult will cause the task to be marked as failure without adding yet another error + ExitWithExitCode 0 + else + ExitWithExitCode $exit_code + fi + } + } + + RunBuildTool "$_InitializeBuildToolCommand" /m /nologo /clp:Summary /v:$verbosity /nr:$node_reuse $warnaserror_switch /p:TreatWarningsAsErrors=$warn_as_error /p:ContinuousIntegrationBuild=$ci "$@" +} + +ResolvePath "${BASH_SOURCE[0]}" +_script_dir=`dirname "$_ResolvePath"` + +. "$_script_dir/pipeline-logging-functions.sh" + +eng_root=`cd -P "$_script_dir/.." && pwd` +repo_root=`cd -P "$_script_dir/../.." && pwd` +repo_root="${repo_root}/" +artifacts_dir="${repo_root}artifacts" +toolset_dir="$artifacts_dir/toolset" +tools_dir="${repo_root}.tools" +log_dir="$artifacts_dir/log/$configuration" +temp_dir="$artifacts_dir/tmp/$configuration" + +global_json_file="${repo_root}global.json" +# determine if global.json contains a "runtimes" entry +global_json_has_runtimes=false +if command -v jq &> /dev/null; then + if jq -er '. | select(has("runtimes"))' "$global_json_file" &> /dev/null; then + global_json_has_runtimes=true + fi +elif [[ "$(cat "$global_json_file")" =~ \"runtimes\"[[:space:]\:]*\{ ]]; then + global_json_has_runtimes=true +fi + +# HOME may not be defined in some scenarios, but it is required by NuGet +if [[ -z $HOME ]]; then + export HOME="${repo_root}artifacts/.home/" + mkdir -p "$HOME" +fi + +mkdir -p "$toolset_dir" +mkdir -p "$temp_dir" +mkdir -p "$log_dir" + +Write-PipelineSetVariable -name "Artifacts" -value "$artifacts_dir" +Write-PipelineSetVariable -name "Artifacts.Toolset" -value "$toolset_dir" +Write-PipelineSetVariable -name "Artifacts.Log" -value "$log_dir" +Write-PipelineSetVariable -name "Temp" -value "$temp_dir" +Write-PipelineSetVariable -name "TMP" -value "$temp_dir" + +# Import custom tools configuration, if present in the repo. +if [ -z "${disable_configure_toolset_import:-}" ]; then + configure_toolset_script="$eng_root/configure-toolset.sh" + if [[ -a "$configure_toolset_script" ]]; then + . "$configure_toolset_script" + fi +fi + +# TODO: https://github.com/dotnet/arcade/issues/1468 +# Temporary workaround to avoid breaking change. +# Remove once repos are updated. +if [[ -n "${useInstalledDotNetCli:-}" ]]; then + use_installed_dotnet_cli="$useInstalledDotNetCli" +fi diff --git a/eng/publishing/v3/common-variables.yml b/eng/publishing/v3/common-variables.yml new file mode 100644 index 000000000..ed518e46b --- /dev/null +++ b/eng/publishing/v3/common-variables.yml @@ -0,0 +1,24 @@ +variables: + - group: AzureDevOps-Artifact-Feeds-Pats + - group: DotNet-Blob-Feed + - group: DotNet-DotNetCli-Storage + - group: DotNet-MSRC-Storage + - group: Publish-Build-Assets + + # Default Maestro++ API Endpoint and API Version + - name: MaestroApiEndPoint + value: "https://maestro-prod.westus2.cloudapp.azure.com" + - name: MaestroApiAccessToken + value: $(MaestroAccessToken) + - name: MaestroApiVersion + value: "2020-02-20" + + - name: SourceLinkCLIVersion + value: 3.0.0 + + # Skip component governance and codesign validation for SDL. These jobs + # create no content. + - name: skipComponentGovernanceDetection + value: true + - name: runCodesignValidationInjection + value: false \ No newline at end of file diff --git a/eng/publishing/v3/nuget-validation.yml b/eng/publishing/v3/nuget-validation.yml new file mode 100644 index 000000000..6c9e0b8c3 --- /dev/null +++ b/eng/publishing/v3/nuget-validation.yml @@ -0,0 +1,54 @@ +jobs: +- job: + displayName: NuGet Validation + dependsOn: setupMaestroVars + pool: + vmImage: 'windows-2019' + variables: + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Package Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: PackageArtifacts + checkDownloadedFiles: true + + - task: PowerShell@2 + displayName: Validate + inputs: + targetType: inline + script: | + try { + $ErrorActionPreference = 'Stop' + Set-StrictMode -Version 2.0 + + # `tools.ps1` requires $ci to be $true + $ci = $true + $disableConfigureToolsetImport = $true + . ${Env:BUILD_SOURCESDIRECTORY}\eng\common\tools.ps1 + + $ToolDestinationPath = "${Env:AGENT_BUILDDIRECTORY}\Extract\" + $PackagesPath = "${Env:BUILD_ARTIFACTSTAGINGDIRECTORY}\PackageArtifacts\" + $url = 'https://raw.githubusercontent.com/NuGet/NuGetGallery/3e25ad135146676bcab0050a516939d9958bfa5d/src/VerifyMicrosoftPackage/verify.ps1' + + New-Item -ItemType 'directory' -Path ${ToolDestinationPath} -Force + + Invoke-WebRequest $url -OutFile ${ToolDestinationPath}\verify.ps1 + + & ${ToolDestinationPath}\verify.ps1 ${PackagesPath}\*.nupkg + } + catch { + Write-Host $_.ScriptStackTrace + Write-PipelineTelemetryError -Category 'NuGetValidation' -Message $_ + ExitWithExitCode 1 + } diff --git a/eng/publishing/v3/postbuild-checks.yml b/eng/publishing/v3/postbuild-checks.yml new file mode 100644 index 000000000..9382a1a40 --- /dev/null +++ b/eng/publishing/v3/postbuild-checks.yml @@ -0,0 +1,9 @@ +jobs: +- job: + displayName: Post-build Checks + dependsOn: setupMaestroVars + variables: + - name: TargetChannels + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.TargetChannels'] ] + pool: + vmImage: 'windows-2019' diff --git a/eng/publishing/v3/publish-assets.yml b/eng/publishing/v3/publish-assets.yml new file mode 100644 index 000000000..17c85fba2 --- /dev/null +++ b/eng/publishing/v3/publish-assets.yml @@ -0,0 +1,100 @@ +parameters: + artifactsPublishingAdditionalParameters: '' + publishInstallersAndChecksums: true + PromoteToChannelIds: '' + symbolPublishingAdditionalParameters: '' + buildQuality: 'daily' + +jobs: +- job: publish_assets + displayName: Publish Assets and Symbols + dependsOn: setupMaestroVars + timeoutInMinutes: 120 + variables: + - group: DotNet-Symbol-Server-Pats + - name: BARBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.BARBuildId'] ] + - name: IsStableBuild + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.IsStableBuild'] ] + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + - name: AzDOAccount + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildAccount'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + enabled: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + AssetManifests/** + BlobArtifacts/MergedManifest.xml + PdbArtifacts/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + + - task: NuGetToolInstaller@1 + displayName: 'Install NuGet.exe' + + # This is necessary whenever we want to publish/restore to an AzDO private feed + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish packages, blobs and symbols + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/sdk-task.ps1 + arguments: -task PublishArtifactsInManifest -restore -msbuildEngine dotnet + /p:PublishingInfraVersion=3 + /p:BARBuildId=$(BARBuildId) + /p:TargetChannels='${{ parameters.PromoteToChannelIds }}' + /p:IsInternalBuild=${{ and(ne(variables['System.TeamProject'], 'public'), contains(variables['Build.SourceBranch'], 'internal')) }} + /p:NugetPath=$(NuGetExeToolPath) + /p:MaestroApiEndpoint='$(MaestroApiEndPoint)' + /p:BuildAssetRegistryToken='$(MaestroApiAccessToken)' + /p:ManifestsBasePath='$(Build.ArtifactStagingDirectory)/AssetManifests/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:PackageBasePath='$(Build.ArtifactStagingDirectory)/PackageArtifacts/' + /p:PublishInstallersAndChecksums=${{ parameters.publishInstallersAndChecksums }} + /p:InstallersAzureAccountKey=$(dotnetcli-storage-key) + /p:InternalInstallersAzureAccountKey=$(dotnetclimsrc-access-key) + /p:ChecksumsAzureAccountKey=$(dotnetclichecksums-storage-key) + /p:InternalChecksumsAzureAccountKey=$(dotnetclichecksumsmsrc-storage-key) + /p:AzureDevOpsFeedsKey='$(dn-bot-dnceng-artifact-feeds-rw)' + /p:AzureStorageTargetFeedPAT='$(dotnetfeed-storage-access-key-1)' + /p:AkaMSClientId=$(akams-client-id) + /p:AkaMSClientSecret=$(akams-client-secret) + ${{ parameters.artifactsPublishingAdditionalParameters }} + /p:PDBArtifactsBasePath='$(Build.ArtifactStagingDirectory)/PDBArtifacts/' + /p:SymbolPublishingExclusionsFile='$(Build.SourcesDirectory)/eng/SymbolPublishingExclusionsFile.txt' + ${{ parameters.symbolPublishingAdditionalParameters}} + /p:MsdlToken=$(microsoft-symbol-server-pat) + /p:SymWebToken=$(symweb-symbol-server-pat) + /p:BuildQuality='${{ parameters.buildQuality }}' + /p:AzdoApiToken='$(dn-bot-all-orgs-build-rw-code-rw)' + /p:ArtifactsBasePath='$(Build.ArtifactStagingDirectory)/' + /p:BuildId='$(AzDOBuildId)' + /p:AzureDevOpsOrg='$(AzDOAccount)' + /p:AzureProject='$(AzDOProjectName)' + /p:UseStreamingPublishing='true' + - template: /eng/common/templates/steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'AssetsPublishing' diff --git a/eng/publishing/v3/publish-symbols.yml b/eng/publishing/v3/publish-symbols.yml new file mode 100644 index 000000000..10196525e --- /dev/null +++ b/eng/publishing/v3/publish-symbols.yml @@ -0,0 +1,65 @@ +parameters: + symbolPublishingAdditionalParameters: '' + +jobs: +- job: publish_symbols + displayName: Symbols Publishing + dependsOn: setupMaestroVars + variables: + - group: DotNet-Symbol-Server-Pats + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Build Assets + continueOnError: true + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + downloadType: 'specific' + itemPattern: | + PdbArtifacts/** + BlobArtifacts/** + downloadPath: '$(Build.ArtifactStagingDirectory)' + checkDownloadedFiles: true + + # This is necessary whenever we want to publish/restore to an AzDO private feed + # Since sdk-task.ps1 tries to restore packages we need to do this authentication here + # otherwise it'll complain about accessing a private feed. + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + - task: PowerShell@2 + displayName: Publish + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/sdk-task.ps1 + arguments: -task PublishToSymbolServers -restore -msbuildEngine dotnet + /p:DotNetSymbolServerTokenMsdl=$(microsoft-symbol-server-pat) + /p:DotNetSymbolServerTokenSymWeb=$(symweb-symbol-server-pat) + /p:PDBArtifactsDirectory='$(Build.ArtifactStagingDirectory)/PDBArtifacts/' + /p:BlobBasePath='$(Build.ArtifactStagingDirectory)/BlobArtifacts/' + /p:SymbolPublishingExclusionsFile='$(Build.SourcesDirectory)/eng/SymbolPublishingExclusionsFile.txt' + /p:Configuration=Release + /p:PublishToMSDL=false + /p:PublishToSymWeb=true + ${{ parameters.symbolPublishingAdditionalParameters }} + + - template: /eng/common/templates/steps/publish-logs.yml + parameters: + StageLabel: '${{ parameters.stageName }}' + JobLabel: 'SymbolPublishing' diff --git a/eng/publishing/v3/publish.yml b/eng/publishing/v3/publish.yml new file mode 100644 index 000000000..ef0315cff --- /dev/null +++ b/eng/publishing/v3/publish.yml @@ -0,0 +1,61 @@ +parameters: + BARBuildId: '' + PromoteToChannelIds: '' + + enableSourceLinkValidation: false + enableSigningValidation: true + enableNugetValidation: true + publishInstallersAndChecksums: true + + # These parameters let the user customize the call to sdk-task.ps1 for publishing + # symbols & general artifacts as well as for signing validation + symbolPublishingAdditionalParameters: '' + artifactsPublishingAdditionalParameters: '' + signingValidationAdditionalParameters: '' + + # Which stages should finish execution before post-build stages start + validateDependsOn: + - build + publishDependsOn: + - Validate + +stages: + - stage: Validate + dependsOn: ${{ parameters.validateDependsOn }} + displayName: Validate Build Assets + variables: + - template: /eng/publishing/v3/common-variables.yml + jobs: + - template: /eng/publishing/v3/setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - template: /eng/publishing/v3/postbuild-checks.yml + + - ${{ if eq(parameters.enableNugetValidation, 'True') }}: + - template: /eng/publishing/v3/nuget-validation.yml + + - ${{ if eq(parameters.enableSigningValidation, 'True') }}: + - template: /eng/publishing/v3/signing-validation.yml + + - ${{ if eq(parameters.enableSourceLinkValidation, 'True') }}: + - template: /eng/publishing/v3/sourcelink-validation.yml + + - stage: publish + dependsOn: ${{ parameters.publishDependsOn }} + variables: + - template: /eng/publishing/v3/common-variables.yml + displayName: Publishing + jobs: + - template: /eng/publishing/v3/setup-maestro-vars.yml + parameters: + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + + - template: /eng/publishing/v3/publish-assets.yml + parameters: + PromoteToChannelIds: ${{ parameters.PromoteToChannelIds }} + publishInstallersAndChecksums: ${{ parameters.publishInstallersAndChecksums }} + artifactsPublishingAdditionalParameters: ${{ parameters.artifactsPublishingAdditionalParameters }} + symbolPublishingAdditionalParameters: ${{parameters.symbolPublishingAdditionalParameters}} diff --git a/eng/publishing/v3/setup-maestro-vars.yml b/eng/publishing/v3/setup-maestro-vars.yml new file mode 100644 index 000000000..ae2e65527 --- /dev/null +++ b/eng/publishing/v3/setup-maestro-vars.yml @@ -0,0 +1,61 @@ +parameters: + BARBuildId: '' + PromoteToChannelIds: '' + +jobs: +- job: setupMaestroVars + displayName: Setup Maestro Vars + variables: + - template: /eng/publishing/v3/common-variables.yml + pool: + vmImage: 'windows-2019' + steps: + - checkout: none + + - task: PowerShell@2 + name: setReleaseVars + displayName: Set Release Configs Vars + inputs: + targetType: inline + script: | + try { + dir Env: + + $buildApiEndpoint = "${Env:MaestroApiEndPoint}/api/builds/${Env:BARBuildId}?api-version=${Env:MaestroApiVersion}" + + $apiHeaders = New-Object 'System.Collections.Generic.Dictionary[[String],[String]]' + $apiHeaders.Add('Accept', 'application/json') + $apiHeaders.Add('Authorization',"Bearer ${Env:MAESTRO_API_TOKEN}") + + $buildInfo = try { Invoke-WebRequest -Method Get -Uri $buildApiEndpoint -Headers $apiHeaders | ConvertFrom-Json } catch { Write-Host "Error: $_" } + + $BarId = $Env:BARBuildId + $Channels = $Env:PromoteToMaestroChannels -split "," + $Channels = $Channels -join "][" + $Channels = "[$Channels]" + + $IsStableBuild = $buildInfo.stable + $AzureDevOpsProject = $buildInfo.azureDevOpsProject + $AzureDevOpsBuildDefinitionId = $buildInfo.azureDevOpsBuildDefinitionId + $AzureDevOpsBuildId = $buildInfo.azureDevOpsBuildId + $AzureDevOpsAccount = $buildInfo.azureDevOpsAccount + + Write-Host "##vso[task.setvariable variable=BARBuildId;isOutput=true]$BarId" + Write-Host "##vso[task.setvariable variable=TargetChannels;isOutput=true]$Channels" + Write-Host "##vso[task.setvariable variable=IsStableBuild;isOutput=true]$IsStableBuild" + + Write-Host "##vso[task.setvariable variable=AzDOProjectName;isOutput=true]$AzureDevOpsProject" + Write-Host "##vso[task.setvariable variable=AzDOPipelineId;isOutput=true]$AzureDevOpsBuildDefinitionId" + Write-Host "##vso[task.setvariable variable=AzDOBuildId;isOutput=true]$AzureDevOpsBuildId" + Write-Host "##vso[task.setvariable variable=AzDOBuildAccount;isOutput=true]$AzureDevOpsAccount" + } + catch { + Write-Host $_ + Write-Host $_.Exception + Write-Host $_.ScriptStackTrace + exit 1 + } + env: + MAESTRO_API_TOKEN: $(MaestroApiAccessToken) + BARBuildId: ${{ parameters.BARBuildId }} + PromoteToMaestroChannels: ${{ parameters.PromoteToChannelIds }} diff --git a/eng/publishing/v3/signing-validation.yml b/eng/publishing/v3/signing-validation.yml new file mode 100644 index 000000000..22611ddff --- /dev/null +++ b/eng/publishing/v3/signing-validation.yml @@ -0,0 +1,56 @@ +jobs: +- job: + displayName: Signing Validation + dependsOn: setupMaestroVars + variables: + - template: /eng/publishing/v3/common-variables.yml + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Package Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: PackageArtifacts + checkDownloadedFiles: true + itemPattern: | + ** + !**/Microsoft.SourceBuild.Intermediate.*.nupkg + + # This is necessary whenever we want to publish/restore to an AzDO private feed + # Since sdk-task.ps1 tries to restore packages we need to do this authentication here + # otherwise it'll complain about accessing a private feed. + - task: NuGetAuthenticate@0 + displayName: 'Authenticate to AzDO Feeds' + + - task: PowerShell@2 + displayName: Enable cross-org publishing + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/enable-cross-org-publishing.ps1 + arguments: -token $(dn-bot-dnceng-artifact-feeds-rw) + + # Signing validation will optionally work with the buildmanifest file which is downloaded from + # Azure DevOps above. + - task: PowerShell@2 + displayName: Validate + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/sdk-task.ps1 + arguments: -task SigningValidation -restore -msbuildEngine vs + /p:PackageBasePath='$(Build.ArtifactStagingDirectory)/PackageArtifacts' + /p:SignCheckExclusionsFile='$(Build.SourcesDirectory)/eng/SignCheckExclusionsFile.txt' + ${{ parameters.signingValidationAdditionalParameters }} + + - template: /eng/common/templates/steps/publish-logs.yml + parameters: + StageLabel: 'Validation' + JobLabel: 'Signing' diff --git a/eng/publishing/v3/sourcelink-validation.yml b/eng/publishing/v3/sourcelink-validation.yml new file mode 100644 index 000000000..b290d57e4 --- /dev/null +++ b/eng/publishing/v3/sourcelink-validation.yml @@ -0,0 +1,36 @@ +jobs: +- job: + displayName: SourceLink Validation + dependsOn: setupMaestroVars + variables: + - template: /eng/publishing/v3/common-variables.yml + - name: AzDOProjectName + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOProjectName'] ] + - name: AzDOPipelineId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOPipelineId'] ] + - name: AzDOBuildId + value: $[ dependencies.setupMaestroVars.outputs['setReleaseVars.AzDOBuildId'] ] + pool: + vmImage: 'windows-2019' + steps: + - task: DownloadBuildArtifacts@0 + displayName: Download Blob Artifacts + inputs: + buildType: specific + buildVersionToDownload: specific + project: $(AzDOProjectName) + pipeline: $(AzDOPipelineId) + buildId: $(AzDOBuildId) + artifactName: BlobArtifacts + checkDownloadedFiles: true + + - task: PowerShell@2 + displayName: Validate + inputs: + filePath: $(Build.SourcesDirectory)/eng/common/post-build/sourcelink-validation.ps1 + arguments: -InputPath $(Build.ArtifactStagingDirectory)/BlobArtifacts/ + -ExtractPath $(Agent.BuildDirectory)/Extract/ + -GHRepoName $(Build.Repository.Name) + -GHCommit $(Build.SourceVersion) + -SourcelinkCliVersion $(SourceLinkCLIVersion) + continueOnError: true diff --git a/global.json b/global.json new file mode 100644 index 000000000..80304e5d6 --- /dev/null +++ b/global.json @@ -0,0 +1,18 @@ +{ + "tools": { + "vs": { + "version": "16.0", + "components": [ + "Microsoft.Net.Component.4.5.2.TargetingPack", + "Microsoft.VisualStudio.Windows.Build", + "Microsoft.VisualStudio.Component.VSSDK" + ] + }, + "dotnet": "6.0.100-preview.4.21255.9", + "vswhere": "2.5.2" + }, + "msbuild-sdks": { + "Microsoft.DotNet.Arcade.Sdk": "6.0.0-beta.21369.3", + "Microsoft.DotNet.Helix.Sdk": "6.0.0-beta.21369.3" + } +} diff --git a/samples/FxExtensibility/FxExtensibility.csproj b/samples/FxExtensibility/FxExtensibility.csproj index 7085c3cff..deda03426 100644 --- a/samples/FxExtensibility/FxExtensibility.csproj +++ b/samples/FxExtensibility/FxExtensibility.csproj @@ -1,9 +1,7 @@  - - ..\..\ - - + + Debug AnyCPU @@ -14,7 +12,9 @@ MSTest.Extensibility.Samples v4.5.2 512 + PackageReference + true full @@ -39,10 +39,11 @@ - + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core - + + \ No newline at end of file diff --git a/scripts/Build.ps1 b/scripts/Build.ps1 index 2f6aa55ed..80a1b4f3b 100644 --- a/scripts/Build.ps1 +++ b/scripts/Build.ps1 @@ -82,22 +82,6 @@ $TFB_Solutions = @( "TestFx.sln" ) -$TFB_NetCoreProjects = @( - "src\Adapter\PlatformServices.NetCore\PlatformServices.NetCore.csproj" - - "test\ComponentTests\TestAssets\TestProjectForAssemblyResolution\TestProjectForAssemblyResolution.csproj" - "test\E2ETests\TestAssets\CompatTestProject\CompatTestProject.csproj" - "test\E2ETests\TestAssets\DataRowTestProject\DataRowTestProject.csproj" - "test\E2ETests\TestAssets\DataSourceTestProject\DataSourceTestProject.csproj" - "test\E2ETests\TestAssets\DeploymentTestProject\DeploymentTestProject.csproj" - "test\E2ETests\TestAssets\DeploymentTestProjectNetCore\DeploymentTestProjectNetCore.csproj" - "test\E2ETests\TestAssets\DoNotParallelizeTestProject\DoNotParallelizeTestProject.csproj" - "test\E2ETests\TestAssets\FSharpTestProject\FSharpTestProject.fsproj" - "test\E2ETests\TestAssets\TimeoutTestProject\TimeoutTestProject.csproj" - "test\E2ETests\TestAssets\TimeoutTestProjectNetCore\TimeoutTestProjectNetCore.csproj" - "test\UnitTests\PlatformServices.NetCore.Unit.Tests\PlatformServices.NetCore.Unit.Tests.csproj" -) - # # Script Preferences # @@ -136,6 +120,25 @@ function Print-Help { Exit 0 } +function Install-WindowsSDK { + Push-Location + $temp = [System.IO.Path]::GetTempFileName(); + Remove-Item $temp + New-Item $temp -Type Directory | Out-Null + Set-Location $temp + + try { + Invoke-WebRequest -Method Get -Uri https://go.microsoft.com/fwlink/p/?LinkId=838916 -OutFile sdksetup.exe -UseBasicParsing + Start-Process -Wait sdksetup.exe -ArgumentList "/q", "/norestart", "/ceip off", "/features OptionId.WindowsSoftwareDevelopmentKit" -Wait -PassThru + } + finally { + Pop-Location + + Remove-Item $temp -Force -Recurse | Out-Null + } + +} + # # Restores packages for the solutions. # @@ -151,46 +154,16 @@ function Perform-Restore { $nuget = Locate-NuGet $nugetConfig = Locate-NuGetConfig - $toolset = Locate-Toolset - + $toolset = ".\scripts\Toolset\tools.proj" if ($TFB_ClearPackageCache) { - Write-Log " Clearing local package cache..." + Write-Log "Clearing local package cache..." & $nuget locals all -clear } - Write-Log " Starting toolset restore..." - Write-Verbose "$nuget restore -msbuildVersion $msbuildVersion -verbosity normal -nonInteractive -configFile $nugetConfig $toolset" - & $nuget restore -msbuildVersion $msbuildVersion -verbosity normal -nonInteractive -configFile $nugetConfig $toolset - - if ($lastExitCode -ne 0) { - throw "The restore failed with an exit code of '$lastExitCode'." - } - - Write-Verbose "Locating MSBuild install path..." - $msbuildPath = Locate-MSBuildPath - - Write-Verbose "Starting solution restore..." - foreach ($solution in $TFB_Solutions) { - $solutionPath = Locate-Item -relativePath $solution - - Write-Verbose "$nuget restore -msbuildPath $msbuildPath -verbosity quiet -nonInteractive -configFile $nugetConfig $solutionPath" - & $nuget restore -msbuildPath $msbuildPath -verbosity quiet -nonInteractive -configFile $nugetConfig $solutionPath - } - - if ($lastExitCode -ne 0) { - throw "The restore failed with an exit code of '$lastExitCode'." - } - - $msbuild = Join-Path $msbuildPath "MSBuild.exe" - - Write-Verbose "Starting restore for NetCore Projects" - foreach ($project in $TFB_NetCoreProjects) { - $projectPath = Locate-Item -relativePath $project + Write-Log "Starting toolset restore..." + Write-Verbose "$nuget restore -verbosity normal -nonInteractive -configFile $nugetConfig $toolset" + & $nuget restore -verbosity normal -nonInteractive -configFile $nugetConfig $toolset - Write-Verbose "$msbuild /t:restore -verbosity:minimal $projectPath /m" - & $msbuild /t:restore -verbosity:minimal $projectPath /m - } - if ($lastExitCode -ne 0) { throw "The restore failed with an exit code of '$lastExitCode'." } @@ -219,22 +192,37 @@ function Perform-Build { } } - Invoke-Build -solution "TestFx.sln" + Invoke-MSBuild -solution "TestFx.sln" Write-Log "Perform-Build: Completed. {$(Get-ElapsedTime($timer))}" } -function Invoke-Build([string] $solution, $hasVsixExtension = "false") { +function Invoke-MSBuild([string]$solution, $buildTarget = $Target, $hasVsixExtension = "false", [switch]$NoRestore) { $msbuild = Locate-MSBuild -hasVsixExtension $hasVsixExtension $solutionPath = Locate-Item -relativePath $solution - $solutionDir = [System.IO.Path]::GetDirectoryName($solutionPath) - $solutionSummaryLog = Join-Path -path $solutionDir -childPath "msbuild.log" - $solutionWarningLog = Join-Path -path $solutionDir -childPath "msbuild.wrn" - $solutionFailureLog = Join-Path -path $solutionDir -childPath "msbuild.err" - - Write-Log " Building $solution..." - Write-Verbose "$msbuild /t:$Target /p:Configuration=$configuration /v:m /flp1:Summary`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionSummaryLog /flp2:WarningsOnly`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionWarningLog /flp3:ErrorsOnly`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionFailureLog /p:IsLocalizedBuild=$TFB_IsLocalizedBuild /p:UpdateXlf=$TFB_UpdateXlf /p:BuildVersion=$TFB_BuildVersion $solutionPath /bl /m" - & $msbuild /t:$Target /p:Configuration=$configuration /v:m /flp1:Summary`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionSummaryLog /flp2:WarningsOnly`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionWarningLog /flp3:ErrorsOnly`;Verbosity=diagnostic`;Encoding=UTF-8`;LogFile=$solutionFailureLog /p:IsLocalizedBuild=$TFB_IsLocalizedBuild /p:UpdateXlf=$TFB_UpdateXlf /p:BuildVersion=$TFB_BuildVersion $solutionPath /bl /m + $logsDir = Get-LogsPath + + $fileName = [System.IO.Path]::GetFileNameWithoutExtension($solution) + $binLog = Join-Path -path $logsDir -childPath "$fileName.$buildTarget.binlog" + + $restore = "True" + if($NoRestore) { + $restore = "False" + } + + $argument = @("-t:$buildTarget", + "-p:Configuration=$configuration", + "-v:m", + "-p:IsLocalizedBuild=$TFB_IsLocalizedBuild", + "-p:UpdateXlf=$TFB_UpdateXlf", + "-p:BuildVersion=$TFB_BuildVersion", + "-restore:$restore", + "`"$solutionPath`"", + "-bl:`"$binLog`"", + "-m") + + Write-Log " $buildTarget`: $solution..." + & "$msbuild" $argument; if ($lastExitCode -ne 0) { throw "Build failed with an exit code of '$lastExitCode'." @@ -271,10 +259,6 @@ function Create-NugetPackages { Copy-Item -Path "$($env:TF_PACKAGES_DIR)\microsoft.testplatform.adapterutilities\$TestPlatformVersion\lib" -Destination "$($stagingDir)\Microsoft.TestPlatform.AdapterUtilities" -Recurse -Force - # Copy over LICENSE file to staging directory - $licenseFilePath = Join-Path $env:TF_ROOT_DIR "LICENSE" - Copy-Item $licenseFilePath $stagingDir -Force - # Call nuget pack on these components. $nugetExe = Locate-Nuget @@ -300,34 +284,6 @@ function Create-NugetPackages { Write-Log "Create-NugetPackages: Complete. {$(Get-ElapsedTime($timer))}" } -function Replace-InFile($File, $RegEx, $ReplaceWith) { - $content = Get-Content -Raw -Encoding utf8 $File - $newContent = ($content -replace $RegEx, $ReplaceWith) - if (-not $content.Equals($newContent)) { - Write-Log "Updating TestPlatform version in $File" - $newContent | Set-Content -Encoding utf8 $File -NoNewline - } -} - -function Sync-PackageVersions { - $versionsRegex = '(?mi)<(TestPlatformVersion.*?)>(.*?)<\/TestPlatformVersion>' - $packageRegex = '(?mi)$TestPlatformVersion" - } - - (Get-ChildItem "$PSScriptRoot\..\src\*packages.config", "$PSScriptRoot\..\test\*packages.config" -Recurse) | ForEach-Object { - Replace-InFile -File $_ -RegEx $packageRegex -ReplaceWith (' - - - + + + - + - - + + - + - - + + - + - + - + - + - + - <_SourcePath>$(TestFxPackagesRoot)MSTest.Internal.TestFx.Localized.Documentation.1.0.0-build-20170420-1\contentFiles\any\any\$(LocDocumentationSubPath) + <_SourcePath>$(NuGetPackageRoot)\MSTest.Internal.TestFx.Localized.Documentation\$(MsTestInternalTestFxLocalizedDocumentationVersion)\contentFiles\any\any\$(LocDocumentationSubPath) <_LocalizedFiles Include="$(_SourcePath)\**\*.*" /> @@ -80,9 +80,17 @@ - + - + + + + diff --git a/scripts/build/TestFx.Settings.targets b/scripts/build/TestFx.Settings.targets deleted file mode 100644 index 2f53ecce3..000000000 --- a/scripts/build/TestFx.Settings.targets +++ /dev/null @@ -1,40 +0,0 @@ - - - - ..\..\ - $(MSBuildThisFileDirectory)..\..\ - true - - - - - - - - - Debug - AnyCPU - en-US - 512 - true - $(MSBuildThisFileDirectory)key.snk - true - true - - true - $(TestFxRoot)artifacts\$(Configuration)\$(MSBuildProjectName)\ - $(TestFxRoot)artifacts\$(Configuration)\$(MSBuildProjectName)\obj\ - true - - - - true - - - - - false - $(MSBuildThisFileDirectory)stylecop.ruleset - $(MSBuildThisFileDirectory)stylecop.test.ruleset - - \ No newline at end of file diff --git a/scripts/build/TestFx.Versions.targets b/scripts/build/TestFx.Versions.targets deleted file mode 100644 index 4e3fe47b7..000000000 --- a/scripts/build/TestFx.Versions.targets +++ /dev/null @@ -1,7 +0,0 @@ - - - - 16.9.1 - 11.0 - - \ No newline at end of file diff --git a/scripts/build/TestFx.props b/scripts/build/TestFx.props new file mode 100644 index 000000000..ddc819bce --- /dev/null +++ b/scripts/build/TestFx.props @@ -0,0 +1,37 @@ + + + + $([MSBuild]::NormalizeDirectory('$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildProjectDirectory), 'LICENSE'))')) + $(RepoRoot)artifacts\$(Configuration)\ + true + + + + + + Debug + AnyCPU + en-US + 512 + true + $(MSBuildThisFileDirectory)key.snk + true + true + + true + $(RepoRoot)artifacts\$(Configuration)\$(MSBuildProjectName)\ + $(RepoRoot)artifacts\$(Configuration)\$(MSBuildProjectName)\obj\ + true + + + + true + + + + + false + $(MSBuildThisFileDirectory)stylecop.ruleset + $(MSBuildThisFileDirectory)stylecop.test.ruleset + + \ No newline at end of file diff --git a/scripts/build/TestFx.targets b/scripts/build/TestFx.targets index 3156375e2..c6155c40f 100644 --- a/scripts/build/TestFx.targets +++ b/scripts/build/TestFx.targets @@ -1,21 +1,7 @@  - - - - - - ..\..\ - ..\..\ - $(TestFxRoot)packages\ - true - - - - - - + @@ -25,19 +11,19 @@ - - + + stylecop.json - - - + + + - - + + Microsoft400 StrongName @@ -48,14 +34,6 @@ - - - This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. - - - - - @@ -84,7 +62,7 @@ - + diff --git a/scripts/common.lib.ps1 b/scripts/common.lib.ps1 index d63a78aeb..6f7b4714c 100644 --- a/scripts/common.lib.ps1 +++ b/scripts/common.lib.ps1 @@ -3,26 +3,39 @@ # Common utilities for building solution and running tests +$TF_ROOT_DIR = (Get-Item (Split-Path $MyInvocation.MyCommand.Path)).Parent.FullName +$TF_VERSIONS_FILE = "$TF_ROOT_DIR\eng\Versions.props" +$TF_OUT_DIR = Join-Path $TF_ROOT_DIR "artifacts" +$TF_SRC_DIR = Join-Path $TF_ROOT_DIR "src" +$TF_TEST_DIR = Join-Path $TF_ROOT_DIR "test" +$TF_PACKAGES_DIR = Join-Path $TF_ROOT_DIR "packages" +$TF_TOOLS_DIR = Join-Path $TF_ROOT_DIR "tools" + +function Get-PackageVersion ([string]$PackageName) { + $packages = ([XML](Get-Content $TF_VERSIONS_FILE)).Project.PropertyGroup + + return $packages[$PackageName].InnerText; +} + # # Global Variables # -$global:msbuildVersion = "15.0" -$global:nugetVersion = "5.8.1" -$global:vswhereVersion = "2.0.2" -$global:nugetUrl = "https://dist.nuget.org/win-x86-commandline/v$nugetVersion/NuGet.exe" +$global:nugetVersion = Get-PackageVersion -PackageName "NuGetFrameworksVersion" +$global:vswhereVersion = Get-PackageVersion -PackageName "VsWhereVersion" # # Global Environment Variables # -$env:TF_ROOT_DIR = (Get-Item (Split-Path $MyInvocation.MyCommand.Path)).Parent.FullName -$env:TF_OUT_DIR = Join-Path $env:TF_ROOT_DIR "artifacts" -$env:TF_SRC_DIR = Join-Path $env:TF_ROOT_DIR "src" -$env:TF_TEST_DIR = Join-Path $env:TF_ROOT_DIR "test" -$env:TF_PACKAGES_DIR = Join-Path $env:TF_ROOT_DIR "packages" +$env:TF_ROOT_DIR = $TF_ROOT_DIR +$env:TF_OUT_DIR = $TF_OUT_DIR +$env:TF_SRC_DIR = $TF_SRC_DIR +$env:TF_TEST_DIR = $TF_TEST_DIR +$env:TF_PACKAGES_DIR = $TF_PACKAGES_DIR +$env:TF_TOOLS_DIR = $TF_TOOLS_DIR +$env:DOTNET_CLI_VERSION = "6.0.100-alpha.1.21067.8" -$TF_VERSIONS_FILE = "$PSScriptRoot\build\TestFx.Versions.targets" if ([String]::IsNullOrWhiteSpace($TestPlatformVersion)) { - $TestPlatformVersion = (([XML](Get-Content $TF_VERSIONS_FILE)).Project.PropertyGroup.TestPlatformVersion).InnerText + $TestPlatformVersion = Get-PackageVersion -PackageName "MicrosoftNETTestSdkVersion" } function Create-Directory([string[]] $path) { @@ -50,7 +63,7 @@ function Locate-MSBuild($hasVsixExtension = "false") { $msbuild = Join-Path -path $msbuildPath -childPath "MSBuild.exe" if (!(Test-Path -path $msbuild)) { - throw "The specified MSBuild version ($msbuildVersion) could not be located." + throw "The specified MSBuild could not be located." } return Resolve-Path -path $msbuild @@ -66,7 +79,7 @@ function Locate-MSBuildPath($hasVsixExtension = "false") { } catch { # Resolve-Path throws if the path does not exist, so use the VS2017 path as a fallback - $msbuildPath = Join-Path -path $vsInstallPath -childPath "MSBuild\$msbuildVersion\Bin" + $msbuildPath = Join-Path -path $vsInstallPath -childPath "MSBuild\15.0\Bin" $msbuildPath = Resolve-Path $msbuildPath } @@ -74,7 +87,7 @@ function Locate-MSBuildPath($hasVsixExtension = "false") { } function Locate-NuGet { - $rootPath = $env:TF_ROOT_DIR + $rootPath = Join-Path -path $env:TF_PACKAGES_DIR -childPath "toolset" $nuget = Join-Path -path $rootPath -childPath "nuget.exe" if (Test-Path -path $nuget) { @@ -88,7 +101,8 @@ function Locate-NuGet { Remove-Item -path $nuget | Out-Null } - Download-File -address $nugetUrl -fileName $nuget + New-Item $rootPath -ItemType Directory | Out-Null + Download-File -address "https://dist.nuget.org/win-x86-commandline/v$nugetVersion/NuGet.exe" -fileName $nuget if (!(Test-Path -path $nuget)) { throw "The specified NuGet version ($nugetVersion) could not be downloaded." @@ -103,12 +117,6 @@ function Locate-NuGetConfig { return Resolve-Path -path $nugetConfig } -function Locate-Toolset { - $rootPath = $env:TF_ROOT_DIR - $toolset = Join-Path -path $rootPath -childPath "scripts\Toolset\packages.config" - return Resolve-Path -path $toolset -} - function Locate-PackagesPath { $rootPath = $env:TF_ROOT_DIR $packagesPath = Join-Path -path $rootPath -childPath "packages" @@ -120,7 +128,7 @@ function Locate-PackagesPath { function Locate-VsWhere { $packagesPath = Locate-PackagesPath - $vswhere = Join-Path -path $packagesPath -childPath "vswhere.$vswhereVersion\tools\vswhere.exe" + $vswhere = Join-Path -path $packagesPath -childPath "vswhere\$vswhereVersion\tools\vswhere.exe" Write-Verbose "vswhere location is : $vswhere" return $vswhere @@ -162,6 +170,24 @@ function Locate-Item([string] $relativePath) { return Resolve-Path -path $itemPath } +function Get-LogsPath { + $artifacts = Join-Path -path $TF_OUT_DIR -childPath "logs" + + if (-not (Test-Path $artifacts)) { + New-Item -Type Directory -Path $artifacts | Out-Null + } + + return $artifacts +} + +function Get-VSTestPath +{ + $TestPlatformVersion = Get-PackageVersion -PackageName "MicrosoftNETTestSdkVersion" + $vstestPath = Join-Path -path (Locate-PackagesPath) "Microsoft.TestPlatform\$TestPlatformVersion\tools\net451\Common7\IDE\Extensions\TestPlatform\vstest.console.exe" + + return Resolve-Path -path $vstestPath +} + function Start-Timer { return [System.Diagnostics.Stopwatch]::StartNew() } @@ -180,6 +206,34 @@ function Write-Log ([string] $message, $messageColor = "Green") { $Host.UI.RawUI.ForegroundColor = $currentColor } +function Replace-InFile($File, $RegEx, $ReplaceWith) { + $content = Get-Content -Raw -Encoding utf8 $File + $newContent = ($content -replace $RegEx, $ReplaceWith) + if (-not $content.Equals($newContent)) { + Write-Log "Updating TestPlatform version in $File" + $newContent | Set-Content -Encoding utf8 $File -NoNewline + } +} + +function Sync-PackageVersions { + $versionsRegex = '(?mi)<(MicrosoftNETTestSdkVersion.*?)>(.*?)<\/MicrosoftNETTestSdkVersion>' + $packageRegex = '(?mi)$TestPlatformVersion" + } + + (Get-ChildItem "$PSScriptRoot\..\src\*packages.config", "$PSScriptRoot\..\test\*packages.config" -Recurse) | ForEach-Object { + Replace-InFile -File $_ -RegEx $packageRegex -ReplaceWith (' - - - - - - - - \ No newline at end of file diff --git a/scripts/toolset/tools.proj b/scripts/toolset/tools.proj new file mode 100644 index 000000000..53ff31938 --- /dev/null +++ b/scripts/toolset/tools.proj @@ -0,0 +1,42 @@ + + + $([MSBuild]::NormalizeDirectory('$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildProjectDirectory), 'LICENSE'))')) + + + <_NuGetRestoreTargets Condition="Exists('$(MSBuildToolsPath)\NuGet.targets')" >$(MSBuildToolsPath)\NuGet.targets + <_NuGetRestoreTargets Condition="'$([MSBuild]::IsRunningFromVisualStudio())' == 'true' And Exists('$(MSBuildToolsPath32)\..\..\..\Common7\IDE\CommonExtensions\Microsoft\NuGet\NuGet.targets')">$(MSBuildToolsPath32)\..\..\..\Common7\IDE\CommonExtensions\Microsoft\NuGet\NuGet.targets + + + + + + + true + + + + + net472 + + 5 + .NETFramework + .NETFramework,Version=v4.7.2 + $(RepoRoot)artifacts\toolset\ + $(OutputPath) + + + + + $(RepoRoot)NuGet.config + + + + + \ No newline at end of file diff --git a/scripts/verify-sign.ps1 b/scripts/verify-sign.ps1 index 14ac0a0e0..5f34d6731 100644 --- a/scripts/verify-sign.ps1 +++ b/scripts/verify-sign.ps1 @@ -1,4 +1,6 @@ -# Copyright (c) Microsoft. All rights reserved. +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT license. See LICENSE file in the project root for full license information. + # Build script for Test Platform. [CmdletBinding()] @@ -33,7 +35,7 @@ function Verify-NugetPackages $artifactsDirectory = Join-Path $rootDirectory "artifacts" $artifactsConfigDirectory = Join-Path $artifactsDirectory $TPB_Configuration $packagesDirectory = Join-Path $artifactsConfigDirectory "MSTestPackages" - Get-ChildItem -Filter *.nupkg $packagesDirectory | % { + Get-ChildItem -Filter *.nupkg $packagesDirectory | ForEach-Object { & $nugetInstallPath verify -signature -CertificateFingerprint "3F9001EA83C560D712C24CF213C3D312CB3BFF51EE89435D3430BD06B5D0EECE;AA12DA22A49BCE7D5C1AE64CC1F3D892F150DA76140F210ABD2CBFFCA2C18A27;" $_.FullName } diff --git a/scripts/write-release-notes.ps1 b/scripts/write-release-notes.ps1 index c4e9b0609..a2332a986 100644 --- a/scripts/write-release-notes.ps1 +++ b/scripts/write-release-notes.ps1 @@ -1,3 +1,6 @@ +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT license. See LICENSE file in the project root for full license information. + [CmdletBinding()] param ( @@ -99,7 +102,7 @@ $issues = $log | ForEach-Object { $output = @" -See release notes [here](https://github.com/microsoft/testfx-docs/blob/master/docs/releases.md#$(("$v $date" -replace "\.", "" -replace "\W", "-").ToLowerInvariant())). +See release notes [here](https://github.com/microsoft/testfx-docs/blob/main/docs/releases.md#$(("$v $date" -replace "\.", "" -replace "\W", "-").ToLowerInvariant())). --- diff --git a/src/Adapter/Build/Desktop/MSTest.TestAdapter.targets b/src/Adapter/Build/Desktop/MSTest.TestAdapter.targets index 0649e3a2a..1c80426d0 100644 --- a/src/Adapter/Build/Desktop/MSTest.TestAdapter.targets +++ b/src/Adapter/Build/Desktop/MSTest.TestAdapter.targets @@ -1,7 +1,7 @@ - true + true @@ -10,21 +10,21 @@ So the below code should not break build in any case. --> - - - - + + + + - + %(CurrentUICultureHierarchy.Identity) - + %(MSTestV2ResourceFiles.CultureString)\%(Filename)%(Extension) PreserveNewest False diff --git a/src/Adapter/Build/Universal/MSTest.TestAdapter.targets b/src/Adapter/Build/Universal/MSTest.TestAdapter.targets index b0404380c..8d11b4937 100644 --- a/src/Adapter/Build/Universal/MSTest.TestAdapter.targets +++ b/src/Adapter/Build/Universal/MSTest.TestAdapter.targets @@ -1,7 +1,7 @@ - true + true @@ -10,15 +10,15 @@ So the below code should not break build in any case. --> - - - - + + + + - + %(CurrentUICultureHierarchy.Identity) diff --git a/src/Adapter/Build/WinUI/MSTest.TestAdapter.props b/src/Adapter/Build/WinUI/MSTest.TestAdapter.props new file mode 100644 index 000000000..aa6baccb4 --- /dev/null +++ b/src/Adapter/Build/WinUI/MSTest.TestAdapter.props @@ -0,0 +1,33 @@ + + + + + Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.dll + PreserveNewest + False + + + Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.dll + PreserveNewest + False + + + Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll + PreserveNewest + False + + + Microsoft.TestPlatform.AdapterUtilities.dll + PreserveNewest + False + + + + + + + + diff --git a/src/Adapter/Build/WinUI/MSTest.TestAdapter.targets b/src/Adapter/Build/WinUI/MSTest.TestAdapter.targets new file mode 100644 index 000000000..8d11b4937 --- /dev/null +++ b/src/Adapter/Build/WinUI/MSTest.TestAdapter.targets @@ -0,0 +1,42 @@ + + + + true + + + + + + + + + + + + + + + + + + %(CurrentUICultureHierarchy.Identity) + + + + + + + + + $(CurrentUICultureHierarchy)\%(FileName).resources.dll + PreserveNewest + %(FullPath) + False + + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Constants.cs b/src/Adapter/MSTest.CoreAdapter/Constants.cs index 98a758d91..6d930643a 100644 --- a/src/Adapter/MSTest.CoreAdapter/Constants.cs +++ b/src/Adapter/MSTest.CoreAdapter/Constants.cs @@ -89,6 +89,9 @@ internal static class Constants internal static readonly TestProperty TfsTeamProjectProperty = TestProperty.Register(TfsTeamProject, TfsTeamProject, typeof(string), TestPropertyAttributes.Hidden, typeof(TestCase)); + internal static readonly TestProperty TestDynamicDataTypeProperty = TestProperty.Register("MSTest.DynamicDataType", "DynamicDataType", typeof(int), TestPropertyAttributes.Hidden, typeof(TestCase)); + + internal static readonly TestProperty TestDynamicDataProperty = TestProperty.Register("MSTest.DynamicData", "DynamicData", typeof(string[]), TestPropertyAttributes.Hidden, typeof(TestCase)); #endregion #region Private Constants diff --git a/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumerator.cs b/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumerator.cs index 4c67d2bad..a8a3b9dde 100644 --- a/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumerator.cs +++ b/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumerator.cs @@ -6,21 +6,35 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Discovery using System; using System.Collections.Generic; using System.Diagnostics; - using System.Diagnostics.CodeAnalysis; using System.Globalization; using System.Linq; using System.Reflection; + using System.Runtime.Serialization; using System.Security; using System.Text; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Execution; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface; + + using UTF = Microsoft.VisualStudio.TestTools.UnitTesting; /// /// Enumerates through all types in the assembly in search of valid test methods. /// internal class AssemblyEnumerator : MarshalByRefObject { + /// + /// Helper for reflection API's. + /// + private static readonly ReflectHelper ReflectHelper = ReflectHelper.Instance; + + /// + /// Type cache + /// + private readonly TypeCache typeCache = new TypeCache(ReflectHelper); + /// /// Initializes a new instance of the class. /// @@ -40,6 +54,11 @@ public AssemblyEnumerator(MSTestSettings settings) MSTestSettings.PopulateSettings(settings); } + /// + /// Gets or sets the run settings to use for current discovery session. + /// + public string RunSettingsXml { get; set; } + /// /// Returns object to be used for controlling lifetime, null means infinite lifetime. /// @@ -62,6 +81,7 @@ internal ICollection EnumerateAssembly(string assemblyFileName, { Debug.Assert(!string.IsNullOrWhiteSpace(assemblyFileName), "Invalid assembly file name."); + var runSettingsXml = this.RunSettingsXml; var warningMessages = new List(); var tests = new List(); @@ -88,42 +108,8 @@ internal ICollection EnumerateAssembly(string assemblyFileName, continue; } - string typeFullName = null; - - try - { - ICollection warningsFromTypeEnumerator; - - typeFullName = type.FullName; - var unitTestCases = this.GetTypeEnumerator(type, assemblyFileName).Enumerate(out warningsFromTypeEnumerator); - - if (warningsFromTypeEnumerator != null) - { - warningMessages.AddRange(warningsFromTypeEnumerator); - } - - if (unitTestCases != null) - { - tests.AddRange(unitTestCases); - } - } - catch (Exception exception) - { - // If we fail to discover type from a class, then don't abort the discovery - // Move to the next type. - string message = string.Format( - CultureInfo.CurrentCulture, - Resource.CouldNotInspectTypeDuringDiscovery, - typeFullName, - assemblyFileName, - exception.Message); - warningMessages.Add(message); - - PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo( - "AssemblyEnumerator: Exception occurred while enumerating type {0}. {1}", - typeFullName, - exception); - } + var testsInType = this.DiscoverTestsInType(assemblyFileName, runSettingsXml, assembly, type, warningMessages); + tests.AddRange(testsInType); } warnings = warningMessages; @@ -146,20 +132,13 @@ internal Type[] GetTypes(Assembly assembly, string assemblyFileName, ICollection } catch (ReflectionTypeLoadException ex) { - PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning( - "MSTestExecutor.TryGetTests: Failed to discover tests from {0}. Reason:{1}", - assemblyFileName, - ex); - PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning("Exceptions thrown from the Loader :"); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning($"MSTestExecutor.TryGetTests: {Resource.TestAssembly_AssemblyDiscoveryFailure}", assemblyFileName, ex); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning(Resource.ExceptionsThrown); if (ex.LoaderExceptions != null) { // If not able to load all type, log a warning and continue with loaded types. - var message = string.Format( - CultureInfo.CurrentCulture, - Resource.TypeLoadFailed, - assemblyFileName, - this.GetLoadExceptionDetails(ex)); + var message = string.Format(CultureInfo.CurrentCulture, Resource.TypeLoadFailed, assemblyFileName, this.GetLoadExceptionDetails(ex)); warningMessages?.Add(message); @@ -217,11 +196,205 @@ internal string GetLoadExceptionDetails(ReflectionTypeLoadException ex) /// a TypeEnumerator instance. internal virtual TypeEnumerator GetTypeEnumerator(Type type, string assemblyFileName) { - var reflectHelper = new ReflectHelper(); - var typevalidator = new TypeValidator(reflectHelper); - var testMethodValidator = new TestMethodValidator(reflectHelper); + var typeValidator = new TypeValidator(ReflectHelper); + var testMethodValidator = new TestMethodValidator(ReflectHelper); + + return new TypeEnumerator(type, assemblyFileName, ReflectHelper, typeValidator, testMethodValidator); + } + + private IEnumerable DiscoverTestsInType(string assemblyFileName, string runSettingsXml, Assembly assembly, Type type, List warningMessages) + { + var sourceLevelParameters = PlatformServiceProvider.Instance.SettingsProvider.GetProperties(assemblyFileName); + sourceLevelParameters = RunSettingsUtilities.GetTestRunParameters(runSettingsXml)?.ConcatWithOverwrites(sourceLevelParameters) + ?? sourceLevelParameters + ?? new Dictionary(); + + string typeFullName = null; + var tests = new List(); + + try + { + typeFullName = type.FullName; + var unitTestCases = this.GetTypeEnumerator(type, assemblyFileName).Enumerate(out var warningsFromTypeEnumerator); + var typeIgnored = ReflectHelper.IsAttributeDefined(type, typeof(UTF.IgnoreAttribute), false); + + if (warningsFromTypeEnumerator != null) + { + warningMessages.AddRange(warningsFromTypeEnumerator); + } + + if (unitTestCases != null) + { + foreach (var test in unitTestCases) + { + if (this.DynamicDataAttached(sourceLevelParameters, assembly, test, tests)) + { + continue; + } + + tests.Add(test); + } + } + } + catch (Exception exception) + { + // If we fail to discover type from a class, then don't abort the discovery + // Move to the next type. + string message = string.Format(CultureInfo.CurrentCulture, Resource.CouldNotInspectTypeDuringDiscovery, typeFullName, assemblyFileName, exception.Message); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo($"AssemblyEnumerator: {message}"); + warningMessages.Add(message); + } + + return tests; + } + + private bool DynamicDataAttached(IDictionary sourceLevelParameters, Assembly assembly, UnitTestElement test, List tests) + { + // It should always be `true`, but if any part of the chain is obsolete; it might not contain those. + // Since we depend on those properties, if they don't exist, we bail out early. + if (!test.TestMethod.HasManagedMethodAndTypeProperties) + { + return false; + } + + using (var writer = new ThreadSafeStringWriter(CultureInfo.InvariantCulture)) + { + var testMethod = test.TestMethod; + var testContext = PlatformServiceProvider.Instance.GetTestContext(testMethod, writer, sourceLevelParameters); + var testMethodInfo = this.typeCache.GetTestMethodInfo(testMethod, testContext, MSTestSettings.CurrentSettings.CaptureDebugTraces); + if (testMethodInfo == null) + { + return false; + } + + return /* DataSourceAttribute discovery is disabled for now, since we cannot serialize DataRow values. + this.TryProcessDataSource(test, testMethodInfo, testContext, tests) || */ + this.TryProcessTestDataSourceTests(test, testMethodInfo, tests); + } + } + + private bool TryProcessDataSource(UnitTestElement test, TestMethodInfo testMethodInfo, ITestContext testContext, List tests) + { + var dataSourceAttributes = ReflectHelper.GetAttributes(testMethodInfo.MethodInfo, false); + if (dataSourceAttributes == null) + { + return false; + } + + if (dataSourceAttributes.Length > 1) + { + var message = string.Format(CultureInfo.CurrentCulture, Resource.CannotEnumerateDataSourceAttribute_MoreThenOneDefined, test.TestMethod.ManagedTypeName, test.TestMethod.ManagedMethodName, dataSourceAttributes.Length); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo($"DynamicDataEnumarator: {message}"); + throw new InvalidOperationException(message); + } + + // dataSourceAttributes.Length == 1 + try + { + return this.ProcessDataSourceTests(test, testMethodInfo, testContext, tests); + } + catch (Exception ex) + { + var message = string.Format(CultureInfo.CurrentCulture, Resource.CannotEnumerateDataSourceAttribute, test.TestMethod.ManagedTypeName, test.TestMethod.ManagedMethodName, ex); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo($"DynamicDataEnumarator: {message}"); + return false; + } + } + + private bool ProcessDataSourceTests(UnitTestElement test, TestMethodInfo testMethodInfo, ITestContext testContext, List tests) + { + var dataRows = PlatformServiceProvider.Instance.TestDataSource.GetData(testMethodInfo, testContext); + if (dataRows == null || !dataRows.Any()) + { + return false; + } + + try + { + int rowIndex = 0; + + foreach (var dataRow in dataRows) + { + // TODO: Test serialization + rowIndex++; + + var displayName = string.Format(CultureInfo.CurrentCulture, Resource.DataDrivenResultDisplayName, test.DisplayName, rowIndex); + var discoveredTest = test.Clone(); + discoveredTest.DisplayName = displayName; + discoveredTest.TestMethod.DataType = DynamicDataType.DataSourceAttribute; + discoveredTest.TestMethod.SerializedData = DataSerializationHelper.Serialize(new[] { (object)rowIndex }); + tests.Add(discoveredTest); + } + + return true; + } + finally + { + testContext.SetDataConnection(null); + testContext.SetDataRow(null); + } + } + + private bool TryProcessTestDataSourceTests(UnitTestElement test, TestMethodInfo testMethodInfo, List tests) + { + var methodInfo = testMethodInfo.MethodInfo; + var testDataSources = ReflectHelper.GetAttributes(methodInfo, false)?.Where(a => a is UTF.ITestDataSource).OfType().ToArray(); + if (testDataSources == null || testDataSources.Length == 0) + { + return false; + } + + try + { + return this.ProcessTestDataSourceTests(test, (MethodInfo)methodInfo, testDataSources, tests); + } + catch (Exception ex) + { + var message = string.Format(CultureInfo.CurrentCulture, Resource.CannotEnumerateIDataSourceAttribute, test.TestMethod.ManagedTypeName, test.TestMethod.ManagedMethodName, ex); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo($"DynamicDataEnumarator: {message}"); + return false; + } + } + + private bool ProcessTestDataSourceTests(UnitTestElement test, MethodInfo methodInfo, UTF.ITestDataSource[] testDataSources, List tests) + { + foreach (var dataSource in testDataSources) + { + var data = dataSource.GetData(methodInfo); + var discoveredTests = new List(); + var serializationFailed = false; + + foreach (var d in data) + { + var discoveredTest = test.Clone(); + discoveredTest.DisplayName = dataSource.GetDisplayName(methodInfo, d); + + try + { + discoveredTest.TestMethod.SerializedData = DataSerializationHelper.Serialize(d); + discoveredTest.TestMethod.DataType = DynamicDataType.ITestDataSource; + } + catch (SerializationException) + { + serializationFailed = true; + break; + } + + discoveredTests.Add(discoveredTest); + } + + // Serialization failed for the type, bail out. + if (serializationFailed) + { + tests.Add(test); + + break; + } + + tests.AddRange(discoveredTests); + } - return new TypeEnumerator(type, assemblyFileName, reflectHelper, typevalidator, testMethodValidator); + return true; } } } diff --git a/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumeratorWrapper.cs b/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumeratorWrapper.cs index 2a1d19244..42f2a7a76 100644 --- a/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumeratorWrapper.cs +++ b/src/Adapter/MSTest.CoreAdapter/Discovery/AssemblyEnumeratorWrapper.cs @@ -69,7 +69,7 @@ internal ICollection GetTests(string assemblyFileName, IRunSett { var message = string.Format(CultureInfo.CurrentCulture, Resource.TestAssembly_AssemblyDiscoveryFailure, fullFilePath, ex.Message); PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning($"{nameof(AssemblyEnumeratorWrapper)}.{nameof(this.GetTests)}: {Resource.TestAssembly_AssemblyDiscoveryFailure}", fullFilePath, ex); - PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning("Exceptions thrown from the loader: "); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning(Resource.ExceptionsThrown); warnings.Add(message); if (ex.LoaderExceptions != null) @@ -108,6 +108,16 @@ private ICollection GetTestsInIsolation(string fullFilePath, IR // Create an instance of a type defined in adapter so that adapter gets loaded in the child app domain var assemblyEnumerator = isolationHost.CreateInstanceForType(typeof(AssemblyEnumerator), new object[] { MSTestSettings.CurrentSettings }) as AssemblyEnumerator; + // This might not be supported if an older version of "PlatformServices" (Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices) assembly is already loaded into the App Domain. + try + { + assemblyEnumerator.RunSettingsXml = runSettings?.SettingsXml; + } + catch + { + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning(Resource.OlderTFMVersionFound); + } + return assemblyEnumerator.EnumerateAssembly(fullFilePath, out warnings); } } diff --git a/src/Adapter/MSTest.CoreAdapter/Discovery/TypeEnumerator.cs b/src/Adapter/MSTest.CoreAdapter/Discovery/TypeEnumerator.cs index 5c585a579..769545484 100644 --- a/src/Adapter/MSTest.CoreAdapter/Discovery/TypeEnumerator.cs +++ b/src/Adapter/MSTest.CoreAdapter/Discovery/TypeEnumerator.cs @@ -198,11 +198,10 @@ internal UnitTestElement GetTestFromMethod(MethodInfo method, bool isDeclaredInT testElement.WorkItemIds = workItemAttributes.Select(x => x.Id.ToString()).ToArray(); } + testElement.Ignored = this.reflectHelper.IsAttributeDefined(method, typeof(IgnoreAttribute), false); + // Get Deployment items if any. - testElement.DeploymentItems = PlatformServiceProvider.Instance.TestDeployment.GetDeploymentItems( - method, - this.type, - warnings); + testElement.DeploymentItems = PlatformServiceProvider.Instance.TestDeployment.GetDeploymentItems(method, this.type, warnings); // get DisplayName from TestMethodAttribute var testMethodAttribute = this.reflectHelper.GetCustomAttribute(method, typeof(TestMethodAttribute)) as TestMethodAttribute; diff --git a/src/Adapter/MSTest.CoreAdapter/Discovery/UnitTestDiscoverer.cs b/src/Adapter/MSTest.CoreAdapter/Discovery/UnitTestDiscoverer.cs index 4a75207da..dbd6614bb 100644 --- a/src/Adapter/MSTest.CoreAdapter/Discovery/UnitTestDiscoverer.cs +++ b/src/Adapter/MSTest.CoreAdapter/Discovery/UnitTestDiscoverer.cs @@ -58,9 +58,7 @@ internal UnitTestDiscoverer() ITestCaseDiscoverySink discoverySink, IDiscoveryContext discoveryContext) { - ICollection warnings; - - var testElements = this.assemblyEnumeratorWrapper.GetTests(source, discoveryContext?.RunSettings, out warnings); + var testElements = this.assemblyEnumeratorWrapper.GetTests(source, discoveryContext?.RunSettings, out var warnings); // log the warnings foreach (var warning in warnings) @@ -100,8 +98,7 @@ internal void SendTestCases(string source, IEnumerable testElem } // Get filter expression and skip discovery in case filter expression has parsing error. - bool filterHasError = false; - ITestCaseFilterExpression filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, logger, out filterHasError); + ITestCaseFilterExpression filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, logger, out var filterHasError); if (filterHasError) { return; @@ -117,12 +114,11 @@ internal void SendTestCases(string source, IEnumerable testElem continue; } - object testNavigationSession; if (shouldCollectSourceInformation) { string testSource = testElement.TestMethod.DeclaringAssemblyName ?? source; - if (!navigationSessions.TryGetValue(testSource, out testNavigationSession)) + if (!navigationSessions.TryGetValue(testSource, out var testNavigationSession)) { testNavigationSession = PlatformServiceProvider.Instance.FileOperations.CreateNavigationSession(testSource); navigationSessions.Add(testSource, testNavigationSession); @@ -144,15 +140,12 @@ internal void SendTestCases(string source, IEnumerable testElem methodName = "MoveNext"; } - int minLineNumber; - string fileName; - PlatformServiceProvider.Instance.FileOperations.GetNavigationData( testNavigationSession, className, methodName, - out minLineNumber, - out fileName); + out var minLineNumber, + out var fileName); if (!string.IsNullOrEmpty(fileName)) { diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/StackTraceHelper.cs b/src/Adapter/MSTest.CoreAdapter/Execution/StackTraceHelper.cs index 6b7fded5e..d9cd04721 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/StackTraceHelper.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/StackTraceHelper.cs @@ -97,13 +97,12 @@ internal static StackTraceInformation GetStackTraceInformation(Exception ex) bool first = true; while (stackTraces.Count != 0) { - result.Append( - string.Format( + result.AppendFormat( CultureInfo.CurrentCulture, "{0} {1}{2}", first ? string.Empty : (Resource.UTA_EndOfInnerExceptionTrace + Environment.NewLine), stackTraces.Pop(), - Environment.NewLine)); + Environment.NewLine); first = false; } @@ -121,7 +120,7 @@ internal static StackTraceInformation GetStackTraceInformation(Exception ex) /// internal static string TrimStackTrace(string stackTrace) { - Debug.Assert(stackTrace != null && stackTrace.Length > 0, "stack trace should be non-empty."); + Debug.Assert(!string.IsNullOrEmpty(stackTrace), "stack trace should be non-empty."); StringBuilder result = new StringBuilder(stackTrace.Length); string[] stackFrames = Regex.Split(stackTrace, Environment.NewLine); @@ -179,13 +178,12 @@ internal static string GetExceptionMessage(Exception ex) msg = string.Format(CultureInfo.CurrentCulture, Resource.UTF_FailedToGetExceptionMessage, curException.GetType()); } - result.Append( - string.Format( + result.AppendFormat( CultureInfo.CurrentCulture, "{0}{1}: {2}", first ? string.Empty : " ---> ", curException.GetType(), - msg)); + msg); first = false; } diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblyInfo.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblyInfo.cs index b197afcda..ca3ff03b9 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblyInfo.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblyInfo.cs @@ -173,9 +173,7 @@ public void RunAssemblyInitialize(TestContext testContext) ?? this.AssemblyInitializationException; var outcome = UnitTestOutcome.Failed; - string errorMessage = null; - StackTraceInformation stackTraceInfo = null; - if (!realException.TryGetUnitTestAssertException(out outcome, out errorMessage, out stackTraceInfo)) + if (!realException.TryGetUnitTestAssertException(out outcome, out var errorMessage, out var stackTraceInfo)) { var exception = realException.GetType().ToString(); var message = StackTraceHelper.GetExceptionMessage(realException); diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblySettingsProvider.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblySettingsProvider.cs index a5d904d53..b21eca5b2 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblySettingsProvider.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TestAssemblySettingsProvider.cs @@ -5,6 +5,7 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Execution { using System; using System.Security; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; @@ -13,7 +14,7 @@ internal class TestAssemblySettingsProvider : MarshalByRefObject private ReflectHelper reflectHelper; public TestAssemblySettingsProvider() - : this(new ReflectHelper()) + : this(ReflectHelper.Instance) { } diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TestExecutionManager.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TestExecutionManager.cs index ba61d7b71..dc95db608 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TestExecutionManager.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TestExecutionManager.cs @@ -13,6 +13,7 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Execution using System.Linq; using System.Threading; using System.Threading.Tasks; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Extensions; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; @@ -375,18 +376,14 @@ private void ExecuteTestsInSource(IEnumerable tests, IRunContext runCo var startTime = DateTimeOffset.Now; - PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo( - "Executing test {0}", - unitTestElement.TestMethod.Name); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo("Executing test {0}", unitTestElement.TestMethod.Name); // Run single test passing test context properties to it. var tcmProperties = TcmTestPropertiesProvider.GetTcmProperties(currentTest); var testContextProperties = this.GetTestContextProperties(tcmProperties, sourceLevelParameters); var unitTestResult = testRunner.RunSingleTest(unitTestElement.TestMethod, testContextProperties); - PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo( - "Executed test {0}", - unitTestElement.TestMethod.Name); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo("Executed test {0}", unitTestElement.TestMethod.Name); var endTime = DateTimeOffset.Now; @@ -472,17 +469,17 @@ private void LogCleanupResult(ITestExecutionRecorder testExecutionRecorder, RunC { Debug.Assert(testExecutionRecorder != null, "Logger should not be null"); - if (!string.IsNullOrEmpty(result.StandardOut)) + if (!string.IsNullOrWhiteSpace(result.StandardOut)) { testExecutionRecorder.SendMessage(TestMessageLevel.Informational, result.StandardOut); } - if (!string.IsNullOrEmpty(result.DebugTrace)) + if (!string.IsNullOrWhiteSpace(result.DebugTrace)) { testExecutionRecorder.SendMessage(TestMessageLevel.Informational, result.DebugTrace); } - if (!string.IsNullOrEmpty(result.StandardError)) + if (!string.IsNullOrWhiteSpace(result.StandardError)) { testExecutionRecorder.SendMessage( MSTestSettings.CurrentSettings.TreatClassAndAssemblyCleanupWarningsAsErrors ? TestMessageLevel.Error : TestMessageLevel.Warning, @@ -493,9 +490,12 @@ private void LogCleanupResult(ITestExecutionRecorder testExecutionRecorder, RunC { foreach (string warning in result.Warnings) { - testExecutionRecorder.SendMessage( - MSTestSettings.CurrentSettings.TreatClassAndAssemblyCleanupWarningsAsErrors ? TestMessageLevel.Error : TestMessageLevel.Warning, - warning); + if (!string.IsNullOrWhiteSpace(warning)) + { + testExecutionRecorder.SendMessage( + MSTestSettings.CurrentSettings.TreatClassAndAssemblyCleanupWarningsAsErrors ? TestMessageLevel.Error : TestMessageLevel.Warning, + warning); + } } } } diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodInfo.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodInfo.cs index fd918bd17..1d4d0d13b 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodInfo.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodInfo.cs @@ -11,10 +11,12 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Execution using System.Reflection; using System.Text; using System.Threading; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Extensions; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; using Microsoft.VisualStudio.TestTools.UnitTesting; + using UnitTestOutcome = Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel.UnitTestOutcome; using UTF = Microsoft.VisualStudio.TestTools.UnitTesting; @@ -92,30 +94,8 @@ public Attribute[] GetAllAttributes(bool inherit) public TAttributeType[] GetAttributes(bool inherit) where TAttributeType : Attribute - { - Attribute[] attributeArray = ReflectHelper.GetCustomAttributes(this.TestMethod, typeof(TAttributeType), inherit); - - TAttributeType[] tAttributeArray = attributeArray as TAttributeType[]; - if (tAttributeArray != null) - { - return tAttributeArray; - } - - List tAttributeList = new List(); - if (attributeArray != null) - { - foreach (Attribute attribute in attributeArray) - { - TAttributeType tAttribute = attribute as TAttributeType; - if (tAttribute != null) - { - tAttributeList.Add(tAttribute); - } - } - } - - return tAttributeList.ToArray(); - } + => ReflectHelper.GetAttributes(this.TestMethod, inherit) + ?? EmptyHolder.Array; /// /// Execute test method. Capture failures, handle async and return result. @@ -453,11 +433,9 @@ private Exception HandleMethodException(Exception ex, string className, string m // Get the real exception thrown by the test method Exception realException = this.GetRealException(ex); - string exceptionMessage = null; - StackTraceInformation exceptionStackTraceInfo = null; var outcome = TestTools.UnitTesting.UnitTestOutcome.Failed; - if (realException.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out exceptionStackTraceInfo)) + if (realException.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var exceptionStackTraceInfo)) { return new TestFailedException(outcome.ToUnitTestOutcome(), exceptionMessage, exceptionStackTraceInfo, realException); } @@ -546,11 +524,9 @@ private void RunTestCleanupMethod(object classInstance, TestResult result) } Exception realException = ex.GetInnerExceptionOrDefault(); - string exceptionMessage = null; - StackTraceInformation realExceptionStackTraceInfo = null; // special case UnitTestAssertException to trim off part of the stack trace - if (!realException.TryGetUnitTestAssertException(out cleanupOutcome, out exceptionMessage, out realExceptionStackTraceInfo)) + if (!realException.TryGetUnitTestAssertException(out cleanupOutcome, out var exceptionMessage, out var realExceptionStackTraceInfo)) { cleanupOutcome = UTF.UnitTestOutcome.Failed; exceptionMessage = this.GetTestCleanUpExceptionMessage(testCleanupMethod, realException); @@ -632,11 +608,9 @@ private bool RunTestInitializeMethod(object classInstance, TestResult result) catch (Exception ex) { var innerException = ex.GetInnerExceptionOrDefault(); - string exceptionMessage = null; - StackTraceInformation exceptionStackTraceInfo = null; var outcome = TestTools.UnitTesting.UnitTestOutcome.Failed; - if (innerException.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out exceptionStackTraceInfo)) + if (innerException.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var exceptionStackTraceInfo)) { result.Outcome = outcome; result.TestFailureException = new TestFailedException( @@ -725,11 +699,27 @@ private object CreateTestClassInstance(TestResult result) } catch (Exception ex) { + if (ex == null) + { + // It seems that ex can be null in some rare cases when initialization fails in native code. + // Get our own exception with a stack trace to satisfy GetStackTraceInformation. + try + { + throw new InvalidOperationException(Resource.UTA_UserCodeThrewNullValueException); + } + catch (Exception exception) + { + ex = exception; + } + } + // In most cases, exception will be TargetInvocationException with real exception wrapped - // in the InnerException; or user code throws an exception + // in the InnerException; or user code throws an exception. + // It also seems that in rare cases the ex can be null. var actualException = ex.InnerException ?? ex; var exceptionMessage = StackTraceHelper.GetExceptionMessage(actualException); var stackTraceInfo = StackTraceHelper.GetStackTraceInformation(actualException); + var errorMessage = string.Format( CultureInfo.CurrentCulture, Resource.UTA_InstanceCreationError, @@ -796,5 +786,10 @@ void executeAsyncAction() return timeoutResult; } } + + private static class EmptyHolder + { + internal static readonly T[] Array = new T[0]; + } } } diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodRunner.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodRunner.cs index 63bc78323..8dfd82a85 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodRunner.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TestMethodRunner.cs @@ -64,21 +64,9 @@ internal class TestMethodRunner /// /// The capture debug traces. /// - public TestMethodRunner( - TestMethodInfo testMethodInfo, - TestMethod testMethod, - ITestContext testContext, - bool captureDebugTraces) - : this(testMethodInfo, testMethod, testContext, captureDebugTraces, new ReflectHelper()) + public TestMethodRunner(TestMethodInfo testMethodInfo, TestMethod testMethod, ITestContext testContext, bool captureDebugTraces) + : this(testMethodInfo, testMethod, testContext, captureDebugTraces, ReflectHelper.Instance) { - Debug.Assert(testMethodInfo != null, "testMethodInfo should not be null"); - Debug.Assert(testMethod != null, "testMethod should not be null"); - Debug.Assert(testContext != null, "testContext should not be null"); - - this.testMethodInfo = testMethodInfo; - this.test = testMethod; - this.testContext = testContext; - this.captureDebugTraces = captureDebugTraces; } /// @@ -99,12 +87,7 @@ internal class TestMethodRunner /// /// The reflect Helper object. /// - public TestMethodRunner( - TestMethodInfo testMethodInfo, - TestMethod testMethod, - ITestContext testContext, - bool captureDebugTraces, - ReflectHelper reflectHelper) + public TestMethodRunner(TestMethodInfo testMethodInfo, TestMethod testMethod, ITestContext testContext, bool captureDebugTraces, ReflectHelper reflectHelper) { Debug.Assert(testMethodInfo != null, "testMethodInfo should not be null"); Debug.Assert(testMethod != null, "testMethod should not be null"); @@ -219,136 +202,31 @@ internal UnitTestResult[] RunTestMethod() List results = new List(); var isDataDriven = false; - // Parent result. Added in properties bag only when results are greater than 1. - var parentResultWatch = new Stopwatch(); - parentResultWatch.Start(); - var parentResult = new UTF.TestResult - { - Outcome = UTF.UnitTestOutcome.InProgress, - ExecutionId = Guid.NewGuid() - }; - if (this.testMethodInfo.TestMethodOptions.Executor != null) { - UTF.DataSourceAttribute[] dataSourceAttribute = this.testMethodInfo.GetAttributes(false); - if (dataSourceAttribute != null && dataSourceAttribute.Length == 1) + if (this.test.DataType == DynamicDataType.ITestDataSource) + { + var data = DataSerializationHelper.Deserialize(this.test.SerializedData); + var testResults = this.ExecuteTestWithDataSource(null, data); + results.AddRange(testResults); + } + else if (this.ExecuteDataSourceBasedTests(results)) { isDataDriven = true; - Stopwatch watch = new Stopwatch(); - watch.Start(); - - try - { - IEnumerable dataRows = PlatformServiceProvider.Instance.TestDataSource.GetData(this.testMethodInfo, this.testContext); - - if (dataRows == null) - { - watch.Stop(); - var inconclusiveResult = new UTF.TestResult(); - inconclusiveResult.Outcome = UTF.UnitTestOutcome.Inconclusive; - inconclusiveResult.Duration = watch.Elapsed; - results.Add(inconclusiveResult); - } - else - { - try - { - int rowIndex = 0; - foreach (object dataRow in dataRows) - { - watch.Reset(); - watch.Start(); - - this.testContext.SetDataRow(dataRow); - UTF.TestResult[] testResults; - - try - { - testResults = this.testMethodInfo.TestMethodOptions.Executor.Execute(this.testMethodInfo); - } - catch (Exception ex) - { - testResults = new[] - { - new UTF.TestResult() { TestFailureException = new Exception(string.Format(CultureInfo.CurrentCulture, Resource.UTA_ExecuteThrewException, ex.Message), ex) } - }; - } - - watch.Stop(); - foreach (var testResult in testResults) - { - testResult.DatarowIndex = rowIndex; - testResult.Duration = watch.Elapsed; - } - - rowIndex++; - - results.AddRange(testResults); - } - } - finally - { - this.testContext.SetDataConnection(null); - this.testContext.SetDataRow(null); - } - } - } - catch (Exception ex) - { - watch.Stop(); - var failedResult = new UTF.TestResult(); - failedResult.Outcome = UTF.UnitTestOutcome.Error; - failedResult.TestFailureException = ex; - failedResult.Duration = watch.Elapsed; - results.Add(failedResult); - } } else { - UTF.ITestDataSource[] testDataSources = this.testMethodInfo.GetAttributes(false)?.Where(a => a is UTF.ITestDataSource).OfType().ToArray(); + var testResults = this.ExecuteTest(this.testMethodInfo); - if (testDataSources != null && testDataSources.Length > 0) + foreach (var testResult in testResults) { - isDataDriven = true; - foreach (var testDataSource in testDataSources) + if (string.IsNullOrWhiteSpace(testResult.DisplayName)) { - foreach (var data in testDataSource.GetData(this.testMethodInfo.MethodInfo)) - { - this.testMethodInfo.SetArguments(data); - UTF.TestResult[] testResults; - try - { - testResults = this.testMethodInfo.TestMethodOptions.Executor.Execute(this.testMethodInfo); - } - catch (Exception ex) - { - testResults = new[] - { - new UTF.TestResult() { TestFailureException = new Exception(string.Format(CultureInfo.CurrentCulture, Resource.UTA_ExecuteThrewException, ex.Message), ex) } - }; - } - - foreach (var testResult in testResults) - { - testResult.DisplayName = testDataSource.GetDisplayName(this.testMethodInfo.MethodInfo, data); - } - - results.AddRange(testResults); - this.testMethodInfo.SetArguments(null); - } - } - } - else - { - try - { - results.AddRange(this.testMethodInfo.TestMethodOptions.Executor.Execute(this.testMethodInfo)); - } - catch (Exception ex) - { - results.Add(new UTF.TestResult() { TestFailureException = new Exception(string.Format(CultureInfo.CurrentCulture, Resource.UTA_ExecuteThrewException, ex.Message), ex) }); + testResult.DisplayName = this.test.DisplayName; } } + + results.AddRange(testResults); } } else @@ -359,9 +237,6 @@ internal UnitTestResult[] RunTestMethod() this.testMethodInfo.TestMethodName); } - parentResultWatch.Stop(); - parentResult.Duration = parentResultWatch.Elapsed; - // Get aggregate outcome. var aggregateOutcome = this.GetAggregateOutcome(results); this.testContext.SetOutcome(aggregateOutcome); @@ -375,13 +250,171 @@ internal UnitTestResult[] RunTestMethod() // In case of data driven, set parent info in results. if (isDataDriven) { - parentResult.Outcome = aggregateOutcome; - results = this.UpdateResultsWithParentInfo(results, parentResult); + results = this.UpdateResultsWithParentInfo(results, Guid.NewGuid()); } return results.ToArray().ToUnitTestResults(); } + private bool ExecuteDataSourceBasedTests(List results) + { + var isDataDriven = false; + + UTF.DataSourceAttribute[] dataSourceAttribute = this.testMethodInfo.GetAttributes(false); + if (dataSourceAttribute != null && dataSourceAttribute.Length == 1) + { + isDataDriven = true; + Stopwatch watch = new Stopwatch(); + watch.Start(); + + try + { + IEnumerable dataRows = PlatformServiceProvider.Instance.TestDataSource.GetData(this.testMethodInfo, this.testContext); + + if (dataRows == null) + { + watch.Stop(); + var inconclusiveResult = new UTF.TestResult(); + inconclusiveResult.Outcome = UTF.UnitTestOutcome.Inconclusive; + inconclusiveResult.Duration = watch.Elapsed; + results.Add(inconclusiveResult); + } + else + { + try + { + int rowIndex = 0; + + foreach (object dataRow in dataRows) + { + UTF.TestResult[] testResults = this.ExecuteTestWithDataRow(dataRow, rowIndex++); + results.AddRange(testResults); + } + } + finally + { + this.testContext.SetDataConnection(null); + this.testContext.SetDataRow(null); + } + } + } + catch (Exception ex) + { + watch.Stop(); + var failedResult = new UTF.TestResult(); + failedResult.Outcome = UTF.UnitTestOutcome.Error; + failedResult.TestFailureException = ex; + failedResult.Duration = watch.Elapsed; + results.Add(failedResult); + } + } + else + { + UTF.ITestDataSource[] testDataSources = this.testMethodInfo.GetAttributes(false)?.Where(a => a is UTF.ITestDataSource).OfType().ToArray(); + + if (testDataSources != null && testDataSources.Length > 0) + { + isDataDriven = true; + foreach (var testDataSource in testDataSources) + { + foreach (var data in testDataSource.GetData(this.testMethodInfo.MethodInfo)) + { + try + { + var testResults = this.ExecuteTestWithDataSource(testDataSource, data); + + results.AddRange(testResults); + } + finally + { + this.testMethodInfo.SetArguments(null); + } + } + } + } + } + + return isDataDriven; + } + + private UTF.TestResult[] ExecuteTestWithDataSource(UTF.ITestDataSource testDataSource, object[] data) + { + var stopwatch = Stopwatch.StartNew(); + + this.testMethodInfo.SetArguments(data); + var testResults = this.ExecuteTest(this.testMethodInfo); + stopwatch.Stop(); + + var hasDisplayName = !string.IsNullOrWhiteSpace(this.test.DisplayName); + foreach (var testResult in testResults) + { + if (testResult.Duration == TimeSpan.Zero) + { + testResult.Duration = stopwatch.Elapsed; + } + + var displayName = this.test.Name; + if (testDataSource != null) + { + displayName = testDataSource.GetDisplayName(this.testMethodInfo.MethodInfo, data); + } + else if (hasDisplayName) + { + displayName = this.test.DisplayName; + } + + testResult.DisplayName = displayName; + } + + return testResults; + } + + private UTF.TestResult[] ExecuteTestWithDataRow(object dataRow, int rowIndex) + { + var displayName = string.Format(CultureInfo.CurrentCulture, Resource.DataDrivenResultDisplayName, this.test.DisplayName, rowIndex); + Stopwatch stopwatch = null; + + UTF.TestResult[] testResults = null; + try + { + stopwatch = Stopwatch.StartNew(); + this.testContext.SetDataRow(dataRow); + testResults = this.ExecuteTest(this.testMethodInfo); + } + finally + { + stopwatch?.Stop(); + this.testContext.SetDataRow(null); + } + + foreach (var testResult in testResults) + { + testResult.DisplayName = displayName; + testResult.DatarowIndex = rowIndex; + testResult.Duration = stopwatch.Elapsed; + } + + return testResults; + } + + private UTF.TestResult[] ExecuteTest(TestMethodInfo testMethodInfo) + { + try + { + return this.testMethodInfo.TestMethodOptions.Executor.Execute(testMethodInfo); + } + catch (Exception ex) + { + return new[] + { + new UTF.TestResult() + { + TestFailureException = new Exception(string.Format(CultureInfo.CurrentCulture, Resource.UTA_ExecuteThrewException, ex?.Message, ex?.StackTrace), ex) + } + }; + } + } + /// /// Gets aggregate outcome. /// @@ -410,9 +443,9 @@ private UTF.UnitTestOutcome GetAggregateOutcome(List results) /// Add parent results as first result in updated result. /// /// Results. - /// Parent results. + /// Current execution id. /// Updated results which contains parent result as first result. All other results contains parent result info. - private List UpdateResultsWithParentInfo(List results, UTF.TestResult parentResult) + private List UpdateResultsWithParentInfo(List results, Guid executionId) { // Return results in case there are no results. if (!results.Any()) @@ -422,13 +455,11 @@ private List UpdateResultsWithParentInfo(List re // UpdatedResults contain parent result at first position and remaining results has parent info updated. var updatedResults = new List(); - updatedResults.Add(parentResult); foreach (var result in results) { result.ExecutionId = Guid.NewGuid(); - result.ParentExecId = parentResult.ExecutionId; - parentResult.InnerResultsCount++; + result.ParentExecId = executionId; updatedResults.Add(result); } diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/TypeCache.cs b/src/Adapter/MSTest.CoreAdapter/Execution/TypeCache.cs index 074845f5f..058f1a057 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/TypeCache.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/TypeCache.cs @@ -54,7 +54,7 @@ internal class TypeCache : MarshalByRefObject /// Initializes a new instance of the class. /// internal TypeCache() - : this(new ReflectHelper()) + : this(ReflectHelper.Instance) { } @@ -100,12 +100,12 @@ public TestMethodInfo GetTestMethodInfo(TestMethod testMethod, ITestContext test { if (testMethod == null) { - throw new ArgumentNullException("testMethod"); + throw new ArgumentNullException(nameof(testMethod)); } if (testContext == null) { - throw new ArgumentNullException("testContext"); + throw new ArgumentNullException(nameof(testContext)); } // Get the classInfo (This may throw as GetType calls assembly.GetType(..,true);) @@ -682,9 +682,9 @@ private MethodInfo GetMethodInfoUsingRuntimeMethods(TestMethod testMethod, TestC { // Only find methods that match the given declaring name. testMethodInfo = - methodsInClass.Where(method => method.Name.Equals(testMethod.Name) + Array.Find(methodsInClass, method => method.Name.Equals(testMethod.Name) && method.DeclaringType.FullName.Equals(testMethod.DeclaringClassFullName) - && method.HasCorrectTestMethodSignature(true)).FirstOrDefault(); + && method.HasCorrectTestMethodSignature(true)); } else { diff --git a/src/Adapter/MSTest.CoreAdapter/Execution/UnitTestRunner.cs b/src/Adapter/MSTest.CoreAdapter/Execution/UnitTestRunner.cs index 679d5a897..ea183f498 100644 --- a/src/Adapter/MSTest.CoreAdapter/Execution/UnitTestRunner.cs +++ b/src/Adapter/MSTest.CoreAdapter/Execution/UnitTestRunner.cs @@ -28,7 +28,7 @@ internal class UnitTestRunner : MarshalByRefObject /// /// Specifies adapter settings that need to be instantiated in the domain running these tests. public UnitTestRunner(MSTestSettings settings) - : this(settings, new ReflectHelper()) + : this(settings, ReflectHelper.Instance) { } @@ -68,7 +68,7 @@ internal UnitTestResult[] RunSingleTest(TestMethod testMethod, IDictionary /// The to unit test element. /// @@ -57,13 +69,24 @@ internal static UnitTestElement ToUnitTestElement(this TestCase testCase, string TestMethod testMethod; if (testCase.ContainsManagedMethodAndType()) { - testMethod = new TestMethod(testCase.GetManagedType(), testCase.GetManagedMethod(), name, testClassName, source, isAsync); + testMethod = new TestMethod(testCase.GetManagedType(), testCase.GetManagedMethod(), testCase.GetHierarchy(), name, testClassName, source, isAsync); } else { testMethod = new TestMethod(name, testClassName, source, isAsync); } + var dataType = (DynamicDataType)testCase.GetPropertyValue(Constants.TestDynamicDataTypeProperty, (int)DynamicDataType.None); + if (dataType != DynamicDataType.None) + { + var data = testCase.GetPropertyValue(Constants.TestDynamicDataProperty, null); + + testMethod.DataType = dataType; + testMethod.SerializedData = data; + } + + testMethod.DisplayName = testCase.DisplayName; + if (declaringClassName != null && declaringClassName != testClassName) { testMethod.DeclaringClassFullName = declaringClassName; @@ -77,6 +100,43 @@ internal static UnitTestElement ToUnitTestElement(this TestCase testCase, string DisplayName = testCase.DisplayName }; + if (testCase.Traits.Any()) + { + testElement.Traits = testCase.Traits.ToArray(); + } + + var cssIteration = testCase.GetPropertyValue(Constants.CssIterationProperty, null); + if (!string.IsNullOrWhiteSpace(cssIteration)) + { + testElement.CssIteration = cssIteration; + } + + var cssProjectStructure = testCase.GetPropertyValue(Constants.CssProjectStructureProperty, null); + if (!string.IsNullOrWhiteSpace(cssIteration)) + { + testElement.CssProjectStructure = cssProjectStructure; + } + + var description = testCase.GetPropertyValue(Constants.DescriptionProperty, null); + if (!string.IsNullOrWhiteSpace(description)) + { + testElement.Description = description; + } + + var workItemIds = testCase.GetPropertyValue(Constants.WorkItemIdsProperty, null); + if (workItemIds != null && workItemIds.Length > 0) + { + testElement.WorkItemIds = workItemIds; + } + + var deploymentItems = testCase.GetPropertyValue[]>(Constants.DeploymentItemsProperty, null); + if (deploymentItems != null && deploymentItems.Length > 0) + { + testElement.DeploymentItems = deploymentItems; + } + + testElement.DoNotParallelize = testCase.GetPropertyValue(Constants.DoNotParallelizeProperty, false); + return testElement; } @@ -89,5 +149,9 @@ internal static UnitTestElement ToUnitTestElement(this TestCase testCase, string internal static void SetManagedMethod(this TestCase testCase, string value) => testCase.SetPropertyValue(ManagedMethodProperty, value); internal static bool ContainsManagedMethodAndType(this TestCase testCase) => !string.IsNullOrWhiteSpace(testCase.GetManagedMethod()) && !string.IsNullOrWhiteSpace(testCase.GetManagedType()); + + internal static string[] GetHierarchy(this TestCase testCase) => testCase.GetPropertyValue(HierarchyProperty, null); + + internal static void SetHierarchy(this TestCase testCase, params string[] value) => testCase.SetPropertyValue(HierarchyProperty, value); } } diff --git a/src/Adapter/MSTest.CoreAdapter/Friends.cs b/src/Adapter/MSTest.CoreAdapter/Friends.cs index d4224b84e..0b478fdb3 100644 --- a/src/Adapter/MSTest.CoreAdapter/Friends.cs +++ b/src/Adapter/MSTest.CoreAdapter/Friends.cs @@ -6,4 +6,5 @@ [assembly: InternalsVisibleTo(assemblyName: "Microsoft.VisualStudio.TestPlatform.MSTestAdapter.UnitTests, PublicKey=002400000480000094000000060200000024000052534131000400000100010007d1fa57c4aed9f0a32e84aa0faefd0de9e8fd6aec8f87fb03766c834c99921eb23be79ad9d5dcc1dd9ad236132102900b723cf980957fc4e177108fc607774f29e8320e92ea05ece4e821c0a5efe8f1645c4c0c93c1ab99285d622caa652c1dfad63d745d6f2de5f17e5eaf0fc4963d261c8a12436518206dc093344d5ad293")] [assembly: InternalsVisibleTo(assemblyName: "DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")] -[assembly: InternalsVisibleTo(assemblyName: "MSTestAdapter.Smoke.E2ETests, PublicKey=002400000480000094000000060200000024000052534131000400000100010007d1fa57c4aed9f0a32e84aa0faefd0de9e8fd6aec8f87fb03766c834c99921eb23be79ad9d5dcc1dd9ad236132102900b723cf980957fc4e177108fc607774f29e8320e92ea05ece4e821c0a5efe8f1645c4c0c93c1ab99285d622caa652c1dfad63d745d6f2de5f17e5eaf0fc4963d261c8a12436518206dc093344d5ad293")] \ No newline at end of file +[assembly: InternalsVisibleTo(assemblyName: "MSTestAdapter.Smoke.E2ETests, PublicKey=002400000480000094000000060200000024000052534131000400000100010007d1fa57c4aed9f0a32e84aa0faefd0de9e8fd6aec8f87fb03766c834c99921eb23be79ad9d5dcc1dd9ad236132102900b723cf980957fc4e177108fc607774f29e8320e92ea05ece4e821c0a5efe8f1645c4c0c93c1ab99285d622caa652c1dfad63d745d6f2de5f17e5eaf0fc4963d261c8a12436518206dc093344d5ad293")] +[assembly: InternalsVisibleTo(assemblyName: "DiscoveryAndExecutionTests, PublicKey=002400000480000094000000060200000024000052534131000400000100010007d1fa57c4aed9f0a32e84aa0faefd0de9e8fd6aec8f87fb03766c834c99921eb23be79ad9d5dcc1dd9ad236132102900b723cf980957fc4e177108fc607774f29e8320e92ea05ece4e821c0a5efe8f1645c4c0c93c1ab99285d622caa652c1dfad63d745d6f2de5f17e5eaf0fc4963d261c8a12436518206dc093344d5ad293")] diff --git a/src/Adapter/MSTest.CoreAdapter/Helpers/DataSerializationHelper.cs b/src/Adapter/MSTest.CoreAdapter/Helpers/DataSerializationHelper.cs new file mode 100644 index 000000000..3c99e68b2 --- /dev/null +++ b/src/Adapter/MSTest.CoreAdapter/Helpers/DataSerializationHelper.cs @@ -0,0 +1,137 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers +{ + using System; + using System.Collections.Generic; + using System.IO; + using System.Linq; + using System.Reflection; + using System.Runtime.Serialization.Json; + using System.Text; + + internal static class DataSerializationHelper + { + private static readonly Dictionary SerializerCache = new Dictionary(); + private static readonly DataContractJsonSerializerSettings SerializerSettings = new DataContractJsonSerializerSettings() + { + UseSimpleDictionaryFormat = true, + EmitTypeInformation = System.Runtime.Serialization.EmitTypeInformation.Always, + DateTimeFormat = new System.Runtime.Serialization.DateTimeFormat("O", System.Globalization.CultureInfo.InvariantCulture) + }; + + /// + /// Serializes the date in such a way that won't throw exceptions during deserialization in Test Platform. + /// The result can be deserialized using method. + /// + /// Data array to serialize. + /// Serialzed array. + public static string[] Serialize(object[] data) + { + if (data == null) + { + return null; + } + + var serializedData = new string[data.Length * 2]; + + for (int i = 0; i < data.Length; i++) + { + var typeIndex = i * 2; + var dataIndex = typeIndex + 1; + + if (data[i] == null) + { + serializedData[typeIndex] = null; + serializedData[dataIndex] = null; + + continue; + } + + var type = data[i].GetType(); + var typeName = type.AssemblyQualifiedName; + + serializedData[typeIndex] = typeName; + + var serializer = GetSerializer(type); + + using (var memoryStream = new MemoryStream()) + { + serializer.WriteObject(memoryStream, data[i]); + var serializerData = memoryStream.ToArray(); + + serializedData[dataIndex] = Encoding.UTF8.GetString(serializerData, 0, serializerData.Length); + } + } + + return serializedData; + } + + /// + /// Deserialzes the data serialzed by method. + /// + /// Serialized data array to deserialize. + /// Deserialized array. + public static object[] Deserialize(string[] serializedData) + { + if (serializedData == null || serializedData.Length % 2 != 0) + { + return null; + } + + var length = serializedData.Length / 2; + var data = new object[length]; + + for (int i = 0; i < length; i++) + { + var typeIndex = i * 2; + var typeName = serializedData[typeIndex]; + var serializedValue = serializedData[typeIndex + 1]; + + if (serializedValue == null || typeName == null) + { + data[i] = null; + continue; + } + + var serializer = GetSerializer(typeName); + + var serialzedDataBytes = Encoding.UTF8.GetBytes(serializedValue); + using (var memoryStream = new MemoryStream(serialzedDataBytes)) + { + data[i] = serializer.ReadObject(memoryStream); + } + } + + return data; + } + + private static DataContractJsonSerializer GetSerializer(string typeName) + { + var serializer = SerializerCache.SingleOrDefault(i => i.Key.FullName == typeName); + if (serializer.Value != null) + { + return serializer.Value; + } + + var type = Type.GetType(typeName); + if (type != null) + { + return GetSerializer(type); + } + + return GetSerializer(typeof(object)); + } + + private static DataContractJsonSerializer GetSerializer(Type type) + { + if (SerializerCache.ContainsKey(type)) + { + return SerializerCache[type]; + } + + return SerializerCache[type] = new DataContractJsonSerializer(type, SerializerSettings); + } + } +} diff --git a/src/Adapter/MSTest.CoreAdapter/Helpers/ReflectHelper.cs b/src/Adapter/MSTest.CoreAdapter/Helpers/ReflectHelper.cs index 22224a405..7c7a681ca 100644 --- a/src/Adapter/MSTest.CoreAdapter/Helpers/ReflectHelper.cs +++ b/src/Adapter/MSTest.CoreAdapter/Helpers/ReflectHelper.cs @@ -18,10 +18,18 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers internal class ReflectHelper : MarshalByRefObject { + private static readonly Lazy InstanceValue = new Lazy(() => new ReflectHelper()); + /// /// Contains the memberInfo Vs the name/type of the attributes defined on that member. (FYI: - MemberInfo denotes properties, fields, methods, events) /// - private Dictionary> attributeCache = new Dictionary>(); + private readonly Dictionary> attributeCache = new Dictionary>(); + + internal ReflectHelper() + { + } + + public static ReflectHelper Instance => InstanceValue.Value; /// /// Checks to see if the parameter memberInfo contains the parameter attribute or not. @@ -113,7 +121,7 @@ public bool HasAttributeDerivedFrom(MemberInfo memberInfo, Type baseAttributeTyp Dictionary attributes = this.GetAttributes(memberInfo, inherit); if (attributes == null) { - PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning("ReflectHelper.HasAttributeDerivedFrom: Failed to get attribute cache. Ignoring attribute inheritance and falling into 'type defines Attribute model', so that we have some data."); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning($"{nameof(ReflectHelper)}.{nameof(GetAttributes)}: {Resource.FailedFetchAttributeCache}"); return this.IsAttributeDefined(memberInfo, baseAttributeType, inherit); } @@ -121,7 +129,7 @@ public bool HasAttributeDerivedFrom(MemberInfo memberInfo, Type baseAttributeTyp // Try to find the attribute that is derived from baseAttrType. foreach (object attribute in attributes.Values) { - Debug.Assert(attribute != null, "ReflectHeler.DefinesAttributeDerivedFrom: internal error: wrong value in the attrs dictionary."); + Debug.Assert(attribute != null, $"{nameof(ReflectHelper)}.{nameof(GetAttributes)}: internal error: wrong value in the attrs dictionary."); Type attributeType = attribute.GetType(); if (attributeType.GetTypeInfo().IsSubclassOf(baseAttributeType)) @@ -200,6 +208,23 @@ public override object InitializeLifetimeService() return null; } + internal static T[] GetAttributes(MethodBase methodBase, bool inherit) + where T : Attribute + { + Attribute[] attributeArray = GetCustomAttributes(methodBase, typeof(T), inherit); + if (attributeArray == null || attributeArray.Length == 0) + { + return null; + } + + if (attributeArray is T[] attributes) + { + return attributes; + } + + return attributeArray.Where(a => a is T).Cast().ToArray(); + } + /// /// Match return type of method. /// @@ -629,7 +654,6 @@ private IEnumerable GetTestPropertyAttributes(MemberInfo propertyAttr /// The member to inspect. /// Look at inheritance chain. /// attributes defined. - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification = "Requirement is to handle all kinds of user exceptions and message appropriately.")] private Dictionary GetAttributes(MemberInfo memberInfo, bool inherit) { // If the information is cached, then use it otherwise populate the cache using @@ -658,16 +682,10 @@ private IEnumerable GetTestPropertyAttributes(MemberInfo propertyAttr } catch (Exception ex2) { - description = - ex.GetType().FullName + - ": (Failed to get exception description due to an exception of type " + - ex2.GetType().FullName + ')'; + description = string.Format(CultureInfo.CurrentCulture, Resource.ExceptionOccuredWhileGettingTheExceptionDescription, ex.GetType().FullName, ex2.GetType().FullName); // ex.GetType().FullName + } - PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning( - "Getting custom attributes for type {0} threw exception (will ignore and use the reflection way): {1}", - memberInfo.GetType().FullName, - description); + PlatformServiceProvider.Instance.AdapterTraceLogger.LogWarning(Resource.FailedToGetCustomAttribute, memberInfo.GetType().FullName, description); // Since we cannot check by attribute names, do it in reflection way. // Note 1: this will not work for different version of assembly but it is better than nothing. diff --git a/src/Adapter/MSTest.CoreAdapter/MSTest.CoreAdapter.csproj b/src/Adapter/MSTest.CoreAdapter/MSTest.CoreAdapter.csproj index f02086162..23dcee5f1 100644 --- a/src/Adapter/MSTest.CoreAdapter/MSTest.CoreAdapter.csproj +++ b/src/Adapter/MSTest.CoreAdapter/MSTest.CoreAdapter.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {98BA6D2C-1F3D-4636-8E1D-D4932B7A253D} Library @@ -29,6 +27,46 @@ prompt 4 + + + + C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETPortable\v4.5\System.Collections.Concurrent.dll + + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + False + + + {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} + PlatformServices.Portable + False + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + False + + + {6c9fe494-8315-4667-b3f6-75dc62a62319} + Extension.Core + False + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + @@ -38,6 +76,7 @@ + @@ -54,6 +93,7 @@ + @@ -88,37 +128,9 @@ Resource.resx - - - - {6c9fe494-8315-4667-b3f6-75dc62a62319} - Extension.Core - False - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - False - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - False - - - {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} - PlatformServices.Portable - False - - - + - - - C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETPortable\v4.5\System.Collections.Concurrent.dll - - ResXFileCodeGenerator @@ -126,21 +138,22 @@ Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter - - - - - runtime; build; native; contentfiles; analyzers; buildtransitive - - - runtime; build; native; contentfiles; analyzers; buildtransitive - - - - - $(ProjectDir)..\Build - - xcopy /Y /I /S /E "$(SourcePath)" "$(OutDir)..\Build" - - + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/MSTestDiscoverer.cs b/src/Adapter/MSTest.CoreAdapter/MSTestDiscoverer.cs index 8179dd273..5ccfab718 100644 --- a/src/Adapter/MSTest.CoreAdapter/MSTestDiscoverer.cs +++ b/src/Adapter/MSTest.CoreAdapter/MSTestDiscoverer.cs @@ -80,7 +80,7 @@ internal bool AreValidSources(IEnumerable sources) source => PlatformServiceProvider.Instance.TestSource.ValidSourceExtensions.Any( extension => - string.Compare(Path.GetExtension(source), extension, StringComparison.OrdinalIgnoreCase) == 0)); + string.Equals(Path.GetExtension(source), extension, StringComparison.OrdinalIgnoreCase))); } } } diff --git a/src/Adapter/MSTest.CoreAdapter/MSTestSettings.cs b/src/Adapter/MSTest.CoreAdapter/MSTestSettings.cs index a6fd56243..351491782 100644 --- a/src/Adapter/MSTest.CoreAdapter/MSTestSettings.cs +++ b/src/Adapter/MSTest.CoreAdapter/MSTestSettings.cs @@ -245,7 +245,7 @@ public static bool IsLegacyScenario(IMessageLogger logger) /// /// Gets the adapter specific settings from the xml. /// - /// The xml with the settings passed from the test platform. + /// The xml with the settings passed from the test platform. /// The name of the adapter settings to fetch - Its either MSTest or MSTestV2 /// The settings if found. Null otherwise. internal static MSTestSettings GetSettings(string runSettingsXml, string settingName) diff --git a/src/Adapter/MSTest.CoreAdapter/ObjectModel/DynamicDataType.cs b/src/Adapter/MSTest.CoreAdapter/ObjectModel/DynamicDataType.cs new file mode 100644 index 000000000..b1b82712c --- /dev/null +++ b/src/Adapter/MSTest.CoreAdapter/ObjectModel/DynamicDataType.cs @@ -0,0 +1,12 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel +{ + internal enum DynamicDataType : int + { + None = 0, + DataSourceAttribute = 1, + ITestDataSource = 2 + } +} diff --git a/src/Adapter/MSTest.CoreAdapter/ObjectModel/TestMethod.cs b/src/Adapter/MSTest.CoreAdapter/ObjectModel/TestMethod.cs index 1d0a4f80f..210fd9d55 100644 --- a/src/Adapter/MSTest.CoreAdapter/ObjectModel/TestMethod.cs +++ b/src/Adapter/MSTest.CoreAdapter/ObjectModel/TestMethod.cs @@ -4,9 +4,12 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel { using System; + using System.Collections.Generic; + using System.Collections.ObjectModel; using System.Diagnostics; using System.Reflection; + using Microsoft.TestPlatform.AdapterUtilities; using Microsoft.TestPlatform.AdapterUtilities.ManagedNameUtilities; using MSTestAdapter.PlatformServices.Interface.ObjectModel; @@ -17,18 +20,15 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel [Serializable] public sealed class TestMethod : ITestMethod { - #region Fields - /// - /// Member field for the property 'DeclaringClassFullName' + /// Number of elements in . /// - private string declaringClassFullName = null; + public const int TotalHierarchyLevels = HierarchyConstants.Levels.TotalLevelCount; - /// - /// Member field for the property 'DeclaringAssemblyName' - /// + #region Fields + private IReadOnlyCollection hierarchy; + private string declaringClassFullName = null; private string declaringAssemblyName = null; - #endregion public TestMethod(string name, string fullClassName, string assemblyName, bool isAsync) @@ -45,6 +45,12 @@ public TestMethod(string name, string fullClassName, string assemblyName, bool i this.FullClassName = fullClassName; this.AssemblyName = assemblyName; this.IsAsync = isAsync; + + var hierarchy = new string[HierarchyConstants.Levels.TotalLevelCount]; + hierarchy[HierarchyConstants.Levels.NamespaceIndex] = fullClassName; + hierarchy[HierarchyConstants.Levels.ClassIndex] = name; + + this.hierarchy = new ReadOnlyCollection(hierarchy); } internal TestMethod(MethodBase method, string name, string fullClassName, string assemblyName, bool isAsync) @@ -55,33 +61,25 @@ internal TestMethod(MethodBase method, string name, string fullClassName, string throw new ArgumentNullException(nameof(method)); } - ManagedNameHelper.GetManagedName(method, out var managedType, out var managedMethod); - - // ManagedNameHelpers currently does not support spaces in method names. - // If there are spaces in the method name, we'll use the legacy way to find the method. - if (!managedMethod.Contains(" ")) - { - this.ManagedTypeName = managedType; - this.ManagedMethodName = managedMethod; - } + ManagedNameHelper.GetManagedName(method, out var managedType, out var managedMethod, out var hierarchyValues); + this.ManagedTypeName = managedType; + this.ManagedMethodName = managedMethod; + this.hierarchy = new ReadOnlyCollection(hierarchyValues); } - internal TestMethod(string managedTypeName, string managedMethodName, string name, string fullClassName, string assemblyName, bool isAsync) + internal TestMethod(string managedTypeName, string managedMethodName, string[] hierarchyValues, string name, string fullClassName, string assemblyName, bool isAsync) : this(name, fullClassName, assemblyName, isAsync) { this.ManagedTypeName = managedTypeName; this.ManagedMethodName = managedMethodName; + this.hierarchy = new ReadOnlyCollection(hierarchyValues); } - /// - /// Gets the name of the test method - /// - public string Name { get; private set; } + /// + public string Name { get; } - /// - /// Gets the full classname of the test method - /// - public string FullClassName { get; private set; } + /// + public string FullClassName { get; } /// /// Gets or sets the declaring assembly full name. This will be used while getting navigation data. @@ -136,5 +134,30 @@ public string DeclaringClassFullName /// public bool HasManagedMethodAndTypeProperties => !string.IsNullOrWhiteSpace(this.ManagedTypeName) && !string.IsNullOrWhiteSpace(this.ManagedMethodName); + + /// + public IReadOnlyCollection Hierarchy => this.hierarchy; + + /// + /// Gets or sets type of dynamic data if any + /// + internal DynamicDataType DataType { get; set; } + + /// + /// Gets or sets the serialized data + /// + internal string[] SerializedData { get; set; } + + /// + /// Gets or sets the test group set during discovery + /// + internal string TestGroup { get; set; } + + /// + /// Gets or sets the display name set during discovery + /// + internal string DisplayName { get; set; } + + internal TestMethod Clone() => this.MemberwiseClone() as TestMethod; } } diff --git a/src/Adapter/MSTest.CoreAdapter/ObjectModel/UnitTestElement.cs b/src/Adapter/MSTest.CoreAdapter/ObjectModel/UnitTestElement.cs index b9b8d13bc..c1b38dacd 100644 --- a/src/Adapter/MSTest.CoreAdapter/ObjectModel/UnitTestElement.cs +++ b/src/Adapter/MSTest.CoreAdapter/ObjectModel/UnitTestElement.cs @@ -7,7 +7,10 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel using System.Collections.Generic; using System.Diagnostics; using System.Globalization; + using System.IO; + using System.Linq; + using Microsoft.TestPlatform.AdapterUtilities; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Extensions; using Microsoft.VisualStudio.TestPlatform.ObjectModel; @@ -15,6 +18,7 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel /// The unit test element. /// [Serializable] + [DebuggerDisplay("{GetDisplayName()} ({TestMethod.ManagedTypeName})")] internal class UnitTestElement { /// @@ -103,6 +107,17 @@ public UnitTestElement(TestMethod testMethod) /// internal string[] WorkItemIds { get; set; } + internal UnitTestElement Clone() + { + var clone = this.MemberwiseClone() as UnitTestElement; + if (this.TestMethod != null) + { + clone.TestMethod = this.TestMethod.Clone(); + } + + return clone; + } + /// /// Convert the UnitTestElement instance to an Object Model testCase instance. /// @@ -129,6 +144,12 @@ internal TestCase ToTestCase() testCase.SetPropertyValue(TestAdapter.Constants.TestClassNameProperty, this.TestMethod.FullClassName); } + var hierarchy = this.TestMethod.Hierarchy; + if (hierarchy != null && hierarchy.Count > 0) + { + testCase.SetHierarchy(hierarchy.ToArray()); + } + // Set declaring type if present so the correct method info can be retrieved if (this.TestMethod.DeclaringClassFullName != null) { @@ -190,6 +211,44 @@ internal TestCase ToTestCase() testCase.SetPropertyValue(TestAdapter.Constants.DoNotParallelizeProperty, this.DoNotParallelize); } + // Store resolved data if any + if (this.TestMethod.DataType != DynamicDataType.None) + { + var data = this.TestMethod.SerializedData; + + testCase.SetPropertyValue(TestAdapter.Constants.TestDynamicDataTypeProperty, (int)this.TestMethod.DataType); + testCase.SetPropertyValue(TestAdapter.Constants.TestDynamicDataProperty, data); + } + + string fileName = testCase.Source; + try + { + fileName = Path.GetFileName(fileName); + } + catch + { + } + + var idProvider = new TestIdProvider(); + idProvider.AppendString(testCase.ExecutorUri?.ToString()); + idProvider.AppendString(fileName); + if (this.TestMethod.HasManagedMethodAndTypeProperties) + { + idProvider.AppendString(this.TestMethod.ManagedTypeName); + idProvider.AppendString(this.TestMethod.ManagedMethodName); + } + else + { + idProvider.AppendString(testCase.FullyQualifiedName); + } + + if (this.TestMethod.DataType != DynamicDataType.None) + { + idProvider.AppendString(testCase.DisplayName); + } + + testCase.Id = idProvider.GetId(); + return testCase; } diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/Resource.Designer.cs b/src/Adapter/MSTest.CoreAdapter/Resources/Resource.Designer.cs index 4724a2c69..6d880c368 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/Resource.Designer.cs +++ b/src/Adapter/MSTest.CoreAdapter/Resources/Resource.Designer.cs @@ -20,7 +20,7 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter { // class via a tool like ResGen or Visual Studio. // To add or remove a member, edit your .ResX file then rerun ResGen // with the /str option, or rebuild your VS project. - [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "15.0.0.0")] + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "16.0.0.0")] [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] internal class Resource { @@ -70,6 +70,33 @@ internal class Resource { } } + /// + /// Looks up a localized string similar to Exception occurred while enumarating DataSourceAttribute on "{0}.{1}": {2}. + /// + internal static string CannotEnumerateDataSourceAttribute { + get { + return ResourceManager.GetString("CannotEnumerateDataSourceAttribute", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to A test method can only contain one DataSourceAttribute, but found {2} on "{0}.{1}".. + /// + internal static string CannotEnumerateDataSourceAttribute_MoreThenOneDefined { + get { + return ResourceManager.GetString("CannotEnumerateDataSourceAttribute_MoreThenOneDefined", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Exception occurred while enumarating IDataSource attribute on "{0}.{1}": {2}. + /// + internal static string CannotEnumerateIDataSourceAttribute { + get { + return ResourceManager.GetString("CannotEnumerateIDataSourceAttribute", resourceCulture); + } + } + /// /// Looks up a localized string similar to The parameter should not be null or empty.. /// @@ -142,6 +169,24 @@ internal class Resource { } } + /// + /// Looks up a localized string similar to "{0}": (Failed to get exception description due to an exception of type "{1}".. + /// + internal static string ExceptionOccuredWhileGettingTheExceptionDescription { + get { + return ResourceManager.GetString("ExceptionOccuredWhileGettingTheExceptionDescription", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Exceptions thrown:. + /// + internal static string ExceptionsThrown { + get { + return ResourceManager.GetString("ExceptionsThrown", resourceCulture); + } + } + /// /// Looks up a localized string similar to Test '{0}' execution has been aborted.. /// @@ -160,6 +205,24 @@ internal class Resource { } } + /// + /// Looks up a localized string similar to Failed to get attribute cache. Ignoring attribute inheritance and falling into 'type defines Attribute model', so that we have some data.. + /// + internal static string FailedFetchAttributeCache { + get { + return ResourceManager.GetString("FailedFetchAttributeCache", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Getting custom attributes for type {0} threw exception (will ignore and use the reflection way): {1}. + /// + internal static string FailedToGetCustomAttribute { + get { + return ResourceManager.GetString("FailedToGetCustomAttribute", resourceCulture); + } + } + /// /// Looks up a localized string similar to Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}.. /// @@ -205,6 +268,15 @@ internal class Resource { } } + /// + /// Looks up a localized string similar to An older version of MSTestV2 package is loaded in assembly, test discovery might fail to discover all data tests if they depend on `.runsettings` file.. + /// + internal static string OlderTFMVersionFound { + get { + return ResourceManager.GetString("OlderTFMVersionFound", resourceCulture); + } + } + /// /// Looks up a localized string similar to Running tests in any of the provided sources is not supported for the selected platform. /// @@ -495,7 +567,7 @@ internal class Resource { } /// - /// Looks up a localized string similar to Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0}. + /// Looks up a localized string similar to Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0}, Stack trace: {1}. /// internal static string UTA_ExecuteThrewException { get { @@ -640,6 +712,15 @@ internal class Resource { } } + /// + /// Looks up a localized string similar to The called code threw an exception that was caught, but the exception value was null. + /// + internal static string UTA_UserCodeThrewNullValueException { + get { + return ResourceManager.GetString("UTA_UserCodeThrewNullValueException", resourceCulture); + } + } + /// /// Looks up a localized string similar to {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread.. /// diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/Resource.resx b/src/Adapter/MSTest.CoreAdapter/Resources/Resource.resx index 474f4ed5d..872c6ab19 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/Resource.resx +++ b/src/Adapter/MSTest.CoreAdapter/Resources/Resource.resx @@ -209,7 +209,7 @@ Error: {1} Class Initialization method {0}.{1} threw exception. {2}: {3}. - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0}, Stack trace: {1} Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. @@ -320,4 +320,45 @@ Error: {1} Test '{0}' execution has been aborted. + + Exception occurred while enumarating DataSourceAttribute on "{0}.{1}": {2} + {0}: TypeName with namespace, +{1}: Method name, +{2}: Exception details + + + A test method can only contain one DataSourceAttribute, but found {2} on "{0}.{1}". + {0}: TypeName with namespace, +{1}: Method name, +{2}: Number of attributed defined. + + + Exception occurred while enumarating IDataSource attribute on "{0}.{1}": {2} + {0}: TypeName with namespace, +{1}: Method name, +{2}: Exception details + + + "{0}": (Failed to get exception description due to an exception of type "{1}". + {0}: Type of the original exception that we're trying to get the desciption of. +{1}: Thrown exception + + + Exceptions thrown: + This is usually preceeds by TestAssembly_AssemblyDiscoveryFailure message, and precceded by list of exceptions thrown in a test discovery session. + + + Failed to get attribute cache. Ignoring attribute inheritance and falling into 'type defines Attribute model', so that we have some data. + + + Getting custom attributes for type {0} threw exception (will ignore and use the reflection way): {1} + {0}: Attribute full type name. +{1}: Exception description + + + An older version of MSTestV2 package is loaded in assembly, test discovery might fail to discover all data tests if they depend on `.runsettings` file. + + + The called code threw an exception that was caught, but the exception value was null + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.cs.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.cs.xlf index 6f77f6ae5..aa8544f0d 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.cs.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.cs.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Test {0} překročil časový limit spuštění. - - - - - Running tests in any of the provided sources is not supported for the selected platform - Spouštění testů v některém z uvedených zdrojů se pro vybranou platformu nepodporuje. - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - Metoda TestCleanup {0}.{1} způsobila výjimku. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Konec trasování zásobníku pro vnitřní výjimku --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: V jednom sestavení nejde definovat více jak jednu metodu s atributem AssemblyCleanup. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: V jednom sestavení nejde definovat více jak jednu metodu s atributem AssemblyInitialize. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: Uvnitř třídy nejde definovat více jak jednu metodu s atributem ClassCleanup. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: Uvnitř třídy nejde definovat více jak jednu metodu s atributem ClassInitialize. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: Nejde definovat více jak jednu metodu s atributem TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: Nejde definovat více jak jednu metodu s atributem TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - Inicializační metoda {0}.{1} způsobila výjimku. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Nepodařilo se vytvořit instanci třídy {0}. Chyba: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Pro třídu {0} se nepodařilo nastavit vlastnost TestContext. Chyba: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Z důvodu výjimky se nepodařilo získat zprávu o výjimce typu {0}.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: Třída {0} neobsahuje platnou vlastnost TestContext. Vlastnost TestContext musí být typu TestContext, musí být nestatická, veřejná a nemůže být určena jenom pro čtení. Například: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: Atribut TestClass se definoval v neveřejné třídě {0}. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter nezjistil v třídě {0} sestavení {1} žádný test, protože: {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Nepovedlo se načíst typy ze zdroje testu {0}. Je možné, že se některé nebo všechny testy v tomto zdroji nezjistily. -Chyba: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: Obecná metoda nemůže být testovací metodou. {0}.{1} má neplatný podpis. - - - - - The parameter should not be null or empty. - Parametr nemůže být null nebo prázdný. - - - - - The parameter must be greater than zero. - Parametr musí být vetší než nula. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter nezjistil v třídě {0} sestavení {1} žádný test. Důvod {2}. - - - - - File does not exist: {0} - Neexistující soubor: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: Metoda {1} definovaná ve třídě {0} nemá správný podpis. Testovací metoda označená pomocí atributu [TestMethod] musí být nestatická, veřejná, nesmí vracet žádnou hodnotu a neměla by mít žádné parametry. Například: public void Test.Class1.Test(). Navíc pokud v testovací metodě používáte asynchronní čekání, musí návratový typ být Task. Například: public Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext nemůže být Null. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Čisticí metoda sestavení {0}.{1} selhala. Chybová zpráva: {2}. Trasování zásobníku: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Inicializační metoda sestavení {0}.{1} vyvolala výjimku. {2}: {3}. Přerušuje se provádění testu. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Čisticí metoda třídy {0}.{1} selhala. Chybová zpráva: {2}. Trasování zásobníku: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Inicializační metoda třídy {0}.{1} vyvolala výjimku. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Při provádění testu došlo k výjimce. Pokud používáte rozšíření třídy TestMethodAttribute, obraťte se na dodavatele. Chybová zpráva: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Při provádění testu došlo k chybě. Rozšíření nevrátilo žádný výsledek. Pokud používáte rozšíření třídy TestMethodAttribute, obraťte se na dodavatele. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} má špatný podpis. Metoda musí být statická, veřejná, nevracet hodnotu a nepřijímat žádné parametry. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} má špatný podpis. Metoda musí být statická, veřejná, nevracet hodnotu a přijímat jeden parametr typu TestContext. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} má neplatný atribut Timeout. Timeout musí být platné celé číslo a nesmí být menší než 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: V metodě {1} nejde definovat předdefinovanou vlastnost {2}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: Vlastní vlastnost {2} je už definovaná. Použije se hodnota {3}. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: V metodě {1} je definovaná vlastní vlastnost, která je null nebo je prázdná. Vlastní vlastnost musí mít platný název. - - - - - Method {0}.{1} does not exist. - Metoda {0}.{1} neexistuje. - - - - - Unable to get default constructor for class {0}. - Pro třídu {0} se nepodařilo najít výchozí konstruktor. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Nepodařilo se najít vlastnost {0}.TestContext. Chyba:{1}. - - - - - The {0}.TestContext has incorrect type. - {0}.TestContext má nesprávný typ. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} má chybný podpis. Metoda musí být nestatická, veřejná, nevracet hodnotu a nepřijímat žádný parametr. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. - - - - - Unable to get type {0}. Error: {1}. - Nepodařilo se získat typ {0}. Chyba: {1}. - - - - - Test method {0} was not found. - Testovací metoda {0} se nenašla. - - - - - Debug Trace: - Trasování ladění: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Nepovedlo se získat výjimku vyvolanou testovací metodou {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - V testovací metodě {0}.{1} došlo k výjimce: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0}. Pokud v testu používáte objekty uživatelského rozhraní, zvažte u projektů pro platformu UPW použití atributu [UITestMethod] místo atributu [TestMethod], aby se test provedl ve vlákně uživatelského rozhraní. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Neplatné nastavení {0}. Neočekávaný XmlAttribute: {1}. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Neplatné nastavení {0}. Neočekávaný XmlElement: {1}. - - - - - {0} (Data Row {1}) - {0} (datový řádek {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - Atribut ExpectedException definovaný u testovací metody {0}.{1} vyvolal během vytváření výjimku. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - Testovací metoda {0}.{1} má definovaných více atributů odvozených od atributu ExpectedExceptionBaseAttribute. Povolený je jenom jeden takový atribut. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Upozornění: Adaptér MSTest V2 nepodporuje soubor testsettings ani vsmdi. - - - - - TestContext Messages: - Zprávy pro TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Při volání čisticí metody testu pro třídu {0} došlo k chybě: {1} - - - - - TestCleanup Stack Trace - Trasování zásobníku čištění testu - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Prováděcí modul MSTest: Je povolená paralelizace testu pro {0} (pracovní procesy: {1}, obor: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Pro Obor je zadaná neplatná hodnota {0}. Podporované obory jsou {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Pro Pracovní procesy je zadaná neplatná hodnota {0}. Hodnota by měla být nezáporné celé číslo. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Nepovedlo se zjistit testy ze sestavení {0}. Důvod:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Parametry můžou mít pouze testovací metody řízené daty. Nechtěli jste použít atribut [DataRow] nebo [DynamicData]? - - - - - Test '{0}' execution has been aborted. - Spouštění testu {0} se přerušilo. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Test {0} překročil časový limit spuštění. + + + + Running tests in any of the provided sources is not supported for the selected platform + Spouštění testů v některém z uvedených zdrojů se pro vybranou platformu nepodporuje. + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + Metoda TestCleanup {0}.{1} způsobila výjimku. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Konec trasování zásobníku pro vnitřní výjimku --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: V jednom sestavení nejde definovat více jak jednu metodu s atributem AssemblyCleanup. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: V jednom sestavení nejde definovat více jak jednu metodu s atributem AssemblyInitialize. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: Uvnitř třídy nejde definovat více jak jednu metodu s atributem ClassCleanup. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: Uvnitř třídy nejde definovat více jak jednu metodu s atributem ClassInitialize. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: Nejde definovat více jak jednu metodu s atributem TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: Nejde definovat více jak jednu metodu s atributem TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + Inicializační metoda {0}.{1} způsobila výjimku. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Nepodařilo se vytvořit instanci třídy {0}. Chyba: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Pro třídu {0} se nepodařilo nastavit vlastnost TestContext. Chyba: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Z důvodu výjimky se nepodařilo získat zprávu o výjimce typu {0}.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: Třída {0} neobsahuje platnou vlastnost TestContext. Vlastnost TestContext musí být typu TestContext, musí být nestatická, veřejná a nemůže být určena jenom pro čtení. Například: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: Atribut TestClass se definoval v neveřejné třídě {0}. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter nezjistil v třídě {0} sestavení {1} žádný test, protože: {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Nepovedlo se načíst typy ze zdroje testu {0}. Je možné, že se některé nebo všechny testy v tomto zdroji nezjistily. +Chyba: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: Obecná metoda nemůže být testovací metodou. {0}.{1} má neplatný podpis. + + + + The parameter should not be null or empty. + Parametr nemůže být null nebo prázdný. + + + + The parameter must be greater than zero. + Parametr musí být vetší než nula. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter nezjistil v třídě {0} sestavení {1} žádný test. Důvod {2}. + + + + File does not exist: {0} + Neexistující soubor: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: Metoda {1} definovaná ve třídě {0} nemá správný podpis. Testovací metoda označená pomocí atributu [TestMethod] musí být nestatická, veřejná, nesmí vracet žádnou hodnotu a neměla by mít žádné parametry. Například: public void Test.Class1.Test(). Navíc pokud v testovací metodě používáte asynchronní čekání, musí návratový typ být Task. Například: public Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext nemůže být Null. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Čisticí metoda sestavení {0}.{1} selhala. Chybová zpráva: {2}. Trasování zásobníku: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Inicializační metoda sestavení {0}.{1} vyvolala výjimku. {2}: {3}. Přerušuje se provádění testu. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Čisticí metoda třídy {0}.{1} selhala. Chybová zpráva: {2}. Trasování zásobníku: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Inicializační metoda třídy {0}.{1} vyvolala výjimku. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Při provádění testu došlo k výjimce. Pokud používáte rozšíření třídy TestMethodAttribute, obraťte se na dodavatele. Chybová zpráva: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Při provádění testu došlo k chybě. Rozšíření nevrátilo žádný výsledek. Pokud používáte rozšíření třídy TestMethodAttribute, obraťte se na dodavatele. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} má špatný podpis. Metoda musí být statická, veřejná, nevracet hodnotu a nepřijímat žádné parametry. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} má špatný podpis. Metoda musí být statická, veřejná, nevracet hodnotu a přijímat jeden parametr typu TestContext. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} má neplatný atribut Timeout. Timeout musí být platné celé číslo a nesmí být menší než 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: V metodě {1} nejde definovat předdefinovanou vlastnost {2}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: Vlastní vlastnost {2} je už definovaná. Použije se hodnota {3}. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: V metodě {1} je definovaná vlastní vlastnost, která je null nebo je prázdná. Vlastní vlastnost musí mít platný název. + + + + Method {0}.{1} does not exist. + Metoda {0}.{1} neexistuje. + + + + Unable to get default constructor for class {0}. + Pro třídu {0} se nepodařilo najít výchozí konstruktor. + + + + Unable to find property {0}.TestContext. Error:{1}. + Nepodařilo se najít vlastnost {0}.TestContext. Chyba:{1}. + + + + The {0}.TestContext has incorrect type. + {0}.TestContext má nesprávný typ. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} má chybný podpis. Metoda musí být nestatická, veřejná, nevracet hodnotu a nepřijímat žádný parametr. Pokud navíc v metodě používáte operátor async-await, musí být návratový typ Task. + + + + Unable to get type {0}. Error: {1}. + Nepodařilo se získat typ {0}. Chyba: {1}. + + + + Test method {0} was not found. + Testovací metoda {0} se nenašla. + + + + Debug Trace: + Trasování ladění: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Nepovedlo se získat výjimku vyvolanou testovací metodou {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + V testovací metodě {0}.{1} došlo k výjimce: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0}. Pokud v testu používáte objekty uživatelského rozhraní, zvažte u projektů pro platformu UPW použití atributu [UITestMethod] místo atributu [TestMethod], aby se test provedl ve vlákně uživatelského rozhraní. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Neplatné nastavení {0}. Neočekávaný XmlAttribute: {1}. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Neplatné nastavení {0}. Neočekávaný XmlElement: {1}. + + + + {0} (Data Row {1}) + {0} (datový řádek {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + Atribut ExpectedException definovaný u testovací metody {0}.{1} vyvolal během vytváření výjimku. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + Testovací metoda {0}.{1} má definovaných více atributů odvozených od atributu ExpectedExceptionBaseAttribute. Povolený je jenom jeden takový atribut. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Upozornění: Adaptér MSTest V2 nepodporuje soubor testsettings ani vsmdi. + + + + TestContext Messages: + Zprávy pro TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Při volání čisticí metody testu pro třídu {0} došlo k chybě: {1} + + + + TestCleanup Stack Trace + Trasování zásobníku čištění testu + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Prováděcí modul MSTest: Je povolená paralelizace testu pro {0} (pracovní procesy: {1}, obor: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Pro Obor je zadaná neplatná hodnota {0}. Podporované obory jsou {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Pro Pracovní procesy je zadaná neplatná hodnota {0}. Hodnota by měla být nezáporné celé číslo. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Nepovedlo se zjistit testy ze sestavení {0}. Důvod:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Parametry můžou mít pouze testovací metody řízené daty. Nechtěli jste použít atribut [DataRow] nebo [DynamicData]? + + + + Test '{0}' execution has been aborted. + Spouštění testu {0} se přerušilo. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.de.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.de.xlf index f9a8d8366..83c71acf7 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.de.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.de.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Der Test "{0}" hat das Ausführungstimeout überschritten. - - - - - Running tests in any of the provided sources is not supported for the selected platform - Das Ausführen von Tests in einer der angegebenen Quellen wird für die ausgewählte Plattform nicht unterstützt. - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - Die TestCleanup-Methode "{0}.{1}" hat eine Ausnahme ausgelöst. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Ende der internen Ausnahmestapelüberwachung --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: Es darf nur eine Methode mit dem Attribut 'AssemblyCleanup' innerhalb einer Assembly definiert werden. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: Es darf nur eine Methode mit dem Attribut 'AssemblyInitialize' innerhalb einer Assembly definiert werden. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: Es darf nur eine Methode mit dem Attribut 'ClassCleanup' innerhalb einer Klasse definiert werden. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: Es darf nur eine Methode mit dem Attribut 'ClassInitialize' innerhalb einer Klasse definiert werden. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: Es darf nur eine Methode mit dem Attribut 'TestCleanup' definiert werden. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: Es darf nur eine Methode mit dem Attribut 'TestInitialize' definiert werden. - - - - - Initialization method {0}.{1} threw exception. {2}. - Die Initialisierungsmethode '{0}.{1}' hat eine Ausnahme ausgelöst. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Es kann keine Instanz der Klasse '{0}' erstellt werden. Fehler: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Die Eigenschaft 'TestContext' für die Klasse '{0}' kann nicht festgelegt werden. Fehler: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Fehler beim Abrufen der Meldung für eine Ausnahme vom Typ "{0}" aufgrund einer Ausnahme.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: Die Klasse '{0}' weist keine gültige Eigenschaft 'TestContext' auf. 'TestContext' muss vom Typ 'TestContext', nicht statisch und öffentlich sein und darf nicht schreibgeschützt sein. Beispiel: 'public TestContext TestContext'. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: Für die nicht öffentliche Klasse '{0}' definiertes Attribut 'TestClass'. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - Fehler von 'MSTestAdapter' beim Ermitteln von Tests in der Klasse "{0}" der Assembly "{1}". Ursache: {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Fehler beim Laden von Typen aus der Testquelle "{0}". Möglicherweise werden einige oder alle Tests in dieser Quelle nicht ermittelt. -Fehler: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: Eine generische Methode kann keine Testmethode sein. '{0}.{1}' weist eine ungültige Signatur auf. - - - - - The parameter should not be null or empty. - Der Parameter darf nicht NULL oder leer sein. - - - - - The parameter must be greater than zero. - Der Parameter muss größer als Null sein. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - Fehler von 'MSTestAdapter' beim Ermitteln von Tests in der Klasse "{0}" der Assembly "{1}". Ursache {2}. - - - - - File does not exist: {0} - Die Datei ist nicht vorhanden: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: Die in der Klasse {0} definierte Methode {1} weist nicht die richtige Signatur auf. Die mit dem [TestMethod]-Attribut markierte Testmethode muss nicht statisch und öffentlich sein, muss den Rückgabetyp "void" aufweisen und darf keine Parameter annehmen. Beispiel: "public void Test.Class1.Test()". Wenn Sie "async-await" in der Testmethode verwenden, muss der Rückgabetyp außerdem "Task" sein. Beispiel: "public async Task Test.Class1.Test2()" - - - - - TestContext cannot be Null. - "TestContext" darf nicht NULL sein. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Fehler bei der Methode "{0}.{1}" für die Assemblybereinigung. Fehlermeldung: {2}. "StackTrace": {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Die Methode "{0}.{1}" für die Assemblyinitialisierung hat eine Ausnahme ausgelöst. {2}: {3}. Die Ausführung des Tests wird abgebrochen. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Fehler bei der Methode "{0}.{1}" für die Klassenbereinigung. Fehlermeldung: {2}. Stapelüberwachung: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Die Methode "{0}.{1}" für die Klasseninitialisierung hat eine Ausnahme ausgelöst. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Während der Ausführung des Tests wurde eine Ausnahme ausgelöst. Wenn Sie eine Extension von "TestMethodAttribute" verwenden, wenden Sie sich bitte an den Anbieter. Fehlermeldung: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Fehler beim Ausführen des Tests. Von der Extension wurde kein Ergebnis zurückgegeben. Wenn Sie eine Extension von "TestMethodAttribute" verwenden, wenden Sie sich bitte an den Anbieter. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Die Methode "{0}.{1}" weist eine falsche Signatur auf. Die Methode muss statisch und öffentlich sein, gibt keinen Wert zurück und sollte keinen Parameter annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - Die Methode {0}.{1} weist eine falsche Signatur auf. Die Methode muss statisch und öffentlich sein, gibt keinen Wert zurück und sollte einen einzigen Parameter vom Typ "TestContext" annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: "{0}.{1}" weist ein ungültiges Attribut "Timeout" auf. Das Timeout muss ein gültiger ganzzahliger Wert sein und darf nicht kleiner als 0 sein. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: Die vordefinierte Eigenschaft "{2}" kann nicht für die Methode "{1}" definiert werden. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: Die benutzerdefinierte Eigenschaft "{2}" ist bereits definiert. "{3}" wird als Wert verwendet. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: Für die Methode "{1}" wurde eine benutzerdefinierte Eigenschaft mit dem Wert NULL oder eine benutzerdefinierte leere Eigenschaft definiert. Die benutzerdefinierte Eigenschaft muss einen gültigen Namen aufweisen. - - - - - Method {0}.{1} does not exist. - Die Methode "{0}.{1}" ist nicht vorhanden. - - - - - Unable to get default constructor for class {0}. - Der Standardkonstruktor für die Klasse "{0}" kann nicht abgerufen werden. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Die Eigenschaft "{0}.TestContext" wurde nicht gefunden. Fehler: {1}. - - - - - The {0}.TestContext has incorrect type. - "{0}.TestContext" weist einen falschen Typ auf. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Die Methode "{0}.{1}" weist eine falsche Signatur auf. Die Methode muss nicht statisch und öffentlich sein, gibt keinen Wert zurück und sollte keinen Parameter annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. - - - - - Unable to get type {0}. Error: {1}. - Der Typ "{0}" kann nicht abgerufen werden. Fehler: {1}. - - - - - Test method {0} was not found. - Die Testmethode "{0}" wurde nicht gefunden. - - - - - Debug Trace: - Debugablaufverfolgung: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Fehler beim Abrufen der von der Testmethode "{0}.{1}" ausgelösten Ausnahme. - - - - - Test method {0}.{1} threw exception: -{2} - Die Testmethode "{0}.{1}" hat eine Ausnahme ausgelöst: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0}: Erwägen Sie für UWP-Projekte bei Einsatz von UI-Objekten im Test die Verwendung des [UITestMethod]-Attributs anstelle von "[TestMethod]", um den Test im UI-Thread auszuführen. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Ungültige Einstellungen "{0}". Unerwartetes XmlAttribute: "{1}". - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Ungültige Einstellungen "{0}". Unerwartetes XmlElement: "{1}". - - - - - {0} (Data Row {1}) - {0} (Datenzeile {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - Das für die Testmethode "{0}.{1}" definierte ExpectedException-Attribut hat während der Konstruktion eine Ausnahme ausgelöst. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - Für die Testmethode "{0}.{1}" sind mehrere Attribute definiert, die von ExpectedExceptionBaseAttribute abgeleitet werden. Nur ein einziges solches Attribut ist zulässig. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Warnung: Eine TESTSETTINGS-Datei oder eine VSMDI-Datei wird vom MSTest-V2-Adapter nicht unterstützt. - - - - - TestContext Messages: - TestContext-Meldungen: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Fehler beim Aufruf der Testbereinigungsmethode für die Testklasse "{0}": {1} - - - - - TestCleanup Stack Trace - TestCleanup-Stapelüberwachung - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - MSTest-Executor: Testparallelisierung für "{0}" aktiviert (Worker: {1}, Bereich: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Ungültiger Wert "{0}" für "Scope" angegeben. Unterstützte Bereiche: {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Ungültiger Wert "{0}" für "Workers" angegeben. Der Wert muss eine nicht negative Ganzzahl sein. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Fehler beim Ermitteln von Tests aus der Assembly "{0}". Ursache:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Nur datengesteuerte Testmethoden können Parameter aufweisen. Wollten Sie [DataRow] oder [DynamicData] verwenden? - - - - - Test '{0}' execution has been aborted. - Die Ausführung des Tests "{0}" wurde abgebrochen. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Der Test "{0}" hat das Ausführungstimeout überschritten. + + + + Running tests in any of the provided sources is not supported for the selected platform + Das Ausführen von Tests in einer der angegebenen Quellen wird für die ausgewählte Plattform nicht unterstützt. + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + Die TestCleanup-Methode "{0}.{1}" hat eine Ausnahme ausgelöst. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Ende der internen Ausnahmestapelüberwachung --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: Es darf nur eine Methode mit dem Attribut 'AssemblyCleanup' innerhalb einer Assembly definiert werden. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: Es darf nur eine Methode mit dem Attribut 'AssemblyInitialize' innerhalb einer Assembly definiert werden. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: Es darf nur eine Methode mit dem Attribut 'ClassCleanup' innerhalb einer Klasse definiert werden. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: Es darf nur eine Methode mit dem Attribut 'ClassInitialize' innerhalb einer Klasse definiert werden. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: Es darf nur eine Methode mit dem Attribut 'TestCleanup' definiert werden. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: Es darf nur eine Methode mit dem Attribut 'TestInitialize' definiert werden. + + + + Initialization method {0}.{1} threw exception. {2}. + Die Initialisierungsmethode '{0}.{1}' hat eine Ausnahme ausgelöst. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Es kann keine Instanz der Klasse '{0}' erstellt werden. Fehler: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Die Eigenschaft 'TestContext' für die Klasse '{0}' kann nicht festgelegt werden. Fehler: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Fehler beim Abrufen der Meldung für eine Ausnahme vom Typ "{0}" aufgrund einer Ausnahme.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: Die Klasse '{0}' weist keine gültige Eigenschaft 'TestContext' auf. 'TestContext' muss vom Typ 'TestContext', nicht statisch und öffentlich sein und darf nicht schreibgeschützt sein. Beispiel: 'public TestContext TestContext'. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: Für die nicht öffentliche Klasse '{0}' definiertes Attribut 'TestClass'. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + Fehler von 'MSTestAdapter' beim Ermitteln von Tests in der Klasse "{0}" der Assembly "{1}". Ursache: {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Fehler beim Laden von Typen aus der Testquelle "{0}". Möglicherweise werden einige oder alle Tests in dieser Quelle nicht ermittelt. +Fehler: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: Eine generische Methode kann keine Testmethode sein. '{0}.{1}' weist eine ungültige Signatur auf. + + + + The parameter should not be null or empty. + Der Parameter darf nicht NULL oder leer sein. + + + + The parameter must be greater than zero. + Der Parameter muss größer als Null sein. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + Fehler von 'MSTestAdapter' beim Ermitteln von Tests in der Klasse "{0}" der Assembly "{1}". Ursache {2}. + + + + File does not exist: {0} + Die Datei ist nicht vorhanden: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: Die in der Klasse {0} definierte Methode {1} weist nicht die richtige Signatur auf. Die mit dem [TestMethod]-Attribut markierte Testmethode muss nicht statisch und öffentlich sein, muss den Rückgabetyp "void" aufweisen und darf keine Parameter annehmen. Beispiel: "public void Test.Class1.Test()". Wenn Sie "async-await" in der Testmethode verwenden, muss der Rückgabetyp außerdem "Task" sein. Beispiel: "public async Task Test.Class1.Test2()" + + + + TestContext cannot be Null. + "TestContext" darf nicht NULL sein. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Fehler bei der Methode "{0}.{1}" für die Assemblybereinigung. Fehlermeldung: {2}. "StackTrace": {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Die Methode "{0}.{1}" für die Assemblyinitialisierung hat eine Ausnahme ausgelöst. {2}: {3}. Die Ausführung des Tests wird abgebrochen. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Fehler bei der Methode "{0}.{1}" für die Klassenbereinigung. Fehlermeldung: {2}. Stapelüberwachung: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Die Methode "{0}.{1}" für die Klasseninitialisierung hat eine Ausnahme ausgelöst. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Während der Ausführung des Tests wurde eine Ausnahme ausgelöst. Wenn Sie eine Extension von "TestMethodAttribute" verwenden, wenden Sie sich bitte an den Anbieter. Fehlermeldung: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Fehler beim Ausführen des Tests. Von der Extension wurde kein Ergebnis zurückgegeben. Wenn Sie eine Extension von "TestMethodAttribute" verwenden, wenden Sie sich bitte an den Anbieter. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Die Methode "{0}.{1}" weist eine falsche Signatur auf. Die Methode muss statisch und öffentlich sein, gibt keinen Wert zurück und sollte keinen Parameter annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + Die Methode {0}.{1} weist eine falsche Signatur auf. Die Methode muss statisch und öffentlich sein, gibt keinen Wert zurück und sollte einen einzigen Parameter vom Typ "TestContext" annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: "{0}.{1}" weist ein ungültiges Attribut "Timeout" auf. Das Timeout muss ein gültiger ganzzahliger Wert sein und darf nicht kleiner als 0 sein. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: Die vordefinierte Eigenschaft "{2}" kann nicht für die Methode "{1}" definiert werden. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: Die benutzerdefinierte Eigenschaft "{2}" ist bereits definiert. "{3}" wird als Wert verwendet. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: Für die Methode "{1}" wurde eine benutzerdefinierte Eigenschaft mit dem Wert NULL oder eine benutzerdefinierte leere Eigenschaft definiert. Die benutzerdefinierte Eigenschaft muss einen gültigen Namen aufweisen. + + + + Method {0}.{1} does not exist. + Die Methode "{0}.{1}" ist nicht vorhanden. + + + + Unable to get default constructor for class {0}. + Der Standardkonstruktor für die Klasse "{0}" kann nicht abgerufen werden. + + + + Unable to find property {0}.TestContext. Error:{1}. + Die Eigenschaft "{0}.TestContext" wurde nicht gefunden. Fehler: {1}. + + + + The {0}.TestContext has incorrect type. + "{0}.TestContext" weist einen falschen Typ auf. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Die Methode "{0}.{1}" weist eine falsche Signatur auf. Die Methode muss nicht statisch und öffentlich sein, gibt keinen Wert zurück und sollte keinen Parameter annehmen. Wenn Sie außerdem in der Methode "async-await" verwenden, muss der Rückgabetyp "Task" sein. + + + + Unable to get type {0}. Error: {1}. + Der Typ "{0}" kann nicht abgerufen werden. Fehler: {1}. + + + + Test method {0} was not found. + Die Testmethode "{0}" wurde nicht gefunden. + + + + Debug Trace: + Debugablaufverfolgung: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Fehler beim Abrufen der von der Testmethode "{0}.{1}" ausgelösten Ausnahme. + + + + Test method {0}.{1} threw exception: +{2} + Die Testmethode "{0}.{1}" hat eine Ausnahme ausgelöst: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0}: Erwägen Sie für UWP-Projekte bei Einsatz von UI-Objekten im Test die Verwendung des [UITestMethod]-Attributs anstelle von "[TestMethod]", um den Test im UI-Thread auszuführen. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Ungültige Einstellungen "{0}". Unerwartetes XmlAttribute: "{1}". + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Ungültige Einstellungen "{0}". Unerwartetes XmlElement: "{1}". + + + + {0} (Data Row {1}) + {0} (Datenzeile {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + Das für die Testmethode "{0}.{1}" definierte ExpectedException-Attribut hat während der Konstruktion eine Ausnahme ausgelöst. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + Für die Testmethode "{0}.{1}" sind mehrere Attribute definiert, die von ExpectedExceptionBaseAttribute abgeleitet werden. Nur ein einziges solches Attribut ist zulässig. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Warnung: Eine TESTSETTINGS-Datei oder eine VSMDI-Datei wird vom MSTest-V2-Adapter nicht unterstützt. + + + + TestContext Messages: + TestContext-Meldungen: + + + + Error calling Test Cleanup method for test class {0}: {1} + Fehler beim Aufruf der Testbereinigungsmethode für die Testklasse "{0}": {1} + + + + TestCleanup Stack Trace + TestCleanup-Stapelüberwachung + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + MSTest-Executor: Testparallelisierung für "{0}" aktiviert (Worker: {1}, Bereich: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Ungültiger Wert "{0}" für "Scope" angegeben. Unterstützte Bereiche: {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Ungültiger Wert "{0}" für "Workers" angegeben. Der Wert muss eine nicht negative Ganzzahl sein. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Fehler beim Ermitteln von Tests aus der Assembly "{0}". Ursache:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Nur datengesteuerte Testmethoden können Parameter aufweisen. Wollten Sie [DataRow] oder [DynamicData] verwenden? + + + + Test '{0}' execution has been aborted. + Die Ausführung des Tests "{0}" wurde abgebrochen. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.es.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.es.xlf index 5a64a7069..4dbd9fd9a 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.es.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.es.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - La prueba '{0}' superó el tiempo de espera de ejecución. - - - - - Running tests in any of the provided sources is not supported for the selected platform - La ejecución de pruebas en las fuentes proporcionadas no se admite para la plataforma seleccionada - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - El método TestCleanup {0}.{1} devolvió una excepción. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Fin del seguimiento de la pila de excepción interna --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: No se puede definir más de un método con el atributo AssemblyCleanup dentro de un ensamblado. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: No se puede definir más de un método con el atributo AssemblyInitialize dentro de un ensamblado. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: No se puede definir más de un método con el atributo ClassCleanup dentro de una clase. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: No se puede definir más de un método con el atributo ClassInitialize dentro de una clase. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: No se puede definir más de un método con el atributo TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: No se puede definir más de un método con el atributo TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - El método de inicialización {0}.{1} devolvió una excepción. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - No se puede crear una instancia de la clase {0}. Error: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - No se puede establecer la propiedad TestContext para la clase {0}. Error: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (No se pudo obtener el mensaje para una excepción del tipo {0} debido a una excepción.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: la clase {0} no tiene la propiedad TestContext válida. TestContext debe ser de tipo TestContext, debe ser no estática, pública y no debe ser de solo lectura. Por ejemplo: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: se ha definido el atributo TestClass en la clase no pública {0} - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter no detectó pruebas en la clase '{0}' del ensamblado '{1}' porque {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - No se pueden cargar tipos del origen de prueba "{0}". Puede que no se detecten algunas o ninguna de las pruebas de este origen. -Error: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: Un método genérico no puede ser un método de prueba. {0}.{1} tiene una firma no válida - - - - - The parameter should not be null or empty. - El parámetro no debe ser NULL ni estar vacío. - - - - - The parameter must be greater than zero. - El parámetro debe ser mayor que cero. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter no detectó pruebas en la clase '{0}' del ensamblado '{1}'. Motivo: {2}. - - - - - File does not exist: {0} - El archivo no existe: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: El método {1} definido en la clase {0} no tiene una signatura correcta. El método de prueba marcado con el atributo [TestMethod] debe ser no estático, público, con el tipo devuelto void y no debe tomar ningún parámetro. Ejemplo: public void Test.Class1.Test(). Además, si está usando async-await en el método de prueba, el tipo devuelto debe ser Task. Ejemplo: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext no será null. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Error de método Cleanup de ensamblado {0}.{1}. Mensaje de error: {2}. StackTrace: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Excepción método inicialización ensamblado {0}.{1}. {2}: {3}. Anulada ejecución de prueba. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Error de método Cleanup de clase {0}.{1}. Mensaje error: {2}. Seguimiento de pila: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Excepción del método inicialización clase {0}. {1}. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Se inició una excepción al ejecutar la prueba. Si usa la extensión de TestMethodAttribute, póngase en contacto con el proveedor. Mensaje de error: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - No se pudo ejecutar prueba. Extensión no devolvió resultados. Si usa extensión TestMethodAttribute, contacte con el proveedor. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Método {0}.{1} tiene firma incorrecta. El método debe ser estático, público, no devolver un valor y no aceptar ningún parámetro. Además, si usa async-esperan en método de tipo de valor devuelto debe ser una tarea. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - Método {0}.{1} tiene firma incorrecta. El método debe ser estático y público, no devolver ningún valor y debe aceptar un solo parámetro tipo TestContext. Además, si está usando async-await en el método, el tipo devuelto debe ser Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: atributo tiempo espera {0}.{1} no válido. Valor tiempo de espera debe ser entero válido y no menor que 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: no se puede definir la propiedad predefinida {2} en el método {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: ya definida propiedad personalizada "{2}". Usando "{3}" como valor. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: se ha definido una propiedad personalizada nula o vacía en el método {1}. La propiedad personalizada debe tener un nombre válido. - - - - - Method {0}.{1} does not exist. - El método {0}.{1} no existe. - - - - - Unable to get default constructor for class {0}. - No se puede obtener el constructor predeterminado para la clase {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - No se puede encontrar la propiedad {0}.TestContext. Error:{1}. - - - - - The {0}.TestContext has incorrect type. - Tipo {0}.TestContext no es correcto. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Método {0}.{1} tiene firma incorrecta. Debe ser un método no estático, público, no devolver ningún valor y no debe aceptar parámetros. Además, si está usando async-await en el método, el tipo devuelto debe ser Task. - - - - - Unable to get type {0}. Error: {1}. - No se puede obtener el tipo {0}. Error: {1}. - - - - - Test method {0} was not found. - No encontrado método prueba {0}. - - - - - Debug Trace: - Seguimiento de depuración: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - No se pudo obtener la excepción iniciada por el método de prueba {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - Excepción método de prueba {0}.{1}: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0}. En proyectos de UWP, si usa objetos de interfaz de usuario en la prueba, podría usar el atributo [UITestMethod] en lugar de [TestMethod] para ejecutar la prueba en el subproceso de interfaz de usuario. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Valor no válido '{0}'. XmlAttribute no esperado: '{1}'. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Valor no válido '{0}'. XmlElement no esperado: '{1}'. - - - - - {0} (Data Row {1}) - {0} (Fila de datos {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - El atributo ExpectedException definido en el método de prueba {0}.{1} inició una excepción durante la construcción. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - El método de prueba {0}.{1} tiene definidos varios atributos derivados de ExpectedExceptionBaseAttribute. Solo se permite uno de estos atributos. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Advertencia: No se admite un archivo testsettings o vsmdi con el adaptador de MSTest V2. - - - - - TestContext Messages: - Mensajes de TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Error al llamar al método Test Cleanup para la clase de prueba {0}: {1} - - - - - TestCleanup Stack Trace - Seguimiento de pila de TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Ejecutor de MSTest Executor: paralelización de prueba habilitada para {0} (Trabajadores: {1}, Ámbito: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Valor no válido "{0}" especificado para "Ámbito". Los ámbitos admitidos son {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Valor no válido "{0}" especificado para "Trabajadores". El valor debe ser un entero no negativo. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - No se pudieron detectar pruebas desde el ensamblado {0}. Motivo:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Solo los métodos de pruebas controladas por datos pueden tener parámetros. ¿Quería usar [DataRow] o [DynamicData]? - - - - - Test '{0}' execution has been aborted. - Se anuló la ejecución de la prueba "{0}". - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + La prueba '{0}' superó el tiempo de espera de ejecución. + + + + Running tests in any of the provided sources is not supported for the selected platform + La ejecución de pruebas en las fuentes proporcionadas no se admite para la plataforma seleccionada + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + El método TestCleanup {0}.{1} devolvió una excepción. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Fin del seguimiento de la pila de excepción interna --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: No se puede definir más de un método con el atributo AssemblyCleanup dentro de un ensamblado. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: No se puede definir más de un método con el atributo AssemblyInitialize dentro de un ensamblado. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: No se puede definir más de un método con el atributo ClassCleanup dentro de una clase. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: No se puede definir más de un método con el atributo ClassInitialize dentro de una clase. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: No se puede definir más de un método con el atributo TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: No se puede definir más de un método con el atributo TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + El método de inicialización {0}.{1} devolvió una excepción. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + No se puede crear una instancia de la clase {0}. Error: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + No se puede establecer la propiedad TestContext para la clase {0}. Error: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (No se pudo obtener el mensaje para una excepción del tipo {0} debido a una excepción.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: la clase {0} no tiene la propiedad TestContext válida. TestContext debe ser de tipo TestContext, debe ser no estática, pública y no debe ser de solo lectura. Por ejemplo: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: se ha definido el atributo TestClass en la clase no pública {0} + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter no detectó pruebas en la clase '{0}' del ensamblado '{1}' porque {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + No se pueden cargar tipos del origen de prueba "{0}". Puede que no se detecten algunas o ninguna de las pruebas de este origen. +Error: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: Un método genérico no puede ser un método de prueba. {0}.{1} tiene una firma no válida + + + + The parameter should not be null or empty. + El parámetro no debe ser NULL ni estar vacío. + + + + The parameter must be greater than zero. + El parámetro debe ser mayor que cero. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter no detectó pruebas en la clase '{0}' del ensamblado '{1}'. Motivo: {2}. + + + + File does not exist: {0} + El archivo no existe: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: El método {1} definido en la clase {0} no tiene una signatura correcta. El método de prueba marcado con el atributo [TestMethod] debe ser no estático, público, con el tipo devuelto void y no debe tomar ningún parámetro. Ejemplo: public void Test.Class1.Test(). Además, si está usando async-await en el método de prueba, el tipo devuelto debe ser Task. Ejemplo: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext no será null. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Error de método Cleanup de ensamblado {0}.{1}. Mensaje de error: {2}. StackTrace: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Excepción método inicialización ensamblado {0}.{1}. {2}: {3}. Anulada ejecución de prueba. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Error de método Cleanup de clase {0}.{1}. Mensaje error: {2}. Seguimiento de pila: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Excepción del método inicialización clase {0}. {1}. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Se inició una excepción al ejecutar la prueba. Si usa la extensión de TestMethodAttribute, póngase en contacto con el proveedor. Mensaje de error: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + No se pudo ejecutar prueba. Extensión no devolvió resultados. Si usa extensión TestMethodAttribute, contacte con el proveedor. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Método {0}.{1} tiene firma incorrecta. El método debe ser estático, público, no devolver un valor y no aceptar ningún parámetro. Además, si usa async-esperan en método de tipo de valor devuelto debe ser una tarea. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + Método {0}.{1} tiene firma incorrecta. El método debe ser estático y público, no devolver ningún valor y debe aceptar un solo parámetro tipo TestContext. Además, si está usando async-await en el método, el tipo devuelto debe ser Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: atributo tiempo espera {0}.{1} no válido. Valor tiempo de espera debe ser entero válido y no menor que 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: no se puede definir la propiedad predefinida {2} en el método {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: ya definida propiedad personalizada "{2}". Usando "{3}" como valor. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: se ha definido una propiedad personalizada nula o vacía en el método {1}. La propiedad personalizada debe tener un nombre válido. + + + + Method {0}.{1} does not exist. + El método {0}.{1} no existe. + + + + Unable to get default constructor for class {0}. + No se puede obtener el constructor predeterminado para la clase {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + No se puede encontrar la propiedad {0}.TestContext. Error:{1}. + + + + The {0}.TestContext has incorrect type. + Tipo {0}.TestContext no es correcto. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Método {0}.{1} tiene firma incorrecta. Debe ser un método no estático, público, no devolver ningún valor y no debe aceptar parámetros. Además, si está usando async-await en el método, el tipo devuelto debe ser Task. + + + + Unable to get type {0}. Error: {1}. + No se puede obtener el tipo {0}. Error: {1}. + + + + Test method {0} was not found. + No encontrado método prueba {0}. + + + + Debug Trace: + Seguimiento de depuración: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + No se pudo obtener la excepción iniciada por el método de prueba {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + Excepción método de prueba {0}.{1}: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0}. En proyectos de UWP, si usa objetos de interfaz de usuario en la prueba, podría usar el atributo [UITestMethod] en lugar de [TestMethod] para ejecutar la prueba en el subproceso de interfaz de usuario. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Valor no válido '{0}'. XmlAttribute no esperado: '{1}'. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Valor no válido '{0}'. XmlElement no esperado: '{1}'. + + + + {0} (Data Row {1}) + {0} (Fila de datos {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + El atributo ExpectedException definido en el método de prueba {0}.{1} inició una excepción durante la construcción. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + El método de prueba {0}.{1} tiene definidos varios atributos derivados de ExpectedExceptionBaseAttribute. Solo se permite uno de estos atributos. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Advertencia: No se admite un archivo testsettings o vsmdi con el adaptador de MSTest V2. + + + + TestContext Messages: + Mensajes de TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Error al llamar al método Test Cleanup para la clase de prueba {0}: {1} + + + + TestCleanup Stack Trace + Seguimiento de pila de TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Ejecutor de MSTest Executor: paralelización de prueba habilitada para {0} (Trabajadores: {1}, Ámbito: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Valor no válido "{0}" especificado para "Ámbito". Los ámbitos admitidos son {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Valor no válido "{0}" especificado para "Trabajadores". El valor debe ser un entero no negativo. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + No se pudieron detectar pruebas desde el ensamblado {0}. Motivo:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Solo los métodos de pruebas controladas por datos pueden tener parámetros. ¿Quería usar [DataRow] o [DynamicData]? + + + + Test '{0}' execution has been aborted. + Se anuló la ejecución de la prueba "{0}". + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.fr.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.fr.xlf index 3206d3d4d..e9ebd4931 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.fr.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.fr.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Le test '{0}' a dépassé le délai d'attente de l'exécution. - - - - - Running tests in any of the provided sources is not supported for the selected platform - L'exécution de tests dans l'une des sources fournies n'est pas prise en charge pour la plateforme sélectionnée - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - La méthode TestCleanup {0}.{1} a levé une exception. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Fin de la trace de la pile d'exception interne --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014 : {0} : impossible de définir plus d'une méthode avec l'attribut AssemblyCleanup à l'intérieur d'un assembly. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013 : {0} : impossible de définir plus d'une méthode avec l'attribut AssemblyInitialize à l'intérieur d'un assembly. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026 : {0} : impossible de définir plus d'une méthode avec l'attribut ClassCleanup à l'intérieur d'une classe. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025 : {0} : impossible de définir plus d'une méthode avec l'attribut ClassInitialize à l'intérieur d'une classe. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024 : {0} : impossible de définir plus d'une méthode avec l'attribut TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018 : {0} : impossible de définir plus d'une méthode avec l'attribut TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - La méthode Initialization {0}.{1} a levé une exception. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Impossible de créer une instance de la classe {0}. Erreur : {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Impossible de définir la propriété TestContext pour la classe {0}. Erreur : {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Échec de la réception du message pour une exception de type {0} en raison d'une exception.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031 : la classe {0} ne possède pas une propriété TestContext valide. TestContext doit être de type TestContext, doit être non statique, publique, et ne doit pas être en lecture seule. Par exemple : public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001 : attribut TestClass défini sur la classe non publique {0} - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter n'a pas découvert de tests dans la classe '{0}' de l'assembly '{1}', car {2}. - - - - - {0}: {1} - {0} : {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Impossible de charger les types à partir de la source de tests '{0}'. Une partie ou l'ensemble des tests de cette source ne peuvent pas être découverts. -Erreur : {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015 : une méthode générique ne peut pas être une méthode de test. {0}.{1} a une signature non valide - - - - - The parameter should not be null or empty. - Le paramètre ne doit pas être une valeur Null ou être vide. - - - - - The parameter must be greater than zero. - Le paramètre doit être supérieur à zéro. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter n'a pas découvert de tests dans la classe '{0}' de l'assembly '{1}'. Raison {2}. - - - - - File does not exist: {0} - Fichier inexistant : {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007 : la méthode {1} définie dans la classe {0} ne dispose pas d'une signature correcte. Une méthode de test marquée avec l'attribut [TestMethod] doit être non statique, doit utiliser void pour return-type et ne doit pas accepter aucun paramètre. Exemple : public void Test.Class1.Test(). En outre, si vous utilisez async-await dans la méthode de test, return-type doit être Task. Exemple : public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext ne peut pas être null. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - La méthode Cleanup d'assembly {0}.{1} a échoué. Message d'erreur : {2}. StackTrace : {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - La méthode d'assembly Initialization {0}.{1} a levé une exception. {2} : {3}. Abandon de l'exécution de tests. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - La méthode de classe Cleanup {0}.{1} a échoué. Message d'erreur : {2}. Trace de la pile : {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - La méthode de classe Initialization {0}.{1} a levé une exception. {2} : {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Exception levée pendant l'exécution du test. Si vous utilisez l'extension de TestMethodAttribute, contactez le fournisseur. Message d'erreur : {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Erreur lors de l'exécution du test. L'extension n'a retourné aucun résultat. Si vous utilisez l'extension de TestMethodAttribute, contactez le fournisseur. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - La méthode {0}.{1} possède une signature incorrecte. La méthode doit être statique, publique et ne doit retourner aucune valeur ni accepter aucun paramètre. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - La méthode {0}.{1} possède une signature incorrecte. La méthode doit être statique, publique et ne doit retourner aucune valeur et accepter un seul paramètre de type TestContext. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054 : {0}.{1} possède un attribut Timeout non valide. Timeout doit être une valeur entière valide, qui ne doit pas être inférieure à 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023 : {0} : Impossible de définir la propriété prédéfinie {2} sur la méthode {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022 : {0}.{1} : La propriété personnalisée "{2}" est déjà définie. Utilisation de "{3}" comme valeur. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021 : {0} : Une propriété null ou vide personnalisée est définie sur la méthode {1}. La propriété personnalisée doit posséder un nom valide. - - - - - Method {0}.{1} does not exist. - La méthode {0}.{1} n'existe pas. - - - - - Unable to get default constructor for class {0}. - Impossible d'obtenir le constructeur par défaut de la classe {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Propriété {0}.TestContext introuvable. Erreur :{1}. - - - - - The {0}.TestContext has incorrect type. - {0}.TestContext possède un type incorrect. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - La méthode {0}.{1} possède une signature incorrecte. La méthode doit être non statique, publique et ne doit retourner aucune valeur ni accepter aucun paramètre. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. - - - - - Unable to get type {0}. Error: {1}. - Impossible d'obtenir le type {0}. Erreur : {1}. - - - - - Test method {0} was not found. - Méthode de test {0} introuvable. - - - - - Debug Trace: - Trace du débogage : - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Échec de l'obtention de l'exception levée par la méthode de test {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - La méthode de test {0}.{1} a levé une exception : -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} Pour les projets UWP, si vous utilisez des objets d'IU dans un test, utilisez l'attribut [UITestMethod] à la place de [TestMethod] pour exécuter le test dans le thread d'interface utilisateur. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Paramètres non valides '{0}'. XmlAttribute inattendu : '{1}'. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Paramètres non valides '{0}'. XmlElement inattendu : '{1}'. - - - - - {0} (Data Row {1}) - {0} (ligne de données {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - L'attribut ExpectedException défini dans la méthode de test {0}.{1} a levé une exception durant la construction. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - Plusieurs attributs dérivés de ExpectedExceptionBaseAttribute sont définis dans la méthode de test {0}.{1}. Un seul attribut de ce type est autorisé. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Avertissement : L'adaptateur MSTest V2 ne prend pas en charge les fichiers testsettings ou vsmdi. - - - - - TestContext Messages: - Messages TestContext : - - - - - Error calling Test Cleanup method for test class {0}: {1} - Erreur lors de l'appel de la méthode Test Cleanup pour la classe de test {0} : {1} - - - - - TestCleanup Stack Trace - Trace de la pile TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Exécuteur MSTest : parallélisation des tests activée pour {0} (threads de travail : {1}, portée : {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Valeur non valide '{0}' spécifiée pour la 'Portée'. Les portées prises en charge sont {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Valeur non valide '{0}' spécifiée pour 'Workers'. La valeur doit être un entier non négatif. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Échec de la découverte de tests à partir de l'assembly {0}. Raison :{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Seules les méthodes de test basées sur les données peuvent avoir des paramètres. Souhaitiez-vous utiliser [DataRow] ou [DynamicData] ? - - - - - Test '{0}' execution has been aborted. - L'exécution du test '{0}' a été abandonnée. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Le test '{0}' a dépassé le délai d'attente de l'exécution. + + + + Running tests in any of the provided sources is not supported for the selected platform + L'exécution de tests dans l'une des sources fournies n'est pas prise en charge pour la plateforme sélectionnée + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + La méthode TestCleanup {0}.{1} a levé une exception. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Fin de la trace de la pile d'exception interne --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014 : {0} : impossible de définir plus d'une méthode avec l'attribut AssemblyCleanup à l'intérieur d'un assembly. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013 : {0} : impossible de définir plus d'une méthode avec l'attribut AssemblyInitialize à l'intérieur d'un assembly. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026 : {0} : impossible de définir plus d'une méthode avec l'attribut ClassCleanup à l'intérieur d'une classe. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025 : {0} : impossible de définir plus d'une méthode avec l'attribut ClassInitialize à l'intérieur d'une classe. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024 : {0} : impossible de définir plus d'une méthode avec l'attribut TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018 : {0} : impossible de définir plus d'une méthode avec l'attribut TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + La méthode Initialization {0}.{1} a levé une exception. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Impossible de créer une instance de la classe {0}. Erreur : {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Impossible de définir la propriété TestContext pour la classe {0}. Erreur : {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Échec de la réception du message pour une exception de type {0} en raison d'une exception.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031 : la classe {0} ne possède pas une propriété TestContext valide. TestContext doit être de type TestContext, doit être non statique, publique, et ne doit pas être en lecture seule. Par exemple : public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001 : attribut TestClass défini sur la classe non publique {0} + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter n'a pas découvert de tests dans la classe '{0}' de l'assembly '{1}', car {2}. + + + + {0}: {1} + {0} : {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Impossible de charger les types à partir de la source de tests '{0}'. Une partie ou l'ensemble des tests de cette source ne peuvent pas être découverts. +Erreur : {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015 : une méthode générique ne peut pas être une méthode de test. {0}.{1} a une signature non valide + + + + The parameter should not be null or empty. + Le paramètre ne doit pas être une valeur Null ou être vide. + + + + The parameter must be greater than zero. + Le paramètre doit être supérieur à zéro. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter n'a pas découvert de tests dans la classe '{0}' de l'assembly '{1}'. Raison {2}. + + + + File does not exist: {0} + Fichier inexistant : {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007 : la méthode {1} définie dans la classe {0} ne dispose pas d'une signature correcte. Une méthode de test marquée avec l'attribut [TestMethod] doit être non statique, doit utiliser void pour return-type et ne doit pas accepter aucun paramètre. Exemple : public void Test.Class1.Test(). En outre, si vous utilisez async-await dans la méthode de test, return-type doit être Task. Exemple : public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext ne peut pas être null. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + La méthode Cleanup d'assembly {0}.{1} a échoué. Message d'erreur : {2}. StackTrace : {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + La méthode d'assembly Initialization {0}.{1} a levé une exception. {2} : {3}. Abandon de l'exécution de tests. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + La méthode de classe Cleanup {0}.{1} a échoué. Message d'erreur : {2}. Trace de la pile : {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + La méthode de classe Initialization {0}.{1} a levé une exception. {2} : {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Exception levée pendant l'exécution du test. Si vous utilisez l'extension de TestMethodAttribute, contactez le fournisseur. Message d'erreur : {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Erreur lors de l'exécution du test. L'extension n'a retourné aucun résultat. Si vous utilisez l'extension de TestMethodAttribute, contactez le fournisseur. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + La méthode {0}.{1} possède une signature incorrecte. La méthode doit être statique, publique et ne doit retourner aucune valeur ni accepter aucun paramètre. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + La méthode {0}.{1} possède une signature incorrecte. La méthode doit être statique, publique et ne doit retourner aucune valeur et accepter un seul paramètre de type TestContext. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054 : {0}.{1} possède un attribut Timeout non valide. Timeout doit être une valeur entière valide, qui ne doit pas être inférieure à 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023 : {0} : Impossible de définir la propriété prédéfinie {2} sur la méthode {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022 : {0}.{1} : La propriété personnalisée "{2}" est déjà définie. Utilisation de "{3}" comme valeur. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021 : {0} : Une propriété null ou vide personnalisée est définie sur la méthode {1}. La propriété personnalisée doit posséder un nom valide. + + + + Method {0}.{1} does not exist. + La méthode {0}.{1} n'existe pas. + + + + Unable to get default constructor for class {0}. + Impossible d'obtenir le constructeur par défaut de la classe {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + Propriété {0}.TestContext introuvable. Erreur :{1}. + + + + The {0}.TestContext has incorrect type. + {0}.TestContext possède un type incorrect. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + La méthode {0}.{1} possède une signature incorrecte. La méthode doit être non statique, publique et ne doit retourner aucune valeur ni accepter aucun paramètre. En outre, si vous utilisez async-await dans la méthode, return-type doit être Task. + + + + Unable to get type {0}. Error: {1}. + Impossible d'obtenir le type {0}. Erreur : {1}. + + + + Test method {0} was not found. + Méthode de test {0} introuvable. + + + + Debug Trace: + Trace du débogage : + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Échec de l'obtention de l'exception levée par la méthode de test {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + La méthode de test {0}.{1} a levé une exception : +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} Pour les projets UWP, si vous utilisez des objets d'IU dans un test, utilisez l'attribut [UITestMethod] à la place de [TestMethod] pour exécuter le test dans le thread d'interface utilisateur. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Paramètres non valides '{0}'. XmlAttribute inattendu : '{1}'. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Paramètres non valides '{0}'. XmlElement inattendu : '{1}'. + + + + {0} (Data Row {1}) + {0} (ligne de données {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + L'attribut ExpectedException défini dans la méthode de test {0}.{1} a levé une exception durant la construction. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + Plusieurs attributs dérivés de ExpectedExceptionBaseAttribute sont définis dans la méthode de test {0}.{1}. Un seul attribut de ce type est autorisé. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Avertissement : L'adaptateur MSTest V2 ne prend pas en charge les fichiers testsettings ou vsmdi. + + + + TestContext Messages: + Messages TestContext : + + + + Error calling Test Cleanup method for test class {0}: {1} + Erreur lors de l'appel de la méthode Test Cleanup pour la classe de test {0} : {1} + + + + TestCleanup Stack Trace + Trace de la pile TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Exécuteur MSTest : parallélisation des tests activée pour {0} (threads de travail : {1}, portée : {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Valeur non valide '{0}' spécifiée pour la 'Portée'. Les portées prises en charge sont {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Valeur non valide '{0}' spécifiée pour 'Workers'. La valeur doit être un entier non négatif. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Échec de la découverte de tests à partir de l'assembly {0}. Raison :{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Seules les méthodes de test basées sur les données peuvent avoir des paramètres. Souhaitiez-vous utiliser [DataRow] ou [DynamicData] ? + + + + Test '{0}' execution has been aborted. + L'exécution du test '{0}' a été abandonnée. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.it.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.it.xlf index 670b7f1e3..e34a99bec 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.it.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.it.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - È stato superato il periodo di timeout per l'esecuzione del test '{0}'. - - - - - Running tests in any of the provided sources is not supported for the selected platform - L'esecuzione di test in una delle origini specificate non è supportata per la piattaforma selezionata - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - Il metodo TestCleanup {0}.{1} ha generato un'eccezione. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Fine dell'analisi dello stack dell'eccezione interna --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: non è possibile definire più di un metodo con l'attributo AssemblyCleanup all'interno di un assembly. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: non è possibile definire più di un metodo con l'attributo AssemblyInitialize all'interno di un assembly. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: non è possibile definire più di un metodo con l'attributo ClassCleanup all'interno di una classe. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: non è possibile definire più di un metodo con l'attributo ClassInitialize all'interno di una classe. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: non è possibile definire più di un metodo con l'attributo TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: non è possibile definire più di un metodo con l'attributo TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - Il metodo di inizializzazione {0}.{1} ha generato un'eccezione. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Non è possibile creare un'istanza della classe {0}. Errore: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Non è possibile impostare la proprietà TestContext per la classe {0}. Errore: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - Non è stato possibile ottenere il messaggio per un'eccezione di tipo {0} a causa di un'eccezione. - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: la classe {0} non contiene una proprietà TestContext valida. TestContext deve essere una proprietà di tipo TestContext, non statica, pubblica e non di sola lettura. Esempio: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: è stato definito l'attributo TestClass per la classe non pubblica {0} - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter non è riuscito a individuare test nella classe '{0}' dell'assembly '{1}' perché {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Non è possibile caricare i tipi dall'origine test '{0}'. È possibile che alcuni o tutti i test non siano stati individuati in questa origine. -Errore: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: un metodo generico non può essere un metodo di test. La firma di {0}.{1} non è valida - - - - - The parameter should not be null or empty. - Il parametro non deve essere vuoto o Null. - - - - - The parameter must be greater than zero. - Il parametro deve essere maggiore di zero. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter non è riuscito a individuare test nella classe '{0}' dell'assembly '{1}'. Motivo: {2}. - - - - - File does not exist: {0} - Il file {0} non esiste - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: la firma del metodo {1} definito nella classe {0} non è corretta. Il metodo di test contrassegnato con l'attributo [TestMethod] deve essere pubblico e non statico, non deve accettare parametri e deve includere un tipo restituito void. Esempio: public void Test.Class1.Test(). Se inoltre nel metodo di test si usa async-await, il tipo restituito deve essere Task. Esempio: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext non può essere Null. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Il metodo di pulizia assembly {0}.{1} non è riuscito. Messaggio di errore: {2}. Analisi dello stack: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Il metodo di inizializzazione assembly {0}.{1} ha generato un'eccezione. {2}: {3}. L'esecuzione del test verrà interrotta. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Il metodo di pulizia classi {0}.{1} non è riuscito. Messaggio di errore: {2}. Analisi dello stack: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Il metodo di inizializzazione classi {0}.{1} ha generato un'eccezione. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - È stata generata un'eccezione durante l'esecuzione del test. Se si usa l'estensione di TestMethodAttribute, contattare il fornitore. Messaggio di errore: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Si è verificato un errore durante l'esecuzione del test. L'estensione non ha restituito alcun risultato. Se si usa l'estensione di TestMethodAttribute, contattare il fornitore. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - La firma del metodo {0}.{1} non è corretta. Il metodo deve essere statico e pubblico, non deve restituire un valore né accettare parametri. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - La firma del metodo {0}.{1} non è corretta. Il metodo deve essere statico e pubblico, non deve restituire un valore e deve accettare un singolo parametro di tipo TestContext. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: l'attributo Timeout di {0}.{1} non è valido. Il timeout deve essere un valore intero valido non minore di 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: non è possibile definire la proprietà predefinita {2} per il metodo {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: la proprietà personalizzata "{2}" dell'agente è già definita. Verrà usato il valore "{3}". - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: per il metodo {1} è stata definita una proprietà personalizzata Null o vuota. Specificare un nome valido per la proprietà personalizzata. - - - - - Method {0}.{1} does not exist. - Il metodo {0}.{1} non esiste. - - - - - Unable to get default constructor for class {0}. - Non è possibile ottenere il costruttore predefinito per la classe {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - La proprietà {0}.TestContext non è stata trovata. Errore: {1}. - - - - - The {0}.TestContext has incorrect type. - Il tipo di {0}.TestContext non è corretto. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - La firma del metodo {0}.{1} non è corretta. Il metodo deve essere non statico e pubblico, non deve restituire un valore né accettare parametri. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. - - - - - Unable to get type {0}. Error: {1}. - Non è possibile ottenere il tipo {0}. Errore: {1}. - - - - - Test method {0} was not found. - Il metodo di test {0} non è stato trovato. - - - - - Debug Trace: - Traccia di debug: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Non è stato possibile ottenere l'eccezione generata dal metodo di test {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - Il metodo di test {0}.{1} ha generato un'eccezione: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0}. Se, per i progetti della piattaforma UWP, nel test si usano oggetti dell'interfaccia utente, provare a specificare l'attributo [UITestMethod] invece di [TestMethod] per eseguire il test nel thread di UI. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Le impostazioni '{0}' non sono valide. Elemento XmlAttribute imprevisto: '{1}'. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Le impostazioni '{0}' non sono valide. Elemento XmlElement imprevisto: '{1}'. - - - - - {0} (Data Row {1}) - {0} (riga dati {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - L'attributo ExpectedException definito nel metodo di test {0}.{1} ha generato un'eccezione durante la costruzione. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - Il metodo di test {0}.{1} contiene più attributi derivati dall'elemento ExpectedExceptionBaseAttribute definito per esso. È consentito solo uno di tali attributi. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Avviso: con l'adattatore MSTest V2 non è possibile usare un file testsettings o un file vsmdi. - - - - - TestContext Messages: - Messaggi di TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Si è verificato un errore durante la chiamata del metodo TestCleanup per la classe di test {0}: {1} - - - - - TestCleanup Stack Trace - Analisi dello stato di TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Individuazione][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Executor MSTest: Parallelizzazione test abilitata per {0} (Workers: {1}. Scope: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Il valore '{0}', specificato per 'Scope', non è valido. I valori supportati per Scope sono {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Il valore '{0}', specificato per 'Workers', non è valido. Il valore deve essere un numero intero non negativo. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Non è stato possibile individuare i test dall'assembly {0}. Motivo: {1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Solo i metodi di test basati sui dati possono includere parametri. Si intendeva usare [DataRow] o [DynamicData]? - - - - - Test '{0}' execution has been aborted. - L'esecuzione del test '{0}' è stata interrotta. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + È stato superato il periodo di timeout per l'esecuzione del test '{0}'. + + + + Running tests in any of the provided sources is not supported for the selected platform + L'esecuzione di test in una delle origini specificate non è supportata per la piattaforma selezionata + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + Il metodo TestCleanup {0}.{1} ha generato un'eccezione. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Fine dell'analisi dello stack dell'eccezione interna --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: non è possibile definire più di un metodo con l'attributo AssemblyCleanup all'interno di un assembly. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: non è possibile definire più di un metodo con l'attributo AssemblyInitialize all'interno di un assembly. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: non è possibile definire più di un metodo con l'attributo ClassCleanup all'interno di una classe. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: non è possibile definire più di un metodo con l'attributo ClassInitialize all'interno di una classe. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: non è possibile definire più di un metodo con l'attributo TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: non è possibile definire più di un metodo con l'attributo TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + Il metodo di inizializzazione {0}.{1} ha generato un'eccezione. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Non è possibile creare un'istanza della classe {0}. Errore: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Non è possibile impostare la proprietà TestContext per la classe {0}. Errore: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + Non è stato possibile ottenere il messaggio per un'eccezione di tipo {0} a causa di un'eccezione. + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: la classe {0} non contiene una proprietà TestContext valida. TestContext deve essere una proprietà di tipo TestContext, non statica, pubblica e non di sola lettura. Esempio: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: è stato definito l'attributo TestClass per la classe non pubblica {0} + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter non è riuscito a individuare test nella classe '{0}' dell'assembly '{1}' perché {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Non è possibile caricare i tipi dall'origine test '{0}'. È possibile che alcuni o tutti i test non siano stati individuati in questa origine. +Errore: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: un metodo generico non può essere un metodo di test. La firma di {0}.{1} non è valida + + + + The parameter should not be null or empty. + Il parametro non deve essere vuoto o Null. + + + + The parameter must be greater than zero. + Il parametro deve essere maggiore di zero. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter non è riuscito a individuare test nella classe '{0}' dell'assembly '{1}'. Motivo: {2}. + + + + File does not exist: {0} + Il file {0} non esiste + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: la firma del metodo {1} definito nella classe {0} non è corretta. Il metodo di test contrassegnato con l'attributo [TestMethod] deve essere pubblico e non statico, non deve accettare parametri e deve includere un tipo restituito void. Esempio: public void Test.Class1.Test(). Se inoltre nel metodo di test si usa async-await, il tipo restituito deve essere Task. Esempio: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext non può essere Null. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Il metodo di pulizia assembly {0}.{1} non è riuscito. Messaggio di errore: {2}. Analisi dello stack: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Il metodo di inizializzazione assembly {0}.{1} ha generato un'eccezione. {2}: {3}. L'esecuzione del test verrà interrotta. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Il metodo di pulizia classi {0}.{1} non è riuscito. Messaggio di errore: {2}. Analisi dello stack: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Il metodo di inizializzazione classi {0}.{1} ha generato un'eccezione. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + È stata generata un'eccezione durante l'esecuzione del test. Se si usa l'estensione di TestMethodAttribute, contattare il fornitore. Messaggio di errore: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Si è verificato un errore durante l'esecuzione del test. L'estensione non ha restituito alcun risultato. Se si usa l'estensione di TestMethodAttribute, contattare il fornitore. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + La firma del metodo {0}.{1} non è corretta. Il metodo deve essere statico e pubblico, non deve restituire un valore né accettare parametri. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + La firma del metodo {0}.{1} non è corretta. Il metodo deve essere statico e pubblico, non deve restituire un valore e deve accettare un singolo parametro di tipo TestContext. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: l'attributo Timeout di {0}.{1} non è valido. Il timeout deve essere un valore intero valido non minore di 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: non è possibile definire la proprietà predefinita {2} per il metodo {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: la proprietà personalizzata "{2}" dell'agente è già definita. Verrà usato il valore "{3}". + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: per il metodo {1} è stata definita una proprietà personalizzata Null o vuota. Specificare un nome valido per la proprietà personalizzata. + + + + Method {0}.{1} does not exist. + Il metodo {0}.{1} non esiste. + + + + Unable to get default constructor for class {0}. + Non è possibile ottenere il costruttore predefinito per la classe {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + La proprietà {0}.TestContext non è stata trovata. Errore: {1}. + + + + The {0}.TestContext has incorrect type. + Il tipo di {0}.TestContext non è corretto. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + La firma del metodo {0}.{1} non è corretta. Il metodo deve essere non statico e pubblico, non deve restituire un valore né accettare parametri. Se inoltre si usa async-await nel metodo di test, il tipo restituito deve essere Task. + + + + Unable to get type {0}. Error: {1}. + Non è possibile ottenere il tipo {0}. Errore: {1}. + + + + Test method {0} was not found. + Il metodo di test {0} non è stato trovato. + + + + Debug Trace: + Traccia di debug: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Non è stato possibile ottenere l'eccezione generata dal metodo di test {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + Il metodo di test {0}.{1} ha generato un'eccezione: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0}. Se, per i progetti della piattaforma UWP, nel test si usano oggetti dell'interfaccia utente, provare a specificare l'attributo [UITestMethod] invece di [TestMethod] per eseguire il test nel thread di UI. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Le impostazioni '{0}' non sono valide. Elemento XmlAttribute imprevisto: '{1}'. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Le impostazioni '{0}' non sono valide. Elemento XmlElement imprevisto: '{1}'. + + + + {0} (Data Row {1}) + {0} (riga dati {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + L'attributo ExpectedException definito nel metodo di test {0}.{1} ha generato un'eccezione durante la costruzione. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + Il metodo di test {0}.{1} contiene più attributi derivati dall'elemento ExpectedExceptionBaseAttribute definito per esso. È consentito solo uno di tali attributi. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Avviso: con l'adattatore MSTest V2 non è possibile usare un file testsettings o un file vsmdi. + + + + TestContext Messages: + Messaggi di TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Si è verificato un errore durante la chiamata del metodo TestCleanup per la classe di test {0}: {1} + + + + TestCleanup Stack Trace + Analisi dello stato di TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Individuazione][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Executor MSTest: Parallelizzazione test abilitata per {0} (Workers: {1}. Scope: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Il valore '{0}', specificato per 'Scope', non è valido. I valori supportati per Scope sono {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Il valore '{0}', specificato per 'Workers', non è valido. Il valore deve essere un numero intero non negativo. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Non è stato possibile individuare i test dall'assembly {0}. Motivo: {1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Solo i metodi di test basati sui dati possono includere parametri. Si intendeva usare [DataRow] o [DynamicData]? + + + + Test '{0}' execution has been aborted. + L'esecuzione del test '{0}' è stata interrotta. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ja.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ja.xlf index c0d288509..39c7249ab 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ja.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ja.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - テスト '{0}' は実行タイムアウトを超えました。 - - - - - Running tests in any of the provided sources is not supported for the selected platform - 指定されたソースのいずれかでのテストの実行は、選択されたプラットフォームでサポートされていません - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - TestCleanup メソッド {0}.{1} は例外をスローしました。{2}: {3}。 - - - - - --- End of inner exception stack trace --- - --- 内部例外スタック トレースの終わり --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: 1 つのアセンブリ内で、AssemblyCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: 1 つのアセンブリ内で、AssemblyInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: 1 つのクラス内で、ClassCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: 1 つのクラス内で、ClassInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: TestCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: TestInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 - - - - - Initialization method {0}.{1} threw exception. {2}. - 初期化メソッド {0}.{1} は例外をスローしました。{2}。 - - - - - Unable to create instance of class {0}. Error: {1}. - クラス {0} のインスタンスを作成できません。エラー: {1}。 - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - クラス {0} の TestContext プロパティを設定できません。エラー: {1}。 - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (例外が発生したため、型 {0} の例外のメッセージを取得できませんでした。) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: クラス {0} は有効な TestContext プロパティを含んでいません。TestContext は、型 TestContext でなければなりません。また、non-static および public である必要があり、読み取り専用に指定することはできません。例: public TestContext TestContext。 - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: TestClass 属性がパブリックでないクラス {0} で定義されています - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter でアセンブリ '{1}' のクラス '{0}' にテストが見つかりませんでした。理由 {2}。 - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - テスト ソース '{0}' から型を読み込むことができません。このソース内の一部またはすべてのテストが見つからない可能性があります。 -エラー: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: ジェネリック メソッドがテスト メソッドになることはできません。{0}.{1} のシグネチャは無効です - - - - - The parameter should not be null or empty. - パラメーターを null または空にすることはできません。 - - - - - The parameter must be greater than zero. - パラメーターはゼロよりも大きい必要があります。 - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter でアセンブリ '{1}' のクラス '{0}' にテストが見つかりませんでした。理由 {2}。 - - - - - File does not exist: {0} - ファイルが存在しません: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: クラス {0} で定義されたメソッド {1} は正しいシグネチャを含んでいません。[TestMethod] 属性を伴って設定されたテスト メソッドは non-static、public にする必要があり、戻り値の型は void でなければなりません。また、パラメーターを受け取ることはできません。例: public void Test.Class1.Test()。また、テスト メソッドで async-await を使用する場合、戻り値の型は Task にする必要があります。例: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext を Null にすることはできません。 - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - アセンブリ クリーンアップ メソッド {0}.{1} に失敗しました。エラー メッセージ: {2}。スタック トレース: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - アセンブリ初期化メソッド {0}.{1} は例外をスローしました。{2}: {3}。テストの実行を中止しています。 - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - クラス クリーンアップ メソッド {0}.{1} に失敗しました。エラー メッセージ: {2}。スタック トレース: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - クラス初期化メソッド {0}.{1} は例外をスローしました。{2}: {3}。 - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - テストの実行中に例外がスローされました。TestMethodAttribute の拡張クラスを使用している場合は、ベンダーに連絡してください。エラー メッセージ: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - テストの実行中にエラーが発生しました。拡張から結果が返されませんでした。TestMethodAttribute の拡張クラスを使用している場合は、ベンダーに連絡してください。 - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは static および public である必要があり、値を返しません。また、パラメーターを受け取ることはできません。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは static および public である必要があり、値を返しません。また、TestContext 型の 1 つのパラメーターを受け取る必要があります。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} は無効な Timeout 属性を含んでいます。タイムアウトは有効な整数値でなければなりません。0 よりも小さい値にすることはできません。 - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: メソッド {1} 上の以前に定義されたプロパティ {2} を定義することはできません。 - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: カスタム プロパティ "{2}" は既に定義されています。"{3}" を値として使用しています。 - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: Null または空のカスタム プロパティが、メソッド {1} で定義されています。カスタム プロパティには有効な名前を指定しなければなりません。 - - - - - Method {0}.{1} does not exist. - メソッド {0}.{1} は存在しません。 - - - - - Unable to get default constructor for class {0}. - クラス {0} の既定コンストラクターを取得できません。 - - - - - Unable to find property {0}.TestContext. Error:{1}. - プロパティ {0}.TestContext が見つかりません。エラー: {1}。 - - - - - The {0}.TestContext has incorrect type. - {0}.TestContext は不適切な型を含んでいます。 - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは non-static および public である必要があり、値を返しません。また、パラメーターを受け取ることはできません。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 - - - - - Unable to get type {0}. Error: {1}. - 型 {0} を取得できません。エラー: {1}。 - - - - - Test method {0} was not found. - テスト メソッド {0} が見つかりませんでした。 - - - - - Debug Trace: - デバッグ トレース: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - テスト メソッド {0}.{1} によってスローされた例外を取得できませんでした。 - - - - - Test method {0}.{1} threw exception: -{2} - テスト メソッド {0}.{1} が例外をスローしました: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} UWP プロジェクトについて、テスト内で UI オブジェクトを使用している場合は、[TestMethod] の代わりに [UITestMethod] 属性を使用して UI スレッド内でテストを実行することを検討してください。 - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - 設定 '{0}' は無効です。予期しない XmlAttribute: '{1}'。 - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - 設定 '{0}' は無効です。予期しない XmlElement: '{1}'。 - - - - - {0} (Data Row {1}) - {0} (データ行 {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - テスト メソッド {0}.{1} に定義されている ExpectedException 属性が、作成中に例外をスローしました。 -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - テスト メソッド {0}.{1} には、ExpectedExceptionBaseAttribute から派生した属性が複数定義されています。このような属性は 1 つしか許可されません。 - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - 警告: testsettings ファイル、vsmdi ファイルは MSTest V2 アダプターではサポートされていません。 - - - - - TestContext Messages: - TestContext メッセージ: - - - - - Error calling Test Cleanup method for test class {0}: {1} - テスト クラス {0} のテスト クリーンアップ メソッドの呼び出しでエラーが発生しました: {1} - - - - - TestCleanup Stack Trace - TestCleanup スタック トレース - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - MSTest 実行プログラム: {0} でテスト並列処理が有効にされています (Workers: {1}、Scope: {2})。 - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - 無効な値 '{0}' が 'Scope' に指定されました。サポートされているスコープは {1} です。 - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - 無効な値 '{0}' が 'Workers' に指定されました。値は負ではない整数である必要があります。 - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - アセンブリ {0} からテストを検出できませんでした。理由:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - データ ドリブン テスト メソッドのみがパラメーターを使用できます。[DataRow] または [DynamicData] の使用を意図していましたか? - - - - - Test '{0}' execution has been aborted. - テスト '{0}' の実行が中止されました。 - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + テスト '{0}' は実行タイムアウトを超えました。 + + + + Running tests in any of the provided sources is not supported for the selected platform + 指定されたソースのいずれかでのテストの実行は、選択されたプラットフォームでサポートされていません + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + TestCleanup メソッド {0}.{1} は例外をスローしました。{2}: {3}。 + + + + --- End of inner exception stack trace --- + --- 内部例外スタック トレースの終わり --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: 1 つのアセンブリ内で、AssemblyCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: 1 つのアセンブリ内で、AssemblyInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: 1 つのクラス内で、ClassCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: 1 つのクラス内で、ClassInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: TestCleanup 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: TestInitialize 属性を伴う 2 つ以上のメソッドを定義することはできません。 + + + + Initialization method {0}.{1} threw exception. {2}. + 初期化メソッド {0}.{1} は例外をスローしました。{2}。 + + + + Unable to create instance of class {0}. Error: {1}. + クラス {0} のインスタンスを作成できません。エラー: {1}。 + + + + Unable to set TestContext property for the class {0}. Error: {1}. + クラス {0} の TestContext プロパティを設定できません。エラー: {1}。 + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (例外が発生したため、型 {0} の例外のメッセージを取得できませんでした。) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: クラス {0} は有効な TestContext プロパティを含んでいません。TestContext は、型 TestContext でなければなりません。また、non-static および public である必要があり、読み取り専用に指定することはできません。例: public TestContext TestContext。 + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: TestClass 属性がパブリックでないクラス {0} で定義されています + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter でアセンブリ '{1}' のクラス '{0}' にテストが見つかりませんでした。理由 {2}。 + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + テスト ソース '{0}' から型を読み込むことができません。このソース内の一部またはすべてのテストが見つからない可能性があります。 +エラー: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: ジェネリック メソッドがテスト メソッドになることはできません。{0}.{1} のシグネチャは無効です + + + + The parameter should not be null or empty. + パラメーターを null または空にすることはできません。 + + + + The parameter must be greater than zero. + パラメーターはゼロよりも大きい必要があります。 + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter でアセンブリ '{1}' のクラス '{0}' にテストが見つかりませんでした。理由 {2}。 + + + + File does not exist: {0} + ファイルが存在しません: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: クラス {0} で定義されたメソッド {1} は正しいシグネチャを含んでいません。[TestMethod] 属性を伴って設定されたテスト メソッドは non-static、public にする必要があり、戻り値の型は void でなければなりません。また、パラメーターを受け取ることはできません。例: public void Test.Class1.Test()。また、テスト メソッドで async-await を使用する場合、戻り値の型は Task にする必要があります。例: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext を Null にすることはできません。 + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + アセンブリ クリーンアップ メソッド {0}.{1} に失敗しました。エラー メッセージ: {2}。スタック トレース: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + アセンブリ初期化メソッド {0}.{1} は例外をスローしました。{2}: {3}。テストの実行を中止しています。 + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + クラス クリーンアップ メソッド {0}.{1} に失敗しました。エラー メッセージ: {2}。スタック トレース: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + クラス初期化メソッド {0}.{1} は例外をスローしました。{2}: {3}。 + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + テストの実行中に例外がスローされました。TestMethodAttribute の拡張クラスを使用している場合は、ベンダーに連絡してください。エラー メッセージ: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + テストの実行中にエラーが発生しました。拡張から結果が返されませんでした。TestMethodAttribute の拡張クラスを使用している場合は、ベンダーに連絡してください。 + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは static および public である必要があり、値を返しません。また、パラメーターを受け取ることはできません。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは static および public である必要があり、値を返しません。また、TestContext 型の 1 つのパラメーターを受け取る必要があります。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} は無効な Timeout 属性を含んでいます。タイムアウトは有効な整数値でなければなりません。0 よりも小さい値にすることはできません。 + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: メソッド {1} 上の以前に定義されたプロパティ {2} を定義することはできません。 + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: カスタム プロパティ "{2}" は既に定義されています。"{3}" を値として使用しています。 + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: Null または空のカスタム プロパティが、メソッド {1} で定義されています。カスタム プロパティには有効な名前を指定しなければなりません。 + + + + Method {0}.{1} does not exist. + メソッド {0}.{1} は存在しません。 + + + + Unable to get default constructor for class {0}. + クラス {0} の既定コンストラクターを取得できません。 + + + + Unable to find property {0}.TestContext. Error:{1}. + プロパティ {0}.TestContext が見つかりません。エラー: {1}。 + + + + The {0}.TestContext has incorrect type. + {0}.TestContext は不適切な型を含んでいます。 + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + メソッド {0}.{1} は不適切なシグネチャを含んでいます。メソッドは non-static および public である必要があり、値を返しません。また、パラメーターを受け取ることはできません。さらに、メソッドで async-await を使用している場合、戻り値の型は Task である必要があります。 + + + + Unable to get type {0}. Error: {1}. + 型 {0} を取得できません。エラー: {1}。 + + + + Test method {0} was not found. + テスト メソッド {0} が見つかりませんでした。 + + + + Debug Trace: + デバッグ トレース: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + テスト メソッド {0}.{1} によってスローされた例外を取得できませんでした。 + + + + Test method {0}.{1} threw exception: +{2} + テスト メソッド {0}.{1} が例外をスローしました: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} UWP プロジェクトについて、テスト内で UI オブジェクトを使用している場合は、[TestMethod] の代わりに [UITestMethod] 属性を使用して UI スレッド内でテストを実行することを検討してください。 + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + 設定 '{0}' は無効です。予期しない XmlAttribute: '{1}'。 + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + 設定 '{0}' は無効です。予期しない XmlElement: '{1}'。 + + + + {0} (Data Row {1}) + {0} (データ行 {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + テスト メソッド {0}.{1} に定義されている ExpectedException 属性が、作成中に例外をスローしました。 +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + テスト メソッド {0}.{1} には、ExpectedExceptionBaseAttribute から派生した属性が複数定義されています。このような属性は 1 つしか許可されません。 + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + 警告: testsettings ファイル、vsmdi ファイルは MSTest V2 アダプターではサポートされていません。 + + + + TestContext Messages: + TestContext メッセージ: + + + + Error calling Test Cleanup method for test class {0}: {1} + テスト クラス {0} のテスト クリーンアップ メソッドの呼び出しでエラーが発生しました: {1} + + + + TestCleanup Stack Trace + TestCleanup スタック トレース + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + MSTest 実行プログラム: {0} でテスト並列処理が有効にされています (Workers: {1}、Scope: {2})。 + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + 無効な値 '{0}' が 'Scope' に指定されました。サポートされているスコープは {1} です。 + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + 無効な値 '{0}' が 'Workers' に指定されました。値は負ではない整数である必要があります。 + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + アセンブリ {0} からテストを検出できませんでした。理由:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + データ ドリブン テスト メソッドのみがパラメーターを使用できます。[DataRow] または [DynamicData] の使用を意図していましたか? + + + + Test '{0}' execution has been aborted. + テスト '{0}' の実行が中止されました。 + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ko.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ko.xlf index 376a6c5bc..c25951285 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ko.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ko.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - '{0}' 테스트가 실행 시간 제한을 초과했습니다. - - - - - Running tests in any of the provided sources is not supported for the selected platform - 선택된 플랫폼의 경우 제공된 소스에서 테스트를 실행할 수 없습니다. - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - TestCleanup 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- 내부 예외 스택 추적의 끝 --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: 어셈블리 내부에서 AssemblyCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: 어셈블리 내부에서 AssemblyInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: 클래스 내부에서 ClassCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: 클래스 내부에서 ClassInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: TestCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: TestInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. - - - - - Initialization method {0}.{1} threw exception. {2}. - 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - {0} 클래스의 인스턴스를 만들 수 없습니다. 오류: {1} - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - {0} 클래스에 대해 TestContext 속성을 설정할 수 없습니다. 오류: {1} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (예외로 인해 {0} 형식의 예외에 대한 메시지를 가져오지 못했습니다.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: {0} 클래스에 올바른 TestContext 속성이 없습니다. TestContext는 TestContext 형식이어야 하고 읽기 전용이 아니어야 하며, static이 아니고 public이어야 합니다. 예: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: public이 아닌 클래스 {0}에서 TestClass 특성을 정의했습니다. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter가 {2} 때문에 어셈블리 '{1}'의 클래스 '{0}'에서 테스트를 검색하지 못했습니다. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - 테스트 소스 '{0}'에서 형식을 로드할 수 없습니다. 이 소스의 일부 또는 모든 테스트를 검색할 수 없습니다. -오류: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: 제네릭 메서드는 테스트 메서드일 수 없습니다. {0}.{1}에 잘못된 서명이 있습니다. - - - - - The parameter should not be null or empty. - 매개 변수는 null이거나 비워 둘 수 없습니다. - - - - - The parameter must be greater than zero. - 매개 변수는 0보다 커야 합니다. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter가 어셈블리 '{1}'의 클래스 '{0}'에서 테스트를 검색하지 못했습니다. 이유는 {2}입니다. - - - - - File does not exist: {0} - 파일이 없습니다. {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: {0} 클래스에 정의된 {1} 메서드의 서명이 잘못되었습니다. [TestMethod] 특성으로 표시된 테스트 메서드는 static이 아니고 public이어야 하며, 반환 형식이 void여야 하고 매개 변수를 사용할 수 없습니다. 예: public void Test.Class1.Test(). 또한 테스트 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. 예: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext는 null일 수 없습니다. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - 어셈블리 정리 메서드 {0}.{1}이(가) 실패했습니다. 오류 메시지: {2}. StackTrace: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - 어셈블리 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3}. 테스트 실행을 중단합니다. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - 클래스 정리 메서드 {0}.{1}이(가) 실패했습니다. 오류 메시지: {2}. 스택 추적: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - 클래스 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3} - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - 테스트를 실행하는 동안 예외가 발생했습니다. TestMethodAttribute 확장을 사용하는 경우 공급업체에 문의하세요. 오류 메시지: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - 테스트를 실행하는 중에 오류가 발생했습니다. 확장에서 결과가 반환되지 않았습니다. TestMethodAttribute 확장을 사용하는 경우 공급업체에 문의하세요. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이고 공용이어야 하며, 값을 반환하거나 매개 변수를 취하지 않습니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이고 공용이어야 하며, 값을 반환하지 않고 TestContext 형식의 매개 변수 한 개를 사용해야 합니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1}에 잘못된 Timeout 특성이 있습니다. Timeout은 유효한 정수 값이어야 하며 0보다 작을 수 없습니다. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: {1} 메서드에서 미리 정의된 속성 {2}을(를) 정의할 수 없습니다. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: 사용자 지정 속성 "{2}"은(는) 이미 정의되어 있습니다. 값으로 "{3}"을(를) 사용합니다. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: {1} 메서드에서 Null 또는 빈 사용자 지정 속성을 정의했습니다. 사용자 지정 속성에는 올바른 이름이 지정되어 있어야 합니다. - - - - - Method {0}.{1} does not exist. - {0}.{1} 메서드가 없습니다. - - - - - Unable to get default constructor for class {0}. - {0} 클래스의 기본 생성자를 가져올 수 없습니다. - - - - - Unable to find property {0}.TestContext. Error:{1}. - {0}.TestContext 속성을 찾을 수 없습니다. 오류: {1} - - - - - The {0}.TestContext has incorrect type. - {0}.TestContext의 형식이 잘못되었습니다. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이 아니고 공용이어야 하며, 값을 반환하거나 매개 변수를 사용할 수 없습니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. - - - - - Unable to get type {0}. Error: {1}. - {0} 형식을 가져올 수 없습니다. 오류: {1} - - - - - Test method {0} was not found. - {0} 테스트 메서드를 찾을 수 없습니다. - - - - - Debug Trace: - 디버그 추적: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - 테스트 메서드 {0}.{1}에서 throw한 예외를 가져오지 못했습니다. - - - - - Test method {0}.{1} threw exception: -{2} - 테스트 메서드 {0}.{1}에서 예외를 throw했습니다. -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} UWP 프로젝트의 경우 테스트에서 UI 개체를 사용 중이면 [TestMethod] 대신 [UITestMethod] 특성을 사용하여 UI 스레드에서 테스트를 실행하세요. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - '{0}' 설정이 잘못되었습니다. 예기치 않은 XmlAttribute '{1}'이(가) 있습니다. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - '{0}' 설정이 잘못되었습니다. 예기치 않은 XmlElement '{1}'이(가) 있습니다. - - - - - {0} (Data Row {1}) - {0}(데이터 행 {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - 테스트 메서드 {0}.{1}에 정의된 ExpectedException 특성이 생성하는 동안 예외를 throw했습니다. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - 테스트 메서드 {0}.{1}에는 정의되어 있는 ExpectedExceptionBaseAttribute에서 파생된 특성이 여러 개 있습니다. 이러한 특성은 하나만 허용됩니다. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - 경고: MSTest V2 어댑터에서는 testsettings 파일 또는 vsmdi 파일이 지원되지 않습니다. - - - - - TestContext Messages: - TestContext 메시지: - - - - - Error calling Test Cleanup method for test class {0}: {1} - 테스트 클래스 {0}에 대한 테스트 정리 메서드를 호출하는 오류: {1} - - - - - TestCleanup Stack Trace - TestCleanup 스택 추적 - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][검색][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - MSTest 실행기: {0}에 대해 테스트 병렬 처리를 사용합니다(Workers: {1}, Scope: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - 'Scope'에 대해 잘못된 값 '{0}'이(가) 지정되었습니다. 지원되는 범위는 {1}입니다. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - 'Workers'에 대해 잘못된 값 '{0}'이(가) 지정되었습니다. 이 값은 음수가 아닌 정수여야 합니다. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - 어셈블리 {0}에서 테스트를 검색하지 못했습니다. 이유:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - 데이터 기반 테스트 메서드에만 매개 변수를 포함할 수 있습니다. [DataRow] 또는 [DynamicData]를 사용하려고 하셨습니까? - - - - - Test '{0}' execution has been aborted. - 테스트 '{0}' 실행이 중단되었습니다. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + '{0}' 테스트가 실행 시간 제한을 초과했습니다. + + + + Running tests in any of the provided sources is not supported for the selected platform + 선택된 플랫폼의 경우 제공된 소스에서 테스트를 실행할 수 없습니다. + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + TestCleanup 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- 내부 예외 스택 추적의 끝 --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: 어셈블리 내부에서 AssemblyCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: 어셈블리 내부에서 AssemblyInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: 클래스 내부에서 ClassCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: 클래스 내부에서 ClassInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: TestCleanup 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: TestInitialize 특성을 사용하는 메서드를 여러 개 정의할 수 없습니다. + + + + Initialization method {0}.{1} threw exception. {2}. + 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + {0} 클래스의 인스턴스를 만들 수 없습니다. 오류: {1} + + + + Unable to set TestContext property for the class {0}. Error: {1}. + {0} 클래스에 대해 TestContext 속성을 설정할 수 없습니다. 오류: {1} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (예외로 인해 {0} 형식의 예외에 대한 메시지를 가져오지 못했습니다.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: {0} 클래스에 올바른 TestContext 속성이 없습니다. TestContext는 TestContext 형식이어야 하고 읽기 전용이 아니어야 하며, static이 아니고 public이어야 합니다. 예: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: public이 아닌 클래스 {0}에서 TestClass 특성을 정의했습니다. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter가 {2} 때문에 어셈블리 '{1}'의 클래스 '{0}'에서 테스트를 검색하지 못했습니다. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + 테스트 소스 '{0}'에서 형식을 로드할 수 없습니다. 이 소스의 일부 또는 모든 테스트를 검색할 수 없습니다. +오류: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: 제네릭 메서드는 테스트 메서드일 수 없습니다. {0}.{1}에 잘못된 서명이 있습니다. + + + + The parameter should not be null or empty. + 매개 변수는 null이거나 비워 둘 수 없습니다. + + + + The parameter must be greater than zero. + 매개 변수는 0보다 커야 합니다. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter가 어셈블리 '{1}'의 클래스 '{0}'에서 테스트를 검색하지 못했습니다. 이유는 {2}입니다. + + + + File does not exist: {0} + 파일이 없습니다. {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: {0} 클래스에 정의된 {1} 메서드의 서명이 잘못되었습니다. [TestMethod] 특성으로 표시된 테스트 메서드는 static이 아니고 public이어야 하며, 반환 형식이 void여야 하고 매개 변수를 사용할 수 없습니다. 예: public void Test.Class1.Test(). 또한 테스트 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. 예: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext는 null일 수 없습니다. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + 어셈블리 정리 메서드 {0}.{1}이(가) 실패했습니다. 오류 메시지: {2}. StackTrace: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + 어셈블리 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3}. 테스트 실행을 중단합니다. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + 클래스 정리 메서드 {0}.{1}이(가) 실패했습니다. 오류 메시지: {2}. 스택 추적: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + 클래스 초기화 메서드 {0}.{1}에서 예외를 throw했습니다. {2}: {3} + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + 테스트를 실행하는 동안 예외가 발생했습니다. TestMethodAttribute 확장을 사용하는 경우 공급업체에 문의하세요. 오류 메시지: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + 테스트를 실행하는 중에 오류가 발생했습니다. 확장에서 결과가 반환되지 않았습니다. TestMethodAttribute 확장을 사용하는 경우 공급업체에 문의하세요. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이고 공용이어야 하며, 값을 반환하거나 매개 변수를 취하지 않습니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이고 공용이어야 하며, 값을 반환하지 않고 TestContext 형식의 매개 변수 한 개를 사용해야 합니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1}에 잘못된 Timeout 특성이 있습니다. Timeout은 유효한 정수 값이어야 하며 0보다 작을 수 없습니다. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: {1} 메서드에서 미리 정의된 속성 {2}을(를) 정의할 수 없습니다. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: 사용자 지정 속성 "{2}"은(는) 이미 정의되어 있습니다. 값으로 "{3}"을(를) 사용합니다. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: {1} 메서드에서 Null 또는 빈 사용자 지정 속성을 정의했습니다. 사용자 지정 속성에는 올바른 이름이 지정되어 있어야 합니다. + + + + Method {0}.{1} does not exist. + {0}.{1} 메서드가 없습니다. + + + + Unable to get default constructor for class {0}. + {0} 클래스의 기본 생성자를 가져올 수 없습니다. + + + + Unable to find property {0}.TestContext. Error:{1}. + {0}.TestContext 속성을 찾을 수 없습니다. 오류: {1} + + + + The {0}.TestContext has incorrect type. + {0}.TestContext의 형식이 잘못되었습니다. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} 메서드의 서명이 잘못되었습니다. 메서드는 정적이 아니고 공용이어야 하며, 값을 반환하거나 매개 변수를 사용할 수 없습니다. 또한 메서드에서 비동기 대기를 사용하는 경우 반환 형식은 Task여야 합니다. + + + + Unable to get type {0}. Error: {1}. + {0} 형식을 가져올 수 없습니다. 오류: {1} + + + + Test method {0} was not found. + {0} 테스트 메서드를 찾을 수 없습니다. + + + + Debug Trace: + 디버그 추적: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + 테스트 메서드 {0}.{1}에서 throw한 예외를 가져오지 못했습니다. + + + + Test method {0}.{1} threw exception: +{2} + 테스트 메서드 {0}.{1}에서 예외를 throw했습니다. +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} UWP 프로젝트의 경우 테스트에서 UI 개체를 사용 중이면 [TestMethod] 대신 [UITestMethod] 특성을 사용하여 UI 스레드에서 테스트를 실행하세요. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + '{0}' 설정이 잘못되었습니다. 예기치 않은 XmlAttribute '{1}'이(가) 있습니다. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + '{0}' 설정이 잘못되었습니다. 예기치 않은 XmlElement '{1}'이(가) 있습니다. + + + + {0} (Data Row {1}) + {0}(데이터 행 {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + 테스트 메서드 {0}.{1}에 정의된 ExpectedException 특성이 생성하는 동안 예외를 throw했습니다. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + 테스트 메서드 {0}.{1}에는 정의되어 있는 ExpectedExceptionBaseAttribute에서 파생된 특성이 여러 개 있습니다. 이러한 특성은 하나만 허용됩니다. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + 경고: MSTest V2 어댑터에서는 testsettings 파일 또는 vsmdi 파일이 지원되지 않습니다. + + + + TestContext Messages: + TestContext 메시지: + + + + Error calling Test Cleanup method for test class {0}: {1} + 테스트 클래스 {0}에 대한 테스트 정리 메서드를 호출하는 오류: {1} + + + + TestCleanup Stack Trace + TestCleanup 스택 추적 + + + + [MSTest][Discovery][{0}] {1} + [MSTest][검색][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + MSTest 실행기: {0}에 대해 테스트 병렬 처리를 사용합니다(Workers: {1}, Scope: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + 'Scope'에 대해 잘못된 값 '{0}'이(가) 지정되었습니다. 지원되는 범위는 {1}입니다. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + 'Workers'에 대해 잘못된 값 '{0}'이(가) 지정되었습니다. 이 값은 음수가 아닌 정수여야 합니다. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + 어셈블리 {0}에서 테스트를 검색하지 못했습니다. 이유:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + 데이터 기반 테스트 메서드에만 매개 변수를 포함할 수 있습니다. [DataRow] 또는 [DynamicData]를 사용하려고 하셨습니까? + + + + Test '{0}' execution has been aborted. + 테스트 '{0}' 실행이 중단되었습니다. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pl.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pl.xlf index f4b2557f6..b1a88cac4 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pl.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pl.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Test „{0}” przekroczył okres limitu czasu na wykonanie. - - - - - Running tests in any of the provided sources is not supported for the selected platform - Uruchamianie testów w żadnym z podanych źródeł nie jest obsługiwane dla wybranej platformy - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - Metoda TestCleanup {0}.{1} zgłosiła wyjątek. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Koniec śledzenia stosu wyjątku wewnętrznego --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: W zestawie nie można zdefiniować więcej niż jednej metody z atrybutem AssemblyCleanup. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: W zestawie nie można zdefiniować więcej niż jednej metody z atrybutem AssemblyInitialize. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: W klasie nie można zdefiniować więcej niż jednej metody z atrybutem ClassCleanup. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: W klasie nie można zdefiniować więcej niż jednej metody z atrybutem ClassInitialize. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: Nie można zdefiniować więcej niż jednej metody z atrybutem TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: Nie można zdefiniować więcej niż jednej metody z atrybutem TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - Metoda inicjowania {0}.{1} zgłosiła wyjątek. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Nie można utworzyć wystąpienia klasy {0}. Błąd: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Nie można ustawić właściwości TestContext w klasie {0}. Błąd: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Nie można pobrać komunikatu dotyczącego wyjątku typu {0} z powodu wyjątku). - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: Klasa {0} nie ma prawidłowej właściwości TestContext. Właściwość TestContext musi być typu TestContext, niestatyczna, publiczna i nie może być tylko do odczytu. Na przykład : public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: Atrybut TestClass zdefiniowany dla niepublicznej klasy {0} - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - Adapter MSTestAdapter nie mógł odnaleźć testów w klasie „{0}” zestawu „{1}”, przyczyna: {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Nie można załadować typów ze źródła testów „{0}”. Niektóre lub wszystkie testy w tym źródle mogły nie zostać odnalezione. -Błąd: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: Metoda ogólna nie może być metodą testową. {0}{1} ma nieprawidłową sygnaturę - - - - - The parameter should not be null or empty. - Parametr nie może mieć wartości null ani być pusty. - - - - - The parameter must be greater than zero. - Parametr musi być większy od zera. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - Adapter MSTestAdapter nie mógł odnaleźć testów w klasie „{0}” zestawu „{1}”. Przyczyna: {2}. - - - - - File does not exist: {0} - Plik nie istnieje: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: Metoda {1} zdefiniowana w klasie {0} nie ma poprawnej sygnatury. Metoda testowa oznaczona przez atrybut [TestMethod] musi być niestatyczna, publiczna, zwracać wartość typu void i nie powinna przyjmować żadnego parametru. Przykład: public void Test.Class1.Test(). Ponadto zwracana wartość musi być typu Task, gdy w metodzie testowej jest używane oczekiwanie asynchroniczne. Przykład: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - Wartość TestContext nie może być równa null. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Metoda czyszczenia zestawu {0}.{1} nie powiodła się. Komunikat o błędzie: {2}. Ślad stosu: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Metoda inicjująca zestaw {0}.{1} nie powiodła się. {2}: {3}. Przerywanie wykonywania testu. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Metoda czyszczenia klasy {0}.{1} nie powiodła się. Komunikat o błędzie: {2}. Ślad stosu: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Metoda inicjowania klasy {0}.{1} zgłosiła wyjątek. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Zgłoszono wyjątek podczas wykonywania testu. W przypadku korzystania z rozszerzenia atrybutu TestMethodAttribute należy skontaktować się z dostawcą. Komunikat o błędzie: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Błąd podczas wykonywania testu. Rozszerzenie nie zwróciło żadnego wyniku. W przypadku korzystania z rozszerzenia atrybutu TestMethodAttribute należy skontaktować się z dostawcą. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być statyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować żadnego parametru. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być statyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować pojedynczego parametru typu TestContext. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} ma nieprawidłowy atrybut Timeout. Limit czasu musi być prawidłową liczbą całkowitą i nie może być mniejszy niż 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: Nie można zdefiniować wstępnie zdefiniowanej właściwości {2} dla metody {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: Właściwość niestandardowa „{2}” jest już zdefiniowana. Jako wartość jest używane „{3}”. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: Zerowa lub pusta niestandardowa właściwość została zdefiniowana dla metody {1}. Niestandardowa właściwość musi mieć prawidłową nazwę. - - - - - Method {0}.{1} does not exist. - Metoda {0}.{1} nie istnieje. - - - - - Unable to get default constructor for class {0}. - Nie można pobrać domyślnego konstruktora dla klasy {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Nie można znaleźć właściwości {0}.TestContext. Błąd:{1}. - - - - - The {0}.TestContext has incorrect type. - Element {0}.TestContext ma niepoprawny typ. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być niestatyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować żadnego parametru. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. - - - - - Unable to get type {0}. Error: {1}. - Nie można uzyskać typu {0}. Błąd: {1}. - - - - - Test method {0} was not found. - Nie znaleziono metody testowej {0}. - - - - - Debug Trace: - Ślad debugowania: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Nie powiodło się uzyskanie wyjątku zgłoszonego przez metodę testową {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - Metoda testowa {0}.{1} zgłosiła wyjątek: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} Jeśli w projektach UWP korzystasz z obiektów interfejsu użytkownika podczas testowania, rozważ użycie atrybutu [UITestMethod] zamiast atrybutu [TestMethod], aby wykonywać test w wątku interfejsu użytkownika. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Nieprawidłowe ustawienia „{0}”. Nieoczekiwany atrybut XmlAttribute: „{1}”. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Nieprawidłowe ustawienia „{0}”. Nieoczekiwany atrybut XmlElement: „{1}”. - - - - - {0} (Data Row {1}) - {0} (wiersz danych {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - Atrybut ExpectedException zdefiniowany dla metody testowej {0}.{1} zgłosił wyjątek w trakcie konstruowania. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - Metoda testowa {0}.{1} ma wiele zdefiniowanych dla niej atrybutów pochodzących od atrybutu ExpectedExceptionBaseAttribute. Dozwolony jest tylko jeden taki atrybut. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Ostrzeżenie: Plik testsettings lub plik vsmdi nie jest obsługiwany przez adapter MSTest w wersji 2. - - - - - TestContext Messages: - Komunikaty TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Błąd podczas wywoływania metody czyszczącej testu dla klasy testowej {0}: {1} - - - - - TestCleanup Stack Trace - Ślad stosu dla TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Moduł wykonywania MSTest: włączono obsługę równoległego wykonywania testów dla elementu {0} (procesy robocze: {1}, zakres: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Określono nieprawidłową wartość „{0}” dla właściwości „Scope”. Obsługiwane zakresy to {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Określono nieprawidłową wartość „{0}” dla właściwości „Workers”. Wartość musi być nieujemną liczbą całkowitą. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Nie można odnaleźć testów z zestawu {0}. Przyczyna:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Tylko metody testowe bazujące na danych mogą mieć parametry. Czy chodziło Ci o użycie elementu [DataRow] lub [DynamicData]? - - - - - Test '{0}' execution has been aborted. - Wykonanie testu „{0}” zostało przerwane. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Test „{0}” przekroczył okres limitu czasu na wykonanie. + + + + Running tests in any of the provided sources is not supported for the selected platform + Uruchamianie testów w żadnym z podanych źródeł nie jest obsługiwane dla wybranej platformy + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + Metoda TestCleanup {0}.{1} zgłosiła wyjątek. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Koniec śledzenia stosu wyjątku wewnętrznego --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: W zestawie nie można zdefiniować więcej niż jednej metody z atrybutem AssemblyCleanup. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: W zestawie nie można zdefiniować więcej niż jednej metody z atrybutem AssemblyInitialize. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: W klasie nie można zdefiniować więcej niż jednej metody z atrybutem ClassCleanup. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: W klasie nie można zdefiniować więcej niż jednej metody z atrybutem ClassInitialize. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: Nie można zdefiniować więcej niż jednej metody z atrybutem TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: Nie można zdefiniować więcej niż jednej metody z atrybutem TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + Metoda inicjowania {0}.{1} zgłosiła wyjątek. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Nie można utworzyć wystąpienia klasy {0}. Błąd: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Nie można ustawić właściwości TestContext w klasie {0}. Błąd: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Nie można pobrać komunikatu dotyczącego wyjątku typu {0} z powodu wyjątku). + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: Klasa {0} nie ma prawidłowej właściwości TestContext. Właściwość TestContext musi być typu TestContext, niestatyczna, publiczna i nie może być tylko do odczytu. Na przykład : public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: Atrybut TestClass zdefiniowany dla niepublicznej klasy {0} + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + Adapter MSTestAdapter nie mógł odnaleźć testów w klasie „{0}” zestawu „{1}”, przyczyna: {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Nie można załadować typów ze źródła testów „{0}”. Niektóre lub wszystkie testy w tym źródle mogły nie zostać odnalezione. +Błąd: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: Metoda ogólna nie może być metodą testową. {0}{1} ma nieprawidłową sygnaturę + + + + The parameter should not be null or empty. + Parametr nie może mieć wartości null ani być pusty. + + + + The parameter must be greater than zero. + Parametr musi być większy od zera. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + Adapter MSTestAdapter nie mógł odnaleźć testów w klasie „{0}” zestawu „{1}”. Przyczyna: {2}. + + + + File does not exist: {0} + Plik nie istnieje: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: Metoda {1} zdefiniowana w klasie {0} nie ma poprawnej sygnatury. Metoda testowa oznaczona przez atrybut [TestMethod] musi być niestatyczna, publiczna, zwracać wartość typu void i nie powinna przyjmować żadnego parametru. Przykład: public void Test.Class1.Test(). Ponadto zwracana wartość musi być typu Task, gdy w metodzie testowej jest używane oczekiwanie asynchroniczne. Przykład: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + Wartość TestContext nie może być równa null. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Metoda czyszczenia zestawu {0}.{1} nie powiodła się. Komunikat o błędzie: {2}. Ślad stosu: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Metoda inicjująca zestaw {0}.{1} nie powiodła się. {2}: {3}. Przerywanie wykonywania testu. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Metoda czyszczenia klasy {0}.{1} nie powiodła się. Komunikat o błędzie: {2}. Ślad stosu: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Metoda inicjowania klasy {0}.{1} zgłosiła wyjątek. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Zgłoszono wyjątek podczas wykonywania testu. W przypadku korzystania z rozszerzenia atrybutu TestMethodAttribute należy skontaktować się z dostawcą. Komunikat o błędzie: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Błąd podczas wykonywania testu. Rozszerzenie nie zwróciło żadnego wyniku. W przypadku korzystania z rozszerzenia atrybutu TestMethodAttribute należy skontaktować się z dostawcą. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być statyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować żadnego parametru. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być statyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować pojedynczego parametru typu TestContext. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} ma nieprawidłowy atrybut Timeout. Limit czasu musi być prawidłową liczbą całkowitą i nie może być mniejszy niż 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: Nie można zdefiniować wstępnie zdefiniowanej właściwości {2} dla metody {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: Właściwość niestandardowa „{2}” jest już zdefiniowana. Jako wartość jest używane „{3}”. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: Zerowa lub pusta niestandardowa właściwość została zdefiniowana dla metody {1}. Niestandardowa właściwość musi mieć prawidłową nazwę. + + + + Method {0}.{1} does not exist. + Metoda {0}.{1} nie istnieje. + + + + Unable to get default constructor for class {0}. + Nie można pobrać domyślnego konstruktora dla klasy {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + Nie można znaleźć właściwości {0}.TestContext. Błąd:{1}. + + + + The {0}.TestContext has incorrect type. + Element {0}.TestContext ma niepoprawny typ. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Metoda {0}.{1} ma nieprawidłową sygnaturę. Metoda musi być niestatyczna i publiczna, nie może zwracać wartości i nie powinna przyjmować żadnego parametru. Ponadto jeśli w metodzie jest używane oczekiwanie asynchroniczne, zwracanym typem musi być typ Task. + + + + Unable to get type {0}. Error: {1}. + Nie można uzyskać typu {0}. Błąd: {1}. + + + + Test method {0} was not found. + Nie znaleziono metody testowej {0}. + + + + Debug Trace: + Ślad debugowania: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Nie powiodło się uzyskanie wyjątku zgłoszonego przez metodę testową {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + Metoda testowa {0}.{1} zgłosiła wyjątek: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} Jeśli w projektach UWP korzystasz z obiektów interfejsu użytkownika podczas testowania, rozważ użycie atrybutu [UITestMethod] zamiast atrybutu [TestMethod], aby wykonywać test w wątku interfejsu użytkownika. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Nieprawidłowe ustawienia „{0}”. Nieoczekiwany atrybut XmlAttribute: „{1}”. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Nieprawidłowe ustawienia „{0}”. Nieoczekiwany atrybut XmlElement: „{1}”. + + + + {0} (Data Row {1}) + {0} (wiersz danych {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + Atrybut ExpectedException zdefiniowany dla metody testowej {0}.{1} zgłosił wyjątek w trakcie konstruowania. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + Metoda testowa {0}.{1} ma wiele zdefiniowanych dla niej atrybutów pochodzących od atrybutu ExpectedExceptionBaseAttribute. Dozwolony jest tylko jeden taki atrybut. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Ostrzeżenie: Plik testsettings lub plik vsmdi nie jest obsługiwany przez adapter MSTest w wersji 2. + + + + TestContext Messages: + Komunikaty TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Błąd podczas wywoływania metody czyszczącej testu dla klasy testowej {0}: {1} + + + + TestCleanup Stack Trace + Ślad stosu dla TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Moduł wykonywania MSTest: włączono obsługę równoległego wykonywania testów dla elementu {0} (procesy robocze: {1}, zakres: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Określono nieprawidłową wartość „{0}” dla właściwości „Scope”. Obsługiwane zakresy to {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Określono nieprawidłową wartość „{0}” dla właściwości „Workers”. Wartość musi być nieujemną liczbą całkowitą. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Nie można odnaleźć testów z zestawu {0}. Przyczyna:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Tylko metody testowe bazujące na danych mogą mieć parametry. Czy chodziło Ci o użycie elementu [DataRow] lub [DynamicData]? + + + + Test '{0}' execution has been aborted. + Wykonanie testu „{0}” zostało przerwane. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pt-BR.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pt-BR.xlf index 6b1245585..795eca5a8 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pt-BR.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.pt-BR.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Teste '{0}' ultrapassou o período de tempo limite de execução. - - - - - Running tests in any of the provided sources is not supported for the selected platform - Não há suporte para execução de teste em qualquer uma das origens fontes fornecidas para a plataforma selecionada - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - O método TestCleanup {0}.{1} gerou exceção. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Fim do rastreamento de pilha de exceção interna --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: não é possível definir mais de um método com o atributo AssemblyCleanup em um assembly. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: não é possível definir mais de um método com o atributo AssemblyInitialize dentro de um assembly. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: não é possível definir mais de um método com o atributo ClassCleanup dentro de uma classe. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: não é possível definir mais de um método com o atributo ClassInitialize em uma classe. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: não é possível definir mais de um método com o atributo TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: não é possível definir mais de um método com o atributo TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - O método de inicialização {0}.{1} gerou exceção. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Não é possível criar instância da classe {0}. Erro: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Não é definir a propriedade TestContext para a classe {0}. Erro: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Falha ao obter a mensagem para uma exceção do tipo {0} devido a uma exceção.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: classe {0} não tem propriedade TestContext válida. TestContext deve ser de tipo TestContext, deve ser não estático, público e não deve ser somente leitura. Por exemplo: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: atributo TestClass definido em classe não pública {0} - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - O MSTestAdapter não conseguiu descobrir testes na classe '{0}' do assembly '{1}' devido a {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Não é possível carregar tipos da fonte de teste '{0}'. Alguns ou todos os testes nessa fonte podem não ser descobertos. -Erro: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: um método genérico não pode ser um método de teste. {0}.{1} tem assinatura inválida - - - - - The parameter should not be null or empty. - O parâmetro não deve ser nulo ou vazio. - - - - - The parameter must be greater than zero. - O parâmetro deve ser maior que zero. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter não conseguiu descobrir testes na classe '{0}' do assembly '{1}'. Motivo {2}. - - - - - File does not exist: {0} - O arquivo não existe: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: o método {1} definido na classe {0} não tem assinatura correta. O método de teste marcado com o atributo [TestMethod] deve ser não estático, público, com tipo de retorno nulo e não deve receber parâmetros. Exemplo: public void Test.Class1.Test(). Adicionalmente, se estiver usando async-await no método de teste então o tipo de retorno deve ser Tarefa. Exemplo: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext não pode ser Nulo. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Falha no método de Limpeza de Assembly {0}.{1}. Mensagem de Erro: {2}. StackTrace: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - O método de Inicialização de Assembly {0}.{1} lançou uma exceção. {2}: {3}. Anulando execução de teste. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Falha no método de Limpeza de Classe {0}.{1}. Mensagem de Erro: {2}. Rastreamento de Pilha: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - O método de Inicialização de Classe {0}.{1} lançou uma exceção. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Exceção lançada durante a execução do teste. Se usar a extensão de TestMethodAttribute, entre em contato com o fornecedor. Mensagem de erro: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Erro ao executar o teste. Nenhum resultado retornado pela extensão. Se usar a extensão de TestMethodAttribute, entre em contato com o fornecedor. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - O método {0}.{1} tem assinatura incorreta. O método deve ser estático, público, não deve retornar um valor nem receber parâmetro. Além disso, se estiver usando async-await no método, return-type deverá ser Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - O método {0}.{1} tem assinatura incorreta. O método deve ser estático, público, não deve retornar um valor e deve receber um único parâmetro do tipo TestContext. Além disso, se estiver usando async-await no método, return-type deverá ser Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} tem atributo Timeout inválido. O tempo limite deve ser um valor inteiro válido e não pode ser menor que 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: não é possível definir a propriedade predefinida {2} no método {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: A propriedade personalizada "{2}" já está definida. Usando "{3}" como valor. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: Propriedade personalizada nula ou vazia definida no método {1}. A propriedade personalizada deve ter um nome válido. - - - - - Method {0}.{1} does not exist. - O método {0}.{1} não existe. - - - - - Unable to get default constructor for class {0}. - Não é possível obter o construtor padrão para a classe {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Não é possível encontrar propriedade {0}.TestContext. Erro:{1}. - - - - - The {0}.TestContext has incorrect type. - O {0}.TestContext é do tipo incorreto. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - O método {0}.{1} tem assinatura incorreta. O método deve ser não estático, público, não deve retornar um valor e não deve receber nenhum parâmetro. Além disso, se você estiver usando um async-await no método, então return-type deverá ser Task. - - - - - Unable to get type {0}. Error: {1}. - Não é possível obter o tipo {0}. Erro: {1}. - - - - - Test method {0} was not found. - O método de teste {0} não foi encontrado. - - - - - Debug Trace: - Rastreamento de Depuração: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Falha ao obter a exceção lançada pelo método de teste {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - O método de teste {0}.{1} lançou a exceção: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} Para projetos UWP, se você está usando objetos de IU no teste, considere usar o atributo [UITestMethod] em vez de [TestMethod] para executar o teste no thread da IU. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Configurações inválidas '{0}'. XmlAttribute inesperado: '{1}'. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Configurações inválidas '{0}'. XmlElement inesperado: '{1}'. - - - - - {0} (Data Row {1}) - {0} (Linha de Dados {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - O atributo ExpectedException definido no método de teste {0}.{1} emitiu uma exceção durante a construção. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - O método de teste {0}.{1} tem vários atributos derivados de ExpectedExceptionBaseAttribute definidos nele. Somente um atributo é permitido. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Aviso: um arquivo testsettings ou um arquivo vsmdi não tem suporte no MSTest V2 Adapter. - - - - - TestContext Messages: - Mensagens TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Erro ao chamar o método Test Cleanup para a classe de teste {0}: {1} - - - - - TestCleanup Stack Trace - Rastreamento de pilha TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Descoberta][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - MSTest Executor: paralelização de teste habilitada para {0} (Workers: {1}, Scope: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - Valor inválido '{0}' especificado para 'Scope'. Os escopos compatíveis são {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - Valor inválido '{0}' especificado para 'Workers'. O valor deve ser um inteiro não negativo. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Falha ao descobrir testes por meio do assembly {0}. Motivo: {1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Apenas os métodos de teste controlados por dados podem ter parâmetros. Você pretendia usar [DataRow] ou [DynamicData]? - - - - - Test '{0}' execution has been aborted. - A execução do teste '{0}' foi anulada. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Teste '{0}' ultrapassou o período de tempo limite de execução. + + + + Running tests in any of the provided sources is not supported for the selected platform + Não há suporte para execução de teste em qualquer uma das origens fontes fornecidas para a plataforma selecionada + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + O método TestCleanup {0}.{1} gerou exceção. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Fim do rastreamento de pilha de exceção interna --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: não é possível definir mais de um método com o atributo AssemblyCleanup em um assembly. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: não é possível definir mais de um método com o atributo AssemblyInitialize dentro de um assembly. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: não é possível definir mais de um método com o atributo ClassCleanup dentro de uma classe. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: não é possível definir mais de um método com o atributo ClassInitialize em uma classe. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: não é possível definir mais de um método com o atributo TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: não é possível definir mais de um método com o atributo TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + O método de inicialização {0}.{1} gerou exceção. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Não é possível criar instância da classe {0}. Erro: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Não é definir a propriedade TestContext para a classe {0}. Erro: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Falha ao obter a mensagem para uma exceção do tipo {0} devido a uma exceção.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: classe {0} não tem propriedade TestContext válida. TestContext deve ser de tipo TestContext, deve ser não estático, público e não deve ser somente leitura. Por exemplo: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: atributo TestClass definido em classe não pública {0} + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + O MSTestAdapter não conseguiu descobrir testes na classe '{0}' do assembly '{1}' devido a {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Não é possível carregar tipos da fonte de teste '{0}'. Alguns ou todos os testes nessa fonte podem não ser descobertos. +Erro: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: um método genérico não pode ser um método de teste. {0}.{1} tem assinatura inválida + + + + The parameter should not be null or empty. + O parâmetro não deve ser nulo ou vazio. + + + + The parameter must be greater than zero. + O parâmetro deve ser maior que zero. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter não conseguiu descobrir testes na classe '{0}' do assembly '{1}'. Motivo {2}. + + + + File does not exist: {0} + O arquivo não existe: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: o método {1} definido na classe {0} não tem assinatura correta. O método de teste marcado com o atributo [TestMethod] deve ser não estático, público, com tipo de retorno nulo e não deve receber parâmetros. Exemplo: public void Test.Class1.Test(). Adicionalmente, se estiver usando async-await no método de teste então o tipo de retorno deve ser Tarefa. Exemplo: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext não pode ser Nulo. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Falha no método de Limpeza de Assembly {0}.{1}. Mensagem de Erro: {2}. StackTrace: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + O método de Inicialização de Assembly {0}.{1} lançou uma exceção. {2}: {3}. Anulando execução de teste. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Falha no método de Limpeza de Classe {0}.{1}. Mensagem de Erro: {2}. Rastreamento de Pilha: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + O método de Inicialização de Classe {0}.{1} lançou uma exceção. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Exceção lançada durante a execução do teste. Se usar a extensão de TestMethodAttribute, entre em contato com o fornecedor. Mensagem de erro: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Erro ao executar o teste. Nenhum resultado retornado pela extensão. Se usar a extensão de TestMethodAttribute, entre em contato com o fornecedor. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + O método {0}.{1} tem assinatura incorreta. O método deve ser estático, público, não deve retornar um valor nem receber parâmetro. Além disso, se estiver usando async-await no método, return-type deverá ser Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + O método {0}.{1} tem assinatura incorreta. O método deve ser estático, público, não deve retornar um valor e deve receber um único parâmetro do tipo TestContext. Além disso, se estiver usando async-await no método, return-type deverá ser Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} tem atributo Timeout inválido. O tempo limite deve ser um valor inteiro válido e não pode ser menor que 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: não é possível definir a propriedade predefinida {2} no método {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: A propriedade personalizada "{2}" já está definida. Usando "{3}" como valor. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: Propriedade personalizada nula ou vazia definida no método {1}. A propriedade personalizada deve ter um nome válido. + + + + Method {0}.{1} does not exist. + O método {0}.{1} não existe. + + + + Unable to get default constructor for class {0}. + Não é possível obter o construtor padrão para a classe {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + Não é possível encontrar propriedade {0}.TestContext. Erro:{1}. + + + + The {0}.TestContext has incorrect type. + O {0}.TestContext é do tipo incorreto. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + O método {0}.{1} tem assinatura incorreta. O método deve ser não estático, público, não deve retornar um valor e não deve receber nenhum parâmetro. Além disso, se você estiver usando um async-await no método, então return-type deverá ser Task. + + + + Unable to get type {0}. Error: {1}. + Não é possível obter o tipo {0}. Erro: {1}. + + + + Test method {0} was not found. + O método de teste {0} não foi encontrado. + + + + Debug Trace: + Rastreamento de Depuração: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Falha ao obter a exceção lançada pelo método de teste {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + O método de teste {0}.{1} lançou a exceção: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} Para projetos UWP, se você está usando objetos de IU no teste, considere usar o atributo [UITestMethod] em vez de [TestMethod] para executar o teste no thread da IU. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Configurações inválidas '{0}'. XmlAttribute inesperado: '{1}'. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Configurações inválidas '{0}'. XmlElement inesperado: '{1}'. + + + + {0} (Data Row {1}) + {0} (Linha de Dados {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + O atributo ExpectedException definido no método de teste {0}.{1} emitiu uma exceção durante a construção. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + O método de teste {0}.{1} tem vários atributos derivados de ExpectedExceptionBaseAttribute definidos nele. Somente um atributo é permitido. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Aviso: um arquivo testsettings ou um arquivo vsmdi não tem suporte no MSTest V2 Adapter. + + + + TestContext Messages: + Mensagens TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Erro ao chamar o método Test Cleanup para a classe de teste {0}: {1} + + + + TestCleanup Stack Trace + Rastreamento de pilha TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Descoberta][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + MSTest Executor: paralelização de teste habilitada para {0} (Workers: {1}, Scope: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + Valor inválido '{0}' especificado para 'Scope'. Os escopos compatíveis são {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + Valor inválido '{0}' especificado para 'Workers'. O valor deve ser um inteiro não negativo. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Falha ao descobrir testes por meio do assembly {0}. Motivo: {1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Apenas os métodos de teste controlados por dados podem ter parâmetros. Você pretendia usar [DataRow] ou [DynamicData]? + + + + Test '{0}' execution has been aborted. + A execução do teste '{0}' foi anulada. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ru.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ru.xlf index 73891d57b..f37f6892a 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ru.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.ru.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - Превышено время ожидания выполнения теста "{0}". - - - - - Running tests in any of the provided sources is not supported for the selected platform - Запуск тестов в любом из предоставленных источников не поддерживается на выбранной платформе - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - Метод TestCleanup {0}.{1} вызвал исключение. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- Конец трассировки стека внутренних исключений --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: в сборке невозможно определить несколько методов с атрибутом AssemblyCleanup. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: в сборке невозможно определить несколько методов с атрибутом AssemblyInitialize. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: в классе невозможно определить несколько методов с атрибутом ClassCleanup. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: в классе невозможно определить несколько методов с атрибутом ClassInitialize. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: невозможно определить несколько методов с атрибутом TestCleanup. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: невозможно определить несколько методов с атрибутом TestInitialize. - - - - - Initialization method {0}.{1} threw exception. {2}. - Метод инициализации {0}.{1} вызвал исключение. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - Не удалось создать экземпляр класса {0}. Ошибка: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - Не удалось задать свойство TestContext для класса {0}. Ошибка: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Не удалось получить сообщение для исключения с типом {0} в связи с возникновением исключения.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: в классе {0} отсутствует допустимое свойство TestContext. Свойство TestContext должно иметь тип TestContext, быть нестатическим, открытым и не должно быть предназначено только для чтения. Например: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: атрибут TestClass определен в классе {0}, не являющемся открытым - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - Средству MSTestAdapter не удалось обнаружить тесты в классе "{0}" сборки "{1}", так как {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - Не удалось загрузить типы из тестового источника "{0}". В этом источнике могут быть не обнаружены некоторые или все тесты. -Ошибка: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: универсальный метод не может быть методом теста. {0}.{1} имеет недопустимую сигнатуру - - - - - The parameter should not be null or empty. - Этот параметр не должен быть пустым или иметь значение NULL. - - - - - The parameter must be greater than zero. - Этот параметр должен быть больше нуля. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - Средству MSTestAdapter не удалось обнаружить тесты в классе "{0}" сборки "{1}". Причина: {2}. - - - - - File does not exist: {0} - Файл не существует: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: метод {1}, определенный в классе {0}, имеет неправильную сигнатуру. Метод теста, помеченный атрибутом [TestMethod], должен быть нестатическим, открытым и иметь тип возвращаемого значения void; он также не должен принимать параметры. Пример: public void Test.Class1.Test(). Кроме того, если вы используете модификатор async-await в методе теста, тип возвращаемого значения должен быть Task. Пример: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext не может иметь значение NULL. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Не удалось применить метод очистки сборки {0}.{1}. Сообщение об ошибке: {2}. Трассировка стека (StackTrace): {3}. - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Методом инициализации сборки {0}.{1} создано исключение. {2}: {3}. Выполнение теста прекращается. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Не удалось применить метод очистки класса {0}.{1}. Сообщение об ошибке: {2}. Трассировка стека: {3}. - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Методом инициализации класса {0}.{1} создано исключение. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - При выполнении теста возникло исключение. Если используется расширение атрибута TestMethodAttribute, обратитесь к поставщику. Сообщение об ошибке: {0}. - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Ошибка при выполнении теста. Расширение не возвратило результаты. Если используется расширение атрибута TestMethodAttribute, обратитесь к поставщику. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть статическим и открытым, не должен возвращать значение и принимать параметры. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть статическим и открытым, не должен возвращать значение и должен принимать один параметр, имеющий тип TestContext. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} имеет недопустимый атрибут Timeout. Время ожидания должно быть допустимым целым числом и не может быть меньше 0. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: не удается определить предопределенное свойство {2} в методе {1}. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: пользовательское свойство "{2}" уже определено. В качестве значения используется "{3}". - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: в методе {1} определено пользовательское свойство, имя которого имеет значение NULL или пусто. Пользовательское свойство должно иметь допустимое имя. - - - - - Method {0}.{1} does not exist. - Метод {0}.{1} не существует. - - - - - Unable to get default constructor for class {0}. - Не удается получить конструктор по умолчанию для класса {0}. - - - - - Unable to find property {0}.TestContext. Error:{1}. - Не удается найти свойство {0}.TestContext. Ошибка: {1}. - - - - - The {0}.TestContext has incorrect type. - Для свойства {0}.TestContext указан неправильный тип. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть нестатическим и открытым, не должен возвращать значение и принимать параметры. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. - - - - - Unable to get type {0}. Error: {1}. - Не удается получить тип {0}. Ошибка: {1}. - - - - - Test method {0} was not found. - Метод теста {0} не найден. - - - - - Debug Trace: - Трассировка отладки: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - Не удалось получить исключение, созданное методом теста {0}.{1}. - - - - - Test method {0}.{1} threw exception: -{2} - Метод теста {0}.{1} создал исключение: -{2}. - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} В проектах UWP, если в тесте используются объекты пользовательского интерфейса, рассмотрите возможность использования атрибута [UITestMethod] вместо атрибута [TestMethod] для выполнения теста в потоке пользовательского интерфейса. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Недопустимые параметры "{0}". Непредвиденный атрибут XmlAttribute: "{1}". - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Недопустимые параметры "{0}". Непредвиденный элемент XmlElement: "{1}". - - - - - {0} (Data Row {1}) - {0} (строка данных {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - Атрибут ExpectedException, определенный в методе теста {0}.{1}, породил исключение во время создания. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - В методе теста {0}.{1} определено несколько атрибутов, производных от ExpectedExceptionBaseAttribute, заданного в нем. Допускается только один такой атрибут. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Внимание! Адаптер MSTest версии 2 не поддерживает файл TESTSETTINGS или VSMDI. - - - - - TestContext Messages: - Сообщения TestContext: - - - - - Error calling Test Cleanup method for test class {0}: {1} - Ошибка при вызове метода TestCleanup для тестового класса {0}: {1} - - - - - TestCleanup Stack Trace - Трассировка стека TestCleanup - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - Исполнитель MSTest: включена параллелизация тестов для {0} (рабочие роли: {1}, область: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - В поле "Область" указано недопустимое значение "{0}". Поддерживаемые области: {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - В поле "Рабочие роли" указано недопустимое значение "{0}". Оно должно быть неотрицательным целым числом. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - Не удалось обнаружить тесты из сборки {0}. Причина:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Только методы теста, управляемые данными, могут иметь параметры. Вы планировали использовать [DataRow] или [DynamicData]? - - - - - Test '{0}' execution has been aborted. - Выполнение теста "{0}" было прервано. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + Превышено время ожидания выполнения теста "{0}". + + + + Running tests in any of the provided sources is not supported for the selected platform + Запуск тестов в любом из предоставленных источников не поддерживается на выбранной платформе + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + Метод TestCleanup {0}.{1} вызвал исключение. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- Конец трассировки стека внутренних исключений --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: в сборке невозможно определить несколько методов с атрибутом AssemblyCleanup. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: в сборке невозможно определить несколько методов с атрибутом AssemblyInitialize. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: в классе невозможно определить несколько методов с атрибутом ClassCleanup. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: в классе невозможно определить несколько методов с атрибутом ClassInitialize. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: невозможно определить несколько методов с атрибутом TestCleanup. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: невозможно определить несколько методов с атрибутом TestInitialize. + + + + Initialization method {0}.{1} threw exception. {2}. + Метод инициализации {0}.{1} вызвал исключение. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + Не удалось создать экземпляр класса {0}. Ошибка: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + Не удалось задать свойство TestContext для класса {0}. Ошибка: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Не удалось получить сообщение для исключения с типом {0} в связи с возникновением исключения.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: в классе {0} отсутствует допустимое свойство TestContext. Свойство TestContext должно иметь тип TestContext, быть нестатическим, открытым и не должно быть предназначено только для чтения. Например: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: атрибут TestClass определен в классе {0}, не являющемся открытым + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + Средству MSTestAdapter не удалось обнаружить тесты в классе "{0}" сборки "{1}", так как {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + Не удалось загрузить типы из тестового источника "{0}". В этом источнике могут быть не обнаружены некоторые или все тесты. +Ошибка: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: универсальный метод не может быть методом теста. {0}.{1} имеет недопустимую сигнатуру + + + + The parameter should not be null or empty. + Этот параметр не должен быть пустым или иметь значение NULL. + + + + The parameter must be greater than zero. + Этот параметр должен быть больше нуля. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + Средству MSTestAdapter не удалось обнаружить тесты в классе "{0}" сборки "{1}". Причина: {2}. + + + + File does not exist: {0} + Файл не существует: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: метод {1}, определенный в классе {0}, имеет неправильную сигнатуру. Метод теста, помеченный атрибутом [TestMethod], должен быть нестатическим, открытым и иметь тип возвращаемого значения void; он также не должен принимать параметры. Пример: public void Test.Class1.Test(). Кроме того, если вы используете модификатор async-await в методе теста, тип возвращаемого значения должен быть Task. Пример: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext не может иметь значение NULL. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Не удалось применить метод очистки сборки {0}.{1}. Сообщение об ошибке: {2}. Трассировка стека (StackTrace): {3}. + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Методом инициализации сборки {0}.{1} создано исключение. {2}: {3}. Выполнение теста прекращается. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Не удалось применить метод очистки класса {0}.{1}. Сообщение об ошибке: {2}. Трассировка стека: {3}. + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Методом инициализации класса {0}.{1} создано исключение. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + При выполнении теста возникло исключение. Если используется расширение атрибута TestMethodAttribute, обратитесь к поставщику. Сообщение об ошибке: {0}. + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Ошибка при выполнении теста. Расширение не возвратило результаты. Если используется расширение атрибута TestMethodAttribute, обратитесь к поставщику. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть статическим и открытым, не должен возвращать значение и принимать параметры. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть статическим и открытым, не должен возвращать значение и должен принимать один параметр, имеющий тип TestContext. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} имеет недопустимый атрибут Timeout. Время ожидания должно быть допустимым целым числом и не может быть меньше 0. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: не удается определить предопределенное свойство {2} в методе {1}. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: пользовательское свойство "{2}" уже определено. В качестве значения используется "{3}". + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: в методе {1} определено пользовательское свойство, имя которого имеет значение NULL или пусто. Пользовательское свойство должно иметь допустимое имя. + + + + Method {0}.{1} does not exist. + Метод {0}.{1} не существует. + + + + Unable to get default constructor for class {0}. + Не удается получить конструктор по умолчанию для класса {0}. + + + + Unable to find property {0}.TestContext. Error:{1}. + Не удается найти свойство {0}.TestContext. Ошибка: {1}. + + + + The {0}.TestContext has incorrect type. + Для свойства {0}.TestContext указан неправильный тип. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + Метод {0}.{1} имеет неправильную сигнатуру. Метод должен быть нестатическим и открытым, не должен возвращать значение и принимать параметры. Кроме того, при использовании в методе async-await возвращаемое значение должно иметь тип Task. + + + + Unable to get type {0}. Error: {1}. + Не удается получить тип {0}. Ошибка: {1}. + + + + Test method {0} was not found. + Метод теста {0} не найден. + + + + Debug Trace: + Трассировка отладки: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + Не удалось получить исключение, созданное методом теста {0}.{1}. + + + + Test method {0}.{1} threw exception: +{2} + Метод теста {0}.{1} создал исключение: +{2}. + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} В проектах UWP, если в тесте используются объекты пользовательского интерфейса, рассмотрите возможность использования атрибута [UITestMethod] вместо атрибута [TestMethod] для выполнения теста в потоке пользовательского интерфейса. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Недопустимые параметры "{0}". Непредвиденный атрибут XmlAttribute: "{1}". + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Недопустимые параметры "{0}". Непредвиденный элемент XmlElement: "{1}". + + + + {0} (Data Row {1}) + {0} (строка данных {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + Атрибут ExpectedException, определенный в методе теста {0}.{1}, породил исключение во время создания. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + В методе теста {0}.{1} определено несколько атрибутов, производных от ExpectedExceptionBaseAttribute, заданного в нем. Допускается только один такой атрибут. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Внимание! Адаптер MSTest версии 2 не поддерживает файл TESTSETTINGS или VSMDI. + + + + TestContext Messages: + Сообщения TestContext: + + + + Error calling Test Cleanup method for test class {0}: {1} + Ошибка при вызове метода TestCleanup для тестового класса {0}: {1} + + + + TestCleanup Stack Trace + Трассировка стека TestCleanup + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + Исполнитель MSTest: включена параллелизация тестов для {0} (рабочие роли: {1}, область: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + В поле "Область" указано недопустимое значение "{0}". Поддерживаемые области: {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + В поле "Рабочие роли" указано недопустимое значение "{0}". Оно должно быть неотрицательным целым числом. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + Не удалось обнаружить тесты из сборки {0}. Причина:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Только методы теста, управляемые данными, могут иметь параметры. Вы планировали использовать [DataRow] или [DynamicData]? + + + + Test '{0}' execution has been aborted. + Выполнение теста "{0}" было прервано. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.tr.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.tr.xlf index 205021e36..3906031eb 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.tr.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.tr.xlf @@ -1,407 +1,343 @@ - - - - - - Test '{0}' exceeded execution timeout period. - '{0}' testi yürütme zaman aşımı süresini aştı. - - - - - Running tests in any of the provided sources is not supported for the selected platform - Testlerin sağlanan kaynakların herhangi birinde çalıştırılması seçili platformda desteklenmiyor - - - - - TestCleanup method {0}.{1} threw exception. {2}: {3}. - TestCleanup metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. - - - - - --- End of inner exception stack trace --- - --- İç özel durum yığın izlemesinin sonu --- - - - - - UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. - UTA014: {0}: Bir bütünleştirilmiş kod içinde AssemblyCleanup özniteliği ile birden fazla metot tanımlanamaz. - - - - - UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. - UTA013: {0}: Bir bütünleştirilmiş kod içinde AssemblyInitialize özniteliği ile birden fazla metot tanımlanamaz. - - - - - UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. - UTA026: {0}: Bir sınıf içinde ClassCleanup özniteliği ile birden fazla metot tanımlanamaz. - - - - - UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. - UTA025: {0}: Bir sınıf içinde ClassInitialize özniteliği ile birden fazla metot tanımlanamaz. - - - - - UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. - UTA024: {0}: TestCleanup özniteliği ile birden fazla metot tanımlanamaz. - - - - - UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. - UTA018: {0}: TestInitialize özniteliği ile birden fazla metot tanımlanamaz. - - - - - Initialization method {0}.{1} threw exception. {2}. - Başlatma metodu {0}.{1} özel durum oluşturdu. {2}. - - - - - Unable to create instance of class {0}. Error: {1}. - {0} sınıfının örneği oluşturulamıyor. Hata: {1}. - - - - - Unable to set TestContext property for the class {0}. Error: {1}. - {0} sınıfı için TestContext özelliği ayarlanamıyor. Hata: {1}. - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Bir özel durum nedeniyle, {0} türündeki özel durum iletisi alınamadı.) - - - - - UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. - UTA031: {0} sınıfı geçerli bir TestContext özelliğine sahip değil. TestContext, TestContext türünde olmalı, statik olmamalı, genel olmalı ve salt okunur olmamalı. Örnek: public TestContext TestContext. - - - - - UTA001: TestClass attribute defined on non-public class {0} - UTA001: TestClass özniteliği genel olmayan {0} sınıfında tanımlanmış - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. - MSTestAdapter, '{1}' bütünleştirilmiş kodunun '{0}' sınıfındaki testleri bulamadı. Nedeni: {2}. - - - - - {0}: {1} - {0}: {1} - - - - - Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. -Error: {1} - '{0}' test kaynağından türler yüklenemiyor. Kaynaktaki testlerin bazıları veya tümü bulunamayabilir. -Hata: {1} - - - - - UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature - UTA015: Genel metot bir test metodu olamaz. {0}.{1} geçersiz imzaya sahip - - - - - The parameter should not be null or empty. - Parametre null veya boş olmamalıdır. - - - - - The parameter must be greater than zero. - Parametre sıfırdan büyük olmalıdır. - - - - - MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. - MSTestAdapter, '{1}' bütünleştirilmiş kodunun '{0}' sınıfında testleri bulamadı. Nedeni: {2}. - - - - - File does not exist: {0} - Dosya yok: {0} - - - - - UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() - UTA007: {0} sınıfında tanımlanan {1} metodunun imzası doğru değil. [TestMethod] özniteliğiyle işaretlenen test metodu statik olmamalı, genel olmalı, return-type değeri void olmalı ve hiçbir parametre almamalıdır. Örnek: public void Test.Class1.Test(). Bunlara ek olarak, test metodunda async-await kullanıyorsanız return-type değeri Task olmalıdır. Örnek: public async Task Test.Class1.Test2() - - - - - TestContext cannot be Null. - TestContext, Null olamaz. - - - - - Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} - Bütünleştirilmiş Kod Temizleme metodu ({0}.{1}) başarısız oldu. Hata İletisi: {2}. StackTrace: {3} - - - - - Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. - Bütünleştirilmiş Kod Başlatma metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. Test yürütmesi durduruluyor. - - - - - Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} - Sınıf Temizleme metodu ({0}.{1}) başarısız oldu. Hata İletisi: {2}. Yığın İzlemesi: {3} - - - - - Class Initialization method {0}.{1} threw exception. {2}: {3}. - Sınıf Başlatma metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. - - - - - Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} - Test yürütülürken özel durum oluşturuldu. TestMethodAttribute uzantısı kullanılıyorsa, lütfen satıcıya başvurun. Hata iletisi: {0} - - - - - Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. - Test yürütülürken hata oluştu. Uzantı tarafından hiç sonuç döndürülmedi. TestMethodAttribute uzantısı kullanılıyorsa, lütfen satıcıya başvurun. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} metodunun imzası yanlış. Metot statik, genel, değer döndürmeyen bir metot olmalı, hiçbir parametre almamalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. - - - - - Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} metodunun imzası yanlış. Metot statik, genel, değer döndürmeyen bir metot olmalı ve TestContext türünde tek bir parametre almalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. - - - - - UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. - UTA054: {0}.{1} geçersiz Timeout özniteliğine sahip. Zaman aşımı geçerli bir tamsayı değer olmalıdır ve 0'dan küçük olamaz. - - - - - UTA023: {0}: Cannot define predefined property {2} on method {1}. - UTA023: {0}: Önceden tanımlanmış {2} özelliği {1} metodunda tanımlanamaz. - - - - - UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. - UTA022: {0}.{1}: "{2}" özel özelliği zaten tanımlanmış. Değer olarak "{3}" kullanılıyor. - - - - - UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. - UTA021: {0}: {1} metodunda null veya boş özel özellik tanımlanmış. Özel özellik geçerli bir ada sahip olmalıdır. - - - - - Method {0}.{1} does not exist. - {0}.{1} metodu yok. - - - - - Unable to get default constructor for class {0}. - {0} sınıfı için varsayılan oluşturucu alınamıyor. - - - - - Unable to find property {0}.TestContext. Error:{1}. - {0}.TestContext özelliği bulunamıyor. Hata:{1}. - - - - - The {0}.TestContext has incorrect type. - {0}.TestContext yanlış türe sahip. - - - - - Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. - {0}.{1} metodunun imzası yanlış. Metot statik olmayan, genel, değer döndürmeyen bir metot olmalı, hiçbir parametre almamalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. - - - - - Unable to get type {0}. Error: {1}. - {0} türü alınamıyor. Hata: {1}. - - - - - Test method {0} was not found. - {0} test metodu bulunamadı. - - - - - Debug Trace: - Hata Ayıklama İzleyici: - - - - - Failed to obtain the exception thrown by test method {0}.{1}. - {0}.{1} metodu tarafından oluşturulan özel durum alınamadı. - - - - - Test method {0}.{1} threw exception: -{2} - {0}.{1} test metodu özel durum oluşturdu: -{2} - - - - - {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. - {0} UWP projeleri için testte UI nesneleri kullanıyorsanız, testi UI iş parçacığında yürütmek için [TestMethod] yerine [UITestMethod] özniteliğini kullanabilirsiniz. - - - - - MSTestAdapterV2 - MSTestAdapterV2 - - - - - Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. - Geçersiz '{0}' ayarları. Beklenmeyen XmlAttribute: '{1}'. - - - - - Invalid settings '{0}'. Unexpected XmlElement: '{1}'. - Geçersiz '{0}' ayarları. Beklenmeyen XmlElement: '{1}'. - - - - - {0} (Data Row {1}) - {0} (Veri Satırı {1}) - - - - - The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. -{2} - {0}.{1} test yöntemi üzerinde tanımlanan ExpectedException özniteliği, oluşturma sırasında bir özel durum oluşturdu. -{2} - - - - - The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. - {0}.{1} test yöntemi, üzerinde tanımlanan ExpectedExceptionBaseAttribute öğesinden türetilmiş birden fazla öznitelik içeriyor. Bu türde yalnızca bir tane özniteliğe izin verilir. - - - - - Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. - Uyarı : MSTest V2 Adapter ile bir testsettings dosyası veya bir vsmdi dosyası desteklenmez. - - - - - TestContext Messages: - TestContext İletileri: - - - - - Error calling Test Cleanup method for test class {0}: {1} - {0} test sınıfı için Test Temizleme metodu çağrılırken hata oluştu: {1} - - - - - TestCleanup Stack Trace - TestCleanup Yığın İzleme - - - - - [MSTest][Discovery][{0}] {1} - [MSTest][Discovery][{0}] {1} - - - - - MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). - MSTest Yürütücü: {0} için Test Paralelleştirme etkin (Workers: {1}, Scope: {2}). - - - - - Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. - 'Scope' için geçersiz '{0}' değeri belirtildi. Desteklenen kapsamlar {1}. - 'Scope' is a setting name that shouldn't be localized. - - - Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. - 'Workers' için geçersiz '{0}' değeri belirtildi. Değer negatif olmayan bir tamsayı olmalıdır. - `Workers` is a setting name that shouldn't be localized. - - - Failed to discover tests from assembly {0}. Reason:{1} - {0} bütünleştirilmiş kodundan testler bulunamadı. Neden:{1} - - - - - Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? - Yalnızca veri temelli test metotları parametrelere sahip olabilir. [DataRow] veya [DynamicData] kullanmak mı istediniz? - - - - - Test '{0}' execution has been aborted. - '{0}' testinin yürütülmesi iptal edildi. - - - - - + + + + + + Test '{0}' exceeded execution timeout period. + '{0}' testi yürütme zaman aşımı süresini aştı. + + + + Running tests in any of the provided sources is not supported for the selected platform + Testlerin sağlanan kaynakların herhangi birinde çalıştırılması seçili platformda desteklenmiyor + + + + TestCleanup method {0}.{1} threw exception. {2}: {3}. + TestCleanup metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. + + + + --- End of inner exception stack trace --- + --- İç özel durum yığın izlemesinin sonu --- + + + + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. + UTA014: {0}: Bir bütünleştirilmiş kod içinde AssemblyCleanup özniteliği ile birden fazla metot tanımlanamaz. + + + + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. + UTA013: {0}: Bir bütünleştirilmiş kod içinde AssemblyInitialize özniteliği ile birden fazla metot tanımlanamaz. + + + + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. + UTA026: {0}: Bir sınıf içinde ClassCleanup özniteliği ile birden fazla metot tanımlanamaz. + + + + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. + UTA025: {0}: Bir sınıf içinde ClassInitialize özniteliği ile birden fazla metot tanımlanamaz. + + + + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. + UTA024: {0}: TestCleanup özniteliği ile birden fazla metot tanımlanamaz. + + + + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. + UTA018: {0}: TestInitialize özniteliği ile birden fazla metot tanımlanamaz. + + + + Initialization method {0}.{1} threw exception. {2}. + Başlatma metodu {0}.{1} özel durum oluşturdu. {2}. + + + + Unable to create instance of class {0}. Error: {1}. + {0} sınıfının örneği oluşturulamıyor. Hata: {1}. + + + + Unable to set TestContext property for the class {0}. Error: {1}. + {0} sınıfı için TestContext özelliği ayarlanamıyor. Hata: {1}. + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Bir özel durum nedeniyle, {0} türündeki özel durum iletisi alınamadı.) + + + + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. + UTA031: {0} sınıfı geçerli bir TestContext özelliğine sahip değil. TestContext, TestContext türünde olmalı, statik olmamalı, genel olmalı ve salt okunur olmamalı. Örnek: public TestContext TestContext. + + + + UTA001: TestClass attribute defined on non-public class {0} + UTA001: TestClass özniteliği genel olmayan {0} sınıfında tanımlanmış + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. + MSTestAdapter, '{1}' bütünleştirilmiş kodunun '{0}' sınıfındaki testleri bulamadı. Nedeni: {2}. + + + + {0}: {1} + {0}: {1} + + + + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. +Error: {1} + '{0}' test kaynağından türler yüklenemiyor. Kaynaktaki testlerin bazıları veya tümü bulunamayabilir. +Hata: {1} + + + + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature + UTA015: Genel metot bir test metodu olamaz. {0}.{1} geçersiz imzaya sahip + + + + The parameter should not be null or empty. + Parametre null veya boş olmamalıdır. + + + + The parameter must be greater than zero. + Parametre sıfırdan büyük olmalıdır. + + + + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. + MSTestAdapter, '{1}' bütünleştirilmiş kodunun '{0}' sınıfında testleri bulamadı. Nedeni: {2}. + + + + File does not exist: {0} + Dosya yok: {0} + + + + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() + UTA007: {0} sınıfında tanımlanan {1} metodunun imzası doğru değil. [TestMethod] özniteliğiyle işaretlenen test metodu statik olmamalı, genel olmalı, return-type değeri void olmalı ve hiçbir parametre almamalıdır. Örnek: public void Test.Class1.Test(). Bunlara ek olarak, test metodunda async-await kullanıyorsanız return-type değeri Task olmalıdır. Örnek: public async Task Test.Class1.Test2() + + + + TestContext cannot be Null. + TestContext, Null olamaz. + + + + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} + Bütünleştirilmiş Kod Temizleme metodu ({0}.{1}) başarısız oldu. Hata İletisi: {2}. StackTrace: {3} + + + + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. + Bütünleştirilmiş Kod Başlatma metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. Test yürütmesi durduruluyor. + + + + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} + Sınıf Temizleme metodu ({0}.{1}) başarısız oldu. Hata İletisi: {2}. Yığın İzlemesi: {3} + + + + Class Initialization method {0}.{1} threw exception. {2}: {3}. + Sınıf Başlatma metodu ({0}.{1}) özel durum oluşturdu. {2}: {3}. + + + + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} + Test yürütülürken özel durum oluşturuldu. TestMethodAttribute uzantısı kullanılıyorsa, lütfen satıcıya başvurun. Hata iletisi: {0} + + + + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. + Test yürütülürken hata oluştu. Uzantı tarafından hiç sonuç döndürülmedi. TestMethodAttribute uzantısı kullanılıyorsa, lütfen satıcıya başvurun. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} metodunun imzası yanlış. Metot statik, genel, değer döndürmeyen bir metot olmalı, hiçbir parametre almamalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. + + + + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} metodunun imzası yanlış. Metot statik, genel, değer döndürmeyen bir metot olmalı ve TestContext türünde tek bir parametre almalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. + + + + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. + UTA054: {0}.{1} geçersiz Timeout özniteliğine sahip. Zaman aşımı geçerli bir tamsayı değer olmalıdır ve 0'dan küçük olamaz. + + + + UTA023: {0}: Cannot define predefined property {2} on method {1}. + UTA023: {0}: Önceden tanımlanmış {2} özelliği {1} metodunda tanımlanamaz. + + + + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. + UTA022: {0}.{1}: "{2}" özel özelliği zaten tanımlanmış. Değer olarak "{3}" kullanılıyor. + + + + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. + UTA021: {0}: {1} metodunda null veya boş özel özellik tanımlanmış. Özel özellik geçerli bir ada sahip olmalıdır. + + + + Method {0}.{1} does not exist. + {0}.{1} metodu yok. + + + + Unable to get default constructor for class {0}. + {0} sınıfı için varsayılan oluşturucu alınamıyor. + + + + Unable to find property {0}.TestContext. Error:{1}. + {0}.TestContext özelliği bulunamıyor. Hata:{1}. + + + + The {0}.TestContext has incorrect type. + {0}.TestContext yanlış türe sahip. + + + + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. + {0}.{1} metodunun imzası yanlış. Metot statik olmayan, genel, değer döndürmeyen bir metot olmalı, hiçbir parametre almamalıdır. Bunlara ek olarak, metotta async-await kullanıyorsanız return-type değeri Task olmalıdır. + + + + Unable to get type {0}. Error: {1}. + {0} türü alınamıyor. Hata: {1}. + + + + Test method {0} was not found. + {0} test metodu bulunamadı. + + + + Debug Trace: + Hata Ayıklama İzleyici: + + + + Failed to obtain the exception thrown by test method {0}.{1}. + {0}.{1} metodu tarafından oluşturulan özel durum alınamadı. + + + + Test method {0}.{1} threw exception: +{2} + {0}.{1} test metodu özel durum oluşturdu: +{2} + + + + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. + {0} UWP projeleri için testte UI nesneleri kullanıyorsanız, testi UI iş parçacığında yürütmek için [TestMethod] yerine [UITestMethod] özniteliğini kullanabilirsiniz. + + + + MSTestAdapterV2 + MSTestAdapterV2 + + + + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. + Geçersiz '{0}' ayarları. Beklenmeyen XmlAttribute: '{1}'. + + + + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. + Geçersiz '{0}' ayarları. Beklenmeyen XmlElement: '{1}'. + + + + {0} (Data Row {1}) + {0} (Veri Satırı {1}) + + + + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. +{2} + {0}.{1} test yöntemi üzerinde tanımlanan ExpectedException özniteliği, oluşturma sırasında bir özel durum oluşturdu. +{2} + + + + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. + {0}.{1} test yöntemi, üzerinde tanımlanan ExpectedExceptionBaseAttribute öğesinden türetilmiş birden fazla öznitelik içeriyor. Bu türde yalnızca bir tane özniteliğe izin verilir. + + + + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. + Uyarı : MSTest V2 Adapter ile bir testsettings dosyası veya bir vsmdi dosyası desteklenmez. + + + + TestContext Messages: + TestContext İletileri: + + + + Error calling Test Cleanup method for test class {0}: {1} + {0} test sınıfı için Test Temizleme metodu çağrılırken hata oluştu: {1} + + + + TestCleanup Stack Trace + TestCleanup Yığın İzleme + + + + [MSTest][Discovery][{0}] {1} + [MSTest][Discovery][{0}] {1} + + + + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). + MSTest Yürütücü: {0} için Test Paralelleştirme etkin (Workers: {1}, Scope: {2}). + + + + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. + 'Scope' için geçersiz '{0}' değeri belirtildi. Desteklenen kapsamlar {1}. + 'Scope' is a setting name that shouldn't be localized. + + + Invalid value '{0}' specified for 'Workers'. The value should be a non-negative integer. + 'Workers' için geçersiz '{0}' değeri belirtildi. Değer negatif olmayan bir tamsayı olmalıdır. + `Workers` is a setting name that shouldn't be localized. + + + Failed to discover tests from assembly {0}. Reason:{1} + {0} bütünleştirilmiş kodundan testler bulunamadı. Neden:{1} + + + + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? + Yalnızca veri temelli test metotları parametrelere sahip olabilir. [DataRow] veya [DynamicData] kullanmak mı istediniz? + + + + Test '{0}' execution has been aborted. + '{0}' testinin yürütülmesi iptal edildi. + + + + \ No newline at end of file diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hans.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hans.xlf index e44f789cd..bf78fc768 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hans.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hans.xlf @@ -5,374 +5,313 @@ Test '{0}' exceeded execution timeout period. 测试“{0}”的执行超时。 - - + Running tests in any of the provided sources is not supported for the selected platform 选定的平台不支持在任何提供的源中运行测试 - - + TestCleanup method {0}.{1} threw exception. {2}: {3}. TestCleanup 方法 {0}。{1} 引发异常。{2}: {3}。 - - + --- End of inner exception stack trace --- ---内部异常堆栈跟踪结束--- - - + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. UTA014: {0}: 在一个程序集内部,不能定义多个具有 AssemblyCleanup 特性的方法。 - - + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. UTA013: {0}: 在一个程序集内部,不能定义多个具有 AssemblyInitialize 特性的方法。 - - + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. UTA026: {0}: 在一个类内部,不能定义多个具有 ClassCleanup 特性的方法。 - - + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. UTA025: {0}: 在一个类内部,不能定义多个具有 ClassInitialize 特性的方法。 - - + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. UTA024: {0}: 不能定义多个具有 TestCleanup 特性的方法。 - - + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. UTA018: {0}: 不能定义多个具有 TestInitialize 特性的方法。 - - + Initialization method {0}.{1} threw exception. {2}. 初始化方法 {0}.{1} 引发异常。{2}。 - - + Unable to create instance of class {0}. Error: {1}. 无法创建类 {0} 的实例。错误: {1}。 - - + Unable to set TestContext property for the class {0}. Error: {1}. 无法设置类 {0} 的 TestContext 属性。错误: {1}。 - - + (Failed to get the message for an exception of type {0} due to an exception.) (因异常而未能获取类型为 {0} 的异常的消息。) - - + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. UTA031: 类 {0} 没有有效的 TestContext 属性。TestContext 的类型必须为 TestContext,必须是非静态的、公共的而且不能为只读。例如: public TestContext TestContext。 - - + UTA001: TestClass attribute defined on non-public class {0} UTA001: 在非公共类 {0} 上定义的 TestClass 特性 - - + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. 由于 {2},MSTestAdapter 未能在程序集“{1}”的类“{0}”中发现测试。 - - + {0}: {1} {0}: {1} - - + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. Error: {1} 无法从测试源“{0}”加载类型。可能无法发现此源中的部分或所有测试。 错误: {1} - - + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature UTA015: 泛型方法不可为测试方法。{0}.{1} 具有无效签名 - - + The parameter should not be null or empty. 参数不应为 NULL 或为空。 - - + The parameter must be greater than zero. 参数必须大于零。 - - + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. MSTestAdapter 未能在程序集“{1}”的类“{0}”中发现测试。原因是 {2}。 - - + File does not exist: {0} 文件不存在: {0} - - + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() UTA007: 在类 {0} 中定义的方法 {1} 没有正确的签名。用 [TestMethod] 特性标记的测试方法必须是返回类型为 void 的非静态的公共方法,并且不应采用任何参数。示例: public void Test.Class1.Test()。此外,如果你在测试方法中使用异步等待,则返回类型必须为 Task。示例: public async Task Test.Class1.Test2() - - + TestContext cannot be Null. TestContext 不能为 NULL。 - - + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} 程序集清理方法 {0}.{1} 失败。错误消息: {2}。StackTrace: {3} - - + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. 程序集初始化方法 {0}.{1} 引发异常。{2}: {3}。正在中止测试的执行。 - - + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} 类清理方法 {0}.{1} 失败。错误消息: {2}。堆栈跟踪: {3} - - + Class Initialization method {0}.{1} threw exception. {2}: {3}. 类初始化方法 {0}.{1} 引发异常。{2}: {3}。 - - + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} 执行测试时引发了异常。如果使用的是扩展 TestMethodAttribute,请与供应商联系。错误消息: {0} - - + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. 执行测试时出错。扩展未返回任何结果。如果使用的是扩展 TestMethodAttribute ,请与供应商联系。 - - + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 具有错误的签名。该方法必须是静态的公共方法、不返回值并且不应采用任何参数。此外,如果在方法中使用同步等待,则返回类型必须为 Task。 - - + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 具有错误的签名。该方法必须是静态的公共方法、不返回值并且应采用一个 TestContext 类型的参数。此外,如果在方法中使用同步等待,则返回类型必须为 Task。 - - + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. UTA054: {0}.{1} 具有无效的 Timeout 特性。超时值必须是有效的整数值而且不能小于 0。 - - + UTA023: {0}: Cannot define predefined property {2} on method {1}. UTA023: {0}: 不能在方法 {1} 上定义预定义属性 {2}。 - - + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. UTA022: {0}.{1}: 已经定义了自定义属性“{2}”。其值为“{3}”。 - - + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. UTA021: {0}: 对方法 {1} 定义了为 NULL 或为空的自定义属性。自定义属性必须具有有效名称。 - - + Method {0}.{1} does not exist. 方法 {0}.{1} 不存在。 - - + Unable to get default constructor for class {0}. 无法获取类 {0} 的默认构造函数。 - - + Unable to find property {0}.TestContext. Error:{1}. 无法找到属性 {0}.TestContext。错误: {1}。 - - + The {0}.TestContext has incorrect type. {0}.TestContext 的类型不正确。 - - + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 具有错误的签名。该方法必须是非静态的公共方法、不返回值并且不应采用任何参数。此外,如果在方法中使用同步等待,则返回类型必须为 Task。 - - + Unable to get type {0}. Error: {1}. 无法获取类型 {0}。错误: {1}。 - - + Test method {0} was not found. 未找到测试方法 {0}。 - - + Debug Trace: 调试跟踪: - - + Failed to obtain the exception thrown by test method {0}.{1}. 未能获取测试方法 {0}.{1} 引发的异常。 - - + Test method {0}.{1} threw exception: {2} 测试方法 {0}.{1} 引发了异常: {2} - - + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. {0} 对于 UWP 项目,如果在测试中使用 UI 对象,请考虑使用 [UITestMethod] 属性代替 [TestMethod] 属性在 UI 线程中执行测试。 - - + MSTestAdapterV2 MSTestAdapterV2 - - + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. 设置“{0}”无效。意外的 XmlAttribute:“{1}”。 - - + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. 设置“{0}”无效。意外的 XmlElement:“{1}”。 - - + {0} (Data Row {1}) {0} (数据行 {1}) - - + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. {2} 测试方法 {0}.{1} 上定义的 ExpectedException 属性在构造过程中引发了一个异常。 {2} - - + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. 测试方法 {0}.{1} 具有多个在该方法上定义的 ExpectedExceptionBaseAttribute 的派生属性。仅允许一个此类属性。 - - + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. 警告: MSTest V2 适配器不支持 testsettings 文件或 vsmdi 文件。 - - + TestContext Messages: TestContext 消息: - - + Error calling Test Cleanup method for test class {0}: {1} 为测试类 {0} 调用 Test Cleanup 方法时出错: {1} - - + TestCleanup Stack Trace TestCleanup 堆栈跟踪 - - + [MSTest][Discovery][{0}] {1} [MSTest][发现][{0}] {1} - - + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). MSTest 执行程序: 为 {0} 启用测试并行化(辅助角色: {1},范围: {2})。 - - + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. @@ -387,20 +326,17 @@ Error: {1} Failed to discover tests from assembly {0}. Reason:{1} 未能发现程序集 {0} 中的测试。原因: {1} - - + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? 只有数据驱动的测试方法可具有参数。曾打算使用 [DataRow] 或 [DynamicData]? - - + Test '{0}' execution has been aborted. 已中止测试“{0}”的执行。 - - + diff --git a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hant.xlf b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hant.xlf index 2049bc642..9c9e5fcd1 100644 --- a/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hant.xlf +++ b/src/Adapter/MSTest.CoreAdapter/Resources/xlf/Resource.zh-Hant.xlf @@ -5,374 +5,313 @@ Test '{0}' exceeded execution timeout period. 測試 '{0}' 超過執行逾時期限。 - - + Running tests in any of the provided sources is not supported for the selected platform 所選取的平台不支援在任何提供的來源中執行測試 - - + TestCleanup method {0}.{1} threw exception. {2}: {3}. TestCleanup 方法 {0}.{1} 擲回例外狀況。{2}: {3}。 - - + --- End of inner exception stack trace --- --- 已到達內部例外狀況堆疊追蹤的結尾 --- - - + UTA014: {0}: Cannot define more than one method with the AssemblyCleanup attribute inside an assembly. UTA014: {0}: 組件內不可定義一個以上具有 AssemblyCleanup 屬性的方法。 - - + UTA013: {0}: Cannot define more than one method with the AssemblyInitialize attribute inside an assembly. UTA013: {0}: 組件內不可定義一個以上具有 AssemblyInitialize 屬性的方法。 - - + UTA026: {0}: Cannot define more than one method with the ClassCleanup attribute inside a class. UTA026: {0}: 類別內不可定義一個以上具有 ClassCleanup 屬性的方法。 - - + UTA025: {0}: Cannot define more than one method with the ClassInitialize attribute inside a class. UTA025: {0}: 類別內不可定義一個以上具有 ClassInitialize 屬性的方法。 - - + UTA024: {0}: Cannot define more than one method with the TestCleanup attribute. UTA024: {0}: 不可定義一個以上具有 TestCleanup 屬性的方法。 - - + UTA018: {0}: Cannot define more than one method with the TestInitialize attribute. UTA018: {0}: 不可定義一個以上具有 TestInitialize 屬性的方法。 - - + Initialization method {0}.{1} threw exception. {2}. 初始設定方法 {0}.{1} 擲回例外狀況。{2}。 - - + Unable to create instance of class {0}. Error: {1}. 無法建立類別 {0} 的執行個體。錯誤: {1}。 - - + Unable to set TestContext property for the class {0}. Error: {1}. 無法設定類別 {0} 的 TestContext 屬性。錯誤: {1}。 - - + (Failed to get the message for an exception of type {0} due to an exception.) (因為發生例外狀況,所以無法取得類型 {0} 之例外狀況的訊息。) - - + UTA031: class {0} does not have valid TestContext property. TestContext must be of type TestContext, must be non-static, public and must not be read-only. For example: public TestContext TestContext. UTA031: 類別 {0} 不具備有效的 TestContext 屬性。TestContext 必須屬於 TestContext 類型,同時必須為非靜態、公用,且不可為唯讀。例如: public TestContext TestContext。 - - + UTA001: TestClass attribute defined on non-public class {0} UTA001: 在非公用類別 {0} 上定義了 TestClass 屬性 - - + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}' because {2}. MSTestAdapter 無法在組件 '{1}' 的類別 '{0}' 中探索測試,因為 {2}。 - - + {0}: {1} {0}: {1} - - + Unable to load types from the test source '{0}'. Some or all of the tests in this source may not be discovered. Error: {1} 無法從測試來源 '{0}' 載入類型。有可能無法探索此來源中的部分或所有測試。 錯誤: {1} - - + UTA015: A generic method cannot be a test method. {0}.{1} has invalid signature UTA015: 泛型方法不可為測試方法。{0}.{1} 具有無效的簽章 - - + The parameter should not be null or empty. 參數不可為 null 或空白。 - - + The parameter must be greater than zero. 參數必須大於零。 - - + MSTestAdapter failed to discover tests in class '{0}' of assembly '{1}'. Reason {2}. MSTestAdapter 無法在組件 '{1}' 的類別 '{0}' 中探索測試。原因 {2}。 - - + File does not exist: {0} 檔案不存在: {0} - - + UTA007: Method {1} defined in class {0} does not have correct signature. Test method marked with the [TestMethod] attribute must be non-static, public, return-type as void and should not take any parameter. Example: public void Test.Class1.Test(). Additionally, if you are using async-await in test method then return-type must be Task. Example: public async Task Test.Class1.Test2() UTA007: 類別 {0} 中定義的方法 {1} 沒有正確的簽章。以 [TestMethod] 屬性標記的測試方法必須為非靜態、公用的傳回類型 void,而且不應該接受任何參數。範例: public void Test.Class1.Test()。此外,如果您在測試方法中使用 async-await,則傳回類型必須是 Task。範例: public async Task Test.Class1.Test2() - - + TestContext cannot be Null. TestContext 不可為 Null。 - - + Assembly Cleanup method {0}.{1} failed. Error Message: {2}. StackTrace: {3} 組件清除方法 {0}.{1} 失敗。錯誤訊息: {2}。堆疊追蹤: {3} - - + Assembly Initialization method {0}.{1} threw exception. {2}: {3}. Aborting test execution. 組件初始設定方法 {0}.{1} 擲回例外狀況。{2}: {3}。正在中止測試執行。 - - + Class Cleanup method {0}.{1} failed. Error Message: {2}. Stack Trace: {3} 類別清除方法 {0}.{1} 失敗。錯誤訊息: {2}。堆疊追蹤: {3} - - + Class Initialization method {0}.{1} threw exception. {2}: {3}. 類別初始設定方法 {0}.{1} 擲回例外狀況。{2}: {3}。 - - + Exception thrown while executing test. If using extension of TestMethodAttribute then please contact vendor. Error message: {0} 執行測試時擲回例外狀況。如果您使用 TestMethodAttribute 的擴充功能,請連絡廠商。錯誤訊息: {0} - - + Error in executing test. No result returned by extension. If using extension of TestMethodAttribute then please contact vendor. 執行測試時發生錯誤。擴充功能未傳回任何結果。如果您使用 TestMethodAttribute 的擴充功能,請連絡廠商。 - - + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 有錯誤的簽章。方法必須為靜態、公用、不傳回值,並且不應該接受任何參數。此外,如果您在方法中使用 async-await,則傳回類型必須是 Task。 - - + Method {0}.{1} has wrong signature. The method must be static, public, does not return a value and should take a single parameter of type TestContext. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 有錯誤的簽章。方法必須為靜態、公用、不傳回值,而且接受一個類型為 TestContext 的參數。此外,如果您在方法中使用 async-await,則傳回類型必須是 Task。 - - + UTA054: {0}.{1} has invalid Timeout attribute. The timeout must be a valid integer value and cannot be less than 0. UTA054: {0}.{1} 中具有無效的 Timeout 屬性。逾時值必須是有效的整數值,而且不可小於 0。 - - + UTA023: {0}: Cannot define predefined property {2} on method {1}. UTA023: {0}: 不可在方法 {1} 上定義預先定義的屬性 {2}。 - - + UTA022: {0}.{1}: The custom property "{2}" is already defined. Using "{3}" as value. UTA022: {0}.{1}: 自訂屬性 "{2}" 已經定義過了。請使用 "{3}" 為值。 - - + UTA021: {0}: Null or empty custom property defined on method {1}. The custom property must have a valid name. UTA021: {0}: 在方法 {1} 上定義了 Null 或空白的自訂屬性。自訂屬性的名稱必須有效。 - - + Method {0}.{1} does not exist. 方法 {0}.{1} 不存在。 - - + Unable to get default constructor for class {0}. 無法取得類別 {0} 的預設建構函式。 - - + Unable to find property {0}.TestContext. Error:{1}. 找不到屬性 {0}.TestContext。錯誤: {1}。 - - + The {0}.TestContext has incorrect type. {0}.TestContext 有不正確的類型。 - - + Method {0}.{1} has wrong signature. The method must be non-static, public, does not return a value and should not take any parameter. Additionally, if you are using async-await in method then return-type must be Task. 方法 {0}.{1} 有錯誤的簽章。方法必須為非靜態、公用、不傳回值,並且不應該接受任何參數。此外,如果您在方法中使用 async-await,則傳回類型必須是 Task。 - - + Unable to get type {0}. Error: {1}. 無法取得類型 {0}。錯誤: {1}。 - - + Test method {0} was not found. 找不到測試方法 {0}。 - - + Debug Trace: 偵錯追蹤: - - + Failed to obtain the exception thrown by test method {0}.{1}. 無法取得測試方法 {0}.{1} 所擲回的例外狀況。 - - + Test method {0}.{1} threw exception: {2} 測試方法 {0}.{1} 擲回例外狀況: {2} - - + {0} For UWP projects, if you are using UI objects in test consider using [UITestMethod] attribute instead of [TestMethod] to execute test in UI thread. {0} 針對 UWP 專案,如果您在測試中使用 UI 物件,請考慮使用 [UITestMethod] 屬性取代 [TestMethod] 在 UI 執行緒中執行測試。 - - + MSTestAdapterV2 MSTestAdapterV2 - - + Invalid settings '{0}'. Unexpected XmlAttribute: '{1}'. 設定 '{0}' 無效。未預期的 XmlAttribute: '{1}'。 - - + Invalid settings '{0}'. Unexpected XmlElement: '{1}'. 設定 '{0}' 無效。未預期的 XmlElement: '{1}'。 - - + {0} (Data Row {1}) {0} (資料列 {1}) - - + The ExpectedException attribute defined on test method {0}.{1} threw an exception during construction. {2} 測試方法 {0} 上定義的 ExpectedException 屬性。{1} 在建構期間擲回例外狀況。 {2} - - + The test method {0}.{1} has multiple attributes derived from ExpectedExceptionBaseAttribute defined on it. Only one such attribute is allowed. 測試方法 {0}。{1} 上定義了多個衍生自 ExpectedExceptionBaseAttribute 的屬性。只允許一個此類屬性。 - - + Warning : A testsettings file or a vsmdi file is not supported with the MSTest V2 Adapter. 警告: MSTest V2 配接器不支援 testsettings 檔案 vsmdi 檔案。 - - + TestContext Messages: TestContext 訊息: - - + Error calling Test Cleanup method for test class {0}: {1} 呼叫測試類別 {0} 的測試清除方法時發生錯誤: {1} - - + TestCleanup Stack Trace TestCleanup 堆疊追蹤 - - + [MSTest][Discovery][{0}] {1} [MSTest][Discovery][{0}] {1} - - + MSTest Executor: Test Parallelization enabled for {0} (Workers: {1}, Scope: {2}). MSTest 執行程式: 已為 {0} 啟用平行測試。(Workers: {1},Scope: {2})。 - - + Invalid value '{0}' specified for 'Scope'. Supported scopes are {1}. @@ -387,20 +326,17 @@ Error: {1} Failed to discover tests from assembly {0}. Reason:{1} 無法從組件 {0} 中探索測試。原因:{1} - - + Only data driven test methods can have parameters. Did you intend to use [DataRow] or [DynamicData]? 只有資料驅動的測試方法可以有參數。您想要使用的是否為 [DataRow] 或 [DynamicData]? - - + Test '{0}' execution has been aborted. 測試 '{0}' 執行已中止。 - - + diff --git a/src/Adapter/MSTest.CoreAdapter/RunConfigurationSettings.cs b/src/Adapter/MSTest.CoreAdapter/RunConfigurationSettings.cs index 86bf7829a..1a5aeb417 100644 --- a/src/Adapter/MSTest.CoreAdapter/RunConfigurationSettings.cs +++ b/src/Adapter/MSTest.CoreAdapter/RunConfigurationSettings.cs @@ -117,13 +117,12 @@ private static RunConfigurationSettings ToSettings(XmlReader reader) while (reader.NodeType == XmlNodeType.Element) { - bool result; string elementName = reader.Name.ToUpperInvariant(); switch (elementName) { case "COLLECTSOURCEINFORMATION": { - if (bool.TryParse(reader.ReadInnerXml(), out result)) + if (bool.TryParse(reader.ReadInnerXml(), out var result)) { settings.CollectSourceInformation = result; PlatformServiceProvider.Instance.AdapterTraceLogger.LogInfo( diff --git a/src/Adapter/MSTest.CoreAdapter/TestMethodFilter.cs b/src/Adapter/MSTest.CoreAdapter/TestMethodFilter.cs index afc795f50..70f033f87 100644 --- a/src/Adapter/MSTest.CoreAdapter/TestMethodFilter.cs +++ b/src/Adapter/MSTest.CoreAdapter/TestMethodFilter.cs @@ -65,8 +65,7 @@ internal ITestCaseFilterExpression GetFilterExpression(IDiscoveryContext context /// a TestProperty instance. internal TestProperty PropertyProvider(string propertyName) { - TestProperty testProperty; - this.supportedProperties.TryGetValue(propertyName, out testProperty); + this.supportedProperties.TryGetValue(propertyName, out var testProperty); Debug.Assert(testProperty != null, "Invalid property queried"); return testProperty; } @@ -81,8 +80,7 @@ internal object PropertyValueProvider(TestCase currentTest, string propertyName) { if (currentTest != null && propertyName != null) { - TestProperty testProperty; - if (this.supportedProperties.TryGetValue(propertyName, out testProperty)) + if (this.supportedProperties.TryGetValue(propertyName, out var testProperty)) { // Test case might not have defined this property. In that case GetPropertyValue() // would return default value. For filtering, if property is not defined return null. diff --git a/src/Adapter/PlatformServices.Desktop/AssemblyResolver.cs b/src/Adapter/PlatformServices.Desktop/AssemblyResolver.cs index 96c6262c5..e424b582e 100644 --- a/src/Adapter/PlatformServices.Desktop/AssemblyResolver.cs +++ b/src/Adapter/PlatformServices.Desktop/AssemblyResolver.cs @@ -81,7 +81,7 @@ public AssemblyResolver(IList directories) { if (directories == null || directories.Count == 0) { - throw new ArgumentNullException("directories"); + throw new ArgumentNullException(nameof(directories)); } this.searchDirectories = new List(directories); @@ -395,7 +395,7 @@ private Assembly OnResolveInternal(object senderAppDomain, ResolveEventArgs args { if (string.IsNullOrEmpty(args?.Name)) { - Debug.Assert(false, "AssemblyResolver.OnResolve: args.Name is null or empty."); + Debug.Fail("AssemblyResolver.OnResolve: args.Name is null or empty."); return null; } @@ -424,9 +424,7 @@ private Assembly OnResolveInternal(object senderAppDomain, ResolveEventArgs args lock (this.syncLock) { // Since both normal and reflection only cache are accessed in same block, putting only one lock should be sufficient. - Assembly assembly = null; - - if (this.TryLoadFromCache(assemblyNameToLoad, isReflectionOnly, out assembly)) + if (this.TryLoadFromCache(assemblyNameToLoad, isReflectionOnly, out var assembly)) { return assembly; } @@ -528,10 +526,7 @@ private Assembly OnResolveInternal(object senderAppDomain, ResolveEventArgs args { if (EqtTrace.IsInfoEnabled) { - EqtTrace.Info( - "AssemblyResolver: {0}: Failed to load assembly. Reason:{1} ", - assemblyNameToLoad, - ex); + EqtTrace.Info("AssemblyResolver: {0}: Failed to load assembly. Reason: {1}", assemblyNameToLoad, ex); } }); } diff --git a/src/Adapter/PlatformServices.Desktop/Data/OdbcDataConnection.cs b/src/Adapter/PlatformServices.Desktop/Data/OdbcDataConnection.cs index 6280c485b..13af29c8f 100644 --- a/src/Adapter/PlatformServices.Desktop/Data/OdbcDataConnection.cs +++ b/src/Adapter/PlatformServices.Desktop/Data/OdbcDataConnection.cs @@ -21,7 +21,7 @@ public OdbcDataConnection(string invariantProviderName, string connectionString, // Need open connection to get Connection.Driver. Debug.Assert(this.IsOpen(), "The connection must be open!"); - this.isMSSql = this.Connection != null ? IsMSSql(this.Connection.Driver) : false; + this.isMSSql = this.Connection != null && IsMSSql(this.Connection.Driver); } public new OdbcCommandBuilder CommandBuilder diff --git a/src/Adapter/PlatformServices.Desktop/Data/OleDataConnection.cs b/src/Adapter/PlatformServices.Desktop/Data/OleDataConnection.cs index e4019c877..35c4fcb89 100644 --- a/src/Adapter/PlatformServices.Desktop/Data/OleDataConnection.cs +++ b/src/Adapter/PlatformServices.Desktop/Data/OleDataConnection.cs @@ -23,7 +23,7 @@ public OleDataConnection(string invariantProviderName, string connectionString, Debug.Assert(this.IsOpen(), "The connection must be open!"); // Fill m_isMSSql. - this.isMSSql = this.Connection != null ? IsMSSql(this.Connection.Provider) : false; + this.isMSSql = this.Connection != null && IsMSSql(this.Connection.Provider); } public new OleDbCommandBuilder CommandBuilder diff --git a/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionFactory.cs b/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionFactory.cs index 0331f0c50..c7351a723 100644 --- a/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionFactory.cs +++ b/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionFactory.cs @@ -49,8 +49,7 @@ public virtual TestDataConnection Create(string invariantProviderName, string co // Most, but not all, connections are actually database based, // here we look for special cases - TestDataConnectionFactory factory; - if (specializedProviders.TryGetValue(invariantProviderName, out factory)) + if (specializedProviders.TryGetValue(invariantProviderName, out var factory)) { Debug.Assert(factory != null, "factory"); return factory.Create(invariantProviderName, connectionString, dataFolders); diff --git a/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionSql.cs b/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionSql.cs index 0593e22fc..d849b1992 100644 --- a/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionSql.cs +++ b/src/Adapter/PlatformServices.Desktop/Data/TestDataConnectionSql.cs @@ -443,7 +443,7 @@ private int FindIdentifierEnd(string text, int start) } // Skip the quote we just found - here = here + 1; + here++; // If this the end? if (here == end || text[here] != suffixChar) @@ -453,7 +453,7 @@ private int FindIdentifierEnd(string text, int start) } // We have a double quote, skip the second one, then keep looking - here = here + 1; + here++; } // If we fall off end of loop, @@ -601,9 +601,7 @@ public override List GetColumns(string tableName) WriteDiagnostics("GetColumns for {0}", tableName); try { - string targetSchema; - string targetName; - this.SplitTableName(tableName, out targetSchema, out targetName); + this.SplitTableName(tableName, out var targetSchema, out var targetName); // This lets us specifically query for columns from the appropriate table name // but assumes all databases have the same restrictions on all the column @@ -728,7 +726,7 @@ private static bool IsInArray(string candidate, string[] values) public bool IsOpen() #pragma warning restore SA1202 // Elements must be ordered by access { - return this.connection != null ? this.connection.State == ConnectionState.Open : false; + return this.connection != null && this.connection.State == ConnectionState.Open; } /// diff --git a/src/Adapter/PlatformServices.Desktop/PlatformServices.Desktop.csproj b/src/Adapter/PlatformServices.Desktop/PlatformServices.Desktop.csproj index 0c04867a7..020b9b88d 100644 --- a/src/Adapter/PlatformServices.Desktop/PlatformServices.Desktop.csproj +++ b/src/Adapter/PlatformServices.Desktop/PlatformServices.Desktop.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {B0FCE474-14BC-449A-91EA-A433342C0D63} Library @@ -29,35 +27,12 @@ 4 true + - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net45\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net45\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net45\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - ..\..\..\packages\System.ComponentModel.Primitives.4.3.0\lib\net45\System.ComponentModel.Primitives.dll - - - ..\..\..\packages\System.ComponentModel.TypeConverter.4.3.0\lib\net45\System.ComponentModel.TypeConverter.dll - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - @@ -65,45 +40,78 @@ + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + False + + + {a7ea583b-a2b0-47da-a058-458f247c7575} + Extension.Desktop + False + + + {7252D9E3-267D-442C-96BC-C73AEF3241D6} + MSTest.Core + False + + + + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + - + ns10RecursiveDirectoryPath.cs - + Services\ns10MSTestSettingsProvider.cs - + Services\ns10TestContextPropertyStrings.cs - + Utilities\ns10Validate.cs - + Extensions\ns13ExceptionExtensions.cs - + Deployment\ns13DeploymentItem.cs - + Resources\Resource.Designer.cs True True Resource.resx - + Services\ns13MSTestAdapterSettings.cs - + Services\ns13TestDeployment.cs - + Utilities\ns13DeploymentItemUtility.cs - + Utilities\ns13DeploymentUtilityBase.cs - + Utilities\ns13FileUtility.cs @@ -122,10 +130,10 @@ - + Services\ns13TraceListener.cs - + Services\ns13TraceListenerManager.cs @@ -145,30 +153,11 @@ - - - - {a7ea583b-a2b0-47da-a058-458f247c7575} - Extension.Desktop - False - - - {7252D9E3-267D-442C-96BC-C73AEF3241D6} - MSTest.Core - False - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - False - - - + - - + Resources\Resource.resx ResXFileCodeGenerator Resource.Designer.cs @@ -176,6 +165,6 @@ Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices - - + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Desktop/Services/DesktopTestContextImplementation.cs b/src/Adapter/PlatformServices.Desktop/Services/DesktopTestContextImplementation.cs index 7d7245bde..e103c4814 100644 --- a/src/Adapter/PlatformServices.Desktop/Services/DesktopTestContextImplementation.cs +++ b/src/Adapter/PlatformServices.Desktop/Services/DesktopTestContextImplementation.cs @@ -250,7 +250,7 @@ public override void AddResultFile(string fileName) { if (string.IsNullOrEmpty(fileName)) { - throw new ArgumentException(Resource.Common_CannotBeNullOrEmpty, "fileName"); + throw new ArgumentException(Resource.Common_CannotBeNullOrEmpty, nameof(fileName)); } this.testResultFiles.Add(Path.GetFullPath(fileName)); @@ -427,7 +427,7 @@ public void AddProperty(string propertyName, string propertyValue) /// Results files generated in run. public IList GetResultFiles() { - if (this.testResultFiles.Count() == 0) + if (!this.testResultFiles.Any()) { return null; } @@ -490,8 +490,7 @@ private static UTF.UnitTestOutcome ToUTF(UTF.UnitTestOutcome outcome) /// Property value private string GetStringPropertyValue(string propertyName) { - object propertyValue = null; - this.properties.TryGetValue(propertyName, out propertyValue); + this.properties.TryGetValue(propertyName, out var propertyValue); return propertyValue as string; } diff --git a/src/Adapter/PlatformServices.Desktop/Utilities/DesktopDeploymentUtility.cs b/src/Adapter/PlatformServices.Desktop/Utilities/DesktopDeploymentUtility.cs index 1f708d012..d37d72431 100644 --- a/src/Adapter/PlatformServices.Desktop/Utilities/DesktopDeploymentUtility.cs +++ b/src/Adapter/PlatformServices.Desktop/Utilities/DesktopDeploymentUtility.cs @@ -68,8 +68,7 @@ public override string GetRootDeploymentDirectory(string baseDirectory) protected void ProcessNewStorage(string testSource, IList deploymentItems, IList warnings) { // Add deployment items and process .config files only for storages we have not processed before. - string errorMessage; - if (!this.DeploymentItemUtility.IsValidDeploymentItem(testSource, string.Empty, out errorMessage)) + if (!this.DeploymentItemUtility.IsValidDeploymentItem(testSource, string.Empty, out var errorMessage)) { warnings.Add(errorMessage); return; @@ -222,8 +221,7 @@ private void AddDependencies(string testSource, string configFile, IList warningList; - string[] references = this.AssemblyUtility.GetFullPathToDependentAssemblies(testSource, configFile, out warningList); + string[] references = this.AssemblyUtility.GetFullPathToDependentAssemblies(testSource, configFile, out var warningList); if (warningList != null && warningList.Count > 0) { warnings = warnings.Concat(warningList).ToList(); diff --git a/src/Adapter/PlatformServices.Desktop/Utilities/RandomIntPermutation.cs b/src/Adapter/PlatformServices.Desktop/Utilities/RandomIntPermutation.cs index 56b2ffd83..9b713cc48 100644 --- a/src/Adapter/PlatformServices.Desktop/Utilities/RandomIntPermutation.cs +++ b/src/Adapter/PlatformServices.Desktop/Utilities/RandomIntPermutation.cs @@ -19,7 +19,7 @@ public RandomIntPermutation(int numberOfObjects) { if (numberOfObjects < 0) { - throw new ArgumentException(Resource.WrongNumberOfObjects, "numberOfObjects"); + throw new ArgumentException(Resource.WrongNumberOfObjects, nameof(numberOfObjects)); } this.objects = new int[numberOfObjects]; diff --git a/src/Adapter/PlatformServices.Desktop/Utilities/SequentialIntPermutation.cs b/src/Adapter/PlatformServices.Desktop/Utilities/SequentialIntPermutation.cs index 7d345e7e0..921c4e5cf 100644 --- a/src/Adapter/PlatformServices.Desktop/Utilities/SequentialIntPermutation.cs +++ b/src/Adapter/PlatformServices.Desktop/Utilities/SequentialIntPermutation.cs @@ -19,7 +19,7 @@ public SequentialIntPermutation(int numberOfObjects) { if (numberOfObjects < 0) { - throw new ArgumentException(Resource.WrongNumberOfObjects, "numberOfObjects"); + throw new ArgumentException(Resource.WrongNumberOfObjects, nameof(numberOfObjects)); } this.numberOfObjects = numberOfObjects; diff --git a/src/Adapter/PlatformServices.Desktop/Utilities/XmlUtilities.cs b/src/Adapter/PlatformServices.Desktop/Utilities/XmlUtilities.cs index 6d5d829f3..5a0871cdd 100644 --- a/src/Adapter/PlatformServices.Desktop/Utilities/XmlUtilities.cs +++ b/src/Adapter/PlatformServices.Desktop/Utilities/XmlUtilities.cs @@ -109,7 +109,7 @@ private static XmlElement FindOrCreateAssemblyBindingSection(XmlDocument doc, Xm Debug.Assert(assemblyName != null, "assemblyName should not be null."); if (assemblyName == null) { - throw new ArgumentNullException("assemblyName"); + throw new ArgumentNullException(nameof(assemblyName)); } // Convert the public key token into a string. diff --git a/src/Adapter/PlatformServices.Desktop/packages.config b/src/Adapter/PlatformServices.Desktop/packages.config deleted file mode 100644 index fc97748e3..000000000 --- a/src/Adapter/PlatformServices.Desktop/packages.config +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Interface/ObjectModel/ITestMethod.cs b/src/Adapter/PlatformServices.Interface/ObjectModel/ITestMethod.cs index 5fa8b3a2b..aa7c734a8 100644 --- a/src/Adapter/PlatformServices.Interface/ObjectModel/ITestMethod.cs +++ b/src/Adapter/PlatformServices.Interface/ObjectModel/ITestMethod.cs @@ -3,6 +3,8 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.ObjectModel { + using System.Collections.Generic; + /// /// TestMethod structure that is shared between adapter and platform services only. /// @@ -39,7 +41,7 @@ public interface ITestMethod /// Gets the fully specified type name metadata format. /// /// - /// NamespaceA.NamespaceB.ClassName`1+InnerClass`2 + /// NamespaceA.NamespaceB.ClassName`1+InnerClass`2 /// string ManagedTypeName { get; } @@ -47,7 +49,7 @@ public interface ITestMethod /// Gets the fully specified method name metadata format. /// /// - /// MethodName`2(ParamTypeA,ParamTypeB,...) + /// MethodName`2(ParamTypeA,ParamTypeB,...) /// string ManagedMethodName { get; } @@ -55,5 +57,13 @@ public interface ITestMethod /// Gets a value indicating whether both and are not null or whitespace. /// bool HasManagedMethodAndTypeProperties { get; } + + /// + /// Gets the test case hierarchy parsed by the adapter. + /// + /// + /// Contains four items in order: Namespace, class name, test group, display name. + /// + IReadOnlyCollection Hierarchy { get; } } } diff --git a/src/Adapter/PlatformServices.Interface/PlatformServices.Interface.csproj b/src/Adapter/PlatformServices.Interface/PlatformServices.Interface.csproj index b7a861970..6a346d87d 100644 --- a/src/Adapter/PlatformServices.Interface/PlatformServices.Interface.csproj +++ b/src/Adapter/PlatformServices.Interface/PlatformServices.Interface.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {BBC99A6B-4490-49DD-9C12-AF2C1E95576E} Library @@ -30,6 +28,31 @@ 4 true + + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + False + + + {6c9fe494-8315-4667-b3f6-75dc62a62319} + Extension.Core + False + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + @@ -45,39 +68,9 @@ - - + - - - - - {6c9fe494-8315-4667-b3f6-75dc62a62319} - Extension.Core - False - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - False - - - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\System.ComponentModel.Primitives.4.3.0\lib\netstandard1.0\System.ComponentModel.Primitives.dll - - - ..\..\..\packages\System.ComponentModel.TypeConverter.4.3.0\lib\netstandard1.0\System.ComponentModel.TypeConverter.dll - - + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Interface/packages.config b/src/Adapter/PlatformServices.Interface/packages.config deleted file mode 100644 index 477f795ab..000000000 --- a/src/Adapter/PlatformServices.Interface/packages.config +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/src/Adapter/PlatformServices.NetCore/PlatformServices.NetCore.csproj b/src/Adapter/PlatformServices.NetCore/PlatformServices.NetCore.csproj index cedc665c7..9eb94fd02 100644 --- a/src/Adapter/PlatformServices.NetCore/PlatformServices.NetCore.csproj +++ b/src/Adapter/PlatformServices.NetCore/PlatformServices.NetCore.csproj @@ -1,9 +1,7 @@  - ..\..\..\ NetCore - Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices @@ -13,33 +11,47 @@ true false true + true - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - @@ -47,7 +59,8 @@ - + + Resources\Resource.Designer.cs True True @@ -56,7 +69,7 @@ - + Resources\Resource.resx ResXFileCodeGenerator Resource.Designer.cs @@ -65,18 +78,4 @@ - - - - - - - - - - - - - - \ No newline at end of file diff --git a/src/Adapter/PlatformServices.NetCore/Services/NetCoreTestContextImplementation.cs b/src/Adapter/PlatformServices.NetCore/Services/NetCoreTestContextImplementation.cs index 23eeebd7d..108268ce2 100644 --- a/src/Adapter/PlatformServices.NetCore/Services/NetCoreTestContextImplementation.cs +++ b/src/Adapter/PlatformServices.NetCore/Services/NetCoreTestContextImplementation.cs @@ -226,7 +226,7 @@ public override void AddResultFile(string fileName) { if (string.IsNullOrEmpty(fileName)) { - throw new ArgumentException(Resource.Common_CannotBeNullOrEmpty, "fileName"); + throw new ArgumentException(Resource.Common_CannotBeNullOrEmpty, nameof(fileName)); } this.testResultFiles.Add(Path.GetFullPath(fileName)); @@ -422,8 +422,7 @@ public void SetDataConnection(object dbConnection) /// Property value private object GetPropertyValue(string propertyName) { - object propertyValue = null; - this.properties.TryGetValue(propertyName, out propertyValue); + this.properties.TryGetValue(propertyName, out var propertyValue); return propertyValue; } @@ -435,8 +434,7 @@ private object GetPropertyValue(string propertyName) /// Property value private string GetStringPropertyValue(string propertyName) { - object propertyValue = null; - this.properties.TryGetValue(propertyName, out propertyValue); + this.properties.TryGetValue(propertyName, out var propertyValue); return propertyValue as string; } diff --git a/src/Adapter/PlatformServices.Portable/PlatformServices.Portable.csproj b/src/Adapter/PlatformServices.Portable/PlatformServices.Portable.csproj index 103ddb317..c229207ca 100644 --- a/src/Adapter/PlatformServices.Portable/PlatformServices.Portable.csproj +++ b/src/Adapter/PlatformServices.Portable/PlatformServices.Portable.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {58BDD63D-5E58-4D23-BDF5-592E5E03D29D} Library @@ -30,95 +28,90 @@ 4 true + + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + False + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + False + + + {6C9FE494-8315-4667-B3F6-75DC62A62319} + Extension.Core + False + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + - + Constants.cs - + MarshalByRefObject.cs - + SerializableAttribute.cs - + Services\ns10DiaSessionOperations.cs - + Services\ns10FileOperations.cs - + Services\ns10ReflectionOperations.cs - + Services\ns10SettingsProvider.cs - + Services\ns10TestContextImplementation.cs - + Services\ns10TestDataSource.cs - + Services\ns10TestDeployment.cs - + Services\ns10TestSource.cs - + Services\ns10TestSourceHost.cs - + Services\ns10ThreadOperations.cs - + Services\ns10TraceListener.cs - + Services\ns10TraceListenerManager.cs - + Services\ns10TraceLogger.cs - - - - {6C9FE494-8315-4667-B3F6-75DC62A62319} - Extension.Core - False - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - False - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - False - - - + - - - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\System.ComponentModel.Primitives.4.3.0\lib\netstandard1.0\System.ComponentModel.Primitives.dll - - - ..\..\..\packages\System.ComponentModel.TypeConverter.4.3.0\lib\netstandard1.0\System.ComponentModel.TypeConverter.dll - - + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Portable/packages.config b/src/Adapter/PlatformServices.Portable/packages.config deleted file mode 100644 index 477f795ab..000000000 --- a/src/Adapter/PlatformServices.Portable/packages.config +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.projitems b/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.projitems index 9baba9aea..9ce58de0a 100644 --- a/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.projitems +++ b/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.projitems @@ -11,4 +11,4 @@ - \ No newline at end of file + diff --git a/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.shproj b/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.shproj index 40daaa8ea..fe9f815b3 100644 --- a/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.shproj +++ b/src/Adapter/PlatformServices.Shared/PlatformServices.Shared.shproj @@ -4,6 +4,7 @@ 2177c273-ae07-43b3-b87a-443e47a23c5a 14.0 + diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.0/Services/ns10TestContextImplementation.cs b/src/Adapter/PlatformServices.Shared/netstandard1.0/Services/ns10TestContextImplementation.cs index b444ccb6b..db9d7e2fe 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.0/Services/ns10TestContextImplementation.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.0/Services/ns10TestContextImplementation.cs @@ -329,8 +329,7 @@ public void SetDataConnection(object dbConnection) /// Property value private object GetPropertyValue(string propertyName) { - object propertyValue = null; - this.properties.TryGetValue(propertyName, out propertyValue); + this.properties.TryGetValue(propertyName, out var propertyValue); return propertyValue; } diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.0/ns10RecursiveDirectoryPath.cs b/src/Adapter/PlatformServices.Shared/netstandard1.0/ns10RecursiveDirectoryPath.cs index 9064d432c..68bf86274 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.0/ns10RecursiveDirectoryPath.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.0/ns10RecursiveDirectoryPath.cs @@ -54,6 +54,9 @@ public RecursiveDirectoryPath(string dirPath, bool includeSubDirectories) /// The . /// [SecurityCritical] +#if NET5_0 + [Obsolete] +#endif public override object InitializeLifetimeService() { return null; diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.cs.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.cs.xlf index 3baae6016..886a642fa 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.cs.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.cs.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Soubor {0} se nenašel. - - - - - The parameter should not be null or empty. - Parametr nemůže být null nebo prázdný. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problém nasazení testovacího běhu: Chybná položka nasazení: {0}: výstupní adresář {1} určuje položku, která se má nasadit mimo kořenový adresář nasazení, což není povolené. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problém nasazení testovacího běhu: Nepodařilo se získat přístup k výstupnímu adresáři {1} zadanému položkou nasazení {0}, položka se nenasadí: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problém nasazení testovacího běhu: Nepodařilo se získat přístup k souboru {0}: {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problém nasazení testovacího běhu: Nepodařilo se zkopírovat soubor {0} do {1}: {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problém nasazení testovacího běhu: Nepodařilo se nasadit závislosti úložiště testů {0}: {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problém nasazení testovacího běhu: Nepodařilo se získat soubor pro {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problém nasazení testovacího běhu: Během získávání satelitních sestavení pro {0}: {1}: {2} došlo k chybě - - - - - deployment item '{0}' - položka nasazení {0} - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Neplatná položka nasazení: Zadaná cesta {0} nebo adresář výstupu {1} obsahuje neplatné znaky. - - - - - Invalid deployment item: the output directory cannot be null. - Neplatná položka nasazení: Adresář výstupu nemůže být null. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Neplatná položka nasazení: Zadaný adresář výstupu {0} nemá relativní adresu. - - - - - Invalid deployment item: the path must contain at least one character. - Neplatná položka nasazení: Cesta musí obsahovat minimálně jeden znak. - - - - - deployment item '{0}' (output directory '{1}') - položka nasazení {0} (adresář výstupu {1}) - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - Nástroj MSTestAdapter zjistil neočekávaný prvek {0} v nastavení {1}. Odeberte tento prvek a zkuste to znovu. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problém nasazení testovacího běhu: Sestavení nebo modul {0} se nenašly. Důvod: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problém nasazení testovacího běhu: Sestavení nebo modul {0} se nenašly. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - Zdroj dat {0} se v nastavení konfigurace testu nenašel. - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - Adaptéru testování částí se buď nepodařilo připojit ke zdroji dat, nebo přečíst data. Další informace o odstraňování této chyby najdete v knihovně MSDN v tématu Troubleshooting Data-Driven Unit Tests (http://go.microsoft.com/fwlink/?LinkId=62412). Podrobnosti o chybě: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Chybný počet objektů pro permutaci. Počet musí být větší než nula. - - - - - + + + + + + Could not find file '{0}'. + Soubor {0} se nenašel. + + + + The parameter should not be null or empty. + Parametr nemůže být null nebo prázdný. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problém nasazení testovacího běhu: Chybná položka nasazení: {0}: výstupní adresář {1} určuje položku, která se má nasadit mimo kořenový adresář nasazení, což není povolené. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problém nasazení testovacího běhu: Nepodařilo se získat přístup k výstupnímu adresáři {1} zadanému položkou nasazení {0}, položka se nenasadí: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problém nasazení testovacího běhu: Nepodařilo se získat přístup k souboru {0}: {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problém nasazení testovacího běhu: Nepodařilo se zkopírovat soubor {0} do {1}: {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problém nasazení testovacího běhu: Nepodařilo se nasadit závislosti úložiště testů {0}: {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problém nasazení testovacího běhu: Nepodařilo se získat soubor pro {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problém nasazení testovacího běhu: Během získávání satelitních sestavení pro {0}: {1}: {2} došlo k chybě + + + + deployment item '{0}' + položka nasazení {0} + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Neplatná položka nasazení: Zadaná cesta {0} nebo adresář výstupu {1} obsahuje neplatné znaky. + + + + Invalid deployment item: the output directory cannot be null. + Neplatná položka nasazení: Adresář výstupu nemůže být null. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Neplatná položka nasazení: Zadaný adresář výstupu {0} nemá relativní adresu. + + + + Invalid deployment item: the path must contain at least one character. + Neplatná položka nasazení: Cesta musí obsahovat minimálně jeden znak. + + + + deployment item '{0}' (output directory '{1}') + položka nasazení {0} (adresář výstupu {1}) + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + Nástroj MSTestAdapter zjistil neočekávaný prvek {0} v nastavení {1}. Odeberte tento prvek a zkuste to znovu. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problém nasazení testovacího běhu: Sestavení nebo modul {0} se nenašly. Důvod: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problém nasazení testovacího běhu: Sestavení nebo modul {0} se nenašly. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + Zdroj dat {0} se v nastavení konfigurace testu nenašel. + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + Adaptéru testování částí se buď nepodařilo připojit ke zdroji dat, nebo přečíst data. Další informace o odstraňování této chyby najdete v knihovně MSDN v tématu Troubleshooting Data-Driven Unit Tests (http://go.microsoft.com/fwlink/?LinkId=62412). Podrobnosti o chybě: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Chybný počet objektů pro permutaci. Počet musí být větší než nula. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.de.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.de.xlf index 7050451bf..cb160ff87 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.de.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.de.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Die Datei "{0}" konnte nicht gefunden werden. - - - - - The parameter should not be null or empty. - Der Parameter darf nicht NULL oder leer sein. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problem bei der Testlaufbereitstellung: Ungültiges Bereitstellungselement: "{0}". Das Ausgabeverzeichnis "{1}" gibt das unzulässige Element an, das außerhalb des Bereitstellungsstammverzeichnisses bereitgestellt werden soll. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problem bei der Testlaufbereitstellung: Fehler beim Zugriff auf das vom Bereitstellungselement "{0}" angegebene Ausgabeverzeichnis "{1}". Das Element wird nicht bereitgestellt: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problem bei der Testlaufbereitstellung: Fehler beim Zugriff auf die Datei "{0}": {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problem bei der Testlaufbereitstellung: Fehler beim Kopieren der Datei "{0}" nach "{1}": {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problem bei der Testlaufbereitstellung: Fehler beim Bereitstellen der Abhängigkeiten für den Testspeicher "{0}": {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problem bei der Testlaufbereitstellung: Fehler beim Abrufen der Datei für {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problem bei der Testlaufbereitstellung: Fehler beim Abrufen der Satellitenassemblys für {0}: {1}: {2} - - - - - deployment item '{0}' - Bereitstellungselement "{0}" - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Ungültiges Bereitstellungselement: Der angegebene Pfad "{0}" oder das angegebene Ausgabeverzeichnis "{1}" enthält unzulässige Zeichen. - - - - - Invalid deployment item: the output directory cannot be null. - Ungültiges Bereitstellungselement: Das Ausgabeverzeichnis darf nicht NULL sein. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Ungültiges Bereitstellungselement: Das angegebene Ausgabeverzeichnis "{0}" ist nicht relativ. - - - - - Invalid deployment item: the path must contain at least one character. - Ungültiges Bereitstellungselement: Der Pfad muss mindestens ein Zeichen enthalten. - - - - - deployment item '{0}' (output directory '{1}') - Bereitstellungselement "{0}" (Ausgabeverzeichnis "{1}") - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - "MSTestAdapter" hat ein unerwartetes Element "{0}" in den Einstellungen "{1}" ermittelt. Entfernen Sie dieses Element, und versuchen Sie es erneut. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problem bei der Testlaufbereitstellung: Die Assembly oder das Modul "{0}" wurde nicht gefunden. Ursache: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problem bei der Testlaufbereitstellung: Die Assembly oder das Modul "{0}" wurde nicht gefunden. - - - - - {0}_{1} {2} - {0}{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - Die Datenquelle "{0}" wurde in den Testkonfigurationseinstellungen nicht gefunden. - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - Der Komponententestadapter konnte keine Verbindung mit der Datenquelle herstellen bzw. die Daten nicht lesen. Weitere Informationen zur Problembehandlung dieses Fehlers finden Sie unter "Problembehandlung von datengesteuerten Komponententests" (http://go.microsoft.com/fwlink/?LinkId=62412) in der MSDN Library. Fehlerdetails: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Falsche Anzahl von Objekten für die Permutation. Die Anzahl muss größer als NULL sein. - - - - - + + + + + + Could not find file '{0}'. + Die Datei "{0}" konnte nicht gefunden werden. + + + + The parameter should not be null or empty. + Der Parameter darf nicht NULL oder leer sein. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problem bei der Testlaufbereitstellung: Ungültiges Bereitstellungselement: "{0}". Das Ausgabeverzeichnis "{1}" gibt das unzulässige Element an, das außerhalb des Bereitstellungsstammverzeichnisses bereitgestellt werden soll. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problem bei der Testlaufbereitstellung: Fehler beim Zugriff auf das vom Bereitstellungselement "{0}" angegebene Ausgabeverzeichnis "{1}". Das Element wird nicht bereitgestellt: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problem bei der Testlaufbereitstellung: Fehler beim Zugriff auf die Datei "{0}": {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problem bei der Testlaufbereitstellung: Fehler beim Kopieren der Datei "{0}" nach "{1}": {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problem bei der Testlaufbereitstellung: Fehler beim Bereitstellen der Abhängigkeiten für den Testspeicher "{0}": {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problem bei der Testlaufbereitstellung: Fehler beim Abrufen der Datei für {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problem bei der Testlaufbereitstellung: Fehler beim Abrufen der Satellitenassemblys für {0}: {1}: {2} + + + + deployment item '{0}' + Bereitstellungselement "{0}" + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Ungültiges Bereitstellungselement: Der angegebene Pfad "{0}" oder das angegebene Ausgabeverzeichnis "{1}" enthält unzulässige Zeichen. + + + + Invalid deployment item: the output directory cannot be null. + Ungültiges Bereitstellungselement: Das Ausgabeverzeichnis darf nicht NULL sein. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Ungültiges Bereitstellungselement: Das angegebene Ausgabeverzeichnis "{0}" ist nicht relativ. + + + + Invalid deployment item: the path must contain at least one character. + Ungültiges Bereitstellungselement: Der Pfad muss mindestens ein Zeichen enthalten. + + + + deployment item '{0}' (output directory '{1}') + Bereitstellungselement "{0}" (Ausgabeverzeichnis "{1}") + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + "MSTestAdapter" hat ein unerwartetes Element "{0}" in den Einstellungen "{1}" ermittelt. Entfernen Sie dieses Element, und versuchen Sie es erneut. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problem bei der Testlaufbereitstellung: Die Assembly oder das Modul "{0}" wurde nicht gefunden. Ursache: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problem bei der Testlaufbereitstellung: Die Assembly oder das Modul "{0}" wurde nicht gefunden. + + + + {0}_{1} {2} + {0}{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + Die Datenquelle "{0}" wurde in den Testkonfigurationseinstellungen nicht gefunden. + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + Der Komponententestadapter konnte keine Verbindung mit der Datenquelle herstellen bzw. die Daten nicht lesen. Weitere Informationen zur Problembehandlung dieses Fehlers finden Sie unter "Problembehandlung von datengesteuerten Komponententests" (http://go.microsoft.com/fwlink/?LinkId=62412) in der MSDN Library. Fehlerdetails: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Falsche Anzahl von Objekten für die Permutation. Die Anzahl muss größer als NULL sein. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.es.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.es.xlf index 6da98b5f2..e9d881dbe 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.es.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.es.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - No se pudo encontrar el archivo '{0}'. - - - - - The parameter should not be null or empty. - El parámetro no debe ser NULL ni estar vacío. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problema de implementación en la serie de pruebas: elemento de implementación incorrecto '{0}': el directorio de salida '{1}' especifica el elemento que se va a implementar fuera del directorio raíz de implementación, lo cual no está permitido. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problema de implementación en la serie de pruebas: no se pudo acceder al directorio de salida '{1}' especificado por el elemento de implementación '{0}', el elemento no se implementará {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problema de implementación en la serie de pruebas: no se pudo acceder al archivo '{0}': {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problema de implementación en la serie de pruebas: no se pudo copiar el archivo '{0}' en '{1}': {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problema de implementación en la serie de pruebas: no se pudo implementar dependencias para el almacenamiento de prueba '{0}': {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problema de implementación en la serie de pruebas: no se pudo obtener el archivo para {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problema de implementación en la serie de pruebas: no se pudo obtener los ensamblados satélite para {0}: {1}: {2} - - - - - deployment item '{0}' - elemento de implementación '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Elemento de implementación no válido: la ruta de acceso '{0}' o el directorio de salida '{1}' especificados contienen caracteres no válidos. - - - - - Invalid deployment item: the output directory cannot be null. - Elemento de implementación no válido: el directorio de salida no puede ser un valor nulo. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Elemento de implementación no válido: el directorio de salida especificado '{0}' no es relativo. - - - - - Invalid deployment item: the path must contain at least one character. - Elemento de implementación no válido: la ruta de acceso debe contener al menos un carácter. - - - - - deployment item '{0}' (output directory '{1}') - elemento de implementación '{0}' (directorio de salida '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter encontró un elemento inesperado '{0}' en su configuración '{1}'. Quite este elemento e inténtelo de nuevo. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problema de implementación en la serie de pruebas: no se encontró el ensamblado o el módulo '{0}'. Motivo: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problema de implementación en la serie de pruebas: no se encontró el ensamblado o el módulo '{0}'. - - - - - {0}_{1} {2} - {0} {1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - No se encuentra el origen de datos '{0}' en los valores de configuración de prueba - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - El adaptador de pruebas unitarias no puede conectarse al origen de datos o leer los datos. Para obtener más información acerca de cómo solucionar este error, consulte "Solución de problemas de pruebas unitarias orientadas a datos" (http://go.microsoft.com/fwlink/?LinkId=62412) en la biblioteca de MSDN. Detalles del error: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Número incorrecto de objetos para permutación. Debe ser una cantidad mayor que cero. - - - - - + + + + + + Could not find file '{0}'. + No se pudo encontrar el archivo '{0}'. + + + + The parameter should not be null or empty. + El parámetro no debe ser NULL ni estar vacío. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problema de implementación en la serie de pruebas: elemento de implementación incorrecto '{0}': el directorio de salida '{1}' especifica el elemento que se va a implementar fuera del directorio raíz de implementación, lo cual no está permitido. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problema de implementación en la serie de pruebas: no se pudo acceder al directorio de salida '{1}' especificado por el elemento de implementación '{0}', el elemento no se implementará {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problema de implementación en la serie de pruebas: no se pudo acceder al archivo '{0}': {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problema de implementación en la serie de pruebas: no se pudo copiar el archivo '{0}' en '{1}': {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problema de implementación en la serie de pruebas: no se pudo implementar dependencias para el almacenamiento de prueba '{0}': {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problema de implementación en la serie de pruebas: no se pudo obtener el archivo para {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problema de implementación en la serie de pruebas: no se pudo obtener los ensamblados satélite para {0}: {1}: {2} + + + + deployment item '{0}' + elemento de implementación '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Elemento de implementación no válido: la ruta de acceso '{0}' o el directorio de salida '{1}' especificados contienen caracteres no válidos. + + + + Invalid deployment item: the output directory cannot be null. + Elemento de implementación no válido: el directorio de salida no puede ser un valor nulo. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Elemento de implementación no válido: el directorio de salida especificado '{0}' no es relativo. + + + + Invalid deployment item: the path must contain at least one character. + Elemento de implementación no válido: la ruta de acceso debe contener al menos un carácter. + + + + deployment item '{0}' (output directory '{1}') + elemento de implementación '{0}' (directorio de salida '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter encontró un elemento inesperado '{0}' en su configuración '{1}'. Quite este elemento e inténtelo de nuevo. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problema de implementación en la serie de pruebas: no se encontró el ensamblado o el módulo '{0}'. Motivo: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problema de implementación en la serie de pruebas: no se encontró el ensamblado o el módulo '{0}'. + + + + {0}_{1} {2} + {0} {1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + No se encuentra el origen de datos '{0}' en los valores de configuración de prueba + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + El adaptador de pruebas unitarias no puede conectarse al origen de datos o leer los datos. Para obtener más información acerca de cómo solucionar este error, consulte "Solución de problemas de pruebas unitarias orientadas a datos" (http://go.microsoft.com/fwlink/?LinkId=62412) en la biblioteca de MSDN. Detalles del error: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Número incorrecto de objetos para permutación. Debe ser una cantidad mayor que cero. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.fr.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.fr.xlf index 47daa302c..8b349d66e 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.fr.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.fr.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Le fichier '{0}' est introuvable. - - - - - The parameter should not be null or empty. - Le paramètre ne doit pas être une valeur Null ou être vide. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problème de déploiement de la série de tests : élément de déploiement incorrect : '{0}' : le répertoire de sortie '{1}' spécifie l'élément à déployer en dehors du répertoire racine du déploiement, ce qui n'est pas autorisé. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problème de déploiement de la série de tests : échec de l'accès au répertoire de sortie '{1}' spécifié par l'élément de déploiement '{0}', l'élément ne sera pas déployé : {2} : {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problème de déploiement de la série de tests : échec de l'accès au fichier '{0}' : {1} : {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problème de déploiement de la série de tests : échec de la copie du fichier '{0}' dans '{1}' : {2} : {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problème de déploiement de la série de tests : échec du déploiement des dépendances pour le stockage de test '{0}' : {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problème de déploiement de la série de tests : échec de l'obtention du fichier pour {0} : {1} : {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problème de déploiement de la série de tests : une erreur s'est produite durant l'obtention des assemblys satellites pour {0} : {1} : {2} - - - - - deployment item '{0}' - élément de déploiement '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Élément de déploiement non valide : le chemin '{0}' ou le répertoire de sortie '{1}' spécifié contient des caractères non conformes. - - - - - Invalid deployment item: the output directory cannot be null. - Élément de déploiement non valide : le répertoire de sortie doit être défini. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Élément de déploiement non valide : le répertoire de sortie '{0}' spécifié n'est pas relatif. - - - - - Invalid deployment item: the path must contain at least one character. - Élément de déploiement non valide : le chemin doit contenir au moins un caractère. - - - - - deployment item '{0}' (output directory '{1}') - élément de déploiement '{0}' (répertoire de sortie '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter a rencontré un élément inattendu '{0}' dans ses paramètres '{1}'. Supprimez cet élément, puis réessayez. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problème de déploiement de la série de tests : l'assembly ou le module '{0}' est introuvable. Raison : {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problème de déploiement de la série de tests : l'assembly ou le module '{0}' est introuvable. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - Source de données '{0}' introuvable dans les paramètres de configuration de test - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - L'adaptateur de test unitaire n'a pas réussi à se connecter à la source de données ou à lire les données. Pour plus d'informations sur le dépannage de l'erreur, consultez "Résolution des problèmes liés aux tests unitaires pilotés par les données" (http://go.microsoft.com/fwlink/?LinkId=62412) dans MSDN Library. Détails de l'erreur : {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Nombre d'objets erroné pour la permutation. Il doit être supérieur à zéro. - - - - - + + + + + + Could not find file '{0}'. + Le fichier '{0}' est introuvable. + + + + The parameter should not be null or empty. + Le paramètre ne doit pas être une valeur Null ou être vide. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problème de déploiement de la série de tests : élément de déploiement incorrect : '{0}' : le répertoire de sortie '{1}' spécifie l'élément à déployer en dehors du répertoire racine du déploiement, ce qui n'est pas autorisé. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problème de déploiement de la série de tests : échec de l'accès au répertoire de sortie '{1}' spécifié par l'élément de déploiement '{0}', l'élément ne sera pas déployé : {2} : {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problème de déploiement de la série de tests : échec de l'accès au fichier '{0}' : {1} : {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problème de déploiement de la série de tests : échec de la copie du fichier '{0}' dans '{1}' : {2} : {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problème de déploiement de la série de tests : échec du déploiement des dépendances pour le stockage de test '{0}' : {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problème de déploiement de la série de tests : échec de l'obtention du fichier pour {0} : {1} : {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problème de déploiement de la série de tests : une erreur s'est produite durant l'obtention des assemblys satellites pour {0} : {1} : {2} + + + + deployment item '{0}' + élément de déploiement '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Élément de déploiement non valide : le chemin '{0}' ou le répertoire de sortie '{1}' spécifié contient des caractères non conformes. + + + + Invalid deployment item: the output directory cannot be null. + Élément de déploiement non valide : le répertoire de sortie doit être défini. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Élément de déploiement non valide : le répertoire de sortie '{0}' spécifié n'est pas relatif. + + + + Invalid deployment item: the path must contain at least one character. + Élément de déploiement non valide : le chemin doit contenir au moins un caractère. + + + + deployment item '{0}' (output directory '{1}') + élément de déploiement '{0}' (répertoire de sortie '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter a rencontré un élément inattendu '{0}' dans ses paramètres '{1}'. Supprimez cet élément, puis réessayez. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problème de déploiement de la série de tests : l'assembly ou le module '{0}' est introuvable. Raison : {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problème de déploiement de la série de tests : l'assembly ou le module '{0}' est introuvable. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + Source de données '{0}' introuvable dans les paramètres de configuration de test + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + L'adaptateur de test unitaire n'a pas réussi à se connecter à la source de données ou à lire les données. Pour plus d'informations sur le dépannage de l'erreur, consultez "Résolution des problèmes liés aux tests unitaires pilotés par les données" (http://go.microsoft.com/fwlink/?LinkId=62412) dans MSDN Library. Détails de l'erreur : {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Nombre d'objets erroné pour la permutation. Il doit être supérieur à zéro. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.it.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.it.xlf index be383ea75..574b46648 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.it.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.it.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Il file '{0}' non è stato trovato. - - - - - The parameter should not be null or empty. - Il parametro non deve essere vuoto o Null. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problema di distribuzione dell'esecuzione dei test: l'elemento di distribuzione '{0}' non è corretto. La directory di output '{1}' specifica l'elemento da distribuire all'esterno della directory radice della distribuzione e questa operazione non consentita. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problema di distribuzione dell'esecuzione dei test: non è stato possibile accedere alla directory di output '{0}' specificata dall'elemento di distribuzione '{1}'. L'elemento non verrà distribuito: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problema di distribuzione dell'esecuzione dei test: non è stato possibile accedere al file '{0}': {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problema di distribuzione dell'esecuzione dei test: non è stato possibile copiare il file '{0}' in '{1}': {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problema di distribuzione dell'esecuzione dei test: non è stato possibile distribuire le dipendenze per l'archivio dei test '{0}': {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problema di distribuzione dell'esecuzione dei test: non è stato possibile ottenere il file per {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problema di distribuzione dell'esecuzione dei test: si è verificato un errore durante il recupero degli assembly satellite per {0}: {1}: {2} - - - - - deployment item '{0}' - elemento di distribuzione '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Elemento di distribuzione non valido: la directory di output '{1}' o il percorso specificato '{0}' contiene caratteri non validi. - - - - - Invalid deployment item: the output directory cannot be null. - Elemento di distribuzione non valido: la directory di output non può essere Null. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Elemento di distribuzione non valido: la directory di output specificata '{0}' non è relativa. - - - - - Invalid deployment item: the path must contain at least one character. - Elemento di distribuzione non valido: il percorso deve contenere almeno un carattere. - - - - - deployment item '{0}' (output directory '{1}') - elemento di distribuzione '{0}' (directory di output '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter ha rilevato un elemento imprevisto '{0}' nelle impostazioni '{1}'. Rimuovere l'elemento e riprovare. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problema di distribuzione dell'esecuzione dei test: l'assembly o il modulo '{0}' non è stato trovato. Motivo: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problema di distribuzione dell'esecuzione dei test: l'assembly o il modulo '{0}' non è stato trovato. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - L'origine dati '{0}' non è stata trovata nelle impostazioni della configurazione di test - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - L'adattatore di unit test non è riuscito a connettersi all'origine dati o a leggere i dati. Per altre informazioni sulla risoluzione di questo errore, vedere "Risoluzione dei problemi relativi a unit test basati su dati" (http://go.microsoft.com/fwlink/?LinkId=62412) in MSDN Library. Dettagli errore: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Il numero di oggetti non è corretto per la permutazione. Deve essere maggiore di zero. - - - - - + + + + + + Could not find file '{0}'. + Il file '{0}' non è stato trovato. + + + + The parameter should not be null or empty. + Il parametro non deve essere vuoto o Null. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problema di distribuzione dell'esecuzione dei test: l'elemento di distribuzione '{0}' non è corretto. La directory di output '{1}' specifica l'elemento da distribuire all'esterno della directory radice della distribuzione e questa operazione non consentita. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problema di distribuzione dell'esecuzione dei test: non è stato possibile accedere alla directory di output '{0}' specificata dall'elemento di distribuzione '{1}'. L'elemento non verrà distribuito: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problema di distribuzione dell'esecuzione dei test: non è stato possibile accedere al file '{0}': {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problema di distribuzione dell'esecuzione dei test: non è stato possibile copiare il file '{0}' in '{1}': {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problema di distribuzione dell'esecuzione dei test: non è stato possibile distribuire le dipendenze per l'archivio dei test '{0}': {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problema di distribuzione dell'esecuzione dei test: non è stato possibile ottenere il file per {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problema di distribuzione dell'esecuzione dei test: si è verificato un errore durante il recupero degli assembly satellite per {0}: {1}: {2} + + + + deployment item '{0}' + elemento di distribuzione '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Elemento di distribuzione non valido: la directory di output '{1}' o il percorso specificato '{0}' contiene caratteri non validi. + + + + Invalid deployment item: the output directory cannot be null. + Elemento di distribuzione non valido: la directory di output non può essere Null. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Elemento di distribuzione non valido: la directory di output specificata '{0}' non è relativa. + + + + Invalid deployment item: the path must contain at least one character. + Elemento di distribuzione non valido: il percorso deve contenere almeno un carattere. + + + + deployment item '{0}' (output directory '{1}') + elemento di distribuzione '{0}' (directory di output '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter ha rilevato un elemento imprevisto '{0}' nelle impostazioni '{1}'. Rimuovere l'elemento e riprovare. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problema di distribuzione dell'esecuzione dei test: l'assembly o il modulo '{0}' non è stato trovato. Motivo: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problema di distribuzione dell'esecuzione dei test: l'assembly o il modulo '{0}' non è stato trovato. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + L'origine dati '{0}' non è stata trovata nelle impostazioni della configurazione di test + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + L'adattatore di unit test non è riuscito a connettersi all'origine dati o a leggere i dati. Per altre informazioni sulla risoluzione di questo errore, vedere "Risoluzione dei problemi relativi a unit test basati su dati" (http://go.microsoft.com/fwlink/?LinkId=62412) in MSDN Library. Dettagli errore: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Il numero di oggetti non è corretto per la permutazione. Deve essere maggiore di zero. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ja.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ja.xlf index ea0c049ad..0760c6ca3 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ja.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ja.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - ファイル '{0}' が見つかりませんでした。 - - - - - The parameter should not be null or empty. - パラメーターを null または空にすることはできません。 - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - テストの実行の配置問題です: 配置項目が正しくありません: '{0}': 出力ディレクトリ '{1}' は、項目が配置ルート ディレクトリ外に配置されるように指定していますが、それは許可されません。 - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - テストの実行の配置問題です: 配置項目 '{0}' によって指定された出力ディレクトリ '{1}' にアクセスできません。項目は配置されません: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - テストの実行の配置問題です: ファイル '{0}' にアクセスできませんでした: {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - テストの実行の配置問題です: ファイル '{0}' を '{1}' にコピーできませんでした: {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - テストの実行の配置問題です: テスト ストレージ '{0}' の依存関係を配置できませんでした: {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - テストの実行の配置問題です: {0} のファイルを取得できませんでした: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - テストの実行の配置問題です: {0} のサテライト アセンブリを取得中にエラーが発生しました: {1}: {2} - - - - - deployment item '{0}' - 配置項目 '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - 無効な配置項目です: 指定されたパス '{0}' または出力ディレクトリ '{1}' に使用できない文字が含まれています。 - - - - - Invalid deployment item: the output directory cannot be null. - 無効な配置項目です: 出力ディレクトリを null にすることはできません。 - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - 無効な配置項目です: 指定された出力ディレクトリ '{0}' は相対ではありません。 - - - - - Invalid deployment item: the path must contain at least one character. - 無効な配置項目です: パスは少なくとも 1 つの文字を含んでいなければなりません。 - - - - - deployment item '{0}' (output directory '{1}') - 配置項目 '{0}' (出力ディレクトリ '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter で設定 '{1}' に予期しない要素 '{0}' が見つかりました。この要素を削除して、もう一度お試しください。 - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - テストの実行の配置問題です: アセンブリまたはモジュール '{0}' が見つかりませんでした。理由: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - テストの実行の配置問題です: アセンブリまたはモジュール '{0}' が見つかりませんでした。 - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - データ ソース '{0}' がテスト構成の設定に見つかりません - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - 単体テスト アダプターがデータ ソースに接続できなかったか、データを読み取れませんでした。このエラーのトラブルシューティングの詳細については、MSDN ライブラリの「方法: データ ドリブン単体テストを作成する」(http://go.microsoft.com/fwlink/?LinkId=62412) をご覧ください。エラーの詳細: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - 順列のオブジェクト数が正しくありません。ゼロより大きくなければなりません。 - - - - - + + + + + + Could not find file '{0}'. + ファイル '{0}' が見つかりませんでした。 + + + + The parameter should not be null or empty. + パラメーターを null または空にすることはできません。 + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + テストの実行の配置問題です: 配置項目が正しくありません: '{0}': 出力ディレクトリ '{1}' は、項目が配置ルート ディレクトリ外に配置されるように指定していますが、それは許可されません。 + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + テストの実行の配置問題です: 配置項目 '{0}' によって指定された出力ディレクトリ '{1}' にアクセスできません。項目は配置されません: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + テストの実行の配置問題です: ファイル '{0}' にアクセスできませんでした: {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + テストの実行の配置問題です: ファイル '{0}' を '{1}' にコピーできませんでした: {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + テストの実行の配置問題です: テスト ストレージ '{0}' の依存関係を配置できませんでした: {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + テストの実行の配置問題です: {0} のファイルを取得できませんでした: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + テストの実行の配置問題です: {0} のサテライト アセンブリを取得中にエラーが発生しました: {1}: {2} + + + + deployment item '{0}' + 配置項目 '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + 無効な配置項目です: 指定されたパス '{0}' または出力ディレクトリ '{1}' に使用できない文字が含まれています。 + + + + Invalid deployment item: the output directory cannot be null. + 無効な配置項目です: 出力ディレクトリを null にすることはできません。 + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + 無効な配置項目です: 指定された出力ディレクトリ '{0}' は相対ではありません。 + + + + Invalid deployment item: the path must contain at least one character. + 無効な配置項目です: パスは少なくとも 1 つの文字を含んでいなければなりません。 + + + + deployment item '{0}' (output directory '{1}') + 配置項目 '{0}' (出力ディレクトリ '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter で設定 '{1}' に予期しない要素 '{0}' が見つかりました。この要素を削除して、もう一度お試しください。 + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + テストの実行の配置問題です: アセンブリまたはモジュール '{0}' が見つかりませんでした。理由: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + テストの実行の配置問題です: アセンブリまたはモジュール '{0}' が見つかりませんでした。 + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + データ ソース '{0}' がテスト構成の設定に見つかりません + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + 単体テスト アダプターがデータ ソースに接続できなかったか、データを読み取れませんでした。このエラーのトラブルシューティングの詳細については、MSDN ライブラリの「方法: データ ドリブン単体テストを作成する」(http://go.microsoft.com/fwlink/?LinkId=62412) をご覧ください。エラーの詳細: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + 順列のオブジェクト数が正しくありません。ゼロより大きくなければなりません。 + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ko.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ko.xlf index fcad1aeec..5439e70bf 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ko.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ko.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - '{0}' 파일을 찾을 수 없습니다. - - - - - The parameter should not be null or empty. - 매개 변수는 null이거나 비워 둘 수 없습니다. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - 테스트 실행 배포 문제: 잘못된 배포 항목: '{0}': 출력 디렉터리 '{1}'에서 항목을 배포 루트 디렉터리 외부에 배포하도록 지정하며 이는 허용되지 않습니다. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - 테스트 실행 배포 문제: 배포 항목 '{0}'에 의해 지정된 출력 디렉터리 '{1}'에 액세스하지 못했습니다. 항목이 배포되지 않음: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - 테스트 실행 배포 문제: '{0}' 파일에 액세스하지 못함: {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - 테스트 실행 배포 문제: '{0}' 파일을 '{1}'에 복사하지 못함: {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - 테스트 실행 배포 문제: 테스트 스토리지 '{0}'에 대한 종속성을 배포하지 못함: {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - 테스트 실행 배포 문제: {0}에 대한 파일을 가져오지 못함: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - 테스트 실행 배포 문제: {0}에 대한 위성 어셈블리를 가져오는 동안 오류 발생: {1}: {2} - - - - - deployment item '{0}' - 배포 항목 '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - 잘못된 배포 항목: 지정된 경로 '{0}' 또는 출력 디렉터리 '{1}'에 잘못된 문자가 들어 있습니다. - - - - - Invalid deployment item: the output directory cannot be null. - 잘못된 배포 항목: 출력 디렉터리는 null일 수 없습니다. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - 잘못된 배포 항목: 지정된 출력 디렉터리 '{0}'이(가) 상대 디렉터리가 아닙니다. - - - - - Invalid deployment item: the path must contain at least one character. - 잘못된 배포 항목: 경로에는 하나 이상의 문자가 포함되어 있어야 합니다. - - - - - deployment item '{0}' (output directory '{1}') - 배포 항목 '{0}'(출력 디렉터리 '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter의 '{1}' 설정에서 예기치 않은 요소 '{0}'이(가) 발견되었습니다. 이 요소를 제거하고 다시 시도하세요. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - 테스트 실행 배포 문제: 어셈블리 또는 모듈 '{0}'을(를) 찾을 수 없습니다. 이유: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - 테스트 실행 배포 문제: 어셈블리 또는 모듈 '{0}'을(를) 찾을 수 없습니다. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - 테스트 구성 설정에서 데이터 원본 '{0}'을(를) 찾을 수 없습니다. - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - 단위 테스트 어댑터가 데이터 원본에 연결하거나 데이터를 읽지 못했습니다. 이 오류를 해결하는 방법에 대한 자세한 내용은 MSDN 라이브러리에서 "데이터 기반 단위 테스트 문제 해결"(http://go.microsoft.com/fwlink/?LinkId=62412)을 참조하십시오. 오류 세부 정보: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - 순열의 개체 수가 잘못되었습니다. 개체 수는 0보다 커야 합니다. - - - - - + + + + + + Could not find file '{0}'. + '{0}' 파일을 찾을 수 없습니다. + + + + The parameter should not be null or empty. + 매개 변수는 null이거나 비워 둘 수 없습니다. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + 테스트 실행 배포 문제: 잘못된 배포 항목: '{0}': 출력 디렉터리 '{1}'에서 항목을 배포 루트 디렉터리 외부에 배포하도록 지정하며 이는 허용되지 않습니다. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + 테스트 실행 배포 문제: 배포 항목 '{0}'에 의해 지정된 출력 디렉터리 '{1}'에 액세스하지 못했습니다. 항목이 배포되지 않음: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + 테스트 실행 배포 문제: '{0}' 파일에 액세스하지 못함: {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + 테스트 실행 배포 문제: '{0}' 파일을 '{1}'에 복사하지 못함: {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + 테스트 실행 배포 문제: 테스트 스토리지 '{0}'에 대한 종속성을 배포하지 못함: {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + 테스트 실행 배포 문제: {0}에 대한 파일을 가져오지 못함: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + 테스트 실행 배포 문제: {0}에 대한 위성 어셈블리를 가져오는 동안 오류 발생: {1}: {2} + + + + deployment item '{0}' + 배포 항목 '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + 잘못된 배포 항목: 지정된 경로 '{0}' 또는 출력 디렉터리 '{1}'에 잘못된 문자가 들어 있습니다. + + + + Invalid deployment item: the output directory cannot be null. + 잘못된 배포 항목: 출력 디렉터리는 null일 수 없습니다. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + 잘못된 배포 항목: 지정된 출력 디렉터리 '{0}'이(가) 상대 디렉터리가 아닙니다. + + + + Invalid deployment item: the path must contain at least one character. + 잘못된 배포 항목: 경로에는 하나 이상의 문자가 포함되어 있어야 합니다. + + + + deployment item '{0}' (output directory '{1}') + 배포 항목 '{0}'(출력 디렉터리 '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter의 '{1}' 설정에서 예기치 않은 요소 '{0}'이(가) 발견되었습니다. 이 요소를 제거하고 다시 시도하세요. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + 테스트 실행 배포 문제: 어셈블리 또는 모듈 '{0}'을(를) 찾을 수 없습니다. 이유: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + 테스트 실행 배포 문제: 어셈블리 또는 모듈 '{0}'을(를) 찾을 수 없습니다. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + 테스트 구성 설정에서 데이터 원본 '{0}'을(를) 찾을 수 없습니다. + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + 단위 테스트 어댑터가 데이터 원본에 연결하거나 데이터를 읽지 못했습니다. 이 오류를 해결하는 방법에 대한 자세한 내용은 MSDN 라이브러리에서 "데이터 기반 단위 테스트 문제 해결"(http://go.microsoft.com/fwlink/?LinkId=62412)을 참조하십시오. 오류 세부 정보: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + 순열의 개체 수가 잘못되었습니다. 개체 수는 0보다 커야 합니다. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pl.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pl.xlf index 5d1542ec5..800a7ee4d 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pl.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pl.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Nie można odnaleźć pliku „{0}”. - - - - - The parameter should not be null or empty. - Parametr nie może mieć wartości null ani być pusty. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problem wdrażania przebiegu testu: nieprawidłowy element wdrożenia: „{0}”: katalog wyjściowy „{1}” określa element do wdrożenia poza głównym katalogiem wdrożenia. Taka sytuacja jest niedozwolona. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problem wdrażania przebiegu testu: nie można uzyskać dostępu do katalogu wyjściowego „{1}” określonego przy użyciu elementu wdrożenia „{0}”. Nie można wdrożyć elementu: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problem wdrażania przebiegu testu: nie można uzyskać dostępu do pliku „{0}”: {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problem wdrażania przebiegu testu: nie można skopiować pliku „{0}” do „{1}”: {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problem wdrażania przebiegu testu: nie można wdrożyć zależności dla magazynu testowego „{0}”: {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problem wdrażania przebiegu testu: nie można uzyskać pliku dla elementu {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problem wdrażania przebiegu testu: wystąpił błąd podczas pobierania zestawów satelickich dla elementu {0}: {1}: {2} - - - - - deployment item '{0}' - element wdrożenia „{0}” - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Nieprawidłowy element wdrożenia: wybrana ścieżka „{0}” lub katalog wyjściowy „{1}” zawiera niedozwolone znaki. - - - - - Invalid deployment item: the output directory cannot be null. - Nieprawidłowy element wdrożenia: katalog wyjściowy nie może mieć wartości null. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Nieprawidłowy element wdrożenia: wybrany katalog wyjściowy „{0}” nie jest względny. - - - - - Invalid deployment item: the path must contain at least one character. - Nieprawidłowy element wdrożenia: ścieżka musi zawierać co najmniej jeden znak. - - - - - deployment item '{0}' (output directory '{1}') - element wdrożenia „{0}” (katalog wyjściowy „{1}”) - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - Adapter MSTestAdapter napotkał nieoczekiwany element „{0}” w ustawieniach „{1}”. Usuń ten element i spróbuj ponownie. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problem wdrażania przebiegu testu: nie znaleziono zestawu lub modułu „{0}”. Przyczyna: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problem wdrażania przebiegu testu: nie znaleziono zestawu lub modułu „{0}”. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - W ustawieniach konfiguracji testu nie można znaleźć źródła danych „{0}” - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - Adapter testu jednostkowego nie mógł połączyć się ze źródłem danych lub odczytać danych. Aby uzyskać więcej informacji o rozwiązywaniu tego błędu, zobacz „Rozwiązywanie problemów z testami jednostkowymi sterowanymi danymi” (http://go.microsoft.com/fwlink/?LinkId=62412) w bibliotece MSDN. Szczegóły błędu: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Nieprawidłowa liczba obiektów permutacji. Ta liczba powinna być większa od zera. - - - - - + + + + + + Could not find file '{0}'. + Nie można odnaleźć pliku „{0}”. + + + + The parameter should not be null or empty. + Parametr nie może mieć wartości null ani być pusty. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problem wdrażania przebiegu testu: nieprawidłowy element wdrożenia: „{0}”: katalog wyjściowy „{1}” określa element do wdrożenia poza głównym katalogiem wdrożenia. Taka sytuacja jest niedozwolona. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problem wdrażania przebiegu testu: nie można uzyskać dostępu do katalogu wyjściowego „{1}” określonego przy użyciu elementu wdrożenia „{0}”. Nie można wdrożyć elementu: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problem wdrażania przebiegu testu: nie można uzyskać dostępu do pliku „{0}”: {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problem wdrażania przebiegu testu: nie można skopiować pliku „{0}” do „{1}”: {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problem wdrażania przebiegu testu: nie można wdrożyć zależności dla magazynu testowego „{0}”: {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problem wdrażania przebiegu testu: nie można uzyskać pliku dla elementu {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problem wdrażania przebiegu testu: wystąpił błąd podczas pobierania zestawów satelickich dla elementu {0}: {1}: {2} + + + + deployment item '{0}' + element wdrożenia „{0}” + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Nieprawidłowy element wdrożenia: wybrana ścieżka „{0}” lub katalog wyjściowy „{1}” zawiera niedozwolone znaki. + + + + Invalid deployment item: the output directory cannot be null. + Nieprawidłowy element wdrożenia: katalog wyjściowy nie może mieć wartości null. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Nieprawidłowy element wdrożenia: wybrany katalog wyjściowy „{0}” nie jest względny. + + + + Invalid deployment item: the path must contain at least one character. + Nieprawidłowy element wdrożenia: ścieżka musi zawierać co najmniej jeden znak. + + + + deployment item '{0}' (output directory '{1}') + element wdrożenia „{0}” (katalog wyjściowy „{1}”) + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + Adapter MSTestAdapter napotkał nieoczekiwany element „{0}” w ustawieniach „{1}”. Usuń ten element i spróbuj ponownie. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problem wdrażania przebiegu testu: nie znaleziono zestawu lub modułu „{0}”. Przyczyna: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problem wdrażania przebiegu testu: nie znaleziono zestawu lub modułu „{0}”. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + W ustawieniach konfiguracji testu nie można znaleźć źródła danych „{0}” + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + Adapter testu jednostkowego nie mógł połączyć się ze źródłem danych lub odczytać danych. Aby uzyskać więcej informacji o rozwiązywaniu tego błędu, zobacz „Rozwiązywanie problemów z testami jednostkowymi sterowanymi danymi” (http://go.microsoft.com/fwlink/?LinkId=62412) w bibliotece MSDN. Szczegóły błędu: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Nieprawidłowa liczba obiektów permutacji. Ta liczba powinna być większa od zera. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pt-BR.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pt-BR.xlf index 321431f5f..8e9b0e482 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pt-BR.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.pt-BR.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Não foi possível encontrar o arquivo '{0}'. - - - - - The parameter should not be null or empty. - O parâmetro não deve ser nulo ou vazio. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Problema de implantação de Execução de Teste: item de implantação inválido: '{0}': o diretório de saída '{1}' especifica o item a ser implantado fora do diretório raiz de implantação, o que não é permitido. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Problema de implantação de Execução de Teste: falha ao acessar o diretório de saída '{1}' especificado pelo item de implantação '{0}', o item não será implantado: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Problema de implantação de Execução de Teste: falha ao acessar o arquivo '{0}': {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Problema de implantação de Execução de Teste: falha ao copiar o arquivo '{0}' em '{1}': {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Problema de implantação de Execução de Teste: falha ao implantar dependências para o armazenamento de teste '{0}': {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Problema de implantação de Execução de Teste: falha ao obter o arquivo para {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Problema de implantação de Execução de Teste: ocorreu um erro ao obter assemblies satélites para {0}: {1}: {2} - - - - - deployment item '{0}' - item de implantação '{0}' - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Item de implantação inválido: o caminho especificado '{0}' ou o diretório de saída '{1}' contém caracteres ilegais. - - - - - Invalid deployment item: the output directory cannot be null. - Item de implantação inválido: o diretório de saída não pode ser nulo. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Item de implantação inválido: o diretório de saída '{0}' especificado não é relativo. - - - - - Invalid deployment item: the path must contain at least one character. - Item de implantação inválido: o caminho deve conter ao menos um caractere. - - - - - deployment item '{0}' (output directory '{1}') - item de implantação '{0}' (diretório de saída '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter encontrou um elemento inesperado '{0}' em suas configurações '{1}'. Remova este elemento e tente novamente. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Problema de implantação de Execução de Teste: o assembly ou módulo '{0}' não foi encontrado. Motivo: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Problema de implantação de Execução de Teste: o assembly ou módulo '{0}' não foi encontrado. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - A fonte de dados '{0}' não pode ser encontrada nas configurações de teste - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - O adaptador de teste de unidade falhou ao conectar-se à fonte de dados ou ao ler os dados. Para obter mais informações sobre como solucionar esse erro, consulte "Solucionando Problemas em Testes de Unidade Controlados por Dados" (http://go.microsoft.com/fwlink/?LinkId=62412) na Biblioteca do MSDN. Detalhes do erro: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Número incorreto de objetos para permutação. Deve ser maior que zero. - - - - - + + + + + + Could not find file '{0}'. + Não foi possível encontrar o arquivo '{0}'. + + + + The parameter should not be null or empty. + O parâmetro não deve ser nulo ou vazio. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Problema de implantação de Execução de Teste: item de implantação inválido: '{0}': o diretório de saída '{1}' especifica o item a ser implantado fora do diretório raiz de implantação, o que não é permitido. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Problema de implantação de Execução de Teste: falha ao acessar o diretório de saída '{1}' especificado pelo item de implantação '{0}', o item não será implantado: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Problema de implantação de Execução de Teste: falha ao acessar o arquivo '{0}': {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Problema de implantação de Execução de Teste: falha ao copiar o arquivo '{0}' em '{1}': {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Problema de implantação de Execução de Teste: falha ao implantar dependências para o armazenamento de teste '{0}': {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Problema de implantação de Execução de Teste: falha ao obter o arquivo para {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Problema de implantação de Execução de Teste: ocorreu um erro ao obter assemblies satélites para {0}: {1}: {2} + + + + deployment item '{0}' + item de implantação '{0}' + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Item de implantação inválido: o caminho especificado '{0}' ou o diretório de saída '{1}' contém caracteres ilegais. + + + + Invalid deployment item: the output directory cannot be null. + Item de implantação inválido: o diretório de saída não pode ser nulo. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Item de implantação inválido: o diretório de saída '{0}' especificado não é relativo. + + + + Invalid deployment item: the path must contain at least one character. + Item de implantação inválido: o caminho deve conter ao menos um caractere. + + + + deployment item '{0}' (output directory '{1}') + item de implantação '{0}' (diretório de saída '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter encontrou um elemento inesperado '{0}' em suas configurações '{1}'. Remova este elemento e tente novamente. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Problema de implantação de Execução de Teste: o assembly ou módulo '{0}' não foi encontrado. Motivo: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Problema de implantação de Execução de Teste: o assembly ou módulo '{0}' não foi encontrado. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + A fonte de dados '{0}' não pode ser encontrada nas configurações de teste + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + O adaptador de teste de unidade falhou ao conectar-se à fonte de dados ou ao ler os dados. Para obter mais informações sobre como solucionar esse erro, consulte "Solucionando Problemas em Testes de Unidade Controlados por Dados" (http://go.microsoft.com/fwlink/?LinkId=62412) na Biblioteca do MSDN. Detalhes do erro: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Número incorreto de objetos para permutação. Deve ser maior que zero. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ru.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ru.xlf index 665163b7a..e1676f0d5 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ru.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.ru.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - Не удалось найти файл "{0}". - - - - - The parameter should not be null or empty. - Этот параметр не должен быть пустым или иметь значение NULL. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Ошибка развертывания при тестовом запуске: недопустимый элемент развертывания "{0}". В выходном каталоге "{1}" указано, что развертывание этого элемента должно быть выполнено не в корневом каталоге развертывания, что запрещено. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Ошибка развертывания тестового запуска: не удалось получить доступ к выходному каталогу "{1}", указанному элементом развертывания "{0}"; элемент не будет развернут: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Ошибка развертывания тестового запуска: не удалось получить доступ к файлу "{0}": {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Ошибка развертывания тестового запуска: не удалось скопировать файл "{0}" в "{1}": {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Ошибка развертывания тестового запуска: не удалось развернуть зависимости для тестового хранилища "{0}": {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Ошибка развертывания тестового запуска: не удалось получить файл для {0}: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Ошибка развертывания тестового запуска: произошла ошибка при получении вспомогательных сборок для {0}: {1}: {2} - - - - - deployment item '{0}' - элемент развертывания "{0}" - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Недопустимый элемент развертывания: указанный путь "{0}" или выходной каталог "{1}" содержат недопустимые символы. - - - - - Invalid deployment item: the output directory cannot be null. - Недопустимый элемент развертывания: выходной каталог не может быть NULL. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Недопустимый элемент развертывания: указанный выходной каталог "{0}" не является относительным. - - - - - Invalid deployment item: the path must contain at least one character. - Недопустимый элемент развертывания: путь должен содержать по меньшей мере один символ. - - - - - deployment item '{0}' (output directory '{1}') - элемент развертывания "{0}" (выходной каталог "{1}") - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter обнаружил непредвиденный элемент "{0}" в параметрах "{1}". Удалите этот элемент и повторите попытку. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Ошибка развертывания тестового запуска: не удалось найти сборку или модуль "{0}". Причина: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Ошибка развертывания тестового запуска: не удалось найти сборку или модуль "{0}". - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - Не удалось найти источник данных "{0}" в параметрах конфигурации теста - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - Адаптеру модульных тестов не удалось подключиться к источнику данных, чтобы считать данные. Дополнительные сведения об устранении этой ошибки см. в разделе "Устранение неполадок в модульных тестах на основе данных" (http://go.microsoft.com/fwlink/?LinkId=62412) в библиотеке MSDN. Подробности об ошибке: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Неправильное число объектов для перестановки. Оно должно быть больше нуля. - - - - - + + + + + + Could not find file '{0}'. + Не удалось найти файл "{0}". + + + + The parameter should not be null or empty. + Этот параметр не должен быть пустым или иметь значение NULL. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Ошибка развертывания при тестовом запуске: недопустимый элемент развертывания "{0}". В выходном каталоге "{1}" указано, что развертывание этого элемента должно быть выполнено не в корневом каталоге развертывания, что запрещено. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Ошибка развертывания тестового запуска: не удалось получить доступ к выходному каталогу "{1}", указанному элементом развертывания "{0}"; элемент не будет развернут: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Ошибка развертывания тестового запуска: не удалось получить доступ к файлу "{0}": {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Ошибка развертывания тестового запуска: не удалось скопировать файл "{0}" в "{1}": {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Ошибка развертывания тестового запуска: не удалось развернуть зависимости для тестового хранилища "{0}": {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Ошибка развертывания тестового запуска: не удалось получить файл для {0}: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Ошибка развертывания тестового запуска: произошла ошибка при получении вспомогательных сборок для {0}: {1}: {2} + + + + deployment item '{0}' + элемент развертывания "{0}" + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Недопустимый элемент развертывания: указанный путь "{0}" или выходной каталог "{1}" содержат недопустимые символы. + + + + Invalid deployment item: the output directory cannot be null. + Недопустимый элемент развертывания: выходной каталог не может быть NULL. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Недопустимый элемент развертывания: указанный выходной каталог "{0}" не является относительным. + + + + Invalid deployment item: the path must contain at least one character. + Недопустимый элемент развертывания: путь должен содержать по меньшей мере один символ. + + + + deployment item '{0}' (output directory '{1}') + элемент развертывания "{0}" (выходной каталог "{1}") + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter обнаружил непредвиденный элемент "{0}" в параметрах "{1}". Удалите этот элемент и повторите попытку. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Ошибка развертывания тестового запуска: не удалось найти сборку или модуль "{0}". Причина: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Ошибка развертывания тестового запуска: не удалось найти сборку или модуль "{0}". + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + Не удалось найти источник данных "{0}" в параметрах конфигурации теста + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + Адаптеру модульных тестов не удалось подключиться к источнику данных, чтобы считать данные. Дополнительные сведения об устранении этой ошибки см. в разделе "Устранение неполадок в модульных тестах на основе данных" (http://go.microsoft.com/fwlink/?LinkId=62412) в библиотеке MSDN. Подробности об ошибке: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Неправильное число объектов для перестановки. Оно должно быть больше нуля. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.tr.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.tr.xlf index 866672c27..34c368a2e 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.tr.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.tr.xlf @@ -1,139 +1,117 @@ - - - - - - Could not find file '{0}'. - '{0}' adlı dosya bulunamadı. - - - - - The parameter should not be null or empty. - Parametre null veya boş olmamalıdır. - - - - - Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. - Test Çalıştırması dağıtım sorunu: '{0}' dağıtım öğesi hatalı: '{1}' çıktı dizininde öğenin dağıtım kök dizini dışında dağıtılması gerektiği belirtilmiş, ancak buna izin verilmiyor. - - - - - Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} - Test Çalıştırması dağıtım sorunu: '{0}' dağıtım öğesi tarafından belirtilen '{1}' çıktı dizinine erişilemedi, öğe dağıtılmayacak: {2}: {3} - - - - - Test Run deployment issue: Failed to access the file '{0}': {1}: {2} - Test Çalıştırması dağıtım sorunu: '{0}' adlı dosyaya erişilemedi: {1}: {2} - - - - - Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} - Test Çalıştırması dağıtım sorunu: '{0}' dosyası '{1}' hedefine kopyalanamadı: {2}: {3} - - - - - Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} - Test Çalıştırması dağıtım sorunu: '{0}' adlı test depolama alanı için bağımlılıklar dağıtılamadı: {1} - - - - - Test Run deployment issue: Failed to get the file for {0}: {1}: {2} - Test Çalıştırması dağıtım sorunu: {0} için dosya alınamadı: {1}: {2} - - - - - Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} - Test Çalıştırması dağıtım sorunu: {0} için uydu bütünleştirilmiş kodları alınırken bir hata oluştu: {1}: {2} - - - - - deployment item '{0}' - '{0}' dağıtım öğesi - - - - - Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. - Geçersiz dağıtım öğesi: Belirtilen '{0}' yolu veya '{1}' çıktı dizini geçersiz karakterler içeriyor. - - - - - Invalid deployment item: the output directory cannot be null. - Geçersiz dağıtım öğesi: Çıktı dizini null olamaz. - - - - - Invalid deployment item: the specified output directory '{0}' is not relative. - Geçersiz dağıtım öğesi: Belirtilen '{0}' çıktı dizini göreli değil. - - - - - Invalid deployment item: the path must contain at least one character. - Geçersiz dağıtım öğesi: Yol, en az bir karakter içermelidir. - - - - - deployment item '{0}' (output directory '{1}') - '{0}' dağıtım öğesi (çıktı dizini '{1}') - - - - - MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. - MSTestAdapter, '{1}' ayarlarında beklenmedik bir öğeyle ('{0}') karşılaştı. Bu öğeyi kaldırıp yeniden deneyin. - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} - Test Çalıştırması dağıtım sorunu: '{0}' adlı bütünleştirilmiş kod veya modül bulunamadı. Nedeni: {1} - - - - - Test Run deployment issue: The assembly or module '{0}' was not found. - Test Çalıştırması dağıtım sorunu: '{0}' adlı bütünleştirilmiş kod veya modül bulunamadı. - - - - - {0}_{1} {2} - {0}_{1} {2} - - - - - Data source '{0}' cannot be found in the test configuration settings - Test yapılandırması ayarlarında '{0}' adlı veri kaynağı bulunamıyor - - - - - The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} - Birim test bağdaştırıcısı, veri kaynağına bağlanamadı veya verileri okuyamadı. Bu hata ile ilgili daha fazla sorun giderme bilgisi için MSDN Kitaplığı'ndaki "Veri Temelli Birim Testleriyle İlgili Sorunları Giderme" (http://go.microsoft.com/fwlink/?LinkId=62412) konusuna bakın. Hata ayrıntıları: {0} - - - - - Wrong number of objects for permutation. Should be greater than zero. - Permütasyon için nesne sayısı yanlış. Değer, sıfırdan büyük olmalıdır. - - - - - + + + + + + Could not find file '{0}'. + '{0}' adlı dosya bulunamadı. + + + + The parameter should not be null or empty. + Parametre null veya boş olmamalıdır. + + + + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. + Test Çalıştırması dağıtım sorunu: '{0}' dağıtım öğesi hatalı: '{1}' çıktı dizininde öğenin dağıtım kök dizini dışında dağıtılması gerektiği belirtilmiş, ancak buna izin verilmiyor. + + + + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} + Test Çalıştırması dağıtım sorunu: '{0}' dağıtım öğesi tarafından belirtilen '{1}' çıktı dizinine erişilemedi, öğe dağıtılmayacak: {2}: {3} + + + + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} + Test Çalıştırması dağıtım sorunu: '{0}' adlı dosyaya erişilemedi: {1}: {2} + + + + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} + Test Çalıştırması dağıtım sorunu: '{0}' dosyası '{1}' hedefine kopyalanamadı: {2}: {3} + + + + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} + Test Çalıştırması dağıtım sorunu: '{0}' adlı test depolama alanı için bağımlılıklar dağıtılamadı: {1} + + + + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} + Test Çalıştırması dağıtım sorunu: {0} için dosya alınamadı: {1}: {2} + + + + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} + Test Çalıştırması dağıtım sorunu: {0} için uydu bütünleştirilmiş kodları alınırken bir hata oluştu: {1}: {2} + + + + deployment item '{0}' + '{0}' dağıtım öğesi + + + + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. + Geçersiz dağıtım öğesi: Belirtilen '{0}' yolu veya '{1}' çıktı dizini geçersiz karakterler içeriyor. + + + + Invalid deployment item: the output directory cannot be null. + Geçersiz dağıtım öğesi: Çıktı dizini null olamaz. + + + + Invalid deployment item: the specified output directory '{0}' is not relative. + Geçersiz dağıtım öğesi: Belirtilen '{0}' çıktı dizini göreli değil. + + + + Invalid deployment item: the path must contain at least one character. + Geçersiz dağıtım öğesi: Yol, en az bir karakter içermelidir. + + + + deployment item '{0}' (output directory '{1}') + '{0}' dağıtım öğesi (çıktı dizini '{1}') + + + + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. + MSTestAdapter, '{1}' ayarlarında beklenmedik bir öğeyle ('{0}') karşılaştı. Bu öğeyi kaldırıp yeniden deneyin. + + + + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} + Test Çalıştırması dağıtım sorunu: '{0}' adlı bütünleştirilmiş kod veya modül bulunamadı. Nedeni: {1} + + + + Test Run deployment issue: The assembly or module '{0}' was not found. + Test Çalıştırması dağıtım sorunu: '{0}' adlı bütünleştirilmiş kod veya modül bulunamadı. + + + + {0}_{1} {2} + {0}_{1} {2} + + + + Data source '{0}' cannot be found in the test configuration settings + Test yapılandırması ayarlarında '{0}' adlı veri kaynağı bulunamıyor + + + + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} + Birim test bağdaştırıcısı, veri kaynağına bağlanamadı veya verileri okuyamadı. Bu hata ile ilgili daha fazla sorun giderme bilgisi için MSDN Kitaplığı'ndaki "Veri Temelli Birim Testleriyle İlgili Sorunları Giderme" (http://go.microsoft.com/fwlink/?LinkId=62412) konusuna bakın. Hata ayrıntıları: {0} + + + + Wrong number of objects for permutation. Should be greater than zero. + Permütasyon için nesne sayısı yanlış. Değer, sıfırdan büyük olmalıdır. + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hans.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hans.xlf index d14c29657..d87eaa37c 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hans.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hans.xlf @@ -5,134 +5,112 @@ Could not find file '{0}'. 找不到文件“{0}”。 - - + The parameter should not be null or empty. 参数不应为 NULL 或为空。 - - + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. 测试运行部署问题: 错误的部署项:“{0}”: 输出目录“{1}”指定将该项部署到部署根目录的外部,这是不允许的。 - - + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} 测试运行部署问题: 未能访问由部署项“{0}”指定的输出目录“{1}”,将不会部署该项: {2}: {3} - - + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} 测试运行部署问题: 未能访问文件“{0}”: {1}: {2} - - + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} 测试运行部署问题: 未能将文件“{0}”复制到“{1}”: {2}: {3} - - + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} 测试运行部署问题: 未能部署测试存储区“{0}”的依赖项: {1} - - + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} 测试运行部署问题: 未能获得 {0} 的文件: {1}: {2} - - + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} 测试运行部署问题: 在获取 {0} 的附属程序集时出错: {1}: {2} - - + deployment item '{0}' 部署项“{0}” - - + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. 无效的部署项: 指定的路径“{0}”或输出目录“{1}”包含非法字符。 - - + Invalid deployment item: the output directory cannot be null. 无效的部署项: 输出目录不能为 NULL。 - - + Invalid deployment item: the specified output directory '{0}' is not relative. 无效的部署项: 指定的输出目录“{0}”不相关。 - - + Invalid deployment item: the path must contain at least one character. 无效的部署项: 路径必须包含至少一个字符。 - - + deployment item '{0}' (output directory '{1}') 部署项“{0}”(输出目录“{1}”) - - + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. MSTestAdapter 在其设置“{1}”中遇到意外的元素“{0}”。删除此元素,然后再试一次。 - - + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} 测试运行部署问题: 找不到程序集或模块“{0}”。原因: {1} - - + Test Run deployment issue: The assembly or module '{0}' was not found. 测试运行部署问题: 找不到程序集或模块“{0}”。 - - + {0}_{1} {2} {0}_{1} {2} - - + Data source '{0}' cannot be found in the test configuration settings 在测试配置设置中找不到数据源“{0}” - - + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} 单元测试适配器未能连接到数据源或读取数据。有关解决此错误的详细信息,请查看 MSDN 库中的“数据驱动单元测试疑难解答”(http://go.microsoft.com/fwlink/?LinkId=62412)。错误详细信息: {0} - - + Wrong number of objects for permutation. Should be greater than zero. 排列的对象数不正确。应大于零。 - - + diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hant.xlf b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hant.xlf index 011b5f256..0376c06ae 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hant.xlf +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Resources/xlf/Resource.zh-Hant.xlf @@ -5,134 +5,112 @@ Could not find file '{0}'. 找不到檔案 '{0}'。 - - + The parameter should not be null or empty. 參數不可為 null 或空白。 - - + Test Run deployment issue: Bad deployment item: '{0}': output directory '{1}' specifies the item to be deployed outside deployment root directory which is not allowed. 測試回合部署問題: 部署項目錯誤: '{0}': 輸出目錄 '{1}' 指定要將項目部署到部署根目錄之外,但不允許這情況。 - - + Test Run deployment issue: Failed to access output directory '{1}' specified by deployment item '{0}', the item will not be deployed: {2}: {3} 測試回合部署問題: 無法存取由部署項目 '{0}' 指定的輸出目錄 '{1}',將不會部署該項目: {2}: {3} - - + Test Run deployment issue: Failed to access the file '{0}': {1}: {2} 測試回合部署問題: 無法存取檔案 '{0}': {1}: {2} - - + Test Run deployment issue: Failed to copy file '{0}' to '{1}': {2}: {3} 測試回合部署問題: 無法將檔案 '{0}' 複製到 '{1}': {2}: {3} - - + Test Run deployment issue: Failed to deploy dependencies for test storage '{0}': {1} 測試回合部署問題: 無法部署測試儲存區 '{0}' 的相依性: {1} - - + Test Run deployment issue: Failed to get the file for {0}: {1}: {2} 測試回合部署問題: 無法取得 {0} 的檔案: {1}: {2} - - + Test Run deployment issue: an error occurred while getting satellite assemblies for {0}: {1}: {2} 測試回合部署問題: 取得 {0} 的附屬組件時發生錯誤: {1}: {2} - - + deployment item '{0}' 部署項目 '{0}' - - + Invalid deployment item: the specified path '{0}' or output directory '{1}' contains illegal characters. 部署項目無效: 指定的路徑 '{0}' 或輸出目錄 '{1}' 含有非法字元。 - - + Invalid deployment item: the output directory cannot be null. 部署項目無效: 輸出目錄不可為 null。 - - + Invalid deployment item: the specified output directory '{0}' is not relative. 部署項目無效: 指定的輸出目錄 '{0}' 不是相對目錄。 - - + Invalid deployment item: the path must contain at least one character. 部署項目無效: 路徑至少必須包含一個字元。 - - + deployment item '{0}' (output directory '{1}') 部署項目 '{0}' (輸出目錄 '{1}') - - + MSTestAdapter encountered an unexpected element '{0}' in its settings '{1}'. Remove this element and try again. MSTestAdapter 在其設定 '{1}' 中遇到未預期的項目 '{0}'。請移除此項目,然後再試一次。 - - + Test Run deployment issue: The assembly or module '{0}' was not found. Reason: {1} 測試回合部署問題: 找不到組件或模組 '{0}'。原因: {1} - - + Test Run deployment issue: The assembly or module '{0}' was not found. 測試回合部署問題: 找不到組件或模組 '{0}'。 - - + {0}_{1} {2} {0}_{1} {2} - - + Data source '{0}' cannot be found in the test configuration settings 在測試組態設定中找不到資料來源 '{0}' - - + The unit test adapter failed to connect to the data source or to read the data. For more information on troubleshooting this error, see "Troubleshooting Data-Driven Unit Tests" (http://go.microsoft.com/fwlink/?LinkId=62412) in the MSDN Library. Error details: {0} 單元測試配接器無法連接至資料來源或無法讀取資料。如需為此錯誤進行疑難排解的詳細資訊,請參閱 MSDN Library 上的<如何:建立資料驅動型單元測試>(http://go.microsoft.com/fwlink/?LinkId=62412)。錯誤詳細資料: {0} - - + Wrong number of objects for permutation. Should be greater than zero. 排列的物件數目錯誤。應大於零。 - - + diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13MSTestAdapterSettings.cs b/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13MSTestAdapterSettings.cs index 00b2fb794..e6ebf6388 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13MSTestAdapterSettings.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13MSTestAdapterSettings.cs @@ -282,7 +282,7 @@ private void ReadAssemblyResolutionPath(XmlReader reader) { while (reader.NodeType == XmlNodeType.Element) { - if (string.Compare("Directory", reader.Name, StringComparison.OrdinalIgnoreCase) == 0) + if (string.Equals("Directory", reader.Name, StringComparison.OrdinalIgnoreCase)) { string recursiveAttribute = reader.GetAttribute("includeSubDirectories"); @@ -292,7 +292,7 @@ private void ReadAssemblyResolutionPath(XmlReader reader) if (!string.IsNullOrEmpty(path)) { // Do we have to look in sub directory for dependent dll. - var includeSubDirectories = string.Compare(recursiveAttribute, "true", StringComparison.OrdinalIgnoreCase) == 0; + var includeSubDirectories = string.Equals(recursiveAttribute, "true", StringComparison.OrdinalIgnoreCase); this.SearchDirectories.Add(new RecursiveDirectoryPath(path, includeSubDirectories)); } } diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13TestDeployment.cs b/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13TestDeployment.cs index 6a66d03dd..386fb021d 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13TestDeployment.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Services/ns13TestDeployment.cs @@ -139,7 +139,7 @@ public bool Deploy(IEnumerable tests, IRunContext runContext, IFramewo } // Object model currently does not have support for SuspendCodeCoverage. We can remove this once support is added -#if !NETSTANDARD1_5 +#if !NETSTANDARD1_5 && !NET5_0 using (new SuspendCodeCoverage()) #endif { diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentItemUtility.cs b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentItemUtility.cs index ce37f29a4..6565c5348 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentItemUtility.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentItemUtility.cs @@ -181,8 +181,7 @@ private IList GetDeploymentItems(object[] deploymentItemAttribut foreach (DeploymentItemAttribute deploymentItemAttribute in deploymentItemAttributes) { - string warning; - if (this.IsValidDeploymentItem(deploymentItemAttribute.Path, deploymentItemAttribute.OutputDirectory, out warning)) + if (this.IsValidDeploymentItem(deploymentItemAttribute.Path, deploymentItemAttribute.OutputDirectory, out var warning)) { this.AddDeploymentItem(deploymentItems, new DeploymentItem(deploymentItemAttribute.Path, deploymentItemAttribute.OutputDirectory)); } diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentUtilityBase.cs b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentUtilityBase.cs index cfdf44101..9cc8bba3c 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentUtilityBase.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13DeploymentUtilityBase.cs @@ -183,7 +183,7 @@ protected IEnumerable Deploy(IList deploymentItems, stri var filesToDeploy = new List(1); filesToDeploy.Add(deploymentItemFile); - // Find dependencies of test deployment items and deploy them at the same time as master file. + // Find dependencies of test deployment items and deploy them at the same time as the main file. if (deploymentItem.OriginType == DeploymentItemOriginType.PerTestDeployment && this.AssemblyUtility.IsAssemblyExtension(Path.GetExtension(deploymentItemFile))) { diff --git a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13FileUtility.cs b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13FileUtility.cs index 8f672b319..f8d845fba 100644 --- a/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13FileUtility.cs +++ b/src/Adapter/PlatformServices.Shared/netstandard1.3/Utilities/ns13FileUtility.cs @@ -170,8 +170,7 @@ public string FindAndDeployPdb(string destinationFile, string relativeDestinatio { if (this.DoesFileExist(pdbSource)) { - string warning; - pdbDestination = this.CopyFileOverwrite(pdbSource, pdbDestination, out warning); + pdbDestination = this.CopyFileOverwrite(pdbSource, pdbDestination, out var warning); if (!string.IsNullOrEmpty(pdbDestination)) { destToSource.Add(relativePdbDestination, pdbSource); diff --git a/src/Adapter/PlatformServices.Universal/PlatformServices.Universal.csproj b/src/Adapter/PlatformServices.Universal/PlatformServices.Universal.csproj index cec9d7b55..e3c113949 100644 --- a/src/Adapter/PlatformServices.Universal/PlatformServices.Universal.csproj +++ b/src/Adapter/PlatformServices.Universal/PlatformServices.Universal.csproj @@ -1,9 +1,7 @@  - - - ..\..\..\ - - + + + {5D153CAA-80C2-4551-9549-6C406FCEEFB1} Library @@ -14,136 +12,108 @@ UAP 10.0.14393.0 10.0.10240.0 - 15 + 14 + 512 {A5A43C5B-DE2A-4C0C-9213-0A381AF9435A};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - ;2008 + 2008 + + + + true + true + true + PackageReference - - AnyCPU + + + $(Platform) true full false DEBUG;TRACE;NETFX_CORE;WINDOWS_UAP prompt 4 + true - - AnyCPU + + $(Platform) pdbonly true TRACE;NETFX_CORE;WINDOWS_UAP prompt 4 true + false - - ARM - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UAP - ;2008 - full - ARM - false - prompt - true - - - ARM - TRACE;NETFX_CORE;WINDOWS_UAP - true - ;2008 - pdbonly - ARM - false - prompt - true - - - x64 - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UAP - ;2008 - full - x64 - false - prompt - true - - - x64 - TRACE;NETFX_CORE;WINDOWS_UAP - true - ;2008 - pdbonly - x64 - false - prompt - true - - - x86 - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UAP - ;2008 - full - x86 - false - prompt - true - - - x86 - TRACE;NETFX_CORE;WINDOWS_UAP - true - ;2008 - pdbonly - x86 - false - prompt - true - + - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + False + + + {6c9fe494-8315-4667-b3f6-75dc62a62319} + Extension.Core + False + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + False + + - + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + + + Constants.cs - + MarshalByRefObject.cs - + SerializableAttribute.cs - + Services\ns10ReflectionOperations.cs - + Services\ns10DiaSessionOperations.cs - + Services\ns10SettingsProvider.cs - + Services\ns10TestContextImplementation.cs - + Services\ns10TestDataSource.cs - + Services\ns10TestDeployment.cs - + Services\ns10TestSourceHost.cs - + Services\ns10ThreadOperations.cs - + Services\ns10TraceListener.cs - + Services\ns10TraceListenerManager.cs @@ -153,25 +123,9 @@ - - - {6c9fe494-8315-4667-b3f6-75dc62a62319} - Extension.Core - False - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - False - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - False - - 15.0 - + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.Universal/project.json b/src/Adapter/PlatformServices.Universal/project.json deleted file mode 100644 index a459dfaf7..000000000 --- a/src/Adapter/PlatformServices.Universal/project.json +++ /dev/null @@ -1,20 +0,0 @@ -{ - "dependencies": { - "MicroBuild.Core": "0.2.0", - "Microsoft.TestPlatform.ObjectModel": "16.9.0-preview-20201021-10", - "Microsoft.NETCore.UniversalWindowsPlatform": "5.3.0", - - "StyleCop.Analyzers": "1.0.0" - }, - "frameworks": { - "uap10.0.10240": {} - }, - "runtimes": { - "win10-arm": {}, - "win10-arm-aot": {}, - "win10-x86": {}, - "win10-x86-aot": {}, - "win10-x64": {}, - "win10-x64-aot": {} - } -} \ No newline at end of file diff --git a/src/Adapter/PlatformServices.WinUI/Friends.cs b/src/Adapter/PlatformServices.WinUI/Friends.cs new file mode 100644 index 000000000..ddccecfdf --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Friends.cs @@ -0,0 +1,7 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +// Friend assemblies +using System.Runtime.CompilerServices; + +[assembly: InternalsVisibleTo("Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.WinUI.UnitTests, PublicKey=002400000480000094000000060200000024000052534131000400000100010007d1fa57c4aed9f0a32e84aa0faefd0de9e8fd6aec8f87fb03766c834c99921eb23be79ad9d5dcc1dd9ad236132102900b723cf980957fc4e177108fc607774f29e8320e92ea05ece4e821c0a5efe8f1645c4c0c93c1ab99285d622caa652c1dfad63d745d6f2de5f17e5eaf0fc4963d261c8a12436518206dc093344d5ad293")] \ No newline at end of file diff --git a/src/Adapter/PlatformServices.WinUI/PlatformServices.WinUI.csproj b/src/Adapter/PlatformServices.WinUI/PlatformServices.WinUI.csproj new file mode 100644 index 000000000..6d1e0feea --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/PlatformServices.WinUI.csproj @@ -0,0 +1,102 @@ + + + NetCore + + + Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices + Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices + net5.0-windows10.0.18362.0 + + 10.0.18362.0 + 10.0.17763.0 + $(TargetPlatformMinVersion) + true + + false + true + false + true + + + + + + + + + + + + + + + + + + Constants.cs + + + Services\ns10ReflectionOperations.cs + + + Services\ns10DiaSessionOperations.cs + + + Services\ns10TestContextImplementation.cs + + + Services\ns10TestDataSource.cs + + + Services\ns13TestDeployment.cs + + + + + + + + + + + + + + + + + Services\ns10ThreadOperations.cs + + + Services\ns10TraceListener.cs + + + Services\ns10TraceListenerManager.cs + + + + + + + + + + + Resources\Resource.Designer.cs + True + True + Resource.resx + + + + + + Resources\Resource.resx + ResXFileCodeGenerator + Resource.Designer.cs + Designer + Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices + + + + \ No newline at end of file diff --git a/src/Adapter/PlatformServices.WinUI/Properties/AssemblyInfo.cs b/src/Adapter/PlatformServices.WinUI/Properties/AssemblyInfo.cs new file mode 100644 index 000000000..0abb0e7b2 --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Properties/AssemblyInfo.cs @@ -0,0 +1,17 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +using System; +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +[assembly: AssemblyDescription("")] +[assembly: AssemblyCopyright("© Microsoft Corporation. All rights reserved.")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +[assembly: ComVisible(false)] + +[assembly: TypeForwardedTo(typeof(SerializableAttribute))] +[assembly: TypeForwardedTo(typeof(MarshalByRefObject))] \ No newline at end of file diff --git a/src/Adapter/PlatformServices.WinUI/Resources/README.txt b/src/Adapter/PlatformServices.WinUI/Resources/README.txt new file mode 100644 index 000000000..10c545683 --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Resources/README.txt @@ -0,0 +1 @@ +This file is kept to commit Resources directory as language specific resx files needs to be copied here. \ No newline at end of file diff --git a/src/Adapter/PlatformServices.WinUI/Services/WinUIAdapterTraceLogger.cs b/src/Adapter/PlatformServices.WinUI/Services/WinUIAdapterTraceLogger.cs new file mode 100644 index 000000000..2eabfcec3 --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Services/WinUIAdapterTraceLogger.cs @@ -0,0 +1,48 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices +{ + using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface; + using Microsoft.VisualStudio.TestPlatform.ObjectModel; + +#pragma warning disable SA1649 // SA1649FileNameMustMatchTypeName + + /// + /// A service to log any trace messages from the adapter that would be shown in *.TpTrace files. + /// + public class AdapterTraceLogger : IAdapterTraceLogger + { + /// + /// Log an error in a given format. + /// + /// The format. + /// The args. + public void LogError(string format, params object[] args) + { + EqtTrace.ErrorIf(EqtTrace.IsErrorEnabled, format, args); + } + + /// + /// Log a warning in a given format. + /// + /// The format. + /// The args. + public void LogWarning(string format, params object[] args) + { + EqtTrace.WarningIf(EqtTrace.IsWarningEnabled, format, args); + } + + /// + /// Log an information message in a given format. + /// + /// The format. + /// The args. + public void LogInfo(string format, params object[] args) + { + EqtTrace.InfoIf(EqtTrace.IsInfoEnabled, format, args); + } + } + +#pragma warning restore SA1649 // SA1649FileNameMustMatchTypeName +} diff --git a/src/Adapter/PlatformServices.WinUI/Services/WinUIFileOperations.cs b/src/Adapter/PlatformServices.WinUI/Services/WinUIFileOperations.cs new file mode 100644 index 000000000..eb91f87fd --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Services/WinUIFileOperations.cs @@ -0,0 +1,135 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices +{ + using global::System; + using global::System.IO; + using global::System.Reflection; + using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface; + using Microsoft.VisualStudio.TestPlatform.ObjectModel; + +#pragma warning disable SA1649 // SA1649FileNameMustMatchTypeName + + /// + /// The file operations. + /// + public class FileOperations : IFileOperations + { + /// + /// Loads an assembly. + /// + /// The assembly name. + /// + /// Indicates whether this should be a reflection only load. + /// + /// The . + public Assembly LoadAssembly(string assemblyName, bool isReflectionOnly) + { + string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(assemblyName); + return Assembly.Load(new AssemblyName(fileNameWithoutExtension)); + } + + /// + /// Gets the path to the .DLL of the assembly. + /// + /// The assembly. + /// Path to the .DLL of the assembly. + public string GetAssemblyPath(Assembly assembly) + { + return assembly.Location; + } + + /// + /// Verifies if file exists in context. + /// + /// The assembly file name. + /// The . + public bool DoesFileExist(string assemblyFileName) + { + var fileExists = false; + + try + { + var fileNameWithoutPath = Path.GetFileName(assemblyFileName); + var searchTask = Windows.ApplicationModel.Package.Current.InstalledLocation.GetFileAsync(fileNameWithoutPath).AsTask(); + searchTask.Wait(); + fileExists = searchTask.Result != null; + } + catch (Exception) + { + // ignore + } + + return fileExists; + } + + /// + /// Creates a Navigation session for the source file. + /// This is used to get file path and line number information for its components. + /// + /// The source file. + /// A Navigation session instance for the current platform. + /// . + /// + public object CreateNavigationSession(string source) + { + return DiaSessionOperations.CreateNavigationSession(source); + } + + /// + /// Get's the navigation data for a navigation session. + /// + /// The navigation session. + /// The class name. + /// The method name. + /// The min line number. + /// The file name. + public void GetNavigationData(object navigationSession, string className, string methodName, out int minLineNumber, out string fileName) + { + DiaSessionOperations.GetNavigationData(navigationSession, className, methodName, out minLineNumber, out fileName); + } + + /// + /// Dispose's the navigation session instance. + /// + /// The navigation session. + public void DisposeNavigationSession(object navigationSession) + { + DiaSessionOperations.DisposeNavigationSession(navigationSession); + } + + /// + /// Gets the full file path of an assembly file. + /// + /// The assembly file name. + /// The full file path + /// . + /// + public string GetFullFilePath(string assemblyFileName) + { + return (SafeInvoke(() => Path.Combine(Windows.ApplicationModel.Package.Current.InstalledLocation.Path, assemblyFileName)) as string) ?? assemblyFileName; + } + + private static object SafeInvoke(Func action, string messageFormatOnException = null) + { + try + { + return action.Invoke(); + } + catch (Exception exception) + { + if (string.IsNullOrEmpty(messageFormatOnException)) + { + messageFormatOnException = "{0}"; + } + + EqtTrace.ErrorIf(EqtTrace.IsErrorEnabled, messageFormatOnException, exception.Message); + } + + return null; + } + } + +#pragma warning restore SA1649 // SA1649FileNameMustMatchTypeName +} diff --git a/src/Adapter/PlatformServices.WinUI/Services/WinUITestSource.cs b/src/Adapter/PlatformServices.WinUI/Services/WinUITestSource.cs new file mode 100644 index 000000000..4b201042f --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Services/WinUITestSource.cs @@ -0,0 +1,130 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices +{ + using global::System; + using global::System.Collections.Generic; + using global::System.IO; + using global::System.Linq; + using global::System.Reflection; + + using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface; + +#pragma warning disable SA1649 // SA1649FileNameMustMatchTypeName + + /// + /// This platform service is responsible for any data or operations to validate + /// the test sources provided to the adapter. + /// + public class TestSource : ITestSource + { + private const string SystemAssembliesPrefix = "system."; + + private static IEnumerable executableExtensions = new HashSet() + { + Constants.ExeExtension + }; + + private static HashSet systemAssemblies = new HashSet(new string[] + { + "MICROSOFT.CSHARP.DLL", + "MICROSOFT.VISUALBASIC.DLL", + "CLRCOMPRESSION.DLL", + }); + + // Well known platform assemblies. + private static HashSet platformAssemblies = new HashSet(new string[] + { + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.TESTFRAMEWORK.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.TESTFRAMEWORK.EXTENSIONS.CORE.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.CORE.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.COMMON.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.TESTEXECUTOR.CORE.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.EXTENSIONS.MSAPPCONTAINERADAPTER.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.EXTENSIONS.MSPHONEADAPTER.DLL", + "MICROSOFT.VISUALSTUDIO.TESTPLATFORM.OBJECTMODEL.DLL", + "VSTEST_EXECUTIONENGINE_PLATFORMBRIDGE.DLL", + "VSTEST_EXECUTIONENGINE_PLATFORMBRIDGE.WINMD", + "VSTEST.EXECUTIONENGINE.WINDOWSPHONE.DLL", + }); + + /// + /// Gets the set of valid extensions for sources targeting this platform. + /// + public IEnumerable ValidSourceExtensions => new List { Constants.DllExtension, Constants.ExeExtension, Constants.AppxPackageExtension }; + + /// + /// Verifies if the assembly provided is referenced by the source. + /// + /// The assembly name. + /// The source. + /// True if the assembly is referenced. + public bool IsAssemblyReferenced(AssemblyName assemblyName, string source) + { + // This code will get hit when Discovery happens during Run Tests. + // Since Discovery during Discover Tests would have validated the presence of Unit Test Framework as reference, + // no need to do validation again. + // Simply return true. + return true; + } + + /// + /// Gets the set of sources (dll's/exe's) that contain tests. If a source is a package(appx), return the file(dll/exe) that contains tests from it. + /// + /// Sources given to the adapter. + /// Sources that contains tests. . + public IEnumerable GetTestSources(IEnumerable sources) + { + string appxSource; + if ((appxSource = this.FindAppxSource(sources)) != null) + { + var appxSourceDirectory = Path.GetDirectoryName(appxSource); + + List newSources = new List(); + + var fileSearchTask = Windows.ApplicationModel.Package.Current.InstalledLocation.GetFilesAsync().AsTask(); + fileSearchTask.Wait(); + foreach (var filePath in fileSearchTask.Result) + { + var fileName = filePath.Name; + var isExtSupported = + executableExtensions.Any(ext => fileName.EndsWith(ext, StringComparison.OrdinalIgnoreCase)); + + if (isExtSupported && !fileName.StartsWith(SystemAssembliesPrefix, StringComparison.OrdinalIgnoreCase) + && !platformAssemblies.Contains(fileName.ToUpperInvariant()) + && !systemAssemblies.Contains(fileName.ToUpperInvariant())) + { + // WinUI Desktop uses .net 5, which builds both a .dll and an .exe. + // The manifest will provide the .exe, but the tests are inside the .dll, so we replace the name here. + newSources.Add(Path.Combine(appxSourceDirectory, Path.ChangeExtension(fileName, Constants.DllExtension))); + } + } + + return newSources; + } + + return sources; + } + + /// + /// Checks if given list of sources contains any ".appx" source. + /// + /// The list of sources. + /// True if there is an appx source. + private string FindAppxSource(IEnumerable sources) + { + foreach (string source in sources) + { + if (string.Compare(Path.GetExtension(source), Constants.AppxPackageExtension, StringComparison.OrdinalIgnoreCase) == 0) + { + return source; + } + } + + return null; + } + } + +#pragma warning restore SA1649 // SA1649FileNameMustMatchTypeName +} diff --git a/src/Adapter/PlatformServices.WinUI/Services/WinUITestSourceHost.cs b/src/Adapter/PlatformServices.WinUI/Services/WinUITestSourceHost.cs new file mode 100644 index 000000000..574453512 --- /dev/null +++ b/src/Adapter/PlatformServices.WinUI/Services/WinUITestSourceHost.cs @@ -0,0 +1,119 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices +{ + using System; + using System.IO; + + using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface; + using Microsoft.VisualStudio.TestPlatform.ObjectModel; + using Microsoft.VisualStudio.TestPlatform.ObjectModel.Adapter; + + /// + /// A host that loads the test source + /// + public class TestSourceHost : ITestSourceHost + { + private string sourceFileName; + private string currentDirectory = null; + + /// + /// Initializes a new instance of the class. + /// + /// The source file name. + /// The run-settings provided for this session. + /// The handle to the test platform. + public TestSourceHost(string sourceFileName, IRunSettings runSettings, IFrameworkHandle frameworkHandle) + { + this.sourceFileName = sourceFileName; + + // Set the environment context. + this.SetContext(sourceFileName); + } + + /// + /// Setup the isolation host. + /// + public void SetupHost() + { + } + + /// + /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. + /// + public void Dispose() + { + this.ResetContext(); + } + + /// + /// Creates an instance of a given type in the test source host. + /// + /// The type that needs to be created in the host. + /// The arguments to pass to the constructor. + /// This array of arguments must match in number, order, and type the parameters of the constructor to invoke. + /// Pass in null for a constructor with no arguments. + /// + /// An instance of the type created in the host. + /// . + /// + public object CreateInstanceForType(Type type, object[] args) + { + return Activator.CreateInstance(type, args); + } + + /// + /// Sets context required for running tests. + /// + /// + /// source parameter used for setting context + /// + private void SetContext(string source) + { + if (string.IsNullOrEmpty(source)) + { + return; + } + + Exception setWorkingDirectoryException = null; + this.currentDirectory = Directory.GetCurrentDirectory(); + try + { + var dirName = Path.GetDirectoryName(source); + if (string.IsNullOrEmpty(dirName)) + { + dirName = Path.GetDirectoryName(typeof(TestSourceHost).Assembly.Location); + } + + Directory.SetCurrentDirectory(dirName); + } + catch (IOException ex) + { + setWorkingDirectoryException = ex; + } + catch (System.Security.SecurityException ex) + { + setWorkingDirectoryException = ex; + } + + if (setWorkingDirectoryException != null) + { + EqtTrace.Error("MSTestExecutor.SetWorkingDirectory: Failed to set the working directory to '{0}'. {1}", Path.GetDirectoryName(source), setWorkingDirectoryException); + } + } + + /// + /// Resets the context as it was before calling SetContext() + /// + private void ResetContext() + { + if (!string.IsNullOrEmpty(this.currentDirectory)) + { + Directory.SetCurrentDirectory(this.currentDirectory); + } + } + } + +#pragma warning restore SA1649 // SA1649FileNameMustMatchTypeName +} diff --git a/src/Package/MSTest.Internal.TestFx.Documentation.nuspec b/src/Package/MSTest.Internal.TestFx.Documentation.nuspec index 59a08d400..e9d521e80 100644 --- a/src/Package/MSTest.Internal.TestFx.Documentation.nuspec +++ b/src/Package/MSTest.Internal.TestFx.Documentation.nuspec @@ -10,7 +10,8 @@ This is a private nuget package that contains the xml documentation files for MSTest V2 Framework. This is a private nuget package that contains the xml documentation files for MSTest V2 Framework. https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -24,10 +25,6 @@ - - - - diff --git a/src/Package/MSTest.TestAdapter.Enu.nuspec b/src/Package/MSTest.TestAdapter.Enu.nuspec index b11801ed8..b05e80aed 100644 --- a/src/Package/MSTest.TestAdapter.Enu.nuspec +++ b/src/Package/MSTest.TestAdapter.Enu.nuspec @@ -8,15 +8,17 @@ Microsoft Microsoft - The adapter to discover and execute MSTest Framework based tests. + The adapter to discover and execute MSTest Framework based tests. - Supported platforms: - - .NET 4.5.0+ - - .NET Core 1.0+ (Universal Windows Apps 10+) (Visual Studio 2017) - - ASP.NET Core 1.0+ (Visual Studio 2017) + Supported platforms: + - .NET 4.5.0+ + - .NET Core 1.0+ (Universal Windows Apps 10+) (Visual Studio 2017) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) + - ASP.NET Core 1.0+ (Visual Studio 2017) https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -27,7 +29,7 @@ - + @@ -37,7 +39,10 @@ - + + + + @@ -63,15 +68,17 @@ + + + + + + - - - - diff --git a/src/Package/MSTest.TestAdapter.nuspec b/src/Package/MSTest.TestAdapter.nuspec index 6f0011374..61c6b21fc 100644 --- a/src/Package/MSTest.TestAdapter.nuspec +++ b/src/Package/MSTest.TestAdapter.nuspec @@ -13,10 +13,12 @@ Supported platforms: - .NET 4.5.0+ - .NET Core 1.0+ (Universal Windows Apps 10+) (Visual Studio 2017) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) - ASP.NET Core 1.0+ (Visual Studio 2017) https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -37,7 +39,10 @@ - + + + + @@ -63,6 +68,12 @@ + + + + + + @@ -73,10 +84,6 @@ - - - - diff --git a/src/Package/MSTest.TestAdapter.symbols.nuspec b/src/Package/MSTest.TestAdapter.symbols.nuspec index 697c607c1..76697185c 100644 --- a/src/Package/MSTest.TestAdapter.symbols.nuspec +++ b/src/Package/MSTest.TestAdapter.symbols.nuspec @@ -8,15 +8,17 @@ Microsoft Microsoft - The adapter to discover and execute MSTest Framework based tests. + The adapter to discover and execute MSTest Framework based tests. - Supported platforms: - - .NET 4.5.0+ - - .NET Core 1.0+ (Universal Windows Apps 10+) (Visual Studio 2017) - - ASP.NET Core 1.0+ (Visual Studio 2017) + Supported platforms: + - .NET 4.5.0+ + - .NET Core 1.0+ (Universal Windows Apps 10+) (Visual Studio 2017) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) + - ASP.NET Core 1.0+ (Visual Studio 2017) https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -36,7 +38,10 @@ - + + + + @@ -62,6 +67,12 @@ + + + + + + @@ -79,6 +90,9 @@ + + + @@ -90,10 +104,6 @@ - - - - diff --git a/src/Package/MSTest.TestFramework.enu.nuspec b/src/Package/MSTest.TestFramework.enu.nuspec index ea3bc4968..de36aaf02 100644 --- a/src/Package/MSTest.TestFramework.enu.nuspec +++ b/src/Package/MSTest.TestFramework.enu.nuspec @@ -14,14 +14,14 @@ Supported platforms: - .NET 4.5.0+ - .NET Core 1.0+ (Universal Windows Apps 10+) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) - ASP.NET Core 1.0+ - To discover and execute tests install MSTest.TestAdapter. - - To discover and execute tests for project.json based projects install dotnet-test-mstest. + To discover and execute tests install MSTest.TestAdapter. https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -65,10 +65,6 @@ - - - - diff --git a/src/Package/MSTest.TestFramework.nuspec b/src/Package/MSTest.TestFramework.nuspec index d7698b58f..e18d299ff 100644 --- a/src/Package/MSTest.TestFramework.nuspec +++ b/src/Package/MSTest.TestFramework.nuspec @@ -14,14 +14,14 @@ Supported platforms: - .NET 4.5.0+ - .NET Core 1.0+ (Universal Windows Apps 10+, DNX Core 5+) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) - ASP.NET Core 1.0+ To discover and execute tests install MSTest.TestAdapter. - - To discover and execute tests for project.json based projects install dotnet-test-mstest. https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -73,10 +73,6 @@ - - - - diff --git a/src/Package/MSTest.TestFramework.symbols.nuspec b/src/Package/MSTest.TestFramework.symbols.nuspec index 86d6927aa..ab9df30e3 100644 --- a/src/Package/MSTest.TestFramework.symbols.nuspec +++ b/src/Package/MSTest.TestFramework.symbols.nuspec @@ -13,14 +13,14 @@ Supported platforms: - .NET 4.5.0+ - .NET Core 1.0+ (Universal Windows Apps 10+) + - .NET 5.0 Windows.17763+ (WinUI Desktop Apps) (Visual Studio 2019) - ASP.NET Core 1.0+ - To discover and execute tests install MSTest.TestAdapter. - - To discover and execute tests for project.json based projects install dotnet-test-mstest. + To discover and execute tests install MSTest.TestAdapter. https://github.com/microsoft/testfx - LICENSE + MIT + https://licenses.nuget.org/MIT http://go.microsoft.com/fwlink/?LinkID=288859 Icon.png © Microsoft Corporation. All rights reserved. @@ -83,10 +83,6 @@ - - - - diff --git a/src/Package/sign/sign.proj b/src/Package/sign/sign.proj index 1c426b309..86f977e61 100644 --- a/src/Package/sign/sign.proj +++ b/src/Package/sign/sign.proj @@ -1,20 +1,20 @@ - + - Test - 0.2.0 + Test + + $([MSBuild]::NormalizeDirectory('$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildProjectDirectory), 'LICENSE'))')) + $(RepoRoot)artifacts\$(BuildConfiguration)\MSTestPackages + $(RepoRoot)artifacts\obj\$(BuildConfiguration)\MSTestPackages + $(RepoRoot)packages + Release - - $(MSBuildThisFileDirectory)..\..\..\ - Release - $(RootDirectory)artifacts\$(BuildConfiguration)\MSTestPackages - $(RootDirectory)artifacts\obj\$(BuildConfiguration)\MSTestPackages - + - - + + diff --git a/src/TestFramework/Extension.Core/Extension.Core.csproj b/src/TestFramework/Extension.Core/Extension.Core.csproj index 1fc52d1a7..b64bb4c4e 100644 --- a/src/TestFramework/Extension.Core/Extension.Core.csproj +++ b/src/TestFramework/Extension.Core/Extension.Core.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {6C9FE494-8315-4667-B3F6-75DC62A62319} Library @@ -34,20 +32,29 @@ $(OutputPath)\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.XML Extensions\Core + - - - - - - + {7252D9E3-267D-442C-96BC-C73AEF3241D6} MSTest.Core False + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + - + + + - + + \ No newline at end of file diff --git a/src/TestFramework/Extension.Core/packages.config b/src/TestFramework/Extension.Core/packages.config deleted file mode 100644 index 56e01ebc8..000000000 --- a/src/TestFramework/Extension.Core/packages.config +++ /dev/null @@ -1,5 +0,0 @@ - - - - - \ No newline at end of file diff --git a/src/TestFramework/Extension.Desktop/Extension.Desktop.csproj b/src/TestFramework/Extension.Desktop/Extension.Desktop.csproj index 078cd59cc..394f23834 100644 --- a/src/TestFramework/Extension.Desktop/Extension.Desktop.csproj +++ b/src/TestFramework/Extension.Desktop/Extension.Desktop.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {A7EA583B-A2B0-47DA-A058-458F247C7575} Library @@ -32,9 +30,7 @@ $(OutputPath)\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.XML Extensions\Desktop - - - + @@ -45,14 +41,23 @@ - - - + + {7252D9E3-267D-442C-96BC-C73AEF3241D6} MSTest.Core False + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + @@ -66,5 +71,6 @@ - + + \ No newline at end of file diff --git a/src/TestFramework/Extension.Desktop/PrivateObject.cs b/src/TestFramework/Extension.Desktop/PrivateObject.cs index a6c656aff..08f8b57a7 100644 --- a/src/TestFramework/Extension.Desktop/PrivateObject.cs +++ b/src/TestFramework/Extension.Desktop/PrivateObject.cs @@ -770,13 +770,13 @@ private void BuildGenericMethodCacheForType(Type t) this.methodCache = new Dictionary>(); MethodInfo[] members = t.GetMethods(BindToEveryThing); - LinkedList listByName; // automatically initialized to null foreach (MethodInfo member in members) { if (member.IsGenericMethod || member.IsGenericMethodDefinition) { - if (!this.GenericMethodCache.TryGetValue(member.Name, out listByName)) + // automatically initialized to null + if (!this.GenericMethodCache.TryGetValue(member.Name, out LinkedList listByName)) { listByName = new LinkedList(); this.GenericMethodCache.Add(member.Name, listByName); @@ -837,9 +837,8 @@ private LinkedList GetMethodCandidates(string methodName, Type[] par Debug.Assert(typeArguments != null, "typeArguments should not be null."); LinkedList methodCandidates = new LinkedList(); - LinkedList methods = null; - if (!this.GenericMethodCache.TryGetValue(methodName, out methods)) + if (!this.GenericMethodCache.TryGetValue(methodName, out var methods)) { return methodCandidates; } diff --git a/src/TestFramework/Extension.Desktop/PrivateType.cs b/src/TestFramework/Extension.Desktop/PrivateType.cs index 413ff1cba..2cb5c15d8 100644 --- a/src/TestFramework/Extension.Desktop/PrivateType.cs +++ b/src/TestFramework/Extension.Desktop/PrivateType.cs @@ -46,12 +46,7 @@ public PrivateType(string assemblyName, string typeName) /// The wrapped Type to create. public PrivateType(Type type) { - if (type == null) - { - throw new ArgumentNullException("type"); - } - - this.type = type; + this.type = type ?? throw new ArgumentNullException(nameof(type)); } /// diff --git a/src/TestFramework/Extension.Desktop/RuntimeTypeHelper.cs b/src/TestFramework/Extension.Desktop/RuntimeTypeHelper.cs index 987a27cf9..078cb90fe 100644 --- a/src/TestFramework/Extension.Desktop/RuntimeTypeHelper.cs +++ b/src/TestFramework/Extension.Desktop/RuntimeTypeHelper.cs @@ -120,7 +120,7 @@ internal static MethodBase SelectMethod(BindingFlags bindingAttr, MethodBase[] m { if (match == null) { - throw new ArgumentNullException("match"); + throw new ArgumentNullException(nameof(match)); } int i; diff --git a/src/TestFramework/Extension.Desktop/packages.config b/src/TestFramework/Extension.Desktop/packages.config deleted file mode 100644 index 631b26d47..000000000 --- a/src/TestFramework/Extension.Desktop/packages.config +++ /dev/null @@ -1,5 +0,0 @@ - - - - - \ No newline at end of file diff --git a/src/TestFramework/Extension.Shared/Extension.Shared.shproj b/src/TestFramework/Extension.Shared/Extension.Shared.shproj index a83b11796..0815b8ece 100644 --- a/src/TestFramework/Extension.Shared/Extension.Shared.shproj +++ b/src/TestFramework/Extension.Shared/Extension.Shared.shproj @@ -4,6 +4,7 @@ 272ca5e1-8e81-4825-9e47-86cce02f700d 14.0 + diff --git a/src/TestFramework/Extension.UWP/Extension.UWP.csproj b/src/TestFramework/Extension.UWP/Extension.UWP.csproj index 443acffef..24ca9effa 100644 --- a/src/TestFramework/Extension.UWP/Extension.UWP.csproj +++ b/src/TestFramework/Extension.UWP/Extension.UWP.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {DF131865-84EE-4540-8112-E88ACEBDEA09} Library @@ -17,115 +15,71 @@ 15 512 {A5A43C5B-DE2A-4C0C-9213-0A381AF9435A};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + 2008 - - AnyCPU + + + true + true + PackageReference + + + + $(Platform) true full false - DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP + DEBUG;TRACE;NETFX_CORE;WINDOWS_UAP prompt 4 + true - - AnyCPU + + $(Platform) pdbonly true - TRACE;NETFX_CORE;WINDOWS_UWP + TRACE;NETFX_CORE;WINDOWS_UAP prompt 4 + true + false - - x86 - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP - ;2008 - full - x86 - false - prompt - - - x86 - TRACE;NETFX_CORE;WINDOWS_UWP - true - ;2008 - pdbonly - x86 - false - prompt - - - ARM - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP - ;2008 - full - ARM - false - prompt - - - ARM - TRACE;NETFX_CORE;WINDOWS_UWP - true - ;2008 - pdbonly - ARM - false - prompt - - - x64 - true - DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP - ;2008 - full - x64 - false - prompt - - - x64 - TRACE;NETFX_CORE;WINDOWS_UWP - true - ;2008 - pdbonly - x64 - false - prompt - + $(OutputPath)\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.XML Extensions\UWP + + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + False + + + - - + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - False - - - + 15.0 - - + + + \ No newline at end of file diff --git a/src/TestFramework/Extension.UWP/project.json b/src/TestFramework/Extension.UWP/project.json deleted file mode 100644 index a739cd4b0..000000000 --- a/src/TestFramework/Extension.UWP/project.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "dependencies": { - "MicroBuild.Core": "0.2.0", - "Microsoft.NETCore.UniversalWindowsPlatform": "5.3.0", - - "StyleCop.Analyzers": "1.0.0" - }, - "frameworks": { - "uap10.0": {} - }, - "runtimes": { - "win10-arm": {}, - "win10-arm-aot": {}, - "win10-x86": {}, - "win10-x86-aot": {}, - "win10-x64": {}, - "win10-x64-aot": {} - } -} \ No newline at end of file diff --git a/src/TestFramework/Extension.WinUI/Extension.WinUI.csproj b/src/TestFramework/Extension.WinUI/Extension.WinUI.csproj index 58aa6b4c4..5ba1aef9a 100644 --- a/src/TestFramework/Extension.WinUI/Extension.WinUI.csproj +++ b/src/TestFramework/Extension.WinUI/Extension.WinUI.csproj @@ -1,4 +1,7 @@  + + NetCore + Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions @@ -7,33 +10,33 @@ Extension.WinUI Extension.WinUI © Microsoft Corporation. All rights reserved. + true net5.0-windows10.0.18362.0 10.0.18362.0 - 10.0.18362.0 - 10.0.18362.0 + 10.0.17763.0 + 10.0.17763.0 false win10-x86;win10-x64;win10-arm64 + + + + + - - ..\..\..\ - NetCore - - - - - + - + + - + @@ -41,6 +44,4 @@ Extensions\WinUI - - diff --git a/src/TestFramework/Extension.WinUI/UITestMethodAttribute.cs b/src/TestFramework/Extension.WinUI/UITestMethodAttribute.cs index db1d3002d..839a9d84e 100644 --- a/src/TestFramework/Extension.WinUI/UITestMethodAttribute.cs +++ b/src/TestFramework/Extension.WinUI/UITestMethodAttribute.cs @@ -12,10 +12,10 @@ namespace Microsoft.VisualStudio.TestTools.UnitTesting.AppContainer public class UITestMethodAttribute : TestMethodAttribute { /// - /// Gets or sets the that should be used to invoke the UITestMethodAttribute. + /// Gets or sets the that should be used to invoke the UITestMethodAttribute. /// If none is provided, it will try to use the Microsoft.UI.Xaml.Window.Current.DispatcherQueue, which only works on UWP. /// - public static Microsoft.System.DispatcherQueue DispatcherQueue { get; set; } + public static Microsoft.UI.Dispatching.DispatcherQueue DispatcherQueue { get; set; } /// /// Executes the test method on the UI Thread. @@ -59,7 +59,7 @@ public override TestResult[] Execute(ITestMethod testMethod) { var taskCompletionSource = new global::System.Threading.Tasks.TaskCompletionSource(); - if (!dispatcher.TryEnqueue(System.DispatcherQueuePriority.Normal, () => + if (!dispatcher.TryEnqueue(Microsoft.UI.Dispatching.DispatcherQueuePriority.Normal, () => { try { diff --git a/src/TestFramework/MSTest.Core/Assertions/Assert.cs b/src/TestFramework/MSTest.Core/Assertions/Assert.cs index 2b0126dc7..ed83d9e09 100644 --- a/src/TestFramework/MSTest.Core/Assertions/Assert.cs +++ b/src/TestFramework/MSTest.Core/Assertions/Assert.cs @@ -483,11 +483,9 @@ public static void AreSame(object expected, object actual, string message, param { string finalMessage = message; - ValueType valExpected = expected as ValueType; - if (valExpected != null) + if (expected is ValueType valExpected) { - ValueType valActual = actual as ValueType; - if (valActual != null) + if (actual is ValueType valActual) { finalMessage = string.Format( CultureInfo.CurrentCulture, @@ -2186,12 +2184,12 @@ public static T ThrowsException(Action action, string message, params object[ if (action == null) { - throw new ArgumentNullException("action"); + throw new ArgumentNullException(nameof(action)); } if (message == null) { - throw new ArgumentNullException("message"); + throw new ArgumentNullException(nameof(message)); } try @@ -2246,7 +2244,7 @@ public static T ThrowsException(Action action, string message, params object[ public static async Task ThrowsExceptionAsync(Func action) where T : Exception { - return await ThrowsExceptionAsync(action, string.Empty, null); + return await ThrowsExceptionAsync(action, string.Empty, null).ConfigureAwait(false); } /// @@ -2268,7 +2266,7 @@ public static async Task ThrowsExceptionAsync(Func action) public static async Task ThrowsExceptionAsync(Func action, string message) where T : Exception { - return await ThrowsExceptionAsync(action, message, null); + return await ThrowsExceptionAsync(action, message, null).ConfigureAwait(false); } /// @@ -2297,17 +2295,17 @@ public static async Task ThrowsExceptionAsync(Func action, string me if (action == null) { - throw new ArgumentNullException("action"); + throw new ArgumentNullException(nameof(action)); } if (message == null) { - throw new ArgumentNullException("message"); + throw new ArgumentNullException(nameof(message)); } try { - await action(); + await action().ConfigureAwait(false); } catch (Exception ex) { diff --git a/src/TestFramework/MSTest.Core/Assertions/CollectionAssert.cs b/src/TestFramework/MSTest.Core/Assertions/CollectionAssert.cs index ea84a4a6f..d1d9a3dd8 100644 --- a/src/TestFramework/MSTest.Core/Assertions/CollectionAssert.cs +++ b/src/TestFramework/MSTest.Core/Assertions/CollectionAssert.cs @@ -350,7 +350,7 @@ public static void AllItemsAreUnique(ICollection collection, string message, par var finalMessage = string.Format( CultureInfo.CurrentCulture, FrameworkMessages.AllItemsAreUniqueFailMsg, - message == null ? string.Empty : message, + message ?? string.Empty, FrameworkMessages.Common_NullInMessages); Assert.HandleFail("CollectionAssert.AllItemsAreUnique", finalMessage, parameters); @@ -363,7 +363,7 @@ public static void AllItemsAreUnique(ICollection collection, string message, par string finalMessage = string.Format( CultureInfo.CurrentCulture, FrameworkMessages.AllItemsAreUniqueFailMsg, - message == null ? string.Empty : message, + message ?? string.Empty, Assert.ReplaceNulls(current)); Assert.HandleFail("CollectionAssert.AllItemsAreUnique", finalMessage, parameters); @@ -648,10 +648,7 @@ public static void AreEquivalent(ICollection expected, ICollection actual, strin } // Search for a mismatched element. - int expectedCount; - int actualCount; - object mismatchedElement; - if (FindMismatchedElement(expected, actual, out expectedCount, out actualCount, out mismatchedElement)) + if (FindMismatchedElement(expected, actual, out var expectedCount, out var actualCount, out var mismatchedElement)) { var finalMessage = string.Format( CultureInfo.CurrentCulture, @@ -776,10 +773,7 @@ public static void AreNotEquivalent(ICollection expected, ICollection actual, st } // Search for a mismatched element. - int expectedCount; - int actualCount; - object mismatchedElement; - if (!FindMismatchedElement(expected, actual, out expectedCount, out actualCount, out mismatchedElement)) + if (!FindMismatchedElement(expected, actual, out var expectedCount, out var actualCount, out var mismatchedElement)) { var finalMessage = string.Format( CultureInfo.CurrentCulture, @@ -874,8 +868,8 @@ public static void AllItemsAreInstancesOfType(ICollection collection, Type expec int i = 0; foreach (object element in collection) { - var elementTypeInfo = element != null ? element.GetType().GetTypeInfo() : null; - var expectedTypeInfo = expectedType != null ? expectedType.GetTypeInfo() : null; + var elementTypeInfo = element?.GetType().GetTypeInfo(); + var expectedTypeInfo = expectedType?.GetTypeInfo(); if (expectedTypeInfo != null && elementTypeInfo != null && !expectedTypeInfo.IsAssignableFrom(elementTypeInfo)) { var finalMessage = string.Format( @@ -1282,10 +1276,8 @@ internal static bool IsSubsetOfHelper(ICollection subset, ICollection superset) // $ CONSIDER: comparison, which should result in ~n*log(n) + m*log(m) + n. // Count the occurrences of each object in both collections. - int subsetNulls; - Dictionary subsetElements = GetElementCounts(subset, out subsetNulls); - int supersetNulls; - Dictionary supersetElements = GetElementCounts(superset, out supersetNulls); + Dictionary subsetElements = GetElementCounts(subset, out var subsetNulls); + Dictionary supersetElements = GetElementCounts(superset, out var supersetNulls); if (subsetNulls > supersetNulls) { @@ -1296,10 +1288,8 @@ internal static bool IsSubsetOfHelper(ICollection subset, ICollection superset) // in the superset. foreach (object element in subsetElements.Keys) { - int subsetCount; - subsetElements.TryGetValue(element, out subsetCount); - int supersetCount; - supersetElements.TryGetValue(element, out supersetCount); + subsetElements.TryGetValue(element, out var subsetCount); + supersetElements.TryGetValue(element, out var supersetCount); if (subsetCount > supersetCount) { @@ -1340,8 +1330,7 @@ internal static bool IsSubsetOfHelper(ICollection subset, ICollection superset) continue; } - int value; - elementCounts.TryGetValue(element, out value); + elementCounts.TryGetValue(element, out var value); value++; elementCounts[element] = value; } @@ -1390,10 +1379,8 @@ private static bool FindMismatchedElement(ICollection expected, ICollection actu // $ CONSIDER: comparison, which should result in ~n*log(n) + m*log(m) + n. // Count the occurrences of each object in the both collections - int expectedNulls; - Dictionary expectedElements = GetElementCounts(expected, out expectedNulls); - int actualNulls; - Dictionary actualElements = GetElementCounts(actual, out actualNulls); + Dictionary expectedElements = GetElementCounts(expected, out var expectedNulls); + Dictionary actualElements = GetElementCounts(actual, out var actualNulls); if (actualNulls != expectedNulls) { diff --git a/src/TestFramework/MSTest.Core/Attributes/ExpectedExceptionAttribute.cs b/src/TestFramework/MSTest.Core/Attributes/ExpectedExceptionAttribute.cs index 274d322c3..a7eb801c5 100644 --- a/src/TestFramework/MSTest.Core/Attributes/ExpectedExceptionAttribute.cs +++ b/src/TestFramework/MSTest.Core/Attributes/ExpectedExceptionAttribute.cs @@ -38,14 +38,14 @@ public ExpectedExceptionAttribute(Type exceptionType, string noExceptionMessage) { if (exceptionType == null) { - throw new ArgumentNullException("exceptionType"); + throw new ArgumentNullException(nameof(exceptionType)); } if (!typeof(Exception).GetTypeInfo().IsAssignableFrom(exceptionType.GetTypeInfo())) { throw new ArgumentException( FrameworkMessages.UTF_ExpectedExceptionTypeMustDeriveFromException, - "exceptionType"); + nameof(exceptionType)); } this.ExceptionType = exceptionType; diff --git a/src/TestFramework/MSTest.Core/GenericParameterHelper.cs b/src/TestFramework/MSTest.Core/GenericParameterHelper.cs index 1d4c40459..dd70833cd 100644 --- a/src/TestFramework/MSTest.Core/GenericParameterHelper.cs +++ b/src/TestFramework/MSTest.Core/GenericParameterHelper.cs @@ -106,8 +106,7 @@ public override int GetHashCode() /// public int CompareTo(object obj) { - GenericParameterHelper gpf = obj as GenericParameterHelper; - if (gpf != null) + if (obj is GenericParameterHelper gpf) { return this.Data.CompareTo(gpf.Data); } diff --git a/src/TestFramework/MSTest.Core/Internal/UtfHelper.cs b/src/TestFramework/MSTest.Core/Internal/UtfHelper.cs index 8d5dec5cf..6797597eb 100644 --- a/src/TestFramework/MSTest.Core/Internal/UtfHelper.cs +++ b/src/TestFramework/MSTest.Core/Internal/UtfHelper.cs @@ -46,13 +46,12 @@ internal static string GetExceptionMsg(Exception ex) curException.GetType()); } - result.Append( - string.Format( + result.AppendFormat( CultureInfo.CurrentCulture, "{0}{1}: {2}", first ? string.Empty : " ---> ", curException.GetType(), - msg)); + msg); first = false; } diff --git a/src/TestFramework/MSTest.Core/Logger.cs b/src/TestFramework/MSTest.Core/Logger.cs index c0c373993..81cc0d156 100644 --- a/src/TestFramework/MSTest.Core/Logger.cs +++ b/src/TestFramework/MSTest.Core/Logger.cs @@ -37,7 +37,7 @@ public static void LogMessage(string format, params object[] args) { if (format == null) { - throw new ArgumentNullException("format"); + throw new ArgumentNullException(nameof(format)); } string message = string.Format(CultureInfo.InvariantCulture, format, args); diff --git a/src/TestFramework/MSTest.Core/MSTest.Core.csproj b/src/TestFramework/MSTest.Core/MSTest.Core.csproj index e21a2e33e..78ddbd21f 100644 --- a/src/TestFramework/MSTest.Core/MSTest.Core.csproj +++ b/src/TestFramework/MSTest.Core/MSTest.Core.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {7252D9E3-267D-442C-96BC-C73AEF3241D6} Library @@ -34,6 +32,16 @@ $(OutputPath)\Microsoft.VisualStudio.TestPlatform.TestFramework.XML Core + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + @@ -69,9 +77,7 @@ - - - + ResXFileCodeGenerator @@ -80,5 +86,6 @@ Designer - + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.cs.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.cs.xlf index fa46bcb23..477cfea3d 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.cs.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.cs.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - Přístupový řetězec má neplatnou syntaxi. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Očekávaná kolekce obsahuje {1} výskytů <{2}>. Aktuální kolekce obsahuje {3} výskytů. {0} - - - - - Duplicate item found:<{1}>. {0} - Byla nalezena duplicitní položka:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Očekáváno:<{1}>. Aktuálně:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Očekáván rozdíl, který není větší jak <{3}> mezi očekávanou hodnotou <{1}> a aktuální hodnotou <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Očekáváno:<{1}>. Případ je rozdílný pro aktuální hodnotu:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Očekáváno:<{1} ({2})>. Aktuálně:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Nebyla očekávána žádná hodnota kromě:<{1}>. Aktuálně:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Očekáván rozdíl, který je větší jak <{3}> mezi očekávanou hodnotou <{1}> a aktuální hodnotou <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Nevkládejte hodnotu typů do AreSame(). Hodnoty převedené do typu Object už nebudou nikdy stejné. Zvažte použití AreEqual(). {0} - - - - - Both collections are empty. {0} - Obě kolekce jsou prázdné. {0} - - - - - Both collection contain same elements. - Obě kolekce obsahují stejné elementy. - - - - - Both collection references point to the same collection object. {0} - Obě reference na kolekci odkazují na stejný objekt kolekce. {0} - - - - - Both collections contain the same elements. {0} - Obě kolekce obsahují stejné elementy. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - Řetězec '{0}' neobsahuje řetězec '{1}'. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Počet elementů v kolekcích nesouhlasí. Očekáváno:<{1}>. Aktuálně:<{2}>.{0} - - - - - Element at index {0} do not match. - Element na indexu {0} nesouhlasí. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - Element na indexu {1} není očekávaného typu. Očekávaný typ:<{2}>. Aktuální typ:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - Element na indexu {1} je (null). Předpokládaný typ:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - Řetězec '{0}' nekončí řetězcem '{1}'. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Neplatný argument- v EqualsTester nelze použít hodnotu null. - - - - - Cannot convert object of type {0} to {1}. - Nelze převést objekt typu {0} na {1}. - - - - - {0} failed. {1} - {0} selhalo. {1} - - - - - The internal object referenced is no longer valid. - Odkaz na vnitřní objekt už není platný. - - - - - The parameter '{0}' is invalid. {1}. - Parametr '{0}' je neplatný. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Očekávaný typ:<{1}>. Aktuální typ:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - Řetězec '{0}' neodpovídá vzoru '{1}'. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Špatný typ:<{1}>. Aktuální typ:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - Řetězec '{0}' odpovídá vzoru '{1}'. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals by neměla být pro kontrolní výrazy používána. Použijte prosím místo toho Assert.AreEqual a její přetížení. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Zadaný člen ({0}) nemohl být nalezen. Je možné, že bude zapotřebí obnovit soukromý přístupový objekt, - nebo může být člen soukromý a definovaný v základní třídě. Pokud je tvrzení pravdivé, bude zapotřebí předat typ - , který definuje člena do konstruktoru PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Konstruktor se zadaným podpisem se nepovedlo najít. Je možné, že bude zapotřebí obnovit soukromý přistupující objekt, - nebo může být člen soukromý a definovaný v základní třídě. Pokud je tvrzení pravdivé, bude zapotřebí předat typ - , který definuje člena do konstruktoru PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Parametr '{0}' je neplatný. Hodnota nemůže být null. {1}. - - - - - Different number of elements. - Rozdílný počet elementů. - - - - - String '{0}' does not start with string '{1}'. {2}. - Řetězec '{0}' nezačíná řetězcem '{1}'. {2}. - - - - - The property {0} has type {1}; expected type {2}. - Vlastnost {0} je typu {1}; očekávaný typ {2}. - - - - - (null) - (null) - - - - - (object) - (objekt) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Typ očekávané výjimky musí být typu System.Exception nebo z něj odvozený. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Testovací metoda nevyvolala výjimku. Atribut {0} definovaný u testovací metody výjimku očekával. - - - - - Test method did not throw expected exception {0}. {1} - Testovací metoda nevyvolala očekávanou výjimku {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Testovací metoda vyvolala výjimku {0}, ale očekávala se výjimka {1}. Zpráva o výjimce: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Testovací metoda vyvolala výjimku {0}, ale očekávala se výjimka {1} nebo od ní odvozený typ. Zpráva o výjimce: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Z důvodu výjimky se nepodařilo získat zprávu o výjimce typu {0}.) - - - - - No exception thrown. {1} exception was expected. {0} - Nebyla vyvolána žádná výjimka. Byla očekávaná {1} výjimka. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - Způsobil výjimku {2}, ale výjimka {1} byla očekávaná. {0} -Zpráva výjimky: {3} -Trasování zásobníku: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Nebyl zadán žádný zdroj testovacích dat. Při použití atributu DataTestMethodAttribute je požadován alespoň jeden atribut TestDataSource. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - async TestMethod s atributem UITestMethodAttribute se nepodporují. Buď odeberte async, nebo použijte TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - Vlastnost nebo metoda {0} v {1} nevrací IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - Hodnota vrácená vlastností nebo metodou {0} by neměla být null. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - Metoda {0} musí odpovídat očekávanému podpisu: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - Vlastnost nebo metoda {0} ve třídě {1} vrací prázdné IEnumerable<object[]>. - - - - - + + + + + + Access string has invalid syntax. + Přístupový řetězec má neplatnou syntaxi. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Očekávaná kolekce obsahuje {1} výskytů <{2}>. Aktuální kolekce obsahuje {3} výskytů. {0} + + + + Duplicate item found:<{1}>. {0} + Byla nalezena duplicitní položka:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Očekáváno:<{1}>. Aktuálně:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Očekáván rozdíl, který není větší jak <{3}> mezi očekávanou hodnotou <{1}> a aktuální hodnotou <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Očekáváno:<{1}>. Případ je rozdílný pro aktuální hodnotu:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Očekáváno:<{1} ({2})>. Aktuálně:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Nebyla očekávána žádná hodnota kromě:<{1}>. Aktuálně:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Očekáván rozdíl, který je větší jak <{3}> mezi očekávanou hodnotou <{1}> a aktuální hodnotou <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Nevkládejte hodnotu typů do AreSame(). Hodnoty převedené do typu Object už nebudou nikdy stejné. Zvažte použití AreEqual(). {0} + + + + Both collections are empty. {0} + Obě kolekce jsou prázdné. {0} + + + + Both collection contain same elements. + Obě kolekce obsahují stejné elementy. + + + + Both collection references point to the same collection object. {0} + Obě reference na kolekci odkazují na stejný objekt kolekce. {0} + + + + Both collections contain the same elements. {0} + Obě kolekce obsahují stejné elementy. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + Řetězec '{0}' neobsahuje řetězec '{1}'. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Počet elementů v kolekcích nesouhlasí. Očekáváno:<{1}>. Aktuálně:<{2}>.{0} + + + + Element at index {0} do not match. + Element na indexu {0} nesouhlasí. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + Element na indexu {1} není očekávaného typu. Očekávaný typ:<{2}>. Aktuální typ:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + Element na indexu {1} je (null). Předpokládaný typ:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + Řetězec '{0}' nekončí řetězcem '{1}'. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Neplatný argument- v EqualsTester nelze použít hodnotu null. + + + + Cannot convert object of type {0} to {1}. + Nelze převést objekt typu {0} na {1}. + + + + {0} failed. {1} + {0} selhalo. {1} + + + + The internal object referenced is no longer valid. + Odkaz na vnitřní objekt už není platný. + + + + The parameter '{0}' is invalid. {1}. + Parametr '{0}' je neplatný. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Očekávaný typ:<{1}>. Aktuální typ:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + Řetězec '{0}' neodpovídá vzoru '{1}'. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Špatný typ:<{1}>. Aktuální typ:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + Řetězec '{0}' odpovídá vzoru '{1}'. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals by neměla být pro kontrolní výrazy používána. Použijte prosím místo toho Assert.AreEqual a její přetížení. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Zadaný člen ({0}) nemohl být nalezen. Je možné, že bude zapotřebí obnovit soukromý přístupový objekt, + nebo může být člen soukromý a definovaný v základní třídě. Pokud je tvrzení pravdivé, bude zapotřebí předat typ + , který definuje člena do konstruktoru PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Konstruktor se zadaným podpisem se nepovedlo najít. Je možné, že bude zapotřebí obnovit soukromý přistupující objekt, + nebo může být člen soukromý a definovaný v základní třídě. Pokud je tvrzení pravdivé, bude zapotřebí předat typ + , který definuje člena do konstruktoru PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Parametr '{0}' je neplatný. Hodnota nemůže být null. {1}. + + + + Different number of elements. + Rozdílný počet elementů. + + + + String '{0}' does not start with string '{1}'. {2}. + Řetězec '{0}' nezačíná řetězcem '{1}'. {2}. + + + + The property {0} has type {1}; expected type {2}. + Vlastnost {0} je typu {1}; očekávaný typ {2}. + + + + (null) + (null) + + + + (object) + (objekt) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Typ očekávané výjimky musí být typu System.Exception nebo z něj odvozený. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Testovací metoda nevyvolala výjimku. Atribut {0} definovaný u testovací metody výjimku očekával. + + + + Test method did not throw expected exception {0}. {1} + Testovací metoda nevyvolala očekávanou výjimku {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Testovací metoda vyvolala výjimku {0}, ale očekávala se výjimka {1}. Zpráva o výjimce: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Testovací metoda vyvolala výjimku {0}, ale očekávala se výjimka {1} nebo od ní odvozený typ. Zpráva o výjimce: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Z důvodu výjimky se nepodařilo získat zprávu o výjimce typu {0}.) + + + + No exception thrown. {1} exception was expected. {0} + Nebyla vyvolána žádná výjimka. Byla očekávaná {1} výjimka. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + Způsobil výjimku {2}, ale výjimka {1} byla očekávaná. {0} +Zpráva výjimky: {3} +Trasování zásobníku: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Nebyl zadán žádný zdroj testovacích dat. Při použití atributu DataTestMethodAttribute je požadován alespoň jeden atribut TestDataSource. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + async TestMethod s atributem UITestMethodAttribute se nepodporují. Buď odeberte async, nebo použijte TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + Vlastnost nebo metoda {0} v {1} nevrací IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + Hodnota vrácená vlastností nebo metodou {0} by neměla být null. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + Metoda {0} musí odpovídat očekávanému podpisu: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + Vlastnost nebo metoda {0} ve třídě {1} vrací prázdné IEnumerable<object[]>. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.de.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.de.xlf index 452589205..c25555d50 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.de.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.de.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - Die Zugriffszeichenfolge weist eine ungültige Syntax auf. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Die erwartete Sammlung enthält {1} Vorkommen von <{2}>. Die tatsächliche Sammlung enthält {3} Vorkommen. {0} - - - - - Duplicate item found:<{1}>. {0} - Doppeltes Element gefunden: <{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Erwartet:<{1}>. Tatsächlich:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Es wurde eine Differenz nicht größer als <{3}> zwischen dem erwarteten Wert <{1}> und dem tatsächlichen Wert <{2}> erwartet. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Erwartet:<{1}>. Die Großschreibung des tatsächlichen Werts weicht davon ab:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Erwartet:<{1} ({2})>. Tatsächlich:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Es wurde ein beliebiger Wert erwartet außer:<{1}>. Tatsächlich:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Es wurde eine Differenz größer als <{3}> zwischen dem erwarteten Wert <{1}> und dem tatsächlichen Wert <{2}> erwartet. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Übergeben Sie keine Werttypen an AreSame(). In ein Objekt konvertierte Werte sind niemals identisch. Verwenden Sie stattdessen AreEqual(). {0} - - - - - Both collections are empty. {0} - Beide Sammlungen sind leer. {0} - - - - - Both collection contain same elements. - Beide Sammlungen enthalten dieselben Elemente. - - - - - Both collection references point to the same collection object. {0} - Beide Sammlungsverweise zeigen auf dasselbe Sammlungsobjekt. {0} - - - - - Both collections contain the same elements. {0} - Beide Sammlungen enthalten dieselben Elemente. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - Die Zeichenfolge "{0}" enthält nicht die Zeichenfolge "{1}". {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Die Anzahl der Elemente in den Sammlungen stimmt nicht überein. Erwartet: <{1}>. Tatsächlich: <{2}>.{0} - - - - - Element at index {0} do not match. - Die Elemente bei Index "{0}" stimmen nicht überein. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - Das Element bei Index "{1}" weist nicht den erwarteten Typ auf. Erwarteter Typ:<{2}>. Tatsächlicher Typ:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - Das Element bei Index "{1}" ist (NULL). Erwarteter Typ:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - Die Zeichenfolge "{0}" endet nicht auf die Zeichenfolge "{1}". {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Ungültiges Argument - EqualsTester kann NULL nicht verwenden. - - - - - Cannot convert object of type {0} to {1}. - Ein Objekt vom Typ "{0}" kann nicht in "{1}" konvertiert werden. - - - - - {0} failed. {1} - Fehler bei "{0}". {1} - - - - - The internal object referenced is no longer valid. - Das interne Objekt, auf das verwiesen wird, ist nicht mehr gültig. - - - - - The parameter '{0}' is invalid. {1}. - Der {0}-Parameter ist ungültig. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0}Erwarteter Typ:<{1}>. Tatsächlicher Typ:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - Die Zeichenfolge "{0}" stimmt nicht mit dem Muster "{1}" überein. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Falscher Typ:<{1}>. Tatsächlicher Typ:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - Die Zeichenfolge "{0}" stimmt mit dem Muster "{1}" überein. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals sollte nicht für Assertions verwendet werden. Verwenden Sie stattdessen Assert.AreEqual und Überladungen. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Der angegebene Member ({0}) wurde nicht gefunden. Sie müssen möglicherweise Ihren privaten Accessor erneut generieren, - oder der Member ist möglicherweise privat und für die Basisklasse definiert. Wenn letzteres zutrifft, müssen Sie den Typ, - der den Member definiert, an den Konstruktor von PrivateObject übergeben. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Der Konstruktor mit der angegebenen Signatur wurde nicht gefunden. Sie müssen möglicherweise Ihren privaten Accessor erneut generieren, - oder der Member ist möglicherweise privat und für die Basisklasse definiert. Wenn letzteres zutrifft, müssen Sie den Typ, - der den Member definiert, an den Konstruktor von PrivateObject übergeben. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Der {0}-Parameter ist ungültig. Der Wert kann nicht NULL sein. {1}. - - - - - Different number of elements. - Unterschiedliche Anzahl von Elementen. - - - - - String '{0}' does not start with string '{1}'. {2}. - Die Zeichenfolge "{0}" beginnt nicht mit der Zeichenfolge "{1}". {2}. - - - - - The property {0} has type {1}; expected type {2}. - Die {0}-Eigenschaft weist den Typ "{1}" auf; Typ "{2}" wird erwartet. - - - - - (null) - (NULL) - - - - - (object) - (Objekt) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Der erwartete Ausnahmentyp muss System.Exception sein oder von System.Exception abgeleitet werden. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Die Testmethode hat keine Ausnahme ausgelöst. Eine Ausnahme wurde vom Attribut "{0}" erwartet, das für die Testmethode definiert wurde. - - - - - Test method did not throw expected exception {0}. {1} - Die Testmethode hat die erwartete Ausnahme "{0}" nicht ausgelöst. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Die Testmethode hat die Ausnahme "{0}" ausgelöst, aber die Ausnahme "{1}" wurde erwartet. Ausnahmemeldung: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Die Testmethode hat die Ausnahme "{0}" ausgelöst, aber die Ausnahme "{1}" oder ein davon abgeleiteter Typ wurde erwartet. Ausnahmemeldung: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Fehler beim Abrufen der Meldung für eine Ausnahme vom Typ "{0}" aufgrund einer Ausnahme.) - - - - - No exception thrown. {1} exception was expected. {0} - Keine Ausnahme ausgelöst. {1}-Ausnahme wurde erwartet. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - Ausnahme {2} ausgelöst, Ausnahme {1} wurde jedoch erwartet. {0} -Ausnahmemeldung: {3} -Stapelüberwachung: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Es wurde keine Testdatenquelle angegeben. Für DataTestMethodAttribute ist mindestens ein TestDataSource-Wert erforderlich. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - "async TestMethod" wird mit UITestMethodAttribute nicht unterstützt. Entfernen Sie "async", oder verwenden Sie TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - Eigenschaft oder Methode "{0}" in "{1}" gibt IEnumerable<object[]> nicht zurück. - - - - - Value returned by property or method {0} shouldn't be null. - Der von der Eigenschaft oder Methode "{0}" zurückgegebene Wert darf nicht NULL sein. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - Die Methode "{0}" muss der erwarteten Signatur entsprechen: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - Eigenschaft oder Methode "{0}" in "{1}" gibt leeres IEnumerable<object[]> zurück. - - - - - + + + + + + Access string has invalid syntax. + Die Zugriffszeichenfolge weist eine ungültige Syntax auf. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Die erwartete Sammlung enthält {1} Vorkommen von <{2}>. Die tatsächliche Sammlung enthält {3} Vorkommen. {0} + + + + Duplicate item found:<{1}>. {0} + Doppeltes Element gefunden: <{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Erwartet:<{1}>. Tatsächlich:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Es wurde eine Differenz nicht größer als <{3}> zwischen dem erwarteten Wert <{1}> und dem tatsächlichen Wert <{2}> erwartet. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Erwartet:<{1}>. Die Großschreibung des tatsächlichen Werts weicht davon ab:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Erwartet:<{1} ({2})>. Tatsächlich:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Es wurde ein beliebiger Wert erwartet außer:<{1}>. Tatsächlich:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Es wurde eine Differenz größer als <{3}> zwischen dem erwarteten Wert <{1}> und dem tatsächlichen Wert <{2}> erwartet. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Übergeben Sie keine Werttypen an AreSame(). In ein Objekt konvertierte Werte sind niemals identisch. Verwenden Sie stattdessen AreEqual(). {0} + + + + Both collections are empty. {0} + Beide Sammlungen sind leer. {0} + + + + Both collection contain same elements. + Beide Sammlungen enthalten dieselben Elemente. + + + + Both collection references point to the same collection object. {0} + Beide Sammlungsverweise zeigen auf dasselbe Sammlungsobjekt. {0} + + + + Both collections contain the same elements. {0} + Beide Sammlungen enthalten dieselben Elemente. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + Die Zeichenfolge "{0}" enthält nicht die Zeichenfolge "{1}". {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Die Anzahl der Elemente in den Sammlungen stimmt nicht überein. Erwartet: <{1}>. Tatsächlich: <{2}>.{0} + + + + Element at index {0} do not match. + Die Elemente bei Index "{0}" stimmen nicht überein. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + Das Element bei Index "{1}" weist nicht den erwarteten Typ auf. Erwarteter Typ:<{2}>. Tatsächlicher Typ:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + Das Element bei Index "{1}" ist (NULL). Erwarteter Typ:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + Die Zeichenfolge "{0}" endet nicht auf die Zeichenfolge "{1}". {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Ungültiges Argument - EqualsTester kann NULL nicht verwenden. + + + + Cannot convert object of type {0} to {1}. + Ein Objekt vom Typ "{0}" kann nicht in "{1}" konvertiert werden. + + + + {0} failed. {1} + Fehler bei "{0}". {1} + + + + The internal object referenced is no longer valid. + Das interne Objekt, auf das verwiesen wird, ist nicht mehr gültig. + + + + The parameter '{0}' is invalid. {1}. + Der {0}-Parameter ist ungültig. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0}Erwarteter Typ:<{1}>. Tatsächlicher Typ:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + Die Zeichenfolge "{0}" stimmt nicht mit dem Muster "{1}" überein. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Falscher Typ:<{1}>. Tatsächlicher Typ:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + Die Zeichenfolge "{0}" stimmt mit dem Muster "{1}" überein. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals sollte nicht für Assertions verwendet werden. Verwenden Sie stattdessen Assert.AreEqual und Überladungen. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Der angegebene Member ({0}) wurde nicht gefunden. Sie müssen möglicherweise Ihren privaten Accessor erneut generieren, + oder der Member ist möglicherweise privat und für die Basisklasse definiert. Wenn letzteres zutrifft, müssen Sie den Typ, + der den Member definiert, an den Konstruktor von PrivateObject übergeben. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Der Konstruktor mit der angegebenen Signatur wurde nicht gefunden. Sie müssen möglicherweise Ihren privaten Accessor erneut generieren, + oder der Member ist möglicherweise privat und für die Basisklasse definiert. Wenn letzteres zutrifft, müssen Sie den Typ, + der den Member definiert, an den Konstruktor von PrivateObject übergeben. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Der {0}-Parameter ist ungültig. Der Wert kann nicht NULL sein. {1}. + + + + Different number of elements. + Unterschiedliche Anzahl von Elementen. + + + + String '{0}' does not start with string '{1}'. {2}. + Die Zeichenfolge "{0}" beginnt nicht mit der Zeichenfolge "{1}". {2}. + + + + The property {0} has type {1}; expected type {2}. + Die {0}-Eigenschaft weist den Typ "{1}" auf; Typ "{2}" wird erwartet. + + + + (null) + (NULL) + + + + (object) + (Objekt) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Der erwartete Ausnahmentyp muss System.Exception sein oder von System.Exception abgeleitet werden. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Die Testmethode hat keine Ausnahme ausgelöst. Eine Ausnahme wurde vom Attribut "{0}" erwartet, das für die Testmethode definiert wurde. + + + + Test method did not throw expected exception {0}. {1} + Die Testmethode hat die erwartete Ausnahme "{0}" nicht ausgelöst. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Die Testmethode hat die Ausnahme "{0}" ausgelöst, aber die Ausnahme "{1}" wurde erwartet. Ausnahmemeldung: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Die Testmethode hat die Ausnahme "{0}" ausgelöst, aber die Ausnahme "{1}" oder ein davon abgeleiteter Typ wurde erwartet. Ausnahmemeldung: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Fehler beim Abrufen der Meldung für eine Ausnahme vom Typ "{0}" aufgrund einer Ausnahme.) + + + + No exception thrown. {1} exception was expected. {0} + Keine Ausnahme ausgelöst. {1}-Ausnahme wurde erwartet. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + Ausnahme {2} ausgelöst, Ausnahme {1} wurde jedoch erwartet. {0} +Ausnahmemeldung: {3} +Stapelüberwachung: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Es wurde keine Testdatenquelle angegeben. Für DataTestMethodAttribute ist mindestens ein TestDataSource-Wert erforderlich. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + "async TestMethod" wird mit UITestMethodAttribute nicht unterstützt. Entfernen Sie "async", oder verwenden Sie TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + Eigenschaft oder Methode "{0}" in "{1}" gibt IEnumerable<object[]> nicht zurück. + + + + Value returned by property or method {0} shouldn't be null. + Der von der Eigenschaft oder Methode "{0}" zurückgegebene Wert darf nicht NULL sein. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + Die Methode "{0}" muss der erwarteten Signatur entsprechen: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + Eigenschaft oder Methode "{0}" in "{1}" gibt leeres IEnumerable<object[]> zurück. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.es.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.es.xlf index 2029068a5..46ddc1828 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.es.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.es.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - La cadena de acceso tiene una sintaxis no válida. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Apariciones que contiene la colección esperada: {1} de <{2}>. Apariciones que contiene la colección real: {3}. {0} - - - - - Duplicate item found:<{1}>. {0} - Se encontró un elemento duplicado:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Se esperaba <{1}>, pero es <{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Se esperaba una diferencia no superior a <{3}> entre el valor esperado <{1}> y el valor actual <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Se esperaba:<{1}>. La caja es diferente para el valor actual:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Se esperaba:<{1} ({2})>, pero es:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Se esperaba cualquier valor excepto <{1}>, pero es <{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Se esperaba una diferencia mayor que <{3}> entre el valor esperado <{1}> y el valor actual <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - No pase tipos de valor a AreSame(). Los valores convertidos a Object no serán nunca iguales. Considere el uso de AreEqual(). {0} - - - - - Both collections are empty. {0} - Ambas colecciones están vacías. {0} - - - - - Both collection contain same elements. - Ambas colecciones tienen los mismos elementos. - - - - - Both collection references point to the same collection object. {0} - Las referencias de ambas colecciones apuntan al mismo objeto de colección. {0} - - - - - Both collections contain the same elements. {0} - Ambas colecciones tienen los mismos elementos. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - La cadena '{0}' no contiene la cadena '{1}'. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - El número de elementos de las colecciones no coincide. Se esperaba:<{1}>, pero es:<{2}>.{0} - - - - - Element at index {0} do not match. - El elemento del índice {0} no coincide. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - El elemento del índice {1} no es del tipo esperado. Tipo esperado:<{2}>, pero es el tipo:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - El elemento del índice {1} es (null). Se esperaba el tipo:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - La cadena '{0}' no termina con la cadena '{1}'. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Argumento no válido: EqualsTester no puede utilizar valores null. - - - - - Cannot convert object of type {0} to {1}. - No se puede convertir el objeto de tipo {0} en {1}. - - - - - {0} failed. {1} - Error de {0}. {1} - - - - - The internal object referenced is no longer valid. - El objeto interno al que se hace referencia ya no es válido. - - - - - The parameter '{0}' is invalid. {1}. - El parámetro '{0}' no es válido. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Tipo esperado:<{1}>. Tipo real:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - La cadena '{0}' no coincide con el patrón '{1}'. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Tipo incorrecto:<{1}>. Tipo actual:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - La cadena '{0}' coincide con el patrón '{1}'. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - No se debe usar Assert.Equals para aserciones. Use Assert.AreEqual y Overloads en su lugar. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - No se encontró el miembro especificado ({0}). Es posible que tenga que volver a generar el descriptor de acceso privado, - o que el miembro sea privado y esté definido en una clase base. Si esto último es cierto, debe pasar el tipo - que define el miembro al constructor de PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - No se encontró el constructor con la signatura especificada. Es posible que tenga que volver a generar el descriptor de acceso privado, - o que el miembro sea privado y esté definido en una clase base. Si esto último es cierto, debe pasar el tipo - que define el miembro al constructor de PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - El parámetro '{0}' no es válido. El valor no puede ser null. {1}. - - - - - Different number of elements. - Número diferente de elementos. - - - - - String '{0}' does not start with string '{1}'. {2}. - La cadena '{0}' no empieza con la cadena '{1}'. {2}. - - - - - The property {0} has type {1}; expected type {2}. - La propiedad {0} tiene el tipo {1}; se esperaba el tipo {2}. - - - - - (null) - (null) - - - - - (object) - (objeto) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - El tipo de excepción esperado debe ser System.Exception o un tipo derivado de System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - El método de prueba no inició una excepción. El atributo {0} definido en el método de prueba esperaba una excepción. - - - - - Test method did not throw expected exception {0}. {1} - El método de prueba no inició la excepción esperada {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - El método de prueba inició la excepción {0}, pero se esperaba la excepción {1}. Mensaje de la excepción: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - El método de prueba inició la excepción {0}, pero se esperaba la excepción {1} o un tipo derivado de ella. Mensaje de la excepción: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (No se pudo obtener el mensaje para una excepción del tipo {0} debido a una excepción.) - - - - - No exception thrown. {1} exception was expected. {0} - No se produjo ninguna excepción. Se esperaba la excepción {1}. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - Se produjo la excepción {2}, pero se esperaba la excepción {1}. {0} -Mensaje de excepción: {3} -Seguimiento de la pila: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - No se especificó ningún origen de datos de prueba. Se requiere al menos un valor de TestDataSource con DataTestMethodAttribute. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - async TestMethod con UITestMethodAttribute no son compatibles. Quite async o use TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - La propiedad o el método {0} en {1} no devuelve IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - El valor devuelto por la propiedad o el método {0} no debe ser nulo. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - El método {0} debe coincidir con la signatura esperada: {1} {0}({2}) estática pública. - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - La propiedad o el método {0} en {1} devuelve un elemento IEnumerable<object[]> vacío. - - - - - + + + + + + Access string has invalid syntax. + La cadena de acceso tiene una sintaxis no válida. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Apariciones que contiene la colección esperada: {1} de <{2}>. Apariciones que contiene la colección real: {3}. {0} + + + + Duplicate item found:<{1}>. {0} + Se encontró un elemento duplicado:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Se esperaba <{1}>, pero es <{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Se esperaba una diferencia no superior a <{3}> entre el valor esperado <{1}> y el valor actual <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Se esperaba:<{1}>. La caja es diferente para el valor actual:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Se esperaba:<{1} ({2})>, pero es:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Se esperaba cualquier valor excepto <{1}>, pero es <{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Se esperaba una diferencia mayor que <{3}> entre el valor esperado <{1}> y el valor actual <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + No pase tipos de valor a AreSame(). Los valores convertidos a Object no serán nunca iguales. Considere el uso de AreEqual(). {0} + + + + Both collections are empty. {0} + Ambas colecciones están vacías. {0} + + + + Both collection contain same elements. + Ambas colecciones tienen los mismos elementos. + + + + Both collection references point to the same collection object. {0} + Las referencias de ambas colecciones apuntan al mismo objeto de colección. {0} + + + + Both collections contain the same elements. {0} + Ambas colecciones tienen los mismos elementos. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + La cadena '{0}' no contiene la cadena '{1}'. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + El número de elementos de las colecciones no coincide. Se esperaba:<{1}>, pero es:<{2}>.{0} + + + + Element at index {0} do not match. + El elemento del índice {0} no coincide. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + El elemento del índice {1} no es del tipo esperado. Tipo esperado:<{2}>, pero es el tipo:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + El elemento del índice {1} es (null). Se esperaba el tipo:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + La cadena '{0}' no termina con la cadena '{1}'. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Argumento no válido: EqualsTester no puede utilizar valores null. + + + + Cannot convert object of type {0} to {1}. + No se puede convertir el objeto de tipo {0} en {1}. + + + + {0} failed. {1} + Error de {0}. {1} + + + + The internal object referenced is no longer valid. + El objeto interno al que se hace referencia ya no es válido. + + + + The parameter '{0}' is invalid. {1}. + El parámetro '{0}' no es válido. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Tipo esperado:<{1}>. Tipo real:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + La cadena '{0}' no coincide con el patrón '{1}'. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Tipo incorrecto:<{1}>. Tipo actual:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + La cadena '{0}' coincide con el patrón '{1}'. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + No se debe usar Assert.Equals para aserciones. Use Assert.AreEqual y Overloads en su lugar. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + No se encontró el miembro especificado ({0}). Es posible que tenga que volver a generar el descriptor de acceso privado, + o que el miembro sea privado y esté definido en una clase base. Si esto último es cierto, debe pasar el tipo + que define el miembro al constructor de PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + No se encontró el constructor con la signatura especificada. Es posible que tenga que volver a generar el descriptor de acceso privado, + o que el miembro sea privado y esté definido en una clase base. Si esto último es cierto, debe pasar el tipo + que define el miembro al constructor de PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + El parámetro '{0}' no es válido. El valor no puede ser null. {1}. + + + + Different number of elements. + Número diferente de elementos. + + + + String '{0}' does not start with string '{1}'. {2}. + La cadena '{0}' no empieza con la cadena '{1}'. {2}. + + + + The property {0} has type {1}; expected type {2}. + La propiedad {0} tiene el tipo {1}; se esperaba el tipo {2}. + + + + (null) + (null) + + + + (object) + (objeto) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + El tipo de excepción esperado debe ser System.Exception o un tipo derivado de System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + El método de prueba no inició una excepción. El atributo {0} definido en el método de prueba esperaba una excepción. + + + + Test method did not throw expected exception {0}. {1} + El método de prueba no inició la excepción esperada {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + El método de prueba inició la excepción {0}, pero se esperaba la excepción {1}. Mensaje de la excepción: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + El método de prueba inició la excepción {0}, pero se esperaba la excepción {1} o un tipo derivado de ella. Mensaje de la excepción: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (No se pudo obtener el mensaje para una excepción del tipo {0} debido a una excepción.) + + + + No exception thrown. {1} exception was expected. {0} + No se produjo ninguna excepción. Se esperaba la excepción {1}. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + Se produjo la excepción {2}, pero se esperaba la excepción {1}. {0} +Mensaje de excepción: {3} +Seguimiento de la pila: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + No se especificó ningún origen de datos de prueba. Se requiere al menos un valor de TestDataSource con DataTestMethodAttribute. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + async TestMethod con UITestMethodAttribute no son compatibles. Quite async o use TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + La propiedad o el método {0} en {1} no devuelve IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + El valor devuelto por la propiedad o el método {0} no debe ser nulo. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + El método {0} debe coincidir con la signatura esperada: {1} {0}({2}) estática pública. + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + La propiedad o el método {0} en {1} devuelve un elemento IEnumerable<object[]> vacío. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.fr.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.fr.xlf index 6eee0cb52..4bacd13da 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.fr.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.fr.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - La chaîne Access possède une syntaxe non valide. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - La collection attendue contient {1} occurrence(s) de <{2}>. La collection réelle contient {3} occurrence(s). {0} - - - - - Duplicate item found:<{1}>. {0} - Un élément dupliqué a été trouvé : <{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Attendu : <{1}>, Réel : <{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Différence attendue non supérieure à <{3}> comprise entre la valeur attendue <{1}> et la valeur réelle <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Attendu :<{1}>. La casse est différente pour la valeur réelle :<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Attendu : <{1} ({2})>, Réel : <{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Toute valeur attendue sauf :<{1}>. Réel :<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Différence attendue supérieure à <{3}> comprise entre la valeur attendue <{1}> et la valeur réelle <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Ne passez pas de types valeur à AreSame(). Les valeurs converties en Object ne seront plus jamais les mêmes. Si possible, utilisez AreEqual(). {0} - - - - - Both collections are empty. {0} - Les deux collections sont vides. {0} - - - - - Both collection contain same elements. - Les deux collections contiennent des éléments identiques. - - - - - Both collection references point to the same collection object. {0} - Les deux collections Reference pointent vers le même objet Collection. {0} - - - - - Both collections contain the same elements. {0} - Les deux collections contiennent les mêmes éléments. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - La chaîne '{0}' ne contient pas la chaîne '{1}'. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Le nombre d'éléments dans les collections ne correspond pas. Attendu : <{1}>, Réel : <{2}>.{0} - - - - - Element at index {0} do not match. - Les éléments à l'index {0} ne correspondent pas. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - L'élément à l'index {1} n'est pas du type attendu. Type attendu : <{2}>, Type réel : <{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - L'élément à l'index {1} est (null). Type attendu : <{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - La chaîne '{0}' ne se termine pas par la chaîne '{1}'. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Argument non valide - EqualsTester ne peut pas utiliser de valeur null. - - - - - Cannot convert object of type {0} to {1}. - Impossible de convertir un objet de type {0} en {1}. - - - - - {0} failed. {1} - Échec de {0}. {1} - - - - - The internal object referenced is no longer valid. - L'objet interne référencé n'est plus valide. - - - - - The parameter '{0}' is invalid. {1}. - Le paramètre '{0}' n'est pas valide. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0}Type attendu :<{1}>. Type réel :<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - La chaîne '{0}' ne correspond pas au modèle '{1}'. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Type incorrect : <{1}>, Type réel : <{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - La chaîne '{0}' correspond au modèle '{1}'. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals ne doit pas être utilisé pour les assertions. Utilisez Assert.AreEqual & overloads à la place. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Le membre spécifié ({0}) est introuvable. Vous devrez peut-être régénérer votre accesseur private, - ou le membre est peut-être private et défini sur une classe de base. Si le dernier cas est vrai, vous devez transmettre le type - qui définit le membre dans le constructeur de PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Le constructeur doté de la signature spécifiée est introuvable. Vous devrez peut-être régénérer votre accesseur private, - ou le membre est peut-être private et défini sur une classe de base. Si le dernier cas est vrai, vous devez transmettre le type - qui définit le membre dans le constructeur de PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Le paramètre '{0}' n'est pas valide. La valeur ne peut pas être null. {1}. - - - - - Different number of elements. - Nombre d'éléments différent. - - - - - String '{0}' does not start with string '{1}'. {2}. - La chaîne '{0}' ne commence pas par la chaîne '{1}'. {2}. - - - - - The property {0} has type {1}; expected type {2}. - La propriété {0} possède le type {1} ; type attendu {2}. - - - - - (null) - (null) - - - - - (object) - (objet) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Le type de l'exception attendue doit être System.Exception ou un type dérivé de System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - La méthode de test n'a pas levé d'exception. Une exception était attendue par l'attribut {0} défini sur la méthode de test. - - - - - Test method did not throw expected exception {0}. {1} - La méthode de test n'a pas levé l'exception attendue {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - La méthode de test a levé l'exception {0}, mais l'exception {1} était attendue. Message d'exception : {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - La méthode de test a levé l'exception {0}, mais l'exception {1} (ou un type dérivé de cette dernière) était attendue. Message d'exception : {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Échec de la réception du message pour une exception de type {0} en raison d'une exception.) - - - - - No exception thrown. {1} exception was expected. {0} - Aucune exception levée. Exception {1} attendue. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - L'exception {2} a été levée, mais l'exception {1} était attendue. {0} -Message d'exception : {3} -Trace de la pile : {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Aucune source de données de test spécifiée. Au moins une TestDataSouce est obligatoire avec DataTestMethodAttribute. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - async TestMethod avec UITestMethodAttribute ne sont pas pris en charge. Supprimez async ou utilisez TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - La propriété ou la méthode {0} sur {1} ne retourne pas IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - La valeur retournée par la propriété ou la méthode {0} ne doit pas être Null. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - La méthode {0} doit correspondre à la signature attendue : public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - La propriété ou la méthode {0} sur {1} retourne un IEnumerable<object[]> vide. - - - - - + + + + + + Access string has invalid syntax. + La chaîne Access possède une syntaxe non valide. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + La collection attendue contient {1} occurrence(s) de <{2}>. La collection réelle contient {3} occurrence(s). {0} + + + + Duplicate item found:<{1}>. {0} + Un élément dupliqué a été trouvé : <{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Attendu : <{1}>, Réel : <{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Différence attendue non supérieure à <{3}> comprise entre la valeur attendue <{1}> et la valeur réelle <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Attendu :<{1}>. La casse est différente pour la valeur réelle :<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Attendu : <{1} ({2})>, Réel : <{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Toute valeur attendue sauf :<{1}>. Réel :<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Différence attendue supérieure à <{3}> comprise entre la valeur attendue <{1}> et la valeur réelle <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Ne passez pas de types valeur à AreSame(). Les valeurs converties en Object ne seront plus jamais les mêmes. Si possible, utilisez AreEqual(). {0} + + + + Both collections are empty. {0} + Les deux collections sont vides. {0} + + + + Both collection contain same elements. + Les deux collections contiennent des éléments identiques. + + + + Both collection references point to the same collection object. {0} + Les deux collections Reference pointent vers le même objet Collection. {0} + + + + Both collections contain the same elements. {0} + Les deux collections contiennent les mêmes éléments. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + La chaîne '{0}' ne contient pas la chaîne '{1}'. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Le nombre d'éléments dans les collections ne correspond pas. Attendu : <{1}>, Réel : <{2}>.{0} + + + + Element at index {0} do not match. + Les éléments à l'index {0} ne correspondent pas. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + L'élément à l'index {1} n'est pas du type attendu. Type attendu : <{2}>, Type réel : <{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + L'élément à l'index {1} est (null). Type attendu : <{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + La chaîne '{0}' ne se termine pas par la chaîne '{1}'. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Argument non valide - EqualsTester ne peut pas utiliser de valeur null. + + + + Cannot convert object of type {0} to {1}. + Impossible de convertir un objet de type {0} en {1}. + + + + {0} failed. {1} + Échec de {0}. {1} + + + + The internal object referenced is no longer valid. + L'objet interne référencé n'est plus valide. + + + + The parameter '{0}' is invalid. {1}. + Le paramètre '{0}' n'est pas valide. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0}Type attendu :<{1}>. Type réel :<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + La chaîne '{0}' ne correspond pas au modèle '{1}'. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Type incorrect : <{1}>, Type réel : <{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + La chaîne '{0}' correspond au modèle '{1}'. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals ne doit pas être utilisé pour les assertions. Utilisez Assert.AreEqual & overloads à la place. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Le membre spécifié ({0}) est introuvable. Vous devrez peut-être régénérer votre accesseur private, + ou le membre est peut-être private et défini sur une classe de base. Si le dernier cas est vrai, vous devez transmettre le type + qui définit le membre dans le constructeur de PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Le constructeur doté de la signature spécifiée est introuvable. Vous devrez peut-être régénérer votre accesseur private, + ou le membre est peut-être private et défini sur une classe de base. Si le dernier cas est vrai, vous devez transmettre le type + qui définit le membre dans le constructeur de PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Le paramètre '{0}' n'est pas valide. La valeur ne peut pas être null. {1}. + + + + Different number of elements. + Nombre d'éléments différent. + + + + String '{0}' does not start with string '{1}'. {2}. + La chaîne '{0}' ne commence pas par la chaîne '{1}'. {2}. + + + + The property {0} has type {1}; expected type {2}. + La propriété {0} possède le type {1} ; type attendu {2}. + + + + (null) + (null) + + + + (object) + (objet) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Le type de l'exception attendue doit être System.Exception ou un type dérivé de System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + La méthode de test n'a pas levé d'exception. Une exception était attendue par l'attribut {0} défini sur la méthode de test. + + + + Test method did not throw expected exception {0}. {1} + La méthode de test n'a pas levé l'exception attendue {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + La méthode de test a levé l'exception {0}, mais l'exception {1} était attendue. Message d'exception : {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + La méthode de test a levé l'exception {0}, mais l'exception {1} (ou un type dérivé de cette dernière) était attendue. Message d'exception : {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Échec de la réception du message pour une exception de type {0} en raison d'une exception.) + + + + No exception thrown. {1} exception was expected. {0} + Aucune exception levée. Exception {1} attendue. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + L'exception {2} a été levée, mais l'exception {1} était attendue. {0} +Message d'exception : {3} +Trace de la pile : {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Aucune source de données de test spécifiée. Au moins une TestDataSouce est obligatoire avec DataTestMethodAttribute. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + async TestMethod avec UITestMethodAttribute ne sont pas pris en charge. Supprimez async ou utilisez TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + La propriété ou la méthode {0} sur {1} ne retourne pas IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + La valeur retournée par la propriété ou la méthode {0} ne doit pas être Null. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + La méthode {0} doit correspondre à la signature attendue : public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + La propriété ou la méthode {0} sur {1} retourne un IEnumerable<object[]> vide. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.it.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.it.xlf index 78c1cf10c..a016b8fbb 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.it.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.it.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - La sintassi della stringa di accesso non è valida. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - La raccolta prevista contiene {1} occorrenza/e di <{2}>. La raccolta effettiva contiene {3} occorrenza/e. {0} - - - - - Duplicate item found:<{1}>. {0} - Rilevato elemento duplicato:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Previsto:<{1}>. Effettivo:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Prevista una differenza non maggiore di <{3}> tra il valore previsto <{1}> e il valore effettivo <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Previsto:<{1}>. La combinazione di maiuscole e minuscole è diversa per il valore effettivo:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Previsto:<{1} ({2})>. Effettivo:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Previsto qualsiasi valore tranne:<{1}>. Effettivo:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Prevista una differenza maggiore di <{3}> tra il valore previsto <{1}> e il valore effettivo <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Non passare tipi valore a AreSame(). I valori convertiti in Object non saranno mai uguali. Usare AreEqual(). {0} - - - - - Both collections are empty. {0} - Le raccolte sono entrambe vuote. {0} - - - - - Both collection contain same elements. - Le raccolte contengono entrambe gli stessi elementi. - - - - - Both collection references point to the same collection object. {0} - I riferimenti a raccolte puntano entrambi allo stesso oggetto Collection. {0} - - - - - Both collections contain the same elements. {0} - Le raccolte contengono entrambe gli stessi elementi. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - La stringa '{0}' non contiene la stringa '{1}'. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Il numero di elementi nelle raccolte non corrisponde. Previsto:<{1}>. Effettivo:<{2}>.{0} - - - - - Element at index {0} do not match. - L'elemento alla posizione di indice {0} non corrisponde. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - L'elemento nell'indice {1} non è del tipo previsto. Tipo previsto:<{2}>. Tipo effettivo:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - L'elemento nell'indice {1} è (null). Tipo previsto:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - La stringa '{0}' non termina con la stringa '{1}'. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Argomento non valido: EqualsTester non può usare valori Null. - - - - - Cannot convert object of type {0} to {1}. - Non è possibile convertire un oggetto di tipo {0} in {1}. - - - - - {0} failed. {1} - {0} non riuscita. {1} - - - - - The internal object referenced is no longer valid. - L'oggetto interno a cui si fa riferimento non è più valido. - - - - - The parameter '{0}' is invalid. {1}. - Il parametro '{0}' non è valido. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Tipo previsto:<{1}>. Tipo effettivo:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - La stringa '{0}' non corrisponde al criterio '{1}'. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Tipo errato:<{1}>. Tipo effettivo:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - La stringa '{0}' corrisponde al criterio '{1}'. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Non è possibile usare Assert.Equals per le asserzioni. Usare Assert.AreEqual e gli overload. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Il membro specificato ({0}) non è stato trovato. Potrebbe essere necessario rigenerare la funzione di accesso privata - oppure il membro potrebbe essere privato e definito per una classe base. In quest'ultimo caso, è necessario passare il tipo - che definisce il membro nel costruttore di PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Il costruttore con la firma specificata non è stato trovato. Potrebbe essere necessario rigenerare la funzione di accesso privata - oppure il membro potrebbe essere privato e definito per una classe base. In quest'ultimo caso, è necessario passare il tipo - che definisce il membro nel costruttore di PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Il parametro '{0}' non è valido. Il valore non può essere Null. {1}. - - - - - Different number of elements. - Il numero di elementi è diverso. - - - - - String '{0}' does not start with string '{1}'. {2}. - La stringa '{0}' non inizia con la stringa '{1}'. {2}. - - - - - The property {0} has type {1}; expected type {2}. - Il tipo della proprietà {0} è {1}, ma quello previsto è {2}. - - - - - (null) - (Null) - - - - - (object) - (oggetto) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Il tipo di eccezione previsto deve essere System.Exception o un tipo derivato da System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Il metodo di test non ha generato un'eccezione. È prevista un'eccezione dall'attributo {0} definito nel metodo di test. - - - - - Test method did not throw expected exception {0}. {1} - Il metodo di test non ha generato l'eccezione prevista {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Il metodo di test ha generato l'eccezione {0}, ma era prevista l'eccezione {1}. Messaggio dell'eccezione: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Il metodo di test ha generato l'eccezione {0}, ma era prevista l'eccezione {1} o un tipo derivato da essa. Messaggio dell'eccezione: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - Non è stato possibile ottenere il messaggio per un'eccezione di tipo {0} a causa di un'eccezione. - - - - - No exception thrown. {1} exception was expected. {0} - Non è stata generata alcuna eccezione. Era prevista un'eccezione {1}. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - È stata generata l'eccezione {2}, ma era prevista un'eccezione {1}. {0} -Messaggio dell'eccezione: {3} -Analisi dello stack: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Non è stata specificata alcuna origine dati di test. Con DataTestMethodAttribute è necessario almeno un elemento TestDataSource. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - L'elemento async TestMethod con UITestMethodAttribute non è supportato. Rimuovere async o usare TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - La proprietà o il metodo {0} su {1} non restituisce IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - Il valore restituito dalla proprietà o dal metodo {0} non deve essere Null. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - Il metodo {0} deve corrispondere alla firma prevista: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - La proprietà o il metodo {0} nella classe {1} restituisce un elemento IEnumerable<object[]> vuoto. - - - - - + + + + + + Access string has invalid syntax. + La sintassi della stringa di accesso non è valida. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + La raccolta prevista contiene {1} occorrenza/e di <{2}>. La raccolta effettiva contiene {3} occorrenza/e. {0} + + + + Duplicate item found:<{1}>. {0} + Rilevato elemento duplicato:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Previsto:<{1}>. Effettivo:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Prevista una differenza non maggiore di <{3}> tra il valore previsto <{1}> e il valore effettivo <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Previsto:<{1}>. La combinazione di maiuscole e minuscole è diversa per il valore effettivo:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Previsto:<{1} ({2})>. Effettivo:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Previsto qualsiasi valore tranne:<{1}>. Effettivo:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Prevista una differenza maggiore di <{3}> tra il valore previsto <{1}> e il valore effettivo <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Non passare tipi valore a AreSame(). I valori convertiti in Object non saranno mai uguali. Usare AreEqual(). {0} + + + + Both collections are empty. {0} + Le raccolte sono entrambe vuote. {0} + + + + Both collection contain same elements. + Le raccolte contengono entrambe gli stessi elementi. + + + + Both collection references point to the same collection object. {0} + I riferimenti a raccolte puntano entrambi allo stesso oggetto Collection. {0} + + + + Both collections contain the same elements. {0} + Le raccolte contengono entrambe gli stessi elementi. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + La stringa '{0}' non contiene la stringa '{1}'. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Il numero di elementi nelle raccolte non corrisponde. Previsto:<{1}>. Effettivo:<{2}>.{0} + + + + Element at index {0} do not match. + L'elemento alla posizione di indice {0} non corrisponde. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + L'elemento nell'indice {1} non è del tipo previsto. Tipo previsto:<{2}>. Tipo effettivo:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + L'elemento nell'indice {1} è (null). Tipo previsto:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + La stringa '{0}' non termina con la stringa '{1}'. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Argomento non valido: EqualsTester non può usare valori Null. + + + + Cannot convert object of type {0} to {1}. + Non è possibile convertire un oggetto di tipo {0} in {1}. + + + + {0} failed. {1} + {0} non riuscita. {1} + + + + The internal object referenced is no longer valid. + L'oggetto interno a cui si fa riferimento non è più valido. + + + + The parameter '{0}' is invalid. {1}. + Il parametro '{0}' non è valido. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Tipo previsto:<{1}>. Tipo effettivo:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + La stringa '{0}' non corrisponde al criterio '{1}'. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Tipo errato:<{1}>. Tipo effettivo:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + La stringa '{0}' corrisponde al criterio '{1}'. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Non è possibile usare Assert.Equals per le asserzioni. Usare Assert.AreEqual e gli overload. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Il membro specificato ({0}) non è stato trovato. Potrebbe essere necessario rigenerare la funzione di accesso privata + oppure il membro potrebbe essere privato e definito per una classe base. In quest'ultimo caso, è necessario passare il tipo + che definisce il membro nel costruttore di PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Il costruttore con la firma specificata non è stato trovato. Potrebbe essere necessario rigenerare la funzione di accesso privata + oppure il membro potrebbe essere privato e definito per una classe base. In quest'ultimo caso, è necessario passare il tipo + che definisce il membro nel costruttore di PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Il parametro '{0}' non è valido. Il valore non può essere Null. {1}. + + + + Different number of elements. + Il numero di elementi è diverso. + + + + String '{0}' does not start with string '{1}'. {2}. + La stringa '{0}' non inizia con la stringa '{1}'. {2}. + + + + The property {0} has type {1}; expected type {2}. + Il tipo della proprietà {0} è {1}, ma quello previsto è {2}. + + + + (null) + (Null) + + + + (object) + (oggetto) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Il tipo di eccezione previsto deve essere System.Exception o un tipo derivato da System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Il metodo di test non ha generato un'eccezione. È prevista un'eccezione dall'attributo {0} definito nel metodo di test. + + + + Test method did not throw expected exception {0}. {1} + Il metodo di test non ha generato l'eccezione prevista {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Il metodo di test ha generato l'eccezione {0}, ma era prevista l'eccezione {1}. Messaggio dell'eccezione: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Il metodo di test ha generato l'eccezione {0}, ma era prevista l'eccezione {1} o un tipo derivato da essa. Messaggio dell'eccezione: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + Non è stato possibile ottenere il messaggio per un'eccezione di tipo {0} a causa di un'eccezione. + + + + No exception thrown. {1} exception was expected. {0} + Non è stata generata alcuna eccezione. Era prevista un'eccezione {1}. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + È stata generata l'eccezione {2}, ma era prevista un'eccezione {1}. {0} +Messaggio dell'eccezione: {3} +Analisi dello stack: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Non è stata specificata alcuna origine dati di test. Con DataTestMethodAttribute è necessario almeno un elemento TestDataSource. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + L'elemento async TestMethod con UITestMethodAttribute non è supportato. Rimuovere async o usare TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + La proprietà o il metodo {0} su {1} non restituisce IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + Il valore restituito dalla proprietà o dal metodo {0} non deve essere Null. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + Il metodo {0} deve corrispondere alla firma prevista: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + La proprietà o il metodo {0} nella classe {1} restituisce un elemento IEnumerable<object[]> vuoto. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ja.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ja.xlf index 8534ff842..96797a55e 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ja.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ja.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - アクセス文字列は無効な構文を含んでいます。 - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - 予期されたコレクションでは、<{2}> が {1} 回発生します。実際のコレクションでは、{3} 回発生します。{0} - - - - - Duplicate item found:<{1}>. {0} - 重複する項目が見つかりました:<{1}>。{0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - <{1}> が必要ですが、<{2}> が指定されました。{0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - 指定する値 <{1}> と実際の値 <{2}> との間には <{3}> 以内の差が必要です。{0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - <{1}> が必要です。実際の値: <{2}> では大文字と小文字が異なります。{0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - <{1} ({2})> が必要ですが、<{3} ({4})> が指定されました。{0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - <{1}> 以外の任意の値が必要ですが、<{2}> が指定されています。{0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - 指定する値 <{1}> と実際の値 <{2}> との間には、<{3}> を超える差が必要です。{0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - AreSame() には値型を渡すことはできません。オブジェクトに変換された値が同じにはなりません。AreEqual() を使用することを検討してください。{0} - - - - - Both collections are empty. {0} - 両方のコレクションが空です。{0} - - - - - Both collection contain same elements. - 両方のコレクションが同じ要素を含んでいます。 - - - - - Both collection references point to the same collection object. {0} - 両方のコレクションの参照が、同じコレクション オブジェクトにポイントしています。{0} - - - - - Both collections contain the same elements. {0} - 両方のコレクションが同じ要素を含んでいます。{0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - 文字列 '{0}' は文字列 '{1}' を含んでいません。{2}。 - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - コレクション内の要素数が一致しません。<{1}> が必要ですが <{2}> が指定されています。{0} - - - - - Element at index {0} do not match. - インデックス {0} の要素が一致しません。 - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - インデックス {1} の要素は、必要な型ではありません。<{2}> が必要ですが、<{3}> が指定されています。{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - インデックス {1} の要素は null です。必要な型:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - 文字列 '{0}' は文字列 '{1}' で終わりません。{2}。 - - - - - Invalid argument- EqualsTester can't use nulls. - 無効な引数 - EqualsTester は null を使用することはできません。 - - - - - Cannot convert object of type {0} to {1}. - 型 {0} のオブジェクトを {1} に変換できません。 - - - - - {0} failed. {1} - {0} に失敗しました。{1} - - - - - The internal object referenced is no longer valid. - 参照された内部オブジェクトは、現在有効ではありません。 - - - - - The parameter '{0}' is invalid. {1}. - パラメーター '{0}' は無効です。{1}。 - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} には型 <{1}> が必要ですが、型 <{2}> が指定されました。 - - - - - String '{0}' does not match pattern '{1}'. {2}. - 文字列 '{0}' はパターン '{1}' と一致しません。{2}。 - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - 正しくない型は <{1}> であり、実際の型は <{2}> です。{0} - - - - - String '{0}' matches pattern '{1}'. {2}. - 文字列 '{0}' はパターン '{1}' と一致します。{2}。 - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - アサーションには Assert.Equals を使用せずに、Assert.AreEqual とオーバーロードを使用してください。(& ) - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - 指定されたメンバー ({0}) が見つかりませんでした。プライベート アクセサーを再生成しなければならないか、 - またはメンバーがプライベートであり、基底クラスで定義されている可能性があります。後者である場合は、メンバーを - 定義する型を PrivateObject のコンストラクターに渡す必要があります。 - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - 指定されたシグネチャを使用するコンストラクターが見つかりませんでした。プライベート アクセサーを再生成しなければならないか、 - またはメンバーがプライベートであり、基底クラスで定義されている可能性があります。後者である場合は、メンバーを - 定義する型を PrivateObject のコンストラクターに渡す必要があります。 - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - パラメーター '{0}' は無効です。値を null にすることはできません。{1}。 - - - - - Different number of elements. - 要素数が異なります。 - - - - - String '{0}' does not start with string '{1}'. {2}. - 文字列 '{0}' は文字列 '{1}' で始まりません。{2}。 - - - - - The property {0} has type {1}; expected type {2}. - プロパティ {0} は型 {1} を含んでいますが、型 {2} が必要です。 - - - - - (null) - (null) - - - - - (object) - (オブジェクト) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - 予期される例外の型は System.Exception または System.Exception の派生型である必要があります。 - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - テスト メソッドは例外をスローしませんでした。テスト メソッドで定義されている属性 {0} で例外が予期されていました。 - - - - - Test method did not throw expected exception {0}. {1} - テスト メソッドは例外 {0} をスローしませんでした。{1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - テスト メソッドは、例外 {0} をスローしましたが、例外 {1} が予期されていました。例外メッセージ: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - テスト メソッドは、例外 {0} をスローしましたが、例外 {1} またはその派生型が予期されていました。例外メッセージ: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (例外が発生したため、型 {0} の例外のメッセージを取得できませんでした。) - - - - - No exception thrown. {1} exception was expected. {0} - 例外がスローされませんでした。{1} の例外が予期されていました。{0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - 例外 {2} がスローされましたが、例外 {1} は予期されていました。{0} -例外メッセージ: {3} -スタック トレース: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - テスト データ ソースが指定されていません。DataTestMethodAttribute では少なくとも 1 つの TestDataSource が必要です。 - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - UITestMethodAttribute が指定された非同期の TestMethod はサポートされていません。非同期を削除するか、TestMethodAttribute を使用してください。 - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - {1} 上のプロパティまたはメソッド {0} は IEnumerable<object[]> を返しません。 - - - - - Value returned by property or method {0} shouldn't be null. - プロパティやメソッド {0} によって返される値を null にすることはできません。 - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - メソッド {0} は必要なシグネチャと一致しなければなりません: public static {1} {0}({2})。 - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - {1} 上のプロパティまたはメソッド {0} は空の IEnumerable<object[]> を返します。 - - - - - + + + + + + Access string has invalid syntax. + アクセス文字列は無効な構文を含んでいます。 + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + 予期されたコレクションでは、<{2}> が {1} 回発生します。実際のコレクションでは、{3} 回発生します。{0} + + + + Duplicate item found:<{1}>. {0} + 重複する項目が見つかりました:<{1}>。{0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + <{1}> が必要ですが、<{2}> が指定されました。{0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + 指定する値 <{1}> と実際の値 <{2}> との間には <{3}> 以内の差が必要です。{0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + <{1}> が必要です。実際の値: <{2}> では大文字と小文字が異なります。{0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + <{1} ({2})> が必要ですが、<{3} ({4})> が指定されました。{0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + <{1}> 以外の任意の値が必要ですが、<{2}> が指定されています。{0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + 指定する値 <{1}> と実際の値 <{2}> との間には、<{3}> を超える差が必要です。{0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + AreSame() には値型を渡すことはできません。オブジェクトに変換された値が同じにはなりません。AreEqual() を使用することを検討してください。{0} + + + + Both collections are empty. {0} + 両方のコレクションが空です。{0} + + + + Both collection contain same elements. + 両方のコレクションが同じ要素を含んでいます。 + + + + Both collection references point to the same collection object. {0} + 両方のコレクションの参照が、同じコレクション オブジェクトにポイントしています。{0} + + + + Both collections contain the same elements. {0} + 両方のコレクションが同じ要素を含んでいます。{0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + 文字列 '{0}' は文字列 '{1}' を含んでいません。{2}。 + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + コレクション内の要素数が一致しません。<{1}> が必要ですが <{2}> が指定されています。{0} + + + + Element at index {0} do not match. + インデックス {0} の要素が一致しません。 + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + インデックス {1} の要素は、必要な型ではありません。<{2}> が必要ですが、<{3}> が指定されています。{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + インデックス {1} の要素は null です。必要な型:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + 文字列 '{0}' は文字列 '{1}' で終わりません。{2}。 + + + + Invalid argument- EqualsTester can't use nulls. + 無効な引数 - EqualsTester は null を使用することはできません。 + + + + Cannot convert object of type {0} to {1}. + 型 {0} のオブジェクトを {1} に変換できません。 + + + + {0} failed. {1} + {0} に失敗しました。{1} + + + + The internal object referenced is no longer valid. + 参照された内部オブジェクトは、現在有効ではありません。 + + + + The parameter '{0}' is invalid. {1}. + パラメーター '{0}' は無効です。{1}。 + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} には型 <{1}> が必要ですが、型 <{2}> が指定されました。 + + + + String '{0}' does not match pattern '{1}'. {2}. + 文字列 '{0}' はパターン '{1}' と一致しません。{2}。 + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + 正しくない型は <{1}> であり、実際の型は <{2}> です。{0} + + + + String '{0}' matches pattern '{1}'. {2}. + 文字列 '{0}' はパターン '{1}' と一致します。{2}。 + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + アサーションには Assert.Equals を使用せずに、Assert.AreEqual とオーバーロードを使用してください。(& ) + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + 指定されたメンバー ({0}) が見つかりませんでした。プライベート アクセサーを再生成しなければならないか、 + またはメンバーがプライベートであり、基底クラスで定義されている可能性があります。後者である場合は、メンバーを + 定義する型を PrivateObject のコンストラクターに渡す必要があります。 + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + 指定されたシグネチャを使用するコンストラクターが見つかりませんでした。プライベート アクセサーを再生成しなければならないか、 + またはメンバーがプライベートであり、基底クラスで定義されている可能性があります。後者である場合は、メンバーを + 定義する型を PrivateObject のコンストラクターに渡す必要があります。 + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + パラメーター '{0}' は無効です。値を null にすることはできません。{1}。 + + + + Different number of elements. + 要素数が異なります。 + + + + String '{0}' does not start with string '{1}'. {2}. + 文字列 '{0}' は文字列 '{1}' で始まりません。{2}。 + + + + The property {0} has type {1}; expected type {2}. + プロパティ {0} は型 {1} を含んでいますが、型 {2} が必要です。 + + + + (null) + (null) + + + + (object) + (オブジェクト) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + 予期される例外の型は System.Exception または System.Exception の派生型である必要があります。 + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + テスト メソッドは例外をスローしませんでした。テスト メソッドで定義されている属性 {0} で例外が予期されていました。 + + + + Test method did not throw expected exception {0}. {1} + テスト メソッドは例外 {0} をスローしませんでした。{1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + テスト メソッドは、例外 {0} をスローしましたが、例外 {1} が予期されていました。例外メッセージ: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + テスト メソッドは、例外 {0} をスローしましたが、例外 {1} またはその派生型が予期されていました。例外メッセージ: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (例外が発生したため、型 {0} の例外のメッセージを取得できませんでした。) + + + + No exception thrown. {1} exception was expected. {0} + 例外がスローされませんでした。{1} の例外が予期されていました。{0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + 例外 {2} がスローされましたが、例外 {1} は予期されていました。{0} +例外メッセージ: {3} +スタック トレース: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + テスト データ ソースが指定されていません。DataTestMethodAttribute では少なくとも 1 つの TestDataSource が必要です。 + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + UITestMethodAttribute が指定された非同期の TestMethod はサポートされていません。非同期を削除するか、TestMethodAttribute を使用してください。 + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + {1} 上のプロパティまたはメソッド {0} は IEnumerable<object[]> を返しません。 + + + + Value returned by property or method {0} shouldn't be null. + プロパティやメソッド {0} によって返される値を null にすることはできません。 + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + メソッド {0} は必要なシグネチャと一致しなければなりません: public static {1} {0}({2})。 + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + {1} 上のプロパティまたはメソッド {0} は空の IEnumerable<object[]> を返します。 + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ko.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ko.xlf index 0b71fc1e1..f6209b309 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ko.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ko.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - 액세스 문자열의 구문이 잘못되었습니다. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - 필요한 컬렉션에 <{2}>은(는) {1}개가 포함되어야 하는데 실제 컬렉션에는 {3}개가 포함되어 있습니다. {0} - - - - - Duplicate item found:<{1}>. {0} - 중복된 항목이 있습니다. <{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - 예상 값: <{1}>. 실제 값: <{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - 예상 값 <{1}>과(와) 실제 값 <{2}>의 차이가 <{3}>보다 크지 않아야 합니다. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - 예상 값: <{1}>. 대/소문자가 다른 실제 값: <{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - 예상 값: <{1} ({2})>. 실제 값: <{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - 예상 값: <{1}>을(를) 제외한 모든 값. 실제 값: <{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - 예상 값 <{1}>과(와) 실제 값 <{2}>의 차이가 <{3}>보다 커야 합니다. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - AreSame()에 값 형식을 전달하면 안 됩니다. Object로 변환된 값은 동일한 값으로 간주되지 않습니다. AreEqual()을 사용해 보세요. {0} - - - - - Both collections are empty. {0} - 두 컬렉션이 모두 비어 있습니다. {0} - - - - - Both collection contain same elements. - 두 컬렉션에 같은 요소가 포함되어 있습니다. - - - - - Both collection references point to the same collection object. {0} - 두 컬렉션 참조가 동일한 컬렉션 개체를 가리킵니다. {0} - - - - - Both collections contain the same elements. {0} - 두 컬렉션에 같은 요소가 포함되어 있습니다. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - '{0}' 문자열이 '{1}' 문자열을 포함하지 않습니다. {2} - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - 컬렉션의 요소 수가 일치하지 않습니다. 예상 값: <{1}>. 실제 값: <{2}>.{0} - - - - - Element at index {0} do not match. - 인덱스 {0}에 있는 요소가 일치하지 않습니다. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - 인덱스 {1}에 있는 요소가 필요한 형식이 아닙니다. 필요한 형식: <{2}>, 실제 형식: <{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - 인덱스 {1}에 있는 요소가 (null)입니다. 필요한 형식: <{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - '{0}' 문자열이 '{1}' 문자열로 끝나지 않습니다. {2} - - - - - Invalid argument- EqualsTester can't use nulls. - 잘못된 인수 - EqualsTester에는 null을 사용할 수 없습니다. - - - - - Cannot convert object of type {0} to {1}. - {0} 형식의 개체를 {1}(으)로 변환할 수 없습니다. - - - - - {0} failed. {1} - {0}이(가) 실패했습니다. {1} - - - - - The internal object referenced is no longer valid. - 참조된 내부 개체가 더 이상 유효하지 않습니다. - - - - - The parameter '{0}' is invalid. {1}. - '{0}' 매개 변수가 잘못되었습니다. {1} - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} 예상 형식: <{1}>, 실제 형식: <{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - '{0}' 문자열이 '{1}' 패턴과 일치하지 않습니다. {2} - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - 잘못된 형식: <{1}>, 실제 형식: <{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - '{0}' 문자열이 '{1}' 패턴과 일치합니다. {2} - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - 어설션에 Assert.Equals를 사용할 수 없습니다. 대신 Assert.AreEqual 및 오버로드를 사용하세요. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - 지정한 멤버({0})를 찾을 수 없습니다. 프라이빗 접근자를 다시 생성해야 할 수 있습니다. - 또는 멤버가 기본 클래스에 정의된 프라이빗 멤버일 수 있습니다. 기본 클래스에 정의된 전용 멤버인 경우에는 이 멤버를 정의하는 형식을 - PrivateObject의 생성자에 전달해야 합니다. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - 지정한 서명을 가진 생성자를 찾을 수 없습니다. 프라이빗 접근자를 다시 생성해야 할 수 있습니다. - 또는 멤버가 기본 클래스에 정의된 프라이빗 멤버일 수 있습니다. 기본 클래스에 정의된 전용 멤버인 경우에는 이 멤버를 정의하는 형식을 - PrivateObject의 생성자에 전달해야 합니다. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - '{0}' 매개 변수가 잘못되었습니다. 이 값은 null일 수 없습니다. {1}. - - - - - Different number of elements. - 요소 수가 다릅니다. - - - - - String '{0}' does not start with string '{1}'. {2}. - '{0}' 문자열이 '{1}' 문자열로 시작되지 않습니다. {2} - - - - - The property {0} has type {1}; expected type {2}. - {0} 속성의 형식은 {2}이어야 하는데 실제로는 {1}입니다. - - - - - (null) - (null) - - - - - (object) - (개체) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - 예상 예외 형식은 System.Exception이거나 System.Exception에서 파생된 형식이어야 합니다. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - 테스트 메서드에서 예외를 throw하지 않았습니다. 예외는 테스트 메서드에 정의된 {0} 특성에 의해 예상되었습니다. - - - - - Test method did not throw expected exception {0}. {1} - 테스트 메서드에서 예상 예외 {0}을(를) throw하지 않았습니다. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - 테스트 메서드에서 {0} 예외를 throw했지만 {1} 예외를 예상했습니다. 예외 메시지: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - 테스트 메서드에서 {0} 예외를 throw했지만 {1} 예외 또는 해당 예외에서 파생된 형식을 예상했습니다. 예외 메시지: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (예외로 인해 {0} 형식의 예외에 대한 메시지를 가져오지 못했습니다.) - - - - - No exception thrown. {1} exception was expected. {0} - {1} 예외를 예상했지만 예외가 throw되지 않았습니다. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - {1} 예외를 예상했지만 {2} 예외를 throw했습니다. {0} -예외 메시지: {3} -스택 추적: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - 테스트 데이터 소스가 지정되지 않았습니다. DataTestMethodAttribute에는 하나 이상의 TestDataSource가 필요합니다. - - - - - {0} ({1}) - {0}({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - async TestMethod with UITestMethodAttribute는 지원되지 않습니다. async를 제거하거나 TestMethodAttribute를 사용하세요. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - {1}의 속성 또는 메서드 {0}이(가) IEnumerable<object[]>를 반환하지 않습니다. - - - - - Value returned by property or method {0} shouldn't be null. - 속성 또는 메서드 {0}에 의해 반환된 값은 null일 수 없습니다. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - 메서드 {0}은(는) 다음 예상 시그니처와 일치해야 합니다. 공용 정적 {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - {1}의 속성 또는 메서드 {0}이(가) 빈 IEnumerable<object[]>를 반환합니다. - - - - - + + + + + + Access string has invalid syntax. + 액세스 문자열의 구문이 잘못되었습니다. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + 필요한 컬렉션에 <{2}>은(는) {1}개가 포함되어야 하는데 실제 컬렉션에는 {3}개가 포함되어 있습니다. {0} + + + + Duplicate item found:<{1}>. {0} + 중복된 항목이 있습니다. <{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + 예상 값: <{1}>. 실제 값: <{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + 예상 값 <{1}>과(와) 실제 값 <{2}>의 차이가 <{3}>보다 크지 않아야 합니다. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + 예상 값: <{1}>. 대/소문자가 다른 실제 값: <{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + 예상 값: <{1} ({2})>. 실제 값: <{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + 예상 값: <{1}>을(를) 제외한 모든 값. 실제 값: <{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + 예상 값 <{1}>과(와) 실제 값 <{2}>의 차이가 <{3}>보다 커야 합니다. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + AreSame()에 값 형식을 전달하면 안 됩니다. Object로 변환된 값은 동일한 값으로 간주되지 않습니다. AreEqual()을 사용해 보세요. {0} + + + + Both collections are empty. {0} + 두 컬렉션이 모두 비어 있습니다. {0} + + + + Both collection contain same elements. + 두 컬렉션에 같은 요소가 포함되어 있습니다. + + + + Both collection references point to the same collection object. {0} + 두 컬렉션 참조가 동일한 컬렉션 개체를 가리킵니다. {0} + + + + Both collections contain the same elements. {0} + 두 컬렉션에 같은 요소가 포함되어 있습니다. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + '{0}' 문자열이 '{1}' 문자열을 포함하지 않습니다. {2} + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + 컬렉션의 요소 수가 일치하지 않습니다. 예상 값: <{1}>. 실제 값: <{2}>.{0} + + + + Element at index {0} do not match. + 인덱스 {0}에 있는 요소가 일치하지 않습니다. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + 인덱스 {1}에 있는 요소가 필요한 형식이 아닙니다. 필요한 형식: <{2}>, 실제 형식: <{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + 인덱스 {1}에 있는 요소가 (null)입니다. 필요한 형식: <{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + '{0}' 문자열이 '{1}' 문자열로 끝나지 않습니다. {2} + + + + Invalid argument- EqualsTester can't use nulls. + 잘못된 인수 - EqualsTester에는 null을 사용할 수 없습니다. + + + + Cannot convert object of type {0} to {1}. + {0} 형식의 개체를 {1}(으)로 변환할 수 없습니다. + + + + {0} failed. {1} + {0}이(가) 실패했습니다. {1} + + + + The internal object referenced is no longer valid. + 참조된 내부 개체가 더 이상 유효하지 않습니다. + + + + The parameter '{0}' is invalid. {1}. + '{0}' 매개 변수가 잘못되었습니다. {1} + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} 예상 형식: <{1}>, 실제 형식: <{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + '{0}' 문자열이 '{1}' 패턴과 일치하지 않습니다. {2} + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + 잘못된 형식: <{1}>, 실제 형식: <{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + '{0}' 문자열이 '{1}' 패턴과 일치합니다. {2} + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + 어설션에 Assert.Equals를 사용할 수 없습니다. 대신 Assert.AreEqual 및 오버로드를 사용하세요. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + 지정한 멤버({0})를 찾을 수 없습니다. 프라이빗 접근자를 다시 생성해야 할 수 있습니다. + 또는 멤버가 기본 클래스에 정의된 프라이빗 멤버일 수 있습니다. 기본 클래스에 정의된 전용 멤버인 경우에는 이 멤버를 정의하는 형식을 + PrivateObject의 생성자에 전달해야 합니다. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + 지정한 서명을 가진 생성자를 찾을 수 없습니다. 프라이빗 접근자를 다시 생성해야 할 수 있습니다. + 또는 멤버가 기본 클래스에 정의된 프라이빗 멤버일 수 있습니다. 기본 클래스에 정의된 전용 멤버인 경우에는 이 멤버를 정의하는 형식을 + PrivateObject의 생성자에 전달해야 합니다. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + '{0}' 매개 변수가 잘못되었습니다. 이 값은 null일 수 없습니다. {1}. + + + + Different number of elements. + 요소 수가 다릅니다. + + + + String '{0}' does not start with string '{1}'. {2}. + '{0}' 문자열이 '{1}' 문자열로 시작되지 않습니다. {2} + + + + The property {0} has type {1}; expected type {2}. + {0} 속성의 형식은 {2}이어야 하는데 실제로는 {1}입니다. + + + + (null) + (null) + + + + (object) + (개체) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + 예상 예외 형식은 System.Exception이거나 System.Exception에서 파생된 형식이어야 합니다. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + 테스트 메서드에서 예외를 throw하지 않았습니다. 예외는 테스트 메서드에 정의된 {0} 특성에 의해 예상되었습니다. + + + + Test method did not throw expected exception {0}. {1} + 테스트 메서드에서 예상 예외 {0}을(를) throw하지 않았습니다. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + 테스트 메서드에서 {0} 예외를 throw했지만 {1} 예외를 예상했습니다. 예외 메시지: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + 테스트 메서드에서 {0} 예외를 throw했지만 {1} 예외 또는 해당 예외에서 파생된 형식을 예상했습니다. 예외 메시지: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (예외로 인해 {0} 형식의 예외에 대한 메시지를 가져오지 못했습니다.) + + + + No exception thrown. {1} exception was expected. {0} + {1} 예외를 예상했지만 예외가 throw되지 않았습니다. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + {1} 예외를 예상했지만 {2} 예외를 throw했습니다. {0} +예외 메시지: {3} +스택 추적: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + 테스트 데이터 소스가 지정되지 않았습니다. DataTestMethodAttribute에는 하나 이상의 TestDataSource가 필요합니다. + + + + {0} ({1}) + {0}({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + async TestMethod with UITestMethodAttribute는 지원되지 않습니다. async를 제거하거나 TestMethodAttribute를 사용하세요. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + {1}의 속성 또는 메서드 {0}이(가) IEnumerable<object[]>를 반환하지 않습니다. + + + + Value returned by property or method {0} shouldn't be null. + 속성 또는 메서드 {0}에 의해 반환된 값은 null일 수 없습니다. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + 메서드 {0}은(는) 다음 예상 시그니처와 일치해야 합니다. 공용 정적 {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + {1}의 속성 또는 메서드 {0}이(가) 빈 IEnumerable<object[]>를 반환합니다. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pl.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pl.xlf index abb2531f9..df93dfc0e 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pl.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pl.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - Ciąg dostępu ma nieprawidłową składnię. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Oczekiwana kolekcja zawiera {1} wystąpień <{2}>. Bieżąca kolekcja zawiera {3} wystąpień. {0} - - - - - Duplicate item found:<{1}>. {0} - Znaleziono duplikat:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Oczekiwana:<{1}>. Rzeczywista:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Oczekiwano różnicy nie większej niż <{3}> pomiędzy oczekiwaną wartością <{1}> a rzeczywistą wartością <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Oczekiwano:<{1}>. Przypadek różni się od rzeczywistej wartości:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Oczekiwana:<{1} ({2})>. Rzeczywista:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Oczekiwano dowolnej wartości za wyjątkiem:<{1}>. Rzeczywista:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Oczekiwano różnicy większej niż <{3}> pomiędzy oczekiwaną wartością <{1}> a rzeczywistą wartością <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Nie przekazuj typów wartości do metody AreSame(). Wartości przekonwertowane na typ Object nigdy nie będą takie same. Rozważ użycie metody AreEqual(). {0} - - - - - Both collections are empty. {0} - Obie kolekcje są puste. {0} - - - - - Both collection contain same elements. - Obie kolekcje zawierają te same elementy. - - - - - Both collection references point to the same collection object. {0} - Odwołania do obu kolekcji wskazują ten sam obiekt kolekcji. {0} - - - - - Both collections contain the same elements. {0} - Obie kolekcje zawierają te same elementy. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - Ciąg „{0}” nie zawiera ciągu „{1}”. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Nie zgadza się liczba elementów w kolekcji. Oczekiwana:<{1}>. Rzeczywista:<{2}>.{0} - - - - - Element at index {0} do not match. - Element w indeksie {0} nie jest zgodny. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - Element o indeksie {1} jest innego typu niż oczekiwano. Oczekiwany typ:<{2}>. Rzeczywisty typ:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - Element o indeksie {1} jest zerowy (null). Oczekiwany typ: <{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - Ciąg „{0}” nie kończy się ciągiem „{1}”. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Nieprawidłowy argument. Element EqualsTester nie może używać wartości null. - - - - - Cannot convert object of type {0} to {1}. - Nie można przekonwertować obiektu typu {0} na typ {1}. - - - - - {0} failed. {1} - {0} — niepowodzenie. {1} - - - - - The internal object referenced is no longer valid. - Przywoływany obiekt wewnętrzny nie jest już prawidłowy. - - - - - The parameter '{0}' is invalid. {1}. - Parametr „{0}” jest nieprawidłowy. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Oczekiwany typ:<{1}>. Rzeczywisty typ:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - Ciąg „{0}” nie jest zgodny ze wzorcem „{1}”. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Zły typ:<{1}>. Rzeczywisty typ:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - Ciąg „{0}” jest zgodny ze wzorcem „{1}”. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals nie powinno być używane do potwierdzania. Zamiast tego użyj Assert.AreEqual i przeciążeń. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Nie można odnaleźć określonej składowej ({0}). Może być konieczne ponowne wygenerowanie prywatnej metody dostępu - lub składowa może być zdefiniowana jako prywatna w klasie bazowej. W drugim przypadku należy przekazać typ, - który definiuje składową w konstruktorze obiektu PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Nie można odnaleźć konstruktora z określoną sygnaturą. Może być konieczne ponowne wygenerowanie prywatnej metody dostępu - lub składowa może być zdefiniowana jako prywatna w klasie bazowej. W drugim przypadku należy przekazać typ, - który definiuje składową w konstruktorze obiektu PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Parametr „{0}” jest nieprawidłowy. Wartość nie może być równa null. {1}. - - - - - Different number of elements. - Inna liczba elementów. - - - - - String '{0}' does not start with string '{1}'. {2}. - Ciąg „{0}” nie rozpoczyna się od ciągu „{1}”. {2}. - - - - - The property {0} has type {1}; expected type {2}. - Właściwość {0} jest typu {1}; oczekiwano typu {2}. - - - - - (null) - (null) - - - - - (object) - (obiekt) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Oczekiwanym typem wyjątku musi być typ System.Exception lub typ pochodzący od typu System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Metoda testowa nie zgłosiła wyjątku. Oczekiwano zgłoszenia wyjątku przez atrybut {0} zdefiniowany dla metody testowej. - - - - - Test method did not throw expected exception {0}. {1} - Metoda testowa nie zgłosiła oczekiwanego wyjątku {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Metoda testowa zgłosiła wyjątek {0}, lecz oczekiwano wyjątku {1}. Komunikat wyjątku: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Metoda testowa zgłosiła wyjątek {0}, lecz oczekiwano wyjątku typu {1} lub jego typu pochodnego. Komunikat wyjątku: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Nie można pobrać komunikatu dotyczącego wyjątku typu {0} z powodu wyjątku). - - - - - No exception thrown. {1} exception was expected. {0} - Nie zgłoszono wyjątku. Oczekiwany wyjątek: {1}. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - Zgłoszono wyjątek {2}, ale oczekiwano wyjątku {1}. {0} -Komunikat o wyjątku: {3} -Ślad stosu: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Nie określono testowego źródła danych. Atrybut DataTestMethodAttribute wymaga co najmniej jednego atrybutu TestDataSource. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - asynchroniczna metoda TestMethod z elementem UITestMethodAttribute nie są obsługiwane. Usuń element asynchroniczny lub użyj elementu TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - Właściwość lub metoda {0} w elemencie {1} nie zwraca obiektu IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - Wartość zwracana przez właściwość lub metodę {0} nie powinna być równa null. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - Metoda {0} musi być zgodna z oczekiwaną sygnaturą: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - Właściwość lub metoda {0} w elemencie {1} zwraca pusty interfejs IEnumerable<object[]>. - - - - - + + + + + + Access string has invalid syntax. + Ciąg dostępu ma nieprawidłową składnię. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Oczekiwana kolekcja zawiera {1} wystąpień <{2}>. Bieżąca kolekcja zawiera {3} wystąpień. {0} + + + + Duplicate item found:<{1}>. {0} + Znaleziono duplikat:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Oczekiwana:<{1}>. Rzeczywista:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Oczekiwano różnicy nie większej niż <{3}> pomiędzy oczekiwaną wartością <{1}> a rzeczywistą wartością <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Oczekiwano:<{1}>. Przypadek różni się od rzeczywistej wartości:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Oczekiwana:<{1} ({2})>. Rzeczywista:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Oczekiwano dowolnej wartości za wyjątkiem:<{1}>. Rzeczywista:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Oczekiwano różnicy większej niż <{3}> pomiędzy oczekiwaną wartością <{1}> a rzeczywistą wartością <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Nie przekazuj typów wartości do metody AreSame(). Wartości przekonwertowane na typ Object nigdy nie będą takie same. Rozważ użycie metody AreEqual(). {0} + + + + Both collections are empty. {0} + Obie kolekcje są puste. {0} + + + + Both collection contain same elements. + Obie kolekcje zawierają te same elementy. + + + + Both collection references point to the same collection object. {0} + Odwołania do obu kolekcji wskazują ten sam obiekt kolekcji. {0} + + + + Both collections contain the same elements. {0} + Obie kolekcje zawierają te same elementy. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + Ciąg „{0}” nie zawiera ciągu „{1}”. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Nie zgadza się liczba elementów w kolekcji. Oczekiwana:<{1}>. Rzeczywista:<{2}>.{0} + + + + Element at index {0} do not match. + Element w indeksie {0} nie jest zgodny. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + Element o indeksie {1} jest innego typu niż oczekiwano. Oczekiwany typ:<{2}>. Rzeczywisty typ:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + Element o indeksie {1} jest zerowy (null). Oczekiwany typ: <{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + Ciąg „{0}” nie kończy się ciągiem „{1}”. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Nieprawidłowy argument. Element EqualsTester nie może używać wartości null. + + + + Cannot convert object of type {0} to {1}. + Nie można przekonwertować obiektu typu {0} na typ {1}. + + + + {0} failed. {1} + {0} — niepowodzenie. {1} + + + + The internal object referenced is no longer valid. + Przywoływany obiekt wewnętrzny nie jest już prawidłowy. + + + + The parameter '{0}' is invalid. {1}. + Parametr „{0}” jest nieprawidłowy. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Oczekiwany typ:<{1}>. Rzeczywisty typ:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + Ciąg „{0}” nie jest zgodny ze wzorcem „{1}”. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Zły typ:<{1}>. Rzeczywisty typ:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + Ciąg „{0}” jest zgodny ze wzorcem „{1}”. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals nie powinno być używane do potwierdzania. Zamiast tego użyj Assert.AreEqual i przeciążeń. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Nie można odnaleźć określonej składowej ({0}). Może być konieczne ponowne wygenerowanie prywatnej metody dostępu + lub składowa może być zdefiniowana jako prywatna w klasie bazowej. W drugim przypadku należy przekazać typ, + który definiuje składową w konstruktorze obiektu PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Nie można odnaleźć konstruktora z określoną sygnaturą. Może być konieczne ponowne wygenerowanie prywatnej metody dostępu + lub składowa może być zdefiniowana jako prywatna w klasie bazowej. W drugim przypadku należy przekazać typ, + który definiuje składową w konstruktorze obiektu PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Parametr „{0}” jest nieprawidłowy. Wartość nie może być równa null. {1}. + + + + Different number of elements. + Inna liczba elementów. + + + + String '{0}' does not start with string '{1}'. {2}. + Ciąg „{0}” nie rozpoczyna się od ciągu „{1}”. {2}. + + + + The property {0} has type {1}; expected type {2}. + Właściwość {0} jest typu {1}; oczekiwano typu {2}. + + + + (null) + (null) + + + + (object) + (obiekt) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Oczekiwanym typem wyjątku musi być typ System.Exception lub typ pochodzący od typu System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Metoda testowa nie zgłosiła wyjątku. Oczekiwano zgłoszenia wyjątku przez atrybut {0} zdefiniowany dla metody testowej. + + + + Test method did not throw expected exception {0}. {1} + Metoda testowa nie zgłosiła oczekiwanego wyjątku {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Metoda testowa zgłosiła wyjątek {0}, lecz oczekiwano wyjątku {1}. Komunikat wyjątku: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Metoda testowa zgłosiła wyjątek {0}, lecz oczekiwano wyjątku typu {1} lub jego typu pochodnego. Komunikat wyjątku: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Nie można pobrać komunikatu dotyczącego wyjątku typu {0} z powodu wyjątku). + + + + No exception thrown. {1} exception was expected. {0} + Nie zgłoszono wyjątku. Oczekiwany wyjątek: {1}. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + Zgłoszono wyjątek {2}, ale oczekiwano wyjątku {1}. {0} +Komunikat o wyjątku: {3} +Ślad stosu: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Nie określono testowego źródła danych. Atrybut DataTestMethodAttribute wymaga co najmniej jednego atrybutu TestDataSource. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + asynchroniczna metoda TestMethod z elementem UITestMethodAttribute nie są obsługiwane. Usuń element asynchroniczny lub użyj elementu TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + Właściwość lub metoda {0} w elemencie {1} nie zwraca obiektu IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + Wartość zwracana przez właściwość lub metodę {0} nie powinna być równa null. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + Metoda {0} musi być zgodna z oczekiwaną sygnaturą: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + Właściwość lub metoda {0} w elemencie {1} zwraca pusty interfejs IEnumerable<object[]>. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pt-BR.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pt-BR.xlf index ee7f2bc28..c68218a89 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pt-BR.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.pt-BR.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - A cadeia de caracteres de acesso tem sintaxe inválida. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - A coleção esperada contém {1} ocorrência(s) de <{2}>. A coleção real contém {3} ocorrência(s). {0} - - - - - Duplicate item found:<{1}>. {0} - Item duplicado encontrado:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Esperado:<{1}>. Real:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Esperada uma diferença não maior que <{3}> entre o valor esperado <{1}> e o valor real <{2}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Esperado:<{1}>. Capitalização é diferente para o valor real:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Esperado:<{1} ({2})>. Real:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Esperado qualquer valor exceto:<{1}>. Real:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Esperada uma diferença maior que <{3}> entre o valor esperado <{1}> e o valor real <{2}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Não passe tipos de valores para AreSame(). Os valores convertidos para Object nunca serão os mesmos. Considere usar AreEqual(). {0} - - - - - Both collections are empty. {0} - Ambas as coleções estão vazias. {0} - - - - - Both collection contain same elements. - Ambas as coleções contêm os mesmos elementos. - - - - - Both collection references point to the same collection object. {0} - Ambas as referências de coleção apontam para o mesmo objeto de coleção. {0} - - - - - Both collections contain the same elements. {0} - Ambas as coleções contêm os mesmos elementos. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - A cadeia de caracteres '{0}' não contém a cadeia de caracteres '{1}'. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - O número de elementos nas coleções não coincidem. Esperado:<{1}>. Real:<{2}>.{0} - - - - - Element at index {0} do not match. - O elemento no índice {0} não corresponde. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - Elemento de índice {1} não é de tipo esperado. Tipo esperado:<{2}>. Tipo real:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - Elemento de índice {1} é (nulo). Tipo esperado:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - A cadeia de caracteres '{0}' não termina com a cadeia de caracteres '{1}'. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Argumento inválido - EqualsTester não pode usar valores nulos. - - - - - Cannot convert object of type {0} to {1}. - Não é possível converter objeto do tipo {0} em {1}. - - - - - {0} failed. {1} - {0} falhou. {1} - - - - - The internal object referenced is no longer valid. - O objeto interno referenciado não é mais válido. - - - - - The parameter '{0}' is invalid. {1}. - O parâmetro '{0}' é inválido. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Tipo esperado:<{1}>. Tipo real:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - A cadeia de caracteres '{0}' não corresponde ao padrão '{1}'. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Tipo errado:<{1}>. Tipo real:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - A cadeia de caracteres '{0}' corresponde ao padrão '{1}'. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals não deveria ser usado para Declarações. Use Assert.AreEqual e sobrecargas em seu lugar. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - O membro especificado ({0}) não pôde ser encontrado. Talvez seja necessário gerar novamente seu acessador particular - ou o membro pode ser particular e definido em uma classe base. Se o último caso for verdadeiro, será necessário passar o tipo - que define o membro no construtor do PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - O construtor com a assinatura especificada não pôde ser encontrado. Talvez seja necessário gerar novamente seu acessador particular - ou o membro pode ser particular e definido em uma classe base. Se o último caso for verdadeiro, será necessário passar o tipo - que define o membro para o construtor do PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - O parâmetro '{0}' é inválido. O valor não pode ser nulo. {1}. - - - - - Different number of elements. - Número diferente de elementos. - - - - - String '{0}' does not start with string '{1}'. {2}. - A cadeia de caracteres '{0}' não começa com a cadeia de caracteres '{1}'. {2}. - - - - - The property {0} has type {1}; expected type {2}. - A propriedade {0} é do tipo {1}; o tipo esperado era {2}. - - - - - (null) - (nulo) - - - - - (object) - (objeto) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - O tipo de exceção esperado deve ser System.Exception ou um tipo derivado de System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - O método de teste não emitiu uma exceção. Uma exceção era esperada pelo atributo {0} definido no método de teste. - - - - - Test method did not throw expected exception {0}. {1} - O método de teste não emitiu a exceção esperada {0}. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - O método de teste emitiu a exceção {0}, mas a exceção {1} era esperada. Mensagem de exceção: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - O método de teste emitiu a exceção {0}, mas a exceção {1} ou um tipo derivado dela eram esperados. Mensagem da exceção: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Falha ao obter a mensagem para uma exceção do tipo {0} devido a uma exceção.) - - - - - No exception thrown. {1} exception was expected. {0} - Nenhuma exceção lançada. A exceção {1} era esperada. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - A exceção {2} foi lançada, mas a exceção {1} era esperada. {0} -Mensagem de Exceção: {3} -Rastreamento de Pilha: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Nenhuma fonte de dados especificada. Ao menos um TestDataSource é necessário com DataTestMethodAttribute. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - TestMethod assíncrono com UITestMethodAttribute não têm suporte. Remova o assíncrono ou use o TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - A propriedade ou o método {0} em {1} não retorna IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - O valor retornado pela propriedade ou o método {0} não deve ser nulo null. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - O método {0} deve corresponder à assinatura esperada: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - A propriedade ou o método {0} em {1} retorna um IEnumerable<object[]> vazio. - - - - - + + + + + + Access string has invalid syntax. + A cadeia de caracteres de acesso tem sintaxe inválida. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + A coleção esperada contém {1} ocorrência(s) de <{2}>. A coleção real contém {3} ocorrência(s). {0} + + + + Duplicate item found:<{1}>. {0} + Item duplicado encontrado:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Esperado:<{1}>. Real:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Esperada uma diferença não maior que <{3}> entre o valor esperado <{1}> e o valor real <{2}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Esperado:<{1}>. Capitalização é diferente para o valor real:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Esperado:<{1} ({2})>. Real:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Esperado qualquer valor exceto:<{1}>. Real:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Esperada uma diferença maior que <{3}> entre o valor esperado <{1}> e o valor real <{2}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Não passe tipos de valores para AreSame(). Os valores convertidos para Object nunca serão os mesmos. Considere usar AreEqual(). {0} + + + + Both collections are empty. {0} + Ambas as coleções estão vazias. {0} + + + + Both collection contain same elements. + Ambas as coleções contêm os mesmos elementos. + + + + Both collection references point to the same collection object. {0} + Ambas as referências de coleção apontam para o mesmo objeto de coleção. {0} + + + + Both collections contain the same elements. {0} + Ambas as coleções contêm os mesmos elementos. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + A cadeia de caracteres '{0}' não contém a cadeia de caracteres '{1}'. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + O número de elementos nas coleções não coincidem. Esperado:<{1}>. Real:<{2}>.{0} + + + + Element at index {0} do not match. + O elemento no índice {0} não corresponde. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + Elemento de índice {1} não é de tipo esperado. Tipo esperado:<{2}>. Tipo real:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + Elemento de índice {1} é (nulo). Tipo esperado:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + A cadeia de caracteres '{0}' não termina com a cadeia de caracteres '{1}'. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Argumento inválido - EqualsTester não pode usar valores nulos. + + + + Cannot convert object of type {0} to {1}. + Não é possível converter objeto do tipo {0} em {1}. + + + + {0} failed. {1} + {0} falhou. {1} + + + + The internal object referenced is no longer valid. + O objeto interno referenciado não é mais válido. + + + + The parameter '{0}' is invalid. {1}. + O parâmetro '{0}' é inválido. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Tipo esperado:<{1}>. Tipo real:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + A cadeia de caracteres '{0}' não corresponde ao padrão '{1}'. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Tipo errado:<{1}>. Tipo real:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + A cadeia de caracteres '{0}' corresponde ao padrão '{1}'. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals não deveria ser usado para Declarações. Use Assert.AreEqual e sobrecargas em seu lugar. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + O membro especificado ({0}) não pôde ser encontrado. Talvez seja necessário gerar novamente seu acessador particular + ou o membro pode ser particular e definido em uma classe base. Se o último caso for verdadeiro, será necessário passar o tipo + que define o membro no construtor do PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + O construtor com a assinatura especificada não pôde ser encontrado. Talvez seja necessário gerar novamente seu acessador particular + ou o membro pode ser particular e definido em uma classe base. Se o último caso for verdadeiro, será necessário passar o tipo + que define o membro para o construtor do PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + O parâmetro '{0}' é inválido. O valor não pode ser nulo. {1}. + + + + Different number of elements. + Número diferente de elementos. + + + + String '{0}' does not start with string '{1}'. {2}. + A cadeia de caracteres '{0}' não começa com a cadeia de caracteres '{1}'. {2}. + + + + The property {0} has type {1}; expected type {2}. + A propriedade {0} é do tipo {1}; o tipo esperado era {2}. + + + + (null) + (nulo) + + + + (object) + (objeto) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + O tipo de exceção esperado deve ser System.Exception ou um tipo derivado de System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + O método de teste não emitiu uma exceção. Uma exceção era esperada pelo atributo {0} definido no método de teste. + + + + Test method did not throw expected exception {0}. {1} + O método de teste não emitiu a exceção esperada {0}. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + O método de teste emitiu a exceção {0}, mas a exceção {1} era esperada. Mensagem de exceção: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + O método de teste emitiu a exceção {0}, mas a exceção {1} ou um tipo derivado dela eram esperados. Mensagem da exceção: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Falha ao obter a mensagem para uma exceção do tipo {0} devido a uma exceção.) + + + + No exception thrown. {1} exception was expected. {0} + Nenhuma exceção lançada. A exceção {1} era esperada. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + A exceção {2} foi lançada, mas a exceção {1} era esperada. {0} +Mensagem de Exceção: {3} +Rastreamento de Pilha: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Nenhuma fonte de dados especificada. Ao menos um TestDataSource é necessário com DataTestMethodAttribute. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + TestMethod assíncrono com UITestMethodAttribute não têm suporte. Remova o assíncrono ou use o TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + A propriedade ou o método {0} em {1} não retorna IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + O valor retornado pela propriedade ou o método {0} não deve ser nulo null. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + O método {0} deve corresponder à assinatura esperada: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + A propriedade ou o método {0} em {1} retorna um IEnumerable<object[]> vazio. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ru.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ru.xlf index 9e831e274..f83b4522a 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ru.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.ru.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - Строка доступа имеет недопустимый синтаксис. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Ожидаемый набор содержит следующее число событий <{2}>: {1}. Фактический набор содержит число событий: {3}. {0} - - - - - Duplicate item found:<{1}>. {0} - Обнаружен совпадающий элемент: <{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Ожидается: <{1}>. Фактически: <{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Между ожидаемым значением <{1}> и фактическим значением <{2}> требуется разница не более чем <{3}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Ожидается: <{1}>. Отличается на фактическое значение: <{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Ожидается: <{1} ({2})>. Фактически: <{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Ожидается любое значение, кроме: <{1}>. Фактически: <{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Между ожидаемым значением <{1}> и фактическим значением <{2}> требуется разница более чем <{3}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - Не передавайте типы значений в функцию AreSame(). Значения, преобразованные в Object, никогда не будут одинаковыми. Попробуйте использовать AreEqual(). {0} - - - - - Both collections are empty. {0} - Обе коллекции пусты. {0} - - - - - Both collection contain same elements. - Обе коллекции содержат одинаковые элементы. - - - - - Both collection references point to the same collection object. {0} - Ссылки в обоих коллекциях указывают на один и тот же объект коллекции. {0} - - - - - Both collections contain the same elements. {0} - Обе коллекции содержат одинаковые элементы. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - Строка "{0}" не содержит строку "{1}". {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Число элементов в наборе не соответствует ожидаемому. Ожидается: <{1}>. Фактически: <{2}>.{0} - - - - - Element at index {0} do not match. - Элемент по индексу {0} не совпадает. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - Тип элемента по индексу {1} не соответствует ожидаемому. Ожидаемый тип: <{2}>. Фактический тип: <{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - Элемент по индексу {1} имеет значение (null). Ожидаемый тип: <{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - Строка "{0}" не оканчивается строкой "{1}". {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Недопустимый аргумент — EqualsTester не может использовать значения NULL. - - - - - Cannot convert object of type {0} to {1}. - Невозможно преобразовать объект типа {0} в {1}. - - - - - {0} failed. {1} - Сбой {0}. {1} - - - - - The internal object referenced is no longer valid. - Внутренний объект, на который есть ссылка, больше не является допустимым. - - - - - The parameter '{0}' is invalid. {1}. - Параметр "{0}" является недопустимым. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0}Ожидается тип: <{1}>. Фактический тип: <{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - Строка "{0}" не соответствует шаблону "{1}". {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Неверный тип: <{1}>. Фактический тип: <{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - Строка "{0}" соответствует шаблону "{1}". {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Нельзя использовать Assert.Equals для Assertions. Вместо этого используйте Assert.AreEqual и перегрузки. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Не удается найти указанный член ({0}). Возможно, требуется снова создать закрытый метод доступа - либо член является закрытым и определенным на основе базового класса. Если справедливо последнее, то - необходимо передать тип, определяющий член, в конструктор для PrivateObject. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Не удается найти конструктор с указанной сигнатурой. Возможно, требуется снова создать закрытый - метод доступа либо член является закрытым и определенным на основе базового класса. Если - справедливо последнее, то необходимо передать тип, определяющий член, в конструктор для PrivateObject. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - Параметр "{0}" является недопустимым. Значение не может быть NULL. {1}. - - - - - Different number of elements. - Разное число элементов. - - - - - String '{0}' does not start with string '{1}'. {2}. - Строка "{0}" не начинается со строки "{1}". {2}. - - - - - The property {0} has type {1}; expected type {2}. - Свойство {0} имеет тип {1}. Ожидается тип {2}. - - - - - (null) - (NULL) - - - - - (object) - (объект) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Тип ожидаемого исключения должен быть System.Exception или производным от System.Exception. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Метод теста не создал исключение. Исключение ожидалось атрибутом {0}, определенным в методе теста. - - - - - Test method did not throw expected exception {0}. {1} - Метод теста не создал ожидаемое исключение ({0}). {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Метод теста создал исключение "{0}", а ожидалось исключение "{1}". Сообщение исключения: "{2}". - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Метод теста создал исключение "{0}", а ожидалось исключение "{1}" или производный от него тип. Сообщение исключения: "{2}". - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Не удалось получить сообщение для исключения с типом {0} в связи с возникновением исключения.) - - - - - No exception thrown. {1} exception was expected. {0} - Исключение не создано. Ожидалось исключение {1}. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - Создано исключение {2}, хотя ожидалось исключение {1}. {0} -Сообщение исключения: {3} -Трассировка стека: {4}. - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Не указан источник данных теста. Требуется по меньшей мере один элемент TestDataSource для DataTestMethodAttribute. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - Асинхронный метод TestMethod с UITestMethodAttribute не поддерживается. Удалите префикс async или используйте TestMethodAttribute. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - Свойство или метод {0} объекта {1} не возвращает IEnumerable<object[]>. - - - - - Value returned by property or method {0} shouldn't be null. - Значение, возвращаемое свойством или методом {0}, не должно быть равно NULL. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - Метод {0} должен соответствовать ожидаемой сигнатуре: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - Свойство или метод {0} класса {1} возвращает пустой IEnumerable<object[]>. - - - - - + + + + + + Access string has invalid syntax. + Строка доступа имеет недопустимый синтаксис. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Ожидаемый набор содержит следующее число событий <{2}>: {1}. Фактический набор содержит число событий: {3}. {0} + + + + Duplicate item found:<{1}>. {0} + Обнаружен совпадающий элемент: <{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Ожидается: <{1}>. Фактически: <{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Между ожидаемым значением <{1}> и фактическим значением <{2}> требуется разница не более чем <{3}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Ожидается: <{1}>. Отличается на фактическое значение: <{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Ожидается: <{1} ({2})>. Фактически: <{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Ожидается любое значение, кроме: <{1}>. Фактически: <{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Между ожидаемым значением <{1}> и фактическим значением <{2}> требуется разница более чем <{3}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + Не передавайте типы значений в функцию AreSame(). Значения, преобразованные в Object, никогда не будут одинаковыми. Попробуйте использовать AreEqual(). {0} + + + + Both collections are empty. {0} + Обе коллекции пусты. {0} + + + + Both collection contain same elements. + Обе коллекции содержат одинаковые элементы. + + + + Both collection references point to the same collection object. {0} + Ссылки в обоих коллекциях указывают на один и тот же объект коллекции. {0} + + + + Both collections contain the same elements. {0} + Обе коллекции содержат одинаковые элементы. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + Строка "{0}" не содержит строку "{1}". {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Число элементов в наборе не соответствует ожидаемому. Ожидается: <{1}>. Фактически: <{2}>.{0} + + + + Element at index {0} do not match. + Элемент по индексу {0} не совпадает. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + Тип элемента по индексу {1} не соответствует ожидаемому. Ожидаемый тип: <{2}>. Фактический тип: <{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + Элемент по индексу {1} имеет значение (null). Ожидаемый тип: <{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + Строка "{0}" не оканчивается строкой "{1}". {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Недопустимый аргумент — EqualsTester не может использовать значения NULL. + + + + Cannot convert object of type {0} to {1}. + Невозможно преобразовать объект типа {0} в {1}. + + + + {0} failed. {1} + Сбой {0}. {1} + + + + The internal object referenced is no longer valid. + Внутренний объект, на который есть ссылка, больше не является допустимым. + + + + The parameter '{0}' is invalid. {1}. + Параметр "{0}" является недопустимым. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0}Ожидается тип: <{1}>. Фактический тип: <{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + Строка "{0}" не соответствует шаблону "{1}". {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Неверный тип: <{1}>. Фактический тип: <{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + Строка "{0}" соответствует шаблону "{1}". {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Нельзя использовать Assert.Equals для Assertions. Вместо этого используйте Assert.AreEqual и перегрузки. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Не удается найти указанный член ({0}). Возможно, требуется снова создать закрытый метод доступа + либо член является закрытым и определенным на основе базового класса. Если справедливо последнее, то + необходимо передать тип, определяющий член, в конструктор для PrivateObject. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Не удается найти конструктор с указанной сигнатурой. Возможно, требуется снова создать закрытый + метод доступа либо член является закрытым и определенным на основе базового класса. Если + справедливо последнее, то необходимо передать тип, определяющий член, в конструктор для PrivateObject. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + Параметр "{0}" является недопустимым. Значение не может быть NULL. {1}. + + + + Different number of elements. + Разное число элементов. + + + + String '{0}' does not start with string '{1}'. {2}. + Строка "{0}" не начинается со строки "{1}". {2}. + + + + The property {0} has type {1}; expected type {2}. + Свойство {0} имеет тип {1}. Ожидается тип {2}. + + + + (null) + (NULL) + + + + (object) + (объект) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Тип ожидаемого исключения должен быть System.Exception или производным от System.Exception. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Метод теста не создал исключение. Исключение ожидалось атрибутом {0}, определенным в методе теста. + + + + Test method did not throw expected exception {0}. {1} + Метод теста не создал ожидаемое исключение ({0}). {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Метод теста создал исключение "{0}", а ожидалось исключение "{1}". Сообщение исключения: "{2}". + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Метод теста создал исключение "{0}", а ожидалось исключение "{1}" или производный от него тип. Сообщение исключения: "{2}". + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Не удалось получить сообщение для исключения с типом {0} в связи с возникновением исключения.) + + + + No exception thrown. {1} exception was expected. {0} + Исключение не создано. Ожидалось исключение {1}. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + Создано исключение {2}, хотя ожидалось исключение {1}. {0} +Сообщение исключения: {3} +Трассировка стека: {4}. + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Не указан источник данных теста. Требуется по меньшей мере один элемент TestDataSource для DataTestMethodAttribute. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + Асинхронный метод TestMethod с UITestMethodAttribute не поддерживается. Удалите префикс async или используйте TestMethodAttribute. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + Свойство или метод {0} объекта {1} не возвращает IEnumerable<object[]>. + + + + Value returned by property or method {0} shouldn't be null. + Значение, возвращаемое свойством или методом {0}, не должно быть равно NULL. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + Метод {0} должен соответствовать ожидаемой сигнатуре: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + Свойство или метод {0} класса {1} возвращает пустой IEnumerable<object[]>. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.tr.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.tr.xlf index 8f6d1d8a7..86aa2be21 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.tr.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.tr.xlf @@ -1,351 +1,297 @@ - - - - - - Access string has invalid syntax. - Erişim dizesi geçersiz söz dizimine sahip. - - - - - The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} - Beklenen koleksiyon {1} <{2}> örneği içerir. Gerçek koleksiyon {3} örnek içerir. {0} - - - - - Duplicate item found:<{1}>. {0} - Yinelenen öğe bulundu:<{1}>. {0} - - - - - Expected:<{1}>. Actual:<{2}>. {0} - Beklenen:<{1}>. Gerçek:<{2}>. {0} - - - - - Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Beklenen değer <{1}> ile gerçek değer <{2}> arasında, şundan büyük olmayan fark bekleniyor: <{3}>. {0} - - - - - Expected:<{1}>. Case is different for actual value:<{2}>. {0} - Beklenen:<{1}>. Durum, gerçek değer için farklı:<{2}>. {0} - - - - - Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} - Beklenen:<{1} ({2})>. Gerçek:<{3} ({4})>. {0} - - - - - Expected any value except:<{1}>. Actual:<{2}>. {0} - Şunun dışında bir değer bekleniyor:<{1}>. Gerçek:<{2}>. {0} - - - - - Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} - Beklenen değer <{1}> ile gerçek değer <{2}> arasında, şundan büyük olan fark bekleniyor: <{3}>. {0} - - - - - Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} - AreSame()'e değer türleri geçirmeyin. Object olarak dönüştürülen değerler asla aynı olamayacak. AreEqual() kullanmayı düşün. {0} - - - - - Both collections are empty. {0} - Koleksiyonların her ikisi de boş. {0} - - - - - Both collection contain same elements. - Her iki koleksiyon da aynı öğeleri içeriyor. - - - - - Both collection references point to the same collection object. {0} - Her iki koleksiyon başvurusu da aynı koleksiyon nesnesine işaret ediyor. {0} - - - - - Both collections contain the same elements. {0} - Her iki koleksiyon da aynı öğeleri içeriyor. {0} - - - - - {0}({1}) - {0}({1}) - - - - - String '{0}' does not contain string '{1}'. {2}. - '{0}' dizesi, '{1}' dizesini içermiyor. {2}. - - - - - The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} - Koleksiyonlar içindeki öğe sayıları eşleşmiyor. Beklenen:<{1}>. Gerçek:<{2}>.{0} - - - - - Element at index {0} do not match. - {0} dizinindeki öğe eşleşmiyor. - - - - - Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} - {1} dizinindeki öğe, beklenen türde değil. Beklenen tür:<{2}>. Gerçek tür:<{3}>.{0} - - - - - Element at index {1} is (null). Expected type:<{2}>.{0} - {1} dizinindeki öğe (null). Beklenen tür:<{2}>.{0} - - - - - String '{0}' does not end with string '{1}'. {2}. - '{0}' dizesi, '{1}' dizesi ile sonlanmıyor. {2}. - - - - - Invalid argument- EqualsTester can't use nulls. - Geçersiz bağımsız değişken- EqualsTester, null değerleri kullanamaz. - - - - - Cannot convert object of type {0} to {1}. - {0} türündeki nesne {1} türüne dönüştürülemez. - - - - - {0} failed. {1} - {0} başarısız. {1} - - - - - The internal object referenced is no longer valid. - Başvurulan dahili nesne artık geçerli değil. - - - - - The parameter '{0}' is invalid. {1}. - '{0}' parametresi geçersiz. {1}. - - - - - {0} Expected type:<{1}>. Actual type:<{2}>. - {0} Beklenen tür:<{1}>. Gerçek tür:<{2}>. - - - - - String '{0}' does not match pattern '{1}'. {2}. - '{0}' dizesi, '{1}' deseni ile eşleşmiyor. {2}. - - - - - Wrong Type:<{1}>. Actual type:<{2}>. {0} - Yanlış Tür:<{1}>. Gerçek tür:<{2}>. {0} - - - - - String '{0}' matches pattern '{1}'. {2}. - '{0}' dizesi, '{1}' deseni ile eşleşiyor. {2}. - - - - - Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. - Assert.Equals, Onaylama için kullanılmamalı. Lütfen yerine Assert.AreEqual & aşırı yüklemeleri kullanın. - - - - - - The member specified ({0}) could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Belirtilen üye ({0}) bulunamadı. Özel erişimcinizi yeniden oluşturmanız gerekiyor olabilir - veya üye, özel olabilir ve temel sınıfta tanımlı olabilir. Eğer ikincisi doğru ise, türü geçirmeniz gerekir; - bu tür PrivateObject'in oluşturucusunda üyeyi tanımlar. - - - - - - - The constructor with the specified signature could not be found. You might need to regenerate your private accessor, - or the member may be private and defined on a base class. If the latter is true, you need to pass the type - that defines the member into PrivateObject's constructor. - - - Belirtilmiş imzaya sahip oluşturucu bulunamadı. Özel erişimcinizi yeniden oluşturmanız gerekiyor olabilir - veya üye, özel olabilir ve temel sınıfta tanımlı olabilir. Eğer ikincisi doğru ise, türü geçirmeniz gerekir; - bu tür, PrivateObject'in oluşturucusunda üyeyi tanımlar. - - - - - - The parameter '{0}' is invalid. The value cannot be null. {1}. - '{0}' parametresi geçersiz. Değer null olamaz. {1}. - - - - - Different number of elements. - Öğe sayıları farklı. - - - - - String '{0}' does not start with string '{1}'. {2}. - '{0}' dizesi, '{1}' dizesi ile başlamıyor. {2}. - - - - - The property {0} has type {1}; expected type {2}. - {0} özelliği, {1} türüne sahip; beklenen tür {2}. - - - - - (null) - (null) - - - - - (object) - (nesne) - - - - - The expected exception type must be System.Exception or a type derived from System.Exception. - Beklenen özel durum türü, System.Exception türü veya System.Exception'dan türetilmiş bir tür olmalıdır. - - - - - Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. - Test metodu bir özel durum oluşturmadı. Test metodunda tanımlanan {0} özniteliği tarafından bir özel durum bekleniyordu. - - - - - Test method did not throw expected exception {0}. {1} - Test yöntemi beklenen {0} özel durumunu oluşturmadı. {1} - - - - - Test method threw exception {0}, but exception {1} was expected. Exception message: {2} - Test yöntemi {0} özel durumunu oluşturdu, ancak {1} özel durumu bekleniyordu. Özel durum iletisi: {2} - - - - - Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} - Test yöntemi {0} özel durumunu oluşturdu, ancak {1} özel durumu veya ondan türetilmiş bir tür bekleniyordu. Özel durum iletisi: {2} - - - - - (Failed to get the message for an exception of type {0} due to an exception.) - (Bir özel durum nedeniyle, {0} türündeki özel durum iletisi alınamadı.) - - - - - No exception thrown. {1} exception was expected. {0} - Özel durum oluşturulmadı. {1} özel durumu bekleniyordu. {0} - - - - - Threw exception {2}, but exception {1} was expected. {0} -Exception Message: {3} -Stack Trace: {4} - {2} özel durumu oluşturuldu, ancak {1} özel durumu bekleniyordu. {0} -Özel Durum İletisi: {3} -Yığın İzleme: {4} - - - - - No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. - Test verisi kaynağı belirtilmedi. DataTestMethodAttribute ile en az bir TestDataSource gereklidir. - - - - - {0} ({1}) - {0} ({1}) - - - - - async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. - UITestMethodAttribute özniteliğine sahip async TestMethod metodu desteklenmiyor. async ifadesini kaldırın ya da TestMethodAttribute özniteliğini kullanın. - - - - - Property or method {0} on {1} does not return IEnumerable<object[]>. - {1} üzerindeki {0} özelliği veya metodu IEnumerable<object[]> döndürmez. - - - - - Value returned by property or method {0} shouldn't be null. - {0} özelliği veya metodu tarafından döndürülen değer null olamaz. - - - - - Method {0} must match the expected signature: public static {1} {0}({2}). - {0} metodu, beklenen imzayla eşleşmelidir: public static {1} {0}({2}). - - - - - Property or method {0} on {1} returns empty IEnumerable<object[]>. - {1} üzerindeki {0} özelliği veya metodu boş IEnumerable<object[]> döndürür. - - - - - + + + + + + Access string has invalid syntax. + Erişim dizesi geçersiz söz dizimine sahip. + + + + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} + Beklenen koleksiyon {1} <{2}> örneği içerir. Gerçek koleksiyon {3} örnek içerir. {0} + + + + Duplicate item found:<{1}>. {0} + Yinelenen öğe bulundu:<{1}>. {0} + + + + Expected:<{1}>. Actual:<{2}>. {0} + Beklenen:<{1}>. Gerçek:<{2}>. {0} + + + + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Beklenen değer <{1}> ile gerçek değer <{2}> arasında, şundan büyük olmayan fark bekleniyor: <{3}>. {0} + + + + Expected:<{1}>. Case is different for actual value:<{2}>. {0} + Beklenen:<{1}>. Durum, gerçek değer için farklı:<{2}>. {0} + + + + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} + Beklenen:<{1} ({2})>. Gerçek:<{3} ({4})>. {0} + + + + Expected any value except:<{1}>. Actual:<{2}>. {0} + Şunun dışında bir değer bekleniyor:<{1}>. Gerçek:<{2}>. {0} + + + + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} + Beklenen değer <{1}> ile gerçek değer <{2}> arasında, şundan büyük olan fark bekleniyor: <{3}>. {0} + + + + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} + AreSame()'e değer türleri geçirmeyin. Object olarak dönüştürülen değerler asla aynı olamayacak. AreEqual() kullanmayı düşün. {0} + + + + Both collections are empty. {0} + Koleksiyonların her ikisi de boş. {0} + + + + Both collection contain same elements. + Her iki koleksiyon da aynı öğeleri içeriyor. + + + + Both collection references point to the same collection object. {0} + Her iki koleksiyon başvurusu da aynı koleksiyon nesnesine işaret ediyor. {0} + + + + Both collections contain the same elements. {0} + Her iki koleksiyon da aynı öğeleri içeriyor. {0} + + + + {0}({1}) + {0}({1}) + + + + String '{0}' does not contain string '{1}'. {2}. + '{0}' dizesi, '{1}' dizesini içermiyor. {2}. + + + + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} + Koleksiyonlar içindeki öğe sayıları eşleşmiyor. Beklenen:<{1}>. Gerçek:<{2}>.{0} + + + + Element at index {0} do not match. + {0} dizinindeki öğe eşleşmiyor. + + + + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} + {1} dizinindeki öğe, beklenen türde değil. Beklenen tür:<{2}>. Gerçek tür:<{3}>.{0} + + + + Element at index {1} is (null). Expected type:<{2}>.{0} + {1} dizinindeki öğe (null). Beklenen tür:<{2}>.{0} + + + + String '{0}' does not end with string '{1}'. {2}. + '{0}' dizesi, '{1}' dizesi ile sonlanmıyor. {2}. + + + + Invalid argument- EqualsTester can't use nulls. + Geçersiz bağımsız değişken- EqualsTester, null değerleri kullanamaz. + + + + Cannot convert object of type {0} to {1}. + {0} türündeki nesne {1} türüne dönüştürülemez. + + + + {0} failed. {1} + {0} başarısız. {1} + + + + The internal object referenced is no longer valid. + Başvurulan dahili nesne artık geçerli değil. + + + + The parameter '{0}' is invalid. {1}. + '{0}' parametresi geçersiz. {1}. + + + + {0} Expected type:<{1}>. Actual type:<{2}>. + {0} Beklenen tür:<{1}>. Gerçek tür:<{2}>. + + + + String '{0}' does not match pattern '{1}'. {2}. + '{0}' dizesi, '{1}' deseni ile eşleşmiyor. {2}. + + + + Wrong Type:<{1}>. Actual type:<{2}>. {0} + Yanlış Tür:<{1}>. Gerçek tür:<{2}>. {0} + + + + String '{0}' matches pattern '{1}'. {2}. + '{0}' dizesi, '{1}' deseni ile eşleşiyor. {2}. + + + + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. + Assert.Equals, Onaylama için kullanılmamalı. Lütfen yerine Assert.AreEqual & aşırı yüklemeleri kullanın. + + + + + The member specified ({0}) could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Belirtilen üye ({0}) bulunamadı. Özel erişimcinizi yeniden oluşturmanız gerekiyor olabilir + veya üye, özel olabilir ve temel sınıfta tanımlı olabilir. Eğer ikincisi doğru ise, türü geçirmeniz gerekir; + bu tür PrivateObject'in oluşturucusunda üyeyi tanımlar. + + + + + + The constructor with the specified signature could not be found. You might need to regenerate your private accessor, + or the member may be private and defined on a base class. If the latter is true, you need to pass the type + that defines the member into PrivateObject's constructor. + + + Belirtilmiş imzaya sahip oluşturucu bulunamadı. Özel erişimcinizi yeniden oluşturmanız gerekiyor olabilir + veya üye, özel olabilir ve temel sınıfta tanımlı olabilir. Eğer ikincisi doğru ise, türü geçirmeniz gerekir; + bu tür, PrivateObject'in oluşturucusunda üyeyi tanımlar. + + + + + The parameter '{0}' is invalid. The value cannot be null. {1}. + '{0}' parametresi geçersiz. Değer null olamaz. {1}. + + + + Different number of elements. + Öğe sayıları farklı. + + + + String '{0}' does not start with string '{1}'. {2}. + '{0}' dizesi, '{1}' dizesi ile başlamıyor. {2}. + + + + The property {0} has type {1}; expected type {2}. + {0} özelliği, {1} türüne sahip; beklenen tür {2}. + + + + (null) + (null) + + + + (object) + (nesne) + + + + The expected exception type must be System.Exception or a type derived from System.Exception. + Beklenen özel durum türü, System.Exception türü veya System.Exception'dan türetilmiş bir tür olmalıdır. + + + + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. + Test metodu bir özel durum oluşturmadı. Test metodunda tanımlanan {0} özniteliği tarafından bir özel durum bekleniyordu. + + + + Test method did not throw expected exception {0}. {1} + Test yöntemi beklenen {0} özel durumunu oluşturmadı. {1} + + + + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} + Test yöntemi {0} özel durumunu oluşturdu, ancak {1} özel durumu bekleniyordu. Özel durum iletisi: {2} + + + + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} + Test yöntemi {0} özel durumunu oluşturdu, ancak {1} özel durumu veya ondan türetilmiş bir tür bekleniyordu. Özel durum iletisi: {2} + + + + (Failed to get the message for an exception of type {0} due to an exception.) + (Bir özel durum nedeniyle, {0} türündeki özel durum iletisi alınamadı.) + + + + No exception thrown. {1} exception was expected. {0} + Özel durum oluşturulmadı. {1} özel durumu bekleniyordu. {0} + + + + Threw exception {2}, but exception {1} was expected. {0} +Exception Message: {3} +Stack Trace: {4} + {2} özel durumu oluşturuldu, ancak {1} özel durumu bekleniyordu. {0} +Özel Durum İletisi: {3} +Yığın İzleme: {4} + + + + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. + Test verisi kaynağı belirtilmedi. DataTestMethodAttribute ile en az bir TestDataSource gereklidir. + + + + {0} ({1}) + {0} ({1}) + + + + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. + UITestMethodAttribute özniteliğine sahip async TestMethod metodu desteklenmiyor. async ifadesini kaldırın ya da TestMethodAttribute özniteliğini kullanın. + + + + Property or method {0} on {1} does not return IEnumerable<object[]>. + {1} üzerindeki {0} özelliği veya metodu IEnumerable<object[]> döndürmez. + + + + Value returned by property or method {0} shouldn't be null. + {0} özelliği veya metodu tarafından döndürülen değer null olamaz. + + + + Method {0} must match the expected signature: public static {1} {0}({2}). + {0} metodu, beklenen imzayla eşleşmelidir: public static {1} {0}({2}). + + + + Property or method {0} on {1} returns empty IEnumerable<object[]>. + {1} üzerindeki {0} özelliği veya metodu boş IEnumerable<object[]> döndürür. + + + + \ No newline at end of file diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hans.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hans.xlf index 74747b16b..524a1162f 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hans.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hans.xlf @@ -5,188 +5,157 @@ Access string has invalid syntax. 访问字符串的语法无效。 - - + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} 所需集合包含 <{2}> 的 {1} 个匹配项。实际集合包含 {3} 个匹配项。{0} - - + Duplicate item found:<{1}>. {0} 找到了重复项: <{1}>。{0} - - + Expected:<{1}>. Actual:<{2}>. {0} 应为: <{1}>,实际为: <{2}>。{0} - - + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} 预期值 <{1}> 和实际值 <{2}> 之间的差不应大于 <{3}>。{0} - - + Expected:<{1}>. Case is different for actual value:<{2}>. {0} 应为: <{1}>。实际值的大小写有所不同: <{2}>。{0} - - + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} 应为: <{1} ({2})>,实际为: <{3} ({4})>。{0} - - + Expected any value except:<{1}>. Actual:<{2}>. {0} 应为: <{1}> 以外的任意值,实际为: <{2}>。{0} - - + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} 预期值 <{1}> 和实际值 <{2}> 之间的差应大于 <{3}>。{0} - - + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} 不要向 AreSame() 传递值类型。转换为 Object 的值将永远不会相等。请考虑使用 AreEqual()。{0} - - + Both collections are empty. {0} 这两个集合都为空。{0} - - + Both collection contain same elements. 这两个集合包含相同的元素。 - - + Both collection references point to the same collection object. {0} 这两个集合引用指向同一个集合对象。{0} - - + Both collections contain the same elements. {0} 这两个集合包含相同的元素。{0} - - + {0}({1}) {0}({1}) - - + String '{0}' does not contain string '{1}'. {2}. 字符串“{0}”不包含字符串“{1}”。{2}。 - - + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} 集合中元素的数量不匹配。应为: <{1}>,实际为: <{2}>。{0} - - + Element at index {0} do not match. 索引 {0} 处的元素不匹配。 - - + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} 索引 {1} 处的元素不是所需类型。所需类型为: <{2}>,实际类型为: <{3}>。{0} - - + Element at index {1} is (null). Expected type:<{2}>.{0} 索引 {1} 处的元素为(null)。所需类型为: <{2}>。{0} - - + String '{0}' does not end with string '{1}'. {2}. 字符串“{0}”不以字符串“{1}”结尾。{2}。 - - + Invalid argument- EqualsTester can't use nulls. 参数无效 - EqualsTester 不能使用 NULL。 - - + Cannot convert object of type {0} to {1}. 无法将类型为 {0} 的对象转换为 {1}。 - - + {0} failed. {1} {0} 失败。{1} - - + The internal object referenced is no longer valid. 所引用的内部对象不再有效。 - - + The parameter '{0}' is invalid. {1}. 参数“{0}”无效。{1}。 - - + {0} Expected type:<{1}>. Actual type:<{2}>. {0} 类型应为: <{1}>。类型实为: <{2}>。 - - + String '{0}' does not match pattern '{1}'. {2}. 字符串“{0}”与模式“{1}”不匹配。{2}。 - - + Wrong Type:<{1}>. Actual type:<{2}>. {0} 错误类型为: <{1}>,实际类型为: <{2}>。{0} - - + String '{0}' matches pattern '{1}'. {2}. 字符串“{0}”与模式“{1}”匹配。{2}。 - - + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. Assert.Equals 不应用于断言。请改用 Assert.AreEqual 和重载。 - - + @@ -199,8 +168,7 @@ 或者该成员可能是私有成员并且是在基类上定义的。如果属于后一种情况,则需要将定义 该成员的类型传递到 PrivateObject 的构造函数中。 - - + @@ -213,86 +181,72 @@ 或者该成员可能是私有成员并且是在基类上定义的。如果属于后一种情况,则需要将定义 该成员的类型传递到 PrivateObject 的构造函数。 - - + The parameter '{0}' is invalid. The value cannot be null. {1}. 参数“{0}”无效。值不能为 NULL。{1}。 - - + Different number of elements. 不同数量的元素。 - - + String '{0}' does not start with string '{1}'. {2}. 字符串“{0}”没有以字符串“{1}”开头。{2}。 - - + The property {0} has type {1}; expected type {2}. 属性 {0} 的类型为 {1};类型应为 {2}。 - - + (null) (NULL) - - + (object) (对象) - - + The expected exception type must be System.Exception or a type derived from System.Exception. 预期的异常类型必须为 System.Exception 或从 System.Exception 派生的类型。 - - + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. 测试方法未引发异常。预期会因测试方法上定义的属性 {0} 引发一个异常。 - - + Test method did not throw expected exception {0}. {1} 测试方法未引发预期异常 {0}. {1} - - + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} 测试方法引发异常 {0},但预期异常是 {1}。异常消息: {2} - - + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} 测试方法引发异常 {0},但预期异常是 {1} 或其派生类型。异常消息: {2} - - + (Failed to get the message for an exception of type {0} due to an exception.) (因异常而未能获取类型为 {0} 的异常的消息。) - - + No exception thrown. {1} exception was expected. {0} 未引发异常。原来预计会引发异常 {1}。{0} - - + Threw exception {2}, but exception {1} was expected. {0} @@ -301,50 +255,42 @@ Stack Trace: {4} 原来预计会引发异常 {1},但引发了异常 {2}。{0} 异常消息: {3} 堆栈跟踪: {4} - - + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. 未指定测试数据源。使用 DataTestMethodAttribute 至少需要一个 TestDataSource。 - - + {0} ({1}) {0} ({1}) - - + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. 不支持具有 UITestMethodAttribute 的异步 TestMethod。请删除异步或使用 TestMethodAttribute。 - - + Property or method {0} on {1} does not return IEnumerable<object[]>. {1} 上的属性或方法 {0} 不返回 IEnumerable<object[]>。 - - + Value returned by property or method {0} shouldn't be null. 属性或方法 {0} 返回的值不能为 null。 - - + Method {0} must match the expected signature: public static {1} {0}({2}). 方法 {0} 必须匹配预期签名: public static {1} {0}({2})。 - - + Property or method {0} on {1} returns empty IEnumerable<object[]>. {1} 上的属性或方法 {0} 返回空 IEnumerable<object[]>。 - - + diff --git a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hant.xlf b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hant.xlf index f7254d6e6..a5230711f 100644 --- a/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hant.xlf +++ b/src/TestFramework/MSTest.Core/Resources/xlf/FrameworkMessages.zh-Hant.xlf @@ -5,188 +5,157 @@ Access string has invalid syntax. 存取字串有無效的語法。 - - + The expected collection contains {1} occurrence(s) of <{2}>. The actual collection contains {3} occurrence(s). {0} 預期在集合中包含 {1} 項 <{2}>,但實際的集合卻有 {3} 項。{0} - - + Duplicate item found:<{1}>. {0} 找到重複的項目: <{1}>。{0} - - + Expected:<{1}>. Actual:<{2}>. {0} 預期: <{1}>。實際: <{2}>。{0} - - + Expected a difference no greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} 預期值 <{1}> 和實際值 <{2}> 之間的預期差異沒有大於 <{3}>。{0} - - + Expected:<{1}>. Case is different for actual value:<{2}>. {0} 預期: <{1}>。大小寫與下列實際值不同: <{2}>。{0} - - + Expected:<{1} ({2})>. Actual:<{3} ({4})>. {0} 預期: <{1} ({2})>。實際: <{3} ({4})>。{0} - - + Expected any value except:<{1}>. Actual:<{2}>. {0} 預期任何值 (<{1}> 除外)。實際: <{2}>。{0} - - + Expected a difference greater than <{3}> between expected value <{1}> and actual value <{2}>. {0} 預期值 <{1}> 和實際值 <{2}> 之間的預期差異大於 <{3}>。{0} - - + Do not pass value types to AreSame(). Values converted to Object will never be the same. Consider using AreEqual(). {0} 不要將實值型別傳遞給 AreSame()。轉換成 Object 的值從此不再一樣。請考慮使用 AreEqual()。{0} - - + Both collections are empty. {0} 兩個集合皆空白。{0} - - + Both collection contain same elements. 兩個集合含有相同的項目。 - - + Both collection references point to the same collection object. {0} 兩個集合參考都指向同一個集合物件。{0} - - + Both collections contain the same elements. {0} 兩個集合含有相同的項目。{0} - - + {0}({1}) {0}({1}) - - + String '{0}' does not contain string '{1}'. {2}. 字串 '{0}' 未包含字串 '{1}'。{2}。 - - + The number of elements in the collections do not match. Expected:<{1}>. Actual:<{2}>.{0} 集合中的項目數目不符。預期: <{1}>。實際: <{2}>。{0} - - + Element at index {0} do not match. 位於索引 {0} 的項目不符。 - - + Element at index {1} is not of expected type. Expected type:<{2}>. Actual type:<{3}>.{0} 位於索引 {1} 的項目不是預期的類型。預期的類型: <{2}>。實際的類型: <{3}>。{0} - - + Element at index {1} is (null). Expected type:<{2}>.{0} 位於索引 {1} 的項目是 (null)。預期的類型: <{2}>。{0} - - + String '{0}' does not end with string '{1}'. {2}. 字串 '{0}' 不是以字串 '{1}' 結尾。{2}。 - - + Invalid argument- EqualsTester can't use nulls. 引數無效 - EqualsTester 不可使用 null。 - - + Cannot convert object of type {0} to {1}. 無法將 {0} 類型的物件轉換為 {1}。 - - + {0} failed. {1} {0} 失敗。 {1} - - + The internal object referenced is no longer valid. 所參考的內部物件已不再有效。 - - + The parameter '{0}' is invalid. {1}. 參數 '{0}' 無效。{1}。 - - + {0} Expected type:<{1}>. Actual type:<{2}>. {0} 預期的類型: <{1}>,實際的類型: <{2}>。 - - + String '{0}' does not match pattern '{1}'. {2}. 字串 '{0}' 與模式 '{1}' 不符。{2}。 - - + Wrong Type:<{1}>. Actual type:<{2}>. {0} 錯誤的類型: <{1}>。實際的類型: <{2}>。{0} - - + String '{0}' matches pattern '{1}'. {2}. 字串 '{0}' 與模式 '{1}' 相符。{2}。 - - + Assert.Equals should not be used for Assertions. Please use Assert.AreEqual & overloads instead. Assert.Equals 不應使用於判斷提示。請改用 Assert.AreEqual 及多載。 - - + @@ -199,8 +168,7 @@ 或者該成員可能為私用,並且定義在基底類別上。如果是後者, 您必須將定義該成員的類型傳遞至 PrivateObject 的建構函式。 - - + @@ -213,86 +181,72 @@ 或者該成員可能為私用,並且定義在基底類別上。如果是後者,您必須 將定義該成員的類型傳遞至 PrivateObject 的建構函式。 - - + The parameter '{0}' is invalid. The value cannot be null. {1}. 參數 '{0}' 無效。此值不可為 null。{1}。 - - + Different number of elements. 項目數目不同。 - - + String '{0}' does not start with string '{1}'. {2}. 字串 '{0}' 不是以字串 '{1}' 開頭。{2}。 - - + The property {0} has type {1}; expected type {2}. 屬性 {0} 具有類型 {1}; 預期為類型 {2}。 - - + (null) (null) - - + (object) (物件) - - + The expected exception type must be System.Exception or a type derived from System.Exception. 預期的例外狀況類型必須是 System.Exception 或衍生自 System.Exception 的類型。 - - + Test method did not throw an exception. An exception was expected by attribute {0} defined on the test method. 測試方法未擲回例外狀況。測試方法上定義的屬性 {0} 需要例外狀況。 - - + Test method did not throw expected exception {0}. {1} 測試方法未擲回預期的例外狀況 {0}。{1} - - + Test method threw exception {0}, but exception {1} was expected. Exception message: {2} 測試方法擲回例外狀況 {0},但需要的是例外狀況 {1}。例外狀況訊息: {2} - - + Test method threw exception {0}, but exception {1} or a type derived from it was expected. Exception message: {2} 測試方法擲回例外狀況 {0},但需要的是例外狀況 {1} 或是衍生自其的類型。例外狀況訊息: {2} - - + (Failed to get the message for an exception of type {0} due to an exception.) (因為發生例外狀況,所以無法取得類型 {0} 之例外狀況的訊息。) - - + No exception thrown. {1} exception was expected. {0} 未擲回任何例外狀況。預期為 {1} 例外狀況。{0} - - + Threw exception {2}, but exception {1} was expected. {0} @@ -301,50 +255,42 @@ Stack Trace: {4} 擲回例外狀況 {2},但需要的是例外狀況 {1}。{0} 例外狀況訊息: {3} 堆疊追蹤: {4} - - + No test data source specified. Atleast one TestDataSource is required with DataTestMethodAttribute. 未指定任何測試資料來源。必須至少有一個具備 DataTestMethodAttribute 的 TestDataSource。 - - + {0} ({1}) {0} ({1}) - - + async TestMethod with UITestMethodAttribute are not supported. Either remove async or use TestMethodAttribute. 不支援有 UITestMethodAttribute 的 async TestMethod。請移除 async 或使用 TestMethodAttribute。 - - + Property or method {0} on {1} does not return IEnumerable<object[]>. {1} 上的屬性或方法 {0} 並未傳回 IEnumerable<object[]>。 - - + Value returned by property or method {0} shouldn't be null. 屬性或方法 {0} 傳回的值不可為 null。 - - + Method {0} must match the expected signature: public static {1} {0}({2}). 方法 {0} 必須與正確的簽章相符: public static {1} {0}({2})。 - - + Property or method {0} on {1} returns empty IEnumerable<object[]>. {1} 上的屬性或方法 {0} 傳回空的 IEnumerable<object[]>。 - - + diff --git a/src/TestFramework/MSTest.Core/packages.config b/src/TestFramework/MSTest.Core/packages.config deleted file mode 100644 index 56e01ebc8..000000000 --- a/src/TestFramework/MSTest.Core/packages.config +++ /dev/null @@ -1,5 +0,0 @@ - - - - - \ No newline at end of file diff --git a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/App.config b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/App.config index 046966f13..9c2194177 100644 --- a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/App.config +++ b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/App.config @@ -1,18 +1,18 @@ - + - - + + - - + + - + \ No newline at end of file diff --git a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/DesktopTestSourceHostTests.cs b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/DesktopTestSourceHostTests.cs index 88975f66a..b2b3a5f22 100644 --- a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/DesktopTestSourceHostTests.cs +++ b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/DesktopTestSourceHostTests.cs @@ -22,18 +22,6 @@ namespace PlatformServices.Desktop.ComponentTests public class DesktopTestSourceHostTests { private TestSourceHost testSourceHost; - private string testSource; - - public DesktopTestSourceHostTests() - { - var currentAssemblyPath = Path.GetDirectoryName(typeof(DesktopTestSourceHostTests).Assembly.Location); - var testAssetPath = - Path.Combine( - Directory.GetParent(Directory.GetParent(Directory.GetParent(currentAssemblyPath).FullName).FullName).FullName, - "artifacts", - "TestAssets"); - this.testSource = Path.Combine(testAssetPath, "DesktopTestProjectx86Debug.dll"); - } [TestMethod] public void ParentDomainShouldHonourSearchDirectoriesSpecifiedInRunsettings() @@ -52,7 +40,8 @@ public void ParentDomainShouldHonourSearchDirectoriesSpecifiedInRunsettings() "; - this.testSourceHost = new TestSourceHost(this.testSource, this.GetMockedIRunSettings(runSettingxml).Object, null); + var testSource = GetTestAssemblyPath("DesktopTestProjectx86Debug.dll"); + this.testSourceHost = new TestSourceHost(testSource, this.GetMockedIRunSettings(runSettingxml).Object, null); this.testSourceHost.SetupHost(); // Loading TestProjectForAssemblyResolution.dll should not throw. @@ -77,19 +66,24 @@ public void ChildDomainResolutionPathsShouldHaveSearchDirectoriesSpecifiedInRuns "; - this.testSourceHost = new TestSourceHost(this.testSource, this.GetMockedIRunSettings(runSettingxml).Object, null); - + var testSource = GetTestAssemblyPath("DesktopTestProjectx86Debug.dll"); + this.testSourceHost = new TestSourceHost(testSource, this.GetMockedIRunSettings(runSettingxml).Object, null); this.testSourceHost.SetupHost(); + var assemblyResolution = "ComponentTests\\TestProjectForAssemblyResolution.dll"; + var asm = Assembly.LoadFrom(assemblyResolution); + var type = asm.GetType("PlatformServices.Desktop.ComponentTests.TestProjectForAssemblyResolution"); + // Creating instance of TestProjectForAssemblyResolution should not throw. // It is present in specified in runsettings - AppDomainUtilities.CreateInstance(this.testSourceHost.AppDomain, typeof(TestProjectForAssemblyResolution), null); + AppDomainUtilities.CreateInstance(this.testSourceHost.AppDomain, type, null); } [TestMethod] public void DisposeShouldUnloadChildAppDomain() { - this.testSourceHost = new TestSourceHost(this.testSource, null, null); + var testSource = GetTestAssemblyPath("DesktopTestProjectx86Debug.dll"); + this.testSourceHost = new TestSourceHost(testSource, null, null); this.testSourceHost.SetupHost(); // Check that child appdomain was indeed created @@ -100,6 +94,14 @@ public void DisposeShouldUnloadChildAppDomain() Assert.IsNull(this.testSourceHost.AppDomain); } + private static string GetTestAssemblyPath(string assemblyName) + { + var currentAssemblyPath = Path.GetDirectoryName(typeof(DesktopTestSourceHostTests).Assembly.Location); + var testAssetPath = Path.Combine(Directory.GetParent(Directory.GetParent(Directory.GetParent(currentAssemblyPath).FullName).FullName).FullName, "artifacts", "TestAssets"); + + return Path.Combine(testAssetPath, assemblyName); + } + private Mock GetMockedIRunSettings(string runSettingxml) { var mockRunSettings = new Mock(); diff --git a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/PlatformServices.Desktop.Component.Tests.csproj b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/PlatformServices.Desktop.Component.Tests.csproj index 05dbabd7e..e668199da 100644 --- a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/PlatformServices.Desktop.Component.Tests.csproj +++ b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/PlatformServices.Desktop.Component.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + Debug AnyCPU @@ -15,8 +13,8 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest @@ -37,85 +35,54 @@ prompt 4 + - - ..\..\..\packages\Castle.Core.4.2.1\lib\net45\Castle.Core.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Moq.4.8.2\lib\net45\Moq.dll - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - + + + FrameworkV1 - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - - - ..\..\..\packages\System.Threading.Tasks.Extensions.4.3.0\lib\portable-net45+win8+wp8+wpa81\System.Threading.Tasks.Extensions.dll - - - ..\..\..\packages\System.ValueTuple.4.4.0\lib\netstandard1.0\System.ValueTuple.dll - - - - - - - - - - - Designer - - - - - + + {b0fce474-14bc-449a-91ea-a433342c0d63} PlatformServices.Desktop - + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} PlatformServices.Interface - - {7252d9e3-267d-442c-96bc-c73aef3241d6} + + {7252D9E3-267D-442C-96BC-C73AEF3241D6} MSTest.Core FrameworkV2 - + {5c411bbf-fcc9-4430-ae08-07666d39fd04} SampleFrameworkExtensions - - {0b057b99-dcdd-417a-bc19-3e63ddd86f24} - TestProjectForAssemblyResolution - + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + + + + + + + + + Designer + + + - - + \ No newline at end of file diff --git a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/packages.config b/test/ComponentTests/PlatformServices.Desktop.Component.Tests/packages.config deleted file mode 100644 index e77883501..000000000 --- a/test/ComponentTests/PlatformServices.Desktop.Component.Tests/packages.config +++ /dev/null @@ -1,12 +0,0 @@ - - - - - - - - - - - - \ No newline at end of file diff --git a/test/ComponentTests/TestAssets/Directory.Build.targets b/test/ComponentTests/TestAssets/Directory.Build.targets index 5a5c0f5db..87043c6ab 100644 --- a/test/ComponentTests/TestAssets/Directory.Build.targets +++ b/test/ComponentTests/TestAssets/Directory.Build.targets @@ -9,4 +9,4 @@ - \ No newline at end of file + diff --git a/test/ComponentTests/TestAssets/SampleFrameworkExtensions/SampleFrameworkExtensions.csproj b/test/ComponentTests/TestAssets/SampleFrameworkExtensions/SampleFrameworkExtensions.csproj index 8a2e84eb2..ac9fece4d 100644 --- a/test/ComponentTests/TestAssets/SampleFrameworkExtensions/SampleFrameworkExtensions.csproj +++ b/test/ComponentTests/TestAssets/SampleFrameworkExtensions/SampleFrameworkExtensions.csproj @@ -1,8 +1,8 @@  + - ..\..\..\..\ Debug AnyCPU {5C411BBF-FCC9-4430-AE08-07666D39FD04} @@ -30,15 +30,7 @@ prompt 4 - - true - - - true - - - $(TestFxRoot)scripts\build\key.snk - + @@ -48,25 +40,17 @@ + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + + - - - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - - + - \ No newline at end of file diff --git a/test/ComponentTests/TestAssets/TestProject/TestProjectForDiscovery.csproj b/test/ComponentTests/TestAssets/TestProject/TestProjectForDiscovery.csproj index 83331431d..19c19dc58 100644 --- a/test/ComponentTests/TestAssets/TestProject/TestProjectForDiscovery.csproj +++ b/test/ComponentTests/TestAssets/TestProject/TestProjectForDiscovery.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,68 +13,52 @@ v4.5 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ False UnitTest - - true - full - false - DEBUG;TRACE - prompt - 4 - - + + pdbonly - true TRACE + true prompt - 4 + x64 + MinimumRecommendedRules.ruleset - + + + full true DEBUG;TRACE - full - x64 - prompt - MinimumRecommendedRules.ruleset - - - TRACE - true - pdbonly - x64 + false prompt + 4 + x64 MinimumRecommendedRules.ruleset + - - - - - - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core - + {5c411bbf-fcc9-4430-ae08-07666d39fd04} SampleFrameworkExtensions + + + + + + - \ No newline at end of file diff --git a/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/TestProjectForAssemblyResolution.csproj b/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/TestProjectForAssemblyResolution.csproj index 2cef98132..d3bc12ddb 100644 --- a/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/TestProjectForAssemblyResolution.csproj +++ b/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/TestProjectForAssemblyResolution.csproj @@ -1,21 +1,15 @@ - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\ComponentTests - true - $(TestFxRoot)scripts\build\key.snk - true + $(RepoRoot)artifacts\TestAssets\ComponentTests + $(RepoRoot)scripts\build\key.snk - - - + + + diff --git a/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/UnitTest1.cs b/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/UnitTest1.cs index 205eca744..6741422a2 100644 --- a/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/UnitTest1.cs +++ b/test/ComponentTests/TestAssets/TestProjectForAssemblyResolution/UnitTest1.cs @@ -5,7 +5,7 @@ namespace PlatformServices.Desktop.ComponentTests { [TestClass] [Serializable] - public class TestProjectForAssemblyResolution + public class TestProjectForAssemblyResolution : MarshalByRefObject { [TestMethod] public void TestMethod1() diff --git a/test/E2ETests/Automation.CLI/Automation.CLI.csproj b/test/E2ETests/Automation.CLI/Automation.CLI.csproj index 64ef23565..ea7449cee 100644 --- a/test/E2ETests/Automation.CLI/Automation.CLI.csproj +++ b/test/E2ETests/Automation.CLI/Automation.CLI.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + Debug AnyCPU @@ -31,48 +29,26 @@ prompt 4 + + + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + - - ..\..\..\packages\Microsoft.TestPlatform.AdapterUtilities.$(TestPlatformVersion)\lib\netstandard2.0\Microsoft.TestPlatform.AdapterUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.TranslationLayer.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CommunicationUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.TranslationLayer.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.TranslationLayer.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.TranslationLayer.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.VsTestConsole.TranslationLayer.dll - - - ..\..\..\packages\Microsoft.TestPlatform.TranslationLayer.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.Common.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Newtonsoft.Json.9.0.1\lib\net45\Newtonsoft.Json.dll - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\netstandard1.3\System.Collections.Immutable.dll - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - - - ..\..\..\packages\System.Runtime.InteropServices.RuntimeInformation.4.3.0\lib\net45\System.Runtime.InteropServices.RuntimeInformation.dll - True - @@ -80,56 +56,69 @@ - - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core + + + - - - - - $(TargetDir)..\ - $(TargetDir)..\..\TestAssets - $(TestFxRoot)\packages - - xcopy /Y /I "$(PackagesPath)\microsoft.testplatform.adapterutilities.$(TestPlatformVersion)\lib\netstandard2.0\Microsoft.TestPlatform.AdapterUtilities.dll" "$(DestinationPath)" - xcopy /Y /I "$(PackagesPath)\microsoft.testplatform.adapterutilities.$(TestPlatformVersion)\lib\netstandard1.0\Microsoft.TestPlatform.AdapterUtilities.dll" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(PackagesPath)\microsoft.testplatform.adapterutilities.$(TestPlatformVersion)\lib\netstandard2.0\Microsoft.TestPlatform.AdapterUtilities.dll" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.dll" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.pdb" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)PlatformServices.Desktop\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)PlatformServices.Desktop\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.pdb" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.dll" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.pdb" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.pdb" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.dll" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.pdb" "$(DestinationPath)\netcoreapp1.1\" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.dll" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.pdb" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.pdb" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.dll" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.NetCore\netstandard1.5\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.pdb" "$(DestinationPath)\netcoreapp2.1\" - xcopy /Y /I "$(SourcePath)PlatformServices.Interface\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.dll" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)PlatformServices.Interface\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.pdb" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)MSTest.Core\Microsoft.VisualStudio.TestPlatform.TestFramework.dll" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)MSTest.Core\Microsoft.VisualStudio.TestPlatform.TestFramework.pdb" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)Extension.Desktop\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.dll" "$(DestinationPath)" - xcopy /Y /I "$(SourcePath)Extension.Desktop\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.pdb" "$(DestinationPath)" - - + + + + + + $(TargetDir)..\ + $(TargetDir)..\..\TestAssets + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test/E2ETests/Automation.CLI/CLITestBase.common.cs b/test/E2ETests/Automation.CLI/CLITestBase.common.cs new file mode 100644 index 000000000..e00555ca8 --- /dev/null +++ b/test/E2ETests/Automation.CLI/CLITestBase.common.cs @@ -0,0 +1,105 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.CLIAutomation +{ + using System; + using System.IO; + using System.Xml; + + using Microsoft.VisualStudio.TestTools.UnitTesting; + + public partial class CLITestBase + { + private const string E2ETestsRelativePath = @"..\..\..\"; + private const string TestAssetsFolder = "TestAssets"; + private const string ArtifactsFolder = "artifacts"; + private const string PackagesFolder = "packages"; + + // This value is automatically updated by "build.ps1" script. + private const string TestPlatformCLIPackage = @"Microsoft.TestPlatform\17.0.0-preview-20210624-09"; + private const string VstestConsoleRelativePath = @"tools\net451\Common7\IDE\Extensions\TestPlatform\vstest.console.exe"; + + /// + /// Gets the relative path of repository root from start-up directory. + /// + /// Relative path of the repository root + protected virtual string GetRelativeRepositoryRootPath() => E2ETestsRelativePath; + + /// + /// Gets the path of test assets folder + /// + /// Path to testassets folder + protected string GetAssetFolderPath() => Path.Combine(Environment.CurrentDirectory, this.GetRelativeRepositoryRootPath(), ArtifactsFolder, TestAssetsFolder); + + /// + /// Gets the full path to a test asset. + /// + /// Name of the asset with extension. E.g. SimpleUnitTest.dll + /// Full path to the test asset. + /// + /// Test assets follow several conventions: + /// (a) They are built for provided build configuration. + /// (b) Name of the test asset matches the parent directory name. E.g. TestAssets\SimpleUnitTest\SimpleUnitTest.xproj must + /// produce TestAssets\SimpleUnitTest\bin\Debug\SimpleUnitTest.dll + /// (c) TestAssets are copied over to a central location i.e. "TestAssets\artifacts\*.*" + /// + protected string GetAssetFullPath(string assetName) + { + var assetPath = Path.Combine(this.GetAssetFolderPath(), assetName); + + Assert.IsTrue(File.Exists(assetPath), "GetTestAsset: Path not found: {0}.", assetPath); + + return assetPath; + } + + protected string GetTestAdapterPath() + { + var testAdapterPath = Path.Combine( + Environment.CurrentDirectory, + this.GetRelativeRepositoryRootPath(), + ArtifactsFolder, + TestAssetsFolder); + + return testAdapterPath; + } + + /// + /// Gets the RunSettingXml having testadapterpath filled in specified by arguement. + /// Inserts testAdapterPath in existing runSetting if not present already, + /// or generates new runSettings with testAdapterPath if runSettings is Empty. + /// + /// RunSettings provided for discovery/execution + /// Full path to TestAdapter. + /// RunSettingXml as string + protected string GetRunSettingXml(string settingsXml, string testAdapterPath) + { + if (string.IsNullOrEmpty(settingsXml)) + { + settingsXml = XmlRunSettingsUtilities.CreateDefaultRunSettings(); + } + + XmlDocument doc = new XmlDocument(); + using (var xmlReader = XmlReader.Create(new StringReader(settingsXml), new XmlReaderSettings() { XmlResolver = null, CloseInput = true })) + { + doc.Load(xmlReader); + } + + XmlElement root = doc.DocumentElement; + RunConfiguration runConfiguration = new RunConfiguration(testAdapterPath); + XmlElement runConfigElement = runConfiguration.ToXml(); + if (root[runConfiguration.SettingsName] == null) + { + XmlNode newNode = doc.ImportNode(runConfigElement, true); + root.AppendChild(newNode); + } + else + { + XmlNode newNode = doc.ImportNode(runConfigElement.FirstChild, true); + root[runConfiguration.SettingsName].AppendChild(newNode); + } + + return doc.OuterXml; + } + } +} diff --git a/test/E2ETests/Automation.CLI/CLITestBase.cs b/test/E2ETests/Automation.CLI/CLITestBase.e2e.cs similarity index 76% rename from test/E2ETests/Automation.CLI/CLITestBase.cs rename to test/E2ETests/Automation.CLI/CLITestBase.e2e.cs index 9c6f5b85e..3665779e2 100644 --- a/test/E2ETests/Automation.CLI/CLITestBase.cs +++ b/test/E2ETests/Automation.CLI/CLITestBase.e2e.cs @@ -12,17 +12,8 @@ namespace Microsoft.MSTestV2.CLIAutomation using Microsoft.VisualStudio.TestPlatform.ObjectModel.Client; using Microsoft.VisualStudio.TestTools.UnitTesting; - public class CLITestBase + public partial class CLITestBase { - private const string E2ETestsRelativePath = @"..\..\..\"; - private const string TestAssetsFolder = "TestAssets"; - private const string ArtifactsFolder = "artifacts"; - private const string PackagesFolder = "packages"; - - // This value is automatically updated by "build.ps1" script. - private const string TestPlatformCLIPackage = @"Microsoft.TestPlatform.16.9.1"; - private const string VstestConsoleRelativePath = @"tools\net451\Common7\IDE\Extensions\TestPlatform\vstest.console.exe"; - private static VsTestConsoleWrapper vsTestConsoleWrapper; private DiscoveryEventsHandler discoveryEventsHandler; private RunEventsHandler runEventsHandler; @@ -90,7 +81,7 @@ public void InvokeVsTestForExecution(string[] sources, string runSettings = "", /// Full path to vstest.console.exe public string GetConsoleRunnerPath() { - var packagesFolder = Path.Combine(Environment.CurrentDirectory, E2ETestsRelativePath, PackagesFolder); + var packagesFolder = Path.Combine(Environment.CurrentDirectory, this.GetRelativeRepositoryRootPath(), PackagesFolder); var vstestConsolePath = Path.Combine(packagesFolder, TestPlatformCLIPackage, VstestConsoleRelativePath); Assert.IsTrue(File.Exists(vstestConsolePath), "GetConsoleRunnerPath: Path not found: {0}", vstestConsolePath); @@ -227,7 +218,7 @@ public void ValidateFailedTestsContain(string source, bool validateStackTraceInf { if (string.IsNullOrWhiteSpace(testFound.ErrorStackTrace)) { - Assert.Fail($@"The test failure {testFound.DisplayName ?? testFound.TestCase.FullyQualifiedName} with message {testFound.ErrorMessage} lacks stacktrace."); + Assert.Fail($"The test failure {testFound.DisplayName ?? testFound.TestCase.FullyQualifiedName} with message {testFound.ErrorMessage} lacks stacktrace."); } // Verify stack information as well. @@ -258,81 +249,6 @@ public void ValidateTestRunTime(int thresholdTime) $"Test Run was expected to not exceed {thresholdTime} but it took {this.runEventsHandler.ElapsedTimeInRunningTests}"); } - /// - /// Gets the full path to a test asset. - /// - /// Name of the asset with extension. E.g. SimpleUnitTest.dll - /// Full path to the test asset. - /// - /// Test assets follow several conventions: - /// (a) They are built for provided build configuration. - /// (b) Name of the test asset matches the parent directory name. E.g. TestAssets\SimpleUnitTest\SimpleUnitTest.xproj must - /// produce TestAssets\SimpleUnitTest\bin\Debug\SimpleUnitTest.dll - /// (c) TestAssets are copied over to a central location i.e. "TestAssets\artifacts\*.*" - /// - protected string GetAssetFullPath(string assetName) - { - var assetPath = Path.Combine( - Environment.CurrentDirectory, - E2ETestsRelativePath, - ArtifactsFolder, - TestAssetsFolder, - assetName); - - Assert.IsTrue(File.Exists(assetPath), "GetTestAsset: Path not found: {0}.", assetPath); - - return assetPath; - } - - protected string GetTestAdapterPath() - { - var testAdapterPath = Path.Combine( - Environment.CurrentDirectory, - E2ETestsRelativePath, - ArtifactsFolder, - TestAssetsFolder); - - return testAdapterPath; - } - - /// - /// Gets the RunSettingXml having testadapterpath filled in specified by arguement. - /// Inserts testAdapterPath in existing runSetting if not present already, - /// or generates new runSettings with testAdapterPath if runSettings is Empty. - /// - /// RunSettings provided for discovery/execution - /// Full path to TestAdapter. - /// RunSettingXml as string - protected string GetRunSettingXml(string settingsXml, string testAdapterPath) - { - if (string.IsNullOrEmpty(settingsXml)) - { - settingsXml = XmlRunSettingsUtilities.CreateDefaultRunSettings(); - } - - XmlDocument doc = new XmlDocument(); - using (var xmlReader = XmlReader.Create(new StringReader(settingsXml), new XmlReaderSettings() { XmlResolver = null, CloseInput = true })) - { - doc.Load(xmlReader); - } - - XmlElement root = doc.DocumentElement; - RunConfiguration runConfiguration = new RunConfiguration(testAdapterPath); - XmlElement runConfigElement = runConfiguration.ToXml(); - if (root[runConfiguration.SettingsName] == null) - { - XmlNode newNode = doc.ImportNode(runConfigElement, true); - root.AppendChild(newNode); - } - else - { - XmlNode newNode = doc.ImportNode(runConfigElement.FirstChild, true); - root[runConfiguration.SettingsName].AppendChild(newNode); - } - - return doc.OuterXml; - } - /// /// Gets the test method name from full name. /// @@ -343,7 +259,7 @@ private static string GetTestMethodName(string testFullName) string testMethodName = string.Empty; var splits = testFullName.Split('.'); - if (splits.Count() >= 3) + if (splits.Length >= 3) { testMethodName = splits[2]; } diff --git a/test/E2ETests/Automation.CLI/RunConfiguration.cs b/test/E2ETests/Automation.CLI/RunConfiguration.cs index 828d30eaf..485566ce7 100644 --- a/test/E2ETests/Automation.CLI/RunConfiguration.cs +++ b/test/E2ETests/Automation.CLI/RunConfiguration.cs @@ -16,11 +16,11 @@ public class RunConfiguration public string SettingsName { get; set; } /// - /// Gets or sets paths at which engine should look for test adapters + /// Gets the paths at which engine should look for test adapters /// - public string TestAdaptersPaths { get; set; } + public string[] TestAdaptersPaths { get; } - public RunConfiguration(string testAdapterPaths) + public RunConfiguration(params string[] testAdapterPaths) { this.SettingsName = Constants.RunConfigurationSettingsName; this.TestAdaptersPaths = testAdapterPaths; @@ -35,9 +35,13 @@ public XmlElement ToXml() XmlDocument doc = new XmlDocument(); XmlElement root = doc.CreateElement(this.SettingsName); - var testAdaptersPaths = doc.CreateElement("TestAdaptersPaths"); - testAdaptersPaths.InnerXml = this.TestAdaptersPaths; - root.AppendChild(testAdaptersPaths); + foreach (var p in this.TestAdaptersPaths) + { + var testAdaptersPaths = doc.CreateElement("TestAdaptersPaths"); + testAdaptersPaths.InnerText = p; + + root.AppendChild(testAdaptersPaths); + } return root; } diff --git a/test/E2ETests/Automation.CLI/packages.config b/test/E2ETests/Automation.CLI/packages.config deleted file mode 100644 index cfe2887a1..000000000 --- a/test/E2ETests/Automation.CLI/packages.config +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/test/E2ETests/DiscoveryAndExecutionTests/DataRowTests.cs b/test/E2ETests/DiscoveryAndExecutionTests/DataRowTests.cs new file mode 100644 index 000000000..5ab7b8b94 --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/DataRowTests.cs @@ -0,0 +1,184 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System.IO; + + + [TestClass] + public class DataRowTests : CLITestBase + { + private const string TestAssembly = "DataRowTestProject.dll"; + + [TestMethod] + public void ExecuteOnlyDerivedClassDataRowsWhenBothBaseAndDerviedClassHasDataRows_SimpleDataRows() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "TestCategory~DataRowSimple"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMethod (BaseString1)", + "DataRowTestMethod (BaseString2)", + "DataRowTestMethod (BaseString3)", + "DataRowTestMethod (DerivedString1)", + "DataRowTestMethod (DerivedString2)" + ); + } + + [TestMethod] + public void ExecuteOnlyDerivedClassDataRowsWhenItOverridesBaseClassDataRows_SimpleDataRows() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DerivedClass&TestCategory~DataRowSimple"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMethod (DerivedString1)", + "DataRowTestMethod (DerivedString2)" + ); + } + + [TestMethod] + public void DataRowsExecuteWithRequiredAndOptionalParameters() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "TestCategory~DataRowSomeOptional"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMethodWithSomeOptionalParameters (123)", + "DataRowTestMethodWithSomeOptionalParameters (123,DerivedOptionalString1)", + "DataRowTestMethodWithSomeOptionalParameters (123,DerivedOptionalString2,DerivedOptionalString3)" + ); + } + + [TestMethod] + public void DataRowsExecuteWithParamsArrayParameter() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "TestCategory~DataRowParamsArgument"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMethodWithParamsParameters (2)", + "DataRowTestMethodWithParamsParameters (2,DerivedSingleParamsArg)", + "DataRowTestMethodWithParamsParameters (2,DerivedParamsArg1,DerivedParamsArg2)", + "DataRowTestMethodWithParamsParameters (2,DerivedParamsArg1,DerivedParamsArg2,DerivedParamsArg3)" + ); + } + + [TestMethod] + public void DataRowsFailWhenInvalidArgumentsProvided() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "TestCategory~DataRowOptionalInvalidArguments"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMethodFailsWithInvalidArguments ()", + "DataRowTestMethodFailsWithInvalidArguments (2)", + "DataRowTestMethodFailsWithInvalidArguments (2,DerivedRequiredArgument,DerivedOptionalArgument,DerivedExtraArgument)" + ); + } + + [TestMethod] + public void DataRowsShouldSerializeDoublesProperly() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowTestDouble"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestDouble (10.01,20.01)", + "DataRowTestDouble (10.02,20.02)" + ); + } + + [TestMethod] + public void DataRowsShouldSerializeMixedTypesProperly() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowTestMixed"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowTestMixed (10,10,10,10,10,10,10,10)" + ); + } + + [TestMethod] + public void DataRowsShouldSerializeEnumsProperly() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowEnums"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowEnums ()", + "DataRowEnums (Alfa)", + "DataRowEnums (Beta)", + "DataRowEnums (Gamma)" + ); + } + + [TestMethod] + public void DataRowsShouldHandleNonSerializableValues() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowNonSerializable"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsDiscovered(testCases, + "DataRowNonSerializable" + ); + + Assert.That.TestsPassed(testResults, + "DataRowNonSerializable (System.String)", + "DataRowNonSerializable (System.Int32)", + "DataRowNonSerializable (DataRowTestProject.DerivedClass)" + ); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/DataSourceTests.cs b/test/E2ETests/DiscoveryAndExecutionTests/DataSourceTests.cs new file mode 100644 index 000000000..5d8e4b11c --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/DataSourceTests.cs @@ -0,0 +1,40 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System.IO; + using System.Linq; + + [TestClass] + public class DataSourceTests : CLITestBase + { + private const string TestAssembly = "DataSourceTestProject.dll"; + + [TestMethod] + public void ExecuteCsvTestDataSourceTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "CsvTestMethod"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, + "CsvTestMethod (Data Row 0)", + "CsvTestMethod (Data Row 2)" + ); + + Assert.That.ContainsTestsFailed(testResults, + "CsvTestMethod (Data Row 1)", + "CsvTestMethod (Data Row 3)" + ); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/DiscoveryAndExecutionTests.csproj b/test/E2ETests/DiscoveryAndExecutionTests/DiscoveryAndExecutionTests.csproj new file mode 100644 index 000000000..840b0a920 --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/DiscoveryAndExecutionTests.csproj @@ -0,0 +1,49 @@ + + + net452 + v4.5.2 + false + + false + 1685 + true + false + + + + + + + + + + + + + + + + $(ArtifactsBinDir)MSTest.CoreAdapter\Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.dll + + + + $(ArtifactsBinDir)MSTest.CoreAdapter\System.Collections.Concurrent.dll + + + + $(ArtifactsBinDir)PlatformServices.Desktop\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll + + + + $(ArtifactsBinDir)PlatformServices.Interface\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.Interface.dll + + + + $(ArtifactsBinDir)MSTest.Core\Microsoft.VisualStudio.TestPlatform.TestFramework.dll + + + + $(ArtifactsBinDir)Extension.Desktop\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.dll + + + \ No newline at end of file diff --git a/test/E2ETests/DiscoveryAndExecutionTests/Extensions/AssertionExtensions.cs b/test/E2ETests/DiscoveryAndExecutionTests/Extensions/AssertionExtensions.cs new file mode 100644 index 000000000..c8855fd2c --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/Extensions/AssertionExtensions.cs @@ -0,0 +1,151 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter; + using Microsoft.VisualStudio.TestPlatform.ObjectModel; + + using System.Collections.Generic; + using System.Linq; + + using Assert = Microsoft.VisualStudio.TestTools.UnitTesting.Assert; + + public static class AssertionExtensions + { + public static void ContainsTestsDiscovered(this Assert _, IEnumerable actualTests, IEnumerable expectedTests) + => ContainsTestsDiscovered(actualTests, expectedTests); + + public static void PassedTestCount(this Assert _, IEnumerable actual, int expectedCount) + => AssertOutcomeCount(actual, TestOutcome.Passed, expectedCount); + + public static void FailedTestCount(this Assert _, IEnumerable actual, int expectedCount) + => AssertOutcomeCount(actual, TestOutcome.Failed, expectedCount); + + public static void TestsDiscovered(this Assert _, IEnumerable actualTests, IEnumerable expectedTests) + => ContainsTestsDiscovered(actualTests, expectedTests, true); + + public static void TestsDiscovered(this Assert _, IEnumerable actualTests, params string[] expectedTests) + => ContainsTestsDiscovered(actualTests, expectedTests, true); + + public static void TestsPassed(this Assert _, IEnumerable actual, IEnumerable testCases, IEnumerable expectedTests, MSTestSettings settings = null) + => ContainsExpectedTestsWithOutcome(actual, testCases, TestOutcome.Passed, expectedTests, true, settings); + + public static void TestsPassed(this Assert _, IEnumerable actual, params string[] expectedTests) + => ContainsExpectedTestsWithOutcome(actual, TestOutcome.Passed, expectedTests, true); + + public static void TestsFailed(this Assert _, IEnumerable actual, IEnumerable testCases, IEnumerable expectedTests, MSTestSettings settings = null) + => ContainsExpectedTestsWithOutcome(actual, testCases, TestOutcome.Failed, expectedTests, true, settings); + + public static void TestsFailed(this Assert _, IEnumerable actual, params string[] expectedTests) + => ContainsExpectedTestsWithOutcome(actual, TestOutcome.Failed, expectedTests, true); + + public static void ContainsTestsPassed(this Assert _, IEnumerable actual, IEnumerable testCases, IEnumerable expectedTests, MSTestSettings settings = null) + => ContainsExpectedTestsWithOutcome(actual, testCases, TestOutcome.Passed, expectedTests, false, settings); + + public static void ContainsTestsPassed(this Assert _, IEnumerable actual, params string[] expectedTests) + => ContainsExpectedTestsWithOutcome(actual, TestOutcome.Passed, expectedTests); + + public static void ContainsTestsFailed(this Assert _, IEnumerable actual, IEnumerable testCases, IEnumerable expectedTests, MSTestSettings settings = null) + => ContainsExpectedTestsWithOutcome(actual, testCases, TestOutcome.Failed, expectedTests, false, settings); + + public static void ContainsTestsFailed(this Assert _, IEnumerable actual, params string[] expectedTests) + => ContainsExpectedTestsWithOutcome(actual, TestOutcome.Failed, expectedTests); + + private static void ContainsTestsDiscovered(IEnumerable discoveredTests, IEnumerable expectedTests, bool matchCount = false) + { + if (matchCount) + { + var expectedCount = discoveredTests.Count(); + var outcomedCount = expectedTests.Count(); + + AssertDiscoveryCount(outcomedCount, expectedCount); + } + + foreach (var test in expectedTests) + { + var testFound = discoveredTests.Any( + p => test.Equals(p.FullyQualifiedName) + || test.Equals(p.DisplayName) + || test.Equals(p.DisplayName)); + + Assert.IsTrue(testFound, + $"Test Discovery run was expecting to discover \"{test}\", but it has not discovered."); + } + } + + private static void ContainsExpectedTestsWithOutcome(IEnumerable outcomedTests, IEnumerable testCases, TestOutcome expectedOutcome, IEnumerable expectedTests, bool matchCount = false, MSTestSettings settings = null) + { + if (matchCount) + { + var expectedCount = expectedTests.Count(); + AssertOutcomeCount(outcomedTests, expectedOutcome, expectedCount); + } + + foreach (var test in expectedTests) + { + var testFound = outcomedTests.Any( + p => test.Equals(p.TestCase?.FullyQualifiedName) + || test.Equals(p.DisplayName) + || test.Equals(p.TestCase.DisplayName)); + + Assert.IsTrue(testFound, GetOutcomeAssertString(test, expectedOutcome)); + } + } + + private static void ContainsExpectedTestsWithOutcome(IEnumerable outcomedTests, TestOutcome expectedOutcome, string[] expectedTests, bool matchCount = false) + { + if (matchCount) + { + var expectedCount = expectedTests.Count(); + AssertOutcomeCount(outcomedTests, expectedOutcome, expectedCount); + } + + foreach (var test in expectedTests) + { + var testFound = outcomedTests.Any(p => p.DisplayName == test); + + Assert.IsTrue(testFound, GetOutcomeAssertString(test, expectedOutcome)); + } + } + + private static string GetOutcomeAssertString(string testName, TestOutcome outcome) + { + switch (outcome) + { + case TestOutcome.None: + return $"\"{testName}\" does not have TestOutcome.None outcome."; + + case TestOutcome.Passed: + return $"\"{testName}\" does not appear in passed tests list."; + + case TestOutcome.Failed: + return $"\"{testName}\" does not appear in failed tests list."; + + case TestOutcome.Skipped: + return $"\"{testName}\" does not appear in skipped tests list."; + + case TestOutcome.NotFound: + return $"\"{testName}\" does not appear in not found tests list."; + } + + return string.Empty; + } + + private static void AssertOutcomeCount(IEnumerable actual, TestOutcome expectedOutcome, int expectedCount) + { + var outcomedTests = actual.Where(i => i.Outcome == expectedOutcome); + var actualCount = outcomedTests.Count(); + + AssertOutcomeCount(actualCount, expectedCount); + } + private static void AssertOutcomeCount(int actualCount, int expectedCount) + { + Assert.AreEqual(expectedCount, actualCount, $"Test run expected to contain {expectedCount} tests, but ran {actualCount}."); + } + private static void AssertDiscoveryCount(int actualCount, int expectedCount) + { + Assert.AreEqual(expectedCount, actualCount, $"Test discovery expected to contain {expectedCount} tests, but ran {actualCount}."); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/FSharpTestProjectTests.cs b/test/E2ETests/DiscoveryAndExecutionTests/FSharpTestProjectTests.cs new file mode 100644 index 000000000..eaf65dbb5 --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/FSharpTestProjectTests.cs @@ -0,0 +1,33 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System.IO; + + [TestClass] + public class FSharpTestProjectTests : CLITestBase + { + private const string TestAssembly = "FSharpTestProject.dll"; + + [TestMethod] + public void ExecuteCsvTestDataSourceTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, "Test method passing with a . in it"); + Assert.That.PassedTestCount(testResults, 1); + Assert.That.FailedTestCount(testResults, 0); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceExtensibilityTests.cs b/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceExtensibilityTests.cs new file mode 100644 index 000000000..cb7896903 --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceExtensibilityTests.cs @@ -0,0 +1,108 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System.IO; + using System.Linq; + + [TestClass] + public class TestDataSourceExtensibilityTests : CLITestBase + { + private const string TestAssembly = "FxExtensibilityTestProject.dll"; + + /* + Add tests for: + - Ignored tests are discovered during discovery + - Ignored tests are not expanded (DataRow, DataSource, etc) + */ + + [TestMethod] + public void CustomTestDataSourceTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "CustomTestDataSourceTestMethod1"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, "CustomTestDataSourceTestMethod1 (1,2,3)", "CustomTestDataSourceTestMethod1 (4,5,6)"); + } + + [TestMethod] + public void AssertExtensibilityTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FxExtensibilityTestProject.AssertExTest"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, "BasicAssertExtensionTest", "ChainedAssertExtensionTest"); + Assert.That.ContainsTestsFailed(testResults, "BasicFailingAssertExtensionTest", "ChainedFailingAssertExtensionTest"); + } + + [TestMethod] + public void ExecuteCustomTestExtensibilityTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "(Name~CustomTestMethod1)|(Name~CustomTestClass1)"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, + "CustomTestMethod1 - Execution number 1", + "CustomTestMethod1 - Execution number 2", + "CustomTestMethod1 - Execution number 4", + "CustomTestMethod1 - Execution number 5", + "CustomTestClass1 - Execution number 1", + "CustomTestClass1 - Execution number 2", + "CustomTestClass1 - Execution number 4", + "CustomTestClass1 - Execution number 5" + ); + + Assert.That.ContainsTestsFailed(testResults, + "CustomTestMethod1 - Execution number 3", + "CustomTestClass1 - Execution number 3" + ); + } + + [TestMethod] + public void ExecuteCustomTestExtensibilityWithTestDataTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "Name~CustomTestMethod2"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "CustomTestMethod2 (B)", + "CustomTestMethod2 (B)", + "CustomTestMethod2 (B)" + ); + + Assert.That.TestsFailed(testResults, + "CustomTestMethod2 (A)", + "CustomTestMethod2 (A)", + "CustomTestMethod2 (A)", + "CustomTestMethod2 (C)", + "CustomTestMethod2 (C)", + "CustomTestMethod2 (C)" + ); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceTests.cs b/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceTests.cs new file mode 100644 index 000000000..69f334105 --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/TestDataSourceTests.cs @@ -0,0 +1,189 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.MSTestV2.Smoke.DiscoveryAndExecutionTests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System.IO; + using System.Linq; + + [TestClass] + public class TestDataSourceTests : CLITestBase + { + private const string TestAssembly = "DataSourceTestProject.dll"; + + [TestMethod] + public void ExecuteCsvTestDataSourceTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "CsvTestMethod"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, + "CsvTestMethod (Data Row 0)", + "CsvTestMethod (Data Row 2)" + ); + + Assert.That.ContainsTestsFailed(testResults, + "CsvTestMethod (Data Row 1)", + "CsvTestMethod (Data Row 3)" + ); + } + + [TestMethod] + public void ExecuteDynamicDataTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "DynamicDataTest"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.ContainsTestsPassed(testResults, + "DynamicDataTest (John;Doe,DataSourceTestProject.ITestDataSourceTests.User)" + ); + + Assert.That.FailedTestCount(testResults, 0); + } + + [TestMethod] + public void ExecuteDataRowTests_Enums() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowTests_Enums"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowEnums_SByte (Alfa)", + "DataRowEnums_SByte (Beta)", + "DataRowEnums_SByte (Gamma)", + "DataRowEnums_Byte (Alfa)", + "DataRowEnums_Byte (Beta)", + "DataRowEnums_Byte (Gamma)", + "DataRowEnums_Short (Alfa)", + "DataRowEnums_Short (Beta)", + "DataRowEnums_Short (Gamma)", + "DataRowEnums_UShort (Alfa)", + "DataRowEnums_UShort (Beta)", + "DataRowEnums_UShort (Gamma)", + "DataRowEnums_Int (Alfa)", + "DataRowEnums_Int (Beta)", + "DataRowEnums_Int (Gamma)", + "DataRowEnums_UInt (Alfa)", + "DataRowEnums_UInt (Beta)", + "DataRowEnums_UInt (Gamma)", + "DataRowEnum_Long (Alfa)", + "DataRowEnum_Long (Beta)", + "DataRowEnum_Long (Gamma)", + "DataRowEnum_ULong (Alfa)", + "DataRowEnum_ULong (Beta)", + "DataRowEnum_ULong (Gamma)", + + "DataRowEnums_Nullable_SByte ()", + "DataRowEnums_Nullable_SByte (Alfa)", + "DataRowEnums_Nullable_SByte (Beta)", + "DataRowEnums_Nullable_SByte (Gamma)", + "DataRowEnums_Nullable_Byte ()", + "DataRowEnums_Nullable_Byte (Alfa)", + "DataRowEnums_Nullable_Byte (Beta)", + "DataRowEnums_Nullable_Byte (Gamma)", + "DataRowEnums_Nullable_Short ()", + "DataRowEnums_Nullable_Short (Alfa)", + "DataRowEnums_Nullable_Short (Beta)", + "DataRowEnums_Nullable_Short (Gamma)", + "DataRowEnums_Nullable_UShort ()", + "DataRowEnums_Nullable_UShort (Alfa)", + "DataRowEnums_Nullable_UShort (Beta)", + "DataRowEnums_Nullable_UShort (Gamma)", + "DataRowEnums_Nullable_Int ()", + "DataRowEnums_Nullable_Int (Alfa)", + "DataRowEnums_Nullable_Int (Beta)", + "DataRowEnums_Nullable_Int (Gamma)", + "DataRowEnums_Nullable_UInt ()", + "DataRowEnums_Nullable_UInt (Alfa)", + "DataRowEnums_Nullable_UInt (Beta)", + "DataRowEnums_Nullable_UInt (Gamma)", + "DataRowEnums_Nullable_Long ()", + "DataRowEnums_Nullable_Long (Alfa)", + "DataRowEnums_Nullable_Long (Beta)", + "DataRowEnums_Nullable_Long (Gamma)", + "DataRowEnums_Nullable_ULong ()", + "DataRowEnums_Nullable_ULong (Alfa)", + "DataRowEnums_Nullable_ULong (Beta)", + "DataRowEnums_Nullable_ULong (Gamma)", + + "DataRowEnums_MixedTypes_Byte (Alfa,True,1)", + "DataRowEnums_MixedTypes_Byte (Beta,False,2)", + "DataRowEnums_MixedTypes_Byte (Gamma,True,3)" + ); + + Assert.That.FailedTestCount(testResults, 0); + } + + [TestMethod] + public void ExecuteDataRowTests_NonSerializablePaths() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~DataRowTests_NonSerializablePaths"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRowNonSerializable (System.String)", + "DataRowNonSerializable (System.Int32)", + "DataRowNonSerializable (DataSourceTestProject.ITestDataSourceTests.DataRowTests_Enums)"); + Assert.That.FailedTestCount(testResults, 0); + } + + [TestMethod] + public void ExecuteRegular_DataRowTests() + { + // Arrange + var assemblyPath = Path.IsPathRooted(TestAssembly) ? TestAssembly : this.GetAssetFullPath(TestAssembly); + + // Act + var testCases = DiscoverTests(assemblyPath, "FullyQualifiedName~Regular_DataRowTests"); + var testResults = RunTests(assemblyPath, testCases); + + // Assert + Assert.That.TestsPassed(testResults, + "DataRow1 (10)", + "DataRow1 (20)", + "DataRow1 (30)", + "DataRow1 (40)", + "DataRow2 (10,String parameter,True,False)", + "DataRow2 (20,String parameter,True,False)", + "DataRow2 (30,String parameter,True,False)", + "DataRow2 (40,String parameter,True,False)", + "DataRowTestMethodFailsWithInvalidArguments ()", + "DataRowTestMethodFailsWithInvalidArguments (2)", + "DataRowTestMethodFailsWithInvalidArguments (2,DerivedRequiredArgument,DerivedOptionalArgument,DerivedExtraArgument)", + "DataRowTestDouble (10.01,20.01)", + "DataRowTestDouble (10.02,20.02)", + "DataRowTestMixed (1,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (2,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (3,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (4,10,10,10,10,10,10,10,10)", + "NullValueInData (john.doe@example.com,abc123,)", + "NullValueInData (john.doe@example.com,abc123,/unit/test)"); + + Assert.That.FailedTestCount(testResults, 0); + } + } +} diff --git a/test/E2ETests/DiscoveryAndExecutionTests/Utilities/CLITestBase.discovery.cs b/test/E2ETests/DiscoveryAndExecutionTests/Utilities/CLITestBase.discovery.cs new file mode 100644 index 000000000..b14d2ca58 Binary files /dev/null and b/test/E2ETests/DiscoveryAndExecutionTests/Utilities/CLITestBase.discovery.cs differ diff --git a/test/E2ETests/DiscoveryAndExecutionTests/Utilities/TestCaseFilterFactory.cs b/test/E2ETests/DiscoveryAndExecutionTests/Utilities/TestCaseFilterFactory.cs new file mode 100644 index 000000000..c39f7c4df --- /dev/null +++ b/test/E2ETests/DiscoveryAndExecutionTests/Utilities/TestCaseFilterFactory.cs @@ -0,0 +1,362 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DiscoveryAndExecutionTests.Utilities +{ + using Microsoft.VisualStudio.TestPlatform.ObjectModel; + using Microsoft.VisualStudio.TestPlatform.ObjectModel.Adapter; + using Microsoft.VisualStudio.TestPlatform.ObjectModel.Utilities; + + using System; + using System.Collections.Generic; + using System.Linq; + using System.Linq.Expressions; + using System.Reflection; + using System.Text; + using System.Text.RegularExpressions; + + internal static class TestCaseFilterFactory + { + private static readonly MethodInfo CachedGetMultiValueMethod; + private static readonly MethodInfo CachedEqualsComparerMethod; + private static readonly MethodInfo CachedContainsComparerMethod; + + static TestCaseFilterFactory() + { + CachedGetMultiValueMethod = typeof(TestCaseFilterFactory).GetMethod(nameof(GetMultiValue), BindingFlags.Static | BindingFlags.NonPublic); + CachedEqualsComparerMethod = typeof(TestCaseFilterFactory).GetMethod(nameof(EqualsComparer), BindingFlags.Static | BindingFlags.NonPublic); + CachedContainsComparerMethod = typeof(TestCaseFilterFactory).GetMethod(nameof(ContainsComparer), BindingFlags.Static | BindingFlags.NonPublic); + } + + public static ITestCaseFilterExpression ParseTestFilter(string filterString) + { + ValidateArg.NotNullOrEmpty(filterString, nameof(filterString)); + if (Regex.IsMatch(filterString, @"\(\s*\)")) + { + throw new FormatException($"Invalid filter, empty parenthesis: {filterString}"); + } + + var tokens = TokenizeFilter(filterString); + + var ops = new Stack(); + var exp = new Stack, bool>>>(); + + // simplified version of microsoft/vstest/src/Microsoft.TestPlatform.Common/Filtering/FilterExpression.cs + + // This is based on standard parsing of in order expression using two stacks (operand stack and operator stack) + // Precedence(And) > Precedence(Or) + foreach (var t in tokens) + { + var token = t.Trim(); + if (string.IsNullOrEmpty(token)) + { + continue; + } + + switch (token) + { + case "&": + case "|": + var op = token == "&" ? Operator.And : Operator.Or; + var top = ops.Count == 0 ? Operator.None : ops.Peek(); + if (ops.Count == 0 || top == Operator.OpenBrace || top < op) + { + ops.Push(op); + continue; + } + MergeExpression(exp, ops.Pop()); + continue; + + case "(": + ops.Push(Operator.OpenBrace); + continue; + + case ")": + if (ops.Count == 0) + { + throw new FormatException($"Invalid filter, missing parenthesis open: {filterString}"); + } + + while (ops.Peek() != Operator.OpenBrace) + { + MergeExpression(exp, ops.Pop()); + if (ops.Count == 0) + { + throw new FormatException($"Invalid filter, missing parenthesis open: {filterString}"); + } + } + ops.Pop(); + continue; + + default: + var e = ConditionExpresion(token); + exp.Push(e); + break; + } + } + + while (ops.Count != 0) + { + MergeExpression(exp, ops.Pop()); + } + + if (exp.Count != 1) + { + throw new FormatException($"Invalid filter, missing operator: {filterString}"); + } + + var lambda = exp.Pop().Compile(); + + return new TestFilterExpression(filterString, lambda); + } + + private class TestFilterExpression : ITestCaseFilterExpression + { + private readonly string filter; + private readonly Func, bool> expression; + + public TestFilterExpression(string filter, Func, bool> expression) + { + this.filter = filter; + this.expression = expression; + } + + public string TestCaseFilterValue => filter; + + public bool MatchTestCase(TestCase testCase, Func propertyValueProvider) => expression(propertyValueProvider); + } + + private static void MergeExpression(Stack, bool>>> exp, Operator op) + { + ValidateArg.NotNull(exp, nameof(exp)); + if (op != Operator.And && op != Operator.Or) + { + throw new ArgumentException($"Unexpected operator: {op}", nameof(op)); + } + if (exp.Count != 2) + { + throw new ArgumentException($"Unexpected expression tree: {exp.Count} elements, expected 2.", nameof(exp)); + } + + var parameter = Expression.Parameter(typeof(Func), "value"); + var right = Expression.Invoke(exp.Pop(), parameter); + var left = Expression.Invoke(exp.Pop(), parameter); + + Expression body = op == Operator.And ? Expression.And(left, right) : Expression.Or(left, right); + + var lambda = Expression.Lambda, bool>>(body, parameter); + + exp.Push(lambda); + } + + private static IEnumerable TokenizeFilter(string filterString) + { + var token = new StringBuilder(filterString.Length); + + var escaping = false; + for (int i = 0; i < filterString.Length; i++) + { + var c = filterString[i]; + + if (escaping) + { + token.Append(c); + escaping = false; + continue; + } + + switch (c) + { + case FilterHelper.EscapeCharacter: + escaping = true; + continue; + + case '&': + case '|': + case '(': + case ')': + if (token.Length != 0) + { + yield return token.ToString(); + token.Clear(); + } + yield return c.ToString(); + continue; + + default: + token.Append(c); + break; + } + } + + if (token.Length != 0) + { + yield return token.ToString(); + } + } + + private static IEnumerable TokenizeCondition(string conditionString) + { + ValidateArg.NotNullOrEmpty(conditionString, nameof(conditionString)); + var token = new StringBuilder(conditionString.Length); + + var escaped = false; + for (int i = 0; i < conditionString.Length; i++) + { + var c = conditionString[i]; + + if (escaped) + { + token.Append(c); + escaped = false; + continue; + } + + switch (c) + { + case '=': + case '~': + case '!': + if (token.Length > 0) + { + yield return token.ToString(); + token.Clear(); + } + + if (c == '!') + { + var op = conditionString[i + 1]; + + if (op == '~' || op == '=') + { + yield return token.ToString() + conditionString[++i]; + continue; + } + } + + yield return c.ToString(); + continue; + + default: + token.Append(c); + break; + } + } + + if (token.Length > 0) + { + yield return token.ToString(); + } + } + + private static string[] GetMultiValue(object value) + { + if (value is string[] i) + { + return i; + } + else if (value != null) + { + return new[] { value.ToString() }; + } + + return null; + } + + private static bool EqualsComparer(string[] values, string value) + { + if (values == null) return false; + + foreach (var v in values) + { + if (v.Equals(value, StringComparison.OrdinalIgnoreCase)) + { + return true; + } + } + + return false; + } + + private static bool ContainsComparer(string[] values, string value) + { + if (values == null) return false; + + foreach (var v in values) + { + if (v.IndexOf(value, StringComparison.OrdinalIgnoreCase) >= 0) + { + return true; + } + } + + return false; + } + + private static Expression, bool>> ConditionExpresion(string conditionString) + { + ValidateArg.NotNull(conditionString, nameof(conditionString)); + + var condition = TokenizeCondition(conditionString).ToArray(); + + Expression parameterName, expectedValue, parameterValueProvider, expression; + string op; + if (condition.Length == 1) + { + parameterName = Expression.Constant("FullyQualifiedName"); + expectedValue = Expression.Constant(conditionString.Trim()); + op = "~"; + } + else if (condition.Length == 3) + { + parameterName = Expression.Constant(condition[0]); + expectedValue = Expression.Constant(condition[2].Trim()); + op = condition[1]; + } + else + { + throw new FormatException("Invalid ConditionExpresion: " + conditionString); + } + + ParameterExpression parameter = Expression.Parameter(typeof(Func), "p"); + + parameterValueProvider = Expression.Call(CachedGetMultiValueMethod, Expression.Invoke(parameter, parameterName)); + + MethodInfo comparer; + switch (op.Last()) + { + case '=': + comparer = CachedEqualsComparerMethod; + break; + + case '~': + comparer = CachedContainsComparerMethod; + break; + + default: + throw new FormatException($"Invalid operator in {conditionString}: {condition[1]}"); + } + + expression = Expression.Call(comparer, parameterValueProvider, expectedValue); + + if (op[0] == '!') + { + expression = Expression.Not(expression); + } + + + var lambda = Expression.Lambda, bool>>(expression, parameter); + + return lambda; + } + + private enum Operator + { + None, + Or, + And, + OpenBrace, + CloseBrace, + } + } +} diff --git a/test/E2ETests/Smoke.E2E.Tests/CustomTestExecutionExtensibilityTests.cs b/test/E2ETests/Smoke.E2E.Tests/CustomTestExecutionExtensibilityTests.cs index 0358dc983..d057a90ac 100644 --- a/test/E2ETests/Smoke.E2E.Tests/CustomTestExecutionExtensibilityTests.cs +++ b/test/E2ETests/Smoke.E2E.Tests/CustomTestExecutionExtensibilityTests.cs @@ -15,6 +15,7 @@ public class CustomTestExecutionExtensibilityTests : CLITestBase public void ExecuteCustomTestExtensibilityTests() { this.InvokeVsTestForExecution(new string[] { TestAssembly }); + this.ValidatePassedTestsContain( "CustomTestMethod1 - Execution number 1", "CustomTestMethod1 - Execution number 2", @@ -35,13 +36,12 @@ public void ExecuteCustomTestExtensibilityTests() public void ExecuteCustomTestExtensibilityWithTestDataTests() { this.InvokeVsTestForExecution(new string[] { TestAssembly }, testCaseFilter: "FullyQualifiedName~CustomTestExTests.CustomTestMethod2"); + this.ValidatePassedTests( "CustomTestMethod2 (B)", "CustomTestMethod2 (B)", "CustomTestMethod2 (B)"); - - // Parent results should fail and thus failed count should be 7. - this.ValidateFailedTestsCount(7); + this.ValidateFailedTestsCount(6); this.ValidateFailedTestsContain( TestAssembly, true, diff --git a/test/E2ETests/Smoke.E2E.Tests/DataRowTests.cs b/test/E2ETests/Smoke.E2E.Tests/DataRowTests.cs index 280c4aeec..c65799360 100644 --- a/test/E2ETests/Smoke.E2E.Tests/DataRowTests.cs +++ b/test/E2ETests/Smoke.E2E.Tests/DataRowTests.cs @@ -23,10 +23,10 @@ public void ExecuteOnlyDerivedClassDataRowsWhenBothBaseAndDerviedClassHasDataRow "DataRowTestMethod (DerivedString1)", "DataRowTestMethod (DerivedString2)"); - // 4 tests of BaseClass.DataRowTestMethod - 3 data row results and 1 parent result - // 3 tests of DerivedClass.DataRowTestMethod - 2 data row results and 1 parent result - // Total 7 tests - Making sure that DerivedClass doesn't run BaseClass tests - this.ValidatePassedTestsCount(7); + // 3 tests of BaseClass.DataRowTestMethod - 3 data row results and no parent result + // 2 tests of DerivedClass.DataRowTestMethod - 2 data row results and no parent result + // Total 5 tests - Making sure that DerivedClass doesn't run BaseClass tests + this.ValidatePassedTestsCount(5); } [TestMethod] @@ -38,8 +38,8 @@ public void ExecuteOnlyDerivedClassDataRowsWhenItOverridesBaseClassDataRows_Simp "DataRowTestMethod (DerivedString1)", "DataRowTestMethod (DerivedString2)"); - // 3 tests of DerivedClass.DataRowTestMethod - 2 datarow result and 1 parent result - this.ValidatePassedTestsCount(3); + // 2 tests of DerivedClass.DataRowTestMethod - 2 datarow result and no parent result + this.ValidatePassedTestsCount(2); } [TestMethod] @@ -52,8 +52,8 @@ public void DataRowsExecuteWithRequiredAndOptionalParameters() "DataRowTestMethodWithSomeOptionalParameters (123,DerivedOptionalString1)", "DataRowTestMethodWithSomeOptionalParameters (123,DerivedOptionalString2,DerivedOptionalString3)"); - // 4 tests of DerivedClass.DataRowTestMethodWithSomeOptionalParameters - 3 datarow result and 1 parent result - this.ValidatePassedTestsCount(4); + // 3 tests of DerivedClass.DataRowTestMethodWithSomeOptionalParameters - 3 datarow result and no parent result + this.ValidatePassedTestsCount(3); } [TestMethod] @@ -67,8 +67,8 @@ public void DataRowsExecuteWithAllOptionalParameters() "DataRowTestMethodWithAllOptionalParameters (123,DerivedOptionalString4)", "DataRowTestMethodWithAllOptionalParameters (123,DerivedOptionalString5,DerivedOptionalString6)"); - // 5 tests of DerivedClass.DataRowTestMethodWithAllOptionalParameters - 4 datarow result and 1 parent result - this.ValidatePassedTestsCount(5); + // 4 tests of DerivedClass.DataRowTestMethodWithAllOptionalParameters - 4 datarow result and no parent result + this.ValidatePassedTestsCount(4); } [TestMethod] @@ -82,8 +82,8 @@ public void DataRowsExecuteWithParamsArrayParameter() "DataRowTestMethodWithParamsParameters (2,DerivedParamsArg1,DerivedParamsArg2)", "DataRowTestMethodWithParamsParameters (2,DerivedParamsArg1,DerivedParamsArg2,DerivedParamsArg3)"); - // 5 tests of DerivedClass.DataRowTestMethodWithParamsParameters - 4 datarow result and 1 parent result - this.ValidatePassedTestsCount(5); + // 4 tests of DerivedClass.DataRowTestMethodWithParamsParameters - 4 datarow result and no parent result + this.ValidatePassedTestsCount(4); } [TestMethod] @@ -96,8 +96,8 @@ public void DataRowsFailWhenInvalidArgumentsProvided() "DataRowTestMethodFailsWithInvalidArguments (2)", "DataRowTestMethodFailsWithInvalidArguments (2,DerivedRequiredArgument,DerivedOptionalArgument,DerivedExtraArgument)"); - // 4 tests of DerivedClass.DataRowTestMethodFailsWithInvalidArguments - 3 datarow result and 1 parent result - this.ValidatePassedTestsCount(4); + // 3 tests of DerivedClass.DataRowTestMethodFailsWithInvalidArguments - 3 datarow result and no parent result + this.ValidatePassedTestsCount(3); } } } diff --git a/test/E2ETests/Smoke.E2E.Tests/DataSourceTests.cs b/test/E2ETests/Smoke.E2E.Tests/DataSourceTests.cs deleted file mode 100644 index bf23352a0..000000000 --- a/test/E2ETests/Smoke.E2E.Tests/DataSourceTests.cs +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright (c) Microsoft Corporation. All rights reserved. -// Licensed under the MIT license. See LICENSE file in the project root for full license information. - -namespace MSTestAdapter.Smoke.E2ETests -{ - using Microsoft.MSTestV2.CLIAutomation; - using Microsoft.VisualStudio.TestTools.UnitTesting; - - [TestClass] - public class DataSourceTests : CLITestBase - { - private const string TestAssembly = "DataSourceTestProject.dll"; - - [TestMethod] - public void ExecuteCsvTestDataSourceTests() - { - this.InvokeVsTestForExecution(new string[] { TestAssembly }); - - this.ValidatePassedTestsContain( - "CsvTestMethod (Data Row 0)", - "CsvTestMethod (Data Row 2)"); - - this.ValidateFailedTestsContain( - TestAssembly, - true, - "CsvTestMethod (Data Row 1)", - "CsvTestMethod (Data Row 3)"); - } - } -} diff --git a/test/E2ETests/Smoke.E2E.Tests/Smoke.E2E.Tests.csproj b/test/E2ETests/Smoke.E2E.Tests/Smoke.E2E.Tests.csproj index 1b8309dd6..efc75053b 100644 --- a/test/E2ETests/Smoke.E2E.Tests/Smoke.E2E.Tests.csproj +++ b/test/E2ETests/Smoke.E2E.Tests/Smoke.E2E.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + Debug AnyCPU @@ -23,30 +21,41 @@ true full false + DEBUG;TRACE prompt 4 pdbonly true + TRACE prompt 4 - - DEBUG;TRACE - TRACE - + - - + + + + {9c1219e0-e775-47f9-9236-63f03f774801} + Automation.CLI + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + - + @@ -55,15 +64,7 @@ - - - - - - {9c1219e0-e775-47f9-9236-63f03f774801} - Automation.CLI - - + - + \ No newline at end of file diff --git a/test/E2ETests/Smoke.E2E.Tests/TestDataSourceTests.cs b/test/E2ETests/Smoke.E2E.Tests/TestDataSourceTests.cs new file mode 100644 index 000000000..3211e7f92 --- /dev/null +++ b/test/E2ETests/Smoke.E2E.Tests/TestDataSourceTests.cs @@ -0,0 +1,171 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace MSTestAdapter.Smoke.E2ETests +{ + using Microsoft.MSTestV2.CLIAutomation; + using Microsoft.VisualStudio.TestTools.UnitTesting; + + [TestClass] + public class TestDataSourceTests : CLITestBase + { + private const string TestAssembly = "DataSourceTestProject.dll"; + + [TestMethod] + public void ExecuteCsvTestDataSourceTests() + { + // Arrange & Act + this.InvokeVsTestForExecution( + new string[] { TestAssembly }, + testCaseFilter: "CsvTestMethod"); + + // Assert + this.ValidatePassedTests( + "CsvTestMethod (Data Row 0)", + "CsvTestMethod (Data Row 2)"); + + this.ValidateFailedTests( + TestAssembly, + "CsvTestMethod (Data Row 1)", + "CsvTestMethod (Data Row 3)"); + } + + [TestMethod] + public void ExecuteDynamicDataTests() + { + // Arrange & Act + this.InvokeVsTestForExecution( + new string[] { TestAssembly }, + testCaseFilter: "DynamicDataTest"); + + // Assert + this.ValidatePassedTests( + "DynamicDataTest (John;Doe,DataSourceTestProject.ITestDataSourceTests.User)"); + + this.ValidateFailedTestsCount(0); + } + + [TestMethod] + public void ExecuteDataRowTests_Enums() + { + // Arrange & Act + this.InvokeVsTestForExecution( + new string[] { TestAssembly }, + testCaseFilter: "FullyQualifiedName~DataRowTests_Enums"); + + // Assert + this.ValidatePassedTests( + "DataRowEnums_SByte (Alfa)", + "DataRowEnums_SByte (Beta)", + "DataRowEnums_SByte (Gamma)", + "DataRowEnums_Byte (Alfa)", + "DataRowEnums_Byte (Beta)", + "DataRowEnums_Byte (Gamma)", + "DataRowEnums_Short (Alfa)", + "DataRowEnums_Short (Beta)", + "DataRowEnums_Short (Gamma)", + "DataRowEnums_UShort (Alfa)", + "DataRowEnums_UShort (Beta)", + "DataRowEnums_UShort (Gamma)", + "DataRowEnums_Int (Alfa)", + "DataRowEnums_Int (Beta)", + "DataRowEnums_Int (Gamma)", + "DataRowEnums_UInt (Alfa)", + "DataRowEnums_UInt (Beta)", + "DataRowEnums_UInt (Gamma)", + "DataRowEnum_Long (Alfa)", + "DataRowEnum_Long (Beta)", + "DataRowEnum_Long (Gamma)", + "DataRowEnum_ULong (Alfa)", + "DataRowEnum_ULong (Beta)", + "DataRowEnum_ULong (Gamma)", + "DataRowEnums_Nullable_SByte ()", + "DataRowEnums_Nullable_SByte (Alfa)", + "DataRowEnums_Nullable_SByte (Beta)", + "DataRowEnums_Nullable_SByte (Gamma)", + "DataRowEnums_Nullable_Byte ()", + "DataRowEnums_Nullable_Byte (Alfa)", + "DataRowEnums_Nullable_Byte (Beta)", + "DataRowEnums_Nullable_Byte (Gamma)", + "DataRowEnums_Nullable_Short ()", + "DataRowEnums_Nullable_Short (Alfa)", + "DataRowEnums_Nullable_Short (Beta)", + "DataRowEnums_Nullable_Short (Gamma)", + "DataRowEnums_Nullable_UShort ()", + "DataRowEnums_Nullable_UShort (Alfa)", + "DataRowEnums_Nullable_UShort (Beta)", + "DataRowEnums_Nullable_UShort (Gamma)", + "DataRowEnums_Nullable_Int ()", + "DataRowEnums_Nullable_Int (Alfa)", + "DataRowEnums_Nullable_Int (Beta)", + "DataRowEnums_Nullable_Int (Gamma)", + "DataRowEnums_Nullable_UInt ()", + "DataRowEnums_Nullable_UInt (Alfa)", + "DataRowEnums_Nullable_UInt (Beta)", + "DataRowEnums_Nullable_UInt (Gamma)", + "DataRowEnums_Nullable_Long ()", + "DataRowEnums_Nullable_Long (Alfa)", + "DataRowEnums_Nullable_Long (Beta)", + "DataRowEnums_Nullable_Long (Gamma)", + "DataRowEnums_Nullable_ULong ()", + "DataRowEnums_Nullable_ULong (Alfa)", + "DataRowEnums_Nullable_ULong (Beta)", + "DataRowEnums_Nullable_ULong (Gamma)", + "DataRowEnums_MixedTypes_Byte (Alfa,True,1)", + "DataRowEnums_MixedTypes_Byte (Beta,False,2)", + "DataRowEnums_MixedTypes_Byte (Gamma,True,3)"); + + this.ValidateFailedTestsCount(0); + } + + [TestMethod] + public void ExecuteDataRowTests_NonSerializablePaths() + { + // Arrange & Act + this.InvokeVsTestForExecution( + new string[] { TestAssembly }, + testCaseFilter: "FullyQualifiedName~DataRowTests_NonSerializablePaths"); + + // Assert + this.ValidatePassedTests( + "DataRowNonSerializable (System.String)", + "DataRowNonSerializable (System.Int32)", + "DataRowNonSerializable (DataSourceTestProject.ITestDataSourceTests.DataRowTests_Enums)"); + + this.ValidateFailedTestsCount(0); + } + + [TestMethod] + public void ExecuteRegular_DataRowTests() + { + // Arrange & Act + this.InvokeVsTestForExecution( + new string[] { TestAssembly }, + testCaseFilter: "FullyQualifiedName~Regular_DataRowTests"); + + // Assert + this.ValidatePassedTests( + "DataRow1 (10)", + "DataRow1 (20)", + "DataRow1 (30)", + "DataRow1 (40)", + "DataRow2 (10,String parameter,True,False)", + "DataRow2 (20,String parameter,True,False)", + "DataRow2 (30,String parameter,True,False)", + "DataRow2 (40,String parameter,True,False)", + "DataRowTestMethodFailsWithInvalidArguments ()", + "DataRowTestMethodFailsWithInvalidArguments (2)", + "DataRowTestMethodFailsWithInvalidArguments (2,DerivedRequiredArgument,DerivedOptionalArgument,DerivedExtraArgument)", + "DataRowTestDouble (10.01,20.01)", + "DataRowTestDouble (10.02,20.02)", + "DataRowTestMixed (1,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (2,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (3,10,10,10,10,10,10,10,10)", + "DataRowTestMixed (4,10,10,10,10,10,10,10,10)", + "NullValueInData (john.doe@example.com,abc123,)", + "NullValueInData (john.doe@example.com,abc123,/unit/test)"); + + this.ValidateFailedTestsCount(0); + } + } +} diff --git a/test/E2ETests/Smoke.E2E.Tests/packages.config b/test/E2ETests/Smoke.E2E.Tests/packages.config deleted file mode 100644 index e0c6eb980..000000000 --- a/test/E2ETests/Smoke.E2E.Tests/packages.config +++ /dev/null @@ -1,4 +0,0 @@ - - - - \ No newline at end of file diff --git a/test/E2ETests/TestAssets/CompatTestProject/CompatTestProject.csproj b/test/E2ETests/TestAssets/CompatTestProject/CompatTestProject.csproj index 5f88101c0..d847658b7 100644 --- a/test/E2ETests/TestAssets/CompatTestProject/CompatTestProject.csproj +++ b/test/E2ETests/TestAssets/CompatTestProject/CompatTestProject.csproj @@ -1,20 +1,15 @@ - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\CompatTests - + $(RepoRoot)artifacts\TestAssets\CompatTests - - - + + + diff --git a/test/E2ETests/TestAssets/DataRowTestProject/DataRowTestProject.csproj b/test/E2ETests/TestAssets/DataRowTestProject/DataRowTestProject.csproj index 56d97e8d7..411739a44 100644 --- a/test/E2ETests/TestAssets/DataRowTestProject/DataRowTestProject.csproj +++ b/test/E2ETests/TestAssets/DataRowTestProject/DataRowTestProject.csproj @@ -1,19 +1,14 @@  - - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - - + + diff --git a/test/E2ETests/TestAssets/DataRowTestProject/DerivedClass.cs b/test/E2ETests/TestAssets/DataRowTestProject/DerivedClass.cs index f7a94f63e..e581da3ff 100644 --- a/test/E2ETests/TestAssets/DataRowTestProject/DerivedClass.cs +++ b/test/E2ETests/TestAssets/DataRowTestProject/DerivedClass.cs @@ -3,6 +3,8 @@ namespace DataRowTestProject { + using System; + using Microsoft.VisualStudio.TestTools.UnitTesting; [TestClass] @@ -37,13 +39,13 @@ public void DataRowTestMethodWithAllOptionalParameters(int i = 0, string s1 = nu { Assert.IsTrue(true); } - + [TestCategory("DataRowParamsArgument")] [TestMethod] [DataRow(2)] [DataRow(2, "DerivedSingleParamsArg")] [DataRow(2, "DerivedParamsArg1", "DerivedParamsArg2")] - [DataRow(2, "DerivedParamsArg1", "DerivedParamsArg2","DerivedParamsArg3")] + [DataRow(2, "DerivedParamsArg1", "DerivedParamsArg2", "DerivedParamsArg3")] public void DataRowTestMethodWithParamsParameters(int i, params string[] args) { Assert.IsTrue(true); @@ -59,5 +61,57 @@ public void DataRowTestMethodFailsWithInvalidArguments(int i1, string requiredSt { Assert.Fail(); } + + + [TestMethod] + [DataRow(10.01d, 20.01d)] + [DataRow(10.02d, 20.02d)] + public void DataRowTestDouble(double value1, double value2) + { + Assert.IsTrue(value1 > 10d); + Assert.IsTrue(value2 > 20d); + } + + [TestMethod] + [DataRow((byte)10, 10, 10U, 10L, 10UL, 10F, 10D, "10")] + public void DataRowTestMixed(byte b, int i, uint u, long l, ulong ul, float f, double d, string s) + { + Assert.AreEqual(10, b); + Assert.AreEqual(10, i); + Assert.AreEqual(10U, u); + Assert.AreEqual(10L, l); + Assert.AreEqual(10UL, ul); + Assert.AreEqual(10F, f); + Assert.AreEqual(10D, d); + Assert.AreEqual("10", s); + } + + [TestMethod] + [DataRow(null)] + [DataRow(TestEnum.Alfa)] + [DataRow(TestEnum.Beta)] + [DataRow(TestEnum.Gamma)] + public void DataRowEnums(TestEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(typeof(string))] + [DataRow(typeof(int))] + [DataRow(typeof(DerivedClass))] + public void DataRowNonSerializable(Type type) + { + Assert.IsTrue(true); + } + + public enum TestEnum + { + Alfa, + Beta, + Gamma, + Delta, + Epsilon + } } } diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/DataSourceTestProject.csproj b/test/E2ETests/TestAssets/DataSourceTestProject/DataSourceTestProject.csproj index 5b3ec27ed..f52ff44cc 100644 --- a/test/E2ETests/TestAssets/DataSourceTestProject/DataSourceTestProject.csproj +++ b/test/E2ETests/TestAssets/DataSourceTestProject/DataSourceTestProject.csproj @@ -1,20 +1,15 @@ - - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\ - + $(RepoRoot)artifacts\TestAssets\ - - + + + diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Enums.cs b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Enums.cs new file mode 100644 index 000000000..c80baa4e3 --- /dev/null +++ b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Enums.cs @@ -0,0 +1,189 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DataSourceTestProject.ITestDataSourceTests +{ + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System; + + [TestClass] + public class DataRowTests_Enums + { + #region Basic Tests + [TestMethod] + [DataRow(SByteEnum.Alfa)] + [DataRow(SByteEnum.Beta)] + [DataRow(SByteEnum.Gamma)] + public void DataRowEnums_SByte(SByteEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(ByteEnum.Alfa)] + [DataRow(ByteEnum.Beta)] + [DataRow(ByteEnum.Gamma)] + public void DataRowEnums_Byte(ByteEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(ShortEnum.Alfa)] + [DataRow(ShortEnum.Beta)] + [DataRow(ShortEnum.Gamma)] + public void DataRowEnums_Short(ShortEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(UShortEnum.Alfa)] + [DataRow(UShortEnum.Beta)] + [DataRow(UShortEnum.Gamma)] + public void DataRowEnums_UShort(UShortEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(IntEnum.Alfa)] + [DataRow(IntEnum.Beta)] + [DataRow(IntEnum.Gamma)] + public void DataRowEnums_Int(IntEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(UIntEnum.Alfa)] + [DataRow(UIntEnum.Beta)] + [DataRow(UIntEnum.Gamma)] + public void DataRowEnums_UInt(UIntEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(LongEnum.Alfa)] + [DataRow(LongEnum.Beta)] + [DataRow(LongEnum.Gamma)] + public void DataRowEnum_Long(LongEnum testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(ULongEnum.Alfa)] + [DataRow(ULongEnum.Beta)] + [DataRow(ULongEnum.Gamma)] + public void DataRowEnum_ULong(ULongEnum testEnum) + { + Assert.IsTrue(true); + } + #endregion + + #region Basic Tests (Nullable) + [TestMethod] + [DataRow(null)] + [DataRow(SByteEnum.Alfa)] + [DataRow(SByteEnum.Beta)] + [DataRow(SByteEnum.Gamma)] + public void DataRowEnums_Nullable_SByte(SByteEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(ByteEnum.Alfa)] + [DataRow(ByteEnum.Beta)] + [DataRow(ByteEnum.Gamma)] + public void DataRowEnums_Nullable_Byte(ByteEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(ShortEnum.Alfa)] + [DataRow(ShortEnum.Beta)] + [DataRow(ShortEnum.Gamma)] + public void DataRowEnums_Nullable_Short(ShortEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(UShortEnum.Alfa)] + [DataRow(UShortEnum.Beta)] + [DataRow(UShortEnum.Gamma)] + public void DataRowEnums_Nullable_UShort(UShortEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(IntEnum.Alfa)] + [DataRow(IntEnum.Beta)] + [DataRow(IntEnum.Gamma)] + public void DataRowEnums_Nullable_Int(IntEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(UIntEnum.Alfa)] + [DataRow(UIntEnum.Beta)] + [DataRow(UIntEnum.Gamma)] + public void DataRowEnums_Nullable_UInt(UIntEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(LongEnum.Alfa)] + [DataRow(LongEnum.Beta)] + [DataRow(LongEnum.Gamma)] + public void DataRowEnums_Nullable_Long(LongEnum? testEnum) + { + Assert.IsTrue(true); + } + + [TestMethod] + [DataRow(null)] + [DataRow(ULongEnum.Alfa)] + [DataRow(ULongEnum.Beta)] + [DataRow(ULongEnum.Gamma)] + public void DataRowEnums_Nullable_ULong(ULongEnum? testEnum) + { + Assert.IsTrue(true); + } + #endregion + + #region Mixed Types + [TestMethod] + [DataRow(ByteEnum.Alfa, true, 1)] + [DataRow(ByteEnum.Beta, false, 2)] + [DataRow(ByteEnum.Gamma, true, 3)] + public void DataRowEnums_MixedTypes_Byte(ByteEnum testEnum, bool arg1, int arg2) + { + Assert.IsTrue(true); + } + #endregion + + public enum SByteEnum : sbyte { Alfa = sbyte.MinValue, Beta, Gamma, Delta, Epsilon } + public enum ByteEnum : byte { Alfa, Beta, Gamma, Delta, Epsilon } + public enum ShortEnum : short { Alfa = byte.MaxValue + 1, Beta, Gamma, Delta, Epsilon } + public enum UShortEnum : ushort { Alfa = short.MaxValue + 1, Beta, Gamma, Delta, Epsilon } + public enum IntEnum { Alfa = ushort.MaxValue + 1, Beta, Gamma, Delta, Epsilon } + public enum UIntEnum : uint { Alfa = ((uint)int.MaxValue) + 1, Beta, Gamma, Delta, Epsilon } + public enum LongEnum : long { Alfa = ((long)uint.MaxValue) + 1, Beta, Gamma, Delta, Epsilon } + public enum ULongEnum : ulong { Alfa = ((ulong)long.MaxValue) + 1, Beta, Gamma, Delta, Epsilon } + } +} diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_NonSerializablePaths.cs b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_NonSerializablePaths.cs new file mode 100644 index 000000000..34e22fca3 --- /dev/null +++ b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_NonSerializablePaths.cs @@ -0,0 +1,22 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DataSourceTestProject.ITestDataSourceTests +{ + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System; + + [TestClass] + public class DataRowTests_NonSerializablePaths + { + [TestMethod] + [DataRow(typeof(string))] + [DataRow(typeof(int))] + [DataRow(typeof(DataRowTests_Enums))] + public void DataRowNonSerializable(Type type) + { + Assert.IsTrue(true); + } + } +} diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Regular.cs b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Regular.cs new file mode 100644 index 000000000..95c2851bc --- /dev/null +++ b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataRowTests_Regular.cs @@ -0,0 +1,79 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DataSourceTestProject.ITestDataSourceTests +{ + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System; + + [TestClass] + public class Regular_DataRowTests + { + [TestMethod] + [DataRow(10)] + [DataRow(20)] + [DataRow(30)] + [DataRow(40)] + public void DataRow1(int i) + { + Assert.IsTrue(i != 0); + } + + [TestMethod] + [DataRow(10, "String parameter", true, false)] + [DataRow(20, "String parameter", true, false)] + [DataRow(30, "String parameter", true, false)] + [DataRow(40, "String parameter", true, false)] + public void DataRow2(int i, string s, bool b1, bool b2) + { + Assert.IsTrue(i != 200); + } + + [TestCategory("DataRowOptionalInvalidArguments")] + [TestMethod] + [ExpectedException(typeof(System.Reflection.TargetParameterCountException))] + [DataRow()] + [DataRow(2)] + [DataRow(2, "DerivedRequiredArgument", "DerivedOptionalArgument", "DerivedExtraArgument")] + public void DataRowTestMethodFailsWithInvalidArguments(int i1, string requiredString, string s1 = null) + { + Assert.Fail(); + } + + + [TestMethod] + [DataRow(10.01d, 20.01d)] + [DataRow(10.02d, 20.02d)] + public void DataRowTestDouble(double value1, double value2) + { + Assert.IsTrue(value1 > 10d); + Assert.IsTrue(value2 > 20d); + } + + [TestMethod] + [DataRow(1, (byte)10, 10, 10U, 10L, 10UL, 10F, 10D, "10")] + [DataRow(2, (byte)10, 10, 10U, 10L, 10UL, 10F, 10D, "10")] + [DataRow(3, (byte)10, 10, 10U, 10L, 10UL, 10F, 10D, "10")] + [DataRow(4, (byte)10, 10, 10U, 10L, 10UL, 10F, 10D, "10")] + public void DataRowTestMixed(int index, byte b, int i, uint u, long l, ulong ul, float f, double d, string s) + { + Assert.AreEqual(10, b); + Assert.AreEqual(10, i); + Assert.AreEqual(10U, u); + Assert.AreEqual(10L, l); + Assert.AreEqual(10UL, ul); + Assert.AreEqual(10F, f); + Assert.AreEqual(10D, d); + Assert.AreEqual("10", s); + } + + [TestMethod] + [DataRow("john.doe@example.com", "abc123", null)] + [DataRow("john.doe@example.com", "abc123", "/unit/test")] + public void NullValueInData(string email, string password, string returnUrl) + { + + } + } +} diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/UnitTest1.cs b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataSourceTests.cs similarity index 75% rename from test/E2ETests/TestAssets/DataSourceTestProject/UnitTest1.cs rename to test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataSourceTests.cs index f444c78a0..ae1fc4743 100644 --- a/test/E2ETests/TestAssets/DataSourceTestProject/UnitTest1.cs +++ b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DataSourceTests.cs @@ -1,12 +1,14 @@ -// Copyright (c) Microsoft Corporation. All rights reserved. +// Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the MIT license. See LICENSE file in the project root for full license information. -namespace DataSourceTestProject +namespace DataSourceTestProject.ITestDataSourceTests { using Microsoft.VisualStudio.TestTools.UnitTesting; + using System; + [TestClass] - public class UnitTest1 + public class DataRowTests_Regular { public TestContext TestContext { @@ -20,4 +22,4 @@ public void CsvTestMethod() Assert.AreEqual(1, TestContext.DataRow["Item1"]); } } -} \ No newline at end of file +} diff --git a/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DynamicDataTests.cs b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DynamicDataTests.cs new file mode 100644 index 000000000..525e1ce1e --- /dev/null +++ b/test/E2ETests/TestAssets/DataSourceTestProject/ITestDataSourceTests/DynamicDataTests.cs @@ -0,0 +1,42 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DataSourceTestProject.ITestDataSourceTests +{ + using Microsoft.VisualStudio.TestTools.UnitTesting; + + using System; + using System.Collections.Generic; + + [TestClass] + public class DynamicDataTests + { + [DataTestMethod()] + [DynamicData(nameof(GetParseUserDatas), DynamicDataSourceType.Method)] + public void DynamicDataTest(string userDatas, User expectedUser) + { + // Prepare + var srv = new UserService(); + + // Act + var user = srv.ParseUserDatas(userDatas); + + // Assert + Assert.AreNotSame(user, expectedUser); + Assert.AreEqual(user.FirstName, expectedUser.FirstName); + Assert.AreEqual(user.LastName, expectedUser.LastName); + } + + public static IEnumerable GetParseUserDatas() + { + yield return new object[] { + "John;Doe", + new User() + { + FirstName = "John", + LastName = "Doe" + } + }; + } + } +} diff --git a/test/E2ETests/TestAssets/DeploymentTestProject/DeploymentTestProject.csproj b/test/E2ETests/TestAssets/DeploymentTestProject/DeploymentTestProject.csproj index 7052a2f2f..71de29f4e 100644 --- a/test/E2ETests/TestAssets/DeploymentTestProject/DeploymentTestProject.csproj +++ b/test/E2ETests/TestAssets/DeploymentTestProject/DeploymentTestProject.csproj @@ -1,24 +1,22 @@  - ..\..\..\..\ - Never + Never - net452 false false - $(TestFxRoot)artifacts\TestAssets\DesktopDeployment\$(DependencyCopyBehavior)\ + $(RepoRoot)artifacts\TestAssets\DesktopDeployment\$(DependencyCopyBehavior)\ - + + - - + @@ -37,10 +35,10 @@ - + - + diff --git a/test/E2ETests/TestAssets/DeploymentTestProjectNetCore/DeploymentTestProjectNetCore.csproj b/test/E2ETests/TestAssets/DeploymentTestProjectNetCore/DeploymentTestProjectNetCore.csproj index 4227314be..705eead6a 100644 --- a/test/E2ETests/TestAssets/DeploymentTestProjectNetCore/DeploymentTestProjectNetCore.csproj +++ b/test/E2ETests/TestAssets/DeploymentTestProjectNetCore/DeploymentTestProjectNetCore.csproj @@ -1,24 +1,19 @@  - - ..\..\..\..\ - false - - - netcoreapp2.1 NetCore false - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ + false - + + - - + diff --git a/test/E2ETests/TestAssets/DesktopTestProjectx64Debug/DesktopTestProjectx64Debug.csproj b/test/E2ETests/TestAssets/DesktopTestProjectx64Debug/DesktopTestProjectx64Debug.csproj index 7832edbb0..7b039f8e8 100644 --- a/test/E2ETests/TestAssets/DesktopTestProjectx64Debug/DesktopTestProjectx64Debug.csproj +++ b/test/E2ETests/TestAssets/DesktopTestProjectx64Debug/DesktopTestProjectx64Debug.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,72 +13,55 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - + true full - false DEBUG;TRACE + false + x64 prompt 4 - - - pdbonly - true - TRACE - prompt - 4 - - - true - DEBUG;TRACE - full - x64 - prompt MinimumRecommendedRules.ruleset - + + pdbonly TRACE true - pdbonly - x64 + x64 prompt + 4 MinimumRecommendedRules.ruleset + - - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core False - + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop False + UnitTest1.cs + - \ No newline at end of file diff --git a/test/E2ETests/TestAssets/DesktopTestProjectx64Release/DesktopTestProjectx64Release.csproj b/test/E2ETests/TestAssets/DesktopTestProjectx64Release/DesktopTestProjectx64Release.csproj index 53a457c50..12a7362d3 100644 --- a/test/E2ETests/TestAssets/DesktopTestProjectx64Release/DesktopTestProjectx64Release.csproj +++ b/test/E2ETests/TestAssets/DesktopTestProjectx64Release/DesktopTestProjectx64Release.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,72 +13,56 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - + + true full - false DEBUG;TRACE + false + x64 prompt 4 - - - pdbonly - true - TRACE - prompt - 4 - - - true - DEBUG;TRACE - full - x64 - prompt MinimumRecommendedRules.ruleset - + + pdbonly TRACE true - pdbonly - x64 + x64 prompt + 4 MinimumRecommendedRules.ruleset + - - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core False - + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop False + UnitTest1.cs + - \ No newline at end of file diff --git a/test/E2ETests/TestAssets/DesktopTestProjectx86Debug/DesktopTestProjectx86Debug.csproj b/test/E2ETests/TestAssets/DesktopTestProjectx86Debug/DesktopTestProjectx86Debug.csproj index 807205e88..d751651f8 100644 --- a/test/E2ETests/TestAssets/DesktopTestProjectx86Debug/DesktopTestProjectx86Debug.csproj +++ b/test/E2ETests/TestAssets/DesktopTestProjectx86Debug/DesktopTestProjectx86Debug.csproj @@ -1,9 +1,7 @@  - - - ..\..\..\..\ - + + Debug AnyCPU @@ -15,73 +13,57 @@ v4.5 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - + + true full - false DEBUG;TRACE + false + x86 prompt 4 - - - pdbonly - true - TRACE - prompt - 4 - - - true - DEBUG;TRACE - full - x86 - prompt MinimumRecommendedRules.ruleset - + + pdbonly TRACE true - pdbonly - x86 + x86 prompt + 4 MinimumRecommendedRules.ruleset + - + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core False - + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop False - - - + + - \ No newline at end of file diff --git a/test/E2ETests/TestAssets/DesktopTestProjectx86Release/DesktopTestProjectx86Release.csproj b/test/E2ETests/TestAssets/DesktopTestProjectx86Release/DesktopTestProjectx86Release.csproj index 0f63eaa29..f61882547 100644 --- a/test/E2ETests/TestAssets/DesktopTestProjectx86Release/DesktopTestProjectx86Release.csproj +++ b/test/E2ETests/TestAssets/DesktopTestProjectx86Release/DesktopTestProjectx86Release.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,72 +13,56 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - + + true full - false DEBUG;TRACE + false + x86 prompt 4 - - - pdbonly - true - TRACE - prompt - 4 - - - true - DEBUG;TRACE - full - x86 - prompt MinimumRecommendedRules.ruleset - + + pdbonly TRACE true - pdbonly - x86 + x86 prompt + 4 MinimumRecommendedRules.ruleset + - - - + + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core False - + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop False + - + UnitTest1.cs + - \ No newline at end of file diff --git a/test/E2ETests/TestAssets/Directory.Build.targets b/test/E2ETests/TestAssets/Directory.Build.targets index 5a5c0f5db..87043c6ab 100644 --- a/test/E2ETests/TestAssets/Directory.Build.targets +++ b/test/E2ETests/TestAssets/Directory.Build.targets @@ -9,4 +9,4 @@ - \ No newline at end of file + diff --git a/test/E2ETests/TestAssets/DoNotParallelizeTestProject/DoNotParallelizeTestProject.csproj b/test/E2ETests/TestAssets/DoNotParallelizeTestProject/DoNotParallelizeTestProject.csproj index d17b65853..41a9d2fa5 100644 --- a/test/E2ETests/TestAssets/DoNotParallelizeTestProject/DoNotParallelizeTestProject.csproj +++ b/test/E2ETests/TestAssets/DoNotParallelizeTestProject/DoNotParallelizeTestProject.csproj @@ -1,19 +1,14 @@ - - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - - + + diff --git a/test/E2ETests/TestAssets/FSharpTestProject/FSharpTestProject.fsproj b/test/E2ETests/TestAssets/FSharpTestProject/FSharpTestProject.fsproj index bab287180..694d4652c 100644 --- a/test/E2ETests/TestAssets/FSharpTestProject/FSharpTestProject.fsproj +++ b/test/E2ETests/TestAssets/FSharpTestProject/FSharpTestProject.fsproj @@ -1,20 +1,16 @@  - - ..\..\..\..\ - - net472 false false false false - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - - + + diff --git a/test/E2ETests/TestAssets/FxExtensibilityTestProject/FxExtensibilityTestProject.csproj b/test/E2ETests/TestAssets/FxExtensibilityTestProject/FxExtensibilityTestProject.csproj index 9e587e801..60b89a66b 100644 --- a/test/E2ETests/TestAssets/FxExtensibilityTestProject/FxExtensibilityTestProject.csproj +++ b/test/E2ETests/TestAssets/FxExtensibilityTestProject/FxExtensibilityTestProject.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,12 +13,12 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ true @@ -36,9 +35,20 @@ prompt 4 + + + + {a82770c0-1ff5-43c7-8790-471d5e4f8d6e} + FxExtensibility + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + + @@ -47,16 +57,7 @@ - - - {a82770c0-1ff5-43c7-8790-471d5e4f8d6e} - FxExtensibility - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - - + \ No newline at end of file diff --git a/test/E2ETests/TestAssets/ParallelTestClass/ParallelClassesTestProject.csproj b/test/E2ETests/TestAssets/ParallelTestClass/ParallelClassesTestProject.csproj index 794da950c..f00bad153 100644 --- a/test/E2ETests/TestAssets/ParallelTestClass/ParallelClassesTestProject.csproj +++ b/test/E2ETests/TestAssets/ParallelTestClass/ParallelClassesTestProject.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,12 +13,12 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ true @@ -36,26 +35,30 @@ prompt 4 + + - - - - - - - - + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop - + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core + + + + + + + + + \ No newline at end of file diff --git a/test/E2ETests/TestAssets/ParallelTestMethods/ParallelMethodsTestProject.csproj b/test/E2ETests/TestAssets/ParallelTestMethods/ParallelMethodsTestProject.csproj index 6ad0a60ac..891c94a6c 100644 --- a/test/E2ETests/TestAssets/ParallelTestMethods/ParallelMethodsTestProject.csproj +++ b/test/E2ETests/TestAssets/ParallelTestMethods/ParallelMethodsTestProject.csproj @@ -1,8 +1,7 @@  - - ..\..\..\..\ - + + Debug AnyCPU @@ -14,12 +13,12 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ true @@ -36,25 +35,27 @@ prompt 4 + - - - - - - - - - + + {a7ea583b-a2b0-47da-a058-458f247c7575} Extension.Desktop - + {7252d9e3-267d-442c-96bc-c73aef3241d6} MSTest.Core + + + + + + + + \ No newline at end of file diff --git a/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/ReferencedProjectFromDataSourceTest.csproj b/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/ReferencedProjectFromDataSourceTest.csproj new file mode 100644 index 000000000..7f4f98b98 --- /dev/null +++ b/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/ReferencedProjectFromDataSourceTest.csproj @@ -0,0 +1,7 @@ + + + + net452 + + + diff --git a/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/User.cs b/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/User.cs new file mode 100644 index 000000000..9957914e7 --- /dev/null +++ b/test/E2ETests/TestAssets/ReferencedProjectFromDataSourceTest/User.cs @@ -0,0 +1,26 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace DataSourceTestProject.ITestDataSourceTests +{ + public class User + { + public string LastName { get; set; } + + public string FirstName { get; set; } + } + + public class UserService + { + public User ParseUserDatas(string datas) + { + var splittedDatas = datas.Split(';'); + + return new User() + { + FirstName = splittedDatas[0], + LastName = splittedDatas[1] + }; + } + } +} diff --git a/test/E2ETests/TestAssets/TimeoutTestProject/TimeoutTestProject.csproj b/test/E2ETests/TestAssets/TimeoutTestProject/TimeoutTestProject.csproj index 482fd0b45..bef06d394 100644 --- a/test/E2ETests/TestAssets/TimeoutTestProject/TimeoutTestProject.csproj +++ b/test/E2ETests/TestAssets/TimeoutTestProject/TimeoutTestProject.csproj @@ -1,17 +1,13 @@  - - ..\..\..\..\ - - net452 false false - $(TestFxRoot)artifacts\TestAssets\ + $(RepoRoot)artifacts\TestAssets\ - - + + diff --git a/test/E2ETests/TestAssets/TimeoutTestProjectNetCore/TimeoutTestProjectNetCore.csproj b/test/E2ETests/TestAssets/TimeoutTestProjectNetCore/TimeoutTestProjectNetCore.csproj index d4cee39ff..89bf1fe4b 100644 --- a/test/E2ETests/TestAssets/TimeoutTestProjectNetCore/TimeoutTestProjectNetCore.csproj +++ b/test/E2ETests/TestAssets/TimeoutTestProjectNetCore/TimeoutTestProjectNetCore.csproj @@ -1,23 +1,18 @@  - - ..\..\..\..\ - - - netcoreapp2.1 NetCore false false - $(TestFxRoot)artifacts\TestAssets\netcoreapp2.1\ + $(RepoRoot)artifacts\TestAssets\netcoreapp2.1\ - + - - + + diff --git a/test/UnitTests/MSTest.Core.Unit.Tests/Assertions/AssertTests.cs b/test/UnitTests/MSTest.Core.Unit.Tests/Assertions/AssertTests.cs index 6cabbc06c..ac2da6970 100644 --- a/test/UnitTests/MSTest.Core.Unit.Tests/Assertions/AssertTests.cs +++ b/test/UnitTests/MSTest.Core.Unit.Tests/Assertions/AssertTests.cs @@ -71,12 +71,12 @@ public async Task ThrowsExceptionAsyncShouldNotThrowAssertionOnRightException() Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); throw new ArgumentException(); }); // Should not throw an exception. - await t; + await t.ConfigureAwait(false); } [TestMethod] @@ -85,7 +85,7 @@ public void ThrowsExceptionAsyncShouldThrowAssertionOnNoException() Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); }); var ex = ActionUtility.PerformActionAndReturnException(() => t.Wait()); @@ -104,7 +104,7 @@ public void ThrowsExceptionAsyncShouldThrowAssertionOnWrongException() Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); throw new FormatException(); }); var ex = ActionUtility.PerformActionAndReturnException(() => t.Wait()); @@ -124,7 +124,7 @@ public void ThrowsExceptionAsyncWithMessageShouldThrowAssertionOnNoException() Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); }, "The world is not on fire."); var ex = ActionUtility.PerformActionAndReturnException(() => t.Wait()); @@ -144,7 +144,7 @@ public void ThrowsExceptionAsyncWithMessageShouldThrowAssertionOnWrongException( Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); throw new FormatException(); }, "Happily ever after."); @@ -175,7 +175,7 @@ public void ThrowsExceptionAsyncWithMessageAndParamsShouldThrowOnNullMessage() { Action a = () => { - Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync(async () => { await Task.FromResult(true); }, null, null); + Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync(async () => { await Task.FromResult(true).ConfigureAwait(false); }, null, null); t.Wait(); }; ActionUtility.ActionShouldThrowInnerExceptionOfType(a, typeof(ArgumentNullException)); @@ -187,7 +187,7 @@ public void ThrowsExceptionAsyncWithMessageAndParamsShouldThrowAssertionOnNoExce Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); }, "The world is not on fire {0}.{1}-{2}.", "ta", @@ -210,7 +210,7 @@ public void ThrowsExceptionAsyncWithMessageAndParamsShouldThrowAssertionOnWrongE Task t = TestFrameworkV2.Assert.ThrowsExceptionAsync( async () => { - await Task.Delay(5); + await Task.Delay(5).ConfigureAwait(false); throw new FormatException(); }, "Happily ever after. {0} {1}.", @@ -322,5 +322,247 @@ public void IsTrueNullableBooleansShouldFailWithNull() StringAssert.Contains(ex.Message, "Assert.IsTrue failed"); } #endregion + + #region AreNotEqual tests. + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualType() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(null, null); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualTypeWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual(null, null, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualString() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual("A", "A"); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualStringWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual("A", "A", "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualStringAndCaseIgnored() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual("A", "a", true); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualInt() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(1, 1); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualIntWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual(1, 1, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualLong() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(1L, 1L); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualLongWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual(1L, 1L, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualLongWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(1L, 2L, 1L); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualDouble() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(0.1, 0.1); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualDoubleWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual(0.1, 0.1, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualDoubleWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(0.1, 0.2, 0.1); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenFloatDouble() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(100E-2, 100E-2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenFloatDoubleWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreNotEqual(100E-2, 100E-2, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreNotEqualShouldFailWhenNotEqualFloatWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreNotEqual(100E-2, 200E-2, 100E-2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + #endregion + + #region AreEqual tests. + [TestMethod] + public void AreEqualShouldFailWhenNotEqualType() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(null, "string"); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualTypeWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual(null, "string", "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualString() + { + Action action = () => TestFrameworkV2.Assert.AreEqual("A", "a"); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualStringWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual("A", "a", "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualStringAndCaseIgnored() + { + Action action = () => TestFrameworkV2.Assert.AreEqual("A", "a", false); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualInt() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(1, 2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualIntWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual(1, 2, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualLong() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(1L, 2L); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualLongWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual(1L, 2L, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualLongWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(10L, 20L, 5L); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualDouble() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(0.1, 0.2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualDoubleWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual(0.1, 0.2, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualDoubleWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(0.1, 0.2, 0.05); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenFloatDouble() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(100E-2, 200E-2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + [TestMethod] + public void AreEqualShouldFailWhenFloatDoubleWithMessage() + { + var ex = ActionUtility.PerformActionAndReturnException(() => TestFrameworkV2.Assert.AreEqual(100E-2, 200E-2, "A Message")); + Assert.IsNotNull(ex); + StringAssert.Contains(ex.Message, "A Message"); + } + + [TestMethod] + public void AreEqualShouldFailWhenNotEqualFloatWithDelta() + { + Action action = () => TestFrameworkV2.Assert.AreEqual(100E-2, 200E-2, 50E-2); + ActionUtility.ActionShouldThrowExceptionOfType(action, typeof(TestFrameworkV2.AssertFailedException)); + } + + #endregion } } diff --git a/test/UnitTests/MSTest.Core.Unit.Tests/MSTest.Core.Unit.Tests.csproj b/test/UnitTests/MSTest.Core.Unit.Tests/MSTest.Core.Unit.Tests.csproj index 8ffb1e207..54ace3ff2 100644 --- a/test/UnitTests/MSTest.Core.Unit.Tests/MSTest.Core.Unit.Tests.csproj +++ b/test/UnitTests/MSTest.Core.Unit.Tests/MSTest.Core.Unit.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {0A4A76DD-FEE1-4D04-926B-38E1A24A7ED2} Library @@ -12,8 +10,8 @@ Microsoft.VisualStudio.TestPlatform.TestFramework.UnitTests v4.5.2 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest @@ -33,35 +31,32 @@ prompt 4 + - - $(TestFxRoot)packages\Castle.Core.3.3.3\lib\net45\Castle.Core.dll - True - - - $(TestFxRoot)packages\Moq.4.5.21\lib\net45\Moq.dll - True - - - - + + FrameworkV1 + + + {7252D9E3-267D-442C-96BC-C73AEF3241D6} MSTest.Core FrameworkV2 - + {F81C7549-E3A3-4770-AC3F-3BC7356E61E8} MSTest.CoreAdapter.TestUtilities + - - FrameworkV1 - - - + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + @@ -73,9 +68,7 @@ - - - + - + \ No newline at end of file diff --git a/test/UnitTests/MSTest.Core.Unit.Tests/packages.config b/test/UnitTests/MSTest.Core.Unit.Tests/packages.config deleted file mode 100644 index 32d98fb3a..000000000 --- a/test/UnitTests/MSTest.Core.Unit.Tests/packages.config +++ /dev/null @@ -1,6 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/test/UnitTests/MSTest.CoreAdapter.TestUtilities/MSTest.CoreAdapter.TestUtilities.csproj b/test/UnitTests/MSTest.CoreAdapter.TestUtilities/MSTest.CoreAdapter.TestUtilities.csproj index bc697765f..8ccefdee9 100644 --- a/test/UnitTests/MSTest.CoreAdapter.TestUtilities/MSTest.CoreAdapter.TestUtilities.csproj +++ b/test/UnitTests/MSTest.CoreAdapter.TestUtilities/MSTest.CoreAdapter.TestUtilities.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {F81C7549-E3A3-4770-AC3F-3BC7356E61E8} Library @@ -12,8 +10,8 @@ MSTestAdapter.TestUtilities v4.5.1 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest @@ -33,21 +31,26 @@ prompt 4 + - - + FrameworkV1 + - + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + - + \ No newline at end of file diff --git a/test/UnitTests/MSTest.CoreAdapter.TestUtilities/packages.config b/test/UnitTests/MSTest.CoreAdapter.TestUtilities/packages.config deleted file mode 100644 index 3644cdfa3..000000000 --- a/test/UnitTests/MSTest.CoreAdapter.TestUtilities/packages.config +++ /dev/null @@ -1,4 +0,0 @@ - - - - \ No newline at end of file diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Discovery/AssemblyEnumeratorTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Discovery/AssemblyEnumeratorTests.cs index 17a9edda4..b4ca76026 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Discovery/AssemblyEnumeratorTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Discovery/AssemblyEnumeratorTests.cs @@ -19,6 +19,7 @@ namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.UnitTests.Discovery using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.ObjectModel; using Microsoft.VisualStudio.TestPlatform.MSTestAdapter.UnitTests.TestableImplementations; + using Microsoft.VisualStudio.TestPlatform.ObjectModel.Adapter; using Moq; @@ -77,6 +78,7 @@ public void ConstructorShouldPopulateSettings() MSTestSettings adapterSettings = MSTestSettings.GetSettings(runSettingsXml, MSTestSettings.SettingsName); var assemblyEnumerator = new AssemblyEnumerator(adapterSettings); + assemblyEnumerator.RunSettingsXml = runSettingsXml; Assert.IsTrue(MSTestSettings.CurrentSettings.ForcedLegacyMode); Assert.AreEqual("DummyPath\\TestSettings1.testsettings", MSTestSettings.CurrentSettings.TestSettingsFile); @@ -94,7 +96,7 @@ public void GetTypesShouldReturnEmptyArrayWhenNoDeclaredTypes() // Setup mocks mockAssembly.Setup(a => a.DefinedTypes).Returns(new List()); - Assert.AreEqual(0, this.assemblyEnumerator.GetTypes(mockAssembly.Object, string.Empty, this.warnings).Count()); + Assert.AreEqual(0, this.assemblyEnumerator.GetTypes(mockAssembly.Object, string.Empty, this.warnings).Length); } [TestMethodV1] @@ -196,18 +198,16 @@ public void GetLoadExceptionDetailsShouldReturnLoaderExceptionMessagesForMoreTha new Exception[] { loaderException1, loaderException2 }); StringBuilder errorDetails = new StringBuilder(); - errorDetails.AppendLine( - string.Format( + errorDetails.AppendFormat( CultureInfo.CurrentCulture, Resource.EnumeratorLoadTypeErrorFormat, loaderException1.GetType(), - loaderException1.Message)); - errorDetails.AppendLine( - string.Format( + loaderException1.Message).AppendLine(); + errorDetails.AppendFormat( CultureInfo.CurrentCulture, Resource.EnumeratorLoadTypeErrorFormat, loaderException2.GetType(), - loaderException2.Message)); + loaderException2.Message).AppendLine(); Assert.AreEqual(errorDetails.ToString(), this.assemblyEnumerator.GetLoadExceptionDetails(exceptions)); } @@ -243,7 +243,7 @@ public void EnumerateAssemblyShouldReturnEmptyListWhenNoDeclaredTypes() this.testablePlatformServiceProvider.MockFileOperations.Setup(fo => fo.LoadAssembly("DummyAssembly", false)) .Returns(mockAssembly.Object); - Assert.AreEqual(0, this.assemblyEnumerator.EnumerateAssembly("DummyAssembly", out this.warnings).Count()); + Assert.AreEqual(0, this.assemblyEnumerator.EnumerateAssembly("DummyAssembly", out this.warnings).Count); } [TestMethodV1] @@ -260,7 +260,7 @@ public void EnumerateAssemblyShouldReturnEmptyListWhenNoTestElementsInAType() testableAssemblyEnumerator.MockTypeEnumerator.Setup(te => te.Enumerate(out this.warnings)) .Returns((ICollection)null); - Assert.AreEqual(0, this.assemblyEnumerator.EnumerateAssembly("DummyAssembly", out this.warnings).Count()); + Assert.AreEqual(0, this.assemblyEnumerator.EnumerateAssembly("DummyAssembly", out this.warnings).Count); } [TestMethodV1] diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodFilterTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodFilterTests.cs index 3759a38a9..cfbf7545e 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodFilterTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodFilterTests.cs @@ -112,8 +112,7 @@ public void PropertyProviderValueForValidTestAndSupportedPropertyNameReturnsValu public void GetFilterExpressionForNullRunContextReturnsNull() { TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(null, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(null, recorder, out var filterHasError); Assert.IsNull(filterExpression); Assert.IsFalse(filterHasError); @@ -125,8 +124,7 @@ public void GetFilterExpressionForValidRunContextReturnsValidTestCaseFilterExpre TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); var dummyFilterExpression = new TestableTestCaseFilterExpression(); TestableRunContext runContext = new TestableRunContext(() => dummyFilterExpression); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(runContext, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(runContext, recorder, out var filterHasError); Assert.AreEqual(dummyFilterExpression, filterExpression); Assert.IsFalse(filterHasError); @@ -141,8 +139,7 @@ public void GetFilterExpressionForDiscoveryContextWithGetTestCaseFilterReturnsVa TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); var dummyFilterExpression = new TestableTestCaseFilterExpression(); TestableDiscoveryContextWithGetTestCaseFilter discoveryContext = new TestableDiscoveryContextWithGetTestCaseFilter(() => dummyFilterExpression); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out var filterHasError); Assert.AreEqual(dummyFilterExpression, filterExpression); Assert.IsFalse(filterHasError); @@ -156,8 +153,7 @@ public void GetFilterExpressionForDiscoveryContextWithoutGetTestCaseFilterReturn { TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); TestableDiscoveryContextWithoutGetTestCaseFilter discoveryContext = new TestableDiscoveryContextWithoutGetTestCaseFilter(); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out var filterHasError); Assert.IsNull(filterExpression); Assert.IsFalse(filterHasError); @@ -168,8 +164,7 @@ public void GetFilterExpressionForRunContextGetTestCaseFilterThrowingExceptionRe { TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); TestableRunContext runContext = new TestableRunContext(() => { throw new TestPlatformFormatException("DummyException"); }); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(runContext, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(runContext, recorder, out var filterHasError); Assert.IsNull(filterExpression); Assert.IsTrue(filterHasError); @@ -185,8 +180,7 @@ public void GetFilterExpressionForDiscoveryContextWithGetTestCaseFilterThrowingE { TestableTestExecutionRecorder recorder = new TestableTestExecutionRecorder(); TestableDiscoveryContextWithGetTestCaseFilter discoveryContext = new TestableDiscoveryContextWithGetTestCaseFilter(() => { throw new TestPlatformFormatException("DummyException"); }); - bool filterHasError; - var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out filterHasError); + var filterExpression = this.TestMethodFilter.GetFilterExpression(discoveryContext, recorder, out var filterHasError); Assert.IsNull(filterExpression); Assert.IsTrue(filterHasError); diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodRunnerTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodRunnerTests.cs index d800c29e4..ed2649090 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodRunnerTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TestMethodRunnerTests.cs @@ -555,11 +555,9 @@ public void RunTestMethodShouldSetDataRowIndexForDataDrivenTestsWhenDataIsProvid var results = testMethodRunner.RunTestMethod(); // check for datarowIndex - // 1st is parent result. - Assert.AreEqual(-1, results[0].DatarowIndex); - Assert.AreEqual(0, results[1].DatarowIndex); - Assert.AreEqual(1, results[2].DatarowIndex); - Assert.AreEqual(2, results[3].DatarowIndex); + Assert.AreEqual(0, results[0].DatarowIndex); + Assert.AreEqual(1, results[1].DatarowIndex); + Assert.AreEqual(2, results[2].DatarowIndex); } [TestMethodV1] @@ -584,11 +582,9 @@ public void RunTestMethodShoudlRunOnlyDataSourceTestsWhenBothDataSourceAndDataRo var results = testMethodRunner.RunTestMethod(); // check for datarowIndex as only DataSource Tests are Run - // 1st is parent result. - Assert.AreEqual(-1, results[0].DatarowIndex); - Assert.AreEqual(0, results[1].DatarowIndex); - Assert.AreEqual(1, results[2].DatarowIndex); - Assert.AreEqual(2, results[3].DatarowIndex); + Assert.AreEqual(0, results[0].DatarowIndex); + Assert.AreEqual(1, results[1].DatarowIndex); + Assert.AreEqual(2, results[2].DatarowIndex); } [TestMethodV1] @@ -612,9 +608,8 @@ public void RunTestMethodShouldFillInDisplayNameWithDataRowDisplayNameIfProvided var results = testMethodRunner.RunTestMethod(); - // 1st results should be parent result. - Assert.AreEqual(2, results.Length); - Assert.AreEqual("DataRowTestDisplayName", results[1].DisplayName); + Assert.AreEqual(1, results.Length); + Assert.AreEqual("DataRowTestDisplayName", results[0].DisplayName); } [TestMethodV1] @@ -637,9 +632,8 @@ public void RunTestMethodShouldFillInDisplayNameWithDataRowArgumentsIfNoDisplayN var results = testMethodRunner.RunTestMethod(); - // 1st results should be parent result. - Assert.AreEqual(2, results.Length); - Assert.AreEqual("DummyTestMethod (2,DummyString)", results[1].DisplayName); + Assert.AreEqual(1, results.Length); + Assert.AreEqual("DummyTestMethod (2,DummyString)", results[0].DisplayName); } [TestMethodV1] @@ -664,219 +658,8 @@ public void RunTestMethodShouldSetResultFilesIfPresentForDataDrivenTests() this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); var results = testMethodRunner.RunTestMethod(); + CollectionAssert.Contains(results[0].ResultFiles.ToList(), "C:\\temp.txt"); CollectionAssert.Contains(results[1].ResultFiles.ToList(), "C:\\temp.txt"); - CollectionAssert.Contains(results[2].ResultFiles.ToList(), "C:\\temp.txt"); - } - - [TestMethodV1] - public void RunTestMethodShouldReturnParentResultForDataSourceDataDrivenTests() - { - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => new UTF.TestResult()); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false); - - UTF.DataSourceAttribute dataSourceAttribute = new UTF.DataSourceAttribute("DummyConnectionString", "DummyTableName"); - - var attribs = new Attribute[] { dataSourceAttribute }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - this.testablePlatformServiceProvider.MockTestDataSource.Setup(tds => tds.GetData(testMethodInfo, this.testContextImplementation)).Returns(new object[] { 1, 2, 3 }); - - var results = testMethodRunner.RunTestMethod(); - - // check for parent result - Assert.AreEqual(4, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - } - - [TestMethodV1] - public void RunTestMethodShouldReturnParentResultForDataSourceDataDrivenTestsContainingSingleTest() - { - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => new UTF.TestResult()); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false); - - UTF.DataSourceAttribute dataSourceAttribute = new UTF.DataSourceAttribute("DummyConnectionString", "DummyTableName"); - - var attribs = new Attribute[] { dataSourceAttribute }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - this.testablePlatformServiceProvider.MockTestDataSource.Setup(tds => tds.GetData(testMethodInfo, this.testContextImplementation)).Returns(new object[] { 1 }); - - var results = testMethodRunner.RunTestMethod(); - - // Parent result should exist. - Assert.AreEqual(2, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - } - - [TestMethodV1] - public void RunTestMethodShouldReturnParentResultForDataRowDataDrivenTests() - { - UTF.TestResult testResult = new UTF.TestResult - { - ResultFiles = new List() { "C:\\temp.txt" } - }; - - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => testResult); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false, this.mockReflectHelper.Object); - - int dummyIntData1 = 1; - int dummyIntData2 = 2; - UTF.DataRowAttribute dataRowAttribute1 = new UTF.DataRowAttribute(dummyIntData1); - UTF.DataRowAttribute dataRowAttribute2 = new UTF.DataRowAttribute(dummyIntData2); - - var attribs = new Attribute[] { dataRowAttribute1, dataRowAttribute2 }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - - var results = testMethodRunner.RunTestMethod(); - CollectionAssert.Contains(results[1].ResultFiles.ToList(), "C:\\temp.txt"); - CollectionAssert.Contains(results[2].ResultFiles.ToList(), "C:\\temp.txt"); - - // Parent result should exist. - Assert.AreEqual(3, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(results[0].ExecutionId, results[2].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[2].ParentExecId); - } - - [TestMethodV1] - public void RunTestMethodShouldReturnParentResultForDataRowDataDrivenTestsContainingSingleTest() - { - UTF.TestResult testResult = new UTF.TestResult - { - ResultFiles = new List() { "C:\\temp.txt" } - }; - - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => testResult); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false, this.mockReflectHelper.Object); - - int dummyIntData1 = 1; - UTF.DataRowAttribute dataRowAttribute1 = new UTF.DataRowAttribute(dummyIntData1); - - var attribs = new Attribute[] { dataRowAttribute1 }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - - var results = testMethodRunner.RunTestMethod(); - CollectionAssert.Contains(results[1].ResultFiles.ToList(), "C:\\temp.txt"); - - // Parent result should exist. - Assert.AreEqual(2, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - } - - [TestMethodV1] - public void RunTestMethodShouldNotReturnParentResultForNonDataDrivenTests() - { - var testMethodAttributeMock = new Mock(); - testMethodAttributeMock.Setup(_ => _.Execute(It.IsAny())).Returns(new[] - { - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Passed }, - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Failed } - }); - - var localTestMethodOptions = new TestMethodOptions - { - Timeout = 200, - Executor = testMethodAttributeMock.Object, - TestContext = this.testContextImplementation, - ExpectedException = null - }; - - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, localTestMethodOptions, null); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false); - - var results = testMethodRunner.Execute(); - Assert.AreEqual(2, results.Length); - - // Parent result should not exists as its not data driven test. - Assert.AreEqual(AdapterTestOutcome.Passed, results[0].Outcome); - Assert.AreEqual(AdapterTestOutcome.Failed, results[1].Outcome); - } - - [TestMethodV1] - public void RunTestMethodShouldSetParentResultOutcomeProperlyForDataSourceDataDrivenTests() - { - var testExecutedCount = 0; - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => - { - return (testExecutedCount++ == 0) ? - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Failed } : - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Passed }; - }); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false); - - UTF.DataSourceAttribute dataSourceAttribute = new UTF.DataSourceAttribute("DummyConnectionString", "DummyTableName"); - - var attribs = new Attribute[] { dataSourceAttribute }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - this.testablePlatformServiceProvider.MockTestDataSource.Setup(tds => tds.GetData(testMethodInfo, this.testContextImplementation)).Returns(new object[] { 1, 2, 3 }); - - var results = testMethodRunner.RunTestMethod(); - - // check for parent result - Assert.AreEqual(4, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - - // Check for aggregate outcome. - Assert.AreEqual(AdapterTestOutcome.Failed, results[0].Outcome); - Assert.AreEqual(AdapterTestOutcome.Failed, results[1].Outcome); - Assert.AreEqual(AdapterTestOutcome.Passed, results[2].Outcome); - Assert.AreEqual(AdapterTestOutcome.Passed, results[3].Outcome); - } - - [TestMethodV1] - public void RunTestMethodShouldSetParentResultOutcomeProperlyForDataRowDataDrivenTests() - { - var testExecutedCount = 0; - var testMethodInfo = new TestableTestmethodInfo(this.methodInfo, this.testClassInfo, this.testMethodOptions, () => - { - return (testExecutedCount++ == 0) ? - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Failed } : - new UTF.TestResult { Outcome = UTF.UnitTestOutcome.Passed }; - }); - var testMethodRunner = new TestMethodRunner(testMethodInfo, this.testMethod, this.testContextImplementation, false, this.mockReflectHelper.Object); - - int dummyIntData1 = 1; - int dummyIntData2 = 2; - UTF.DataRowAttribute dataRowAttribute1 = new UTF.DataRowAttribute(dummyIntData1); - UTF.DataRowAttribute dataRowAttribute2 = new UTF.DataRowAttribute(dummyIntData2); - - var attribs = new Attribute[] { dataRowAttribute1, dataRowAttribute2 }; - - // Setup mocks - this.testablePlatformServiceProvider.MockReflectionOperations.Setup(rf => rf.GetCustomAttributes(this.methodInfo, It.IsAny(), It.IsAny())).Returns(attribs); - - var results = testMethodRunner.RunTestMethod(); - - // Parent result should exist. - Assert.AreEqual(3, results.Length); - Assert.AreEqual(results[0].ExecutionId, results[1].ParentExecId); - Assert.AreEqual(results[0].ExecutionId, results[2].ParentExecId); - Assert.AreEqual(Guid.Empty, results[0].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[1].ParentExecId); - Assert.AreNotEqual(Guid.Empty, results[2].ParentExecId); - - // Check for aggregate outcome. - Assert.AreEqual(AdapterTestOutcome.Failed, results[0].Outcome); - Assert.AreEqual(AdapterTestOutcome.Failed, results[1].Outcome); - Assert.AreEqual(AdapterTestOutcome.Passed, results[2].Outcome); } #region Test data diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TypeCacheTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TypeCacheTests.cs index ea7be9e8c..70d9436c4 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TypeCacheTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/TypeCacheTests.cs @@ -495,8 +495,8 @@ public void GetTestMethodInfoShouldCacheBaseClassInitializeAttributes() Assert.AreEqual(1, this.typeCache.ClassInfoCache.Count()); Assert.AreEqual(1, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.Count); - Assert.IsNull(this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.First().Item2, "No base class cleanup"); - Assert.AreEqual(baseType.GetMethod("AssemblyInit"), this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.First().Item1); + Assert.IsNull(this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.Peek().Item2, "No base class cleanup"); + Assert.AreEqual(baseType.GetMethod("AssemblyInit"), this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.Peek().Item1); } [TestMethodV1] @@ -543,8 +543,8 @@ public void GetTestMethodInfoShouldCacheBaseClassCleanupAttributes() Assert.AreEqual(1, this.typeCache.ClassInfoCache.Count()); Assert.AreEqual(1, this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.Count); - Assert.IsNull(this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.First().Item1, "No base class init"); - Assert.AreEqual(baseType.GetMethod("AssemblyCleanup"), this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.First().Item2); + Assert.IsNull(this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.Peek().Item1, "No base class init"); + Assert.AreEqual(baseType.GetMethod("AssemblyCleanup"), this.typeCache.ClassInfoCache.First().BaseClassInitAndCleanupMethods.Peek().Item2); } [TestMethodV1] @@ -610,8 +610,8 @@ public void GetTestMethodInfoShouldCacheBaseClassInitAndCleanupAttributes() Assert.AreEqual(type.GetMethod("AssemblyCleanup"), this.typeCache.ClassInfoCache.ToArray()[0].ClassCleanupMethod); Assert.AreEqual(1, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.Count); - Assert.AreEqual(baseInitializeMethod, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.First().Item1); - Assert.AreEqual(baseCleanupMethod, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.First().Item2); + Assert.AreEqual(baseInitializeMethod, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.Peek().Item1); + Assert.AreEqual(baseCleanupMethod, this.typeCache.ClassInfoCache.ToArray()[0].BaseClassInitAndCleanupMethods.Peek().Item2); } [TestMethodV1] @@ -1181,8 +1181,7 @@ public void GetTestMethodInfoShouldNotAddDuplicateTestPropertiesToTestContext() Assert.IsNotNull(testMethodInfo); // Verify that the first value gets set. - object value; - Assert.IsTrue(((IDictionary)testContext.Properties).TryGetValue("WhoAmI", out value)); + Assert.IsTrue(((IDictionary)testContext.Properties).TryGetValue("WhoAmI", out var value)); Assert.AreEqual("Me", value); } diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/UnitTestRunnerTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/UnitTestRunnerTests.cs index e7795818a..b4efbb5be 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/UnitTestRunnerTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Execution/UnitTestRunnerTests.cs @@ -224,8 +224,8 @@ public void RunSingleTestShouldCallAssemblyInitializeAndClassInitializeMethodsIn It.IsAny())).Returns(true); var validator = 1; - DummyTestClassWithInitializeMethods.AssemblyInitializeMethodBody = () => { validator = validator << 2; }; - DummyTestClassWithInitializeMethods.ClassInitializeMethodBody = () => { validator = validator >> 2; }; + DummyTestClassWithInitializeMethods.AssemblyInitializeMethodBody = () => { validator <<= 2; }; + DummyTestClassWithInitializeMethods.ClassInitializeMethodBody = () => { validator >>= 2; }; this.unitTestRunner.RunSingleTest(testMethod, this.testRunParameters); @@ -273,7 +273,7 @@ public void RunCleanupShouldReturnCleanupResultsForAssemblyAndClassCleanupMethod Assert.AreEqual(1, assemblyCleanupCount); Assert.AreEqual(1, classCleanupCount); - Assert.AreEqual(2, cleanupresult.Warnings.Count()); + Assert.AreEqual(2, cleanupresult.Warnings.Count); Assert.IsTrue(cleanupresult.Warnings.All(w => w.Contains("NotImplemented"))); } @@ -294,7 +294,7 @@ public void RunCleanupShouldReturnCleanupResultsWithDebugTraceLogsSetIfDebugTrac this.unitTestRunner.RunSingleTest(testMethod, this.testRunParameters); var cleanupresult = this.unitTestRunner.RunCleanup(); - Assert.AreEqual(cleanupresult.DebugTrace, "DummyTrace"); + Assert.AreEqual("DummyTrace", cleanupresult.DebugTrace); } [TestMethodV1] diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/ExceptionExtensionsTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/ExceptionExtensionsTests.cs index 5b4209afa..05251d0a5 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/ExceptionExtensionsTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/ExceptionExtensionsTests.cs @@ -177,10 +177,8 @@ public void IsUnitTestAssertExceptionReturnsTrueIfExceptionIsAssertException() { var exception = new UTF.AssertInconclusiveException(); UTF.UnitTestOutcome outcome = UTF.UnitTestOutcome.Unknown; - string exceptionMessage = null; - StackTraceInformation stackTraceInfo = null; - Assert.IsTrue(exception.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out stackTraceInfo)); + Assert.IsTrue(exception.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var stackTraceInfo)); } [TestMethod] @@ -188,10 +186,8 @@ public void IsUnitTestAssertExceptionReturnsFalseIfExceptionIsNotAssertException { var exception = new NotImplementedException(); UTF.UnitTestOutcome outcome = UTF.UnitTestOutcome.Unknown; - string exceptionMessage = null; - StackTraceInformation stackTraceInfo = null; - Assert.IsFalse(exception.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out stackTraceInfo)); + Assert.IsFalse(exception.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var stackTraceInfo)); } [TestMethod] @@ -199,10 +195,8 @@ public void IsUnitTestAssertExceptionSetsOutcomeAsInconclusiveIfAssertInconclusi { var exception = new UTF.AssertInconclusiveException("Dummy Message", new NotImplementedException("notImplementedException")); UTF.UnitTestOutcome outcome = UTF.UnitTestOutcome.Unknown; - string exceptionMessage = null; - StackTraceInformation stackTraceInfo = null; - exception.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out stackTraceInfo); + exception.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var stackTraceInfo); Assert.AreEqual(UTF.UnitTestOutcome.Inconclusive, outcome); Assert.AreEqual("Dummy Message", exceptionMessage); @@ -213,10 +207,8 @@ public void IsUnitTestAssertExceptionSetsOutcomeAsFailedIfAssertFailedException( { var exception = new UTF.AssertFailedException("Dummy Message", new NotImplementedException("notImplementedException")); UTF.UnitTestOutcome outcome = UTF.UnitTestOutcome.Unknown; - string exceptionMessage = null; - StackTraceInformation stackTraceInfo = null; - exception.TryGetUnitTestAssertException(out outcome, out exceptionMessage, out stackTraceInfo); + exception.TryGetUnitTestAssertException(out outcome, out var exceptionMessage, out var stackTraceInfo); Assert.AreEqual(UTF.UnitTestOutcome.Failed, outcome); Assert.AreEqual("Dummy Message", exceptionMessage); diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/MethodInfoExtensionsTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/MethodInfoExtensionsTests.cs index c9d27f5e4..ae9adf8f6 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/MethodInfoExtensionsTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Extensions/MethodInfoExtensionsTests.cs @@ -454,7 +454,7 @@ public bool DummyMethod(int x, int y) public async Task DummyAsyncMethod(int x, int y) { - await DummyAsyncMethodBody(x, y); + await DummyAsyncMethodBody(x, y).ConfigureAwait(false); } public void PublicMethodWithParameters(int x, int y) @@ -485,7 +485,7 @@ public static void PublicStaticMethodWithTC(UTFExtension.TestContext tc) public static async Task PublicStaticAsyncTaskMethodWithTC(UTFExtension.TestContext tc) { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public static Task PublicStaticNonAsyncTaskMethodWithTC(UTFExtension.TestContext tc) @@ -495,7 +495,7 @@ public static Task PublicStaticNonAsyncTaskMethodWithTC(UTFExtension.TestContext public static async void PublicStaticAsyncVoidMethodWithTC(UTFExtension.TestContext tc) { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public static int PublicStaticMethodReturningInt() @@ -505,12 +505,12 @@ public static int PublicStaticMethodReturningInt() public static async Task PublicStaticAsyncTaskMethod() { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public static async void PublicStaticAsyncVoidMethod() { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public static Task PublicStaticNonAsyncTaskMethod() @@ -539,12 +539,12 @@ public int PublicMethodReturningInt() public async Task PublicAsyncTaskMethod() { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public async void PublicAsyncVoidMethod() { - await Task.FromResult(true); + await Task.FromResult(true).ConfigureAwait(false); } public Task PublicNonAsyncTaskMethod() diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Helpers/DataSerializationHelperTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Helpers/DataSerializationHelperTests.cs new file mode 100644 index 000000000..1123fc8d6 --- /dev/null +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/Helpers/DataSerializationHelperTests.cs @@ -0,0 +1,80 @@ +// Copyright (c) Microsoft Corporation. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. + +namespace Microsoft.VisualStudio.TestPlatform.MSTestAdapter.UnitTests +{ + extern alias FrameworkV1; + extern alias FrameworkV2; + + using System; + using FluentAssertions; + using Microsoft.VisualStudio.TestPlatform.MSTest.TestAdapter.Helpers; + + using TestableImplementations; + using Assert = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.Assert; + using CollectionAssert = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.CollectionAssert; + using TestClass = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.TestClassAttribute; + using TestCleanup = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.TestCleanupAttribute; + using TestInitialize = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.TestInitializeAttribute; + using TestMethod = FrameworkV1::Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute; + using UTF = FrameworkV2::Microsoft.VisualStudio.TestTools.UnitTesting; + + [TestClass] + public class DataSerializationHelperTests + { + [TestMethod] + public void DataSerializerShouldRoundTripDateTimeOffset() + { + var source = new DateTimeOffset(628381323438126060, TimeSpan.FromHours(-8)); + + var actual = DataSerializationHelper.Deserialize( + DataSerializationHelper.Serialize(new object[] { source })); + + actual.Should().HaveCount(1); + actual[0].Should().BeOfType(); + actual[0].As().Should().Be(source); + } + + [TestMethod] + public void DataSerializerShouldRoundTripDateTime() + { + var source = new DateTime(628381323438126060); + + var actual = DataSerializationHelper.Deserialize( + DataSerializationHelper.Serialize(new object[] { source })); + + actual.Should().HaveCount(1); + actual[0].Should().BeOfType(); + actual[0].As().Should().Be(source); + actual[0].As().Kind.Should().Be(source.Kind); + } + + [TestMethod] + public void DataSerializerShouldRoundTripDateTimeOfKindLocal() + { + var source = new DateTime(628381323438126060, DateTimeKind.Local); + + var actual = DataSerializationHelper.Deserialize( + DataSerializationHelper.Serialize(new object[] { source })); + + actual.Should().HaveCount(1); + actual[0].Should().BeOfType(); + actual[0].As().Should().Be(source); + actual[0].As().Kind.Should().Be(source.Kind); + } + + [TestMethod] + public void DataSerializerShouldRoundTripDateTimeOfKindUtc() + { + var source = new DateTime(628381323438126060, DateTimeKind.Utc); + + var actual = DataSerializationHelper.Deserialize( + DataSerializationHelper.Serialize(new object[] { source })); + + actual.Should().HaveCount(1); + actual[0].Should().BeOfType(); + actual[0].As().Should().Be(source); + actual[0].As().Kind.Should().Be(source.Kind); + } + } +} diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTest.CoreAdapter.Unit.Tests.csproj b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTest.CoreAdapter.Unit.Tests.csproj index 666bbf7ae..8fc2c5f13 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTest.CoreAdapter.Unit.Tests.csproj +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTest.CoreAdapter.Unit.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {1CEB5743-70BF-475E-91BC-0AEBD63835B7} Library @@ -13,8 +11,8 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion False UnitTest 1685 @@ -34,51 +32,63 @@ prompt 4 + - - $(TestFxRoot)packages\Castle.Core.3.3.3\lib\net45\Castle.Core.dll - True - - - ..\..\..\packages\FluentAssertions.5.10.3\lib\net45\FluentAssertions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Microsoft.TestPlatform.AdapterUtilities.$(TestPlatformVersion)\lib\netstandard2.0\Microsoft.TestPlatform.AdapterUtilities.dll - - - $(TestFxRoot)packages\Moq.4.5.21\lib\net45\Moq.dll - True - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - - - ..\..\..\packages\System.ValueTuple.4.4.0\lib\netstandard1.0\System.ValueTuple.dll - + FrameworkV1 True + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + True + + + {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} + PlatformServices.Portable + True + + + {98ba6d2c-1f3d-4636-8e1d-d4932b7a253d} + MSTest.CoreAdapter + True + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + FrameworkV2 + True + + + {6C9FE494-8315-4667-B3F6-75DC62A62319} + Extension.Core + FrameworkV2CoreExtension + True + + + {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} + MSTest.CoreAdapter.TestUtilities + True + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + @@ -106,6 +116,7 @@ + @@ -120,45 +131,10 @@ - - + - - - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - True - - - {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} - PlatformServices.Portable - True - - - {98ba6d2c-1f3d-4636-8e1d-d4932b7a253d} - MSTest.CoreAdapter - True - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - FrameworkV2 - True - - - {6C9FE494-8315-4667-B3F6-75DC62A62319} - Extension.Core - FrameworkV2CoreExtension - True - - - {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} - MSTest.CoreAdapter.TestUtilities - True - + - + \ No newline at end of file diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestDiscovererTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestDiscovererTests.cs index 395e8c1f8..c910ee5f0 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestDiscovererTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestDiscovererTests.cs @@ -71,7 +71,7 @@ public void MSTestDiscovererHasXapAsFileExtension() { IEnumerable attributes = typeof(MSTestDiscoverer).GetTypeInfo().GetCustomAttributes(typeof(FileExtensionAttribute)).Cast(); Assert.IsNotNull(attributes); - Assert.AreEqual(1, attributes.Where(attribute => attribute.FileExtension == ".xap").Count()); + Assert.AreEqual(1, attributes.Count(attribute => attribute.FileExtension == ".xap")); } [TestMethod] @@ -79,7 +79,7 @@ public void MSTestDiscovererHasAppxAsFileExtension() { IEnumerable attributes = typeof(MSTestDiscoverer).GetTypeInfo().GetCustomAttributes(typeof(FileExtensionAttribute)).Cast(); Assert.IsNotNull(attributes); - Assert.AreEqual(1, attributes.Where(attribute => attribute.FileExtension == ".appx").Count()); + Assert.AreEqual(1, attributes.Count(attribute => attribute.FileExtension == ".appx")); } [TestMethod] @@ -87,7 +87,7 @@ public void MSTestDiscovererHasDllAsFileExtension() { IEnumerable attributes = typeof(MSTestDiscoverer).GetTypeInfo().GetCustomAttributes(typeof(FileExtensionAttribute)).Cast(); Assert.IsNotNull(attributes); - Assert.AreEqual(1, attributes.Where(attribute => attribute.FileExtension == ".dll").Count()); + Assert.AreEqual(1, attributes.Count(attribute => attribute.FileExtension == ".dll")); } [TestMethod] @@ -95,7 +95,7 @@ public void MSTestDiscovererHasExeAsFileExtension() { IEnumerable attributes = typeof(MSTestDiscoverer).GetTypeInfo().GetCustomAttributes(typeof(FileExtensionAttribute)).Cast(); Assert.IsNotNull(attributes); - Assert.AreEqual(1, attributes.Where(attribute => attribute.FileExtension == ".exe").Count()); + Assert.AreEqual(1, attributes.Count(attribute => attribute.FileExtension == ".exe")); } [TestMethod] diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestSettingsTests.cs b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestSettingsTests.cs index 61d031aeb..752487788 100644 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestSettingsTests.cs +++ b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/MSTestSettingsTests.cs @@ -600,7 +600,7 @@ public void GetSettingsShouldOnlyPassTheElementSubTreeToPlatformService() "; - string expectedrunSettingxml = @"True"; + string expectedrunSettingxml = "True"; string observedxml = null; this.testablePlatformServiceProvider.MockSettingsProvider.Setup(sp => sp.Load(It.IsAny())) @@ -640,13 +640,12 @@ public void GetSettingsShouldBeAbleToReadSettingsAfterThePlatformServiceReadsIts reader.Read(); while (reader.NodeType == XmlNodeType.Element) { - bool result; string elementName = reader.Name.ToUpperInvariant(); switch (elementName) { case "DUMMYPLATFORMSPECIFICSETTING": { - if (bool.TryParse(reader.ReadInnerXml(), out result)) + if (bool.TryParse(reader.ReadInnerXml(), out var result)) { dummyPlatformSpecificSetting = result; } @@ -697,13 +696,12 @@ public void GetSettingsShouldBeAbleToReadSettingsIfThePlatformServiceDoesNotUnde reader.Read(); while (reader.NodeType == XmlNodeType.Element) { - bool result; string elementName = reader.Name.ToUpperInvariant(); switch (elementName) { case "DUMMYPLATFORMSPECIFICSETTING": { - if (bool.TryParse(reader.ReadInnerXml(), out result)) + if (bool.TryParse(reader.ReadInnerXml(), out var result)) { dummyPlatformSpecificSetting = result; } @@ -806,13 +804,12 @@ public void GetSettingsShouldWorkIfThereAreCommentsInTheXML() reader.Read(); while (reader.NodeType == XmlNodeType.Element) { - bool result; string elementName = reader.Name.ToUpperInvariant(); switch (elementName) { case "DUMMYPLATFORMSPECIFICSETTING": { - if (bool.TryParse(reader.ReadInnerXml(), out result)) + if (bool.TryParse(reader.ReadInnerXml(), out var result)) { dummyPlatformSpecificSetting = result; } diff --git a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/packages.config b/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/packages.config deleted file mode 100644 index 73a75bf39..000000000 --- a/test/UnitTests/MSTest.CoreAdapter.Unit.Tests/packages.config +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - - - - - - \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/App.config b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/App.config index d47716623..fb3c2554d 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/App.config +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/App.config @@ -1,18 +1,18 @@ - + - - + + - - + + - + diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Deployment/AssemblyLoadWorkerTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Deployment/AssemblyLoadWorkerTests.cs index 76c0546e5..d34d4fd7f 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Deployment/AssemblyLoadWorkerTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Deployment/AssemblyLoadWorkerTests.cs @@ -40,10 +40,9 @@ public void GetFullPathToDependentAssembliesShouldReturnV1FrameworkAssembly() .Returns(new TestableAssembly(v1AssemblyName.Name)); var worker = new AssemblyLoadWorker(mockAssemblyUtility.Object); - IList warnings; // Act. - var dependentAssemblies = worker.GetFullPathToDependentAssemblies("C:\\temp\\test3424.dll", out warnings); + var dependentAssemblies = worker.GetFullPathToDependentAssemblies("C:\\temp\\test3424.dll", out var warnings); // Assert. var utfassembly = Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "Microsoft.VisualStudio.QualityTools.UnitTestFramework.dll"); @@ -103,10 +102,9 @@ public void GetFullPathToDependentAssembliesShouldReturnV1FrameworkReferencedInA }); var worker = new AssemblyLoadWorker(mockAssemblyUtility.Object); - IList warnings; // Act. - var dependentAssemblies = worker.GetFullPathToDependentAssemblies("C:\\temp\\test3424.dll", out warnings); + var dependentAssemblies = worker.GetFullPathToDependentAssemblies("C:\\temp\\test3424.dll", out var warnings); // Assert. var utfassembly = Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "Microsoft.VisualStudio.QualityTools.UnitTestFramework.dll"); diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/PlatformServices.Desktop.Unit.Tests.csproj b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/PlatformServices.Desktop.Unit.Tests.csproj index 2eec8729e..d289fcdf0 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/PlatformServices.Desktop.Unit.Tests.csproj +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/PlatformServices.Desktop.Unit.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {599833DC-EC5A-40CA-B5CF-DEF719548EEF} Library @@ -13,8 +11,8 @@ v4.5.2 512 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest @@ -35,74 +33,84 @@ prompt 4 + - - ..\..\..\packages\Castle.Core.3.3.3\lib\net45\Castle.Core.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Moq.4.5.21\lib\net45\Moq.dll - True - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - + + + FrameworkV1 - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - - + + + {b0fce474-14bc-449a-91ea-a433342c0d63} + PlatformServices.Desktop + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + + + {a7ea583b-a2b0-47da-a058-458f247c7575} + Extension.Desktop + FrameworkV2Extension + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + FrameworkV2 + + + {F81C7549-E3A3-4770-AC3F-3BC7356E61E8} + MSTest.CoreAdapter.TestUtilities + + - + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + + + Deployment\ns10DeploymentItemTests.cs - + Deployment\ns10TestRunDirectoriesTests.cs - + Extensions\ns10ExceptionExtensionsTests.cs - + Services\ns10MSTestAdapterSettingsTests.cs - + Utilities\ns10DeploymentUtilityTests.cs - + Utilities\ns10FileUtilityTests.cs - + Services\ns13TraceListenerManagerTests.cs - + Services\ns13TraceListenerTests.cs - + Services\ns13MSTestSettingsProviderTests.cs - + Services\ns13TestDeploymentTests.cs - + Utilities\ns13DeploymentItemUtilityTests.cs - + Utilities\ns13ReflectionUtilityTests.cs @@ -121,43 +129,17 @@ - - + + + Designer + + Always Designer - - - Designer - - - - - - {b0fce474-14bc-449a-91ea-a433342c0d63} - PlatformServices.Desktop - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - - - {a7ea583b-a2b0-47da-a058-458f247c7575} - Extension.Desktop - FrameworkV2Extension - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - FrameworkV2 - - - {F81C7549-E3A3-4770-AC3F-3BC7356E61E8} - MSTest.CoreAdapter.TestUtilities - - + - + \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopFileOperationsTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopFileOperationsTests.cs index b02a82db6..013f5e543 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopFileOperationsTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopFileOperationsTests.cs @@ -45,14 +45,12 @@ public void CreateNavigationSessionShouldReturnDiaSession() public void GetNavigationDataShouldReturnDataFromNavigationSession() { var diaSession = this.fileOperations.CreateNavigationSession(Assembly.GetExecutingAssembly().Location); - int minLineNumber; - string fileName; this.fileOperations.GetNavigationData( diaSession, typeof(DesktopFileOperationsTests).FullName, "GetNavigationDataShouldReturnDataFromNavigationSession", - out minLineNumber, - out fileName); + out var minLineNumber, + out var fileName); Assert.AreNotEqual(-1, minLineNumber); Assert.IsNotNull(fileName); @@ -61,14 +59,12 @@ public void GetNavigationDataShouldReturnDataFromNavigationSession() [TestMethod] public void GetNavigationDataShouldNotThrowOnNullNavigationSession() { - int minLineNumber; - string fileName; this.fileOperations.GetNavigationData( null, typeof(DesktopFileOperationsTests).FullName, "GetNavigationDataShouldReturnDataFromNavigationSession", - out minLineNumber, - out fileName); + out var minLineNumber, + out var fileName); Assert.AreEqual(-1, minLineNumber); Assert.IsNull(fileName); diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestContextImplTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestContextImplTests.cs index e164d16f5..6d3faa6e4 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestContextImplTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestContextImplTests.cs @@ -137,9 +137,7 @@ public void TryGetPropertyValueShouldReturnTrueIfPropertyIsPresent() this.testContextImplementation = new TestContextImplementation(this.testMethod.Object, new System.IO.StringWriter(), this.properties); - object propValue; - - Assert.IsTrue(this.testContextImplementation.TryGetPropertyValue("TestName", out propValue)); + Assert.IsTrue(this.testContextImplementation.TryGetPropertyValue("TestName", out var propValue)); Assert.AreEqual("M", propValue); } @@ -148,9 +146,7 @@ public void TryGetPropertyValueShouldReturnFalseIfPropertyIsNotPresent() { this.testContextImplementation = new TestContextImplementation(this.testMethod.Object, new System.IO.StringWriter(), this.properties); - object propValue; - - Assert.IsFalse(this.testContextImplementation.TryGetPropertyValue("Random", out propValue)); + Assert.IsFalse(this.testContextImplementation.TryGetPropertyValue("Random", out var propValue)); Assert.IsNull(propValue); } diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDataSourceTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDataSourceTests.cs index e69e75cbf..c412c718b 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDataSourceTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDataSourceTests.cs @@ -89,15 +89,15 @@ public DesktopTestFrameworkV2.TestContext TestContext [TestFrameworkV2.TestMethod] public void PassingTest() { - Assert.AreEqual(this.testContextInstance.DataRow["adapter"].ToString(), "v1"); - Assert.AreEqual(this.testContextInstance.DataRow["targetPlatform"].ToString(), "x86"); + Assert.AreEqual("v1", this.testContextInstance.DataRow["adapter"].ToString()); + Assert.AreEqual("x86", this.testContextInstance.DataRow["targetPlatform"].ToString()); this.TestContext.AddResultFile("C:\\temp.txt"); } [TestFrameworkV2.TestMethod] public void FailingTest() { - Assert.AreEqual(this.testContextInstance.DataRow["configuration"].ToString(), "Release"); + Assert.AreEqual("Release", this.testContextInstance.DataRow["configuration"].ToString()); } } diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDeploymentTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDeploymentTests.cs index 8a6f4bea9..292beaaa4 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDeploymentTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Services/DesktopTestDeploymentTests.cs @@ -54,11 +54,10 @@ public void TestInit() [TestMethod] public void DeployShouldDeployFilesInASourceAndReturnTrue() { - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(Assembly.GetExecutingAssembly().Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -79,13 +78,12 @@ public void DeployShouldDeployFilesInASourceAndReturnTrue() [TestMethod] public void DeployShouldDeployFilesInMultipleSourcesAndReturnTrue() { - TestRunDirectories testRunDirectories; var testCase1 = this.GetTestCase(Assembly.GetExecutingAssembly().Location); var sourceFile2 = Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "a.dll"); var testCase2 = this.GetTestCase(sourceFile2); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -113,11 +111,10 @@ public void DeployShouldDeployFilesInMultipleSourcesAndReturnTrue() [TestMethod] public void DeployShouldCreateDeploymentDirectories() { - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(DesktopTestDeploymentTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Utilities/DesktopDeploymentUtilityTests.cs b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Utilities/DesktopDeploymentUtilityTests.cs index c80f7a8d1..0f7a023d1 100644 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Utilities/DesktopDeploymentUtilityTests.cs +++ b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/Utilities/DesktopDeploymentUtilityTests.cs @@ -92,8 +92,7 @@ public void DeployShouldReturnFalseWhenNoDeploymentItemsOnTestCase() [TestMethod] public void DeployShouldDeploySourceAndItsConfigFile() { - TestRunDirectories testRunDirectories; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !(s.EndsWith(".dll") || s.EndsWith(".config"))))).Returns(true); @@ -139,8 +138,7 @@ public void DeployShouldDeployDependentFiles() { var dependencyFile = "C:\\temp\\dependency.dll"; - TestRunDirectories testRunDirectories; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !(s.EndsWith(".dll") || s.EndsWith(".config"))))).Returns(true); @@ -176,8 +174,7 @@ public void DeployShouldDeployDependentFiles() [TestMethod] public void DeployShouldDeploySatelliteAssemblies() { - TestRunDirectories testRunDirectories; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); var assemblyFullPath = Assembly.GetExecutingAssembly().Location; var satelliteFullPath = Path.Combine(Path.GetDirectoryName(assemblyFullPath), "de", "satellite.dll"); @@ -215,12 +212,11 @@ public void DeployShouldDeploySatelliteAssemblies() [TestMethod] public void DeployShouldNotDeployIfOutputDirectoryIsInvalid() { - TestRunDirectories testRunDirectories; var assemblyFullPath = Assembly.GetExecutingAssembly().Location; var deploymentItemPath = "C:\\temp\\sample.dll"; var deploymentItemOutputDirectory = "..\\..\\out"; - var testCase = this.GetTestCaseAndTestRunDirectories(deploymentItemPath, deploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(deploymentItemPath, deploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !(s.EndsWith(".dll") || s.EndsWith(".config"))))).Returns(true); @@ -267,10 +263,9 @@ public void DeployShouldNotDeployIfOutputDirectoryIsInvalid() [TestMethod] public void DeployShouldDeployContentsOfADirectoryIfSpecified() { - TestRunDirectories testRunDirectories; var assemblyFullPath = Assembly.GetExecutingAssembly().Location; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); var content1 = Path.Combine(DefaultDeploymentItemPath, "directoryContents.dll"); var directoryContentFiles = new List { content1 }; @@ -312,8 +307,7 @@ public void DeployShouldDeployContentsOfADirectoryIfSpecified() [TestMethod] public void DeployShouldDeployPdbWithSourceIfPdbFileIsPresentInSourceDirectory() { - TestRunDirectories testRunDirectories; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !s.EndsWith(".dll")))).Returns(true); @@ -369,8 +363,7 @@ public void DeployShouldNotDeployPdbFileOfAssemblyIfPdbFileIsNotPresentInAssembl // Path for pdb file of dependent assembly if pdb file is present. var pdbFile = Path.ChangeExtension(dependencyFile, "pdb"); - TestRunDirectories testRunDirectories; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !s.EndsWith(".dll")))).Returns(true); diff --git a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/packages.config b/test/UnitTests/PlatformServices.Desktop.Unit.Tests/packages.config deleted file mode 100644 index 1438956c8..000000000 --- a/test/UnitTests/PlatformServices.Desktop.Unit.Tests/packages.config +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - - - - \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.NetCore.Unit.Tests/PlatformServices.NetCore.Unit.Tests.csproj b/test/UnitTests/PlatformServices.NetCore.Unit.Tests/PlatformServices.NetCore.Unit.Tests.csproj index 24dfdede8..26911a23b 100644 --- a/test/UnitTests/PlatformServices.NetCore.Unit.Tests/PlatformServices.NetCore.Unit.Tests.csproj +++ b/test/UnitTests/PlatformServices.NetCore.Unit.Tests/PlatformServices.NetCore.Unit.Tests.csproj @@ -1,9 +1,4 @@  - - ..\..\..\ - false - - netcoreapp2.1 NetCore @@ -12,47 +7,43 @@ MSTestAdapter.PlatformServices.NetCore.UnitTests true CS1685 + false + true - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + - - - - - + + + - + - + + + + + + + + + + + + + + + + + + + @@ -66,5 +57,4 @@ - diff --git a/test/UnitTests/PlatformServices.NetCore.Unit.Tests/Utilities/NetCoreDeploymentUtilityTests.cs b/test/UnitTests/PlatformServices.NetCore.Unit.Tests/Utilities/NetCoreDeploymentUtilityTests.cs index f048a99ca..0c355af39 100644 --- a/test/UnitTests/PlatformServices.NetCore.Unit.Tests/Utilities/NetCoreDeploymentUtilityTests.cs +++ b/test/UnitTests/PlatformServices.NetCore.Unit.Tests/Utilities/NetCoreDeploymentUtilityTests.cs @@ -76,12 +76,11 @@ public void DeployShouldReturnFalseWhenNoDeploymentItemsOnTestCase() [TestMethod] public void DeployShouldNotDeployIfOutputDirectoryIsInvalid() { - TestRunDirectories testRunDirectories; var assemblyFullPath = Assembly.GetEntryAssembly().Location; var deploymentItemPath = "C:\\temp\\sample.dll"; var deploymentItemOutputDirectory = "..\\..\\out"; - var testCase = this.GetTestCaseAndTestRunDirectories(deploymentItemPath, deploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(deploymentItemPath, deploymentItemOutputDirectory, out var testRunDirectories); // Setup mocks. this.mockFileUtility.Setup(fu => fu.DoesDirectoryExist(It.Is(s => !(s.EndsWith(".dll") || s.EndsWith(".config"))))).Returns(true); @@ -122,10 +121,9 @@ public void DeployShouldNotDeployIfOutputDirectoryIsInvalid() [TestMethod] public void DeployShouldDeployContentsOfADirectoryIfSpecified() { - TestRunDirectories testRunDirectories; var assemblyFullPath = Assembly.GetEntryAssembly().Location; - var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out testRunDirectories); + var testCase = this.GetTestCaseAndTestRunDirectories(DefaultDeploymentItemPath, DefaultDeploymentItemOutputDirectory, out var testRunDirectories); var content1 = Path.Combine(DefaultDeploymentItemPath, "directoryContents.dll"); var directoryContentFiles = new List { content1 }; diff --git a/test/UnitTests/PlatformServices.Portable.Unit.Tests/PlatformServices.Portable.Unit.Tests.csproj b/test/UnitTests/PlatformServices.Portable.Unit.Tests/PlatformServices.Portable.Unit.Tests.csproj index 0e00c1f40..f72cf66cc 100644 --- a/test/UnitTests/PlatformServices.Portable.Unit.Tests/PlatformServices.Portable.Unit.Tests.csproj +++ b/test/UnitTests/PlatformServices.Portable.Unit.Tests/PlatformServices.Portable.Unit.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {E3C630FE-AF89-4C95-B1B9-2409B1107208} Library @@ -12,8 +10,8 @@ MSTestAdapter.PlatformServices.Portable.UnitTests v4.5.2 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) False UnitTest 1685 @@ -33,95 +31,84 @@ prompt 4 + - - ..\..\..\packages\Castle.Core.3.3.3\lib\net45\Castle.Core.dll - True - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll - + + FrameworkV1 - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Moq.4.5.21\lib\net45\Moq.dll - True - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - - - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - + + + {BBC99A6B-4490-49DD-9C12-AF2C1E95576E} + PlatformServices.Interface + + + {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} + PlatformServices.Portable + + + {6c9fe494-8315-4667-b3f6-75dc62a62319} + Extension.Core + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + FrameworkV2 + + + {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} + MSTest.CoreAdapter.TestUtilities + + - + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + + + + Services\ns10AssemblyAttributes.cs - + Services\ns10FileOperationsTests.cs - + Services\ns10DiaSessionOperationsTests.cs - + Services\ns10ReflectionOperationsTests.cs - + Services\ns10SettingsProviderTests.cs - + Services\ns10TestContextImplementationTests.cs - + Services\ns10TestSourceHostTests.cs - + Services\ns10TestSourceTests.cs - + Services\ns10ThreadOperationsTests.cs - - + - - - - - {BBC99A6B-4490-49DD-9C12-AF2C1E95576E} - PlatformServices.Interface - - - {58bdd63d-5e58-4d23-bdf5-592e5e03d29d} - PlatformServices.Portable - - - {6c9fe494-8315-4667-b3f6-75dc62a62319} - Extension.Core - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - FrameworkV2 - - - {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} - MSTest.CoreAdapter.TestUtilities - + - + \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Portable.Unit.Tests/packages.config b/test/UnitTests/PlatformServices.Portable.Unit.Tests/packages.config deleted file mode 100644 index 637fb47db..000000000 --- a/test/UnitTests/PlatformServices.Portable.Unit.Tests/packages.config +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - - - - \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Services/ns13TestDeploymentTests.cs b/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Services/ns13TestDeploymentTests.cs index 82eef2e92..042d8b6fe 100644 --- a/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Services/ns13TestDeploymentTests.cs +++ b/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Services/ns13TestDeploymentTests.cs @@ -128,17 +128,16 @@ public void CleanupShouldNotDeleteDirectoriesIfRunDirectoiresIsNull() public void CleanupShouldNotDeleteDirectoriesIfRunSettingsSpecifiesSo() { string runSettingxml = - @"False"; + "False"; StringReader stringReader = new StringReader(runSettingxml); XmlReader reader = XmlReader.Create(stringReader, XmlRunSettingsUtilities.ReaderSettings); MSTestSettingsProvider mstestSettingsProvider = new MSTestSettingsProvider(); mstestSettingsProvider.Load(reader); - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(TestDeploymentTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -153,11 +152,10 @@ public void CleanupShouldNotDeleteDirectoriesIfRunSettingsSpecifiesSo() [TestMethod] public void CleanupShouldDeleteRootDeploymentDirectory() { - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(DeploymentUtilityTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -183,11 +181,10 @@ public void GetDeploymentDirectoryShouldReturnNullIfDeploymentDirectoryIsNull() [TestMethod] public void GetDeploymentDirectoryShouldReturnDeploymentOutputDirectory() { - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(TestDeploymentTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -220,7 +217,7 @@ public void DeployShouldReturnFalseWhenDeploymentEnabledSetToFalseButHasDeployme this.mockFileUtility.Object); string runSettingxml = - @"False"; + "False"; StringReader stringReader = new StringReader(runSettingxml); XmlReader reader = XmlReader.Create(stringReader, XmlRunSettingsUtilities.ReaderSettings); MSTestSettingsProvider mstestSettingsProvider = new MSTestSettingsProvider(); @@ -244,7 +241,7 @@ public void DeployShouldReturnFalseWhenDeploymentEnabledSetToFalseAndHasNoDeploy this.mockFileUtility.Object); string runSettingxml = - @"False"; + "False"; StringReader stringReader = new StringReader(runSettingxml); XmlReader reader = XmlReader.Create(stringReader, XmlRunSettingsUtilities.ReaderSettings); MSTestSettingsProvider mstestSettingsProvider = new MSTestSettingsProvider(); @@ -268,7 +265,7 @@ public void DeployShouldReturnFalseWhenDeploymentEnabledSetToTrueButHasNoDeploym this.mockFileUtility.Object); string runSettingxml = - @"True"; + "True"; StringReader stringReader = new StringReader(runSettingxml); XmlReader reader = XmlReader.Create(stringReader, XmlRunSettingsUtilities.ReaderSettings); MSTestSettingsProvider mstestSettingsProvider = new MSTestSettingsProvider(); @@ -300,7 +297,7 @@ public void DeployShouldReturnTrueWhenDeploymentEnabledSetToTrueAndHasDeployment this.mockFileUtility.Object); string runSettingxml = - @"True"; + "True"; StringReader stringReader = new StringReader(runSettingxml); XmlReader reader = XmlReader.Create(stringReader, XmlRunSettingsUtilities.ReaderSettings); MSTestSettingsProvider mstestSettingsProvider = new MSTestSettingsProvider(); @@ -369,11 +366,10 @@ public void GetDeploymentInformationShouldReturnAppBaseDirectoryIfRunDirectoryIs public void GetDeploymentInformationShouldReturnRunDirectoryInformationIfSourceIsNull() { // Arrange. - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(TestDeploymentTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); @@ -430,11 +426,10 @@ public void GetDeploymentInformationShouldReturnRunDirectoryInformationIfSourceI public void GetDeploymentInformationShouldReturnRunDirectoryInformationIfSourceIsNotNull() { // Arrange. - TestRunDirectories testRunDirectories; var testCase = this.GetTestCase(typeof(TestDeploymentTests).GetTypeInfo().Assembly.Location); // Setup mocks. - var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out testRunDirectories); + var testDeployment = this.CreateAndSetupDeploymentRelatedUtilities(out var testRunDirectories); var mockRunContext = new Mock(); mockRunContext.Setup(rc => rc.TestRunDirectory).Returns(testRunDirectories.RootDeploymentDirectory); diff --git a/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Utilities/ns13DeploymentItemUtilityTests.cs b/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Utilities/ns13DeploymentItemUtilityTests.cs index dd038907f..adfd360c8 100644 --- a/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Utilities/ns13DeploymentItemUtilityTests.cs +++ b/test/UnitTests/PlatformServices.Shared.Unit.Tests/netstandard1.3/Utilities/ns13DeploymentItemUtilityTests.cs @@ -354,8 +354,7 @@ public void GetDeploymentItemsShouldReturnClassAndMethodLevelDeploymentItemsWith [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfSourcePathIsNull() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(null, this.defaultDeploymentItemOutputDirectory, out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(null, this.defaultDeploymentItemOutputDirectory, out var warning)); StringAssert.Contains(Resource.DeploymentItemPathCannotBeNullOrEmpty, warning); } @@ -363,8 +362,7 @@ public void IsValidDeploymentItemShouldReportWarningIfSourcePathIsNull() [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfSourcePathIsEmpty() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(string.Empty, this.defaultDeploymentItemOutputDirectory, out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(string.Empty, this.defaultDeploymentItemOutputDirectory, out var warning)); StringAssert.Contains(Resource.DeploymentItemPathCannotBeNullOrEmpty, warning); } @@ -372,8 +370,7 @@ public void IsValidDeploymentItemShouldReportWarningIfSourcePathIsEmpty() [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfDeploymentOutputDirectoryIsNull() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, null, out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, null, out var warning)); StringAssert.Contains(Resource.DeploymentItemOutputDirectoryCannotBeNull, warning); } @@ -381,8 +378,7 @@ public void IsValidDeploymentItemShouldReportWarningIfDeploymentOutputDirectoryI [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfSourcePathHasInvalidCharacters() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem("C:<>", this.defaultDeploymentItemOutputDirectory, out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem("C:<>", this.defaultDeploymentItemOutputDirectory, out var warning)); StringAssert.Contains( string.Format( @@ -395,8 +391,7 @@ public void IsValidDeploymentItemShouldReportWarningIfSourcePathHasInvalidCharac [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfOutputDirectoryHasInvalidCharacters() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, "<>", out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, "<>", out var warning)); StringAssert.Contains( string.Format( @@ -409,8 +404,7 @@ public void IsValidDeploymentItemShouldReportWarningIfOutputDirectoryHasInvalidC [TestMethod] public void IsValidDeploymentItemShouldReportWarningIfDeploymentOutputDirectoryIsRooted() { - string warning; - Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, "C:\\temp", out warning)); + Assert.IsFalse(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, "C:\\temp", out var warning)); StringAssert.Contains( string.Format( @@ -422,8 +416,7 @@ public void IsValidDeploymentItemShouldReportWarningIfDeploymentOutputDirectoryI [TestMethod] public void IsValidDeploymentItemShouldReturnTrueForAValidDeploymentItem() { - string warning; - Assert.IsTrue(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, this.defaultDeploymentItemOutputDirectory, out warning)); + Assert.IsTrue(this.deploymentItemUtility.IsValidDeploymentItem(this.defaultDeploymentItemPath, this.defaultDeploymentItemOutputDirectory, out var warning)); Assert.IsTrue(string.Empty.Equals(warning)); } diff --git a/test/UnitTests/PlatformServices.Universal.Unit.Tests/PlatformServices.Universal.Unit.Tests.csproj b/test/UnitTests/PlatformServices.Universal.Unit.Tests/PlatformServices.Universal.Unit.Tests.csproj index 61f57ff3f..bbeaa6fff 100644 --- a/test/UnitTests/PlatformServices.Universal.Unit.Tests/PlatformServices.Universal.Unit.Tests.csproj +++ b/test/UnitTests/PlatformServices.Universal.Unit.Tests/PlatformServices.Universal.Unit.Tests.csproj @@ -1,9 +1,7 @@  - - ..\..\..\ - - + + {FA7C719F-A400-45AF-8091-7C23435617A8} Library @@ -12,13 +10,19 @@ Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.UWP.UnitTests v4.5.2 {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} - 10.0 - $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + 10.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages False UnitTest 1685 + + true + true + true + PackageReference + true full @@ -34,97 +38,86 @@ prompt 4 + - - ..\..\..\packages\Castle.Core.4.0.0\lib\net45\Castle.Core.dll - True - - - ..\..\..\packages\Microsoft.TestPlatform.AdapterUtilities.$(TestPlatformVersion)\lib\uap10.0\Microsoft.TestPlatform.AdapterUtilities.dll - - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.CoreUtilities.dll + + + + + + + + + + + + + + + $(ArtifactsBinDir)PlatformServices.Universal\Microsoft.VisualStudio.TestPlatform.MSTestAdapter.PlatformServices.dll - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.TestPlatform.PlatformAbstractions.dll + + $(ArtifactsBinDir)Extension.UWP\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.dll FrameworkV1 - - ..\..\..\packages\Microsoft.TestPlatform.ObjectModel.$(TestPlatformVersion)\lib\net451\Microsoft.VisualStudio.TestPlatform.ObjectModel.dll - - - ..\..\..\packages\Moq.4.7.8\lib\net45\Moq.dll - True - - - ..\..\..\packages\NuGet.Frameworks.5.0.0\lib\net40\NuGet.Frameworks.dll - - - - ..\..\..\packages\System.Collections.Immutable.1.5.0\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll - - - ..\..\..\packages\System.Reflection.Metadata.1.6.0\lib\portable-net45+win8\System.Reflection.Metadata.dll - - - + + + {7252d9e3-267d-442c-96bc-c73aef3241d6} + MSTest.Core + FrameworkV2 + + + {bbc99a6b-4490-49dd-9c12-af2c1e95576e} + PlatformServices.Interface + + + {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} + MSTest.CoreAdapter.TestUtilities + + - - - Designer - + + + + + + + + + + runtime; build; native; contentfiles; analyzers; buildtransitive + + - + Services\ns10AssemblyAttributes.cs - + Services\ns10DiaSessionOperationsTests.cs - + Services\ns10ReflectionOperationsTests.cs - + Services\ns10SettingsProviderTests.cs - + Services\ns10TestContextImplementationTests.cs - + Services\ns10TestSourceHostTests.cs - + Services\ns10ThreadOperationsTests.cs - - - {bbc99a6b-4490-49dd-9c12-af2c1e95576e} - PlatformServices.Interface - - - {5D153CAA-80C2-4551-9549-6C406FCEEFB1} - PlatformServices.Universal - - - {f81c7549-e3a3-4770-ac3f-3bc7356e61e8} - MSTest.CoreAdapter.TestUtilities - - - {7252d9e3-267d-442c-96bc-c73aef3241d6} - MSTest.Core - FrameworkV2 - - - {DF131865-84EE-4540-8112-E88ACEBDEA09} - Extension.UWP - - + - + \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Universal.Unit.Tests/Services/UniversalFileOperationsTests.cs b/test/UnitTests/PlatformServices.Universal.Unit.Tests/Services/UniversalFileOperationsTests.cs index 33c19a64d..a51fa7305 100644 --- a/test/UnitTests/PlatformServices.Universal.Unit.Tests/Services/UniversalFileOperationsTests.cs +++ b/test/UnitTests/PlatformServices.Universal.Unit.Tests/Services/UniversalFileOperationsTests.cs @@ -108,10 +108,7 @@ public void CreateNavigationSessionShouldReturnNullForAllSources() [TestMethod] public void GetNavigationDataShouldReturnNullFileName() { - int minLineNumber; - string fileName; - - this.fileOperations.GetNavigationData(null, null, null, out minLineNumber, out fileName); + this.fileOperations.GetNavigationData(null, null, null, out var minLineNumber, out var fileName); Assert.IsNull(fileName); Assert.AreEqual(-1, minLineNumber); } diff --git a/test/UnitTests/PlatformServices.Universal.Unit.Tests/app.config b/test/UnitTests/PlatformServices.Universal.Unit.Tests/app.config deleted file mode 100644 index 33d949fb5..000000000 --- a/test/UnitTests/PlatformServices.Universal.Unit.Tests/app.config +++ /dev/null @@ -1,11 +0,0 @@ - - - - - - - - - - - \ No newline at end of file diff --git a/test/UnitTests/PlatformServices.Universal.Unit.Tests/packages.config b/test/UnitTests/PlatformServices.Universal.Unit.Tests/packages.config deleted file mode 100644 index 311ae4c67..000000000 --- a/test/UnitTests/PlatformServices.Universal.Unit.Tests/packages.config +++ /dev/null @@ -1,11 +0,0 @@ - - - - - - - - - - - \ No newline at end of file