网易云发送短信验证码java实现

首先,登陆网易云信注册账号然后获取自己的App Key与App Secret,这里就不多说了,可以自行百度。

然后进入如下界面https://www.163yun.com/help/documents/33716973365022720#API%E8%B0%83%E7%94%A8%E8%AF%B4%E6%98%8E

在服务端API中我们可以很容易的找到这段代码,这是用来加密用的(关于如何加密也可以找到)

import java.security.MessageDigest;

public class CheckSumBuilder {
   // 计算并获取CheckSum
   public static String getCheckSum(String appSecret, String nonce, String curTime) {
       return encode("sha1", appSecret + nonce + curTime);
   }
   
   // 计算并获取md5值
   public static String getMD5(String requestBody) {
       return encode(“md5”, requestBody);
   }

   private static String encode(String algorithm, String value) {
       if (value == null) {
           return null;
       }
       try {
           MessageDigest messageDigest
                   = MessageDigest.getInstance(algorithm);
           messageDigest.update(value.getBytes());
           return getFormattedText(messageDigest.digest());
       } catch (Exception e) {
           throw new RuntimeException(e);
       }
   }
   private static String getFormattedText(byte[] bytes) {
       int len = bytes.length;
       StringBuilder buf = new StringBuilder(len * 2);
       for (int j = 0; j < len; j++) {
           buf.append(HEX_DIGITS[(bytes[j] >> 4) & 0x0f]);
           buf.append(HEX_DIGITS[bytes[j] & 0x0f]);
       }
       return buf.toString();
   }
   private static final char[] HEX_DIGITS = { '0', '1', '2', '3', '4', '5',
           '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
}

接着在下面我们又可以找到这段模板代码,我们先看他的模板,具体信息可以参考手册然后了解它们的意义

import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

public class Test {
   public static void main(String[] args) throws Exception{
       DefaultHttpClient httpClient = new DefaultHttpClient();
       String url = "https://api.netease.im/nimserver/user/create.action";
       HttpPost httpPost = new HttpPost(url);

       String appKey = "94kid09c9ig9k1loimjg012345123456";
       String appSecret = "123456789012";
       String nonce =  "12345";
       String curTime = String.valueOf((new Date()).getTime() / 1000L);
       String checkSum = CheckSumBuilder.getCheckSum(appSecret, nonce ,curTime);//参考 计算CheckSum的java代码

       // 设置请求的header
       httpPost.addHeader("AppKey", appKey);
       httpPost.addHeader("Nonce", nonce);
       httpPost.addHeader("CurTime", curTime);
       httpPost.addHeader("CheckSum", checkSum);
       httpPost.addHeader("Content-Type", "application/x-www-form-urlencoded;charset=utf-8");

       // 设置请求的参数
       List<NameValuePair> nvps = new ArrayList<NameValuePair>();
       nvps.add(new BasicNameValuePair("accid", "helloworld"));
       httpPost.setEntity(new UrlEncodedFormEntity(nvps, "utf-8"));

       // 执行请求
       HttpResponse response = httpClient.execute(httpPost);

       // 打印执行结果
       System.out.println(EntityUtils.toString(response.getEntity(), "utf-8"));
   }
}

 

然后咱们把上面的代码稍作修改变成如下的样子

package tool;

import com.alibaba.fastjson.JSON;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 短信相关的工具类
 * 
 * @author 李岚祺
 */
public class SMSUtils {

    private static final String NONCE = "123456";
	private static final String APP_SECRET = "你自己登陆所获取的";
    private static final String APP_KEY = "你自己登陆所获取的";
    
    /**
     * 验证码类短信,注意:该短信中验证码不能自己生成,由网易云帮我们生成
     * 
     * @param mobile 手机号码
     * @param templateId 验证码模板ID
     * @return 是否发送成功
     */
    public static final boolean sendCode(String mobile, String templateId) throws IOException {
        HttpPost httpPost = new HttpPost("https://api.netease.im/sms/sendcode.action");

        String currentTime = String.valueOf(new Date().getTime()/1000L);
        String checkSum = CheckSumBuilder.getCheckSum(APP_SECRET,NONCE,currentTime);

        //set header
        httpPost.setHeader("AppKey",APP_KEY);
        httpPost.setHeader("CurTime",currentTime);
        httpPost.setHeader("Nonce",NONCE);
        httpPost.setHeader("CheckSum",checkSum);
        httpPost.setHeader("Content-Type","application/x-www-form-urlencoded;charset=utf-8");

        //set data
        List<NameValuePair> nameValuePairList = new ArrayList<NameValuePair>();
        nameValuePairList.add(new BasicNameValuePair("mobile",mobile));
        nameValuePairList.add(new BasicNameValuePair("templateid", templateId));
        httpPost.setEntity(new UrlEncodedFormEntity(nameValuePairList,"utf-8"));

        //start request
        CloseableHttpClient closeableHttpClient = HttpClients.createDefault();
        HttpResponse httpResponse = closeableHttpClient.execute(httpPost);
        String responseResult = EntityUtils.toString(httpResponse.getEntity(),"utf-8");
        System.out.println("responseResult:"+responseResult);

        String stateCode = JSON.parseObject(responseResult).getString("code");
        if(stateCode.equals("200")){
            return true;
        }
        return false;
    }

