Go web 开发框架 Iris

背景

掌握了 Go 语言的基础后就该开始实践了,编写Web应用首先需要一个 web 开发框架。做框架选型时,处理web请求是基本功能,至于MVC是更进一步需要。现在比较流行的web架构是前后端分离,后端响应RESTful的请求,Iris 能满足我们的需要。

Iris简介

它是用Go编写的一个相当新的web框架。它是精心编写的最快的HTTP/2 web 框架。IRIS提供了相当优美的表达语法,和简单易用的框架支持你开发网站、API或分布式应用程序

简单来说Iris的特点:

  • 语法简单
  • 小巧,轻量,快
  • 支持中间件(插件,请求拦截)
  • 支持 开发网站、API或分布式应用程序

本文结构:

代码语言:javascript

复制

开始吧
   导入包
   设定一些参数和启动:
   响应 HTTP 中的各种方法(method): Get, Post, Put, Patch, Delete 和 Options
   从 请求 中获得参数的值
   从查询字符串( QueryString )中获得值
   从表单(Form) 中获得值
   上传文件
   支持对路由的分组
   中间件
   写入日志到文件中
   Cookie 操作
   处理跨域CORS

开始吧

导入包
设定一些参数和启动:

开始吧

导入包

一些说明:

代码示例: package main

import (
    "github.com/kataras/iris/v12"

    "github.com/kataras/iris/v12/middleware/logger"
    "github.com/kataras/iris/v12/middleware/recover"
)
设定一些参数和启动:
func main() {
    app := iris.New()
    app.Logger().SetLevel("debug")
    // 可选的,recover 和logger 是内建的中间件,帮助在 崩溃时记录和恢复
    app.Use(recover.New())
    app.Use(logger.New())

    // GET方法 返回一个 HTML
    // 示例 URL :  http://localhost:8080
    app.Handle("GET", "/", func(ctx iris.Context) {
        ctx.HTML("<h1>Welcome</h1>")
    })

    //  GET方法 返回 字符串
    // 示例 URL :  http://localhost:8080/ping
    app.Get("/ping", func(ctx iris.Context) {
        ctx.WriteString("pong")
    })

    //  GET 方法 返回 JSON 格式的数据
    // 示例 URL : http://localhost:8080/hello
    app.Get("/hello", func(ctx iris.Context) {
        ctx.JSON(iris.Map{"message": "Hello Iris!"})
    })

    // 启动
    // http://localhost:8080
    // http://localhost:8080/ping
    // http://localhost:8080/hello
    app.Run(iris.Addr(":8080"), iris.WithoutServerError(iris.ErrServerClosed))
}

上面演示了: GET 方法 返回一个 HTML,返回字符串,返回 JSON的情形。 代码很简单,一看就懂。

响应 HTTP 中的各种方法(method): Get, Post, Put, Patch, Delete 和 Options
func main() {
    // Creates an application with default middleware:
    // logger and recovery (crash-free) middleware.
    app := iris.Default()

    app.Get("/someGet", getting)
    app.Post("/somePost", posting)
    app.Put("/somePut", putting)
    app.Delete("/someDelete", deleting)
    app.Patch("/somePatch", patching)
    app.Head("/someHead", head)
    app.Options("/someOptions", options)

    app.Run(iris.Addr(":8080"))
}
从 请求 中获得参数的值
app.Get("/users/{id:uint64}", func(ctx iris.Context){
    id := ctx.Params().GetUint64Default("id", 0)
    // [...]
})
从查询字符串( QueryString )中获得值

查询字符串 QueryString,是网址中的 键值对的格式。 比如这样格式: /welcome?firstname=Jane&lastname=Doe.

app.Get("/welcome", func(ctx iris.Context) {
       
       // 下面这个是 ctx.Request().URL.Query().Get("lastname"). 的简单写法
      // 读取值
       lastname := ctx.URLParam("lastname") 
     // ,读取值支持默认值的方式
       firstname := ctx.URLParamDefault("firstname", "Guest")
   })
