Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

api: add StartedAt in Node.DrainStrategy #6698

Merged
merged 2 commits into from
Nov 15, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions api/nodes.go
Original file line number Diff line number Diff line change
Expand Up @@ -521,6 +521,9 @@ type DrainStrategy struct {
// ForceDeadline is the deadline time for the drain after which drains will
// be forced
ForceDeadline time.Time

// StartedAt is the time the drain process started
StartedAt time.Time
}

// DrainSpec describes a Node's drain behavior.
Expand Down
20 changes: 16 additions & 4 deletions nomad/node_endpoint.go
Original file line number Diff line number Diff line change
Expand Up @@ -523,8 +523,10 @@ func (n *Node) UpdateDrain(args *structs.NodeUpdateDrainRequest,
return fmt.Errorf("node not found")
}

now := time.Now().UTC()

// Update the timestamp of when the node status was updated
args.UpdatedAt = time.Now().Unix()
args.UpdatedAt = now.Unix()

// COMPAT: Remove in 0.9. Attempt to upgrade the request if it is of the old
// format.
Expand All @@ -536,9 +538,19 @@ func (n *Node) UpdateDrain(args *structs.NodeUpdateDrainRequest,
}
}

// Mark the deadline time
if args.DrainStrategy != nil && args.DrainStrategy.Deadline.Nanoseconds() > 0 {
args.DrainStrategy.ForceDeadline = time.Now().Add(args.DrainStrategy.Deadline)
// Setup drain strategy
if args.DrainStrategy != nil {
// Mark start time for the drain
if node.DrainStrategy == nil {
args.DrainStrategy.StartedAt = now
} else {
args.DrainStrategy.StartedAt = node.DrainStrategy.StartedAt
}

// Mark the deadline time
if args.DrainStrategy.Deadline.Nanoseconds() > 0 {
args.DrainStrategy.ForceDeadline = now.Add(args.DrainStrategy.Deadline)
}
}

// Construct the node event
Expand Down
17 changes: 14 additions & 3 deletions nomad/node_endpoint_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -906,6 +906,17 @@ func TestClientEndpoint_UpdateDrain(t *testing.T) {
// now+deadline should be after the forced deadline
require.True(time.Now().Add(strategy.Deadline).After(out.DrainStrategy.ForceDeadline))

drainStartedAt := out.DrainStrategy.StartedAt
// StartedAt should be close to the time the drain started
require.WithinDuration(beforeUpdate, drainStartedAt, 1*time.Second)

// StartedAt shouldn't change if a new request comes while still draining
require.Nil(msgpackrpc.CallWithCodec(codec, "Node.UpdateDrain", dereg, &resp2))
ws = memdb.NewWatchSet()
out, err = state.NodeByID(ws, node.ID)
require.NoError(err)
require.True(out.DrainStrategy.StartedAt.Equal(drainStartedAt))

// Register a system job
job := mock.SystemJob()
require.Nil(s1.State().UpsertJob(10, job))
Expand All @@ -923,16 +934,16 @@ func TestClientEndpoint_UpdateDrain(t *testing.T) {
ws = memdb.NewWatchSet()
out, err = state.NodeByID(ws, node.ID)
require.NoError(err)
require.Len(out.Events, 3)
require.Equal(NodeDrainEventDrainDisabled, out.Events[2].Message)
require.Len(out.Events, 4)
require.Equal(NodeDrainEventDrainDisabled, out.Events[3].Message)

// Check that calling UpdateDrain with the same DrainStrategy does not emit
// a node event.
require.Nil(msgpackrpc.CallWithCodec(codec, "Node.UpdateDrain", dereg, &resp3))
ws = memdb.NewWatchSet()
out, err = state.NodeByID(ws, node.ID)
require.NoError(err)
require.Len(out.Events, 3)
require.Len(out.Events, 4)
}

func TestClientEndpoint_UpdateDrain_ACL(t *testing.T) {
Expand Down
3 changes: 3 additions & 0 deletions nomad/structs/structs.go
Original file line number Diff line number Diff line change
Expand Up @@ -1445,6 +1445,9 @@ type DrainStrategy struct {
// ForceDeadline is the deadline time for the drain after which drains will
// be forced
ForceDeadline time.Time

// StartedAt is the time the drain process started
StartedAt time.Time
}

func (d *DrainStrategy) Copy() *DrainStrategy {
Expand Down