Navigation Menu

Skip to content

Instantly share code, notes, and snippets.

@RitterHou
Created September 17, 2018 03:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save RitterHou/e77b38acdd30d30ee3b9f19004940d3c to your computer and use it in GitHub Desktop.
Save RitterHou/e77b38acdd30d30ee3b9f19004940d3c to your computer and use it in GitHub Desktop.
#!/usr/bin/env bash
# 可以通过命令 go env 获取当前的环境变量
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -ldflags "-s -w" -o http_echo_linux
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -ldflags "-s -w" -o http_echo_windows.exe
CGO_ENABLED=0 GOOS=darwin GOARCH=amd64 go build -ldflags "-s -w" -o http_echo_mac
package main
import (
"flag"
"log"
"net"
"os"
"regexp"
"strconv"
"strings"
)
var p = flag.Int("p", 6728, "port")
const (
frame = 256
crLf2 = "\r\n\r\n"
)
var contentLengthReg = regexp.MustCompile(`content-length: *(\d+)\r\n`)
func getContentLength(request string) (length int) {
request = strings.ToLower(request)
params := contentLengthReg.FindStringSubmatch(request)
if params != nil {
value, err := strconv.Atoi(params[1])
if err != nil {
log.Fatalln(err)
}
length = value
}
return
}
func handleRequest(conn net.Conn) {
// 不断地接受HTTP请求
for {
var contentLength int
data := make([]byte, 0, frame*4)
tmp := make([]byte, frame)
// 读取HTTP请求报文
for {
length, err := conn.Read(tmp)
// 连接断开
if length == 0 {
log.Println("Remove", conn.RemoteAddr().String())
return
}
if err != nil {
log.Fatalln("Error reading:", err)
}
data = append(data, tmp[:length]...)
request := string(data)
if strings.Contains(request, crLf2) {
if contentLength == 0 {
contentLength = getContentLength(request)
if contentLength == 0 {
break
}
}
body := strings.Split(request, crLf2)[1]
if len([]byte(body)) == contentLength {
break
}
}
}
log.Println(string(data))
head := []byte("HTTP/1.1 200 OK\r\n")
head = append(head, []byte("content-length: "+strconv.Itoa(len(data))+"\r\n")...)
head = append(head, []byte("content-type: text/plain"+crLf2)...)
data = append(head, data...)
conn.Write(data)
}
}
func main() {
log.SetOutput(os.Stdout)
flag.Parse()
port := strconv.Itoa(*p)
listener, err := net.Listen("tcp", "0.0.0.0:"+port)
if err != nil {
log.Fatalln("Error listening:", err)
}
log.Println("Listening 0.0.0.0:" + port)
defer listener.Close()
for {
conn, err := listener.Accept()
if err != nil {
log.Fatalln("Error accepting:", err)
}
log.Println("Accept", conn.RemoteAddr().String())
go handleRequest(conn)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment