MyBatis 和 Sybase 存储过程 - 具有未命名列的结果集

MyBatis and Sybase Stored Procedure - ResultSet with unnamed columns

我正在尝试使用 MyBatis 映射 Sybase 存储过程的结果集,但我遇到了一些关于未命名列的问题。 该过程 returns 单行 4 列,其中 2 列根本没有名称:

+---id---|------|-----------|---description---+
     1     name1  surname1        desc1

resultmap .xml 文件如下所示(检查第二个和第三个结果标签):

<resultMap id="person" type="foo.Person">
    <result column="id" property="id"/>
    <result column="" property="name"/>
    <result column="" property="surname"/>
    <result column="description" property="description"/>
</resultMap>

我无法控制存储过程代码,因此不可能向未命名的列添加别名。 查看之前版本的MyBatis,看到以前可以在ResultMap中通知一个columnIndex,现在好像没有了。 是否有某种可用于此的自定义 ResultSet 处理程序?或者可能是某种定制的 TypeHandler?

这是一种解决方法,但由于您无法更改数据库中的过程来添加名称,所以我想不出其他方法。

我们的想法是创建一个特定于这些字段的类型处理程序。请注意,如果您有一个未命名的字段,您可以使用空列名称简单地映射它。

因此在您的情况下,结果图将如下所示:

<resultMap id="person" type="foo.Person">
    <result column="id" property="id"/>
    <result column="" property="name" typeHandler="foo.PersonNameTypeHandler"/>
    <result column="" property="surname"  typeHandler="foo.PersonSurnameTypeHandler"/>
    <result column="description" property="description"/>
</resultMap>

sybase 驱动程序将return所有未命名的列作为“”。

MyBatis 要求您将列映射到现有的列名,否则它不会调用类型处理程序。因为你不能为这些列创建假名,所以对所有未命名的列都使用空名,如果重要的话最后使用空名只是为了强制 MyBatis 处理该列。

重要的部分在类型处理程序中,它只是 return 基于列号的值,其中 "name" 应该是:

public class PersonNameTypeHandler extends BaseTypeHandler<String> {
    ...
    @Override
    public String getNullableResult(ResultSet rs, String columnName) {
        return rs.getString(2);
    }
    ...
}

重要的是要注意被调用的方法传递了 columnName,在这种情况下它是空的,所以忽略它并 return 按列索引。

此外,ResultSet 列索引从 1 开始,因此在这种情况下,要获取姓名,您将获得 2,对于姓氏,实现方式为:

...
return rs.getString(3);
...

另一个重要的细节是列顺序必须与您的过程中定义的 return 顺序相关,而不是在您的结果映射中。如果 "name" 列在上面结果映射中的 "description" 列之后,但是过程 return 没有改变,getString 中使用的索引仍然是 2,而不是 4。

希望对您有所帮助。