######漏发邮件问题【###终归是代码问题(测试出来的-不是直接可见的逻辑问题!!!try catch finally问题)。先耐心测试自身找原因,广泛应用的都是成熟技术!

===ssm整合JavaMail:漏发邮件问题【###终归是代码问题(测试出来的-不是直接可见的逻辑问题!!!try catch finally问题)。】

=== ###知识点:【finally保证异常仍然需要执行的代码一定会执行!】

===最后代码:(只需要看insertUser方法)

 /**
     * 添加用户
     * 手机号、邮箱、备注可空
     * 是否删除、创建时间、修改时间为空,mapper层插入默认值
     * 姓名、角色id、登录名、密码不为空
     * 登录名唯一, 登录名存在返回0
     * 插入成功返回自增主键
     * 其他错误返回-1
     */
    @Override
    public int insertUser(UserDO user, String rePassword,
                          Integer agencyId,
                          Integer advertiserId,
                          HttpServletRequest request) {
        int userMessageIsAvailable = this.checkUserMessage(user, rePassword);
        if (userMessageIsAvailable != 1) {
            return userMessageIsAvailable;
        }

        String salt = Long.toString(System.currentTimeMillis());
        ByteSource byteSource = ByteSource.Util.bytes(salt);
        user.setSalt(salt);
        Object md5Password = new SimpleHash("MD5", user.getPassword(), byteSource, 5);
        String password = user.getPassword();//设置加密密码前,取出明文密码。发邮件
        user.setPassword(String.valueOf(md5Password));
        int result = userMapper.insertSelective(user);//基本信息。

        if(  result>0 ) {

                new Thread(){
                    @Override
                    public void run() {

//========================》freeMarker创建邮件内容:开始
                        Configuration configuration = freeMarkerConfigurer.getConfiguration();
                        //加载模板对象
                        Template template = null;
                        String fileName = null;//拿出来,finally内部可见。
                                //创建一个数据集
                        Map data = new HashMap<>();
                        MockMultipartFile multipartFile = null;
                        try {
                            template = configuration.getTemplate("mail.ftl");
                            //data需要的数据分析:图片绝对路径。
                            //String realPath = request.getServletContext().getRealPath("");
                            String realPath = request.getServletContext().getRealPath("/");
                            if (!realPath.endsWith(java.io.File.separator)) {
                                //linux下拿到的realPath不带"\";Windows下带
                                realPath = realPath + java.io.File.separator;
                            }
                            System.out.println("===》realPath:"+realPath);//E:\ClickCube\classes\artifacts\ClickCube_front_Web_exploded\

                            //防止图片位置变化,每次发邮件,上传一次mailLogo.png
                            InputStream inputStream = new FileInputStream(realPath+"resource/mailLogo/mailLogo.png");//
                            //不行换个MultipartFile的实现类试试======》
                            multipartFile = new MockMultipartFile("mailLogo.png", inputStream);
                            fileName = multipartFile.getName();

//                            add
//                            configuration.clearEncodingMap();
//                            configuration.clearSharedVariables();
//                            configuration.clearTemplateCache();
                        } catch (Exception e) {
                            e.printStackTrace();
                        }finally { //》》》前面  出现任何异常,只要用户插入成功,都要发邮件。
                            //### 【有时漏发邮件 就是没有写到finally里导致的】》没有执行发邮件方法。。。

                            String fileId = null;
                            String content = null;
                            String toMail = null;
                            try{
                                //===》没连接VPN 会报错 部分=== 开始
                                fileId = FastDFSUtil.uploadFile(multipartFile.getBytes(), fileName);//===》没连接VPN 开始报错。。。
                                //获取服务器写在配置文件中的头地址
                                String filePathUrl = ReadPropertiesUtil.readFilePath();
                                //设置在服务器上的绝对地址
                                String logoUrl = filePathUrl + "/" + fileId;
                                System.out.println("=====》logoUrl:" + logoUrl);
                                data.put("logoUrl", logoUrl);//ok

                                data.put("loginName", user.getLoginName());
                                data.put("password", password);//加密前取出的明文密码。

                                content = FreeMarkerTemplateUtils.processTemplateIntoString(template, data);
                                //========================》freeMarker创建邮件内容:结束
                                toMail = user.getEmail();
                                //===》没连接VPN 会报错 部分=== 结束
                            }catch (Exception e){
                                e.printStackTrace();
                            }finally {  //====》没连接VPN 报错。保证发邮件也要执行。。。
                                if(result>0){
                                    //MailUtils.sendMail("注册邮件", content, toMail);//有些邮箱不能解析HTML。是不是content是String的原因?
                                    sendTemplateMail( content,toMail );//设置为html邮件。【使用Spring整合的Mail方式,不用原生JavaMail】
                                }
                            }

                        }


                    }//run线程体
                }.start();



        }//a==1 插入记录成功。


        return user.getId();
    }

    //发送模板邮件
    public void sendTemplateMail(String htmlText,String toMail) {
        MimeMessage msg=mailSender.createMimeMessage();
       try{
           MimeMessageHelper helper=new MimeMessageHelper(msg,false,"utf8");//由于是html邮件,不是mulitpart类型
           helper.setFrom("[email protected]");
           helper.setTo(toMail);
           helper.setSubject("注册成功-邮件");
           helper.setText(htmlText, true);//是html邮件:true
       }catch (Exception e){
           e.printStackTrace();
       }finally {
           mailSender.send(msg);//有异常仍然发邮件。
           System.out.println("成功发送模板邮件");
       }
    }


