Add idle_timeout to routes API (#603)

* Add inactivity_timeout to routes API

Closes: #544

* Fix failing datastore tests

* Rename inactivity_timeout to idle_timeout

* Update swagger doc

* Update hot fn doc

* Fix json tags

* Add function timeouts docs

* Rewording
This commit is contained in:
Denis Makogon
2017-03-25 19:28:53 +02:00
committed by U Cirello
parent 11d3e29304
commit 7603e6e8fa
12 changed files with 148 additions and 46 deletions

View File

@@ -42,14 +42,18 @@ func getTask(ctx context.Context, url string) (*models.Task, error) {
}
func getCfg(t *models.Task) *task.Config {
timeout := int32(30)
if t.Timeout == nil {
timeout := int32(30)
t.Timeout = &timeout
}
if t.IdleTimeout == nil {
t.IdleTimeout = &timeout
}
cfg := &task.Config{
Image: *t.Image,
Timeout: time.Duration(*t.Timeout) * time.Second,
IdleTimeout: time.Duration(*t.IdleTimeout) * time.Second,
ID: t.ID,
AppName: t.AppName,
Env: t.EnvVars,

View File

@@ -35,7 +35,8 @@ func (t *containerTask) Id() string { return t.cfg.ID }
func (t *containerTask) Route() string { return "" }
func (t *containerTask) Image() string { return t.cfg.Image }
func (t *containerTask) Timeout() time.Duration { return t.cfg.Timeout }
func (t *containerTask) Logger() (stdout, stderr io.Writer) { return t.cfg.Stdout, t.cfg.Stderr }
func (t *containerTask) IdleTimeout() time.Duration { return t.cfg.IdleTimeout }
func (t *containerTask) Logger() (io.Writer, io.Writer) { return t.cfg.Stdout, t.cfg.Stderr }
func (t *containerTask) Volumes() [][2]string { return [][2]string{} }
func (t *containerTask) WorkDir() string { return "" }

View File

@@ -9,15 +9,16 @@ import (
)
type Config struct {
ID string
Path string
Image string
Timeout time.Duration
AppName string
Memory uint64
Env map[string]string
Format string
MaxConcurrency int
ID string
Path string
Image string
Timeout time.Duration
IdleTimeout time.Duration
AppName string
Memory uint64
Env map[string]string
Format string
MaxConcurrency int
Stdin io.Reader
Stdout io.Writer

View File

@@ -61,10 +61,6 @@ import (
// Terminate
// (internal clock)
const (
// Terminate hot function after this timeout
htfnScaleDownTimeout = 30 * time.Second
)
// RunTask helps sending a task.Request into the common concurrency stream.
// Refer to StartWorkers() to understand what this is about.
@@ -264,17 +260,29 @@ func newhtfn(cfg *task.Config, proto protocol.Protocol, tasks <-chan task.Reques
func (hc *htfn) serve(ctx context.Context) {
lctx, cancel := context.WithCancel(ctx)
var wg sync.WaitGroup
cfg := *hc.cfg
logger := logrus.WithFields(logrus.Fields{
"app": cfg.AppName,
"route": cfg.Path,
"image": cfg.Image,
"memory": cfg.Memory,
"format": cfg.Format,
"max_concurrency": cfg.MaxConcurrency,
"idle_timeout": cfg.IdleTimeout,
})
wg.Add(1)
go func() {
defer wg.Done()
for {
inactivity := time.After(htfnScaleDownTimeout)
inactivity := time.After(cfg.IdleTimeout)
select {
case <-lctx.Done():
return
case <-inactivity:
logger.Info("Canceling inactive hot function")
cancel()
case t := <-hc.tasks:
@@ -295,7 +303,6 @@ func (hc *htfn) serve(ctx context.Context) {
}
}()
cfg := *hc.cfg
cfg.Env["FN_FORMAT"] = cfg.Format
cfg.Timeout = 0 // add a timeout to simulate ab.end. failure.
cfg.Stdin = hc.containerIn
@@ -324,14 +331,7 @@ func (hc *htfn) serve(ctx context.Context) {
defer wg.Done()
scanner := bufio.NewScanner(errr)
for scanner.Scan() {
logrus.WithFields(logrus.Fields{
"app": cfg.AppName,
"route": cfg.Path,
"image": cfg.Image,
"memory": cfg.Memory,
"format": cfg.Format,
"max_concurrency": cfg.MaxConcurrency,
}).Info(scanner.Text())
logger.Info(scanner.Text())
}
}()
@@ -339,7 +339,6 @@ func (hc *htfn) serve(ctx context.Context) {
if err != nil {
logrus.WithError(err).Error("hot function failure detected")
}
cancel()
errw.Close()
wg.Wait()
logrus.WithField("result", result).Info("hot function terminated")