Hosts

监听服务

您可以启动服务器监听任何类型的net.Listener甚至http.Server实例。服务器的初始化方法应该在最后通过Run函数传递。

Go开发人员用于服务其服务器的最常用方法是传递“hostname:ip”形式的网络地址。有了Iris,我们使用的iris.Addr是一种iris.Runner类型

//用网络地址监听tcp 0.0.0.0:8080

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

有时您在应用程序的其他位置创建了标准的net / http服务器,并希望使用它来为Iris Web应用程序提供服务

// 与之前相同,但使用自定义的http.Server,也可能在其他地方使用

app.Run(iris.Server(&http.Server{Addr:":8080"}))

最高级的用法是创建自定义或标准net.Listener并将其传递给app.Run

// 使用自定义的net.Listener

  1. l, err := net.Listen("tcp4", ":8080")
  2. if err != nil {
  3. panic(err)
  4. }
  5. app.Run(iris.Listener(l))

一个更完整的示例,使用仅限unix的套接字文件功能

  1. package main
  2. import (
  3. "os"
  4. "net"
  5. "github.com/kataras/iris"
  6. )
  7. func main() {
  8. app := iris.New()
  9. // UNIX socket
  10. if errOs := os.Remove(socketFile); errOs != nil && !os.IsNotExist(errOs) {
  11. app.Logger().Fatal(errOs)
  12. }
  13. l, err := net.Listen("unix", socketFile)
  14. if err != nil {
  15. app.Logger().Fatal(err)
  16. }
  17. if err = os.Chmod(socketFile, mode); err != nil {
  18. app.Logger().Fatal(err)
  19. }
  20. app.Run(iris.Listener(l))
  21. }

UNIX和BSD主机可以优先考虑重用端口功能

  1. package main
  2. import (
  3. // Package tcplisten provides customizable TCP net.Listener with various
  4. // performance-related options:
  5. //
  6. // - SO_REUSEPORT. This option allows linear scaling server performance
  7. // on multi-CPU servers.
  8. // See https://www.nginx.com/blog/socket-sharding-nginx-release-1-9-1/ for details.
  9. //
  10. // - TCP_DEFER_ACCEPT. This option expects the server reads from the accepted
  11. // connection before writing to them.
  12. //
  13. // - TCP_FASTOPEN. See https://lwn.net/Articles/508865/ for details.
  14. "github.com/valyala/tcplisten"
  15. "github.com/kataras/iris"
  16. )
  17. //go get github.com/valyala/tcplisten
  18. //go run main.go
  19. func main() {
  20. app := iris.New()
  21. app.Get("/", func(ctx iris.Context) {
  22. ctx.HTML("<h1>Hello World!</h1>")
  23. })
  24. listenerCfg := tcplisten.Config{
  25. ReusePort: true,
  26. DeferAccept: true,
  27. FastOpen: true,
  28. }
  29. l, err := listenerCfg.NewListener("tcp", ":8080")
  30. if err != nil {
  31. app.Logger().Fatal(err)
  32. }
  33. app.Run(iris.Listener(l))
  34. }

HTTP / 2和安全

如果您有已签名的文件密钥,则可以根据这些证书密钥使用该iris.TLS服务https

  1. app.Run(iris.TLS("127.0.0.1:443", "mycert.cert", "mykey.key"))

该方法时,你的应用程序已经准备好,你应该使用的生产是iris.AutoTLS其开始安全服务器所提供的自动认证https://letsencrypt.org为免费

// Automatic TLS

  1. app.Run(iris.AutoTLS(":443", "example.com", "admin@example.com"))

任何 iris.Runner

有时你可能想要一些非常特别的东西来听,这不是一种类型的net.Listener。你能够做到这一点iris.Raw,但你负责这种方法

//使用任何func()错误,//启动听众的责任取决于你这个方式,//为了简单起见,我们将使用//net / http包的ListenAndServe函数

  1. app.Run(iris.Raw(&http.Server{Addr:":8080"}).ListenAndServe)

主机配置器

所有上述形式的倾听都接受了最后的,可变的论证func(*iris.Supervisor)。这用于为通过这些函数传递的特定主机添加配置程序。

例如,假设我们要添加一个在服务器关闭时触发的回调

  1. app.Run(iris.Addr(":8080", func(h *iris.Supervisor) {
  2. h.RegisterOnShutdown(func() {
  3. println("server terminated")
  4. })
  5. }))

您甚至可以在app.Run方法之前执行此操作,但区别在于这些主机配置程序将被执行到您可能用于为您的Web应用程序提供服务的所有主机(通过app.NewHost我们将在一分钟内看到)

  1. app := iris.New()
  2. app.ConfigureHost(func(h *iris.Supervisor) {
  3. h.RegisterOnShutdown(func() {
  4. println("server terminated")
  5. })
  6. })
  7. app.Run(iris.Addr(":8080"))

Application#Hosts在该Run方法之后,字段可以提供对为您的应用程序提供服务的所有主机的访问权限。

但最常见的情况是您可能需要在app.Run方法之前访问主机,有两种获取访问主机主管的方法,请参阅下文。

我们已经看到了如何通过app.Run或的第二个参数配置所有应用程序的主机app.ConfigureHost。还有一种方法更适合简单的场景,即使用app.NewHost创建新主机并使用其中一个Serve或多个Listen函数通过iris#RawRunner 启动应用程序。

请注意,这种方式需要额外导入net/http包。

  1. h := app.NewHost(&http.Server{Addr:":8080"})
  2. h.RegisterOnShutdown(func(){
  3. println("server terminated")
  4. })
  5. app.Run(iris.Raw(h.ListenAndServe))

多主机

您可以使用多个服务器为您的Iris Web应用程序提供服务,因此iris.Router与net/http/Handler功能兼容,您可以理解,它可以在任何net/http服务器上进行调整,但是有一种更简单的方法,通过使用app.NewHost也可以复制所有主机配置程序,它关闭连接到特定Web应用程序的所有主机app.Shutdown。

  1. app := iris.New()
  2. app.Get("/", indexHandler)
  3. //在不同的goroutine中运行,以便不阻止主要的“goroutine”。
  4. go app.Run(iris.Addr(":8080"))
  5. // 启动第二个服务器,它正在监听tcp 0.0.0.0:9090,
  6. //没有“go”关键字,因为我们想要在最后一次服务器运行时阻止。
  7. app.NewHost(&http.Server{Addr:":9090"}).ListenAndServe()

关机(优雅)让我们继续学习如何捕获CONTROL + C / COMMAND + C或unix kill命令并优雅地关闭服务器。

正确关闭CONTROL + C / COMMAND + C或者当发送的kill命令是ENABLED BY-DEFAULT时。

为了手动管理应用程序中断时要执行的操作,我们必须使用该选项禁用默认行为WithoutInterruptHandler 并注册新的中断处理程序(全局,跨所有可能的主机)。

如下代码:

  1. package main
  2. import (
  3. "context"
  4. "time"
  5. "github.com/kataras/iris"
  6. )
  7. func main() {
  8. app := iris.New()
  9. iris.RegisterOnInterrupt(func() {
  10. timeout := 5 * time.Second
  11. ctx, cancel := context.WithTimeout(context.Background(), timeout)
  12. defer cancel()
  13. // close all hosts
  14. app.Shutdown(ctx)
  15. })
  16. app.Get("/", func(ctx iris.Context) {
  17. ctx.HTML(" <h1>hi, I just exist in order to see if the server is closed</h1>")
  18. })
  19. app.Run(iris.Addr(":8080"), iris.WithoutInterruptHandler)
  20. }