JAVA 调用第三方短信平台接口发送短信
做了几个调用三方短信平台发送短信的例子,大部分需要 携带参数,向指定URL发送请求
回顾对接第一个平台时痛苦的乱码经历,这里放一份代码,算是个模版,再用到的时候过来copy一下就OK。
在进入主题之前,考虑一个编码的问题:
1、unicode,utf8,gbk,gb2312之类的指的到底是什么?为什么需要它们?
字符编码中ASCII、Unicode和UTF-8的区别 - 风行风中 - 博客园 (cnblogs.com)
GB2312、GBK、GB18030 这几种字符集的主要区别是什么? - 知乎 (zhihu.com)
- 简单来说,计算机只能识别0和1组成的二进制,所以为了显示某一个字符,必须指定字符与二进制表示的对应关系。
- 各种各样的字符会组合成一个集合,集合被称为字符表,
- 给字符表里的字符编上一个数字,也就是字符集合到一个整数集合的映射,这个整数集合叫做字符集,而按照字符二进制表示标准进行的实现叫做编码,我们需要它们的结合来让屏幕显示出我们看得懂的内容。
- 编码其实就是一种映射关系,将字节表示的值映射到字符集中的符号。
- unicode是一种字符集,涵盖了世界上所有的字符,utf8是一种用于unicode的编码方式
- gb2312是国内针对 ASCII 扩展的字符集,通常我们把编码方案也叫做gb2312。GBK是对gb2312做的扩展。
也就是说,gbk,gb2312和 utf8 不是一个派系的。
2、程序运行时,处于内存中的字符串是不是也具有指定的编码?如果没有,为什么有时候在获取字节数组时还要指定编码方式?
这里我看了一些文章,有了自己的理解,但是不知道理解的是否正确,先不列出来了
Get请求
- getResponse 内将数据写入请求的方式
- 组织数据时对content进行URL编码
- 正确设置content-type 头
//调用处捕获异常处理发送失败的情况,所以代码内不合预期的情况都是直接抛Exception
public void send(String to, String content) throws Exception {
//username,password,content,to...参数的非空 及 格式判断
String apiRspStr = getResponse(to,content); //构建请求,获取响应
String result = resolve(apiRspStr); //解析响应数据(kv,json,html...),
//成功时返回代码,失败时返回错误消息
if(!"0".equals(result)) { //"0" 需要按平台文档替换
throw new Exception("消息发送失败:" + result);
}
}
private String getResponse(String to, String content) throws Exception {
URLConnection con = null;
OutputStreamWriter out = null;
BufferedReader br = null;
String sendSmsData;
try {
sendSmsData = organizationData(to,content);
log.info("请求参数为:" + sendSmsData);
} catch (Exception e) {
log.error("组织请求数据时出现错误", e);
throw e;
}
try {
URL requestUrl = new URL(getUrl());
con = requestUrl.openConnection();
con.setDoOutput(true);
con.setRequestProperty("Pragma", "no-cache");
con.setRequestProperty("Cache-Control", "no-cache");
con.setRequestProperty("Content-Type", "application/x-www-form-urlencoded;charset=gb2312"); // 按短信平台的要求设置 charset的值
out = new OutputStreamWriter(con.getOutputStream());
out.write(sendSmsData);
out.flush();
out.close();
br = new BufferedReader(new InputStreamReader(con.getInputStream()));
String line = "";
StringBuffer buf = new StringBuffer();
while ( (line = br.readLine()) != null ) {
buf.append(line);
}
String responseStr = buf.toString();
log.info("响应数据:" + responseStr);
return responseStr;
} catch (IOException e) {
e.printStackTrace();
log.error("获取响应失败", e);
throw e;
} finally {
try {
if(out != null) {
out.close();
}
}catch(Exception e) {}
try {
if(br != null) {
br.close();
}
}catch(Exception e) {}
}
}
private String organizationData(String to, String content) throws Exception {
StringBuilder sendBuilder = new StringBuilder();
sendBuilder.append("username=");//用户登录名
sendBuilder.append(getUserName());
sendBuilder.append("&password=");//密码需要按平台要求处理;
sendBuilder.append(hashpwd());
sendBuilder.append("&mobiles=");//接收手机号,限定不允许
sendBuilder.append(to);
sendBuilder.append("&content=");
sendBuilder.append(URLEncoder.encode(content, "GB2312"));
return sendBuilder.toString();
}
// resolve方法 依赖于短信平台返回结果的标准,这里提供的内容脱离平台就没有意义
//示例代码内 发送成功result为0,发送失败会返回各种含义的数字,description是中文描述
private String resolve(String rspStr) throws Exception { //rspStr: result=0&description=%B7%A2%CB%CD%B3%C9%B9%A6&faillist=
String[] resultArray = rspStr.split("&");
Map kv = new HashMap();
for(String array : resultArray) {
String[] elementArray = array.split("=");
if(elementArray.length == 2) {
kv.put(elementArray[0], elementArray[1]);
}
}
if(kv.isEmpty()) {
log.error("rspStr: " + rspStr);
throw new Exception("解析返回数据时未得到结果");
}
String result = "";
if("0".equals(kv.get("result").toString())) {
result = "0";
return result;
}
result = URLDecoder.decode(kv.get("description").toString(),"gb2312") ;
return result;
}
Post请求
- 短信内容要用URL编码
- 写入请求体的数据以 List<NameValuePair> 形式组织
public void sendSmsPost(MsgData msgData){
String respContent;//响应报文
CloseableHttpClient httpClient = null;
try{
httpClient = HttpClients.createDefault(); //创建连接对象
HttpPost httpPost = new HttpPost(smsUrl); //创建post对象
Map params = new HashMap(); //构建请求参数
String phone = msgData.getMsgTo(); //接收手机号
String text = msgData.getContent(); //发送内容
String gbkText = URLEncoder.encode(msgData.getContent().trim(), "GBK");
System.out.println("短信内容GBK:" + gbkText);
params.put("username",username);//登录用户名
params.put("password",password);//登录用户密码
params.put("to",phone); //消息接收手机号码
params.put("text",gbkText);
List<NameValuePair> postParams = getParams(params);
httpPost.setHeader("Content-Type","application/x-www-form-urlencoded;charset=gbk");
httpPost.setEntity(new UrlEncodedFormEntity(postParams));
//发送http请求,获取返回结果
HttpResponse httpResponse = httpClient.execute(httpPost);
if(httpResponse.getStatusLine().getStatusCode() == 200){
//解析数据
respContent = EntityUtils.toString(httpResponse.getEntity());
System.out.println("响应数据:" + respContent);
}else {
//请求失败
}
}catch (Exception e){
e.printStackTrace();
}finally {
try {
if(httpClient != null){
httpClient.close();
}
}catch (Exception e2){
e2.printStackTrace();
}
}
}
/**
* 参数解析
* @param map
* @return
*/
public static List<NameValuePair> getParams(Map<String, String> map){
List<NameValuePair> params = new ArrayList<NameValuePair>();
Set<Map.Entry<String, String>> entrySet = map.entrySet();
for (Map.Entry<String, String> e : entrySet) {
String name = e.getKey();
String value = e.getValue();
NameValuePair pair = new BasicNameValuePair(name, value);
params.add(pair);
}
return params;
}
JAVA 调用第三方短信平台接口发送短信的更多相关文章
- java 调用短信 api 接口发送短信
参考: https://blog.csdn.net/u014793522/article/details/59062014 参考 :https://blog.csdn.net/Lu_shilusi ...
- Java之HttpClient调用WebService接口发送短信源码实战
摘要 Java之HttpClient调用WebService接口发送短信源码实战 一:接口文档 二:WSDL 三:HttpClient方法 HttpClient方法一 HttpClient方法二 Ht ...
- Java调用第三方http接口的方式
1. 概述 在实际开发过程中,我们经常需要调用对方提供的接口或测试自己写的接口是否合适.很多项目都会封装规定好本身项目的接口规范,所以大多数需要去调用对方提供的接口或第三方接口(短信.天气等). 在J ...
- 短信平台软件开发,短信发送平台销售,短信软件源码,G客短信发送平台
一:web短信平台组成 需要短信软件平台源码的联系QQ:290615413 vx:290615413 整套短信系统平台还是由B/S(客户端+后台,取消了以前C/S的管理后台) ,C/S发送服务端和 ...
- 企业短信通 C# HTTP接口 发送短信
/* 功能: 企业短信通 C# HTTP接口 发送短信 修改日期: 2014-09-01 说明: http://api.cnsms.cn/?ac=send&uid=用户账号&pwd=M ...
- Java调用第三方dll文件的使用方法 System.load()或System.loadLibrary()
Java调用第三方dll文件的使用方法 public class OtherAdapter { static { //System.loadLibrary("Connector") ...
- java调用C# webService发布的接口
java调用C# webService发布的接口 java调用C# webService方式有很多种我这里只介绍一种 首先需要引入axis的jar包 axis的maven坐标如下 <depend ...
- c# 调用短信平台接口,给手机发送短信
项目上要做个发手机短信的功能.网上找找了,用的微米的短信接口. 注册后,获得UID和UID key,C#代码中需要这个 调用代码很简单 ", con = "[微米]您的验证码是:6 ...
- android 中调用接口发送短信
android中可以通过两种方式发送短信 第一:调用系统短信接口直接发送短信:主要代码如下: //直接调用短信接口发短信 SmsManager smsManager = SmsManager.getD ...
随机推荐
- AcWing 241. 楼兰图腾
#include<bits/stdc++.h> using namespace std; const int N=2e5+5; typedef long long ll; ll ans,l ...
- 搭建Nexus3私服(含使用说明,支持CentOS、Windows)
官方文档 Nexus仓库介绍(支持maven.yum.docker私服等) 仓库分为三种: proxy:是远程仓库的代理.比如说在nexus中配置了一个central repository的proxy ...
- 暑假自学java第六天
1,方法的覆盖:当子类继承父类,而子类中的方法与父类中方法的名称,返回类型及参数都完全一致时,就称子类中的方法覆盖了父类中的方法,有时也称方法的"重写" [不需要关键字] 2,th ...
- Docker:docker部署Sqlite3数据库
1.依赖Ubuntu系统安装sqlite3生成镜像 dockerfile文件 FROM ubuntu:trusty RUN sudo apt-get -y update RUN sudo apt-ge ...
- 在web.xml正确加载spring配置文件的方式
ssm框架整合时一直报出没有创建实例bean的错误,一直以为是代码原因,反复测试了很久,才找到原因是spring配置文件没有正确导入,下图是我的错误示例 web.xml加载spring配置文件的方式主 ...
- 压力测试工具:apache bench(ab)
作为php后端工程师,除了实现业务需求之外,需要考虑的就是自己写的服务,在大并发下是否能正常运行了,例如在我之前文章讲到的,在并发下,数据库查询可能会造成脏读幻读等情况,导致业务不正常. 但是,在一般 ...
- XCTF reverse_box(idapython)
ida先静态分析,发现有很多a2[1]不知道是什么,就远程动调了一下,发现是我们所输入的字符串,也就是我们所输入的字符串作为索引,通过v4这个数组输出,这题题目的数据漏给了,当时也是一头雾水,后面找了 ...
- WPF DataGrid RowDetailsTemplate 鼠标滚动通知到 DataGrid 滚动
前言:上次做了数据驱动UI虽然已经实现,但是在明细中鼠标滚动并不能带动外部 DataGrid 滚动条滚动,上文地址 https://www.cnblogs.com/luguangguang/p/14 ...
- 网站图片无缝兼容 WebP/AVIF
前言 WebP 格式发布已有十余年,但不少站点至今仍未使用,只为兼顾极少数低版本浏览器.至于去年发布的 AVIF 格式,使用的站点就更少了. 然而图片往往是流量大户,与其费尽心机优化脚本体积,可能还不 ...
- 基于YARP实现的FastGithub
前言 最近开源的两个项目,先是FastGithub,旨在解决访问github抽风的问题.然后开发HttpMouse项目,基于yarp的http公网反向代理到内网的服务端与客户端库,在开发HttpMou ...