You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring中DAO层Mapper空指针错误的解决方法咨询

Mapper空指针问题排查与解决

问题背景

已在Dispatcher Servlet.xml中为Mapper接口和DAO构建Bean,新建Mapper包并添加接口,同时实现了DAO;在DAO中通过Dispatcher Servlet内的DAO Bean与Mapper构建服务;在Controller中使用@Autowired和@Qualifier注入DAO,但仍遭遇Mapper空指针错误,相关Controller代码如下:

package Controller;

import java.util.List;

import org.apache.ibatis.session.SqlSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.servlet.ModelAndView;



import DAO.CourseStudentDAO;
import DAO.CourseDAO;
import DAO.StudentDAO;


import DTO.CourseResponseDTO;
import DTO.CourseStudentRequestDTO;

import DTO.StudentRequestDTO;
import DTO.StudentResponseDTO;

import Model.StudentBean;


@Controller
public class StudentController 
{
    @Autowired
    @Qualifier("sqlSession")
    SqlSession session;
    
    
    @Autowired
    @Qualifier("courseStudentDAO")
    private CourseStudentDAO CourseStudentDAO;
    
    @Autowired
    @Qualifier("courseDAO")
    private CourseDAO CourseDAO;
    
    @Autowired
    @Qualifier("studentDAO")
    private StudentDAO StudentDAO;
    
    @RequestMapping(value="/studentaddpage",method=RequestMethod.GET)
    public ModelAndView studentaddpage(ModelMap model)
    {
        CourseDAO.selectAll();
          List<CourseResponseDTO> courseList = CourseDAO.selectAll();            
          model.addAttribute("courseList", courseList);
        return new ModelAndView("STU001", "studentbean", new StudentBean());
    }
     @RequestMapping(value = "/StudentAddPage", method = RequestMethod.POST)
        public String addStu(@ModelAttribute("studentbean")  @Validated StudentBean studentbean, ModelMap model) {
//insert  
         List<String> attendArray = studentbean.getCourse();
         if (studentbean.getStudentname().isBlank() || studentbean.getDob().isBlank() || studentbean.getGender().isBlank()||studentbean.getPhone().isBlank() ||studentbean.getEducation().isBlank() ||studentbean.getStudentid().isBlank()) 
         {
             model.addAttribute("errorFill", "Fill the Blank!!!");
                return "redirect:/studentaddpage";
            }else {
                StudentDAO dao = new StudentDAO();
                StudentResponseDTO res = new StudentResponseDTO();
                StudentRequestDTO dto = new StudentRequestDTO();
                
                 DAO.CourseStudentDAO csdao = new DAO.CourseStudentDAO();
                  CourseStudentRequestDTO csdto = new CourseStudentRequestDTO();
                 
                
                  for(String a : attendArray ) 
                  { csdto.setStudentid(studentbean.getStudentid());
                  csdto.setCourse(a); csdao.insert(csdto); }
                 
                dto.setStudentid(studentbean.getStudentid());
                dto.setStudentname(studentbean.getStudentname());
                dto.setDob(studentbean.getDob());
                dto.setGender(studentbean.getGender());
                dto.setPhone(studentbean.getPhone());
                dto.setEducation(studentbean.getEducation());
                dao.insert(dto);
                session.commit();
                        
                return "redirect:/studentsearchpage";
                
            }
        }
     //show&search
     @RequestMapping(value = "/studentsearchpage", method = RequestMethod.GET)
        public ModelAndView stuSearchPage(ModelMap model) 
        {
         
            StudentDAO dao = new StudentDAO();
            CourseStudentDAO csdao = new CourseStudentDAO();
            List<StudentResponseDTO> list = dao.selectAll();
            for(StudentResponseDTO a : list) {
                List<String> courselist = csdao.selectOne(a.getStudentid());
                a.setCourse(courselist);   
            }
            model.addAttribute("studentList", list);
            return new ModelAndView("STU003", "studentbean", new StudentBean());
        }
    
     
     @RequestMapping(value = "/StudentSearchPage", method = RequestMethod.POST)
        public ModelAndView searchStudent(@ModelAttribute("studentbean") StudentBean studentbean, ModelMap model) 
     {
         
         StudentRequestDTO req = new StudentRequestDTO();
            req.setStudentid(studentbean.getSearchid());
            req.setStudentname(studentbean.getSearchname());

            CourseStudentDAO csdao = new CourseStudentDAO();
            StudentDAO dao = new StudentDAO();
            if(dao.search(req).isEmpty()) {
            
                return new ModelAndView("STU003", "studentbean", new StudentBean());
            }
            else {
                List<StudentResponseDTO> list = dao.search(req);
                for(StudentResponseDTO a : list) {
                    List<String> courselist = csdao.selectOne(a.getStudentid());
                    a.setCourse(courselist);   
                }
                model.addAttribute("studentList", list);
            
            List<StudentResponseDTO> dto=dao.search(req);
            
            return new ModelAndView("STU003", "studentbean", new StudentBean());
            }
        }
     
