blob: 05964fa43b5febaa20a6d044942b97e8cc93c3ca [file] [log] [blame]
Serge Bazanski8d7843c2018-10-04 10:37:36 +01001package main
2
Serge Bazanski46765082018-10-06 12:32:01 +01003import (
Serge Bazanskic7be4a12018-10-06 13:18:05 +01004 "context"
5 "fmt"
Serge Bazanski46765082018-10-06 12:32:01 +01006 "net/http"
Serge Bazanskide869df2018-10-06 13:55:49 +01007 "strings"
Serge Bazanski8d7843c2018-10-04 10:37:36 +01008
Serge Bazanski46765082018-10-06 12:32:01 +01009 "code.hackerspace.pl/q3k/topo/graph"
Serge Bazanskic7be4a12018-10-06 13:18:05 +010010 "github.com/gobuffalo/packr"
Serge Bazanski46765082018-10-06 12:32:01 +010011 "github.com/golang/glog"
Serge Bazanskic7be4a12018-10-06 13:18:05 +010012 "github.com/q3k/statusz"
Serge Bazanski46765082018-10-06 12:32:01 +010013)
14
15type ServiceConfig struct {
16 DebugListen string
17}
18
19type Service struct {
20 gr *graph.Graph
21 config ServiceConfig
22}
23
24func NewService(gr *graph.Graph, c ServiceConfig) *Service {
25 return &Service{
26 gr: gr,
27 config: c,
28 }
29}
30
Serge Bazanskic7be4a12018-10-06 13:18:05 +010031type TopologyStatus struct {
32}
33
34const topologyFragment = `
35 <script src="/assets/viz.js"></script>
36 <script>
37
38 var viz = new Viz({ workerURL: '/assets/full.render.js' });
39 var xmlhttp = new XMLHttpRequest();
40 xmlhttp.onreadystatechange = function() {
41 if (this.readyState == 4 && this.status == 200) {
42 var dot = this.responseText;
43 viz.renderSVGElement(dot)
44 .then(function(element) {
45 document.body.appendChild(element);
46 });
47 }
48 };
49 xmlhttp.open('GET', '/debug/graphviz');
50 xmlhttp.send();
51
52 </script>
53`
54
Serge Bazanski46765082018-10-06 12:32:01 +010055func (s *Service) Run() {
Serge Bazanskic7be4a12018-10-06 13:18:05 +010056 assets := packr.NewBox("./assets")
57 http.Handle("/assets/", http.StripPrefix("/assets/", http.FileServer(assets)))
58
Serge Bazanski46765082018-10-06 12:32:01 +010059 http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
60 http.Redirect(w, r, "/debug/status", http.StatusSeeOther)
61 })
Serge Bazanskic7be4a12018-10-06 13:18:05 +010062
63 http.HandleFunc("/debug/graphviz", func(w http.ResponseWriter, r *http.Request) {
64 fmt.Fprintf(w, "graph G {\n")
Serge Bazanskide869df2018-10-06 13:55:49 +010065 fmt.Fprintf(w, " rankdir = LR\n")
Serge Bazanskic7be4a12018-10-06 13:18:05 +010066 for _, machine := range s.gr.Machines {
Serge Bazanskide869df2018-10-06 13:55:49 +010067 portNames := []string{}
Serge Bazanskic7be4a12018-10-06 13:18:05 +010068 for _, port := range machine.Ports {
Serge Bazanskide869df2018-10-06 13:55:49 +010069 name := fmt.Sprintf("<%s> %s", port.Name, port.Name)
70 portNames = append(portNames, name)
Serge Bazanskic7be4a12018-10-06 13:18:05 +010071 }
Serge Bazanskide869df2018-10-06 13:55:49 +010072 ports := strings.Join(portNames, "|")
73 fmt.Fprintf(w, " %s [shape=record label=\"{ %s | { %s }}\"]\n", machine.Name, machine.Name, ports)
Serge Bazanskic7be4a12018-10-06 13:18:05 +010074 }
75 for _, sw := range s.gr.Switches {
Serge Bazanskide869df2018-10-06 13:55:49 +010076 portNames := []string{}
Serge Bazanskic7be4a12018-10-06 13:18:05 +010077 for _, port := range sw.Ports {
Serge Bazanskide869df2018-10-06 13:55:49 +010078 name := fmt.Sprintf("<%s> %s", port.Name, port.Name)
79 portNames = append(portNames, name)
Serge Bazanskic7be4a12018-10-06 13:18:05 +010080 }
Serge Bazanskide869df2018-10-06 13:55:49 +010081 ports := strings.Join(portNames, "|")
82 fmt.Fprintf(w, " %s [shape=record label=\"{{ %s } | %s}\"]\n", sw.Name, ports, sw.Name)
Serge Bazanskic7be4a12018-10-06 13:18:05 +010083 }
84 for _, machine := range s.gr.Machines {
85 for _, port := range machine.Ports {
86 if port.OtherEnd == nil {
87 continue
88 }
Serge Bazanskide869df2018-10-06 13:55:49 +010089 fmt.Fprintf(w, " %s:%q -- %s:%q\n", machine.Name, port.Name, port.OtherEnd.Switch.Name, port.OtherEnd.Name)
Serge Bazanskic7be4a12018-10-06 13:18:05 +010090 }
91 }
92 fmt.Fprintf(w, "}\n")
93 })
94
95 statusz.AddStatusPart("Topology", topologyFragment, func(ctx context.Context) interface{} {
96 return &TopologyStatus{}
97 })
Serge Bazanski46765082018-10-06 12:32:01 +010098 glog.Infof("Debug listening on %s....", s.config.DebugListen)
99 http.ListenAndServe(s.config.DebugListen, nil)
Serge Bazanski8d7843c2018-10-04 10:37:36 +0100100}