tk_ch’s blog

インフラエンジニアのブログ

GCP Compute Engine インスタンス(無料枠)を作成してSSH接続する

Google Cloud Platform(GCP)のIaaSサービスであるGoogle Compute Engine(GCE)に検証用途でVMインスタンスを作成し、SSH接続をしたときのメモ。

環境

VMインスタンスのOS:CentOS7

実施内容

インスタンスを作成する

GCPのドキュメントを参考に、VMインスタンスを作成する。
GCEの無料枠に収まるよう、以下の内容で作成することにした。
※リージョンはアイオワ(us-central1)、サウスカロライナ(us-east1)も対象だが、東京からの距離が最も近いオレゴンを選択した。

  • リージョン:オレゴン(us-west1)
  • ストレージ:30GBの標準永続ディスク
  • インスタンスタイプ:非プリエンプティブル e2-micro

GCEのページで「インスタンスを作成」をクリックする。
作成するインスタンスの設定画面になるので、上記の無料枠条件に当てはまるよう、以下のようにリージョン、ゾーン、マシンの構成、ブートディスク、アクセススコープの設定を変更する。

  • 今回はCentOS7を使いたいので、ブートディスクのイメージのところは「CentOS7」を選択する。
  • アクセススコープは「デフォルトのアクセス権を許可」だと実行出来ない操作が出てくるので、色々検証できるよう「すべての Cloud API に完全アクセス権を許可」に変更する。

インスタンスの作成1
インスタンスの作成1

インスタンスの作成2
インスタンスの作成2

設定を変更したら、画面一番下の「作成」をクリックする。
すると、以下のようにVMインスタンスが作成される。

作成されたインスタンス
作成されたインスタンス

インスタンスの外部IPを固定する

インスタンスには外部IP(グローバルIP)が割り当てられているが、これはエフェメラル外部IPで、インスタンスの再起動などで変わってしまう。
固定の方が使うときに便利なので、こちらを参考に外部IPをエフェメラルから静的IPに昇格させる。

ナブゲーションメニューからVPCネットワークの画面に遷移し、「IPアドレス」をクリックする。
以下のようにIPアドレスの一覧が表示される。
先ほど作成したinstance-1に割り当てられた外部IPがあるので、一番右の「予約」をクリックする。

IPの情報
IPの情報

静的IPアドレス名を適当に付けて「予約」をクリックする。

静的アドレスの予約
静的アドレスの予約

すると、以下のようにIPの種類列の表示が「エフェメラル」から「静的」に変わる。
これで外部IPを固定化できた。

種類が「エフェメラル」から「静的」に変わっている
種類が「エフェメラル」から「静的」に変わっている

インスタンスファイアウォール設定

インスタンスの一覧のIP列にある「nic0」をクリックすると、ネットワーク インターフェースの詳細を確認することができる。
ここで、デフォルトで設定されているファイアウォールのルールを見ると、以下のようにicmp、ssh、RDP接続がどこからでも可能な設定となっている。

デフォルトのファイアウォールルール
デフォルトのファイアウォールルール

これだとセキュリティ的に不安なので、各ルールをクリックして編集し、送信元IPv4範囲が「0.0.0.0/0」となっている箇所を自分が使うソースIPに書き換えておく。

SSH接続の設定をする

こちらによると、インスタンスへのSSH接続は「OS Login」を使うのがおすすめとのこと。
しかし今回は検証用途で、簡単に設定・接続したいのでメタデータ内の SSH 認証鍵を使う方法でやってみる。

SSH 認証鍵を作成する」を参考に、SSH認証鍵を作成する。
適当なLinuxサーバで以下を実行する。

認証鍵ペアを作成する
# ssh-keygen -t rsa -f ~/.ssh/gce-ssh-key -C dev-user -b 2048
Generating public/private rsa key pair.
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /root/.ssh/gce-ssh-key.
Your public key has been saved in /root/.ssh/gce-ssh-key.pub.
The key fingerprint is:
SHA256:jBio6FJ/0o4KC7B5KD1JaZIFDJyRKPftwiTT6wKPMR0 dev-user
The key's randomart image is:
+---[RSA 2048]----+
|B.+              |
|o*..             |
|..oo..           |
|.+E.+o.o         |
|*.=*.o. S        |
|*X.o+..          |
|OB=.o.o          |
|=+o..=           |
|. .o. .          |
+----[SHA256]-----+

