代码之家  ›  专栏  ›  技术社区  ›  Rob Hruska MegalomanINA

在Bootstrap.groovy中设置Grails域id

  •  3
  • Rob Hruska MegalomanINA  · 技术社区  · 16 年前

    是否可以在Grails的Bootstrap.groovy(或任何地方)中显式设置域对象的id?

    new Foo(id: 1234, name: "My Foo").save()
    

    以及:

    def foo = new Foo()
    foo.id = 1234
    foo.name = "My Foo"
    foo.save()
    

    但在这两种情况下,当我打印出 Foo.list() 在运行时,我看到我的对象的id为1,或者序列中的下一个id是什么。

    chanwit提供了 one good solution below . 然而,我实际上是在寻找一种在不改变域的id生成方法的情况下设置id的方法。这主要是用于测试:我希望能够在测试引导或测试中将某些内容设置为已知的id值 setUp()

    3 回复  |  直到 7 年前
        1
  •  10
  •   chanwit    16 年前

    是,使用手动GORM映射:

    class Foo {
      String name
      static mapping = {
        id generator:'assigned'
      }
    }
    

    您的第二个代码段(不是第一个)将完成这项工作(当通过构造函数传递它时,不会分配Id)。

        2
  •  1
  •   Rob Hruska MegalomanINA    15 年前

    我最终使用的解决方法是不尝试通过对象的id检索对象。因此,对于问题中给出的示例,我更改了我的域对象:

    class Foo {
      short code /* new field */
      String name
    
      static constraints = {
        code(unique: true)
        name()
      }
    }
    

    然后我用了一个 enum 保存代码的所有可能值(静态),并将检索 Foo 通过执行 Foo.findByCode() Foo.get() 和我之前想做的一样)。

        3
  •  1
  •   Volt0    13 年前

    或者,假设您正在导入数据 或从现有应用程序迁移数据 ,出于测试目的,您可以在引导文件中使用本地映射。将其视为具有优点的import.sql;-)

    使用这种方法:

    1. 您不需要仅仅为了一个目的而更改域约束 测试,
    2. 您将拥有来自现有数据的经过测试的迁移路径,并且

    干杯

    def init = { servletContext ->
    
        addFoos()
        addBars()
    
    }
    
    def foosByImportId = [:]
    private addFoos(){
        def pattern = ~/.*\{FooID=(.*), FooCode=(.*), FooName=(.*)}/
        new File("import/Foos.txt").eachLine {
            def matcher = pattern.matcher(it)
            if (!matcher.matches()){
                return;
            }
    
            String fooId = StringUtils.trimToNull(matcher.group(1))
            String fooCode = StringUtils.trimToNull(matcher.group(2))
            String fooName = StringUtils.trimToNull(matcher.group(3))
    
            def foo = Foo.findByFooName(fooName) ?: new Foo(fooCode:fooCode,fooName:fooName).save(faileOnError:true)
            foosByImportId.putAt(Long.valueOf(fooId), foo) // ids could differ
        }
    }
    
    private addBars(){
        ...
        String fooId = StringUtils.trimToNull(matcher.group(5))
        def foo = foosByImportId[Long.valueOf(fooId)]
        ...
    }
    
    推荐文章