first commit
This commit is contained in:
3
comm/Smsbao/WebContent/META-INF/MANIFEST.MF
Executable file
3
comm/Smsbao/WebContent/META-INF/MANIFEST.MF
Executable file
@@ -0,0 +1,3 @@
|
||||
Manifest-Version: 1.0
|
||||
Class-Path:
|
||||
|
||||
12
comm/Smsbao/WebContent/WEB-INF/web.xml
Executable file
12
comm/Smsbao/WebContent/WEB-INF/web.xml
Executable file
@@ -0,0 +1,12 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" id="WebApp_ID" version="2.5">
|
||||
<display-name>Sms253</display-name>
|
||||
<welcome-file-list>
|
||||
<welcome-file>index.html</welcome-file>
|
||||
<welcome-file>index.htm</welcome-file>
|
||||
<welcome-file>index.jsp</welcome-file>
|
||||
<welcome-file>default.html</welcome-file>
|
||||
<welcome-file>default.htm</welcome-file>
|
||||
<welcome-file>default.jsp</welcome-file>
|
||||
</welcome-file-list>
|
||||
</web-app>
|
||||
3
comm/Smsbao/dbscript/1.0/SMSBAO-DML-MYSQL.SQL
Executable file
3
comm/Smsbao/dbscript/1.0/SMSBAO-DML-MYSQL.SQL
Executable file
@@ -0,0 +1,3 @@
|
||||
INSERT INTO `T_SYSPARA` VALUES ('smsbao_url', 'smsbao_url', null, '', '100', '2', '短信宝URL');
|
||||
INSERT INTO `T_SYSPARA` VALUES ('smsbao_u', 'smsbao_u', null, '', '100', '2', '短信宝用户名');
|
||||
INSERT INTO `T_SYSPARA` VALUES ('smsbao_p', 'smsbao_p', null, '', '100', '2', '短信宝密码');
|
||||
17
comm/Smsbao/src/smsbao/SmsSendService.java
Executable file
17
comm/Smsbao/src/smsbao/SmsSendService.java
Executable file
@@ -0,0 +1,17 @@
|
||||
package smsbao;
|
||||
|
||||
/**
|
||||
* 短信发送,异步发送,写入SmsMessageQueue队列返回
|
||||
*
|
||||
*/
|
||||
public interface SmsSendService {
|
||||
|
||||
/**
|
||||
* 单发短信
|
||||
*
|
||||
* @param mobile 手机号
|
||||
* @param content 短信内容
|
||||
*/
|
||||
public void send(String mobile, String content);
|
||||
|
||||
}
|
||||
4
comm/Smsbao/src/smsbao/exception/InvalidMobileException.java
Executable file
4
comm/Smsbao/src/smsbao/exception/InvalidMobileException.java
Executable file
@@ -0,0 +1,4 @@
|
||||
package smsbao.exception;
|
||||
|
||||
public class InvalidMobileException extends RuntimeException {
|
||||
}
|
||||
4
comm/Smsbao/src/smsbao/exception/InvalidSmsContentException.java
Executable file
4
comm/Smsbao/src/smsbao/exception/InvalidSmsContentException.java
Executable file
@@ -0,0 +1,4 @@
|
||||
package smsbao.exception;
|
||||
|
||||
public class InvalidSmsContentException extends RuntimeException {
|
||||
}
|
||||
176
comm/Smsbao/src/smsbao/internal/HttpClientUtil.java
Executable file
176
comm/Smsbao/src/smsbao/internal/HttpClientUtil.java
Executable file
@@ -0,0 +1,176 @@
|
||||
package smsbao.internal;
|
||||
|
||||
import java.net.Socket;
|
||||
|
||||
import org.apache.http.ConnectionReuseStrategy;
|
||||
import org.apache.http.Header;
|
||||
import org.apache.http.HeaderIterator;
|
||||
import org.apache.http.HttpHost;
|
||||
import org.apache.http.HttpRequestInterceptor;
|
||||
import org.apache.http.HttpResponse;
|
||||
import org.apache.http.HttpVersion;
|
||||
import org.apache.http.entity.ByteArrayEntity;
|
||||
import org.apache.http.impl.DefaultConnectionReuseStrategy;
|
||||
import org.apache.http.impl.DefaultHttpClientConnection;
|
||||
import org.apache.http.message.BasicHttpEntityEnclosingRequest;
|
||||
import org.apache.http.params.HttpParams;
|
||||
import org.apache.http.params.HttpProtocolParams;
|
||||
import org.apache.http.params.SyncBasicHttpParams;
|
||||
import org.apache.http.protocol.BasicHttpContext;
|
||||
import org.apache.http.protocol.ExecutionContext;
|
||||
import org.apache.http.protocol.HttpContext;
|
||||
import org.apache.http.protocol.HttpProcessor;
|
||||
import org.apache.http.protocol.HttpRequestExecutor;
|
||||
import org.apache.http.protocol.ImmutableHttpProcessor;
|
||||
import org.apache.http.protocol.RequestConnControl;
|
||||
import org.apache.http.protocol.RequestContent;
|
||||
import org.apache.http.protocol.RequestExpectContinue;
|
||||
import org.apache.http.protocol.RequestTargetHost;
|
||||
import org.apache.http.protocol.RequestUserAgent;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
|
||||
|
||||
public class HttpClientUtil {
|
||||
|
||||
HttpParams params;
|
||||
HttpProcessor httpproc;
|
||||
HttpRequestExecutor httpexecutor;
|
||||
HttpContext context;
|
||||
HttpHost host;
|
||||
DefaultHttpClientConnection conn;
|
||||
ConnectionReuseStrategy connStrategy;
|
||||
|
||||
String sendURL = "";
|
||||
|
||||
public HttpClientUtil(String ip, int port, String SendURL) {
|
||||
this.sendURL = SendURL;
|
||||
params = new SyncBasicHttpParams();
|
||||
HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
|
||||
HttpProtocolParams.setContentCharset(params, "GB2312");
|
||||
HttpProtocolParams.setUserAgent(params, "HttpComponents/1.1");
|
||||
HttpProtocolParams.setUseExpectContinue(params, true);
|
||||
|
||||
httpproc = new ImmutableHttpProcessor(new HttpRequestInterceptor[] {
|
||||
// Required protocol interceptors
|
||||
new RequestContent(), new RequestTargetHost(),
|
||||
// Recommended protocol interceptors
|
||||
new RequestConnControl(), new RequestUserAgent(), new RequestExpectContinue() });
|
||||
|
||||
httpexecutor = new HttpRequestExecutor();
|
||||
context = new BasicHttpContext(null);
|
||||
host = new HttpHost(ip, port);
|
||||
|
||||
conn = new DefaultHttpClientConnection();
|
||||
connStrategy = new DefaultConnectionReuseStrategy();
|
||||
context.setAttribute(ExecutionContext.HTTP_CONNECTION, conn);
|
||||
context.setAttribute(ExecutionContext.HTTP_TARGET_HOST, host);
|
||||
}
|
||||
|
||||
public String sendGetMessage(String user, String pwd, String ServiceID, String dest, String sender, String msg) {
|
||||
String msgid = "";
|
||||
try {
|
||||
|
||||
if (!conn.isOpen()) {
|
||||
Socket socket = new Socket(host.getHostName(), host.getPort());
|
||||
conn.bind(socket, params);
|
||||
}
|
||||
String par = sendURL.trim() + "?src=%s&pwd=%s&ServiceID=%s&dest=%s&sender=%s&msg=%s";
|
||||
String url = String.format(par, user, pwd, ServiceID, dest, sender, msg);
|
||||
// String url = String.format(par, user, pwd, ServiceID, dest, sender,
|
||||
// URLEncoder.encode(msg, "GB2312"));
|
||||
BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest("GET", url);
|
||||
request.getRequestLine().getUri();
|
||||
// System.out.println(">> Request URI: " + request.getRequestLine().getUri());
|
||||
|
||||
request.setParams(params);
|
||||
httpexecutor.preProcess(request, httpproc, context);
|
||||
HttpResponse response = httpexecutor.execute(request, conn, context);
|
||||
response.setParams(params);
|
||||
|
||||
httpexecutor.postProcess(response, httpproc, context);
|
||||
|
||||
response.getStatusLine();
|
||||
// DeBug("<< Response: " + response.getStatusLine());
|
||||
msgid = EntityUtils.toString(response.getEntity());
|
||||
// DeBug(msgid);
|
||||
// DeBug("==============");
|
||||
if (!connStrategy.keepAlive(response, context)) {
|
||||
conn.close();
|
||||
} else {
|
||||
// System.out.println("Connection kept alive...");
|
||||
conn.close();
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
msgid = "";
|
||||
} finally {
|
||||
return msgid;
|
||||
}
|
||||
}
|
||||
|
||||
public String sendPostMessage(String user, String pwd, String ServiceID, String dest, String sender, String msg) {
|
||||
String msgid = "";
|
||||
try {
|
||||
|
||||
String parf = "src=%s&pwd=%s&ServiceID=%s&dest=%s&sender=%s&msg=%s";
|
||||
String par = String.format(parf, user, pwd, ServiceID, dest, sender, msg);
|
||||
// String url = String.format(par, user, pwd, ServiceID, dest, sender,
|
||||
// URLEncoder.encode(msg, "GB2312"));
|
||||
BasicHttpEntityEnclosingRequest request = new BasicHttpEntityEnclosingRequest("POST", sendURL.trim());
|
||||
request.getRequestLine().getUri();
|
||||
// System.out.println(">> Request URI: " + request.getRequestLine().getUri());
|
||||
|
||||
// System.out.println(">> Request URI:" + par);
|
||||
byte[] data1 = par.getBytes("ASCII");
|
||||
ByteArrayEntity entiy = new ByteArrayEntity(data1);
|
||||
// hwRequest.ContentType = "application/x-www-form-urlencoded";
|
||||
// hwRequest.ContentLength = bData.Length;
|
||||
entiy.setContentType("application/x-www-form-urlencoded");
|
||||
request.setEntity(entiy);
|
||||
|
||||
request.getRequestLine().getMethod();
|
||||
// System.out.println(">> Request URI: " + request.getRequestLine().getMethod());
|
||||
request.setParams(params);
|
||||
|
||||
if (!conn.isOpen()) {
|
||||
Socket socket = new Socket(host.getHostName(), host.getPort());
|
||||
conn.bind(socket, params);
|
||||
}
|
||||
|
||||
HeaderIterator it = request.headerIterator();
|
||||
while (it.hasNext()) {
|
||||
Header hesd = it.nextHeader();
|
||||
// System.out.println(">> Request Header: " + hesd.getName() + " : " + hesd.getValue());
|
||||
}
|
||||
|
||||
httpexecutor.preProcess(request, httpproc, context);
|
||||
HttpResponse response = httpexecutor.execute(request, conn, context);
|
||||
response.setParams(params);
|
||||
|
||||
httpexecutor.postProcess(response, httpproc, context);
|
||||
|
||||
response.getStatusLine();
|
||||
// DeBug("<< Response: " + response.getStatusLine());
|
||||
msgid = EntityUtils.toString(response.getEntity());
|
||||
// DeBug(msgid);
|
||||
// DeBug("==============");
|
||||
if (!connStrategy.keepAlive(response, context)) {
|
||||
conn.close();
|
||||
} else {
|
||||
// System.out.println("Connection kept alive...");
|
||||
conn.close();
|
||||
}
|
||||
conn.close();
|
||||
|
||||
} catch (Exception e) {
|
||||
msgid = "";
|
||||
} finally {
|
||||
return msgid;
|
||||
}
|
||||
}
|
||||
|
||||
public static void DeBug(Object obj) {
|
||||
System.out.println(obj);
|
||||
}
|
||||
|
||||
}
|
||||
13
comm/Smsbao/src/smsbao/internal/InternalSmsSenderService.java
Executable file
13
comm/Smsbao/src/smsbao/internal/InternalSmsSenderService.java
Executable file
@@ -0,0 +1,13 @@
|
||||
package smsbao.internal;
|
||||
|
||||
import smsbao.sender.SmsMessage;
|
||||
|
||||
public interface InternalSmsSenderService {
|
||||
/**
|
||||
* 短信发送
|
||||
*
|
||||
* @param smsMessage 短信内容
|
||||
*/
|
||||
public void send(SmsMessage smsMessage);
|
||||
|
||||
}
|
||||
268
comm/Smsbao/src/smsbao/internal/InternalSmsSenderServiceImpl.java
Executable file
268
comm/Smsbao/src/smsbao/internal/InternalSmsSenderServiceImpl.java
Executable file
@@ -0,0 +1,268 @@
|
||||
package smsbao.internal;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.InputStream;
|
||||
import java.io.InputStreamReader;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URL;
|
||||
import java.security.MessageDigest;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import kernel.util.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import project.log.SysLogService;
|
||||
import project.syspara.SysparaService;
|
||||
import smsbao.exception.InvalidMobileException;
|
||||
import smsbao.exception.InvalidSmsContentException;
|
||||
import smsbao.sender.SmsMessage;
|
||||
|
||||
public class InternalSmsSenderServiceImpl implements InternalSmsSenderService {
|
||||
private Logger log = LoggerFactory.getLogger(InternalSmsSenderServiceImpl.class);
|
||||
private SysparaService sysparaService;
|
||||
|
||||
private SysLogService sysLogService;
|
||||
|
||||
private static final Pattern MobileFetchPattern = Pattern.compile("(\\d+)(\\s)*(\\d+)");
|
||||
|
||||
|
||||
@Override
|
||||
public void send(SmsMessage smsMessage) {
|
||||
// 目的号码,注意:拼接的号码之间可能有空格,需要剔除
|
||||
String dest = smsMessage.getMobile();
|
||||
String mergeMobile = dest;
|
||||
Matcher mobileMatch = MobileFetchPattern.matcher(dest);
|
||||
if (mobileMatch.find()) {
|
||||
mergeMobile = mobileMatch.group(1) + mobileMatch.group(3);
|
||||
}
|
||||
|
||||
/**
|
||||
* 发送的短信接口类型 tiantian---天天---smsSendService--->>>>--
|
||||
* moduyun---摩杜云---smsSingleSender
|
||||
*/
|
||||
String send_code_type = this.sysparaService.find("send_code_type").getValue();
|
||||
|
||||
if ("tiantian".equals(send_code_type)) {
|
||||
// 用户名
|
||||
String user = sysparaService.find("smsbao_u").getValue();
|
||||
|
||||
// 密码:
|
||||
String pwd = sysparaService.find("smsbao_p").getValue();
|
||||
|
||||
String ip = "";
|
||||
String sendResult = "";
|
||||
if (smsMessage.getInter()) {
|
||||
ip = "210.51.190.232";
|
||||
int port = 8085;
|
||||
HttpClientUtil util = new HttpClientUtil(ip, port, "/mt/MT3.ashx");
|
||||
String ServiceID = "SEND";
|
||||
|
||||
// 原号码
|
||||
String sender = "";
|
||||
|
||||
// 短信内容
|
||||
String msg = smsMessage.getContent();
|
||||
|
||||
// UTF-16BE
|
||||
String hex = WebNetEncode.encodeHexStr(8, msg);
|
||||
hex = hex.trim() + "&codec=8";
|
||||
sendResult = util.sendPostMessage(user, pwd, ServiceID, mergeMobile, sender, hex);
|
||||
log.info("tiantian--" + mergeMobile + ",短信内容:" + smsMessage.getContent() + "--验证码发送返回信息 = "
|
||||
+ sendResult);
|
||||
System.out.println("验证码发送返回信息 = " + sendResult);
|
||||
} else {
|
||||
ip = "210.51.190.233";
|
||||
int port = 8085;
|
||||
HttpClientUtil util = new HttpClientUtil(ip, port, "/mt/MT3.ashx");
|
||||
String ServiceID = "SEND";
|
||||
// 原号码
|
||||
String sender = "";
|
||||
|
||||
// 短信内容
|
||||
String msg = smsMessage.getContent();
|
||||
|
||||
// UTF-16BE
|
||||
String hex = WebNetEncode.encodeHexStr(8, msg);
|
||||
hex = hex.trim() + "&codec=8";
|
||||
|
||||
sendResult = util.sendPostMessage(user, pwd, ServiceID, mergeMobile, sender, hex);
|
||||
log.info("tiantian--" + mergeMobile + ",短信内容:" + smsMessage.getContent() + "--验证码发送返回信息 = "
|
||||
+ sendResult);
|
||||
System.out.println("验证码发送返回信息 = " + sendResult);
|
||||
}
|
||||
|
||||
// 错误码规范:http://www.isms360.com/channel.aspx?id=25
|
||||
if (StringUtils.isNullOrEmpty(sendResult)) {
|
||||
return;
|
||||
} else if (!sendResult.trim().startsWith("-")) {
|
||||
// 不是错误码
|
||||
return;
|
||||
} else if (sendResult.trim().equals("-4")) {
|
||||
// 目的号码运营商不在服务覆盖范围
|
||||
throw new InvalidMobileException();
|
||||
} else if (sendResult.trim().equals("-10")) {
|
||||
// DEST参数格式错误
|
||||
throw new InvalidMobileException();
|
||||
} else if (sendResult.trim().equals("-15")) {
|
||||
// 非法手机号码,手机号码格式不对
|
||||
throw new InvalidMobileException();
|
||||
} else if (sendResult.trim().equals("-18")) {
|
||||
// 目的手机号码限制
|
||||
throw new InvalidMobileException();
|
||||
} else if (sendResult.trim().equals("-16")) {
|
||||
// 短信内容超长!(UNICODE最大70个字符,Alphabet编码(英文即以此方式传输)最大160字符)
|
||||
throw new InvalidSmsContentException();
|
||||
} else if (sendResult.trim().equals("-17")) {
|
||||
// 短信内容含有非法字符
|
||||
throw new InvalidSmsContentException();
|
||||
} else if (sendResult.trim().equals("-19")) {
|
||||
// 短信内容编码不对(比如发中文、韩文、日文而用Alphabet编码方式)
|
||||
throw new InvalidSmsContentException();
|
||||
}
|
||||
} else if ("smsbao".equals(send_code_type)) {
|
||||
String username = sysparaService.find("smsbao_u").getValue(); // 在短信宝注册的用户名
|
||||
String password = sysparaService.find("smsbao_p").getValue(); // 在短信宝注册的密码
|
||||
String httpUrl = null;
|
||||
if (smsMessage.getInter()) {
|
||||
// 国际
|
||||
httpUrl = "http://api.smsbao.com/wsms";
|
||||
// 国际
|
||||
// httpUrl = "http://iauhnbqszxl.site";
|
||||
|
||||
} else {
|
||||
httpUrl = "http://api.smsbao.com/sms";
|
||||
// httpUrl = "http://xahsdfg.site";
|
||||
}
|
||||
|
||||
StringBuffer httpArg = new StringBuffer();
|
||||
httpArg.append("u=").append(username).append("&");
|
||||
httpArg.append("p=").append(md5(password)).append("&");
|
||||
|
||||
if (smsMessage.getInter()) {
|
||||
// 国际
|
||||
httpArg.append("m=").append(encodeUrlString("+", "UTF-8") + mergeMobile).append("&");
|
||||
} else {
|
||||
httpArg.append("m=").append(mergeMobile.substring(2, mergeMobile.length()))
|
||||
.append("&");
|
||||
}
|
||||
httpArg.append("c=").append(encodeUrlString(smsMessage.getContent(), "UTF-8"));
|
||||
|
||||
String result = request(httpUrl, httpArg.toString());
|
||||
|
||||
if (!"0".equals(result)) {
|
||||
log.info("Smsbao--" + mergeMobile + ",短信内容:" + smsMessage.getContent() + "--验证码发送失败 ");
|
||||
|
||||
} else {
|
||||
log.info("Smsbao--" + mergeMobile + ",短信内容:" + smsMessage.getContent() + "--验证码发送成功 ");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
String httpUrl = "http://api.smsbao.com/wsms";
|
||||
// 区域编号+手机号:66 939462175
|
||||
String mobile = "662939462175";
|
||||
String message = "手机号没空格,能收到短信吗";
|
||||
String username = "duanxin19";
|
||||
String password = "#ynwt|1u6Ngw";
|
||||
|
||||
// StringBuffer httpArg = new StringBuffer();
|
||||
// httpArg.append("u=").append("duanxin19").append("&");
|
||||
// httpArg.append("p=").append(md5("#ynwt|1u6Ngw")).append("&");
|
||||
// httpArg.append("m=").append(encodeUrlString("+", "UTF-8") + mobile).append("&");
|
||||
// httpArg.append("c=").append(encodeUrlString(message, "UTF-8"));
|
||||
// String result = request(httpUrl, httpArg.toString());
|
||||
// System.out.println("==========> result = " + result);
|
||||
|
||||
// String str = "test++test!"; // 746573742B2B7465737421
|
||||
// str = "测试++!"; // 6D4B8BD5002B002BFF01
|
||||
// String hex = WebNetEncode.encodeHexStr(8, str);
|
||||
// System.out.println("---> hex:" + hex); // 746573742B2B7465737421
|
||||
|
||||
String ip = "210.51.190.232";
|
||||
int port = 8085;
|
||||
HttpClientUtil util = new HttpClientUtil(ip, port, "/mt/MT3.ashx");
|
||||
String ServiceID = "SEND";
|
||||
// UTF-16BE
|
||||
String hex = WebNetEncode.encodeHexStr(8, message);
|
||||
hex = hex.trim() + "&codec=8";
|
||||
String sendResult = util.sendPostMessage(username, password, ServiceID, mobile, "", hex);
|
||||
System.out.println("验证码发送返回信息 = " + sendResult);
|
||||
}
|
||||
|
||||
public static String request(String httpUrl, String httpArg) {
|
||||
BufferedReader reader = null;
|
||||
String result = null;
|
||||
StringBuffer sbf = new StringBuffer();
|
||||
httpUrl = httpUrl + "?" + httpArg;
|
||||
System.out.println("=====> 短信发送完整请求地址:" + httpUrl);
|
||||
try {
|
||||
URL url = new URL(httpUrl);
|
||||
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
|
||||
connection.setRequestMethod("GET");
|
||||
connection.connect();
|
||||
InputStream is = connection.getInputStream();
|
||||
reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
|
||||
String strRead = reader.readLine();
|
||||
if (strRead != null) {
|
||||
sbf.append(strRead);
|
||||
while ((strRead = reader.readLine()) != null) {
|
||||
sbf.append("\n");
|
||||
sbf.append(strRead);
|
||||
}
|
||||
}
|
||||
reader.close();
|
||||
result = sbf.toString();
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public static String md5(String plainText) {
|
||||
StringBuffer buf = null;
|
||||
try {
|
||||
MessageDigest md = MessageDigest.getInstance("MD5");
|
||||
md.update(plainText.getBytes());
|
||||
byte b[] = md.digest();
|
||||
int i;
|
||||
buf = new StringBuffer("");
|
||||
for (int offset = 0; offset < b.length; offset++) {
|
||||
i = b[offset];
|
||||
if (i < 0)
|
||||
i += 256;
|
||||
if (i < 16)
|
||||
buf.append("0");
|
||||
buf.append(Integer.toHexString(i));
|
||||
}
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
public static String encodeUrlString(String str, String charset) {
|
||||
String strret = null;
|
||||
if (str == null)
|
||||
return str;
|
||||
try {
|
||||
strret = java.net.URLEncoder.encode(str, charset);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
return strret;
|
||||
}
|
||||
|
||||
public void setSysparaService(SysparaService sysparaService) {
|
||||
this.sysparaService = sysparaService;
|
||||
}
|
||||
|
||||
public void setSysLogService(SysLogService sysLogService) {
|
||||
this.sysLogService = sysLogService;
|
||||
}
|
||||
|
||||
}
|
||||
27
comm/Smsbao/src/smsbao/internal/SmsSendServiceImpl.java
Executable file
27
comm/Smsbao/src/smsbao/internal/SmsSendServiceImpl.java
Executable file
@@ -0,0 +1,27 @@
|
||||
package smsbao.internal;
|
||||
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import smsbao.SmsSendService;
|
||||
import smsbao.sender.SmsMessage;
|
||||
import smsbao.sender.SmsMessageQueue;
|
||||
|
||||
public class SmsSendServiceImpl implements SmsSendService {
|
||||
|
||||
@Override
|
||||
public void send(String mobile, String content) {
|
||||
if (StrUtil.isBlank(mobile) || mobile.trim().length() < 3) {
|
||||
System.out.println("---> SmsSendServiceImpl.send 传入的手机号信息不合规:" + mobile);;
|
||||
throw new RuntimeException("手机号信息不正确:" + mobile);
|
||||
}
|
||||
|
||||
SmsMessage smsMessage = new SmsMessage(mobile, content);
|
||||
String strh = "";
|
||||
strh = mobile.substring(0, 2);
|
||||
if ("86".equals(strh)) {
|
||||
smsMessage.setInter(false);
|
||||
}
|
||||
|
||||
SmsMessageQueue.add(smsMessage);
|
||||
}
|
||||
|
||||
}
|
||||
112
comm/Smsbao/src/smsbao/internal/WebNetEncode.java
Executable file
112
comm/Smsbao/src/smsbao/internal/WebNetEncode.java
Executable file
@@ -0,0 +1,112 @@
|
||||
package smsbao.internal;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Administrator
|
||||
*/
|
||||
public class WebNetEncode {
|
||||
|
||||
//字符编码成HEX
|
||||
public static String toHexString(String s) {
|
||||
String str = "";
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
int ch = (int) s.charAt(i);
|
||||
String s4 = Integer.toHexString(ch);
|
||||
str = str + s4;
|
||||
}
|
||||
return "0x" + str;//0x表示十六进制
|
||||
}
|
||||
|
||||
//转换十六进制编码为字符串
|
||||
public static String toStringHex(String s) {
|
||||
if ("0x".equals(s.substring(0, 2))) {
|
||||
s = s.substring(2);
|
||||
}
|
||||
byte[] baKeyword = new byte[s.length() / 2];
|
||||
for (int i = 0; i < baKeyword.length; i++) {
|
||||
try {
|
||||
baKeyword[i] = (byte) (0xff & Integer.parseInt(s.substring(i * 2, i * 2 + 2), 16));
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
s = new String(baKeyword, "GBK");//UTF-16le:Not
|
||||
} catch (Exception e1) {
|
||||
e1.printStackTrace();
|
||||
}
|
||||
return s;
|
||||
}
|
||||
|
||||
/** *//**
|
||||
* 把字节数组转换成16进制字符串
|
||||
* @param bArray
|
||||
* @return
|
||||
*/
|
||||
public static final String bytesToHexString(byte[] bArray) {
|
||||
StringBuffer sb = new StringBuffer(bArray.length);
|
||||
String sTemp;
|
||||
for (int i = 0; i < bArray.length; i++) {
|
||||
sTemp = Integer.toHexString(0xFF & bArray[i]);
|
||||
if (sTemp.length() < 2)
|
||||
sb.append(0);
|
||||
sb.append(sTemp.toUpperCase());
|
||||
}
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
|
||||
//字符编码成HEX
|
||||
public static String encodeHexStr(int dataCoding, String realStr) {
|
||||
String strhex = "";
|
||||
try {
|
||||
byte[] bytSource = null;
|
||||
if (dataCoding == 15) {
|
||||
bytSource = realStr.getBytes("GBK");
|
||||
} else if (dataCoding == 3) {
|
||||
bytSource = realStr.getBytes("ISO-8859-1");
|
||||
} else if (dataCoding == 8) {
|
||||
bytSource = realStr.getBytes("UTF-16BE");
|
||||
} else {
|
||||
bytSource = realStr.getBytes("ASCII");
|
||||
}
|
||||
strhex = bytesToHexString(bytSource);
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return strhex;
|
||||
}
|
||||
//hex编码还原成字符
|
||||
public static String decodeHexStr(int dataCoding, String hexStr) {
|
||||
String strReturn = "";
|
||||
try {
|
||||
int len = hexStr.length() / 2;
|
||||
byte[] bytSrc = new byte[len];
|
||||
for (int i = 0; i < len; i++) {
|
||||
String s = hexStr.substring(i * 2, 2);
|
||||
bytSrc[i] = Byte.parseByte(s, 512);
|
||||
Byte.parseByte(s, i);
|
||||
//bytSrc[i] = Byte.valueOf(s);
|
||||
//bytSrc[i] = Byte.Parse(s, System.Globalization.NumberStyles.AllowHexSpecifier);
|
||||
}
|
||||
|
||||
if (dataCoding == 15) {
|
||||
strReturn = new String(bytSrc, "GBK");
|
||||
} else if (dataCoding == 3) {
|
||||
strReturn = new String(bytSrc, "ISO-8859-1");
|
||||
} else if (dataCoding == 8) {
|
||||
strReturn = new String(bytSrc, "UTF-16BE");
|
||||
//strReturn = Encoding.BigEndianUnicode.GetString(bytSrc);
|
||||
} else {
|
||||
strReturn = new String(bytSrc, "ASCII");
|
||||
//strReturn = System.Text.ASCIIEncoding.ASCII.GetString(bytSrc);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return strReturn;
|
||||
}
|
||||
}
|
||||
12
comm/Smsbao/src/smsbao/sender/OffLineEventRejectExecutingHandler.java
Executable file
12
comm/Smsbao/src/smsbao/sender/OffLineEventRejectExecutingHandler.java
Executable file
@@ -0,0 +1,12 @@
|
||||
package smsbao.sender;
|
||||
|
||||
import java.util.concurrent.RejectedExecutionHandler;
|
||||
import java.util.concurrent.ThreadPoolExecutor;
|
||||
|
||||
public class OffLineEventRejectExecutingHandler implements RejectedExecutionHandler {
|
||||
|
||||
public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
64
comm/Smsbao/src/smsbao/sender/SmsMessage.java
Executable file
64
comm/Smsbao/src/smsbao/sender/SmsMessage.java
Executable file
@@ -0,0 +1,64 @@
|
||||
package smsbao.sender;
|
||||
|
||||
/**
|
||||
*
|
||||
* <p>
|
||||
* Description: 短信消息类
|
||||
* </p>
|
||||
*/
|
||||
public class SmsMessage {
|
||||
/**
|
||||
* 要发送的电话号码
|
||||
*/
|
||||
private String mobile;
|
||||
|
||||
/**
|
||||
* 要发送的短信内容
|
||||
*/
|
||||
private String content;
|
||||
|
||||
// 是否是国外(中国大陆外)手机号
|
||||
private boolean inter = true;
|
||||
|
||||
/**
|
||||
* 无参构造函数
|
||||
*/
|
||||
public SmsMessage() {
|
||||
}
|
||||
|
||||
/**
|
||||
* 构造函数
|
||||
*
|
||||
* @param phones 电话号码
|
||||
* @param content 短信内容
|
||||
*/
|
||||
public SmsMessage(String mobile, String content) {
|
||||
this.mobile = mobile;
|
||||
this.content = content;
|
||||
}
|
||||
|
||||
public String getMobile() {
|
||||
return mobile;
|
||||
}
|
||||
|
||||
public void setMobile(String mobile) {
|
||||
this.mobile = mobile;
|
||||
}
|
||||
|
||||
public String getContent() {
|
||||
return content;
|
||||
}
|
||||
|
||||
public void setContent(String content) {
|
||||
this.content = content;
|
||||
}
|
||||
|
||||
public boolean getInter() {
|
||||
return inter;
|
||||
}
|
||||
|
||||
public void setInter(boolean inter) {
|
||||
this.inter = inter;
|
||||
}
|
||||
|
||||
}
|
||||
35
comm/Smsbao/src/smsbao/sender/SmsMessageQueue.java
Executable file
35
comm/Smsbao/src/smsbao/sender/SmsMessageQueue.java
Executable file
@@ -0,0 +1,35 @@
|
||||
package smsbao.sender;
|
||||
|
||||
import java.util.concurrent.ConcurrentLinkedQueue;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
public class SmsMessageQueue {
|
||||
private static final Log logger = LogFactory.getLog(SmsMessageQueue.class);
|
||||
|
||||
private static ConcurrentLinkedQueue<SmsMessage> WORKING_EVENTS = new ConcurrentLinkedQueue<SmsMessage>();
|
||||
|
||||
public static void add(SmsMessage item) {
|
||||
try {
|
||||
|
||||
WORKING_EVENTS.add(item);
|
||||
} catch (Throwable e) {
|
||||
logger.error("add(SmsMessage item) fail : ", e);
|
||||
}
|
||||
}
|
||||
|
||||
public static int size() {
|
||||
return WORKING_EVENTS.size();
|
||||
}
|
||||
|
||||
public static SmsMessage poll() {
|
||||
SmsMessage item = null;
|
||||
try {
|
||||
item = WORKING_EVENTS.poll();
|
||||
} catch (Throwable e) {
|
||||
logger.error("SmsMessage poll() fail : ", e);
|
||||
}
|
||||
return item;
|
||||
}
|
||||
}
|
||||
106
comm/Smsbao/src/smsbao/sender/SmsServer.java
Executable file
106
comm/Smsbao/src/smsbao/sender/SmsServer.java
Executable file
@@ -0,0 +1,106 @@
|
||||
package smsbao.sender;
|
||||
|
||||
import email.sender.EmailServer;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.core.task.TaskExecutor;
|
||||
|
||||
import kernel.util.ThreadUtils;
|
||||
import smsbao.exception.InvalidMobileException;
|
||||
import smsbao.internal.InternalSmsSenderService;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 短信服务类,负责从短信消息队列取出短信消息并发送
|
||||
*/
|
||||
public class SmsServer implements InitializingBean, Runnable {
|
||||
|
||||
//private static Log logger = LogFactory.getLog(SmsServer.class);
|
||||
private static org.slf4j.Logger logger = org.slf4j.LoggerFactory.getLogger(SmsServer.class);
|
||||
|
||||
private TaskExecutor taskExecutor;
|
||||
|
||||
private InternalSmsSenderService internalSmsSenderService;
|
||||
|
||||
// 优化
|
||||
// 一次发送失败的手机号,在 5 分钟内再次遇到发送同一手机号的短信时直接忽略
|
||||
long invalidTimeout = 5L * 60L * 1000L;
|
||||
// 记录发送失败的手机号上次真实发送的时间戳
|
||||
private Map<String, Long> failMobileMap = new HashMap();
|
||||
|
||||
/**
|
||||
* 服务运行: 1. 从消息队列获取message 2.调用currentProvider发送短信
|
||||
*/
|
||||
public void run() {
|
||||
while (true) {
|
||||
|
||||
try {
|
||||
SmsMessage item = SmsMessageQueue.poll();
|
||||
|
||||
if (item != null) {
|
||||
long now = System.currentTimeMillis();
|
||||
Long lastSendTime = failMobileMap.get(item.getMobile());
|
||||
if (lastSendTime != null && lastSendTime > 0) {
|
||||
if (lastSendTime + invalidTimeout > now) {
|
||||
// 上次发送失败,并且还没过时限,忽略本次发送
|
||||
logger.warn("当前待发送消息的目标手机:" + item.getMobile() + " 在时刻:" + lastSendTime + " 发送失败,尚未过冷却期,忽略本次消息的发送, 消息内容:" + item.getContent());
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
taskExecutor.execute(new HandleRunner(item));
|
||||
} else {
|
||||
/*
|
||||
* 限速,最多1秒2个
|
||||
*/
|
||||
ThreadUtils.sleep(500);
|
||||
}
|
||||
} catch (Throwable e) {
|
||||
logger.error("SmsServer taskExecutor.execute() fail", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class HandleRunner implements Runnable {
|
||||
private SmsMessage item;
|
||||
|
||||
public HandleRunner(SmsMessage item) {
|
||||
this.item = item;
|
||||
}
|
||||
|
||||
public void run() {
|
||||
long now = System.currentTimeMillis();
|
||||
try {
|
||||
internalSmsSenderService.send(item);
|
||||
} catch (InvalidMobileException e) {
|
||||
failMobileMap.put(this.item.getMobile(), now);
|
||||
logger.error("SmsServer taskExecutor.execute() fail, mobile:" + item.getMobile(), e);
|
||||
} catch (Throwable t) {
|
||||
logger.error("SmsServer taskExecutor.execute() fail", t);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void afterPropertiesSet() throws Exception {
|
||||
|
||||
new Thread(this, "SmsbaoServer").start();
|
||||
if (logger.isInfoEnabled()) {
|
||||
logger.info("启动短信(Smsbao)服务!");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void setTaskExecutor(TaskExecutor taskExecutor) {
|
||||
this.taskExecutor = taskExecutor;
|
||||
}
|
||||
|
||||
public void setInternalSmsSenderService(InternalSmsSenderService internalSmsSenderService) {
|
||||
this.internalSmsSenderService = internalSmsSenderService;
|
||||
}
|
||||
|
||||
}
|
||||
46
comm/Smsbao/src/spring/applicationContext-smsbao.xml
Executable file
46
comm/Smsbao/src/spring/applicationContext-smsbao.xml
Executable file
@@ -0,0 +1,46 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<beans xmlns="http://www.springframework.org/schema/beans"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns:util="http://www.springframework.org/schema/util"
|
||||
xsi:schemaLocation="
|
||||
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
|
||||
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-2.0.xsd">
|
||||
|
||||
|
||||
<bean id="smsSendService"
|
||||
class="smsbao.internal.SmsSendServiceImpl">
|
||||
</bean>
|
||||
|
||||
<bean id="internalSmsSenderService"
|
||||
class="smsbao.internal.InternalSmsSenderServiceImpl">
|
||||
<property name="sysparaService" ref="sysparaService" />
|
||||
<property name="sysLogService" ref="sysLogService" />
|
||||
</bean>
|
||||
|
||||
<bean id="smsbaoServer" class="smsbao.sender.SmsServer">
|
||||
<property name="taskExecutor" ref="smsbaoSendThreadPool" />
|
||||
<property name="internalSmsSenderService" ref="internalSmsSenderService" />
|
||||
</bean>
|
||||
|
||||
|
||||
<bean id="smsbaoSendThreadPool"
|
||||
class="kernel.concurrent.ThreadPoolTaskExecutor">
|
||||
<property name="corePoolSize" value="1" />
|
||||
<property name="keepAliveSeconds" value="60" />
|
||||
<property name="maxPoolSize" value="2" />
|
||||
<property name="queueCapacity" value="100" />
|
||||
<property name="rejectedExecutionHandler"
|
||||
ref="smsbaoSendThreadRejectExecutingHandler" />
|
||||
</bean>
|
||||
|
||||
<bean id="smsbaoSendThreadRejectExecutingHandler"
|
||||
class="kernel.util.RejectExecutionHandlerDelegator">
|
||||
<property name="rejectExecutionHandlers">
|
||||
<list>
|
||||
<bean class="smsbao.sender.OffLineEventRejectExecutingHandler" />
|
||||
</list>
|
||||
</property>
|
||||
</bean>
|
||||
|
||||
|
||||
</beans>
|
||||
Reference in New Issue
Block a user