如何在Service与DAO层实现ExerciseInstructions列表的数据库查询返回
解决从数据库获取数据并通过JAX-B返回XML/JSON列表的问题
我来帮你梳理下整个流程,你遇到的核心问题其实是如何把数据库查询到的ExerciseInstructions集合正确装进ExerciseInstructionsList包装类,同时满足JAX-B的序列化要求。下面一步步来:
1. 先确认你的包装类ExerciseInstructionsList结构是否正确
JAX-B对序列化的类有几个硬性要求:必须有无参构造器,集合属性需要正确的注解标记。示例代码如下:
import javax.xml.bind.annotation.XmlElement; import javax.xml.bind.annotation.XmlRootElement; import java.util.List; @XmlRootElement(name = "exerciseInstructionsList") public class ExerciseInstructionsList { private List<ExerciseInstructions> instructions; // JAX-B必须的无参构造器,不能省略 public ExerciseInstructionsList() {} // 方便快速初始化的带参构造器 public ExerciseInstructionsList(List<ExerciseInstructions> instructions) { this.instructions = instructions; } // 给集合属性加@XmlElement,指定XML中子元素的名称 @XmlElement(name = "exerciseInstruction") public List<ExerciseInstructions> getInstructions() { return instructions; } public void setInstructions(List<ExerciseInstructions> instructions) { this.instructions = instructions; } }
如果你的包装类没有无参构造器,或者没给集合加注解,JAX-B会直接序列化失败,这是很多人踩的坑。
2. DAO层:从数据库查询并返回List<ExerciseInstructions>
DAO层的职责就是和数据库交互,返回原始的实体集合就行,不用管包装类。这里分两种常见场景举例:
场景1:用JPA(Spring Data JPA)
直接定义Repository接口,Spring会自动实现查询逻辑:
import org.springframework.data.jpa.repository.JpaRepository; import java.util.List; public interface ExerciseInstructionsDao extends JpaRepository<ExerciseInstructions, Long> { // 查询所有数据,Spring Data JPA会自动生成SQL List<ExerciseInstructions> findAll(); }
场景2:用原生JDBC
手动映射结果集到实体类,收集到List中:
import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.util.ArrayList; import java.util.List; public class ExerciseInstructionsDao { public List<ExerciseInstructions> getAllInstructions() throws SQLException { List<ExerciseInstructions> resultList = new ArrayList<>(); String sql = "SELECT id, name, description FROM exercise_instructions"; // 这里假设你有获取数据库连接的工具方法 try (Connection conn = DbConnectionUtil.getConnection(); PreparedStatement stmt = conn.prepareStatement(sql); ResultSet rs = stmt.executeQuery()) { while (rs.next()) { ExerciseInstructions instruction = new ExerciseInstructions(); instruction.setId(rs.getLong("id")); instruction.setName(rs.getString("name")); instruction.setDescription(rs.getString("description")); resultList.add(instruction); } } return resultList; } }
3. Service层:把DAO返回的集合装进包装类
Service层负责业务逻辑,这里的核心就是把数据库查出来的List<ExerciseInstructions>传入包装类,而不是创建空的ArrayList:
import org.springframework.stereotype.Service; import java.util.List; @Service public class ExerciseInstructionsService { private final ExerciseInstructionsDao dao; // 推荐用构造注入,避免空指针 public ExerciseInstructionsService(ExerciseInstructionsDao dao) { this.dao = dao; } public ExerciseInstructionsList getAllInstructions() { // 从DAO拿到数据库的数据 List<ExerciseInstructions> dbData = dao.findAll(); // 把数据塞进包装类返回 return new ExerciseInstructionsList(dbData); } }
你之前遇到的问题大概率是这里出错了——比如你创建了新的空ArrayList,而没有把DAO返回的数据放进去。
4. Controller层:返回包装类对象
Controller直接返回Service层给的包装类,同时指定支持XML和JSON格式:
import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController; @RestController public class ExerciseInstructionsController { private final ExerciseInstructionsService service; public ExerciseInstructionsController(ExerciseInstructionsService service) { this.service = service; } @GetMapping(value = "/exercise-instructions", produces = {MediaType.APPLICATION_XML_VALUE, MediaType.APPLICATION_JSON_VALUE}) public ExerciseInstructionsList getInstructions() { return service.getAllInstructions(); } }
额外注意事项
- 如果是Spring Boot 2.x及以上版本,默认没有包含JAX-B依赖,需要手动添加:
<!-- Maven依赖 --> <dependency> <groupId>com.sun.xml.bind</groupId> <artifactId>jaxb-core</artifactId> <version>2.3.0.1</version> </dependency> <dependency> <groupId>com.sun.xml.bind</groupId> <artifactId>jaxb-impl</artifactId> <version>2.3.0.1</version> </dependency> <dependency> <groupId>javax.xml.bind</groupId> <artifactId>jaxb-api</artifactId> <version>2.3.1</version> </dependency> - 可以先打印DAO返回的List的大小,确认是否真的从数据库查到了数据,排除数据为空的情况。
内容的提问来源于stack exchange,提问作者manas kumar
相关产品推荐
相关产品推荐

