Spring的NamedParameterJdbcTemplate

使用 NamedParameterJdbcTemplate

NamedParameterJdbcTemplate类增加了对使用命名参数编程 JDBC 语句的支持,这与仅使用经典占位符('?')参数进行编程的 JDBC 相反。 NamedParameterJdbcTemplate类包装JdbcTemplate并委托包装的JdbcTemplate完成其许多工作。本节仅描述NamedParameterJdbcTemplate类的与JdbcTemplate本身不同的区域,即使用命名参数对 JDBC 语句进行编程。以下示例显示了如何使用NamedParameterJdbcTemplate

// some JDBC-backed DAO class...
private NamedParameterJdbcTemplate namedParameterJdbcTemplate;

public void setDataSource(DataSource dataSource) {
    this.namedParameterJdbcTemplate = new NamedParameterJdbcTemplate(dataSource);
}

public int countOfActorsByFirstName(String firstName) {

    String sql = "select count(*) from T_ACTOR where first_name = :first_name";

    SqlParameterSource namedParameters = new MapSqlParameterSource("first_name", firstName);

    return this.namedParameterJdbcTemplate.queryForObject(sql, namedParameters, Integer.class);
}

请注意,在分配给sql变量的值和插入namedParameters变量(类型MapSqlParameterSource)的相应值中使用了命名参数符号。

或者,您可以使用基于Map的样式将命名参数及其对应的值传递给NamedParameterJdbcTemplate实例。NamedParameterJdbcOperations公开并由NamedParameterJdbcTemplate类实现的其余方法遵循类似的模式,此处不再赘述。

下面的示例说明基于Map的样式的用法:

// some JDBC-backed DAO class...
private NamedParameterJdbcTemplate namedParameterJdbcTemplate;

public void setDataSource(DataSource dataSource) {
    this.namedParameterJdbcTemplate = new NamedParameterJdbcTemplate(dataSource);
}

public int countOfActorsByFirstName(String firstName) {

    String sql = "select count(*) from T_ACTOR where first_name = :first_name";

    Map<String, String> namedParameters = Collections.singletonMap("first_name", firstName);

    return this.namedParameterJdbcTemplate.queryForObject(sql, namedParameters,  Integer.class);
}

NamedParameterJdbcTemplate相关联(并且存在于同一 Java 包中)的一项不错的功能是SqlParameterSource接口。您已经在以前的代码片段之一(MapSqlParameterSource类)中看到了此接口的实现示例。 SqlParameterSourceNamedParameterJdbcTemplate的命名参数值的来源。 MapSqlParameterSource类是一个简单的实现,它是围绕java.util.Map的适配器,其中键是参数名称,值是参数值。

另一个SqlParameterSource实现是BeanPropertySqlParameterSource类。此类包装任意 JavaBean(即,遵循JavaBean 约定的类的实例),并使用包装的 JavaBean 的属性作为命名参数值的源。

以下示例显示了典型的 JavaBean:

public class Actor {

    private Long id;
    private String firstName;
    private String lastName;

    public String getFirstName() {
        return this.firstName;
    }

    public String getLastName() {
        return this.lastName;
    }

    public Long getId() {
        return this.id;
    }

    // setters omitted...

}

下面的示例使用NamedParameterJdbcTemplate返回上一示例中显示的类的成员数:

// some JDBC-backed DAO class...
private NamedParameterJdbcTemplate namedParameterJdbcTemplate;

public void setDataSource(DataSource dataSource) {
    this.namedParameterJdbcTemplate = new NamedParameterJdbcTemplate(dataSource);
}

public int countOfActors(Actor exampleActor) {

    // notice how the named parameters match the properties of the above 'Actor' class
    String sql = "select count(*) from T_ACTOR where first_name = :firstName and last_name = :lastName";

    SqlParameterSource namedParameters = new BeanPropertySqlParameterSource(exampleActor);

    return this.namedParameterJdbcTemplate.queryForObject(sql, namedParameters, Integer.class);
}

请记住,NamedParameterJdbcTemplate类包装了经典的JdbcTemplate模板。如果需要访问包装的JdbcTemplate实例以访问仅在JdbcTemplate类中提供的功能,则可以使用getJdbcOperations()方法通过JdbcOperations接口访问包装的JdbcTemplate

示例代码

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = SpringConfiguration.class)
public class SpringNamedParameterJdbcTemplateTest {

    @Autowired
    private NamedParameterJdbcTemplate jdbcTemplate;

    @Test
    public void testFind(){
        Map<String,Object> map = new HashMap<>();
        map.put("id",1);
        Account account = jdbcTemplate.queryForObject("select * from account where id = :id",map,new BeanPropertyRowMapper<Account>(Account.class));
        System.out.println(account);
    }


    @Test
    public void testSave(){
        Account account = new Account();
        account.setName("NamedParameterJdbcTemplate");
        account.setMoney(12345d);
        BeanMap beanMap = BeanMap.create(account);
        jdbcTemplate.update("insert into account(name,money)values(:name,:money)",beanMap);
    }
}

posted @ 2020-09-24 14:33  天宇轩-王  阅读(446)  评论(0编辑  收藏  举报