import fs from 'fs';
import path from 'path';
import moment from 'moment';
import NodeGit from 'nodegit';

function getConfiguredIgnoresIfExist(repoPath) {
  return new Promise((resolve) => {
    fs.readFile(path.join(repoPath, '.gitsweepignore'), 'utf8', (err, data) => {
      if (err) {
        return resolve([]);
      }

      resolve(data.split('\n'));
    })
  });
}

function isIgnored(ref, ignoreList) {
  return ignoreList.includes(ref.replace(/^refs\/remotes\//, ''));
}

function getCutoffMoment(age) {
  const [, year, month, day] = age.match(/(?:(\d+)y)?(?:(\d+)m)?(?:(\d+)d)?/);
  
  return moment()
    .subtract(year, 'years')
    .subtract(month, 'months')
    .subtract(day, 'days');
}

async function sweep({
  path = '.',
  remote = 'origin',
  preview = false,
  ignore = 'origin/master',
  age = '1m',
  password
}) {
  try {
    const cutoffMoment = age ? getCutoffMoment(age) : null;
    const ignoreList = await getConfiguredIgnoresIfExist(path);
    ignoreList.push(...ignore);

    const repo = await NodeGit.Repository.open(path);

    const authTrials = {
      agent: false,
      userpassPlaintext: false
    };
    await repo.fetch(remote, {
      callbacks: {
        certificateCheck: function() { return 1; },
        credentials: function(url, username) {
          // Do not try ssh-agent if password is specified
          if (password) {
            if (!authTrials.userpassPlaintext) {
              authTrials.userpassPlaintext = true;
              return NodeGit.Cred.userpassPlaintextNew(username, password);
            }
          } else if (!authTrials.agent) {
            authTrials.agent = true;
            return NodeGit.Cred.sshKeyFromAgent(username);
          }
        }
      },
      prune: NodeGit.Fetch.PRUNE.GIT_FETCH_PRUNE
    });

    const refNames = await repo.getReferenceNames(NodeGit.Reference.TYPE.LISTALL);
    const sweepRefs = [];

    for (const ref of refNames) {
      if (ref.startsWith(`refs/remotes/${remote}`) && !isIgnored(ref, ignoreList)) {
        const commit = await repo.getReferenceCommit(ref);
        const commitMoment = moment(commit.date());

        if (!cutoffMoment || commitMoment.isBefore(cutoffMoment)) {
          console.log(`- ${ref}\t${commitMoment.fromNow()}`);
          sweepRefs.push(`:${ref.replace(`remotes/${remote}`, 'heads')}`);
        }
      }
    }

    if (sweepRefs.length < 1) {
      console.log('No matching remote branch to sweep');
      return;
    } else if (!!cutoffMoment) {
      console.log(`${sweepRefs.length} branch found with last commit before ${cutoffMoment.toString()}`);
    } else {
      console.log(`${sweepRefs.length} branch found`);
    }

    if (!preview) {
      const theRemote = await repo.getRemote(remote);
      theRemote.push(sweepRefs);

      console.log(`${sweepRefs.length} branch removed`);
    }
  } catch (e) {
    console.error(e.message);
  }
}

export default sweep;

@@ -2693,24 +2693,116 @@
 !preview) %7B%0A
+      const authTrials = %7B%0A        agent: false,%0A        userpassPlaintext: false%0A      %7D;%0A%0A
       const 
@@ -2849,16 +2849,22 @@
 ;%0A      
+await 
 theRemot
@@ -2879,16 +2879,618 @@
 weepRefs
+, %7B%0A        callbacks: %7B%0A          certificateCheck: function() %7B return 1; %7D,%0A          credentials: function(url, username) %7B%0A            // Do not try ssh-agent if password is specified%0A            if (password) %7B%0A              if (!authTrials.userpassPlaintext) %7B%0A                authTrials.userpassPlaintext = true;%0A                return NodeGit.Cred.userpassPlaintextNew(username, password);%0A              %7D%0A            %7D else if (!authTrials.agent) %7B%0A              authTrials.agent = true;%0A              return NodeGit.Cred.sshKeyFromAgent(username);%0A            %7D%0A          %7D%0A        %7D%0A      %7D
 );%0A%0A    

Fix missing auth callbacks with actual push