Ubuntu 18.04でNginxを使用してGo Webアプリケーションを展開する方法

_著者は、https://www.brightfunds.org/funds/tech-education [Tech Education Fund]を選択して、https://do.co/w4do-cta [Write for DOnations]プログラムの一環として寄付を受け取りました。 _

前書き

Goは汎用プログラミング言語であり、徐々に最も人気のあるWebバックエンドプログラミング言語の1つになりつつあります。 シンプルさを重視することで、Goの設計者は、Webアプリケーション用に他の多くの言語よりも学習が容易で高速な言語を作成し、同時実行性により複数のリクエストを一度に処理できるなどの効率的な機能を活用しました。 このため、GoでWebアプリケーションをデプロイすることは、多くのバックエンド開発者にとって有用です。

Nginxは、リソースの軽量化と負荷時の信頼性により、世界で最も人気のあるWebサーバーの1つです。 インターネット上で最大かつ最もトラフィックの多いサイトの多くは、コンテンツを提供するためにNginxに依存しています。 展開では、Nginxはロードバランサーまたはリバースプロキシとしてよく使用され、セキュリティを強化し、アプリケーションをより堅牢にします。 Go Webバックエンドと組み合わせて、Nginxは強力で高速なWebアプリケーションを提供できます。

このチュートリアルでは、Goで + Hello World + Webアプリケーションを構築し、Nginxをリバースプロキシとして使用してUbuntu 18.04サーバーにデプロイします。

前提条件

このチュートリアルを実行するには、次のものが必要です。

  • このhttps://www.digitalocean.com/community/tutorials/initial-server-setup-with-ubuntu-18-04[Ubuntu 18.04チュートリアルの初期サーバー設定]に従ってsudo nonを含む1つのUbuntu 18.04サーバーをセットアップ-rootユーザーとファイアウォール。

  • Goプログラミング言語install-go-and-up-a-local-programming-environment-on-ubuntu-18-04 [Ubuntu 18.04にGoをインストールしてローカルプログラミング環境をセットアップする方法]。

  • Nginx Nginxのインストール方法に従ってインストールUbuntu 18.04で]。 ステップ5 –サーバーブロックの設定;このチュートリアルの後半でNginxサーバーブロックを作成します。

  • https://www.digitalocean.com/community/tutorials/how-to-set-up-a-host-name-with-digitalocean [ホスト名の設定方法]で説明されているように、サーバーを指すドメイン名DigitalOcean]で。 このチュートリアルでは、全体で「++」を使用します。 これは、WebサイトのSSL証明書を取得するために必要なため、TLS暗号化を使用してアプリケーションを安全に提供できます。

さらに、Go Webアプリケーションの実稼働グレードの展開を実現するには、TLS / SSL証明書をインストールしてサーバーを安全に保つことが重要です。 このステップは*強くお勧めします*。 Go Webアプリケーションを保護するには、https://www.digitalocean.com/community/tutorials/how-to-secure-nginx-with-let-s-encrypt-on-ubuntu-18-04 [Nginxを保護する方法]に従ってください。無料のTLS / SSL証明書を取得するために、このチュートリアルの*ステップ3 *の後、Ubuntu 18.04で暗号化しましょう。

手順1-Go Webアプリケーションの構築

この手順では、「+ Hello World」を「+」で表示し、ユーザーに「 / greet / +」で挨拶するサンプルGo Webアプリケーションを構築します。 Goでのプログラミングの基本について詳しく知りたい場合は、https://www.digitalocean.com/community/tutorials/how-to-write-your-first-program-in-go [How To Goで最初のプログラムを書く]の記事。

まず、https://www.digitalocean.com/community/tutorials/understanding-the-gopath [+ GOPATH +]ディレクトリに新しいディレクトリを作成して、ソースファイルを保持します。 フォルダーには好きな名前を付けることができますが、このチュートリアルでは `++`を使用します。

mkdir $GOPATH/

前提条件のチュートリアルhttps://www.digitalocean.com/community/tutorials/how-to-install-go-and-set-up-a-local-programming-environment-on-ubuntu-18で提案されているファイル構造に従う-04 [Ubuntu 18.04でGoをインストールしてローカルプログラミング環境をセットアップする方法]、これによりディレクトリに `+〜/ go / go-web +`のパスが与えられます。

次に、以下を実行して、ディレクトリを `+ GOPATH +`に新しく作成したフォルダに変更します。

cd $GOPATH/go-web

