Skip to content

Commit

Permalink
Merge pull request #2195 from jmyersmsft/onPremSwitching
Browse files Browse the repository at this point in the history
Ignore empty path filters, disable cred provider on hosted, disable config creds on on-prem (M103)
  • Loading branch information
jmyersmsft authored Aug 3, 2016
2 parents afefbcb + 5f087b1 commit b0b3083
Show file tree
Hide file tree
Showing 10 changed files with 110 additions and 16 deletions.
4 changes: 3 additions & 1 deletion Tasks/Common/nuget-task-common/NuGetConfigHelper.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,9 @@ export class NuGetConfigHelper {
};

if (this._nugetConfigPath) {
tl.cp("-f", this._nugetConfigPath, this.tempNugetConfigPath);
// don't use cp as that copies the read-only flag, and tfvc sets that on files
let content = fs.readFileSync(this._nugetConfigPath);
fs.writeFileSync(this.tempNugetConfigPath, content);
}
else {
// small file, use writeFileSync
Expand Down
79 changes: 77 additions & 2 deletions Tasks/Common/nuget-task-common/NuGetToolRunner.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import {ToolRunner, IExecOptions, IExecResult} from 'vsts-task-lib/toolrunner';
import * as auth from "./Authentication"
import * as os from 'os';
import * as path from 'path';
import * as url from 'url';

interface EnvironmentDictionary { [key: string]: string }

Expand Down Expand Up @@ -50,6 +51,7 @@ function prepareNuGetExeEnvironment(input: EnvironmentDictionary, settings: NuGe
env['NUGET_CREDENTIAL_PROVIDER_OVERRIDE_DEFAULT'] = 'true';

if (credProviderPath) {
tl.debug(`credProviderPath = ${credProviderPath}`);
env['NUGET_CREDENTIALPROVIDERS_PATH'] = credProviderPath;
}

Expand Down Expand Up @@ -155,6 +157,79 @@ export function locateNuGetExe(userNuGetExePath: string): string {
return toolPath;
}

function isHosted(): boolean {
// not an ideal way to detect hosted, but there isn't a variable for it, and we can't make network calls from here
// due to proxy issues.
const collectionUri = tl.getVariable("System.TeamFoundationCollectionUri");
const parsedCollectionUri = url.parse(collectionUri);
return /\.visualstudio\.com$/i.test(parsedCollectionUri.hostname);
}

// Currently, there is a race condition of some sort that causes nuget to not send credentials sometimes
// when using the credential provider.
// Unfortunately, on on-premises TFS, we must use credential provider to override NTLM auth with the build
// identity's token.
// Therefore, we are enabling credential provider on on-premises and disabling it on hosted. We allow for test
// instances by an override variable.

export function isCredentialProviderEnabled(): boolean {
// set NuGet.ForceEnableCredentialProvider to "true" to force allowing the credential provider flow, "false"
// to force *not* allowing the credential provider flow, or unset/anything else to fall through to the
// hosted environment detection logic
const credentialProviderOverrideFlag = tl.getVariable("NuGet.ForceEnableCredentialProvider");
if (credentialProviderOverrideFlag === "true") {
tl.debug("Credential provider is force-enabled for testing purposes.");
return true;
}

if (credentialProviderOverrideFlag === "false") {
tl.debug("Credential provider is force-disabled for testing purposes.");
return false;
}

if (isHosted()) {
tl.debug("Credential provider is disabled on hosted.");
return false;
}
else {
tl.debug("Credential provider is enabled.")
return true;
}
}

export function isCredentialConfigEnabled(): boolean {
// set NuGet.ForceEnableCredentialConfig to "true" to force allowing config-based credential flow, "false"
// to force *not* allowing config-based credential flow, or unset/anything else to fall through to the
// hosted environment detection logic
const credentialConfigOverrideFlag = tl.getVariable("NuGet.ForceEnableCredentialConfig");
if (credentialConfigOverrideFlag === "true") {
tl.debug("Credential config is force-enabled for testing purposes.");
return true;
}

if (credentialConfigOverrideFlag === "false") {
tl.debug("Credential config is force-disabled for testing purposes.");
return false;
}

// credentials in config will always fail for on-prem
if (!isHosted()) {
tl.debug("Credential config is disabled on on-premises TFS.");
return false;
}
else {
tl.debug("Credential config is enabled.")
return true;
}
}

export function locateCredentialProvider(): string {
return locateTool('CredentialProvider.TeamBuild.exe');
}
const credentialProviderLocation = locateTool('CredentialProvider.TeamBuild.exe');
if(!credentialProviderLocation) {
tl.debug("Credential provider is not present.");
return null;
}

return isCredentialProviderEnabled() ? credentialProviderLocation : null;
}

14 changes: 11 additions & 3 deletions Tasks/Common/nuget-task-common/Utility.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@ import * as os from 'os';

// Attempts to resolve paths the same way the legacy PowerShell's Find-Files worked
export function resolveFilterSpec(filterSpec: string, basePath?: string, allowEmptyMatch?: boolean): string[] {
let patterns = filterSpec.split(";");
// make sure to remove any empty entries, or else we'll accidentally match the current directory.
let patterns = filterSpec.split(";").map(x => x.trim()).filter(x => !!x);
let result = new Set<string>();

patterns.forEach(pattern => {
Expand All @@ -23,6 +24,8 @@ export function resolveFilterSpec(filterSpec: string, basePath?: string, allowEm
pattern = path.resolve(basePath, pattern);
}

tl.debug(`pattern: ${pattern}, isNegative: ${isNegative}`);

let thisPatternFiles = resolveWildcardPath(pattern, true);
thisPatternFiles.forEach(file => {
if (isNegative) {
Expand All @@ -44,10 +47,15 @@ export function resolveFilterSpec(filterSpec: string, basePath?: string, allowEm

export function resolveWildcardPath(pattern: string, allowEmptyWildcardMatch?: boolean): string[] {
let isWindows = os.platform() === 'win32';

// Resolve files for the specified value or pattern
var filesList: string[];
if (pattern.indexOf('*') == -1 && pattern.indexOf('?') == -1) {

// empty patterns match nothing (otherwise they will effectively match the current directory)
if (!pattern) {
filesList = [];
}
else if (pattern.indexOf('*') == -1 && pattern.indexOf('?') == -1) {

// No pattern found, check literal path to a single file
tl.checkPath(pattern, 'files');
Expand Down
9 changes: 6 additions & 3 deletions Tasks/NuGetInstaller/nugetinstaller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ var solution = tl.getPathInput('solution', true, false);
var filesList = nutil.resolveFilterSpec(solution, tl.getVariable('System.DefaultWorkingDirectory') || process.cwd());
filesList.forEach(solutionFile => {
if (!tl.stats(solutionFile).isFile()) {
throw new Error(tl.loc('NotARegularFile'));
throw new Error(tl.loc('NotARegularFile', solutionFile));
}
});

Expand Down Expand Up @@ -67,7 +67,7 @@ var serviceUri = tl.getEndpointUrl("SYSTEMVSSCONNECTION", false);

//find nuget location to use
var nuGetPathToUse = ngToolRunner.locateNuGetExe(userNuGetPath);
var credProviderPath = null;//ngToolRunner.locateCredentialProvider();
var credProviderPath = ngToolRunner.locateCredentialProvider();

var credProviderDir: string = null;
if (credProviderPath) {
Expand Down Expand Up @@ -123,7 +123,10 @@ locationHelpers.assumeNuGetUriPrefixes(serviceUri)

var configFilePromise = Q<string>(nugetConfigPath);
var credCleanup = () => { return };
if (!credProviderDir || (userNuGetPath && preCredProviderNuGet)) {
if (!ngToolRunner.isCredentialConfigEnabled()) {
tl.debug("Not configuring credentials in nuget.config");
}
else if (!credProviderDir || (userNuGetPath && preCredProviderNuGet)) {
if (nugetConfigPath) {
var nuGetConfigHelper = new NuGetConfigHelper(nuGetPathToUse, nugetConfigPath, authInfo, environmentSettings);
configFilePromise = nuGetConfigHelper.getSourcesFromConfig()
Expand Down
2 changes: 1 addition & 1 deletion Tasks/NuGetInstaller/task.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"version": {
"Major": 0,
"Minor": 2,
"Patch": 6
"Patch": 7
},
"minimumAgentVersion": "1.83.0",
"groups": [
Expand Down
2 changes: 1 addition & 1 deletion Tasks/NuGetInstaller/task.loc.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"version": {
"Major": 0,
"Minor": 2,
"Patch": 6
"Patch": 7
},
"minimumAgentVersion": "1.83.0",
"groups": [
Expand Down
9 changes: 6 additions & 3 deletions Tasks/NugetPublisher/nugetpublisher.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ var searchPattern = tl.getPathInput('searchPattern', true, false);
var filesList = nutil.resolveFilterSpec(searchPattern, tl.getVariable('System.DefaultWorkingDirectory') || process.cwd());
filesList.forEach(packageFile => {
if (!tl.stats(packageFile).isFile()) {
throw new Error(tl.loc('NotARegularFile'));
throw new Error(tl.loc('NotARegularFile', packageFile));
}
});

Expand Down Expand Up @@ -64,7 +64,7 @@ var serviceUri = tl.getEndpointUrl("SYSTEMVSSCONNECTION", false);

//find nuget location to use
var nuGetPathToUse = ngToolRunner.locateNuGetExe(userNuGetPath);
var credProviderPath = null;//ngToolRunner.locateCredentialProvider();
var credProviderPath = ngToolRunner.locateCredentialProvider();

var credProviderDir: string = null;
if (credProviderPath) {
Expand Down Expand Up @@ -123,7 +123,10 @@ locationHelpers.assumeNuGetUriPrefixes(serviceUri)
var feedUri: string;
var credCleanup = () => { return };
if (nuGetFeedType == "internal") {
if (!credProviderDir || (userNuGetPath && preCredProviderNuGet)) {
if (!ngToolRunner.isCredentialConfigEnabled()) {
tl.debug("Not configuring credentials in nuget.config");
}
else if (!credProviderDir || (userNuGetPath && preCredProviderNuGet)) {
var nuGetConfigHelper = new NuGetConfigHelper(nuGetPathToUse, null, authInfo, environmentSettings);
nuGetConfigHelper.setSources([{ feedName: "internalFeed", feedUri: internalFeedUri }]);
configFilePromise = Q(nuGetConfigHelper.tempNugetConfigPath);
Expand Down
2 changes: 1 addition & 1 deletion Tasks/NugetPublisher/task.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"version": {
"Major": 0,
"Minor": 2,
"Patch": 6
"Patch": 7
},
"demands": [
"Cmd"
Expand Down
2 changes: 1 addition & 1 deletion Tasks/NugetPublisher/task.loc.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"version": {
"Major": 0,
"Minor": 2,
"Patch": 6
"Patch": 7
},
"demands": [
"Cmd"
Expand Down
3 changes: 3 additions & 0 deletions definitions/nuget-task-common.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,8 @@ declare module 'nuget-task-common/NuGetToolRunner' {
}
export function createNuGetToolRunner(nuGetExePath: string, settings: NuGetEnvironmentSettings): NuGetToolRunner;
export function locateNuGetExe(userNuGetExePath: string): string;
export function isCredentialProviderEnabled(): boolean;
export function isCredentialConfigEnabled(): boolean;
export function locateCredentialProvider(): string;

}
Expand All @@ -123,6 +125,7 @@ declare module 'nuget-task-common/NuGetConfigHelper' {
private _nugetConfigPath;
private _authInfo;
private _environmentSettings;
private tempNugetConfigBaseDir;
private tempNugetConfigDir;
private tempNugetConfigFileName;
tempNugetConfigPath: string;
Expand Down

0 comments on commit b0b3083

Please sign in to comment.