秘密鍵を確認
#ls -l ~/.ssh/gce-ssh-key
-rw------- 1 root root 1679 10月 14 23:30 /root/.ssh/gce-ssh-key

公開鍵を確認
#ls -l ~/.ssh/gce-ssh-key.pub
-rw-r--r-- 1 root root 390 10月 14 23:30 /root/.ssh/gce-ssh-key.pub
#cat /root/.ssh/gce-ssh-key.pub
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDl7Yvw3k2R7wE/CKhF3etihDLijUVZGlEsIUYjvhny+B/z6eBBn3I2qJ7bPp2yfhh3PQYbb+o2mr/0nQhK0xKIzjNMK0Gqmii3He1nYRb27nFltQ9uAjHE/kkNax1tder9nruAv9YVjahP1raATUUCsiNEGYusS+TjpYY/+wFl74g2JyPMUknSwKpt1Ig+4Pmg1CtFiiDA1bdURSXdFIxOqYp5iZEwtepJne3sWgxqh5hAEtMP9SpArKHkuTUOLmyx3/ArEv5Fr4Fkp8wracc9MlBuDsUM5ih2z25mYGaKKCXEbA5sdy2O1vtOiaXAvPMTYLwv7VMmCkGFE5/bywuf dev-user

次に、「インスタンス メタデータに SSH 認証鍵を追加する」を参考に、インスタンスに公開鍵を登録する。

対象のインスタンスの詳細ページを表示し、「編集」をクリックする。

インスタンスの詳細
インスタンスの詳細

「セキュリティとアクセス」のSSH 認証鍵の「項目の追加」をクリックし、以下のように公開鍵(gce-ssh-key.pub)の中身を記載する。
その後、ページ下部の「保存」をクリックする。

インスタンスに公開鍵を登録
インスタンスに公開鍵を登録

これでインスタンスに公開鍵が登録されたので、秘密鍵を指定して外部IPに対しSSH接続してみる。

#ssh -i ~/.ssh/gce-ssh-key dev-user@34.168.77.125
Warning: Permanently added '34.168.77.125' (ECDSA) to the list of known hosts.
[dev-user@instance-1 ~]$ cat /etc/redhat-release
CentOS Linux release 7.9.2009 (Core)

→無事接続出来た。

gcloud CLI の設定

インスタンスには、最初からgcloud CLIがインストールされている。

$ gcloud version
Google Cloud SDK 404.0.0
alpha 2022.09.23
beta 2022.09.23
bq 2.0.78
bundled-python3-unix 3.9.12
core 2022.09.23
gcloud-crc32c 1.0.0
gsutil 5.14

しかし、このgcloud CLIだとコンポーネントのインストールやアップデートが出来ない。
(以下のように、代わりにyumを使うように言われてしまう。)

gcloud CLIでkubectlをインストールしてみる
$ gcloud components install kubectl
ERROR: (gcloud.components.install)
You cannot perform this action because the Google Cloud CLI component manager
is disabled for this installation. You can run the following command
to achieve the same result for this installation:

sudo yum install kubectl

gcloud CLIでコンポーネントをアップデートする
$ gcloud components update
To help improve the quality of this product, we collect anonymized usage data and anonymized stacktraces when
crashes are encountered; additional information is available at <https://cloud.google.com/sdk/usage-statistics>.
This data is handled in accordance with our privacy policy <https://cloud.google.com/terms/cloud-privacy-notice>.
 You may choose to opt in this collection now (by choosing 'Y' at the below prompt), or at any time in the future
 by running the following command:

    gcloud config set disable_usage_reporting false

Do you want to opt-in (y/N)?  y

Beginning update. This process may take several minutes.
ERROR: (gcloud.components.update)
You cannot perform this action because the Google Cloud CLI component manager
is disabled for this installation. You can run the following command
to achieve the same result for this installation:

