<commit_before>import Q = require('q');
import scmm = require('./lib/scmprovider');
import gitwm = require('./lib/gitwrapper');
import ctxm = require('../context');
import ifm = require('../api/interfaces');
var path = require('path');
var shell = require('shelljs');
var url = require('url');

export function getProvider(ctx: ctxm.JobContext, targetPath: string): scmm.IScmProvider {
	return new GitScmProvider(ctx, targetPath);
}

function _translateRef(ref) {
    var brPre = 'refs/heads/';
    if (ref.startsWith(brPre)) {
        ref = 'refs/remotes/origin/' + ref.substr(brPre.length, ref.length - brPre.length);
    }

    return ref;
}

// TODO: take options with stdout and stderr streams for testing?

export class GitScmProvider extends scmm.ScmProvider {
	constructor(ctx: ctxm.JobContext, targetPath: string) {
		this.gitw = new gitwm.GitWrapper();
		this.gitw.on('stdout', (data) => {
			ctx.info(data.toString());
		});

		this.gitw.on('stderr', (data) => {
			ctx.info(data.toString());
		});

		super(ctx, targetPath);
	}

	public username: string;
	public password: string;
	public gitw: gitwm.GitWrapper;
	public endpoint: ifm.JobEndpoint;

	public initialize(endpoint: ifm.JobEndpoint) {
		this.endpoint = endpoint;

		if (!endpoint) {
			throw (new Error('endpoint null initializing git scm provider'));
		}

	    if (endpoint.authorization && endpoint.authorization['scheme']) {
	        var scheme = endpoint.authorization['scheme'];
	        this.ctx.info('Using auth scheme: ' + scheme);

	        switch (scheme) {
	            case 'UsernamePassword':
	                this.username = this.getAuthParameter(endpoint, 'Username') || 'not supplied';
	                this.password = this.getAuthParameter(endpoint, 'Password') || 'not supplied';
	                break;

	            default:
	                this.ctx.warning('invalid auth scheme: ' + scheme);
	        }
	    }		
	}

