如何为 Go 服务器应用程序设置 Let's Encrypt

How to set up Let's Encrypt for a Go server application

我有自己的域,其中包含用 Go 编写的 Web 服务。我正在使用内置的 Go Web 服务器,前面没有 Nginx 或 Apache。

我想开始通过 HTTPS 提供服务,我意识到 Let's Encrypt 即将成为实现这一目标的方式。

任何人都可以分享在 Linux 服务器上配置 Go 应用 运行 的整个设置过程吗?

我找到了一个非常简单的解决方案,使用standalone模式。


安装 CERTBOT 客户端(Let's Encrypt 推荐)

(go to the directory where you want to install the certbot client)
git clone https://github.com/certbot/certbot
cd certbot
./certbot-auto --help`


颁发证书(第一次)

N.B。此操作通过端口 80 发生,因此如果您的 Go 应用程序侦听端口 80,则需要在 运行 执行此命令之前将其关闭(顺便说一句,运行 执行起来非常快)

./certbot-auto certonly --standalone-supported-challenges http-01 -d www.yourdomain.com

在您的 GO 代码中添加 SSL 侦听器

http.ListenAndServeTLS(":443", "/etc/letsencrypt/live/www.yourdomain.com/fullchain.pem", "/etc/letsencrypt/live/www.yourdomain.com/privkey.pem", nil)

完成!


更新证书(证书在 90 天后过期)

N.B。您可以手动 运行(您将在证书过期前几天收到一封电子邮件),或者设置一个 crontab

如果您的 Go 应用程序不再侦听端口 80,您的 Go 应用程序可以在您执行此命令时保持 运行ning:
./certbot-auto renew --standalone

如果您的 Go 应用程序仍然侦听端口 80,您可以指定停止和重新启动 Go 应用程序的命令:
./certbot-auto renew --standalone --pre-hook "command to stop Go app" --post-hook "command to start Go app"

有关 Certbot 命令的完整文档: https://certbot.eff.org/docs/using.html

这是我发现的使用 Go 和 Let's Encrypt 证书的 HTTPS 服务器的最小自动设置:

package main

import (
    "crypto/tls"
    "log"
    "net/http"

    "golang.org/x/crypto/acme/autocert"
)

func main() {
    certManager := autocert.Manager{
        Prompt:     autocert.AcceptTOS,
        HostPolicy: autocert.HostWhitelist("example.com"), //Your domain here
        Cache:      autocert.DirCache("certs"),            //Folder for storing certificates
    }

    http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
        w.Write([]byte("Hello world"))
    })

    server := &http.Server{
        Addr: ":https",
        TLSConfig: &tls.Config{
            GetCertificate: certManager.GetCertificate,
        },
    }

    go http.ListenAndServe(":http", certManager.HTTPHandler(nil))

    log.Fatal(server.ListenAndServeTLS("", "")) //Key and cert are coming from Let's Encrypt
}

关于 autocert 包的更多信息:link

编辑:由于 letsencrypt security issue, read more here,需要使 http 可用。作为此修复的奖励,我们现在有了 http-->https 重定向。如果您已经收到证书,旧示例将继续工作,但它会在新站点上中断。

如果您可以使用 DNS 验证,这就是续订的方式。

使用证书,简单的做:

    c := &tls.Config{MinVersion: tls.VersionTLS12}
    s := &http.Server{Addr: ":443", Handler: Gzipler(nosurf.New(router), 1), TLSConfig: c}
    log.Fatal(s.ListenAndServeTLS(
        "/etc/letsencrypt/live/XXX/fullchain.pem", 
        "/etc/letsencrypt/live/XXX/privkey.pem"
    ))

这个包含 Gzip 和 CSRF 保护。您可以使用

Handler: router

没有那些额外的功能。