refactor term interrupts & have RunContext take a conf struct now

This commit is contained in:
Adrien Delorme 2020-05-08 12:05:14 +02:00
parent 532a69c968
commit 2f63e4e79d
3 changed files with 50 additions and 35 deletions

View File

@ -6,12 +6,9 @@ import (
"fmt"
"log"
"math"
"os"
"os/signal"
"strconv"
"strings"
"sync"
"syscall"
"github.com/hashicorp/hcl/v2"
"github.com/hashicorp/hcl/v2/hclparse"
@ -29,30 +26,15 @@ type BuildCommand struct {
}
func (c *BuildCommand) Run(args []string) int {
buildCtx, cancelBuildCtx := context.WithCancel(context.Background())
// Handle interrupts for this build
sigCh := make(chan os.Signal, 1)
signal.Notify(sigCh, os.Interrupt, syscall.SIGTERM)
defer func() {
cancelBuildCtx()
signal.Stop(sigCh)
close(sigCh)
}()
go func() {
select {
case sig := <-sigCh:
if sig == nil {
// context got cancelled and this closed chan probably
// triggered first
return
}
c.Ui.Error(fmt.Sprintf("Cancelling build after receiving %s", sig))
cancelBuildCtx()
case <-buildCtx.Done():
}
}()
buildCtx, cleanup := handleTermInterrupt(c.Ui)
defer cleanup()
return c.RunContext(buildCtx, args)
cfg, ret := c.ParseArgs(args)
if ret != 0 {
return ret
}
return c.RunContext(buildCtx, cfg)
}
// Config is the command-configuration parsed from the command line.
@ -207,11 +189,7 @@ func (m *Meta) GetConfigFromJSON(path string) (BuildStarter, int) {
}, ret
}
func (c *BuildCommand) RunContext(buildCtx context.Context, args []string) int {
cfg, ret := c.ParseArgs(args)
if ret != 0 {
return ret
}
func (c *BuildCommand) RunContext(buildCtx context.Context, cfg Config) int {
packerStarter, ret := c.GetConfig(cfg.Path)
if ret != 0 {

View File

@ -71,7 +71,7 @@ func (ba *BuildArgs) AddFlagSets(flags *flag.FlagSet) {
func (ba *BuildArgs) ParseArgvs(args []string) int {
flags := flag.NewFlagSet("build", flag.ContinueOnError)
flags.Usage = func() { ba.Ui.Say(ba.Help()) }
// flags.Usage = func() { ba.Ui.Say(ba.Help()) }
ba.AddFlagSets(flags)
err := flags.Parse(args)
if err != nil {
@ -96,7 +96,7 @@ type BuildArgs struct {
func (ca *ConsoleArgs) ParseArgvs(args []string) int {
flags := flag.NewFlagSet("console", flag.ContinueOnError)
flags.Usage = func() { ca.Ui.Say(ca.Help()) }
// flags.Usage = func() { ca.Ui.Say(ca.Help()) }
ca.AddFlagSets(flags)
err := flags.Parse(args)
if err != nil {
@ -118,7 +118,7 @@ func (fa *FixArgs) AddFlagSets(flags *flag.FlagSet) {
func (fa *FixArgs) ParseArgvs(args []string) int {
flags := flag.NewFlagSet("fix", flag.ContinueOnError)
flags.Usage = func() { fa.Ui.Say(fa.Help()) }
// flags.Usage = func() { fa.Ui.Say(fa.Help()) }
fa.AddFlagSets(flags)
err := flags.Parse(args)
if err != nil {
@ -143,7 +143,7 @@ func (va *ValidateArgs) AddFlagSets(flags *flag.FlagSet) {
func (va *ValidateArgs) ParseArgvs(args []string) int {
flags := flag.NewFlagSet("validate", flag.ContinueOnError)
flags.Usage = func() { va.Ui.Say(va.Help()) }
// flags.Usage = func() { va.Ui.Say(va.Help()) }
va.AddFlagSets(flags)
err := flags.Parse(args)
if err != nil {

37
command/signal.go Normal file
View File

@ -0,0 +1,37 @@
package command
import (
"context"
"fmt"
"os"
"os/signal"
"syscall"
"github.com/hashicorp/packer/packer"
)
func handleTermInterrupt(ui packer.Ui) (context.Context, func()) {
ctx, cancelCtx := context.WithCancel(context.Background())
// Handle interrupts for this build
sigCh := make(chan os.Signal, 1)
signal.Notify(sigCh, os.Interrupt, syscall.SIGTERM)
cleanup := func() {
cancelCtx()
signal.Stop(sigCh)
close(sigCh)
}
go func() {
select {
case sig := <-sigCh:
if sig == nil {
// context got cancelled and this closed chan probably
// triggered first
return
}
ui.Error(fmt.Sprintf("Cancelling build after receiving %s", sig))
cancelCtx()
case <-ctx.Done():
}
}()
return ctx, cleanup
}