diff --git a/src/runtime/cmd/kata-monitor/main.go b/src/runtime/cmd/kata-monitor/main.go
index 356316dcf2..86b5693d9b 100644
--- a/src/runtime/cmd/kata-monitor/main.go
+++ b/src/runtime/cmd/kata-monitor/main.go
@@ -175,6 +175,15 @@ func main() {
}
func indexPage(w http.ResponseWriter, r *http.Request) {
+ htmlResponse := kataMonitor.IfReturnHTMLResponse(w, r)
+ if htmlResponse {
+ indexPageHTML(w, r)
+ } else {
+ indexPageText(w, r)
+ }
+}
+
+func indexPageText(w http.ResponseWriter, r *http.Request) {
w.Write([]byte("Available HTTP endpoints:\n"))
spacing := 0
@@ -184,13 +193,35 @@ func indexPage(w http.ResponseWriter, r *http.Request) {
}
}
spacing = spacing + 3
+ formatter := fmt.Sprintf("%%-%ds: %%s\n", spacing)
- formattedString := fmt.Sprintf("%%-%ds: %%s\n", spacing)
for _, endpoint := range endpoints {
- w.Write([]byte(fmt.Sprintf(formattedString, endpoint.path, endpoint.desc)))
+ w.Write([]byte(fmt.Sprintf(formatter, endpoint.path, endpoint.desc)))
}
}
+func indexPageHTML(w http.ResponseWriter, r *http.Request) {
+
+ w.Write([]byte("
Available HTTP endpoints:
\n"))
+
+ var formattedString string
+ needLinkPaths := []string{"/metrics", "/sandboxes"}
+
+ w.Write([]byte(""))
+ for _, endpoint := range endpoints {
+ formattedString = fmt.Sprintf("%s: %s\n", endpoint.path, endpoint.desc)
+ for _, linkPath := range needLinkPaths {
+ if linkPath == endpoint.path {
+ formattedString = fmt.Sprintf("%s: %s\n", endpoint.path, endpoint.path, endpoint.desc)
+ break
+ }
+ }
+ formattedString = fmt.Sprintf("- %s
", formattedString)
+ w.Write([]byte(formattedString))
+ }
+ w.Write([]byte("
"))
+}
+
// initLog setup logger
func initLog() {
kataMonitorLog := logrus.WithFields(logrus.Fields{
diff --git a/src/runtime/pkg/kata-monitor/metrics.go b/src/runtime/pkg/kata-monitor/metrics.go
index 7249906cea..e5d9477670 100644
--- a/src/runtime/pkg/kata-monitor/metrics.go
+++ b/src/runtime/pkg/kata-monitor/metrics.go
@@ -78,6 +78,21 @@ func (km *KataMonitor) ProcessMetricsRequest(w http.ResponseWriter, r *http.Requ
scrapeDurationsHistogram.Observe(float64(time.Since(start).Nanoseconds() / int64(time.Millisecond)))
}()
+ // this is likely the same as `kata-runtime metrics `.
+ sandboxID, err := getSandboxIDFromReq(r)
+ if err == nil && sandboxID != "" {
+ metrics, err := GetSandboxMetrics(sandboxID)
+ if err != nil {
+ w.WriteHeader(http.StatusInternalServerError)
+ w.Write([]byte(err.Error()))
+ return
+ }
+ w.Write([]byte(metrics))
+ return
+ }
+
+ // if no sandbox provided, will get all sandbox's metrics.
+
// prepare writer for writing response.
contentType := expfmt.Negotiate(r.Header)
diff --git a/src/runtime/pkg/kata-monitor/monitor.go b/src/runtime/pkg/kata-monitor/monitor.go
index ed3ea5c089..1e60a50b7b 100644
--- a/src/runtime/pkg/kata-monitor/monitor.go
+++ b/src/runtime/pkg/kata-monitor/monitor.go
@@ -27,6 +27,7 @@ const (
RuntimeCRIO = "cri-o"
fsMonitorRetryDelaySeconds = 60
podCacheRefreshDelaySeconds = 5
+ contentTypeHtml = "text/html"
)
// SetLogger sets the logger for katamonitor package.
@@ -194,7 +195,41 @@ func (km *KataMonitor) GetAgentURL(w http.ResponseWriter, r *http.Request) {
// ListSandboxes list all sandboxes running in Kata
func (km *KataMonitor) ListSandboxes(w http.ResponseWriter, r *http.Request) {
sandboxes := km.sandboxCache.getSandboxList()
+ htmlResponse := IfReturnHTMLResponse(w, r)
+ if htmlResponse {
+ listSandboxesHtml(sandboxes, w)
+ } else {
+ listSandboxesText(sandboxes, w)
+ }
+}
+
+func listSandboxesText(sandboxes []string, w http.ResponseWriter) {
for _, s := range sandboxes {
w.Write([]byte(fmt.Sprintf("%s\n", s)))
}
}
+func listSandboxesHtml(sandboxes []string, w http.ResponseWriter) {
+ w.Write([]byte("Sandbox list
\n"))
+ w.Write([]byte("\n"))
+ for _, s := range sandboxes {
+ w.Write([]byte(fmt.Sprintf("- %s: pprof, metrics, agent-url
\n", s, s, s, s)))
+ }
+ w.Write([]byte("
\n"))
+}
+
+// IfReturnHTMLResponse returns true if request accepts html response
+// NOTE: IfReturnHTMLResponse will also set response header to `text/html`
+func IfReturnHTMLResponse(w http.ResponseWriter, r *http.Request) bool {
+ accepts := r.Header["Accept"]
+ for _, accept := range accepts {
+ fields := strings.Split(accept, ",")
+ for _, field := range fields {
+ if field == contentTypeHtml {
+ w.Header().Set("Content-Type", contentTypeHtml)
+ return true
+ }
+ }
+ }
+
+ return false
+}
diff --git a/src/runtime/pkg/kata-monitor/pprof.go b/src/runtime/pkg/kata-monitor/pprof.go
index 5dac2da03c..a2ff76bc30 100644
--- a/src/runtime/pkg/kata-monitor/pprof.go
+++ b/src/runtime/pkg/kata-monitor/pprof.go
@@ -55,8 +55,10 @@ func (km *KataMonitor) proxyRequest(w http.ResponseWriter, r *http.Request) {
}
uri := fmt.Sprintf("http://shim%s", r.URL.String())
+ monitorLog.Debugf("proxyRequest to: %s, uri: %s", socketAddress, uri)
resp, err := client.Get(uri)
if err != nil {
+ serveError(w, http.StatusInternalServerError, fmt.Sprintf("failed to request %s through %s", uri, socketAddress))
return
}