【问题标题】:Grails addTo* slowly performance with eventGrails addTo* 在事件中表现缓慢
【发布时间】:2015-09-29 09:03:10
【问题描述】:

在我的 Grails 应用程序中,我非常兴奋地使用了一些技术,但最近我遇到了一些性能问题,我将描述我的场景:

  • 一张桌子有 400 万多个整体;
  • 我正在使用事件总线 API;
  • Grails 2.2.3;
  • MySQL 数据库;

当客户端创建新房间时,也会创建一些 Alloc。

pseudo-code:
    Room {
      hasMany = aloccs: Alloc
    }

看这段代码(不是真正的代码,但具有相同的相等性):

@Listener(topic="topicAlocCreator")
def alocCreator(EventMessage<Long> message) {

    LocalDate start = new DateTime().toLocalDate()
    LocalDate end = new DateTime().plusYears(2).plusMonths(6).toLocalDate()
    LocalDate tmp = start


    Room room = Room.get(message.data)
    List channels = Channel.list
    while(tmp.compareTo(end) <= 0) {
        for(channel in channels) {
            room.addToAlocs(new Aloc(0, 0, tmp.toDate(), channel))
        }
        tmp = tmp.plusDays(1)
    }

    //end of method
}

这段代码运行良好,但它生成了很多 alloc 对象并将其置于休眠会话中。

使用flush完成这项工作的正确方法是什么?批? - 对方法的调用是异步的。

这段代码在 (07/14) 之前都可以正常工作,但在这几天里它非常慢,在数据库中插入 10K 的 alloc 大约需要 1.30 分钟;

非常感谢您的建议。

【问题讨论】:

    标签: mysql hibernate grails


    【解决方案1】:

    因为allocsSet(定义hasMany 关系时的默认Grails 集合类型),Grails 必须在插入发生之前将整个集合加载到内存中以保证唯一性。

    看看 Bert Beckwith 的 presentation 关于使用 GORM 集合的性能影响。

    我认为您有几个选择。您可以完全放弃集合引用,只需像这样定义您的类:

    class Alloc {
        Room room
    }
    
    class Room {
        //no reference child Allocs
    }
    

    或者,您可以将您的 allocs 集合定义为一个包:

    class Alloc {
        static belongsTo = [room: Room]
    }
    
    class Room {
        Collection allocs
        static hasMany = [allocs: Alloc]
    }
    

    在这种情况下,不需要唯一性检查,addTo... 方法不需要将每个Alloc 实例加载到内存中。但是,您将负责自己保持独特性...

    Reference

    【讨论】:

    • 我正在使用de List,并且hibernate在我的数据库中创建了一个alloc_idx,那么使用Collection更具性能?
    • 肯定不会更好(无论集合类型如何,整个集合都不必要地从数据库中加载),实际上可能更糟。使用 Set 只能保证唯一性,因此 Hibernate 会检测 Set 中添加和删除的实例并进行相应的单个数据库更新。该附加列用于跟踪列表中的顺序,如果您打开 SQL 日志记录,您将看到 Hibernate 将删除所有实例并在顺序更改时重新插入它们,而不是更新 idx 列。
    • 事实证明,使用 Bags 并不能解决问题,并且可以使事情正常进行 - 我在 this blog post 中写了一些发现
    • 感谢@BurtBeckwith 和@rcgeorge23。
    • 抱歉,之前评论中的错字,应该是“can make things worse
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-08
    相关资源
    最近更新 更多