sudo yum makecache && sudo yum update google-cloud-sdk-app-engine-go google-cloud-sdk-kpt google-cloud-sdk-kubectl-oidc google-cloud-sdk-harbourbridge google-cloud-sdk-firestore-emulator google-cloud-sdk-pubsub-emulator google-cloud-sdk-datastore-emulator google-cloud-sdk-spanner-emulator google-cloud-sdk-config-connector google-cloud-sdk google-cloud-sdk-terraform-tools google-cloud-sdk-cbt google-cloud-sdk-anthos-auth google-cloud-sdk-app-engine-python google-cloud-sdk-cloud-build-local google-cloud-sdk-nomos google-cloud-sdk-gke-gcloud-auth-plugin google-cloud-sdk-datalab google-cloud-sdk-bigtable-emulator kubectl google-cloud-sdk-app-engine-python-extras google-cloud-sdk-skaffold google-cloud-sdk-cloud-run-proxy google-cloud-sdk-bundled-python3 google-cloud-sdk-package-go-module google-cloud-sdk-local-extract google-cloud-sdk-app-engine-grpc google-cloud-sdk-minikube google-cloud-sdk-app-engine-java

こちらに以下のように記載されている。
最初から入っているgcloud CLIは恐らくyumでインストールされたものだと思われる。

注: APT や yum などのパッケージ マネージャーを使用して gcloud CLI をインストールしている場合、gcloud CLI コンポーネント マネージャーの手順は動作しません。この方法でインストールした場合には gcloud CLIコンポーネント・マネージャが無効になっているためです。代わりに、こちらのパッケージを使用してください。

以下を見ると、gcloud CLIコンポーネント・マネージャを使用したい場合には、パッケージ マネージャーでインストールされたgcloud CLIをアンインストールし、改めてインストーラーを使ってインストールすれば良いらしい。
stackoverflow.com GCPのドキュメントでは、基本的にコンポーネントはgcloud CLIでインストールしているので、gcloud CLIコンポーネント・マネージャを使用出来る状態にしておきたい。
やってみる。

gcloud CLIをアンインストールする。

アンインストール
$ sudo yum remove google-cloud-sdk

アンインストールされたことを確認
$ gcloud version
-bash: /usr/bin/gcloud: そのようなファイルやディレクトリはありません

こちらの手順を参考に、gcloud CLIをインストールする。
前提としてPython3(3.5~3.9)が必要なため、インストールする。

pyenvのインストールする。

yumアップデート
$ sudo yum -y update

必要なツールをインストール
$ sudo yum -y install gcc zlib-devel bzip2 bzip2-devel readline-devel sqlite sqlite-devel openssl-devel tk-devel libffi-devel git make

pyenvをgit clone
$ git clone https://github.com/pyenv/pyenv.git ~/.pyenv

PATHを設定
$ echo 'export PYENV_ROOT="$HOME/.pyenv"' >> ~/.bashrc
$ echo 'command -v pyenv >/dev/null || export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.bashrc
$ echo 'eval "$(pyenv init -)"' >> ~/.bashrc

設定を確認
$ tail -n 3 ~/.bashrc
export PYENV_ROOT="$HOME/.pyenv"
command -v pyenv >/dev/null || export PATH="$PYENV_ROOT/bin:$PATH"
eval "$(pyenv init -)"

設定変更を反映
$ source ~/.bashrc

pyenvがインストールされたことを確認
$ pyenv --version
pyenv 2.3.5-2-g03a5d65

Python3.9をインストールする。

インストールできるPythonバージョンを確認
$ pyenv install --list

Python3.9.15をインストール
$ pyenv install 3.9.15
Downloading Python-3.9.15.tar.xz...
-> https://www.python.org/ftp/python/3.9.15/Python-3.9.15.tar.xz
Installing Python-3.9.15...
WARNING: The Python lzma extension was not compiled. Missing the lzma lib?
Installed Python-3.9.15 to /home/dev-user/.pyenv/versions/3.9.15

実行するPythonをPython3.9に設定する。