`+ nano `または好みのテキストエディターを使用して、 ` main.go +`という名前のファイルを作成します。このファイルには、Webアプリケーションのソースコードが含まれます。

nano main.go

`+ Hello World `アプリケーションの機能を作成するには、新しく作成された ` main.go +`ファイルに次のGoコードを追加します。

〜/ go / go-web / main.go

package main

import (
   "fmt"
   "net/http"
)

func main() {
   http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
       fmt.Fprintf(w, "Hello World")
   })

   http.HandleFunc("/greet/", func(w http.ResponseWriter, r *http.Request) {
       name := r.URL.Path[len("/greet/"):]
       fmt.Fprintf(w, "Hello %s\n", name)
   })

   http.ListenAndServe(":9990", nil)
}

それでは、最初の行から始めて、前述のコードスニペットの動作を見ていきましょう。

最初に、エントリポイントをアプリケーションに書き込みました。

〜/ go / go-web / main.go

package main
...

`+ package main +`は、このファイルを共有ライブラリーではなく実行可能プログラムとしてコンパイルするようGoコンパイラーに指示します。

次に、 `+ import +`ステートメントがあります:

〜/ go / go-web / main.go

...

import (
   "fmt"
   "net/http"
)
...

このスニペットは、このコードが機能するために必要なモジュールをインポートします。これには、Webサーバーの標準の `+ fmt `パッケージと ` net / http +`パッケージが含まれます。

次のスニペットは、Goアプリケーションのエントリポイントである `+ main +`関数で最初のルートを作成します。

〜/ go / go-web / main.go

...
func main () {
   http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
       fmt.Fprintf(w, "Hello World")
   })
 ...
}
...

親ルート `+ / `が ` func main `内に作成され、リクエストされたときにテキスト ` Hello World +`が返されます。

次のスニペットに示されている2番目のルートは、URLパラメーター(この場合は名前)を受け入れて、グリーティングと共に表示します。

〜/ go / go-web / main.go

...
func main () {
 ...
   http.HandleFunc("/greet/", func(w http.ResponseWriter, r *http.Request) {
       name := r.URL.Path[len("/greet/"):]
       fmt.Fprintf(w, "Hello %s\n", name)
   })
...
}
...

これは、Goの `+ URL.Path `を使用して、値を ` / greet / +`の直後に保存し、URLパラメータから名前として渡します。

最後に、サーバーをインスタンス化します。

〜/ go / go-web / main.go

...
func main () {
 ...
 http.ListenAndServe(":9990", nil)
}

上記のスニペットはサーバーを起動し、Goの組み込みの「+ http 」サーバーを使用してポート「+9990」経由でアプリケーションを公開します。

`+ main.go +`のコードの調査が終了したら、ファイルを保存してテキストエディターを終了します。

次に、次を実行して、アプリケーションのバイナリ実行可能ファイルをビルドします。

go build main.go

上記のコマンドは、「+ main.go 」をコンパイルして「 main +」というタイトルの実行可能ファイルを生成します。

サンプルGo Webアプリケーションを作成しました。 次に、systemdユニットファイルを作成して、サーバーにアクセスしていないときでもアプリケーションをバックグラウンドで実行し続けます。

ステップ2-Systemd Unitファイルの作成

この手順では、https://www.digitalocean.com/community/tutorials/understanding-systemd-units-and-unit-files [systemd]ユニットファイルを作成して、ユーザーがバックグラウンドでアプリケーションを実行し続けるようにします。サーバーからログアウトします。 これにより、アプリケーションが永続化され、実稼働グレードのデプロイメントに一歩近づきます。

最初に、 + nano +`または好みのテキストエディターを使用して、 `+ goweb.service ie`という名前の + / lib / systemd / system`ディレクトリに新しいファイルを作成します。

sudo nano /lib/systemd/system/goweb.service

サービスのパラメーターを設定するには、次のスニペットをファイルに追加します。

/lib/systemd/system/goweb.service

[Unit]
Description=goweb

[Service]
Type=simple
Restart=always
RestartSec=5s
ExecStart=/home//go/go-web/main

[Install]
WantedBy=multi-user.target

`+ ExecStart = / home // go / go-web / main `変数は、このサービスのエントリポイントが ` / home // go / go-go `にある ` main `実行可能ファイルを経由することを指定しますここで、「+」はサーバーの非ルートsudoアカウントのユーザー名です。 `+ Restart = always `は、systemdが停止した場合に常にプログラムの再起動を試みるようにします。 次の行では、 ` RestartSec = 5s `は再起動の試行間の5秒の待機時間を設定します。 ` WantedBy = multi-user.target +`は、サーバーがサービスを有効にする状態を指定します。

