1. 'use strict';
    
  2. 
    
  3. const Git = require('nodegit');
    
  4. const rimraf = require('rimraf');
    
  5. const ncp = require('ncp').ncp;
    
  6. const {existsSync} = require('fs');
    
  7. const exec = require('child_process').exec;
    
  8. const {join} = require('path');
    
  9. 
    
  10. const reactUrl = 'https://github.com/facebook/react.git';
    
  11. 
    
  12. function cleanDir() {
    
  13.   return new Promise(_resolve => rimraf('remote-repo', _resolve));
    
  14. }
    
  15. 
    
  16. function executeCommand(command) {
    
  17.   return new Promise(_resolve =>
    
  18.     exec(command, error => {
    
  19.       if (!error) {
    
  20.         _resolve();
    
  21.       } else {
    
  22.         console.error(error);
    
  23.         process.exit(1);
    
  24.       }
    
  25.     })
    
  26.   );
    
  27. }
    
  28. 
    
  29. function asyncCopyTo(from, to) {
    
  30.   return new Promise(_resolve => {
    
  31.     ncp(from, to, error => {
    
  32.       if (error) {
    
  33.         console.error(error);
    
  34.         process.exit(1);
    
  35.       }
    
  36.       _resolve();
    
  37.     });
    
  38.   });
    
  39. }
    
  40. 
    
  41. function getDefaultReactPath() {
    
  42.   return join(__dirname, 'remote-repo');
    
  43. }
    
  44. 
    
  45. async function buildBenchmark(reactPath = getDefaultReactPath(), benchmark) {
    
  46.   // get the build.js from the benchmark directory and execute it
    
  47.   await require(join(__dirname, 'benchmarks', benchmark, 'build.js'))(
    
  48.     reactPath,
    
  49.     asyncCopyTo
    
  50.   );
    
  51. }
    
  52. 
    
  53. async function getMergeBaseFromLocalGitRepo(localRepo) {
    
  54.   const repo = await Git.Repository.open(localRepo);
    
  55.   return await Git.Merge.base(
    
  56.     repo,
    
  57.     await repo.getHeadCommit(),
    
  58.     await repo.getBranchCommit('main')
    
  59.   );
    
  60. }
    
  61. 
    
  62. async function buildBenchmarkBundlesFromGitRepo(
    
  63.   commitId,
    
  64.   skipBuild,
    
  65.   url = reactUrl,
    
  66.   clean
    
  67. ) {
    
  68.   let repo;
    
  69.   const remoteRepoDir = getDefaultReactPath();
    
  70. 
    
  71.   if (!skipBuild) {
    
  72.     if (clean) {
    
  73.       //clear remote-repo folder
    
  74.       await cleanDir(remoteRepoDir);
    
  75.     }
    
  76.     // check if remote-repo directory already exists
    
  77.     if (existsSync(remoteRepoDir)) {
    
  78.       repo = await Git.Repository.open(remoteRepoDir);
    
  79.       // fetch all the latest remote changes
    
  80.       await repo.fetchAll();
    
  81.     } else {
    
  82.       // if not, clone the repo to remote-repo folder
    
  83.       repo = await Git.Clone(url, remoteRepoDir);
    
  84.     }
    
  85.     let commit = await repo.getBranchCommit('main');
    
  86.     // reset hard to this remote head
    
  87.     await Git.Reset.reset(repo, commit, Git.Reset.TYPE.HARD);
    
  88.     // then we checkout the latest main head
    
  89.     await repo.checkoutBranch('main');
    
  90.     // make sure we pull in the latest changes
    
  91.     await repo.mergeBranches('main', 'origin/main');
    
  92.     // then we check if we need to move the HEAD to the merge base
    
  93.     if (commitId && commitId !== 'main') {
    
  94.       // as the commitId probably came from our local repo
    
  95.       // we use it to lookup the right commit in our remote repo
    
  96.       commit = await Git.Commit.lookup(repo, commitId);
    
  97.       // then we checkout the merge base
    
  98.       await Git.Checkout.tree(repo, commit);
    
  99.     }
    
  100.     await buildReactBundles();
    
  101.   }
    
  102. }
    
  103. 
    
  104. async function buildReactBundles(reactPath = getDefaultReactPath(), skipBuild) {
    
  105.   if (!skipBuild) {
    
  106.     await executeCommand(
    
  107.       `cd ${reactPath} && yarn && yarn build react/index,react-dom/index --type=UMD_PROD`
    
  108.     );
    
  109.   }
    
  110. }
    
  111. 
    
  112. // if run directly via CLI
    
  113. if (require.main === module) {
    
  114.   buildBenchmarkBundlesFromGitRepo();
    
  115. }
    
  116. 
    
  117. module.exports = {
    
  118.   buildReactBundles,
    
  119.   buildBenchmark,
    
  120.   buildBenchmarkBundlesFromGitRepo,
    
  121.   getMergeBaseFromLocalGitRepo,
    
  122. };