Delete unused columns with Auto Migration

Viewed 409

I've started working with fantastic library GORM for Go. Auto Migration works perfectly, but in documentation I read the note "It WON’T delete unused columns to protect your data."

Can I skip this rule? In other words, can I add/change something in gorm config in order to have opportunity to delete an unused columns with Auto Migration?

2 Answers

No, I don't think there's an easy option to do this.

Here's the AutoMigrate source: https://github.com/go-gorm/gorm/blob/59730417aabd5b510d66d9d923d265a6fc0195a0/migrator/migrator.go#L83-L153

You would need to enumerate all columns on the table, check that they exist, and delete them.

You would also need to enumerate existing relationships and indexes and delete as necessary if they didn't exist.

If you did end up writing that, I think you could write your own AutoMigrate function that takes a gorm.Migrator interface and runs the automigrate. You can get the Migrator interface in your existing code with db.Migrator() and pass it to your function. Maybe someone has written a function like this somewhere!

You can write a function like this:

func DropUnusedColumns(dst interface{}) {

    stmt := &gorm.Statement{DB: DB}
    stmt.Parse(dst)
    fields := stmt.Schema.Fields
    columns, _ := DB.Debug().Migrator().ColumnTypes(dst)

    for i := range columns {
        found := false
        for j := range fields {
            if columns[i].Name() == fields[j].DBName {
                found = true
                break
            }
        }
        if !found {
            DB.Migrator().DropColumn(dst, columns[i].Name())
        }
    }
}

usage:

DropUnusedColumns(&User{})
Related