const fs = require('fs');
const GithubSlugger = require('github-slugger');

function walk(dir) {
  let results = [];
  const list = fs.readdirSync(dir);
  list.forEach(function(file) {
    file = dir + '/' + file;
    const stat = fs.statSync(file);
    if (stat && stat.isDirectory()) {
      /* Recurse into a subdirectory */
      results = results.concat(walk(file));
    } else {
      /* Is a file */
      results.push(file);
    }
  });
  return results;
}

function stripLinks(line) {
  return line.replace(/\[([^\]]+)\]\([^)]+\)/, (match, p1) => p1);
}

function addHeaderID(line, slugger) {
  // check if we're a header at all
  if (!line.startsWith('#')) {
    return line;
  }
  // check if it already has an id
  if (/\{#[^}]+\}/.test(line)) {
    return line;
  }
  const headingText = line.slice(line.indexOf(' ')).trim();
  const headingLevel = line.slice(0, line.indexOf(' '));
  return `${headingLevel} ${headingText} {#${slugger.slug(
    stripLinks(headingText),
  )}}`;
}

function addHeaderIDs(lines) {
  // Sluggers should be per file
  const slugger = new GithubSlugger();
  let inCode = false;
  const results = [];
  lines.forEach(line => {
    // Ignore code blocks
    if (line.startsWith('```')) {
      inCode = !inCode;
      results.push(line);
      return;
    }
    if (inCode) {
      results.push(line);
      return;
    }

    results.push(addHeaderID(line, slugger));
  });
  return results;
}

const [path] = process.argv.slice(2);

const files = walk(path);
files.forEach(file => {
  if (!file.endsWith('.md')) {
    return;
  }

  const content = fs.readFileSync(file, 'utf8');
  const lines = content.split('\n');
  const updatedLines = addHeaderIDs(lines);
  fs.writeFileSync(file, updatedLines.join('\n'));
});