From 8751b881cfd756809ad42a80d15e58d33efeb40c Mon Sep 17 00:00:00 2001 From: Robi Nino Date: Tue, 18 Jun 2024 17:09:01 +0300 Subject: [PATCH] Support .NET custom command (#497) --- README.md | 2 +- tasks/JFrogDotnet/dotnetBuild.js | 14 +++++++++++- tasks/JFrogDotnet/task.json | 22 ++++++++++++++----- tests/package.json | 4 ++-- .../resources/conanTask/conanConfigInstall.js | 1 + tests/resources/dotnet/custom.js | 15 +++++++++++++ tests/tests.ts | 14 +++++++++++- 7 files changed, 61 insertions(+), 11 deletions(-) create mode 100644 tests/resources/dotnet/custom.js diff --git a/README.md b/README.md index 1989c68f..66ca1415 100644 --- a/README.md +++ b/README.md @@ -1251,7 +1251,7 @@ Use the following commands to run from terminal: ``` Note: If you are running tests via your IDE, make sure you are registering tests with -ts-node: `mocha -r ts-node/register tests.ts -t 600000`. +ts-node: `mocha -r ts-node/register tests.ts -t 1000000`. #### Skipping Tests diff --git a/tasks/JFrogDotnet/dotnetBuild.js b/tasks/JFrogDotnet/dotnetBuild.js index cfb0926d..e79ff284 100644 --- a/tasks/JFrogDotnet/dotnetBuild.js +++ b/tasks/JFrogDotnet/dotnetBuild.js @@ -17,10 +17,17 @@ function RunTaskCbk(cliPath) { case 'push': performDotnetNugetPush(cliPath); break; + case 'custom': + performDotnetCustomCommand(cliPath); + break; } } function performDotnetRestore(cliPath) { + performDotnetCommand(cliPath, cliDotnetCoreRestoreCommand); +} + +function performDotnetCommand(cliPath, commandName) { let sourcesPattern = tl.getInput('rootPath'); let filesList = solutionPathUtil.resolveFilterSpec(sourcesPattern, tl.getVariable('System.DefaultWorkingDirectory') || process.cwd()); // A source file is a solution or csproj file. @@ -33,11 +40,16 @@ function performDotnetRestore(cliPath) { } let resolverServerId = performDotnetConfig(cliPath, sourcePath, 'targetResolveRepo'); let dotnetArguments = buildDotnetCliArgs(); - let dotnetCommand = utils.cliJoin(cliPath, cliDotnetCoreRestoreCommand, dotnetArguments); + let dotnetCommand = utils.cliJoin(cliPath, commandName, dotnetArguments); executeCliCommand(dotnetCommand, sourcePath, cliPath, [resolverServerId]); }); } +function performDotnetCustomCommand(cliPath) { + let customCommand = tl.getInput('customCommand'); + performDotnetCommand(cliPath, 'dotnet ' + customCommand); +} + function performDotnetNugetPush(cliPath) { let buildDir = tl.getVariable('System.DefaultWorkingDirectory'); let targetPath = tl.getInput('targetDeployRepo', true); diff --git a/tasks/JFrogDotnet/task.json b/tasks/JFrogDotnet/task.json index 198ba96f..1020e309 100644 --- a/tasks/JFrogDotnet/task.json +++ b/tasks/JFrogDotnet/task.json @@ -39,17 +39,26 @@ }, "options": { "restore": "restore", - "push": "NuGet push" + "push": "NuGet push", + "custom": "custom" } }, + { + "name": "customCommand", + "type": "string", + "label": "Custom command", + "helpMarkDown": "The custom command which will be passed to .NET Core CLI for execution (for example: 'pack'). Note that commands that require deployment are not supported, and that build-info collection is not available for custom commands.", + "required": true, + "visibleRule": "command=custom" + }, { "name": "arguments", "type": "string", "label": "Arguments", "defaultValue": "", - "helpMarkDown": "The arguments which will be passed to .NET Core CLI for execution. Arguments should be quoted, and space separated.", + "helpMarkDown": "The arguments which will be passed to .NET Core CLI for execution (for example: '--no-restore' '--v:d'). Arguments should be quoted, and space separated.", "required": false, - "visibleRule": "command = restore" + "visibleRule": "command=restore || command=custom" }, { "name": "artifactoryConnection", @@ -65,7 +74,7 @@ "label": "Resolution repository", "defaultValue": "", "required": true, - "visibleRule": "command = restore", + "visibleRule": "command=restore || command=custom", "helpMarkDown": "Sets the resolution repository.", "properties": { "EditableOptions": "True" @@ -99,7 +108,7 @@ "defaultValue": "**/*.sln", "helpMarkDown": "Path to the root directory of a solution/project file to use. If the directory includes more than one sln files, then the first argument passed in the Arguments field should be the name (not the path) of the sln file. Accepts Ant-style patterns.", "required": "true", - "visibleRule": "command = restore" + "visibleRule": "command=restore || command=custom" }, { "name": "pathToNupkg", @@ -150,6 +159,7 @@ "label": "Collect build info", "defaultValue": "false", "required": false, + "visibleRule": "command=restore || command=push", "helpMarkDown": "Select to collect build info." }, { @@ -194,7 +204,7 @@ "label": "NuGet protocol version", "required": false, "defaultValue": "v3", - "visibleRule": "command = restore", + "visibleRule": "command=restore || command=custom", "options": { "v2": "v2", "v3": "v3" diff --git a/tests/package.json b/tests/package.json index 576f046f..a984dc2f 100644 --- a/tests/package.json +++ b/tests/package.json @@ -8,7 +8,7 @@ "main": "testUtils.ts", "dependencies": { "@jfrog/tasks-utils": "file:../jfrog-tasks-utils/jfrog-tasks-utils-1.0.0.tgz", - "azure-pipelines-task-lib": "^4.4.0", + "azure-pipelines-task-lib": "4.12.0", "fs-extra": "^11.1.1", "js-yaml": "^4.1.0", "path": "^0.12.7" @@ -26,6 +26,6 @@ "ts-node": "^10.9.1" }, "scripts": { - "test": "npm i && mocha -r ts-node/register tests.ts -t 600000" + "test": "npm i && mocha -r ts-node/register tests.ts -t 1000000" } } diff --git a/tests/resources/conanTask/conanConfigInstall.js b/tests/resources/conanTask/conanConfigInstall.js index 11a22bd5..afe9574e 100644 --- a/tests/resources/conanTask/conanConfigInstall.js +++ b/tests/resources/conanTask/conanConfigInstall.js @@ -1,5 +1,6 @@ const testUtils = require('../../testUtils'); const join = require('path').join; +const basename = require('path').basename; const TEST_NAME = basename(__dirname); const BUILD_NAME = TEST_NAME; diff --git a/tests/resources/dotnet/custom.js b/tests/resources/dotnet/custom.js new file mode 100644 index 00000000..2700fddc --- /dev/null +++ b/tests/resources/dotnet/custom.js @@ -0,0 +1,15 @@ +const testUtils = require('../../testUtils'); +const join = require('path').join; +const TEST_NAME = testUtils.getTestName(__dirname); + +let inputs = { + command: 'custom', + customCommand: 'restore', + arguments: '"--build-name=DotNET Test" "--build-number=7"', + rootPath: join(testUtils.getLocalTestDir(TEST_NAME)), + targetResolveRepo: testUtils.getRepoKeys().nugetVirtualRepo, + nugetProtocolVersion: "v3" +}; + +testUtils.copyTestFilesToTestWorkDir(TEST_NAME, 'restore'); +testUtils.runArtifactoryTask(testUtils.dotnet, {}, inputs); diff --git a/tests/tests.ts b/tests/tests.ts index c49d5809..309e976c 100644 --- a/tests/tests.ts +++ b/tests/tests.ts @@ -721,6 +721,18 @@ describe('JFrog Artifactory Extension Tests', (): void => { }, TestUtils.isSkipTest('dotnet'), ); + // Run a restore using the custom command task. + runSyncTest( + 'Dotnet custom restore', + (): void => { + const testDir: string = 'dotnet'; + mockTask(testDir, 'custom'); + mockTask(testDir, 'publish'); + getAndAssertBuild('DotNET Test', '7'); + deleteBuild('DotNET Test'); + }, + TestUtils.isSkipTest('dotnet'), + ); }); describe('Docker Tests', (): void => { @@ -968,7 +980,7 @@ function runSyncTest(description: string, testFunc: () => void, skip?: boolean): it(description, (done): void => { testFunc(); done(); - }).timeout(600000); // 6 minutes + }).timeout(1000000); // 10 minutes } /**