从表单(Form) 中获得值

通过POST发来的请求中有 "表单(Form) 数据", 这样来获取

app.Post("/form_post", func(ctx iris.Context) {
        message := ctx.FormValue("message")
        nick := ctx.FormValueDefault("nick", "anonymous")

    })
上传文件

设定 maxSize 控制 请求包的大小,和保存的文件名。

复制

const maxSize = 5 << 20 // 5MB

func main() {
    app := iris.Default()
    app.Post("/upload", iris.LimitRequestBodySize(maxSize), func(ctx iris.Context) {
        // 这里指示了 网址,和  beforeSave
        ctx.UploadFormFiles("./uploads", beforeSave)
    })

    app.Run(iris.Addr(":8080"))
}

func beforeSave(ctx iris.Context, file *multipart.FileHeader) {
    ip := ctx.RemoteAddr()
    // 获取ip地址,转成字符串
    ip = strings.Replace(ip, ".", "_", -1)
    ip = strings.Replace(ip, ":", "_", -1)

    // 这里处理了文件名
    file.Filename = ip + "-" + file.Filename
}
支持对路由的分组

复制

  func main() {
    app := iris.Default()

    // Simple group: v1.
    v1 := app.Party("/v1")
    {
        v1.Post("/login", loginEndpoint)
        v1.Post("/submit", submitEndpoint)
        v1.Post("/read", readEndpoint)
    }

    // Simple group: v2.
    v2 := app.Party("/v2")
    {
        v2.Post("/login", loginEndpoint)
        v2.Post("/submit", submitEndpoint)
        v2.Post("/read", readEndpoint)
    }

    app.Run(iris.Addr(":8080"))
  } 
中间件

使用 app.Use() 函数来添加中间件

示例:

代码语言:javascript

复制

 app := iris.New()
 app.Use(recover.New())

日志中间件:

  requestLogger := logger.New(logger.Config{
      // Status displays status code
      Status: true,
      // IP displays request's remote address
      IP: true,
      // Method displays the http method
      Method: true,
      // Path displays the request path
      Path: true,
      // Query appends the url query to the Path.
      Query: true,

      // if !empty then its contents derives from `ctx.Values().Get("logger_message")
      // will be added to the logs.
      MessageContextKeys: []string{"logger_message"},

      // if !empty then its contents derives from `ctx.GetHeader("User-Agent")
      MessageHeaderKeys: []string{"User-Agent"},
  })
  app.Use(requestLogger)

为某个分组的 url 段添加中间件

// Authorization party /user.
// authorized := app.Party("/user", AuthRequired())
// exactly the same as:
authorized := app.Party("/user")
// per party middleware! in this case we use the custom created
// AuthRequired() middleware just in the "authorized" group/party.
authorized.Use(AuthRequired())
{
    authorized.Post("/login", loginEndpoint)
    authorized.Post("/submit", submitEndpoint)
    authorized.Post("/read", readEndpoint)

    // nested group: /user/testing
    testing := authorized.Party("/testing")
    testing.Get("/analytics", analyticsEndpoint)
}
写入日志到文件中

先准备一个 file 流

// Get a filename based on the date, just for the sugar.
func todayFilename() string {
    today := time.Now().Format("Jan 02 2006")
    return today + ".txt"
}

func newLogFile() *os.File {
    filename := todayFilename()
    // Open the file, this will append to the today's file if server restarted.
    f, err := os.OpenFile(filename, os.O_CREATE|os.O_WRONLY|os.O_APPEND, 0666)
    if err != nil {
        panic(err)
    }

    return f
}

调用 app.Logger().SetOutput 指向这个文件

f := newLogFile()
defer f.Close()

app := iris.New()
app.Logger().SetOutput(f)
    ctx.SetCookieKV(name, value)
    value := ctx.GetCookie(name)
    ctx.RemoveCookie(name)

