func MakeAlertHandler(sq ServiceQuery) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		log.Println("Alert received.")
		body, readErr := ioutil.ReadAll(r.Body)
		log.Println(string(body))
		if readErr != nil {
			w.WriteHeader(http.StatusBadRequest)
			w.Write([]byte("Unable to read alert."))
			log.Println(readErr)
			return
		}
		var req requests.PrometheusAlert
		err := json.Unmarshal(body, &req)
		if err != nil {
			w.WriteHeader(http.StatusBadRequest)
			w.Write([]byte("Unable to parse alert, bad format."))
			log.Println(err)
			return
		}
		errors := handleAlerts(&req, sq)
		if len(errors) > 0 {
			log.Println(errors)
			var errorOutput string
			for d, err := range errors {
				errorOutput += fmt.Sprintf("[%d] %s\n", d, err)
			}
			w.WriteHeader(http.StatusInternalServerError)
			w.Write([]byte(errorOutput))
			return
		}
		w.WriteHeader(http.StatusOK)
	}
}
MakeAlertHandler handles alerts from Prometheus Alertmanager
package handlers
import (
	"context"
	"encoding/json"
	"io/ioutil"
	"log"
	"net/http"
	"strconv"
	"fmt"
	"github.com/docker/docker/api/types"
	"github.com/docker/docker/client"
	"github.com/openfaas/faas/gateway/requests"
)
const DefaultMaxReplicas = 20
type ServiceQuery interface {
	GetReplicas(service string) (currentReplicas uint64, maxReplicas uint64, err error)
	SetReplicas(service string, count uint64) error
}
func NewSwarmServiceQuery(c *client.Client) ServiceQuery {
	return SwarmServiceQuery{
		c: c,
	}
}
type SwarmServiceQuery struct {
	c *client.Client
}
func (s SwarmServiceQuery) GetReplicas(serviceName string) (uint64, uint64, error) {
	var err error
	var currentReplicas uint64
	maxReplicas := uint64(DefaultMaxReplicas)
	opts := types.ServiceInspectOptions{
		InsertDefaults: true,
	}
	service, _, err := s.c.ServiceInspectWithRaw(context.Background(), serviceName, opts)
	if err == nil {
		currentReplicas = *service.Spec.Mode.Replicated.Replicas
		replicaLabel := service.Spec.TaskTemplate.ContainerSpec.Labels["com.faas.max_replicas"]
		if len(replicaLabel) > 0 {
			maxReplicasLabel, err := strconv.Atoi(replicaLabel)
			if err != nil {
				log.Printf("Bad replica count: %s, should be uint.\n", replicaLabel)
			} else {
				maxReplicas = uint64(maxReplicasLabel)
			}
		}
	}
	return currentReplicas, maxReplicas, err
}
func (s SwarmServiceQuery) SetReplicas(serviceName string, count uint64) error {
	opts := types.ServiceInspectOptions{
		InsertDefaults: true,
	}
	service, _, err := s.c.ServiceInspectWithRaw(context.Background(), serviceName, opts)
	if err == nil {
		service.Spec.Mode.Replicated.Replicas = &count
		updateOpts := types.ServiceUpdateOptions{}
		updateOpts.RegistryAuthFrom = types.RegistryAuthFromSpec
		_, updateErr := s.c.ServiceUpdate(context.Background(), service.ID, service.Version, service.Spec, updateOpts)
		if updateErr != nil {
			err = updateErr
		}
	}
	return err
}