func (p *Ping) printStats(c map[int]float64, s []float64) {
	r := calcStats(c, s)
	totalReq := r["sum"] + c[-1]
	failPct := 100 - (100*r["sum"])/totalReq
	fmt.Printf("\n--- %s HTTP ping statistics --- \n", p.host)
	fmt.Printf("%.0f requests transmitted, %.0f replies received, %.0f%% requests failed\n", totalReq, r["sum"], failPct)
	fmt.Printf("HTTP Round-trip min/avg/max = %.2f/%.2f/%.2f ms\n", r["min"], r["avg"], r["max"])
	for k, v := range c {
		if k < 0 {
			continue
		}
		progress := fmt.Sprintf("%-20s", strings.Repeat("\u2588", int(v*100/(totalReq)/5)))
		fmt.Printf("HTTP Code [%d] responses : [%s] %.2f%% \n", k, progress, v*100/(totalReq))
	}
}
printStats prints out the footer
package ping
import (
	"context"
	"crypto/tls"
	"encoding/json"
	"fmt"
	"io"
	"io/ioutil"
	"net"
	"net/http"
	"net/http/httptrace"
	"net/url"
	"os"
	"os/signal"
	"regexp"
	"strings"
	"time"
	"github.com/mehrdadrad/mylg/cli"
)
var stdout *os.File
type Ping struct {
	url           string
	host          string
	interval      time.Duration
	timeout       time.Duration
	count         int
	method        string
	uAgent        string
	buf           string
	transport     *http.Transport
	rAddr         net.Addr
	nsTime        time.Duration
	quiet         bool
	dCompress     bool
	kAlive        bool
	TLSSkipVerify bool
	tracerEnabled bool
	fmtJSON       bool
	ipv4          bool
	ipv6          bool
}
type Result struct {
	StatusCode int
	TotalTime  float64
	Size       int
	Proto      string
	Server     string
	Status     string
	Trace      Trace
}
type Trace struct {
	ConnectionTime  float64
	TimeToFirstByte float64
}
func (p Ping) IPVersion(t string) string {
	if p.ipv4 {
		return fmt.Sprintf("%s4", t)
	} else if p.ipv6 {
		return fmt.Sprintf("%s6", t)
	}
	return t
}
func (r Result) PrintPingResult(p *Ping, seq int, err error) {
	pStrPrefix := "HTTP Response seq=%d, "
	pStrSuffix := "proto=%s, status=%d, size=%d Bytes, time=%.3f ms"
	pStrSuffixHead := "proto=%s, status=%d, time=%.3f ms"
	pStrTrace := ", connection=%.3f ms, first byte read=%.3f ms\n"
	if p.quiet {
		if err != nil {
			fmt.Printf("!")
			return
		}
		fmt.Printf(".")
		return
	}
	if err != nil {
		errmsg := strings.Split(err.Error(), ": ")
		fmt.Printf(pStrPrefix+"%s\n", seq, errmsg[len(errmsg)-1])
		return
	}
	if p.method == "HEAD" {
		if p.tracerEnabled {
			fmt.Printf(pStrPrefix+pStrSuffixHead+pStrTrace, seq, r.Proto, r.StatusCode, r.TotalTime*1e3, r.Trace.ConnectionTime, r.Trace.TimeToFirstByte)
			return
		}
		fmt.Printf(pStrPrefix+pStrSuffixHead+"\n", seq, r.Proto, r.StatusCode, r.TotalTime*1e3)
		return
	}
	if p.tracerEnabled {
		fmt.Printf(pStrPrefix+pStrSuffix+pStrTrace, seq, r.Proto, r.StatusCode, r.Size, r.TotalTime*1e3, r.Trace.ConnectionTime, r.Trace.TimeToFirstByte)
		return
	}
	fmt.Printf(pStrPrefix+pStrSuffix+"\n", seq, r.Proto, r.StatusCode, r.Size, r.TotalTime*1e3)
	return
}
func NewPing(args string, cfg cli.Config) (*Ping, error) {
	URL, flag := cli.Flag(args)
	if _, ok := flag["help"]; ok || URL == "" {
		help(cfg)
		return nil, fmt.Errorf("")
	}
	URL = Normalize(URL)
	u, err := url.Parse(URL)
	if err != nil {
		return &Ping{}, fmt.Errorf("cannot parse url")
	}
	host, _, err := net.SplitHostPort(u.Host)
	if err != nil {
		host = u.Host
	}
	sTime := time.Now()
	p := &Ping{
		url:           URL,
		host:          u.Host,
		buf:           cli.SetFlag(flag, "d", "mylg").(string),
		count:         cli.SetFlag(flag, "c", cfg.Hping.Count).(int),
		tracerEnabled: cli.SetFlag(flag, "trace", false).(bool),
		fmtJSON:       cli.SetFlag(flag, "json", false).(bool),
		uAgent:        cli.SetFlag(flag, "u", "myLG (http://mylg.io)").(string),
		dCompress:     cli.SetFlag(flag, "dc", false).(bool),
		kAlive:        cli.SetFlag(flag, "k", false).(bool),
		TLSSkipVerify: cli.SetFlag(flag, "nc", false).(bool),
		quiet:         cli.SetFlag(flag, "q", false).(bool),
		ipv4:          cli.SetFlag(flag, "4", false).(bool),
		ipv6:          cli.SetFlag(flag, "6", false).(bool),
		nsTime:        time.Since(sTime),
	}
	ipAddr, err := net.ResolveIPAddr(p.IPVersion("ip"), host)
	if err != nil {
		return &Ping{}, fmt.Errorf("cannot resolve %s: Unknown host", host)
	}
	p.rAddr = ipAddr
	interval := cli.SetFlag(flag, "i", cfg.Hping.Interval).(string)
	p.interval, err = time.ParseDuration(interval)
	if err != nil {
		return p, fmt.Errorf("Failed to parse interval: %s. Correct syntax is <number>s/ms", err)
	}
	timeout := cli.SetFlag(flag, "t", cfg.Hping.Timeout).(string)
	p.timeout, err = time.ParseDuration(timeout)
	if err != nil {
		return p, fmt.Errorf("Failed to parse timeout: %s. Correct syntax is <number>s/ms", err)
	}
	p.method = cli.SetFlag(flag, "m", cfg.Hping.Method).(string)
	p.method = strings.ToUpper(p.method)
	if p.fmtJSON {
		muteStdout()
	}
	p.setTransport()
	return p, nil
}
func Normalize(URL string) string {
	re := regexp.MustCompile(`(?i)https{0,1}: 
	if !re.MatchString(URL) {
		URL = fmt.Sprintf("http://%s", URL)
	}
	return URL
}
func (p *Ping) Run() {
	if p.method != "GET" && p.method != "POST" && p.method != "HEAD" {
		fmt.Printf("Error: Method '%s' not recognized.\n", p.method)
		return
	}
	var (
		sigCh = make(chan os.Signal, 1)
		c     = make(map[int]float64, 10)
		s     []float64
	)
	signal.Notify(sigCh, os.Interrupt)
	defer signal.Stop(sigCh)
	fmt.Printf("HPING %s (%s), Method: %s, DNSLookup: %.4f ms\n", p.host, p.rAddr, p.method, p.nsTime.Seconds()*1e3)
LOOP:
	for i := 0; i < p.count; i++ {
		if r, err := p.Ping(); err == nil {
			r.PrintPingResult(p, i, err)
			c[r.StatusCode]++
			s = append(s, r.TotalTime*1e3)
		} else {
			c[-1]++
			r.PrintPingResult(p, i, err)
		}
		select {
		case <-sigCh:
			break LOOP
		default:
		}
		time.Sleep(p.interval)
	}
	if p.fmtJSON {
		unMuteStdout()
		p.printStatsJSON(c, s)
	} else {
		p.printStats(c, s)
	}
}