## 1、使用http包默认启动web服务
- 基于go1.14 开启modules模式
- 模仿gin框架的简单优雅
- 介绍net/http库的简单使用
- 搭建框架雏形
- [代码地址 https://github.com/18211167516/go-Ebb/tree/master/day1-base](https://github.com/18211167516/go-Ebb/tree/master/day1-base)
> Go语言内置了 net/http库,封装了HTTP网络编程的基础的接口,我们实现的ebb Web 框架便是基于net/http的。我们接下来通过一个例子,简单介绍下这个库的使用。
```golang
go mode init explame
```
```golang
package main
import (
"fmt"
"net/http"
)
func indexHandler(w http.ResponseWriter,r *http.Request){
fmt.Fprintf(w, "URL.Path = %q\n", r.URL.Path)
}
func helloHandler(w http.ResponseWriter,r *http.Request){
fmt.Fprintf(w,"URL.PATH=%q\n Header=%q\n",r.URL.Path,r.Header)
}
func main(){
http.HandleFunc("/",indexHandler)
http.HandleFunc("/hello",helloHandler)
http.ListenAndServe(":8080",nil)
}
```
```
go build .
./examplde.exe
启动web服务
```
```
访问 127.0.0.1:8080/
访问 127.0.0.1:8080/hello
```
> main 函数的最后一行,是用来启动 Web 服务的,第一个参数是地址,:9999表示在 9999 端口监听。而第二个参数则代表处理所有的HTTP请求的实例,nil 代表使用标准库中的实例处理。第二个参数,则是我们基于net/http标准库实现Web框架的入口
## 2、接下来我们需要自己实现
* 新建examplde2目录
* 新建ebb目录
* 在ebb目录 执行 go mod init ebb
```golang
package ebb
import (
"net/http"
"log"
)
//定义框架请求处理方法
type HandlerFunc func(w http.ResponseWriter,req *http.Request)
//核心结构体
type Engine struct{
router map[string]HandlerFunc //简单使用map记录路由信息
}
//实例化结构体
func New() *Engine{
engine := &Engine{
router : make(map[string]HandlerFunc),
}
return engine
}
//添加到结构体路由
func (engine *Engine) addRoute(mothod string,pattern string,handler HandlerFunc){
key := mothod+"-"+pattern
engine.router[key] = handler
}
func (engine *Engine) GET(pattern string,handler HandlerFunc){
engine.addRoute("GET",pattern,handler)
}
func (engine *Engine) POST(pattern string,handler HandlerFunc){
engine.addRoute("POST",pattern,handler)
}
//启动服务
func (engine *Engine) Run(addr string) (err error){
return http.ListenAndServe(addr,engine)
}
//engine 实现ServeHTTP接口(所有的请求都会走到这)
//查找是否路由映射表存在,如果存在则调用,否则返回404
func (engine *Engine) ServeHTTP(w http.ResponseWriter,req *http.Request){
key := req.Method + "-" + req.URL.Path
if handler, ok := engine.router[key]; ok {
handler(w, req)
} else {
log.Printf("404 NOT FOUND: %s\n", req.URL)
}
}
```
* 在exmpale2目录下新建main.go
并且执行 go mod init example
* 编辑go.mod(在 go.mod 中使用 replace 将 ebb 指向 ./ebb)
```
module example
go 1.14
require ebb v0.0.0
replace ebb => ./ebb
```
* 编辑main.go
```golang
package main
import (
"ebb"
"fmt"
"net/http"
)
func main(){
r := ebb.New()
r.GET("/index",func(w http.ResponseWriter,req *http.Request){
fmt.Fprintf(w, "URL.Path = %q\n", req.URL.Path)
})
r.GET("/hello", func(w http.ResponseWriter, req *http.Request) {
fmt.Fprintln(w, req.Header)
})
r.Run(":8080")
}
```
> 框架流程
* 定义HandlerFunc(框架的请求方法)
* 定义核心结构体Engine 目前只存储路由信息,路由信息由映射表实现(路由只支持静态路由)
* GET、POST提供路由注册
* Run封装http.ListenAndServe
* 核心结构体Engine实现ServeHTTP接口(所有请求),查找路由并执行
> 到目前为止,一个简易的框架已经OK、后续我们会将HandlerFunc方法优化,也就是Context.期待下一篇文章
有疑问加站长微信联系(非本文作者))