package main

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

	"code.hackerspace.pl/q3k/mirko"
	"github.com/gobuffalo/packr"
	"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 Service struct {
	gr  *graph.Graph
	stm *state.StateManager
}

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

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) Setup(m *mirko.Mirko) {
	assets := packr.NewBox("./assets")
	m.HTTPMux().Handle("/assets/", http.StripPrefix("/assets/", http.FileServer(assets)))
	m.HTTPMux().HandleFunc("/debug/graphviz", s.httpHandleGraphviz)
	statusz.AddStatusPart("Switch Ports", switchportsFragment, s.statusHandleSwitchports)
	statusz.AddStatusPart("Topology", topologyFragment, func(ctx context.Context) interface{} {
		return 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")
}
