mirror of
https://github.com/kubeshark/kubeshark.git
synced 2025-10-21 07:21:49 +00:00
Reduce delay between tap and UI - Skip dump to file (#26)
* Pass HARs between tap and api via channel. * Fixed make docker commad. * Various fixes. * Added .DS_Store to .gitignore. * Parse flags in Mizu main instead of in tap_output.go. * Use channel to pass HAR by default instead of files.
This commit is contained in:
3
.gitignore
vendored
3
.gitignore
vendored
@@ -19,3 +19,6 @@ build
|
|||||||
|
|
||||||
# Build directories
|
# Build directories
|
||||||
build
|
build
|
||||||
|
|
||||||
|
# Mac OS
|
||||||
|
.DS_Store
|
||||||
|
2
Makefile
2
Makefile
@@ -38,7 +38,7 @@ tap: ## build tap binary
|
|||||||
|
|
||||||
docker: ## build Docker image
|
docker: ## build Docker image
|
||||||
@(echo "building docker image" )
|
@(echo "building docker image" )
|
||||||
docker build -t ${DOCKER_IMG}:${DOCKER_TAG} api
|
docker build -t ${DOCKER_IMG}:${DOCKER_TAG} .
|
||||||
docker images ${DOCKER_IMG}
|
docker images ${DOCKER_IMG}
|
||||||
|
|
||||||
publish: ## build and publish Mizu docker image & CLI
|
publish: ## build and publish Mizu docker image & CLI
|
||||||
|
@@ -1,6 +1,8 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"flag"
|
||||||
|
|
||||||
"github.com/gofiber/fiber/v2"
|
"github.com/gofiber/fiber/v2"
|
||||||
"mizuserver/pkg/inserter"
|
"mizuserver/pkg/inserter"
|
||||||
"mizuserver/pkg/middleware"
|
"mizuserver/pkg/middleware"
|
||||||
@@ -10,12 +12,14 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
|
flag.Parse()
|
||||||
|
|
||||||
go tap.StartPassiveTapper()
|
harOutputChannel := tap.StartPassiveTapper()
|
||||||
|
|
||||||
app := fiber.New()
|
app := fiber.New()
|
||||||
|
|
||||||
go inserter.StartReadingFiles(*tap.HarOutputDir) // process to read files and insert to DB
|
// process to read files / channel and insert to DB
|
||||||
|
go inserter.StartReadingFiles(harOutputChannel, tap.HarOutputDir)
|
||||||
|
|
||||||
|
|
||||||
middleware.FiberMiddleware(app) // Register Fiber's middleware for app.
|
middleware.FiberMiddleware(app) // Register Fiber's middleware for app.
|
||||||
|
@@ -17,7 +17,15 @@ import (
|
|||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
func StartReadingFiles(workingDir string) {
|
func StartReadingFiles(harChannel chan *har.Entry, workingDir *string) {
|
||||||
|
if workingDir != nil && *workingDir != "" {
|
||||||
|
startReadingFiles(*workingDir)
|
||||||
|
} else {
|
||||||
|
startReadingSChan(harChannel)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func startReadingFiles(workingDir string) {
|
||||||
err := os.MkdirAll(workingDir, os.ModePerm)
|
err := os.MkdirAll(workingDir, os.ModePerm)
|
||||||
utils.CheckErr(err)
|
utils.CheckErr(err)
|
||||||
|
|
||||||
@@ -49,6 +57,12 @@ func StartReadingFiles(workingDir string) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func startReadingSChan(harChannel chan *har.Entry) {
|
||||||
|
for entry := range harChannel {
|
||||||
|
SaveHarToDb(*entry, "")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func SaveHarToDb(entry har.Entry, source string) {
|
func SaveHarToDb(entry har.Entry, source string) {
|
||||||
entryBytes, _ := json.Marshal(entry)
|
entryBytes, _ := json.Marshal(entry)
|
||||||
serviceName, urlPath := getServiceNameFromUrl(entry.Request.URL)
|
serviceName, urlPath := getServiceNameFromUrl(entry.Request.URL)
|
||||||
|
@@ -2,6 +2,7 @@ package tap
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"net/http"
|
"net/http"
|
||||||
"os"
|
"os"
|
||||||
@@ -38,15 +39,15 @@ type HarFile struct {
|
|||||||
entryCount int
|
entryCount int
|
||||||
}
|
}
|
||||||
|
|
||||||
func (f *HarFile) WriteEntry(request *http.Request, requestTime time.Time, response *http.Response, responseTime time.Time) {
|
func NewEntry(request *http.Request, requestTime time.Time, response *http.Response, responseTime time.Time) (*har.Entry, error) {
|
||||||
// TODO: quick fix until TRA-3212 is implemented
|
// TODO: quick fix until TRA-3212 is implemented
|
||||||
if request.URL == nil || request.Method == "" {
|
if request.URL == nil || request.Method == "" {
|
||||||
return
|
return nil, errors.New("Invalid request")
|
||||||
}
|
}
|
||||||
harRequest, err := har.NewRequest(request, true)
|
harRequest, err := har.NewRequest(request, true)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
SilentError("convert-request-to-har", "Failed converting request to HAR %s (%v,%+v)\n", err, err, err)
|
SilentError("convert-request-to-har", "Failed converting request to HAR %s (%v,%+v)\n", err, err, err)
|
||||||
return
|
return nil, errors.New("Failed converting request to HAR")
|
||||||
}
|
}
|
||||||
|
|
||||||
// Martian copies http.Request.URL.String() to har.Request.URL.
|
// Martian copies http.Request.URL.String() to har.Request.URL.
|
||||||
@@ -56,7 +57,7 @@ func (f *HarFile) WriteEntry(request *http.Request, requestTime time.Time, respo
|
|||||||
harResponse, err := har.NewResponse(response, true)
|
harResponse, err := har.NewResponse(response, true)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
SilentError("convert-response-to-har", "Failed converting response to HAR %s (%v,%+v)\n", err, err, err)
|
SilentError("convert-response-to-har", "Failed converting response to HAR %s (%v,%+v)\n", err, err, err)
|
||||||
return
|
return nil, errors.New("Failed converting response to HAR")
|
||||||
}
|
}
|
||||||
|
|
||||||
totalTime := responseTime.Sub(requestTime).Round(time.Millisecond).Milliseconds()
|
totalTime := responseTime.Sub(requestTime).Round(time.Millisecond).Milliseconds()
|
||||||
@@ -77,6 +78,10 @@ func (f *HarFile) WriteEntry(request *http.Request, requestTime time.Time, respo
|
|||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return &harEntry, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f *HarFile) WriteEntry(harEntry *har.Entry) {
|
||||||
harEntryJson, err := json.Marshal(harEntry)
|
harEntryJson, err := json.Marshal(harEntry)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
SilentError("har-entry-marshal", "Failed converting har entry object to JSON%s (%v,%+v)\n", err, err, err)
|
SilentError("har-entry-marshal", "Failed converting har entry object to JSON%s (%v,%+v)\n", err, err, err)
|
||||||
@@ -131,6 +136,7 @@ func NewHarWriter(outputDir string, maxEntries int) *HarWriter {
|
|||||||
OutputDirPath: outputDir,
|
OutputDirPath: outputDir,
|
||||||
MaxEntries: maxEntries,
|
MaxEntries: maxEntries,
|
||||||
PairChan: make(chan *PairChanItem),
|
PairChan: make(chan *PairChanItem),
|
||||||
|
OutChan: make(chan *har.Entry, 1000),
|
||||||
currentFile: nil,
|
currentFile: nil,
|
||||||
done: make(chan bool),
|
done: make(chan bool),
|
||||||
}
|
}
|
||||||
@@ -140,6 +146,7 @@ type HarWriter struct {
|
|||||||
OutputDirPath string
|
OutputDirPath string
|
||||||
MaxEntries int
|
MaxEntries int
|
||||||
PairChan chan *PairChanItem
|
PairChan chan *PairChanItem
|
||||||
|
OutChan chan *har.Entry
|
||||||
currentFile *HarFile
|
currentFile *HarFile
|
||||||
done chan bool
|
done chan bool
|
||||||
}
|
}
|
||||||
@@ -154,20 +161,31 @@ func (hw *HarWriter) WritePair(request *http.Request, requestTime time.Time, res
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (hw *HarWriter) Start() {
|
func (hw *HarWriter) Start() {
|
||||||
if err := os.MkdirAll(hw.OutputDirPath, os.ModePerm); err != nil {
|
if hw.OutputDirPath != "" {
|
||||||
panic(fmt.Sprintf("Failed to create output directory: %s (%v,%+v)", err, err, err))
|
if err := os.MkdirAll(hw.OutputDirPath, os.ModePerm); err != nil {
|
||||||
|
panic(fmt.Sprintf("Failed to create output directory: %s (%v,%+v)", err, err, err))
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
go func() {
|
go func() {
|
||||||
for pair := range hw.PairChan {
|
for pair := range hw.PairChan {
|
||||||
if hw.currentFile == nil {
|
harEntry, err := NewEntry(pair.Request, pair.RequestTime, pair.Response, pair.ResponseTime)
|
||||||
hw.openNewFile()
|
if err != nil {
|
||||||
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
hw.currentFile.WriteEntry(pair.Request, pair.RequestTime, pair.Response, pair.ResponseTime)
|
if hw.OutputDirPath != "" {
|
||||||
|
if hw.currentFile == nil {
|
||||||
|
hw.openNewFile()
|
||||||
|
}
|
||||||
|
|
||||||
if hw.currentFile.GetEntryCount() >= hw.MaxEntries {
|
hw.currentFile.WriteEntry(harEntry)
|
||||||
hw.closeFile()
|
|
||||||
|
if hw.currentFile.GetEntryCount() >= hw.MaxEntries {
|
||||||
|
hw.closeFile()
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
hw.OutChan <- harEntry
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -29,6 +29,7 @@ import (
|
|||||||
"github.com/google/gopacket/layers" // pulls in all layers decoders
|
"github.com/google/gopacket/layers" // pulls in all layers decoders
|
||||||
"github.com/google/gopacket/pcap"
|
"github.com/google/gopacket/pcap"
|
||||||
"github.com/google/gopacket/reassembly"
|
"github.com/google/gopacket/reassembly"
|
||||||
|
"github.com/google/martian/har"
|
||||||
)
|
)
|
||||||
|
|
||||||
const AppPortsEnvVar = "APP_PORTS"
|
const AppPortsEnvVar = "APP_PORTS"
|
||||||
@@ -96,7 +97,7 @@ var memprofile = flag.String("memprofile", "", "Write memory profile")
|
|||||||
|
|
||||||
// output
|
// output
|
||||||
var dumpToHar = flag.Bool("hardump", false, "Dump traffic to har files")
|
var dumpToHar = flag.Bool("hardump", false, "Dump traffic to har files")
|
||||||
var HarOutputDir = flag.String("hardir", "output", "Directory in which to store output har files")
|
var HarOutputDir = flag.String("hardir", "", "Directory in which to store output har files")
|
||||||
var harEntriesPerFile = flag.Int("harentriesperfile", 200, "Number of max number of har entries to store in each file")
|
var harEntriesPerFile = flag.Int("harentriesperfile", 200, "Number of max number of har entries to store in each file")
|
||||||
|
|
||||||
var reqResMatcher = createResponseRequestMatcher() // global
|
var reqResMatcher = createResponseRequestMatcher() // global
|
||||||
@@ -198,7 +199,22 @@ func (c *Context) GetCaptureInfo() gopacket.CaptureInfo {
|
|||||||
return c.CaptureInfo
|
return c.CaptureInfo
|
||||||
}
|
}
|
||||||
|
|
||||||
func StartPassiveTapper() {
|
func StartPassiveTapper() chan *har.Entry {
|
||||||
|
var harWriter *HarWriter
|
||||||
|
if *dumpToHar {
|
||||||
|
harWriter = NewHarWriter(*HarOutputDir, *harEntriesPerFile)
|
||||||
|
}
|
||||||
|
|
||||||
|
go startPassiveTapper(harWriter)
|
||||||
|
|
||||||
|
if harWriter != nil {
|
||||||
|
return harWriter.OutChan
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func startPassiveTapper(harWriter *HarWriter) {
|
||||||
defer util.Run()()
|
defer util.Run()()
|
||||||
if *debug {
|
if *debug {
|
||||||
outputLevel = 2
|
outputLevel = 2
|
||||||
@@ -311,14 +327,11 @@ func StartPassiveTapper() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var harWriter *HarWriter
|
|
||||||
if *dumpToHar {
|
if *dumpToHar {
|
||||||
harWriter = NewHarWriter(*HarOutputDir, *harEntriesPerFile)
|
|
||||||
harWriter.Start()
|
harWriter.Start()
|
||||||
defer harWriter.Stop()
|
defer harWriter.Stop()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
var dec gopacket.Decoder
|
var dec gopacket.Decoder
|
||||||
var ok bool
|
var ok bool
|
||||||
decoder_name := *decoder
|
decoder_name := *decoder
|
||||||
|
@@ -3,7 +3,6 @@ package tap
|
|||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"flag"
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"net/http"
|
"net/http"
|
||||||
@@ -200,7 +199,6 @@ func serveWs(hub *Hub, w http.ResponseWriter, r *http.Request) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func startOutputServer(port string, messageCallback func([]byte)) {
|
func startOutputServer(port string, messageCallback func([]byte)) {
|
||||||
flag.Parse()
|
|
||||||
hub = newHub(messageCallback)
|
hub = newHub(messageCallback)
|
||||||
go hub.run()
|
go hub.run()
|
||||||
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
|
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
@@ -1,2 +1,2 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
./mizuagent -i any -hardump -hardir /tmp/mizuhars -harentriesperfile 5 -targets ${TAPPED_ADDRESSES}
|
./mizuagent -i any -hardump -targets ${TAPPED_ADDRESSES}
|
||||||
|
Reference in New Issue
Block a user