2
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

GORMでマイグレーションする際の覚書

Last updated at Posted at 2020-10-19

はじめに

structでモデル定義、AutoMigrateでマイグレーションを実行、といった辺りで少し調べた部分をメモしておきます。

IDにUUIDを使用するには

UUIDの自動生成をライブラリに任せつつ、テストやシードデータの投入時には固定のUUIDも指定できるようにしたかったため、以下のように対応しました。

まずはstructでのモデルの定義

package model

import (
	"github.com/go-playground/validator/v10"
	"github.com/google/uuid"
)

type User struct {
  ID string `validate:"is_valid_uuid" gorm:"primaryKey;size:255;default:uuid_generate_v4()" json:"id"`
  ...
}

// IDが渡ってこなければバリデーションをかけず、渡ってきたらUUIDかを確認
validate := validator.New()
validate.RegisterValidation("is_valid_uuid", isValidUUID)

func isValidUUID(fl v.FieldLevel) bool {
	id := fl.Field().String()
	if len(id) == 0 {
		return true
	}
	_, err := uuid.Parse(id)
	return err == nil
}

上記uuid_generate_v4()を利用するために、AutoMigrate(&User{}) する前にpostgresに拡張機能 uuid-ossp をインストール

db, err = gorm.Open("postgres", fmt.Sprintf(
  "host=%s port=%s user=%s password=%s dbname=%s", host, port, user, password, dbname,
))

if err != nil {
  panic(err)
}

db.Exec(`CREATE EXTENSION IF NOT EXISTS "uuid-ossp";`)

result := db.AutoMigrate(&model.User{})
...

Postgresのenum型を使用するには

structのタグで型を指定

type User struct {
  Role string `validate:"is_valid_role" gorm:"type:role_enum;default:'user'" json:"role"`
  ...
}

AutoMigrateする前にpostgresに型の定義を追加

db.Exec(`
DO
$$
BEGIN
  IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'role_enum') THEN
    create type role_enum AS ENUM ('admin', 'editor', 'user');
  END IF;
END
$$;
`)

result := db.AutoMigrate(&model.User{})
...

まとめ

GORMのマイグレーションまわりに関してのメモでした。また他にあれば追記していきます。

2
0
0

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
2
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?