package main

import (
	"context"
	"fmt"
	"net/http"
	"sort"
	"strings"

	"github.com/gobuffalo/packr"
	"github.com/golang/glog"
	"github.com/q3k/statusz"
	"vbom.ml/util/sortorder"

	"code.hackerspace.pl/q3k/topo/graph"
	"code.hackerspace.pl/q3k/topo/state"

	pb "code.hackerspace.pl/q3k/topo/proto/control"
)

type ServiceConfig struct {
	DebugListen string
}

type Service struct {
	gr     *graph.Graph
	stm    *state.StateManager
	config ServiceConfig
}

func NewService(gr *graph.Graph, stm *state.StateManager, c ServiceConfig) *Service {
	return &Service{
		gr:     gr,
		stm:    stm,
		config: c,
	}
}

const topologyFragment = `
  <script src="/assets/viz.js"></script>
  <script>

    var viz = new Viz({ workerURL: '/assets/full.render.js' });
	var xmlhttp = new XMLHttpRequest();
	xmlhttp.onreadystatechange = function() {
      if (this.readyState == 4 && this.status == 200) {
        var dot = this.responseText;
        viz.renderSVGElement(dot)
        .then(function(element) {
          document.getElementById("graph").appendChild(element);
        });
      }
    };
    xmlhttp.open('GET', '/debug/graphviz');
    xmlhttp.send();

  </script>
  <div id="graph" style="text-align: center;"></div>
`

const switchportsFragment = `
    <style type="text/css">
		.table td,th {
			background-color: #eee;
			padding: 0.2em 0.4em 0.2em 0.4em;
		}
		.table th {
			background-color: #c0c0c0;
		}
		.table {
			background-color: #fff;
			border-spacing: 0.2em;
			margin-left: auto;
			margin-right: auto;
		}
	</style>
	<div>
	<table class="table">
		<tr>
      		<th>Switch</th>
      		<th>Port</th>
			<th>Link State</th>
			<th>Port Mode</th>
			<th>MTU</th>
			<th>Sync Status</th>
		</tr>
		{{range .Ports }}
		{{ if .Managed }}
		<tr>
		{{ else }}
		<tr style="opacity: 0.5">
		{{ end}}
			<td style="text-align: right;">{{ .Switch }}</td>
			<td>{{ .Name }}</td>
			{{ if eq .State "DOWN" }}
			<td style="background-color: #ff3030;">{{ .State }}</td>
			{{ else }}
			<td>{{ .State }}</td>
			{{ end }}
			<td>{{ .Mode }}</td>
			<td>{{ .MTU }}</td>
			{{ if .Managed }}
			<td style="background-color: #30ff30;">OK</td>
			{{ else }}
			<td><i>Unmanaged</i></td>
			{{ end }}
		</tr>
		{{end}}
	</table>
	</div>
`

func (s *Service) Run() {
	assets := packr.NewBox("./assets")
	http.Handle("/assets/", http.StripPrefix("/assets/", http.FileServer(assets)))
	http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
		http.Redirect(w, r, "/debug/status", http.StatusSeeOther)
	})
	http.HandleFunc("/debug/graphviz", s.httpHandleGraphviz)

	statusz.AddStatusPart("Switch Ports", switchportsFragment, s.statusHandleSwitchports)
	statusz.AddStatusPart("Topology", topologyFragment, func(ctx context.Context) interface{} {
		return nil
	})
	glog.Infof("Debug listening on %s....", s.config.DebugListen)
	http.ListenAndServe(s.config.DebugListen, nil)
}

func (s *Service) statusHandleSwitchports(ctx context.Context) interface{} {
	managedPorts := make(map[string]bool)
	s.gr.Mu.RLock()
	for _, sw := range s.gr.Switches {
		for _, port := range sw.Ports {
			managedPorts[sw.Name+"|"+port.Name] = true
		}
	}
	s.gr.Mu.RUnlock()

	s.stm.Mu.RLock()
	defer s.stm.Mu.RUnlock()

	res := struct {
		Ports []*struct {
			Switch  string
			Name    string
			State   string
			Mode    string
			Managed bool
			MTU     string
		}
	}{}
	for _, sw := range s.stm.Switches {
		for _, po := range sw.Ports {
			state := "INVALID"
			switch po.Proto.LinkState {
			case pb.SwitchPort_LINKSTATE_DOWN:
				state = "DOWN"
			case pb.SwitchPort_LINKSTATE_UP:
				state = "UP"
			}
			mode := "INVALID"
			switch po.Proto.PortMode {
			case pb.SwitchPort_PORTMODE_SWITCHPORT_UNTAGGED:
				mode = fmt.Sprintf("UNTAGGED (%d)", po.Proto.VlanNative)
			case pb.SwitchPort_PORTMODE_SWITCHPORT_TAGGED:
				mode = fmt.Sprintf("TAGGED (%v)", po.Proto.VlanTagged)
			case pb.SwitchPort_PORTMODE_SWITCHPORT_GENERIC:
				mode = "GENERIC"
			case pb.SwitchPort_PORTMODE_ROUTED:
				mode = "ROUTED"
			case pb.SwitchPort_PORTMODE_MANGLED:
				mode = "MANGLED"
			}

			managed := managedPorts[sw.Name+"|"+po.Proto.Name]
			res.Ports = append(res.Ports, &struct {
				Switch  string
				Name    string
				State   string
				Mode    string
				Managed bool
				MTU     string
			}{
				Switch:  sw.Name,
				Name:    po.Proto.Name,
				State:   state,
				Mode:    mode,
				Managed: managed,
				MTU:     fmt.Sprintf("%d", po.Proto.Mtu),
			})
		}
	}

	return res
}

func (s *Service) httpHandleGraphviz(w http.ResponseWriter, r *http.Request) {
	fmt.Fprintf(w, "graph G {\n")
	fmt.Fprintf(w, "  ranksep = 2\n")
	fmt.Fprintf(w, "  splines = polyline\n")
	fmt.Fprintf(w, "  rankdir = LR\n")
	for _, machine := range s.gr.Machines {
		portNames := []string{}
		for _, port := range machine.Ports {
			name := fmt.Sprintf("<%s> %s", port.Name, port.Name)
			portNames = append(portNames, name)
		}
		ports := strings.Join(portNames, "|")
		fmt.Fprintf(w, "  %s [shape=record label=\"{ %s | { %s }}\"]\n", machine.Name, machine.Name, ports)
	}
	for _, sw := range s.gr.Switches {
		portNames := []string{}
		portsOrdered := []*graph.SwitchPort{}
		for _, port := range sw.Ports {
			portsOrdered = append(portsOrdered, port)
		}
		sort.Slice(portsOrdered, func(i, j int) bool {
			return sortorder.NaturalLess(portsOrdered[i].Name, portsOrdered[j].Name)
		})
		for _, port := range portsOrdered {
			name := fmt.Sprintf("<%s> %s", port.Name, port.Name)
			portNames = append(portNames, name)
		}
		ports := strings.Join(portNames, "|")
		fmt.Fprintf(w, "  %s [shape=record label=\"{{ %s } | %s}\"]\n", sw.Name, ports, sw.Name)
	}
	for _, machine := range s.gr.Machines {
		for _, port := range machine.Ports {
			if port.OtherEnd == nil {
				continue
			}
			fmt.Fprintf(w, "  %s:%q:e -- %s:%q:w\n", machine.Name, port.Name, port.OtherEnd.Switch.Name, port.OtherEnd.Name)
		}
	}
	fmt.Fprintf(w, "}\n")
}
