SHARE
TWEET

Untitled

a guest Feb 22nd, 2019 57 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. // How a team of engineers interacts with projects
  2.  
  3. engineers = [];
  4. backlog = new PriorityQueue();
  5. projectsInProgress = new PriorityQueue();
  6. projectsFinished = [];
  7.  
  8. engineers.forEach(engineer => {
  9.   engineer.on('puzzled', findHelp);
  10.   engineer.on('tired', rest);
  11.   engineer.on('frustrated', takeBreak);
  12.   // this can happen when the engineer's current project no longer has an available stream of work
  13.   engineer.on('idle', allocateProjects);
  14. })
  15.  
  16. backlog.forEach(project => {
  17.   project.on('ship', handleShip);
  18. })
  19.  
  20. const handleShip = (project) => {
  21.   project.engineers.forEach(handleFinish);
  22.   projectsInProgress.remove(project);
  23.   projectsFinished.push(project);
  24.   allocateProjects();
  25. }
  26.  
  27. const handleFinish = (engineer) => {
  28.   engineer.project = undefined;
  29.   engineer.celebrate();
  30.   engineer.takeBreak();
  31. }
  32.  
  33. const availableEngineers = () => _.reject(engineers, 'project');
  34. const isEngineerAvailable = () => !.empty(availableEngineers());
  35. const mostExcitedAvailableEngineer = (project) => _.first(
  36.   _.sortBy(
  37.     availableEngineers(),
  38.     engineer => getExcitement(engineer, project)
  39.   )
  40. )
  41.  
  42. const assign = (engineer, project) => {
  43.   engineer.project = project;
  44.   project.engineers.push(engineer);
  45. }
  46.  
  47. const allocateEngineer = (engineer, project = new Project('engineer driven project')) => {
  48.   assign(engineer, project);
  49. }
  50.  
  51. const mostImportantAvailableProject = () => _.first(_.filter(projectsInProgress, canUseEngineer)) || backlog.pop();
  52.  
  53. const allocateProjects = () => {
  54.   while (isEngineerAvailable()) {
  55.     // something truly exciting happens when project === undefined, and in the best performing teams I've seen
  56.     // this will happen and we view it as a joyous occasion
  57.     const project = mostImportantAvailableProject();
  58.  
  59.     while (isEngineerAvailable() && canUseEngineer(project)) {
  60.       const chosenEngineer = mostExcitedAvailableEngineer(project);
  61.       allocateEngineer(chosenEngineer, project);
  62.     }
  63.   }
  64. }
  65.  
  66. // To kick it all off
  67. allocateProjects();
  68.  
  69. // ============
  70.  
  71. // How a team of engineers interacts with a single project
  72.  
  73. // A project can start out as vague as 'Plan how to build this' and the
  74. // DAG grows as the team gets clarity on the scope of the project.
  75.  
  76. const tasks = new DirectedAcyclicGraph();
  77. const engineers = [];
  78. let canUseEngineer = false;
  79.  
  80. const isReady = (task) => _.every(task.dependency, 'isDone');
  81.  
  82. const availableTasks = () => _.filter(tasks, isReady);
  83.  
  84. const mostExcitedAvailableEngineer = (task) => _.first(
  85.   _.sortBy(
  86.     availableEngineers(),
  87.     engineer => getExcitement(engineer, task)
  88.   )
  89. )
  90.  
  91. const allocateTasks = () => {
  92.   while (isEngineerAvailable() && !_.empty(availableTasks())) {
  93.     const chosenEngineer = mostExcitedAvailableEngineer(task);
  94.     assign(chosenEngineer, task);
  95.   }
  96.  
  97.   if (isEngineerAvailable()) {
  98.     // we've run out of parallel workstreams, engineers left out of work might want
  99.     // to find another project using their idle callback
  100.     availableEngineers().forEach(engineer => engineer.idle());
  101.   }
  102.  
  103.   if (isTaskAvailable()) {
  104.     canUseEngineer = makeAnInformedGuess();
  105.   }
  106. }
  107.  
  108. // kick it off
  109.  
  110. allocateTasks();
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
 
Top