donte1234567 2017-12-26 18:42
浏览 57
已采纳

Golang Iris:将父控制器的模型初始化为子控制器的模型

I understand that Go is not an object-oriented language but I'm trying to implement a inheritance structure in my Iris controllers as suggested by this article. My main motivation for doing so is to avoid repetition. So far, it has been working for me. Take a look at the following code for example.

// APIController.go (package Controllers)
type APIController struct {
    mvc.C
}
func (c *APIController) Post(data map[string][]string) ([]byte, error) {
    data_parsed := c.ParseFormData(data)
    return json.Marshal(data_parsed)
}

// UserController.go  (package Controllers)
type UserController struct {
    mvc.C
    *APIController
}

func (c *UserController) Post() ([]byte, error) {
    return c.APIController.Post(c.Ctx.FormValues())
}

So far so good.

But I'm finding it difficult to replicate the same strategy for Models. This is what I've done so far

// Model.go (package Models)
type Model struct {
    Id         string `json:"_id"`
    Created_at string `json:"created_at"`
    Updated_at string `json:"updated_at"`
    Deleted_at string `json:"deleted_at"`
}
// implements further set of functions to be used by 'child' models...

// User.go (package Models)
type User struct {
    *Model

    First_name string `json:"first_name"`
    Last_name  string `json:"last_name"`
    Email      string `json:"email"`
    Username   string `json:"username"`
    Password   string `json:"password"`
    Last_login string `json:"last_login"`
}


// APIController.go (package Controllers)
type APIController struct {
    mvc.C
    Model Models.Model
}

// UserController.go  (package Controllers)
type UserController struct {
    mvc.C
    *APIController
}

func (c *UserController) Post() ([]byte, error) {
    c.APIController.Model = new(Models.User) //WRONG!
    return c.APIController.Post(c.Ctx.FormValues())
}

As you can see, the APIController is expecting type Models.Model while UserController is passing *Models.User. The end goal is to have a generic model in APIController that any model from any controller and then is able to call all the functions defined in Models.Model so that I don't have to call those function everywhere.

Is it possible to do so? If not, what might be the best approach to avoid repeating the code?

Update

By using inheritance and single parent model and using that in parent APIController, I want to avoid replicating my filter/CRUD logic. For example, inside UserController, if I want to save a record, then instead of using User.Save(input_data) inside UserController, the Save should ideally be defined inside Models.Model and from APIController, I'm able to call Model.Save(input_data) rather than making the same call from child controllers individually.

  • 写回答

1条回答 默认 最新

  • duanqu9279 2017-12-27 10:09
    关注

    First make Model an interface instead of a struct. Have it contain all methods that should be common to all models:

    type Model interface {
        // Common methods
    }
    

    Then, as long as User implements all those methods, you can have

    c.APIController.Model = new(Models.User) // Now works!
    

    One of the common methods could be Save. Otherwise make Save a non-method:

    func Save(m Model) error {
        ...
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 基于卷积神经网络的声纹识别
  • ¥15 Python中的request,如何使用ssr节点,通过代理requests网页。本人在泰国,需要用大陆ip才能玩网页游戏,合法合规。
  • ¥100 为什么这个恒流源电路不能恒流?
  • ¥15 有偿求跨组件数据流路径图
  • ¥15 写一个方法checkPerson,入参实体类Person,出参布尔值
  • ¥15 我想咨询一下路面纹理三维点云数据处理的一些问题,上传的坐标文件里是怎么对无序点进行编号的,以及xy坐标在处理的时候是进行整体模型分片处理的吗
  • ¥15 CSAPPattacklab
  • ¥15 一直显示正在等待HID—ISP
  • ¥15 Python turtle 画图
  • ¥15 stm32开发clion时遇到的编译问题