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