Try   HackMD

架設一個簡單的Https Web伺服器

OS: Ubuntu 20.04

Install Golang packages

  1. 安裝GVM

    ​​​​sudo apt-get update
    ​​​​sudo apt-get install -y binutils bison gcc make 
    
    ​​​​bash < <(curl -s -S -L https://raw.githubusercontent.com/moovweb/gvm/master/binscripts/gvm-installer) 
    
    ​​​​source /home/$(whoami)/.gvm/scripts/gvm 
    
  2. 安裝1.18版本,並設定預設版本。

    ​​​​gvm install go1.18 -B
    ​​​​gvm use go1.18 --default 
    

Generate a SSL certificate

先行產生兩個檔案,.csr.key檔案會用來產生證書(.crt)用的。

例如:server.key (私密金鑰 Private Key)、server.crt (憑證檔)、server.crt (中繼憑證 Intermediate CA)

指令: openssl req -newkey rsa:4096 -nodes -keyout server.key -out server.csr

For example:

$ openssl req -newkey rsa:4096 -nodes -keyout server.key -out server.csr

Generating a RSA private key
...............................................................++++
............++++
writing new private key to 'server.key'
-----
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:
State or Province Name (full name) [Some-State]:
Locality Name (eg, city) []:
Organization Name (eg, company) [Internet Widgits Pty Ltd]:
Organizational Unit Name (eg, section) []:
Common Name (e.g. server FQDN or YOUR name) []:
Email Address []:

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:

$ ls
server.csr  server.key

再來產生ssl檔案。

$ openssl x509 -signkey server.key -in server.csr -req -days 365 -out server.crt

Signature ok
subject=C = AU, ST = Some-State, O = Internet Widgits Pty Ltd
Getting Private key

$ ls
server.crt  server.csr  server.key

創建一個Web server

  1. 先行下載相依包。

    ​​​​go install "github.com/gin-gonic/gin@latest"
    
  2. 創見一個檔案夾名為 server 然後初始化一下。

    ​​​​mkdir server && cd server
    ​​​​go mod init server
    ​​​​go mod tidy
    
  3. 創立一個名為main.go的文件並打開。

    ​​​​package main ​​​​import "github.com/gin-gonic/gin" ​​​​func main() { ​​​​ // gin.SetMode(gin.ReleaseMode) ​​​​ r := gin.Default() ​​​​ r.GET("/", func(c *gin.Context) { ​​​​ c.String(200, "hello world") ​​​​ }) ​​​​ ​​​​ // go r.RunTLS(":5555", "./certs/server.crt", "./certs/server.key") ​​​​ r.Run(":5757") ​​​​}
  4. 先啟動http服務測試一下是否有問題。

    ​​​​go run main.go
    

    Outputs:

    ​​​​[GIN-debug] [WARNING] Creating an Engine instance with the Logger and Recovery middleware already attached.
    
    ​​​​[GIN-debug] [WARNING] Running in "debug" mode. Switch to "release" mode in production.
    ​​​​ - using env:	export GIN_MODE=release
    ​​​​ - using code:	gin.SetMode(gin.ReleaseMode)
    
    ​​​​[GIN-debug] GET    /                         --> main.main.func1 (3 handlers)
    ​​​​[GIN-debug] [WARNING] You trusted all proxies, this is NOT safe. We recommend you to set a value.
    ​​​​Please check https://pkg.go.dev/github.com/gin-gonic/gin#readme-don-t-trust-all-proxies for details.
    ​​​​[GIN-debug] Listening and serving HTTP on :5757
    

    成功。

  5. 把剛剛產生的keys丟到程式目錄底下。

    ​​​​mkdir certs
    ​​​​mv ../server.key certs/
    ​​​​mv ../server.crt certs/
    
  6. 把第12行的程式註解掉,再跑一次。

    ​​​​go run main.go
    

    即可同時跑起http和https的web server了。

  7. 接下來,讓我們來產生執行。

    ​​​​go build main.go
    ​​​​./main 
    

    即可運行成功!
    (如果搬動此執行檔,務必把certs的檔案夾也要一起放置相對路徑下,方能正常執行。)

可以簡單的在瀏覽器查看:https://(ip):5555