mirror of
https://github.com/kubeshark/kubeshark.git
synced 2025-09-05 04:23:09 +00:00
Service Map (#623)
* debug builds and gcflags * update dockerfile for debug * service map routes and controller * service map graph structure * service map interface and new methods * adding service map edges from mizu entries * new service map count methods * implementing the status endpoint * ServiceMapResponse and ServiceMapEdge models * service map get endpoint logic * reset logic and endpoint * fixed service map get status * improvements to graph node structure * front-end implementation and service map buttons * new render endpoint to render the graph in real time * spinner sass * new ServiceMapModal component * testing react-force-graph-2d lib * Improvements to service map graph structure, added node id and updated edge source/destination type * Revert "testing react-force-graph-2d lib" This reverts commit1153938386
. * testing react-graph-vis lib * updated to work with react-graph-vis lib * removed render endpoint * go mod tidy * serviceMap config flag * using the serviceMap config flag * passing mizu config to service map as a dependency * service map tests * Removed print functions * finished service map tests * new service property * service map controller tests * moved service map reset button to service map modal reset closes the modal * service map modal refresh button and logic * reset button resets data and refresh * service map modal close button * node size/edge size based on the count value edge color based on protocol * nodes and edges shadow * enabled physics to avoid node overlap, changed kafka protocol color to dark green * showing edges count values and fixed bidirectional edges overlap * go mod tidy * removed console.log * Using the destination node protocol instead of the source node protocol * Revert "debug builds and gcflags" Addressed by #624 and #626 This reverts commit17ecaece3e
. * Revert "update dockerfile for debug" Addressed by #635 This reverts commit5dfc15b140
. * using the entire tap Protocol struct instead of only the protocol name * using the backend protocol background color for node colors * fixed test, the node list order can change * re-factoring to get 100% coverage * using protocol colors just for edges * re-factored service map to use TCP Entry data. Node key is the entry ip-address instead of the name * fallback to ip-address when entry name is unresolved * re-factored front-end * adjustment to main div style * added support for multiple protocols for the same edge * using the item protocol instead of the extension variable * fixed controller tests * displaying service name and ip-address on graph nodes * fixed service map test, we cannot guarantee the slice order * auth middleware * created a new pkg for the service map * re-factoring * re-factored front-end * reverting the import order as previous * Aligning with other UI feature flags handling * we don't need to get the status anymore, we have window["isServiceMapEnabled"] * small adjustments * renamed from .tsx to .ts * button styles and minor improvements * moved service map modal from trafficPage to app component Co-authored-by: Igor Gov <igor.govorov1@gmail.com>
This commit is contained in:
committed by
GitHub
parent
7477f867f9
commit
d5fd2ff1da
36
agent/pkg/controllers/service_map_controller.go
Normal file
36
agent/pkg/controllers/service_map_controller.go
Normal file
@@ -0,0 +1,36 @@
|
||||
package controllers
|
||||
|
||||
import (
|
||||
"mizuserver/pkg/servicemap"
|
||||
"net/http"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
type ServiceMapController struct {
|
||||
service servicemap.ServiceMap
|
||||
}
|
||||
|
||||
func NewServiceMapController() *ServiceMapController {
|
||||
return &ServiceMapController{
|
||||
service: servicemap.GetInstance(),
|
||||
}
|
||||
}
|
||||
|
||||
func (s *ServiceMapController) Status(c *gin.Context) {
|
||||
c.JSON(http.StatusOK, s.service.GetStatus())
|
||||
}
|
||||
|
||||
func (s *ServiceMapController) Get(c *gin.Context) {
|
||||
response := &servicemap.ServiceMapResponse{
|
||||
Status: s.service.GetStatus(),
|
||||
Nodes: s.service.GetNodes(),
|
||||
Edges: s.service.GetEdges(),
|
||||
}
|
||||
c.JSON(http.StatusOK, response)
|
||||
}
|
||||
|
||||
func (s *ServiceMapController) Reset(c *gin.Context) {
|
||||
s.service.Reset()
|
||||
s.Status(c)
|
||||
}
|
147
agent/pkg/controllers/service_map_controller_test.go
Normal file
147
agent/pkg/controllers/service_map_controller_test.go
Normal file
@@ -0,0 +1,147 @@
|
||||
package controllers
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"mizuserver/pkg/servicemap"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
"github.com/stretchr/testify/suite"
|
||||
"github.com/up9inc/mizu/shared"
|
||||
tapApi "github.com/up9inc/mizu/tap/api"
|
||||
)
|
||||
|
||||
const (
|
||||
a = "aService"
|
||||
b = "bService"
|
||||
Ip = "127.0.0.1"
|
||||
Port = "80"
|
||||
)
|
||||
|
||||
var (
|
||||
TCPEntryA = &tapApi.TCP{
|
||||
Name: a,
|
||||
Port: Port,
|
||||
IP: fmt.Sprintf("%s.%s", Ip, a),
|
||||
}
|
||||
TCPEntryB = &tapApi.TCP{
|
||||
Name: b,
|
||||
Port: Port,
|
||||
IP: fmt.Sprintf("%s.%s", Ip, b),
|
||||
}
|
||||
)
|
||||
|
||||
var ProtocolHttp = &tapApi.Protocol{
|
||||
Name: "http",
|
||||
LongName: "Hypertext Transfer Protocol -- HTTP/1.1",
|
||||
Abbreviation: "HTTP",
|
||||
Macro: "http",
|
||||
Version: "1.1",
|
||||
BackgroundColor: "#205cf5",
|
||||
ForegroundColor: "#ffffff",
|
||||
FontSize: 12,
|
||||
ReferenceLink: "https://datatracker.ietf.org/doc/html/rfc2616",
|
||||
Ports: []string{"80", "443", "8080"},
|
||||
Priority: 0,
|
||||
}
|
||||
|
||||
type ServiceMapControllerSuite struct {
|
||||
suite.Suite
|
||||
|
||||
c *ServiceMapController
|
||||
w *httptest.ResponseRecorder
|
||||
g *gin.Context
|
||||
}
|
||||
|
||||
func (s *ServiceMapControllerSuite) SetupTest() {
|
||||
s.c = NewServiceMapController()
|
||||
s.c.service.SetConfig(&shared.MizuAgentConfig{
|
||||
ServiceMap: true,
|
||||
})
|
||||
s.c.service.NewTCPEntry(TCPEntryA, TCPEntryB, ProtocolHttp)
|
||||
|
||||
s.w = httptest.NewRecorder()
|
||||
s.g, _ = gin.CreateTestContext(s.w)
|
||||
}
|
||||
|
||||
func (s *ServiceMapControllerSuite) TestGetStatus() {
|
||||
assert := s.Assert()
|
||||
|
||||
s.c.Status(s.g)
|
||||
assert.Equal(http.StatusOK, s.w.Code)
|
||||
|
||||
var status servicemap.ServiceMapStatus
|
||||
err := json.Unmarshal(s.w.Body.Bytes(), &status)
|
||||
assert.NoError(err)
|
||||
assert.Equal("enabled", status.Status)
|
||||
assert.Equal(1, status.EntriesProcessedCount)
|
||||
assert.Equal(2, status.NodeCount)
|
||||
assert.Equal(1, status.EdgeCount)
|
||||
}
|
||||
|
||||
func (s *ServiceMapControllerSuite) TestGet() {
|
||||
assert := s.Assert()
|
||||
|
||||
s.c.Get(s.g)
|
||||
assert.Equal(http.StatusOK, s.w.Code)
|
||||
|
||||
var response servicemap.ServiceMapResponse
|
||||
err := json.Unmarshal(s.w.Body.Bytes(), &response)
|
||||
assert.NoError(err)
|
||||
|
||||
// response status
|
||||
assert.Equal("enabled", response.Status.Status)
|
||||
assert.Equal(1, response.Status.EntriesProcessedCount)
|
||||
assert.Equal(2, response.Status.NodeCount)
|
||||
assert.Equal(1, response.Status.EdgeCount)
|
||||
|
||||
// response nodes
|
||||
aNode := servicemap.ServiceMapNode{
|
||||
Id: 1,
|
||||
Name: TCPEntryA.IP,
|
||||
Entry: TCPEntryA,
|
||||
Count: 1,
|
||||
}
|
||||
bNode := servicemap.ServiceMapNode{
|
||||
Id: 2,
|
||||
Name: TCPEntryB.IP,
|
||||
Entry: TCPEntryB,
|
||||
Count: 1,
|
||||
}
|
||||
assert.Contains(response.Nodes, aNode)
|
||||
assert.Contains(response.Nodes, bNode)
|
||||
assert.Len(response.Nodes, 2)
|
||||
|
||||
// response edges
|
||||
assert.Equal([]servicemap.ServiceMapEdge{
|
||||
{
|
||||
Source: aNode,
|
||||
Destination: bNode,
|
||||
Protocol: ProtocolHttp,
|
||||
Count: 1,
|
||||
},
|
||||
}, response.Edges)
|
||||
}
|
||||
|
||||
func (s *ServiceMapControllerSuite) TestGetReset() {
|
||||
assert := s.Assert()
|
||||
|
||||
s.c.Reset(s.g)
|
||||
assert.Equal(http.StatusOK, s.w.Code)
|
||||
|
||||
var status servicemap.ServiceMapStatus
|
||||
err := json.Unmarshal(s.w.Body.Bytes(), &status)
|
||||
assert.NoError(err)
|
||||
assert.Equal("enabled", status.Status)
|
||||
assert.Equal(0, status.EntriesProcessedCount)
|
||||
assert.Equal(0, status.NodeCount)
|
||||
assert.Equal(0, status.EdgeCount)
|
||||
}
|
||||
|
||||
func TestServiceMapControllerSuite(t *testing.T) {
|
||||
suite.Run(t, new(ServiceMapControllerSuite))
|
||||
}
|
Reference in New Issue
Block a user