レコードを作成する
user := User{Name: "Jinzhu", Age: 18, Birthday: time.Now()} |
Create()
を使用して複数のレコードを作成することもできます:
users := []*User{ |
注意 **Create()**の引数として構造体を渡すことはできません。代わりにポインタを渡すようにしてください。
フィールドを選択してレコードを作成する
レコード作成時に、Selectで指定されたフィールドのみに対して値をアサインできます。
db.Select("Name", "Age", "CreatedAt").Create(&user) |
省略する項目を指定し、レコードを作成します。
db.Omit("Name", "Age", "CreatedAt").Create(&user) |
一括作成
大量のレコードを効率的に挿入するには、スライスを Create
メソッドに渡します。 GORMはすべてのデータを挿入する1つのSQL文を生成します。SQLが実行されると登録された主キーの値がモデルに代入され、フックメソッドも呼び出されます。 レコードを複数のバッチに分割することが可能な場合には、 トランザクション が開始されます。
var users = []User{{Name: "jinzhu1"}, {Name: "jinzhu2"}, {Name: "jinzhu3"}} |
CreateInBatches
を利用することで、バッチサイズを指定してレコードを作成することができます。
var users = []User{{Name: "jinzhu_1"}, ...., {Name: "jinzhu_10000"}} |
Upsert や Create With Associations を使用する場合もバッチインサートはサポートされています。
注記
CreateBatchSize
オプションを使ってGORMを初期化した場合、すべてのINSERT
は、その設定を参照してレコードやアソシエーションを作成します。
db, err := gorm.Open(sqlite.Open("gorm.db"), &gorm.Config{ |
作成時のHook
GORM allows user defined hooks to be implemented for BeforeSave
, BeforeCreate
, AfterSave
, AfterCreate
. These hook method will be called when creating a record, refer Hooks for details on the lifecycle
func (u *User) BeforeCreate(tx *gorm.DB) (err error) { |
If you want to skip Hooks
methods, you can use the SkipHooks
session mode, for example:
DB.Session(&gorm.Session{SkipHooks: true}).Create(&user) |
Mapを使って作成する
GORM supports create from map[string]interface{}
and []map[string]interface{}{}
, e.g:
db.Model(&User{}).Create(map[string]interface{}{ |
NOTE When creating from map, hooks won’t be invoked, associations won’t be saved and primary key values won’t be back filled
SQL式/Context Valuer で作成する
GORM allows insert data with SQL expression, there are two ways to achieve this goal, create from map[string]interface{}
or Customized Data Types, for example:
// Create from map |
高度な機能
関連データと関連付けて作成する
When creating some data with associations, if its associations value is not zero-value, those associations will be upserted, and its Hooks
methods will be invoked.
type CreditCard struct { |
You can skip saving associations with Select
, Omit
, for example:
db.Omit("CreditCard").Create(&user) |
デフォルト値
You can define default values for fields with tag default
, for example:
type User struct { |
Then the default value will be used when inserting into the database for zero-value fields
NOTE Any zero value like
0
,''
,false
won’t be saved into the database for those fields defined default value, you might want to use pointer type or Scanner/Valuer to avoid this, for example:
type User struct { |
NOTE You have to setup the
default
tag for fields having default or virtual/generated value in database, if you want to skip a default value definition when migrating, you could usedefault:(-)
, for example:
type User struct { |
NOTE SQLite doesn’t support some records are default values when batch insert. See SQLite Insert stmt. For example:
type Pet struct {
Name string `gorm:"default:cat"`
}
// In SQLite, this is not supported, so GORM will build a wrong SQL to raise error:
// INSERT INTO `pets` (`name`) VALUES ("dog"),(DEFAULT) RETURNING `name`
db.Create(&[]Pet{{Name: "dog"}, {}})A viable alternative is to assign default value to fields in the hook, e.g.
func (p *Pet) BeforeCreate(tx *gorm.DB) (err error) {
if p.Name == "" {
p.Name = "cat"
}
}You can see more info in issues#6335
When using virtual/generated value, you might need to disable its creating/updating permission, check out Field-Level Permission
コンフリクト発生時のUpsert
GORM provides compatible Upsert support for different databases
import "gorm.io/gorm/clause" |
Also checkout FirstOrInit
, FirstOrCreate
on Advanced Query
Checkout Raw SQL and SQL Builder for more details