<commit_before>package main

import (
	"encoding/json"
	"fmt"
	"io/ioutil"
	"net/http"
	"os"
	"os/exec"
	"sync"
	"time"

	log "github.com/Sirupsen/logrus"
	"github.com/gorilla/handlers"
	"github.com/gorilla/mux"
	"github.com/newrelic/sidecar/catalog"
	"github.com/newrelic/sidecar/haproxy"
	"gopkg.in/alecthomas/kingpin.v1"
)

const (
	RELOAD_BUFFER = 256
	// A new service usually comes in as three events.
	// By 5 seconds it's usually alive.
	RELOAD_HOLD_DOWN = 5 * time.Second
)

var (
	proxy         *haproxy.HAproxy
	stateLock     sync.Mutex
	reloadChan    chan time.Time
	currentState  *catalog.ServicesState
	updateSuccess bool
)

type CliOpts struct {
	ConfigFile *string
}

type ApiErrors struct {
	Errors []string `json:"errors"`
}

type ApiStatus struct {
	Message     string `json:"message"`
	LastChanged string `json:"last_changed"`
}

func exitWithError(err error, message string) {
	if err != nil {
		log.Fatal("%s: %s", message, err.Error())
	}
}

func parseCommandLine() *CliOpts {
	var opts CliOpts
	opts.ConfigFile = kingpin.Flag("config-file", "The config file to use").Short('f').Default("haproxy-api.toml").String()
	kingpin.Parse()
	return &opts
}

func run(command string) error {
	cmd := exec.Command("/bin/bash", "-c", command)
	err := cmd.Run()
	if err != nil {
		log.Errorf("Error running '%s': %s", command, err.Error())
	}

	return err
}

func healthHandler(response http.ResponseWriter, req *http.Request) {
	defer req.Body.Close()
	response.Header().Set("Content-Type", "application/json")

	errors := make([]string, 0)

	err := run("test -f " + proxy.PidFile + " && ps aux `cat " + proxy.PidFile + "`")
	if err != nil {
		errors = append(errors, "No HAproxy running!")
	}

	stateLock.Lock()
	defer stateLock.Unlock()

	if updateSuccess == false {
		errors = append(errors, "Last attempted HAproxy config write failed!")
	}

	if len(errors) != 0 {
		message, _ := json.Marshal(ApiErrors{errors})
		response.WriteHeader(http.StatusInternalServerError)
		response.Write(message)
		return
	}

	lastChanged := currentState.LastChanged

	message, _ := json.Marshal(ApiStatus{Message: "Healthy!", LastChanged: lastChanged.String()})
	response.Write(message)
}

func stateHandler(response http.ResponseWriter, req *http.Request) {
	defer req.Body.Close()<commit_msg>Make sure we never get nil here.<commit_after>package main

import (
	"encoding/json"
	"fmt"
	"io/ioutil"
	"net/http"
	"os"
	"os/exec"
	"sync"
	"time"

	log "github.com/Sirupsen/logrus"
	"github.com/gorilla/handlers"
	"github.com/gorilla/mux"
	"github.com/newrelic/sidecar/catalog"
	"github.com/newrelic/sidecar/haproxy"
	"gopkg.in/alecthomas/kingpin.v1"
)

const (
	RELOAD_BUFFER = 256
	// A new service usually comes in as three events.
	// By 5 seconds it's usually alive.
	RELOAD_HOLD_DOWN = 5 * time.Second
)

var (
	proxy         *haproxy.HAproxy
	stateLock     sync.Mutex
	reloadChan    chan time.Time
	currentState  *catalog.ServicesState
	updateSuccess bool
)

type CliOpts struct {
	ConfigFile *string
}

type ApiErrors struct {
	Errors []string `json:"errors"`
}

type ApiStatus struct {
	Message     string `json:"message"`
	LastChanged string `json:"last_changed"`
}

func exitWithError(err error, message string) {
	if err != nil {
		log.Fatal("%s: %s", message, err.Error())
	}
}

func parseCommandLine() *CliOpts {
	var opts CliOpts
	opts.ConfigFile = kingpin.Flag("config-file", "The config file to use").Short('f').Default("haproxy-api.toml").String()
	kingpin.Parse()
	return &opts
}

func run(command string) error {
	cmd := exec.Command("/bin/bash", "-c", command)
	err := cmd.Run()
	if err != nil {
		log.Errorf("Error running '%s': %s", command, err.Error())
	}

	return err
}

func healthHandler(response http.ResponseWriter, req *http.Request) {
	defer req.Body.Close()
	response.Header().Set("Content-Type", "application/json")

	errors := make([]string, 0)

	err := run("test -f " + proxy.PidFile + " && ps aux `cat " + proxy.PidFile + "`")
	if err != nil {
		errors = append(errors, "No HAproxy running!")
	}

	stateLock.Lock()
	defer stateLock.Unlock()

	if updateSuccess == false {
		errors = append(errors, "Last attempted HAproxy config write failed!")
	}

	if errors != nil && len(errors) != 0 {
		message, _ := json.Marshal(ApiErrors{errors})
		response.WriteHeader(http.StatusInternalServerError)
		response.Write(message)
		return
	}

	lastChanged := currentState.LastChanged

	message, _ := json.Marshal(ApiStatus{Message: "Healthy!", LastChanged: lastChanged.String()})
	response.Write(message)
}

func stateHandler(response http.ResponseWriter, req *http.Request) {
	defer req.Body.Close()
{'fraction_non_alphanumeric': 0.1474025974025974, 'fraction_numerical': 0.003463203463203463, 'mean_word_length': 4.23922902494331, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '576458', 'n_tokens_mistral': 1681, 'n_tokens_neox': 1626, 'n_words': 377}