	public getCode(): Q.Promise<number> {
		if (!this.endpoint) {
			throw (new Error('endpoint not set.  initialize not called'));
		}

        // encodes projects and repo names with spaces
        var gu = url.parse(this.endpoint.url);
        var giturl = gu.format(gu);
        var folder = path.basename(this.targetPath);

        // figure out ref
	    var srcVersion = this.ctx.job.environment.variables['build.sourceVersion'];
	    var srcBranch = this.ctx.job.environment.variables['build.sourceBranch'];
	    this.ctx.info('srcVersion: ' + srcVersion);
	    this.ctx.info('srcBranch: ' + srcBranch);

	    
	    var selectedRef = srcVersion ? srcVersion : srcBranch;

	    var inputref = "refs/heads/master";
	    if (selectedRef && selectedRef.trim().length > 0) {
	        inputref = selectedRef;
	    }

	    // if branch, we want to clone remote branch name to avoid tracking etc.. ('/refs/remotes/...')
	    var ref = _translateRef(inputref);
	    this.ctx.info('Using ref: ' + ref);

	    var gopt = <gitwm.IGitExecOptions>{
	    	creds: true
	    	debugOutput: this.debugOutput
	    }

	    this.gitw.username = this.username;
	    this.gitw.password = <PASSWORD>;

        return Q(0)
        .then((code: number) => {
	        if (!this.enlistmentExists()) {
	        	return this.gitw.clone(giturl, true, folder, gopt);
	        }
	        else {
	        	shell.cd(this.targetPath);
	        	return this.gitw.fetch(gopt)
	        	.then((code: number) => {
	        		return this.gitw.checkout(ref, gopt);
	        	})
	        }
        })
        .then((code: number) => {
        	if (this.endpoint.data['checkoutSubmodules'] === "True") {
        		this.ctx.info('Updating Submodules');
        		shell.cd(this.targetPath);
        		return this.gitw.submodule(['init'])
        		.then((code: number) => {
        			return this.gitw.submodule(['update']);
        		})<commit_msg>comma missing<commit_after>import Q = require('q');
import scmm = require('./lib/scmprovider');
import gitwm = require('./lib/gitwrapper');
import ctxm = require('../context');
import ifm = require('../api/interfaces');
var path = require('path');
var shell = require('shelljs');
var url = require('url');

export function getProvider(ctx: ctxm.JobContext, targetPath: string): scmm.IScmProvider {
	return new GitScmProvider(ctx, targetPath);
}

function _translateRef(ref) {
    var brPre = 'refs/heads/';
    if (ref.startsWith(brPre)) {
        ref = 'refs/remotes/origin/' + ref.substr(brPre.length, ref.length - brPre.length);
    }

    return ref;
}

// TODO: take options with stdout and stderr streams for testing?

export class GitScmProvider extends scmm.ScmProvider {
	constructor(ctx: ctxm.JobContext, targetPath: string) {
		this.gitw = new gitwm.GitWrapper();
		this.gitw.on('stdout', (data) => {
			ctx.info(data.toString());
		});

		this.gitw.on('stderr', (data) => {
			ctx.info(data.toString());
		});

		super(ctx, targetPath);
	}

	public username: string;
	public password: string;
	public gitw: gitwm.GitWrapper;
	public endpoint: ifm.JobEndpoint;

	public initialize(endpoint: ifm.JobEndpoint) {
		this.endpoint = endpoint;

		if (!endpoint) {
			throw (new Error('endpoint null initializing git scm provider'));
		}

	    if (endpoint.authorization && endpoint.authorization['scheme']) {
	        var scheme = endpoint.authorization['scheme'];
	        this.ctx.info('Using auth scheme: ' + scheme);

	        switch (scheme) {
	            case 'UsernamePassword':
	                this.username = this.getAuthParameter(endpoint, 'Username') || 'not supplied';
	                this.password = this.getAuthParameter(endpoint, 'Password') || 'not supplied';
	                break;

	            default:
	                this.ctx.warning('invalid auth scheme: ' + scheme);
	        }
	    }		
	}

	public getCode(): Q.Promise<number> {
		if (!this.endpoint) {
			throw (new Error('endpoint not set.  initialize not called'));
		}

        // encodes projects and repo names with spaces
        var gu = url.parse(this.endpoint.url);
        var giturl = gu.format(gu);
        var folder = path.basename(this.targetPath);

        // figure out ref
	    var srcVersion = this.ctx.job.environment.variables['build.sourceVersion'];
	    var srcBranch = this.ctx.job.environment.variables['build.sourceBranch'];
	    this.ctx.info('srcVersion: ' + srcVersion);
	    this.ctx.info('srcBranch: ' + srcBranch);

	    
	    var selectedRef = srcVersion ? srcVersion : srcBranch;

	    var inputref = "refs/heads/master";
	    if (selectedRef && selectedRef.trim().length > 0) {
	        inputref = selectedRef;
	    }

	    // if branch, we want to clone remote branch name to avoid tracking etc.. ('/refs/remotes/...')
	    var ref = _translateRef(inputref);
	    this.ctx.info('Using ref: ' + ref);

	    var gopt = <gitwm.IGitExecOptions>{
	    	creds: true,
	    	debugOutput: this.debugOutput
	    }

	    this.gitw.username = this.username;
	    this.gitw.password = <PASSWORD>;

        return Q(0)
        .then((code: number) => {
	        if (!this.enlistmentExists()) {
	        	return this.gitw.clone(giturl, true, folder, gopt);
	        }
	        else {
	        	shell.cd(this.targetPath);
	        	return this.gitw.fetch(gopt)
	        	.then((code: number) => {
	        		return this.gitw.checkout(ref, gopt);
	        	})
	        }
        })
        .then((code: number) => {
        	if (this.endpoint.data['checkoutSubmodules'] === "True") {
        		this.ctx.info('Updating Submodules');
        		shell.cd(this.targetPath);
        		return this.gitw.submodule(['init'])
        		.then((code: number) => {
        			return this.gitw.submodule(['update']);
        		})
{'fraction_non_alphanumeric': 0.14442844048710227, 'fraction_numerical': 0.0005237658766531361, 'mean_word_length': 2.619905213270142, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 23, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5176476', 'n_tokens_mistral': 2472, 'n_tokens_neox': 2299, 'n_words': 515}