aboutsummaryrefslogtreecommitdiff
path: root/example
diff options
context:
space:
mode:
authorShulhan <ms@kilabit.info>2021-03-24 01:56:39 +0700
committerShulhan <ms@kilabit.info>2021-03-24 02:00:47 +0700
commit7035a7fb42b9054657f5a99bb479fd4722d8ae7c (patch)
tree44c5e4d328722a8877082f8b47ca0850dc55702e /example
parent896e55e6406b0837041c0aad75035f5839083e25 (diff)
downloadgorankusu-7035a7fb42b9054657f5a99bb479fd4722d8ae7c.tar.xz
all: implement target for WebSocket
One can register WebSocketTarget just like HttpTarget, its have ID, Name, Headers, and Params. Unlike HTTP, the WebSocket target only able to execute Run, it does not have "Attack", yet.
Diffstat (limited to 'example')
-rw-r--r--example/example.go113
1 files changed, 112 insertions, 1 deletions
diff --git a/example/example.go b/example/example.go
index b2ef46c..851b614 100644
--- a/example/example.go
+++ b/example/example.go
@@ -5,12 +5,16 @@
package example
import (
+ "context"
"encoding/json"
"fmt"
"net/http"
+ "sync"
"time"
libhttp "github.com/shuLhan/share/lib/http"
+ "github.com/shuLhan/share/lib/mlog"
+ "github.com/shuLhan/share/lib/websocket"
vegeta "github.com/tsenart/vegeta/v12/lib"
"git.sr.ht/~shulhan/trunks"
@@ -21,8 +25,14 @@ const (
pathExamplePostForm = "/example/post/form"
)
+const (
+ websocketAddress = "127.0.0.1:28240"
+)
+
type Example struct {
- trunks *trunks.Trunks
+ trunks *trunks.Trunks
+ wsServer *websocket.Server
+
targetExampleGet vegeta.Target
targetExamplePostForm vegeta.Target
}
@@ -48,6 +58,19 @@ func New() (ex *Example, err error) {
return nil, fmt.Errorf("example: New: %w", err)
}
+ // Create and register endpoint for WebSocket server.
+ wsOpts := &websocket.ServerOptions{
+ Address: websocketAddress,
+ }
+
+ ex.wsServer = websocket.NewServer(wsOpts)
+
+ err = ex.registerWebSocketEndpoints()
+ if err != nil {
+ return nil, fmt.Errorf("example: New: %w", err)
+ }
+
+ // Register targets for testing HTTP and WebSocket endpoints.
err = ex.registerTargets()
if err != nil {
return nil, fmt.Errorf("example: New: %w", err)
@@ -57,10 +80,18 @@ func New() (ex *Example, err error) {
}
func (ex *Example) Start() (err error) {
+ go func() {
+ err = ex.wsServer.Start()
+ if err != nil {
+ mlog.Errf("example.Start: %s\n", err)
+ }
+ }()
+
return ex.trunks.Start()
}
func (ex *Example) Stop() {
+ ex.wsServer.Stop()
ex.trunks.Stop()
}
@@ -90,6 +121,15 @@ func (ex *Example) registerEndpoints() (err error) {
return err
}
+func (ex *Example) registerWebSocketEndpoints() (err error) {
+ err = ex.wsServer.RegisterTextHandler(http.MethodGet, pathExampleGet,
+ ex.handleWSExampleGet)
+ if err != nil {
+ return err
+ }
+ return nil
+}
+
func (ex *Example) registerTargets() (err error) {
targetHttp := &trunks.Target{
Name: "Example HTTP",
@@ -137,6 +177,24 @@ func (ex *Example) registerTargets() (err error) {
ex.trunks.RegisterTarget(targetHttp)
+ targetWebSocket := &trunks.Target{
+ Name: "Example WebSocket",
+ BaseUrl: fmt.Sprintf("ws://%s", websocketAddress),
+ Opts: &trunks.AttackOptions{},
+ Vars: trunks.KeyValue{
+ "WebSocketVar": "hello",
+ },
+ WebSocketTargets: []*trunks.WebSocketTarget{{
+ Name: "Similar to HTTP GET",
+ Params: trunks.KeyValue{
+ "Param1": "123",
+ },
+ Run: ex.runWebSocketGet,
+ }},
+ }
+
+ ex.trunks.RegisterTarget(targetWebSocket)
+
return nil
}
@@ -233,3 +291,56 @@ func (ex *Example) attackExamplePostForm(rr *trunks.RunRequest) vegeta.Targeter
return nil
}
}
+
+func (ex *Example) handleWSExampleGet(ctx context.Context, req *websocket.Request) (res websocket.Response) {
+ res.ID = req.ID
+ res.Code = http.StatusOK
+ res.Body = req.Body
+ return res
+}
+
+func (ex *Example) runWebSocketGet(rr *trunks.RunRequest) (resbody []byte, err error) {
+ var wg sync.WaitGroup
+
+ wsc := &websocket.Client{
+ Endpoint: "ws://" + websocketAddress,
+ HandleText: func(cl *websocket.Client, frame *websocket.Frame) error {
+ resbody = frame.Payload()
+ wg.Done()
+ return nil
+ },
+ }
+
+ err = wsc.Connect()
+ if err != nil {
+ return nil, err
+ }
+
+ body, err := json.Marshal(rr.WebSocketTarget.Params)
+ if err != nil {
+ return nil, err
+ }
+
+ req := websocket.Request{
+ ID: uint64(time.Now().UnixNano()),
+ Method: http.MethodGet,
+ Target: pathExampleGet,
+ Body: string(body),
+ }
+
+ reqtext, err := json.Marshal(&req)
+ if err != nil {
+ return nil, err
+ }
+
+ err = wsc.SendText(reqtext)
+ if err != nil {
+ return nil, err
+ }
+ wg.Add(1)
+ wg.Wait()
+
+ _ = wsc.Close()
+
+ return resbody, err
+}