示例:

 app.Get("/cookies/{name}/{value}", func(ctx iris.Context) {
     name := ctx.Params().Get("name")
     value := ctx.Params().Get("value")

     ctx.SetCookieKV(name, value)

     ctx.Writef("cookie added: %s = %s", name, value)
 })
处理跨域CORS

跨域资源共享(CORS) 是一种机制,它使用额外的 HTTP 头来告诉浏览器 让运行在一个 origin (domain) 上的Web应用被准许访问来自不同源服务器上的指定的资源。 出于安全原因,浏览器限制从脚本内发起的跨源HTTP请求。 例如,XMLHttpRequest和Fetch API遵循同源策略。 这意味着使用这些API的Web应用程序只能从加载应用程序的同一个域请求HTTP资源,除非响应报文包含了正确CORS响应头。

跨域资源共享( CORS )机制允许 Web 应用服务器进行跨域访问控制,从而使跨域数据传输得以安全进行。现代浏览器支持在 API 容器中(例如 XMLHttpRequest 或 Fetch )使用 CORS,以降低跨域 HTTP 请求所带来的风险。

Iris 的一个社区框架可以帮助解决跨域问题,分几个步骤:

  • 配置 crs 对象的参数,AllowedOrigins 参数设定服务器地址
  • 为你的 Party 加入允许。方法: app.Party("/api/v1", crs).AllowMethods(iris.MethodOptions)

代码示例:

  package main

  import (
    "github.com/kataras/iris/v12"

    "github.com/iris-contrib/middleware/cors"
  )

  func main() {
    app := iris.New()

    crs := cors.New(cors.Options{
        AllowedOrigins:   []string{"*"}, // 这里写允许的服务器地址,* 号标识任意
        AllowCredentials: true,
    })

    v1 := app.Party("/api/v1", crs).AllowMethods(iris.MethodOptions) // <- important for the preflight.
    {
        v1.Get("/home", func(ctx iris.Context) {
            ctx.WriteString("Hello from /home")
        })
        v1.Get("/about", func(ctx iris.Context) {
            ctx.WriteString("Hello from /about")
        })
        v1.Post("/send", func(ctx iris.Context) {
            ctx.WriteString("sent")
        })
        v1.Put("/send", func(ctx iris.Context) {
            ctx.WriteString("updated")
        })
        v1.Delete("/send", func(ctx iris.Context) {
            ctx.WriteString("deleted")
        })
    }

    app.Run(iris.Addr("localhost:8080"))
  }

详细见:https://github.com/iris-contrib/middleware/tree/master/cors

了解更多

更多请参考官方文档:https://iris-go.com/

官方GIT地址: https://github.com/kataras/iris

相关推荐
析木不会编程2 分钟前
【C语言】特殊指针汇总
c语言·开发语言
Komorebi_99994 分钟前
javaScript中slice()和splice()的用法与区别
开发语言·前端·javascript
橘颂TA8 分钟前
【C++】大厂算法题(详解)
开发语言·c++·算法
严就方法18 分钟前
Qt creator ,语言家功能缺失解决方法
开发语言·qt
云空23 分钟前
《 QT 5.14.1 类库模块列表详述》
开发语言·qt·系统架构
opentogether35 分钟前
Swift 的动态性
开发语言·ssh·swift
安卓机器36 分钟前
探索 Python编程 调试案例:计算小程序中修复偶数的bug
开发语言·python
明月看潮生36 分钟前
青少年编程与数学 02-004 Go语言Web编程 11课题、认证、授权与安全
开发语言·安全·青少年编程·编程与数学·goweb
Jelena技术达人1 小时前
利用Java获取淘宝商品详情API接口的深入指南引言
java·开发语言
数据小爬虫@1 小时前
如何确保Java爬虫不超出API使用限制:策略示例
java·开发语言·爬虫