Help us understand the problem. What is going on with this article?

net/httpでポート443のHTTPSサーバーを立ち上げるまで

More than 3 years have passed since last update.

動的言語しかやったこと無い私ですが、ひょんなことからGoにふれてみることにしました。
まだ、チュートリアルを読んだり、Effective Goを読んでみたりのレベルですが・・・

環境

  • CentOS6.7
    • Go 1.5.2

参考にしたサイト

まずはオレオレ証明書を作ってみる

証明書無いと動かないのでオレオレ証明書をopensslで作る(詳細版)を参考に証明書を作成

$ openssl genrsa 2048 > myself.key
$ openssl req -new -key myself.key > myself.csr
$ openssl x509 -days 3650 -req -signkey myself.key < myself.csr > myself.crt
$ mkdir -p ssl/development/
$ mv myself.crt ssl/development
$ mv myself.key ssl/development

Goでhttpsサーバーを書く

mainの一行(http.ListenAndServeTLS(":50124", "ssl/development/myself.crt", "ssl/development/myself.key", nil) )で作成したオレオレ証明書を食わせてます。今回はログインを想定した内容でフォームの値を確認するところまで記載しています。GoのHTTPSサーバー自体のポートは50124で起動するようにしています

server.go
package main

import (
    "fmt"
    "html/template"
    "log"
    "net/http"
    "strings"
)

func login(w http.ResponseWriter, r *http.Request) {
    fmt.Println("method:", r.Method) //リクエストを取得するメソッド
    if r.Method == "GET" {
        t, _ := template.ParseFiles("login.gtpl")
        t.Execute(w, nil)
    } else {
        r.ParseForm()
        //ログインデータがリクエストされ、ログインのロジック判断が実行されます。
        fmt.Println("username:", r.Form["username"])
        fmt.Println("password:", r.Form["password"])
    }
}

func main() {
    http.HandleFunc("/login", login)   //アクセスのルーティングを設定します

    err := http.ListenAndServeTLS(":50124", "ssl/development/myself.crt", "ssl/development/myself.key", nil)
    if err != nil {
        log.Fatal("ListenAndServe: ", err)
    }
}

以下ログインフォームのテンプレート

login.gtpl
<html>
<head>
<title></title>
</head>
<body>
<form action="/login" method="post">
    ユーザ名:<input type="text" name="username">
    パスワード:<input type="password" name="password">
    <input type="submit" value="ログイン">
</form>
</body>
</html>

SSLってポート443じゃ???

今回はrootではないユーザーでgoのHTTPSサーバーを起動させることを想定していますので、root以外のユーザーだとポート1024以上ではないとポートをlistenできないので、GoのHTTPサーバーを80番や443番ポートでListenする方法を調べたを参考にiptablesでポートフォワーディングして50124につなぎます。

ポート周りの設定はiptablesに寄せる方針です。

# Firewall configuration written by system-config-firewall
# Manual customization of this file is not recommended.
*nat
:PREROUTING ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
:POSTROUTING ACCEPT [0:0]
# HTTP
-A PREROUTING -p tcp --dport 80 -j REDIRECT --to-port 50123
# HTTPS
-A PREROUTING -p tcp --dport 443 -j REDIRECT --to-port 50124
COMMIT


*filter
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
-A INPUT -p icmp -j ACCEPT
-A INPUT -i lo -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 22 -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 80 -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 443  -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 50123 -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 50124 -j ACCEPT

-A INPUT -j REJECT --reject-with icmp-host-prohibited
-A FORWARD -j REJECT --reject-with icmp-host-prohibited
COMMIT
  • *filterに443と50124ポートのポート開放の設定を
  • *natに443ポートをlistenした場合は50124にポートフォワーディングをする設定を

書きます。
(上記内容は80番ポートの設定も一緒に記載しています)

Goのサーバーを起動してみる

root以外のユーザーで起動してみます

go run server.go

ブラウザで https://localhost/login vagrantとかなら https://{IPアドレス}/login にアクセスしてみください。

最後に

HTTPSとHTTPをserver.goで同時に動かしたいんだけども方法がわからない・・・・・

ryurock
認定スクラムマスター 認定プロダクトオーナー http://www.scrumalliance.org/community/profile/rkimura2
https://github.com/ryurock
visasq
ビザスクは「知見と、挑戦をつなぐ」をミッションに、世界で1番のナレッジプラットフォームをつくっています。 様々なニーズにつなぐことで、実際に経験したことで得られた知識や意見を、知見として価値最大化します。組織、世代、地域を超えて、知見を集めつなぐことで、世界中のイノベーションに貢献します。
https://visasq.co.jp
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away