現在のPythonバージョンを確認
$ pyenv versions
* system (set by /home/dev-user/.pyenv/version)
  3.9.15
$ python -V
Python 2.7.5

バージョンを切り替え
$ pyenv global 3.9.15

切り替え後のPythonバージョンを確認
$ pyenv versions
  system
* 3.9.15 (set by /home/dev-user/.pyenv/version)
$ python -V
Python 3.9.15

gcloud CLIをインストールする。

gcloud CLIパッケージをダウンロード
$ curl -O https://dl.google.com/dl/cloudsdk/channels/rapid/downloads/google-cloud-cli-404.0.0-linux-x86_64.tar.gz

展開する
$ tar -xf google-cloud-cli-404.0.0-linux-x86_64.tar.gz

gcloud CLIのPATHを設定
$ ./google-cloud-sdk/install.sh \
  --usage-reporting false \
  --rc-path ~/.bashrc \
  --command-completion true \
  --path-update true

設定を確認
$ tail -n 5  ~/.bashrc
# The next line updates PATH for the Google Cloud SDK.
if [ -f '/home/dev-user/google-cloud-sdk/path.bash.inc' ]; then . '/home/dev-user/google-cloud-sdk/path.bash.inc'; fi

# The next line enables shell command completion for gcloud.
if [ -f '/home/dev-user/google-cloud-sdk/completion.bash.inc' ]; then . '/home/dev-user/google-cloud-sdk/completion.bash.inc'; fi

設定変更を反映
$ source ~/.bashrc

インストールされたgcloud CLIを確認
$ gcloud --version
Google Cloud SDK 404.0.0
bq 2.0.78
bundled-python3-unix 3.9.12
core 2022.09.23
gcloud-crc32c 1.0.0
gsutil 5.14

※install.sh実行時のオプションの意味は以下。

  • --usage-reporting:gcloud CLI の改善のために匿名の使用統計情報を送信するかどうか。
  • --rc-path:更新するプロファイルの場所
  • --command-completion:コマンド補完を有効にするかどうか。
  • --path-update:プロファイルのPATHを更新するかどうか。

※最初からインストールされていたgcloud CLIのプロパティが残っているので、初期化(gcloud init)は実行しなかった。

 

これで、gcloud CLIコンポーネントのインストールやアップデートが出来るようになる。

gcloud CLIでkubectlをインストールしてみる
$ gcloud components install kubectl

インストールできた
$ kubectl version
Client Version: version.Info{Major:"1", Minor:"22+", GitVersion:"v1.22.14-dispatcher-dirty", GitCommit:"009f3ac5f1d09b1ec5d4dc811b6032271fe61f75", GitTreeState:"dirty", BuildDate:"2022-09-19T01:31:36Z", GoVersion:"go1.16.15", Compiler:"gc", Platform:"linux/amd64"}
The connection to the server localhost:8080 was refused - did you specify the right host or port?

gcloud CLIでコンポーネントをアップデートする
$ gcloud components update

おまけ:インスタンスの初期設定

検証用途なので、検証の邪魔になりがちなOSファイアウォールSELinuxは停止・無効化しておく。

OSファイアウォールを無効化する。

$ sudo systemctl stop firewalld

$ sudo systemctl disable firewalld
Removed symlink /etc/systemd/system/multi-user.target.wants/firewalld.service.
Removed symlink /etc/systemd/system/dbus-org.fedoraproject.FirewallD1.service.

$ sudo systemctl status firewalld
● firewalld.service - firewalld - dynamic firewall daemon
   Loaded: loaded (/usr/lib/systemd/system/firewalld.service; disabled; vendor preset: enabled)
   Active: inactive (dead)
     Docs: man:firewalld(1)

$ sudo systemctl is-enabled firewalld
disabled

SELinuxを無効化する

$ getenforce
Enforcing

$ sudo sed -i".org" -e "s/^SELINUX=enforcing$/SELINUX=disabled/g" /etc/selinux/config

$ sudo reboot

$ getenforce
Disabled

参考文献

pyenv
Amazon Linux 2環境上にGCPコマンドラインツール・Google Cloud SDK動作環境を整える
SELinux無効化一行コマンド