     //Student Update
     @RequestMapping(value="/studentupdatedpage/{studentid}" ,method=RequestMethod.GET)
        public ModelAndView studentupdatepage(@PathVariable String studentid,ModelMap model)
        {
            StudentRequestDTO dto=new StudentRequestDTO();
            dto.setStudentid(studentid);
            CourseDAO.selectAll();
              List<CourseResponseDTO> courseList = CourseDAO.selectAll();            
              model.addAttribute("courseList", courseList);
            return new ModelAndView("STU002","studentbean",StudentDAO.selectOne(dto));
        }
     @RequestMapping(value = "/studentupdatedpage/UpdateStudentUpdatePage" , method = RequestMethod.POST)
     public String updateStu(@ModelAttribute("studentbean")StudentBean studentbean,ModelMap model) {
         List<String> attendArray = studentbean.getCourse();
            
            
    
            if (studentbean.getStudentname().isBlank() || studentbean.getDob().isBlank() || studentbean.getGender().isBlank()||studentbean.getPhone().isBlank() ||studentbean.getEducation().isBlank() ||studentbean.getStudentid().isBlank() ) {
                model.addAttribute("errorFill", "Fill the Blank!!!");
                model.addAttribute("studentbean", studentbean);
                return "redirect:/studentupdatedpage";
            } else {
                StudentResponseDTO res = new StudentResponseDTO();
                StudentRequestDTO dto = new StudentRequestDTO();
                StudentDAO dao=new StudentDAO();
                CourseStudentDAO csdao = new CourseStudentDAO();
                CourseStudentRequestDTO csdto = new CourseStudentRequestDTO();
                
                csdto.setStudentid(studentbean.getStudentid());
                csdao.delete(csdto);
                
                for(String a : attendArray ) {
                    csdto.setStudentid(studentbean.getStudentid());
                    csdto.setCourse(a);
                    csdao.insert(csdto);
                }
                dto.setStudentid(studentbean.getStudentid());
                dto.setStudentname(studentbean.getStudentname());
                dto.setDob(studentbean.getDob());
                dto.setGender(studentbean.getGender());
                dto.setPhone(studentbean.getPhone());
                dto.setEducation(studentbean.getEducation());
                dao.update(dto);
                
                
                return "redirect:/studentsearchpage";

            }
     }
     @RequestMapping(value = "/DeleteStudent/{studentid}", method = RequestMethod.GET)
        public String deleteStu(@PathVariable String studentid, ModelMap model) {
         StudentDAO dao=new StudentDAO();
         StudentRequestDTO dto = new StudentRequestDTO();
            CourseStudentDAO csdao = new CourseStudentDAO(); 
            CourseStudentRequestDTO csdto = new CourseStudentRequestDTO();
         dto.setStudentid(studentid);
            csdto.setStudentid(studentid);
            dao.delete(dto);
            csdao.delete(csdto);
                model.addAttribute("errorFill", "Success delete");
                
                return "redirect:/stuSearchPage";
        }
}

问题根源

代码核心错误是在方法内部手动new了DAO实例(比如StudentDAO dao = new StudentDAO();、CourseStudentDAO csdao = new CourseStudentDAO();),这些手动创建的对象未被Spring容器管理,内部的Mapper依赖不会被注入,调用方法时必然触发空指针异常。

而类顶部通过@Autowired注入的StudentDAO、CourseStudentDAO等实例才是被Spring管理、完成依赖注入的对象,应该直接使用这些对象。

修复步骤

  1. 删除所有手动new DAO的代码,直接使用类中已注入的DAO成员变量
  2. 确保DAO实现类中,Mapper是通过Spring注入(比如@Autowired注入Mapper接口)或者通过Spring管理的SqlSession获取(sqlSession.getMapper(XXXMapper.class))
  3. 建议使用Spring声明式事务管理,替代手动调用session.commit(),避免事务管理混乱

修改后的核心代码示例

以addStu方法为例,修改后如下:

@RequestMapping(value = "/StudentAddPage", method = RequestMethod.POST)
public String addStu(@ModelAttribute("studentbean") @Validated StudentBean studentbean, ModelMap model) {
    List<String> attendArray = studentbean.getCourse();
    if (studentbean.getStudentname().isBlank() || studentbean.getDob().isBlank() || studentbean.getGender().isBlank()||studentbean.getPhone().isBlank() ||studentbean.getEducation().isBlank() ||studentbean.getStudentid().isBlank()) {
        model.addAttribute("errorFill", "Fill the Blank!!!");
        return "redirect:/studentaddpage";
    } else {
        StudentRequestDTO dto = new StudentRequestDTO();
        CourseStudentRequestDTO csdto = new CourseStudentRequestDTO();
        
        for(String a : attendArray ) {
            csdto.setStudentid(studentbean.getStudentid());
            csdto.setCourse(a);
            // 使用注入的CourseStudentDAO
            CourseStudentDAO.insert(csdto); 
        }
        
        dto.setStudentid(studentbean.getStudentid());
        dto.setStudentname(studentbean.getStudentname());
        dto.setDob(studentbean.getDob());
        dto.setGender(studentbean.getGender());
        dto.setPhone(studentbean.getPhone());
        dto.setEducation(studentbean.getEducation());
        // 使用注入的StudentDAO
        StudentDAO.insert(dto);
        session.commit();
                
        return "redirect:/studentsearchpage";
    }
}

其他方法如stuSearchPage、updateStu、deleteStu都需要做同样的修改:删除new DAO实例的代码,直接使用类顶部注入的对象。


内容的提问来源于stack exchange,提问作者Minthway Khaing

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.21 07:54:23