ファイルを保存して終了します。

サービスユニットファイルを作成したら、次を実行してGo Webサービスを開始します。

sudo service goweb start

サービスが実行されているかどうかを確認するには、次のコマンドを使用します。

sudo service goweb status

次の出力が表示されます。

Output● goweb.service - goweb
  Loaded: loaded (/lib/systemd/system/goweb.service; disabled; vendor preset: enabled)
  Active: active (running) since Wed 2019-07-17 23:28:57 UTC; 6s ago
Main PID: 1891 (main)
   Tasks: 4 (limit: 1152)
  CGroup: /system.slice/goweb.service
          └─1891 /home//go/go-web/main

systemdユニットファイルの操作の詳細については、https://www.digitalocean.com/community/tutorials/understanding-systemd-units-and-unit-files [Systemdユニットとユニットファイルについて]をご覧ください。

アプリケーションを起動して実行したら、Nginxリバースプロキシを設定できます。

手順3-Nginxを使用したリバースプロキシのセットアップ

この手順では、Nginxサーバーブロックを作成し、Nginxリバースプロキシを設定して、アプリケーションをインターネットに公開します。

最初に、作業ディレクトリをNginxの `+ sites-available +`ディレクトリに変更します。

cd /etc/nginx/sites-available

アプリケーションを公開するドメインの名前で新しいファイルを作成します。 このチュートリアルでは、「++」を使用します。

sudo nano

ファイルに次の行を追加して、「++」の設定を確立します。

/ etc / nginx / sites-available / your_domain

server {
   server_name  ;

   location / {
       proxy_pass http://localhost:9990;
   }
}

このNginxサーバーブロックは、http://nginx.org/en/docs/http/ngx_http_proxy_module.html#proxy_pass [+ proxy_pass +]を使用して、サーバーのIPアドレスでGo Webアプリケーションを提供し、「+ localhost 」として示されます。ポート ` 9990 `で実行します。 「 server_name +」は、IPアドレスにマッピングされたドメイン名を示します。この場合は「」と「」です。

次に、次のコマンドを実行して、 `+ sites-enabled +`フォルダーにこのNginx設定のシンボリックリンクを作成します。

sudo ln -s /etc/nginx/sites-available/ /etc/nginx/sites-enabled/

シンボリックリンクは、別の場所にあるファイルのショートカットです。 新しく作成されたショートカットは、元のファイルを常に参照して、編集が行われたときに更新に適応します。 Nginxでは、両方のディレクトリに設定のコピーが必要です。

次に、reloadコマンドを実行してNginxの構成を再読み込みします。

sudo nginx -s reload

展開が機能していることを確認するには、ブラウザで「+ http:// +」にアクセスします。 * Hello World *テキスト文字列が表示されます。

これで、Nginxリバースプロキシを設定して、ドメイン名でアプリケーションを公開し、Go WebアプリケーションをSSL / TLSで保護しました。 次のステップでは、安全な接続を介してアプリケーションをテストします。

ステップ4-アプリケーションのテスト

このステップでは、安全な接続を介してアプリケーションをテストし、すべてが機能していることを確認します。

好みのWebブラウザーを開き、「+ https:// +」にアクセスします。

image:https://assets.digitalocean.com/articles/66224/Hello_World.png [Hello World Page Display]

シンプルな「+ Hello World」メッセージが表示されます。 URLで「+ https:// +」を使用しているときにこのメッセージを受け取った場合、アプリケーションが安全な接続で提供されていることを示しています。

次に、2番目のルート「+ https:/// greet / 」にアクセスして、「+」をアプリに挨拶したい名前に置き換えます。

image:https://assets.digitalocean.com/articles/66224/Greet.png [挨拶ページの表示]

アプリケーションは、URLに渡されたパラメーターに基づいて、「++」とともに簡単な挨拶を返します。

これらの結果を受け取ったら、Go Webアプリケーションを正常にデプロイしました。

結論

このチュートリアルでは、標準ライブラリを使用してGoで簡単なWebアプリケーションを作成し、Nginxを使用してリバースプロキシを設定し、ドメインでSSL証明書を使用してアプリを保護しました。 Goの詳細については、https://golang.org/doc/ [公式ドキュメント]をご覧ください。 また、この効率的な言語でのプログラミングの詳細については、https://www.digitalocean.com/community/tutorial_series/how-to-code-in-go [Goでコーディングする方法]シリーズをご覧ください。

Related