mirror of https://github.com/tidwall/evio.git
benchmarks
This commit is contained in:
parent
23d55c2b35
commit
6a86476275
|
@ -1,6 +1,6 @@
|
||||||
<p align="center">
|
<p align="center">
|
||||||
<img
|
<img
|
||||||
src="resources/logo.png"
|
src="logo.png"
|
||||||
width="213" height="75" border="0" alt="evio">
|
width="213" height="75" border="0" alt="evio">
|
||||||
<br>
|
<br>
|
||||||
<a href="https://travis-ci.org/tidwall/evio"><img src="https://img.shields.io/travis/tidwall/evio.svg?style=flat-square" alt="Build Status"></a>
|
<a href="https://travis-ci.org/tidwall/evio"><img src="https://img.shields.io/travis/tidwall/evio.svg?style=flat-square" alt="Build Status"></a>
|
||||||
|
|
|
@ -0,0 +1,2 @@
|
||||||
|
bin/
|
||||||
|
socket
|
|
@ -0,0 +1,8 @@
|
||||||
|
## evio benchmark tools
|
||||||
|
|
||||||
|
Required:
|
||||||
|
|
||||||
|
- [wrk](https://github.com/wg/wrk) for HTTP
|
||||||
|
- [tcpkali](https://github.com/machinezone/tcpkali) for Echo
|
||||||
|
- [Redis](http://redis.io) for Redis
|
||||||
|
|
|
@ -0,0 +1,37 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
#set -e
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "--- ECHO START ---"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
cd $(dirname "${BASH_SOURCE[0]}")
|
||||||
|
function cleanup {
|
||||||
|
echo "--- ECHO DONE ---"
|
||||||
|
kill $(jobs -rp)
|
||||||
|
wait $(jobs -rp) 2>/dev/null
|
||||||
|
}
|
||||||
|
trap cleanup EXIT
|
||||||
|
|
||||||
|
mkdir -p bin
|
||||||
|
|
||||||
|
$(pkill net-echo-server || printf "")
|
||||||
|
$(pkill evio-echo-server || printf "")
|
||||||
|
|
||||||
|
function gobench {
|
||||||
|
printf "\e[96m[%s]\e[0m\n" $1
|
||||||
|
if [ "$3" != "" ]; then
|
||||||
|
go build -o $2 $3
|
||||||
|
fi
|
||||||
|
$2 -port $4 &
|
||||||
|
sleep 1
|
||||||
|
echo "Sending 6 byte packets, 50 connections"
|
||||||
|
nl=$'\r\n'
|
||||||
|
tcpkali -c 50 -m "PING{$nl}" 127.0.0.1:$4
|
||||||
|
echo "--- DONE ---"
|
||||||
|
echo ""
|
||||||
|
}
|
||||||
|
|
||||||
|
gobench "net/echo" bin/net-echo-server net-echo-server/main.go 5001
|
||||||
|
gobench "evio/echo" bin/evio-echo-server ../examples/echo-server/main.go 5002
|
|
@ -0,0 +1,39 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
#set -e
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "--- HTTP START ---"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
cd $(dirname "${BASH_SOURCE[0]}")
|
||||||
|
function cleanup {
|
||||||
|
echo "--- HTTP DONE ---"
|
||||||
|
kill $(jobs -rp)
|
||||||
|
wait $(jobs -rp) 2>/dev/null
|
||||||
|
}
|
||||||
|
trap cleanup EXIT
|
||||||
|
|
||||||
|
mkdir -p bin
|
||||||
|
$(pkill net-http-server || printf "")
|
||||||
|
$(pkill fasthttp-server || printf "")
|
||||||
|
$(pkill iris-server || printf "")
|
||||||
|
$(pkill evio-http-server || printf "")
|
||||||
|
|
||||||
|
function gobench {
|
||||||
|
printf "\e[96m[%s]\e[0m\n" $1
|
||||||
|
if [ "$3" != "" ]; then
|
||||||
|
go build -o $2 $3
|
||||||
|
fi
|
||||||
|
$2 -port $4 &
|
||||||
|
sleep 1
|
||||||
|
echo "Using 4 threads, 50 connections, 10 seconds"
|
||||||
|
wrk -t4 -c50 -d10 http://127.0.0.1:$4
|
||||||
|
echo "--- DONE ---"
|
||||||
|
echo ""
|
||||||
|
}
|
||||||
|
|
||||||
|
gobench "net/http" bin/net-http-server net-http-server/main.go 8081
|
||||||
|
gobench "iris" bin/iris-server iris-server/main.go 8082
|
||||||
|
gobench "fasthttp" bin/fasthttp-server fasthttp-server/main.go 8083
|
||||||
|
gobench "evio/http" bin/evio-http-server ../examples/http-server/main.go 8084
|
|
@ -0,0 +1,40 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
#set -e
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "--- REDIS START ---"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
|
||||||
|
cd $(dirname "${BASH_SOURCE[0]}")
|
||||||
|
function cleanup {
|
||||||
|
echo "--- REDIS DONE ---"
|
||||||
|
kill $(jobs -rp)
|
||||||
|
wait $(jobs -rp) 2>/dev/null
|
||||||
|
}
|
||||||
|
trap cleanup EXIT
|
||||||
|
|
||||||
|
mkdir -p bin
|
||||||
|
|
||||||
|
$(pkill redis-server || printf "")
|
||||||
|
$(pkill evio-redis-server || printf "")
|
||||||
|
|
||||||
|
function gobench {
|
||||||
|
printf "\e[96m[%s]\e[0m\n" $1
|
||||||
|
if [ "$3" != "" ]; then
|
||||||
|
go build -o $2 $3
|
||||||
|
fi
|
||||||
|
$2 --port $4 &
|
||||||
|
sleep 1
|
||||||
|
echo "Sending pings, 50 connections, 1 packet pipeline"
|
||||||
|
redis-benchmark -p $4 -t ping -q -P 1
|
||||||
|
echo "Sending pings, 50 connections, 10 packet pipeline"
|
||||||
|
redis-benchmark -p $4 -t ping -q -P 10
|
||||||
|
echo "Sending pings, 50 connections, 20 packet pipeline"
|
||||||
|
redis-benchmark -p $4 -t ping -q -P 20
|
||||||
|
echo "--- DONE ---"
|
||||||
|
echo ""
|
||||||
|
}
|
||||||
|
gobench "real/redis" redis-server "" 6392
|
||||||
|
gobench "evio/redis" bin/evio-redis-server ../examples/redis-server/main.go 6393
|
|
@ -0,0 +1,9 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
#set -e
|
||||||
|
|
||||||
|
cd $(dirname "${BASH_SOURCE[0]}")
|
||||||
|
|
||||||
|
./bench-http.sh
|
||||||
|
./bench-echo.sh
|
||||||
|
./bench-redis.sh
|
|
@ -0,0 +1,32 @@
|
||||||
|
// Copyright 2017 Joshua J Baker. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
|
||||||
|
"github.com/valyala/fasthttp"
|
||||||
|
)
|
||||||
|
|
||||||
|
var res string
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var port int
|
||||||
|
flag.IntVar(&port, "port", 8080, "server port")
|
||||||
|
flag.Parse()
|
||||||
|
go log.Printf("http server started on port %d", port)
|
||||||
|
err := fasthttp.ListenAndServe(fmt.Sprintf(":%d", port),
|
||||||
|
func(c *fasthttp.RequestCtx) {
|
||||||
|
_, werr := c.WriteString("Hello World!\r\n")
|
||||||
|
if werr != nil {
|
||||||
|
log.Fatal(werr)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,31 @@
|
||||||
|
// Copyright 2017 Joshua J Baker. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
|
||||||
|
"github.com/kataras/iris"
|
||||||
|
)
|
||||||
|
|
||||||
|
var res string
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var port int
|
||||||
|
flag.IntVar(&port, "port", 8080, "server port")
|
||||||
|
flag.Parse()
|
||||||
|
go log.Printf("http server started on port %d", port)
|
||||||
|
app := iris.New()
|
||||||
|
app.Get("/", func(ctx iris.Context) {
|
||||||
|
ctx.WriteString("Hello World!\r\n")
|
||||||
|
})
|
||||||
|
err := app.Run(iris.Addr(fmt.Sprintf(":%d", port)))
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,47 @@
|
||||||
|
// Copyright 2017 Joshua J Baker. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"net"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var port int
|
||||||
|
flag.IntVar(&port, "port", 5000, "server port")
|
||||||
|
flag.Parse()
|
||||||
|
ln, err := net.Listen("tcp4", fmt.Sprintf(":%d", port))
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
defer ln.Close()
|
||||||
|
log.Printf("echo server started on port %d", port)
|
||||||
|
var id int
|
||||||
|
for {
|
||||||
|
conn, err := ln.Accept()
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
id++
|
||||||
|
go func(id int, conn net.Conn) {
|
||||||
|
defer func() {
|
||||||
|
//log.Printf("closed: %d", id)
|
||||||
|
conn.Close()
|
||||||
|
}()
|
||||||
|
//log.Printf("opened: %d: %s", id, conn.RemoteAddr().String())
|
||||||
|
var packet [0xFFF]byte
|
||||||
|
for {
|
||||||
|
n, err := conn.Read(packet[:])
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
conn.Write(packet[:n])
|
||||||
|
}
|
||||||
|
}(id, conn)
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,36 @@
|
||||||
|
// Copyright 2017 Joshua J Baker. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"net/http"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
var res string
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
var port int
|
||||||
|
var aaaa bool
|
||||||
|
flag.IntVar(&port, "port", 8080, "server port")
|
||||||
|
flag.BoolVar(&aaaa, "aaaa", false, "aaaaa....")
|
||||||
|
flag.Parse()
|
||||||
|
if aaaa {
|
||||||
|
res = strings.Repeat("a", 1024)
|
||||||
|
} else {
|
||||||
|
res = "Hello World!\r\n"
|
||||||
|
}
|
||||||
|
log.Printf("http server started on port %d", port)
|
||||||
|
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
w.Write([]byte(res))
|
||||||
|
})
|
||||||
|
err := http.ListenAndServe(fmt.Sprintf(":%d", port), nil)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
}
|
|
@ -323,7 +323,7 @@ func serve(events Events, lns []*listener) error {
|
||||||
c.outpos += n
|
c.outpos += n
|
||||||
if len(c.outbuf)-c.outpos == 0 {
|
if len(c.outbuf)-c.outpos == 0 {
|
||||||
c.outpos = 0
|
c.outpos = 0
|
||||||
c.outbuf = nil
|
c.outbuf = c.outbuf[:0]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if c.action == Shutdown {
|
if c.action == Shutdown {
|
||||||
|
|
|
@ -5,6 +5,8 @@
|
||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"net"
|
"net"
|
||||||
|
|
||||||
|
@ -12,17 +14,26 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
var events evio.Events
|
var port int
|
||||||
|
flag.IntVar(&port, "port", 5000, "server port")
|
||||||
|
flag.Parse()
|
||||||
|
|
||||||
|
var events evio.Events
|
||||||
events.Serving = func(wake func(id int) bool, addrs []net.Addr) (action evio.Action) {
|
events.Serving = func(wake func(id int) bool, addrs []net.Addr) (action evio.Action) {
|
||||||
log.Print("echo server started on port 5000")
|
log.Printf("echo server started on port %d", port)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
events.Opened = func(id int, addr evio.Addr) (out []byte, opts evio.Options, action evio.Action) {
|
||||||
|
//log.Printf("opened: %d: %s", id, addr.Remote.String())
|
||||||
|
return
|
||||||
|
}
|
||||||
|
events.Closed = func(id int, err error) (action evio.Action) {
|
||||||
|
//log.Printf("closed: %d", id)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
events.Data = func(id int, in []byte) (out []byte, action evio.Action) {
|
events.Data = func(id int, in []byte) (out []byte, action evio.Action) {
|
||||||
out = in
|
out = in
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
log.Fatal(evio.Serve(events, fmt.Sprintf("tcp://:%d", port)))
|
||||||
log.Fatal(evio.Serve(events, "tcp://0.0.0.0:5000"))
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -63,28 +63,18 @@ func main() {
|
||||||
|
|
||||||
events.Opened = func(id int, addr evio.Addr) (out []byte, opts evio.Options, action evio.Action) {
|
events.Opened = func(id int, addr evio.Addr) (out []byte, opts evio.Options, action evio.Action) {
|
||||||
conns[id] = &conn{addr: addr}
|
conns[id] = &conn{addr: addr}
|
||||||
log.Printf("%s: opened", addr.Remote.String())
|
//log.Printf("opened: %d: %s: %s", id, addr.Local.String(), addr.Remote.String())
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
events.Closed = func(id int, err error) (action evio.Action) {
|
events.Closed = func(id int, err error) (action evio.Action) {
|
||||||
c := conns[id]
|
// c := conns[id]
|
||||||
log.Printf("%s: closed: %v", c.addr.Remote.String(), err)
|
// log.Printf("closed: %d: %s: %s", id, c.addr.Local.String(), c.addr.Remote.String())
|
||||||
delete(conns, id)
|
delete(conns, id)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
events.Data = func(id int, in []byte) (out []byte, action evio.Action) {
|
events.Data = func(id int, in []byte) (out []byte, action evio.Action) {
|
||||||
// out = []byte(`HTTP/1.1 200 OK
|
|
||||||
// Server: evio
|
|
||||||
// Date: Thu, 02 Nov 2017 15:48:57 GMT
|
|
||||||
// Content-Type: text/plain; charset=utf-8
|
|
||||||
// Content-Length: 1024
|
|
||||||
|
|
||||||
// aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa`)
|
|
||||||
|
|
||||||
// return
|
|
||||||
|
|
||||||
if in == nil {
|
if in == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -112,7 +102,7 @@ func main() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
// We at least want the single http address.
|
// We at least want the single http address.
|
||||||
addrs := []string{fmt.Sprintf("tcp://localhost:%d", port)}
|
addrs := []string{fmt.Sprintf("tcp://:%d", port)}
|
||||||
if tlspem != "" {
|
if tlspem != "" {
|
||||||
// load the cert and key pair from the concat'd pem file.
|
// load the cert and key pair from the concat'd pem file.
|
||||||
cer, err := tls.LoadX509KeyPair(tlspem, tlspem)
|
cer, err := tls.LoadX509KeyPair(tlspem, tlspem)
|
||||||
|
@ -121,7 +111,7 @@ func main() {
|
||||||
}
|
}
|
||||||
config := &tls.Config{Certificates: []tls.Certificate{cer}}
|
config := &tls.Config{Certificates: []tls.Certificate{cer}}
|
||||||
// Update the address list to include https.
|
// Update the address list to include https.
|
||||||
addrs = append(addrs, fmt.Sprintf("tcp://localhost:%d", tlsport))
|
addrs = append(addrs, fmt.Sprintf("tcp://:%d", tlsport))
|
||||||
|
|
||||||
// TLS translate the events
|
// TLS translate the events
|
||||||
events = evio.Translate(events,
|
events = evio.Translate(events,
|
||||||
|
|
|
@ -130,7 +130,7 @@ func main() {
|
||||||
c.is.End(data)
|
c.is.End(data)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addrs := []string{fmt.Sprintf("tcp://0.0.0.0:%d", port)}
|
addrs := []string{fmt.Sprintf("tcp://:%d", port)}
|
||||||
if unixsocket != "" {
|
if unixsocket != "" {
|
||||||
addrs = append(addrs, fmt.Sprintf("unix://%s", unixsocket))
|
addrs = append(addrs, fmt.Sprintf("unix://%s", unixsocket))
|
||||||
}
|
}
|
||||||
|
|
Before Width: | Height: | Size: 25 KiB After Width: | Height: | Size: 25 KiB |
Loading…
Reference in New Issue