LoginSignup
5
2

More than 1 year has passed since last update.

Cloud SQLの自動起動停止

Last updated at Posted at 2021-09-05

概要

Cloud SQLは、インスタンスを継続的に実行するとコストが非常に高い。
そのため、開発環境など24時間稼働する必要のないインスタンスは、必要な時以外インスタンスを停止していくことがベストである。
しかし、「起動停止を毎回しないといけない」+「起動に時間がかかる」で効率が悪い。
したがって、以下のGoogleの公式ブログを参考にCloud SQLの起動停止を自動化してみた。

全体像

スケジューリングの役割をなすのが、Cloud Scheduler
Cloud SQLインスタンスを起動停止させるのが、Cloud Functions
Cloud SchedulerからCloud Functionsへの通知の役割をするのが、Cloud Pub/Sub

Screen Shot 2021-09-05 at 13.27.58.png

ステップは3つある。

  1. Cloud SQLインスタンスの作成(本記事では省略)
  2. Cloud SQL インスタンスを起動、停止させる Cloud Functions の関数を作成する
  3. Cloud Functions の関数をトリガーする Cloud Scheduler ジョブを作成する

Cloud Functionsの作成

まず、以下のようにCloud Functionsを設定して「次へ」をクリック
Screen Shot 2021-09-05 at 13.59.15.png

次に、以下のようにランタイムとエントリポイントを設定し、function.goにてコードを作成する。
Screen Shot 2021-09-05 at 13.56.00.png

function.go
// Package p には、Pub/Sub Cloud Function を含む
package p

import (
    "context"
    "encoding/json"
    "log"

    "golang.org/x/oauth2/google"
    sqladmin "google.golang.org/api/sqladmin/v1beta4"
)

// PubSubMessage は、Pub/Sub eventのペイロード
type PubSubMessage struct {
    Data []byte `json:"data"`
}

type MessagePayload struct {
    Instance string // Cloud SQL のインスタンス名
    Project  string // プロジェクトID
    Action   string // 起動か停止か
}

// Pub/Sub message を受け取って処理
func ProcessPubSub(ctx context.Context, m PubSubMessage) error {
    var psData MessagePayload
    // PubSubMessageのjsonデータをMessagePayloadオブジェクトに変換する
    err := json.Unmarshal(m.Data, &psData)
    if err != nil {
        log.Println(err)
    }
    log.Printf("Request received for Cloud SQL instance %s action: %s, %s", psData.Action, psData.Instance, psData.Project)

    // デフォルトの認証情報を使って、http.Cllientを作成
    hc, err := google.DefaultClient(ctx, sqladmin.CloudPlatformScope)
    if err != nil {
        return err
    }

    // Cloud SQL service を作成
    service, err := sqladmin.New(hc)
    if err != nil {
        return err
    }

    // 起動と停止のアクションのリクエストを読み取る
    action := "UNDEFINED"
    switch psData.Action {
    case "start":
        action = "ALWAYS"
    case "stop":
        action = "NEVER"
    default:
        log.Fatal("No valid action provided.")
    }

    // 読み取ったアクションをCloud SQLに設定する準備をする
    rb := &sqladmin.DatabaseInstance{
        Settings: &sqladmin.Settings{
            ActivationPolicy: action,
        },
    }
    // CloudSQLインスタンス内のデータベースに関する情報を含むリソースを部分的に更新
    resp, err := service.Instances.Patch(psData.Project, psData.Instance, rb).Context(ctx).Do()
    if err != nil {
        log.Fatal(err)
    }
    log.Printf("%#v\n", resp)
    return nil
} 

最後に、Cloud Functions の関数に Cloud SQL インスタンスを起動または停止する権限を付与します。
Cloud Console の IAM セクションに移動し、Cloud Functions で使用される「App Engine デフォルト サービス アカウント」を見つけます。このサービス アカウントのサフィックスは「@appspot.gserviceaccount.com」です。
そして、[Cloud SQL 管理者] ロールを追加します。

Cloud Scheduler ジョブの作成

以下のようにCloud Scheduler を設定し、「作成」をクリック。
Screen Shot 2021-10-26 at 8.45.59.png

ジョブの「頻度」は、「平日の朝9時」に実行する記述である。
Pub/Subの「メッセージ本文」は、Cloud Functionsの関数に必要な情報を記述する。

同様に、停止のジョブも作成する。
※停止の場合は、Pub/Subのメッセージ本文の"Action"をstopに変更すること。

参照

5
2
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
2