The screeps website doesn't work properly without javascrip, who would have thought?   I have a similar approach. Every time the worker is full of energy he ckecks with the local spawns memory what the max builders, repairer and so on are and then chooses his role accordingly. My creeps work with roles and jobs. The roles are worker, goon and longwayharvesters and such and the jobs are builder, harvester, upgrader, repairer. The job memory gets cleared when they switch from getting energy to work and getting reasigned. I think I lose one tick every time that happens though.  I have no idea how efficient my code is, the last time I coded anything really was in 2004   module.exports = { run: function(creep){ grid = creep.room.name;var gridcontrol = creep.pos.findClosestByRange(FIND_MY_STRUCTURES, { filter: (s) => (s.structureType == STRUCTURE_SPAWN)}); var miniharvester = gridcontrol.memory.harvester; var maxrepair = gridcontrol.memory.repair; var minibuilder = gridcontrol.memory.builder; var maxbuilder = gridcontrol.memory.maxbuilder; var numberworkers = creep.room.find(FIND_MY_CREEPS, { filter: (s) => (s.memory.role == 'worker')}).length; var energyneed = creep.pos.findClosestByPath(FIND_MY_STRUCTURES, { filter: (s) => (s.structureType == STRUCTURE_SPAWN || s.structureType == STRUCTURE_EXTENSION || s.structureType == STRUCTURE_TOWER) && s.energy < s.energyCapacity });//console.log(miniharvester); gridcontrol.memory.workeractive = numberworkers; //console.log(gridcontrol.memory.workeractive); var numberofharvesters = creep.room.find(FIND_MY_CREEPS, { filter: (s) => (s.memory.job == 'harvester')}).length; var numberofbuilders = creep.room.find(FIND_MY_CREEPS, { filter: (s) => (s.memory.job == 'builder')}).length; var numberofupgraders = creep.room.find(FIND_MY_CREEPS, { filter: (s) => (s.memory.job == 'upgrader')}).length; var numberofrepair = creep.room.find(FIND_MY_CREEPS, { filter: (s) => (s.memory.job == 'repair')}).length; var constructionSite = creep.pos.findClosestByPath(FIND_CONSTRUCTION_SITES); var repair = creep.pos.findClosestByPath(FIND_STRUCTURES, { filter: (s) => s.hits < s.hitsMax && s.structureType != STRUCTURE_WALL }); //For when I need feedback, I should write a function for that at some point -.- //console.log(" "); //console.log("harv: " + numberofharvesters); //console.log("build: " +numberofbuilders); //console.log("repair: " +numberofrepair); //console.log("upgrader: " + numberofupgraders); //console.log(energyneed);  if ((creep.memory.job == false || creep.memory.job == undefined) == true){ if (numberofharvesters < miniharvester == true && energyneed != undefined){ creep.memory.job = 'harvester'; } else if ((numberofrepair < gridcontrol.memory.maxrepair == true) && repair > 0){ creep.memory.job = 'repair'; } else if (constructionSite != undefined && numberofbuilders < maxbuilder){ creep.memory.job = 'builder'; } else { creep.memory.job = 'upgrader'; } } else if (creep.memory.job != false) { if(creep.memory.job == 'harvester' && energyneed == undefined){ creep.memory.job = undefined; } if(creep.memory.job == 'builder' && constructionSite == undefined){ creep.memory.job = undefined; } if(creep.memory.job == 'harvester') {jobharvester.run(creep);} else if (creep.memory.job == 'repair') {jobrepair.run(creep);} else if (creep.memory.job == 'builder') {jobbuilder.run(creep);} else if (creep.memory.job == 'upgrader') {jobupgrader.run(creep);} } } };