    /**
     * 判断用户输入验证码与网易云生成的验证码是否一致
     * 
     * @param mobile 电话号码
     * @param code 发送到mobile上的短信
     */
    public static final boolean verifyCode(String mobile, String code) throws IOException {
        HttpPost httpPost = new HttpPost("https://api.netease.im/sms/verifycode.action");

        String currentTime = String.valueOf(new Date().getTime()/1000L);
        String checkSum = CheckSumBuilder.getCheckSum(APP_SECRET,NONCE,currentTime);

        //set header
        httpPost.setHeader("AppKey",APP_KEY);
        httpPost.setHeader("CurTime",currentTime);
        httpPost.setHeader("Nonce",NONCE);
        httpPost.setHeader("CheckSum",checkSum);
        httpPost.setHeader("Content-Type","application/x-www-form-urlencoded;charset=utf-8");

        //set data
        List<NameValuePair> nameValuePairList = new ArrayList<NameValuePair>();
        nameValuePairList.add(new BasicNameValuePair("code",code));
        nameValuePairList.add(new BasicNameValuePair("mobile",mobile));
        httpPost.setEntity(new UrlEncodedFormEntity(nameValuePairList,"utf-8"));

        //start request
        CloseableHttpClient closeableHttpClient = HttpClients.createDefault();
        HttpResponse httpResponse = closeableHttpClient.execute(httpPost);
        String responseResult = EntityUtils.toString(httpResponse.getEntity(),"utf-8");
        System.out.println("responseResult:"+responseResult);

        String stateCode = JSON.parseObject(responseResult).getString("code");
        if(stateCode.equals("200")){
            return true;
        }
        return false;
    }
}

接下来就是测试了,我们来一个简单的代码来试一试

import java.io.IOException;
import java.util.Scanner;

import tool.SMSUtils;

public class Test1 {
	
	private static String mobile = "你需要发送短信的手机号";

	public static void main(String[] args) {
		try {
			SMSUtils.sendCode(mobile, "模板号(在里面有你自己设置的发送格式)");
		} catch (IOException e) {
			e.printStackTrace();
		}
		Scanner scanner = new Scanner(System.in);
		System.out.println("请输入你收到的验证码");
		String code = scanner.nextLine();
		try {
			if(SMSUtils.verifyCode(mobile, code)) {
				System.out.println("校验成功");
			}else {
				System.out.println("校验失败");
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
}

 一番操作下来之后就大功告成了,下面我们结合web来一起试一下(运用了一点点异步),有关于这异步,不知道的可以稍微去看看,不会用太多时间的

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
	<head>
		<title></title>
		<script type="text/javascript" src="./js/jquery-3.3.1.js"></script>
		<script>
			function sendcode(){
				var ajaxObject={
					url:"./SendcodeServlet",
					type:"GET",
					data:{
						mobile:document.getElementById("mobile").value,
					},
					dataType:"text",
					success:function(data){						
					}
				}
				$.ajax(ajaxObject);
			}
			function checkcode(){
				var ajaxObject={
					url:"./CheckcodeServlet",
					type:"GET",
					data:{mobile:document.getElementById("mobile").value,
						  code:document.getElementById("code").value
						 },
					dataType:"text",
					success:function(data){						
					}
				}
				$.ajax(ajaxObject);
			}

		</script>
	</head>
	<body>
		<input name="mobile" id="mobile" placeholder="请输入手机号" value=""/><br />
		<input name="code" id="code" placeholder="请输入验证码" value=""/><br />
		<button  onclick="sendcode()">发送验证码</button>
		<button  onclick="checkcode()">提交</button>
	</body>
</html>

 接下来是俩个Servlet

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import tool.SMSUtils;

public class SendcodeServlet extends HttpServlet {
	
	private static final long serialVersionUID = 1L;
	private static String templateId = "4003516";
   
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String mobile = request.getParameter("mobile");
		System.out.println(mobile);
		SMSUtils.sendCode(mobile, templateId);
	}
}


import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import tool.SMSUtils;

public class CheckcodeServlet extends HttpServlet {
	
	private static final long serialVersionUID = 1L;
       
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		String code = request.getParameter("code");//用户输入的验证码
		String mobile = request.getParameter("mobile");
		System.out.println(code);
		if(SMSUtils.verifyCode(mobile,code)) {
			System.out.println("成功");
			//验证成功跳转到成功界面
			request.getRequestDispatcher("success.jsp").forward(request, response);
		}else {
			System.out.println("失败");
		}
	}

}

 不过在这里我有一个疑问就是最后验证出来是成功,也打印了出来,但是那个跳转界面不知道为什么没有出现,然而到这时候我的短信已经全部发送完了,没有剩余的存货了,有点尴尬。。。。。。先留个坑,或许之后写类似的项目的时候我就知道了。

我觉得实现这种功能比较重要的一点就是学会去看开发者API,里面有各种介绍,还有好多东西我也没怎么看,但单单看这俩种就能实现验证码的发送与校验了。

猜你喜欢

转载自blog.csdn.net/LanQiLi/article/details/82686565