====之前导致问题的代码:

①测试发现:漏发的邮件,没有执行发邮件代码。。。

②问题原因:

【### 只有一个try catch。try中代码过多,

####  前面代码出现异常,不能保证:“出现异常,后面仍然需要执行的代码(发邮件)”  仍然继续执行!!!】

  /**
     * 添加用户
     * 手机号、邮箱、备注可空
     * 是否删除、创建时间、修改时间为空,mapper层插入默认值
     * 姓名、角色id、登录名、密码不为空
     * 登录名唯一, 登录名存在返回0
     * 插入成功返回自增主键
     * 其他错误返回-1
     */
    @Override
    public int insertUser(UserDO user, String rePassword,
                          Integer agencyId,
                          Integer advertiserId,
                          HttpServletRequest request) {
        int userMessageIsAvailable = this.checkUserMessage(user, rePassword);
        if (userMessageIsAvailable != 1) {
            return userMessageIsAvailable;
        }

        String salt = Long.toString(System.currentTimeMillis());
        ByteSource byteSource = ByteSource.Util.bytes(salt);
        user.setSalt(salt);
        Object md5Password = new SimpleHash("MD5", user.getPassword(), byteSource, 5);
        String password = user.getPassword();//设置加密密码前,取出明文密码。发邮件
        user.setPassword(String.valueOf(md5Password));
        int a = userMapper.insertSelective(user);//基本信息。

        if(  new Integer(a) !=null ) {

                new Thread(){
                    @Override
                    public void run() {

//========================》freeMarker创建邮件内容:开始
                        Configuration configuration = freeMarkerConfigurer.getConfiguration();
                        //加载模板对象
                        Template template = null;
                        //创建一个数据集
                        Map data = new HashMap<>();
                        try {
                            template = configuration.getTemplate("mail.ftl");
                            //data需要的数据分析:图片绝对路径。
                            //String realPath = request.getServletContext().getRealPath("");

                            String realPath = request.getServletContext().getRealPath("/");
                            if (!realPath.endsWith(java.io.File.separator)) {
                                //linux下拿到的realPath不带"\";Windows下带
                                realPath = realPath + java.io.File.separator;
                            }
                            System.out.println("===》realPath:"+realPath);//E:\ClickCube\classes\artifacts\ClickCube_front_Web_exploded\


                            //String logoUrl="http://"+localAddr+":"+localPort+contextPath+"/resource/mailLogo/mailLogo.png";//必须加http
                            //        logoUrl的IP不对。换个设备就访问不到Logot图片了。IP总是服务器本机的127.0.0.1
                            //解决思路:
                            // ①图片写到浏览器。
                            // ②拿到正确的服务器IP【同一台服务器。网络变化:服务器IP变化(所以只能发送logo附件。本地显示附件太麻烦)】
                            // ③logo图片放到 fastDFS(稳定的文件服务器)上,再访问远程的图片。

                            //防止图片位置变化,每次发邮件,上传一次mailLogo.png
                            InputStream inputStream = new FileInputStream(realPath+"resource/mailLogo/mailLogo.png");//
                            //不行换个MultipartFile的实现类试试======》
                            MockMultipartFile multipartFile = new MockMultipartFile("mailLogo.png", inputStream);
                            //
                            String fileName = multipartFile.getName();
                            //businessLicenseFileId等4个XXXFileId是要存到数据库中的绝对ID,或者相对路径,也是在服务器中的相对地址
                            String fileId = FastDFSUtil.uploadFile(multipartFile.getBytes(), fileName);

                            //获取服务器写在配置文件中的头地址
                            String filePathUrl = ReadPropertiesUtil.readFilePath();
                            //设置在服务器上的绝对地址
                            String logoUrl = filePathUrl + "/" + fileId;
                            System.out.println("=====》logoUrl:" + logoUrl);
                            data.put("logoUrl", logoUrl);//ok

                            data.put("loginName", user.getLoginName());
                            data.put("password", password);//加密前取出的明文密码。

                           /* //指定文件输出的路径及文件名
                            File htmlFile = new File("D:\\freemarker_registerMail\\mail.html");
                            Writer out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(htmlFile),"UTF-8"));
                            //输出文件
                            template.process(data, out);//ok
                            //关闭流
                            out.close();*/

                            String content = FreeMarkerTemplateUtils.processTemplateIntoString(template, data);
                            //========================》freeMarker创建邮件内容:结束
                            String toMail = user.getEmail();
                            //MailUtils.sendMail("注册邮件", content, toMail);//有些邮箱不能解析HTML。是不是content是String的原因?
                            sendTemplateMail( content,toMail );//设置为html邮件。【使用Spring整合的Mail方式,不用原生JavaMail】
                        } catch (Exception e) {
                            e.printStackTrace();
                        }



                    }//run线程体
                }.start();



        }//a==1 插入记录成功。


        return user.getId();
    }

猜你喜欢

转载自blog.csdn.net/qq_20597149/article/details/81171800