github.com/rohankumardubey/nomad@v0.11.8/scheduler/scheduler.go (about) 1 package scheduler 2 3 import ( 4 "fmt" 5 6 log "github.com/hashicorp/go-hclog" 7 8 memdb "github.com/hashicorp/go-memdb" 9 "github.com/hashicorp/nomad/nomad/state" 10 "github.com/hashicorp/nomad/nomad/structs" 11 ) 12 13 const ( 14 // SchedulerVersion is the version of the scheduler. Changes to the 15 // scheduler that are incompatible with prior schedulers will increment this 16 // version. It is used to disallow dequeueing when the versions do not match 17 // across the leader and the dequeueing scheduler. 18 SchedulerVersion uint16 = 1 19 ) 20 21 // BuiltinSchedulers contains the built in registered schedulers 22 // which are available 23 var BuiltinSchedulers = map[string]Factory{ 24 "service": NewServiceScheduler, 25 "batch": NewBatchScheduler, 26 "system": NewSystemScheduler, 27 } 28 29 // NewScheduler is used to instantiate and return a new scheduler 30 // given the scheduler name, initial state, and planner. 31 func NewScheduler(name string, logger log.Logger, state State, planner Planner) (Scheduler, error) { 32 // Lookup the factory function 33 factory, ok := BuiltinSchedulers[name] 34 if !ok { 35 return nil, fmt.Errorf("unknown scheduler '%s'", name) 36 } 37 38 // Instantiate the scheduler 39 sched := factory(logger, state, planner) 40 return sched, nil 41 } 42 43 // Factory is used to instantiate a new Scheduler 44 type Factory func(log.Logger, State, Planner) Scheduler 45 46 // Scheduler is the top level instance for a scheduler. A scheduler is 47 // meant to only encapsulate business logic, pushing the various plumbing 48 // into Nomad itself. They are invoked to process a single evaluation at 49 // a time. The evaluation may result in task allocations which are computed 50 // optimistically, as there are many concurrent evaluations being processed. 51 // The task allocations are submitted as a plan, and the current leader will 52 // coordinate the commits to prevent oversubscription or improper allocations 53 // based on stale state. 54 type Scheduler interface { 55 // Process is used to handle a new evaluation. The scheduler is free to 56 // apply any logic necessary to make the task placements. The state and 57 // planner will be provided prior to any invocations of process. 58 Process(*structs.Evaluation) error 59 } 60 61 // State is an immutable view of the global state. This allows schedulers 62 // to make intelligent decisions based on allocations of other schedulers 63 // and to enforce complex constraints that require more information than 64 // is available to a local state scheduler. 65 type State interface { 66 // Config returns the configuration of the state store 67 Config() *state.StateStoreConfig 68 69 // Nodes returns an iterator over all the nodes. 70 // The type of each result is *structs.Node 71 Nodes(ws memdb.WatchSet) (memdb.ResultIterator, error) 72 73 // AllocsByJob returns the allocations by JobID 74 AllocsByJob(ws memdb.WatchSet, namespace, jobID string, all bool) ([]*structs.Allocation, error) 75 76 // AllocsByNode returns all the allocations by node 77 AllocsByNode(ws memdb.WatchSet, node string) ([]*structs.Allocation, error) 78 79 // AllocByID returns the allocation 80 AllocByID(ws memdb.WatchSet, allocID string) (*structs.Allocation, error) 81 82 // AllocsByNodeTerminal returns all the allocations by node filtering by terminal status 83 AllocsByNodeTerminal(ws memdb.WatchSet, node string, terminal bool) ([]*structs.Allocation, error) 84 85 // GetNodeByID is used to lookup a node by ID 86 NodeByID(ws memdb.WatchSet, nodeID string) (*structs.Node, error) 87 88 // GetJobByID is used to lookup a job by ID 89 JobByID(ws memdb.WatchSet, namespace, id string) (*structs.Job, error) 90 91 // LatestDeploymentByJobID returns the latest deployment matching the given 92 // job ID 93 LatestDeploymentByJobID(ws memdb.WatchSet, namespace, jobID string) (*structs.Deployment, error) 94 95 // SchedulerConfig returns config options for the scheduler 96 SchedulerConfig() (uint64, *structs.SchedulerConfiguration, error) 97 98 // CSIVolumeByID fetch CSI volumes, containing controller jobs 99 CSIVolumeByID(memdb.WatchSet, string, string) (*structs.CSIVolume, error) 100 101 // CSIVolumeByID fetch CSI volumes, containing controller jobs 102 CSIVolumesByNodeID(memdb.WatchSet, string) (memdb.ResultIterator, error) 103 } 104 105 // Planner interface is used to submit a task allocation plan. 106 type Planner interface { 107 // SubmitPlan is used to submit a plan for consideration. 108 // This will return a PlanResult or an error. It is possible 109 // that this will result in a state refresh as well. 110 SubmitPlan(*structs.Plan) (*structs.PlanResult, State, error) 111 112 // UpdateEval is used to update an evaluation. This should update 113 // a copy of the input evaluation since that should be immutable. 114 UpdateEval(*structs.Evaluation) error 115 116 // CreateEval is used to create an evaluation. This should set the 117 // PreviousEval to that of the current evaluation. 118 CreateEval(*structs.Evaluation) error 119 120 // ReblockEval takes a blocked evaluation and re-inserts it into the blocked 121 // evaluation tracker. This update occurs only in-memory on the leader. The 122 // evaluation must exist in a blocked state prior to this being called such 123 // that on leader changes, the evaluation will be reblocked properly. 124 ReblockEval(*structs.Evaluation) error 125 }