当前位置: 代码网 > it编程>编程语言>Java > Java MySQL动态语句编写实现方式

Java MySQL动态语句编写实现方式

2025年04月28日 Java 我要评论
在java后端开发中,动态sql语句的构建是非常常见的需求,特别是在处理复杂查询条件时。以下是几种常用的实现方式:1. 使用jdbc动态拼接sql这是最基础的方式,但容易导致sql注入风险,不推荐在生

在java后端开发中,动态sql语句的构建是非常常见的需求,特别是在处理复杂查询条件时。以下是几种常用的实现方式:

1. 使用jdbc动态拼接sql

这是最基础的方式,但容易导致sql注入风险,不推荐在生产环境使用。

public list<user> findusers(string name, integer age, string email) {
    connection conn = null;
    preparedstatement stmt = null;
    resultset rs = null;
    list<user> users = new arraylist<>();
    try {
        conn = datasource.getconnection();
        // 基础sql
        stringbuilder sql = new stringbuilder("select * from users where 1=1");
        // 动态添加条件
        list<object> params = new arraylist<>();
        if (name != null) {
            sql.append(" and name = ?");
            params.add(name);
        }
        if (age != null) {
            sql.append(" and age = ?");
            params.add(age);
        }
        if (email != null) {
            sql.append(" and email like ?");
            params.add("%" + email + "%");
        }
        stmt = conn.preparestatement(sql.tostring());
        // 设置参数
        for (int i = 0; i < params.size(); i++) {
            stmt.setobject(i + 1, params.get(i));
        }
        rs = stmt.executequery();
        while (rs.next()) {
            user user = new user();
            user.setid(rs.getint("id"));
            user.setname(rs.getstring("name"));
            user.setage(rs.getint("age"));
            user.setemail(rs.getstring("email"));
            users.add(user);
        }
    } catch (sqlexception e) {
        e.printstacktrace();
    } finally {
        // 关闭资源
    }
    return users;
}

2. 使用jpa criteria api

jpa提供了类型安全的动态查询构建方式:

public list<user> findusers(string name, integer age, string email) {
    criteriabuilder cb = entitymanager.getcriteriabuilder();
    criteriaquery<user> query = cb.createquery(user.class);
    root<user> root = query.from(user.class);
    list<predicate> predicates = new arraylist<>();
    if (name != null) {
        predicates.add(cb.equal(root.get("name"), name));
    }
    if (age != null) {
        predicates.add(cb.equal(root.get("age"), age));
    }
    if (email != null) {
        predicates.add(cb.like(root.get("email"), "%" + email + "%"));
    }
    query.where(predicates.toarray(new predicate[0]));
    return entitymanager.createquery(query).getresultlist();
}

3. 使用spring data jpa的specification

spring data jpa提供了更简洁的specification方式:

public list<user> findusers(string name, integer age, string email) {
    return userrepository.findall((root, query, cb) -> {
        list<predicate> predicates = new arraylist<>();
        if (name != null) {
            predicates.add(cb.equal(root.get("name"), name));
        }
        if (age != null) {
            predicates.add(cb.equal(root.get("age"), age));
        }
        if (email != null) {
            predicates.add(cb.like(root.get("email"), "%" + email + "%"));
        }
        return cb.and(predicates.toarray(new predicate[0]));
    });
}

4. 使用mybatis动态sql

mybatis提供了强大的动态sql功能:

mapper接口

public interface usermapper {
    list<user> findusers(@param("name") string name, 
                        @param("age") integer age, 
                        @param("email") string email);
}

xml映射文件

<select id="findusers" resulttype="user">
    select * from users
    <where>
        <if test="name != null">
            and name = #{name}
        </if>
        <if test="age != null">
            and age = #{age}
        </if>
        <if test="email != null">
            and email like concat('%', #{email}, '%')
        </if>
    </where>
</select>

动态sql标签说明

  • <if>: 条件判断
  • <where>: 自动处理where关键字和and/or前缀
  • <choose><when><otherwise>: 类似switch-case
  • <foreach>: 遍历集合
  • <set>: 更新时自动处理set关键字和逗号

5. 使用mybatis-plus的条件构造器

mybatis-plus提供了更便捷的查询条件构造方式:

public list<user> findusers(string name, integer age, string email) {
    querywrapper<user> querywrapper = new querywrapper<>();
    if (name != null) {
        querywrapper.eq("name", name);
    }
    if (age != null) {
        querywrapper.eq("age", age);
    }
    if (email != null) {
        querywrapper.like("email", email);
    }
    return usermapper.selectlist(querywrapper);
}

6. 使用jooq动态sql

jooq提供了类型安全的dsl:

public list<user> findusers(string name, integer age, string email) {
    return dslcontext.selectfrom(users)
        .where(name == null ? nocondition() : users.name.eq(name))
        .and(age == null ? nocondition() : users.age.eq(age))
        .and(email == null ? nocondition() : users.email.like("%" + email + "%"))
        .fetchinto(user.class);
}

最佳实践建议

  • 安全性: 始终使用参数化查询,防止sql注入
  • 可读性: 保持sql语句清晰易读
  • 性能: 考虑索引使用情况,避免全表扫描
  • 维护性: 复杂查询考虑使用注解或xml分离
  • 工具选择:
    • 简单项目: spring data jpa specification
    • 中等复杂度: mybatis动态sql
    • 高度灵活需求: jooq

到此这篇关于java mysql动态语句编写实现方式的文章就介绍到这了,更多相关java mysql动态语句内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com