grails - 具有2列和查询的自定义userType

时间:2013-10-01 11:37:01

标签: sql hibernate grails

假设我有一个表示坐标(lat和long)的POJO和表示地点的域类。地方有一个坐标。

Coordinate.groovy

class Coordinate implements Serializable{
    float latitude
    float longitude
    ...
}

CoordinateUserType.groovy

class CoordinateUserType implements UserType{

    int[] sqlTypes() { [Types.FLOAT, Types.FLOAT]}

    public Object nullSafeGet(rs, names, owner){
        /*not full code published, just what is relevant*/
        return new Coordinate(rs.getFloat(names[0]), rs.getFloat(names[1]))
    }
    public Object nullSafeSet(st, object, index){
        /*not full code published, just what is relevant*/
        st.setFloat(index, value.latitude)
        st.setFloat(index+1, value.longitude)
    }


}

Place.groovy

class Place{
    ...
    Coordinate coordinate
    ...
    static mapping = {
        coordinate type:CoordinateUserType, {
            column name:'latitude'
            column name:'longitude'
        }
    }

}

我为坐标(2列)创建了一个userType,并在地点域类的映射中引用它。

我可以正确创建和列出地点。

但是我想根据它们的坐标查询这些地方,比如

在哪里:

def matchingPlaces = Place.where{
    coordinate.latitude > 0 && coordinate.latitude < 10 &&
    coordinate.longitude > 0 && coordinate.longitude < 10
}

标准:

def matchingPlaces = Place.createCriteria().list{
    and{
        between('coordinate.latitude', 0,10)
        between('coordinate.longitude', 0,10)
    }
}
/*or */
def matchingPlaces = Place.createCriteria().list{
    coordinate{
        and{
            between('latitude', 0,10)
            between('longitude', 0,10)
        }
    }
}

但无论我在闭包之间的列名中输入什么,我总是会收到错误“无法解析属性”。

查询具有多列的自定义用户类型的步骤是什么?

提前致谢

2 个答案:

答案 0 :(得分:2)

只需在embed中使用Place

static embedded = ['coordinate']

您不需要自定义映射,也可以删除CoordinateUserType

以下内容将起作用:

def matchingPlaces = Place.createCriteria().list{
    coordinate{
        and{
            between('latitude', 0,10)
            between('longitude', 0,10)
        }
    }
}

答案 1 :(得分:0)

假设您的域名如下:

class Place {
    ...
    Coordinate coordinate
    ...
}

您可以在条件中访问此嵌套域,如下所示:

coordinate{
    and {
        between('latitude', 0, 10)
        between('longitude', 0, 10)
    }
}

未经测试但应该有效......