rirs BasicAuth基础认证

  1. 实现原理
  2. 代码实现
  3. 自建基础认证中间件
  4. 优化点

1.实现原理

BasicAuth是一种浏览器端实现的简单认证方式,在请求Headers中检查Authorization字段,是否存在,并且在有效期内,如果不满足条件。返回401 Unauthorised ,浏览器端弹窗输入用户名密码。
步骤1. 客户端请求
步骤2. 服务端验证是否包含字段Authorization
步骤3.服务端验证,包含Authorization,验证为空,验证用户密码是否和服务端信息一致
步骤4.返回信息,验证通过直接返回,不通过返回
code 401
header:WWW-Authenticate:Basic realm=access info

2. 代码实现

package main

import (
    "github.com/kataras/iris/v12"
    "github.com/kataras/iris/v12/middleware/basicauth"
    "time"
)

func newApp() *iris.Application {
    app := iris.New()
    // 配置信息  users{username:password} 可配置多个
    basicAuthConfig := basicauth.Config{
        Users: map[string]string{"admin":"admin"},
        Expires: time.Duration(30) * time.Minute,
    }
    authentication := basicauth.New(basicAuthConfig)

    authRouter := app.Party("/",authentication)
    authRouter.Get("/ping", func(ctx iris.Context) {
        ctx.WriteString("pong")
    })
    authRouter.Get("/profile", h)

    return app
}
func main()  {
    app := newApp()
    app.Run(iris.Addr(":8080"))
}
func h(ctx iris.Context)  {
    username,password,ok :=ctx.Request().BasicAuth()
    if ok {
        ctx.JSON(iris.Map{
            "username":username,
            "password": password,
        })
    }
}

3. 自建基础认证中间件

package basicauth

import (
    "encoding/base64"
    "fmt"
    "github.com/kataras/iris/v12/context"
    "strings"
)

//type BasicAuthMiddleware context.Handler

type BasicAuthConfig struct {
    Users  map[string]string
    Realme string
}
// todo func DefaultConfig
// todo 配置信息 绑定到basicauth上
// todo 过期时间

func NewBasicAuth(config BasicAuthConfig) context.Handler {
    return func(ctx context.Context) {
        //查看Authorization是否存在
        Authorization := ctx.GetHeader("Authorization")
        Authorization = strings.TrimPrefix(Authorization, "Basic ")
        if Authorization == "" {
            NoAuth(ctx, config.Realme)
            ctx.StopExecution()
            return
        }
        //解析Authorization
        res := parseAuthorization(Authorization, config.Users)
        if !res {
            NoAuth(ctx, config.Realme)
            ctx.StopExecution()
            return
        }
        ctx.Next()
    }

}

func parseAuthorization(Authorization string, users map[string]string) bool {
    userinfo, err := base64.StdEncoding.DecodeString(Authorization)
    if err != nil {
        return false
    }
    fmt.Println(string(userinfo))
    user := strings.Split(string(userinfo), ":")
    name := user[0]
    password := user[1]

    if pass, ok := users[name]; ok && pass == password {
        return true
    }

    return false
}
func NoAuth(ctx context.Context, realm string) {
    ctx.StatusCode(401)
    if realm == "" {
        ctx.Header("WWW-Authenticate", "Basic realm=access App")
    } else {
        ctx.Header("WWW-Authenticate", "Basic realm="+realm)
    }

}

4. 代码优化点

  1. 配置信息,创建默认配置方法,调用时先使用默认配置,然后根据传递的配置信息,再修改
  2. 定义basicauth结构体,汇总信息

你可能感兴趣的:(rirs BasicAuth基础认证)