Go 和 Rust 经常被拿来做比较,之前写过一篇文章分别使用go 和rust 编写tcp server,感兴趣的可以翻看历史,今天我们再撸一篇 http server的文章,废话不多说。
Go HTTP Server
我们先展示一个Go 编写HTTP server。
package main
import (
"fmt"
"io"
"log"
"net/http"
)
type handler struct{}
func (theHandler *handler) ServeHTTP(writer http.ResponseWriter, request *http.Request) {
log.Printf("Received request: %s\n", request.URL)
log.Printf("%v\n", request)
io.WriteString(writer, "Hello world!")
}
const port = "8080"
func main() {
server := http.Server{
Addr: fmt.Sprintf(":%s", port),
Handler: &handler{},
}
server.ListenAndServe()
}
go代码已经简单到不能再简单了,没啥好说的。创建一个http server,注册handler,最后启动监听,代码非常简洁高效。
Rust HTTP Server
rust 原生没有http server 的支持,不过你可以使用warp 或者hyper 之类的三方package,不过这里面还是使用原生rust 的能力编写一个。
use std::net::{TcpStream, TcpListener};
use std::io::{Read, Write};
use std::thread;
//获取请求
fn handle_read(mut stream: &TcpStream) {
let mut buf = [0u8; 4096];
match stream.read(&mut buf) {
Ok(_) => {
let req_str = String::from_utf8_lossy(&buf);
println!("{}", req_str);
},
Err(e) => println!("Unable to read stream: {}", e),
}
}
// 返回response
fn handle_write(mut stream: TcpStream) {
let response = b"HTTP/1.1 200 OK\r\nContent-Type: text/html; charset=UTF-8\r\n\r\n<html><body>Hello world</body></html>\r\n";
match stream.write(response) {
Ok(n) => println!("Response sent: {} bytes", n),
Err(e) => println!("Failed sending response: {}", e),
}
}
fn handle_client(stream: TcpStream) {
handle_read(&stream);
handle_write(stream);
}
fn main() {
let port = "8080";
let listener = TcpListener::bind(format!("127.0.0.1:{}", port)).unwrap();
println!("Listening for connections on port {}", port);
for stream in listener.incoming() {
match stream {
Ok(stream) => {
thread::spawn(|| {
handle_client(stream) //处理请求
});
}
Err(e) => {
println!("Unable to connect: {}", e);
}
}
}
}
我们通过建立tcp server 然后解析请求,并返回HTTP response。虽然代码看着长点,但也不复杂。