Adding update to pause provisioner every 10 seconds if pause is greater
than 10 seconds
This commit is contained in:
parent
7d0578c5b7
commit
32cc0fb222
|
@ -145,17 +145,55 @@ func (p *PausedProvisioner) Prepare(raws ...interface{}) error {
|
|||
|
||||
func (p *PausedProvisioner) Provision(ctx context.Context, ui packersdk.Ui, comm packersdk.Communicator, generatedData map[string]interface{}) error {
|
||||
|
||||
// Use a select to determine if we get cancelled during the wait
|
||||
ui.Say(fmt.Sprintf("Pausing %s before the next provisioner...", p.PauseBefore))
|
||||
minimumTimeForPauseUpdate := float64(10)
|
||||
if p.PauseBefore.Seconds() < minimumTimeForPauseUpdate {
|
||||
// Use a select to determine if we get cancelled during the wait
|
||||
select {
|
||||
case <-time.After(p.PauseBefore):
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
}
|
||||
} else {
|
||||
err := p.updatesWhilePausing(ctx, ui)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return p.Provisioner.Provision(ctx, ui, comm, generatedData)
|
||||
}
|
||||
|
||||
func (p *PausedProvisioner) updatesWhilePausing(ctx context.Context, ui packersdk.Ui) error {
|
||||
updateTime := 10
|
||||
timeTicker := time.NewTicker(time.Duration(updateTime) * time.Second)
|
||||
TotalTime := p.PauseBefore.Seconds()
|
||||
tickerChannel := make(chan bool)
|
||||
var err error
|
||||
go func() {
|
||||
for {
|
||||
select {
|
||||
case <-timeTicker.C:
|
||||
TotalTime -= float64(updateTime)
|
||||
ui.Say(fmt.Sprintf("%v seconds left until the next provisioner", TotalTime))
|
||||
case <-ctx.Done():
|
||||
err = ctx.Err()
|
||||
return
|
||||
case <-tickerChannel:
|
||||
return
|
||||
}
|
||||
}
|
||||
}()
|
||||
time.Sleep(p.PauseBefore)
|
||||
timeTicker.Stop()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
tickerChannel <- true
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// RetriedProvisioner is a Provisioner implementation that retries
|
||||
// the provisioner whenever there's an error.
|
||||
type RetriedProvisioner struct {
|
||||
|
|
|
@ -4,6 +4,7 @@ import (
|
|||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"math"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
|
@ -129,11 +130,8 @@ func TestPausedProvisionerProvision(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestPausedProvisionerProvision_waits(t *testing.T) {
|
||||
startTime := time.Now()
|
||||
waitTime := 50 * time.Millisecond
|
||||
|
||||
prov := &PausedProvisioner{
|
||||
func pausedTestProvisionor(startTime time.Time, waitTime time.Duration) *PausedProvisioner {
|
||||
return &PausedProvisioner{
|
||||
PauseBefore: waitTime,
|
||||
Provisioner: &packersdk.MockProvisioner{
|
||||
ProvFunc: func(context.Context) error {
|
||||
|
@ -145,7 +143,13 @@ func TestPausedProvisionerProvision_waits(t *testing.T) {
|
|||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func TestPausedProvisionerProvision_waits(t *testing.T) {
|
||||
startTime := time.Now()
|
||||
waitTime := 50 * time.Millisecond
|
||||
|
||||
prov := pausedTestProvisionor(startTime, waitTime)
|
||||
err := prov.Provision(context.Background(), testUi(), new(packersdk.MockCommunicator), make(map[string]interface{}))
|
||||
|
||||
if err != nil {
|
||||
|
@ -153,6 +157,51 @@ func TestPausedProvisionerProvision_waits(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestPausedProvisionerProvision_waits_with_updates(t *testing.T) {
|
||||
startTime := time.Now()
|
||||
waitTime := 30 * time.Second
|
||||
|
||||
prov := pausedTestProvisionor(startTime, waitTime)
|
||||
ui := new(packersdk.MockUi)
|
||||
currentTime := time.Now()
|
||||
err := prov.Provision(context.Background(), ui, new(packersdk.MockCommunicator), make(map[string]interface{}))
|
||||
|
||||
if err != nil {
|
||||
t.Fatalf("prov failed: %v", err)
|
||||
}
|
||||
|
||||
// TODO have to put check to get timestamp of when these messages were posted and verify that this is working as intended
|
||||
expectedMessages := []string{
|
||||
fmt.Sprintf("Pausing %s before the next provisioner...", waitTime),
|
||||
"20 seconds left until the next provisioner",
|
||||
"10 seconds left until the next provisioner",
|
||||
}
|
||||
|
||||
if ui.SayMessages[0].Message != expectedMessages[0] {
|
||||
t.Fatalf("expected: %s, got: %s", expectedMessages[0], ui.SayMessages[0].Message)
|
||||
}
|
||||
|
||||
lastTime := currentTime
|
||||
for index, message := range expectedMessages {
|
||||
// Skiping first message as this has already been verified
|
||||
if index == 0 {
|
||||
continue
|
||||
}
|
||||
|
||||
if ui.SayMessages[index].Message != message {
|
||||
t.Fatalf("expected: %s, got: %s", message, ui.SayMessages[index].Message)
|
||||
}
|
||||
|
||||
waitTimeBetweenMessages := math.Round(ui.SayMessages[index].SayTime.Sub(lastTime).Seconds())
|
||||
if waitTimeBetweenMessages != 10 {
|
||||
t.Fatalf("Did not wait the appropriate amount of time message: %v", ui.SayMessages[index].Message)
|
||||
}
|
||||
|
||||
// setting last time to current SayTime
|
||||
lastTime = ui.SayMessages[index].SayTime
|
||||
}
|
||||
}
|
||||
|
||||
func TestPausedProvisionerCancel(t *testing.T) {
|
||||
topCtx, cancelTopCtx := context.WithCancel(context.Background())
|
||||
|
||||
|
|
Loading…
Reference in New Issue