| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288 |
- package com.cnd3b.common.websocket;
- import com.alibaba.fastjson.JSONObject;
- import com.cnd3b.common.BaseClass;
- import com.cnd3b.common.D3BReturnObject_Err;
- import com.cnd3b.common.data.Row;
- import com.cnd3b.common.parameter.parameter;
- import javax.websocket.*;
- import javax.websocket.server.PathParam;
- import javax.websocket.server.ServerEndpoint;
- import java.io.IOException;
- import java.lang.reflect.Constructor;
- import java.lang.reflect.InvocationTargetException;
- import java.lang.reflect.Method;
- import java.util.Calendar;
- import java.util.Date;
- import java.util.concurrent.ConcurrentHashMap;
- //ws://127.0.0.1:8080/samex/webSocket/829fef9884bbf7f9fb9c51499d7b332f
- @ServerEndpoint("/webSocket/{accesstoken}")
- public class WebClientSocket extends BaseClass {
- private Session session;
- //当前连接对象的账号ID
- private long userid;
- private Row userRow;
- private String accesstoken;
- private Date createdate;
- /**
- * 连接开启
- *
- * @param accesstoken
- * @param session
- * @throws IOException
- */
- @OnOpen
- private void onOpen(@PathParam("accesstoken") String accesstoken, Session session) throws IOException {
- this.session = session;
- this.accesstoken = accesstoken;
- createdate = getDateTime();
- if (parameter.tokenlist.containsKey(accesstoken)) {
- userid = parameter.tokenlist.get(accesstoken);
- userRow = parameter.userIdList.get(userid);
- } else {
- JSONObject methodobject = new JSONObject();
- methodobject.put("type", "err");
- methodobject.put("msg", "请登陆");
- sendSystemMessage(methodobject);
- return;
- }
- if (parameter.websocketClients.containsKey(userid)) {
- parameter.websocketClients.get(userid).put(accesstoken, this);
- } else {
- ConcurrentHashMap<String, WebClientSocket> map = new ConcurrentHashMap<>();
- map.put(accesstoken, this);
- parameter.websocketClients.put(userid, map);
- }
- parameter.loginDate.put(userid, createdate);
- }
- /**
- * 连接关闭
- *
- * @throws IOException
- */
- @OnClose
- private void onClose() throws IOException {
- if (parameter.websocketClients.containsKey(userid)) {
- parameter.websocketClients.get(userid).remove(accesstoken);
- if (parameter.websocketClients.get(userid).isEmpty()) {
- parameter.websocketClients.remove(userid);
- }
- }
- }
- /**
- * {
- * "dialogid":1,//对话框id
- * "messagetype":"text",//消息类型
- * "description":"",//消息摘要
- * "data":{
- * "message":""//文字正文,
- * }
- * },
- * {
- * "dialogid":1,
- * "messagetype":"file",//text,file,data,image,
- * "description":"",
- * "data":{
- * "ownertable":"",
- * "ownerid":"",
- * "serialnumber":"",
- * "postfix":"",
- * "fobsurl":"",
- * "fobsurl_minimage":"",
- * "fobsurl_hls":"",
- * "fdocument":""
- * }
- * },
- * {
- * "dialogid":1,
- * "messagetype":"data",//text,file,data,image
- * "description":"",
- * "data":{
- * "type":"",
- * "ownertable":"",
- * "ownerid":""
- * }
- * }
- *
- * @param messageObject
- * @throws IOException
- */
- /**
- * 消息接收
- *
- * @param RequestContent
- * @throws IOException
- */
- @OnMessage
- private void onMessage(String RequestContent) throws IOException {
- /**
- * 验证请求正文是否为规范的SONObject格式
- */
- JSONObject requestcontent = null;
- try {
- requestcontent = JSONObject.parseObject(RequestContent);
- } catch (Exception e) {
- return;
- }
- /**
- * 验证请求正文中是否包含必填的键值
- */
- String[] mustkeys = {"classname", "method", "content"};
- for (String mustkey : mustkeys) {
- if (!requestcontent.containsKey(mustkey)) {
- return;
- }
- }
- /**
- * 验证请求正文中的content是否为规范的SONObject格式
- */
- JSONObject content = new JSONObject();
- try {
- content = requestcontent.getJSONObject("content");
- } catch (Exception e) {
- return;
- }
- /**
- * 验证正文中的token是否有效
- */
- String className = requestcontent.getString("classname");
- parameter.requesttime.put(accesstoken, Calendar.getInstance().getTime());
- String methodName = requestcontent.getString("method");
- if (content.isEmpty()) {
- content = new JSONObject();
- }
- content.put("$classname", className);
- content.put("$method", methodName);
- content.put("$accesstoken", accesstoken);
- String key = className + "." + methodName;
- String result;
- Object obj = null;
- try {
- long starttimes = Calendar.getInstance().getTimeInMillis();
- /**
- * 执行请求方法
- */
- Class clz = Class.forName("com.cnd3b.websocketcontroller." + className);
- Constructor cla = clz.getDeclaredConstructor(JSONObject.class);
- obj = cla.newInstance(content);
- Method method = obj.getClass().getDeclaredMethod(methodName);
- result = (String) method.invoke(obj);
- long endtimes = Calendar.getInstance().getTimeInMillis();
- saveCallMethodMsg(key, true, endtimes - starttimes);
- } catch (ClassNotFoundException e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("找不到指定的类" + className).toString();
- } catch (InstantiationException e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("类" + className + "实例化异常").toString();
- } catch (IllegalAccessException e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("类" + className + "安全权限异常,可能该类为非public类").toString();
- } catch (NoSuchMethodException e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("找不到指定的类" + className + "的" + methodName + "方法").toString();
- } catch (IllegalArgumentException e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("类" + className + "的" + methodName + "方法参数不合法").toString();
- } catch (InvocationTargetException e) {
- Throwable targetException = e.getTargetException();
- D3BReturnObject_Err d3BReturnObject_err = new D3BReturnObject_Err();
- d3BReturnObject_err.setErrMsg(targetException.getMessage());
- result = d3BReturnObject_err.toString();
- } catch (Exception e) {
- e.printStackTrace();
- result = new D3BReturnObject_Err().setErrMsg("发生未知异常" + e.getMessage()).toString();
- } finally {
- if (obj != null) {
- try {
- obj.getClass().getMethod("p2ServerSystemPaoSetClose").invoke(obj);
- } catch (Exception e) {
- e.printStackTrace();
- }
- }
- }
- return;
- }
- /**
- * 记录请求数
- *
- * @param key
- * @param fromdb
- * @param time
- */
- private void saveCallMethodMsg(String key, boolean fromdb, long time) {
- long callmethodTimes = parameter.callmethodTimes.containsKey(key) ? parameter.callmethodTimes.get(key) : 0L;
- //更新请求总数
- parameter.callmethodTimes.put(key, callmethodTimes + 1L);
- //最新请求时间
- parameter.lastcallmethodtime.put(key, Calendar.getInstance().getTime());
- //从缓存获取的次数
- long callmethod_fromcacheTimes = parameter.callmethod_fromcacheTimes.containsKey(key) ? parameter.callmethod_fromcacheTimes.get(key) : 0L;
- if (!fromdb) {
- /**
- * 方法请求从缓存获取次数
- */
- parameter.callmethod_fromcacheTimes.put(key, callmethod_fromcacheTimes + 1L);
- } else {
- /**
- * 方法请求查询最新耗时
- */
- parameter.callmethodLastTimeLong.put(key, time);
- long totaltimes = callmethodTimes - callmethod_fromcacheTimes;
- /**
- * 方法请求查询平均时间
- */
- long callmethodTimeLong = parameter.callmethodTimeLong.containsKey(key) ? parameter.callmethodTimeLong.get(key) : 0L;
- parameter.callmethodTimeLong.put(key, (callmethodTimeLong * totaltimes + time) / (totaltimes + 1));
- }
- }
- @OnError
- private void onError(Session session, Throwable error) {
- error.printStackTrace();
- }
- /**
- * 对当前连接发送对话框消息
- *
- * @param message
- */
- public void sendDialogMessage(JSONObject message) {
- JSONObject object = new JSONObject();
- object.put("msgtype", "imdialog");
- object.put("message", message);
- session.getAsyncRemote().sendText(object.toJSONString());
- }
- /**
- * 对当前连接发送系统消息
- *
- * @param message
- */
- public void sendSystemMessage(JSONObject message) {
- JSONObject object = new JSONObject();
- object.put("msgtype", "system");
- object.put("message", message);
- session.getAsyncRemote().sendText(object.toJSONString());
- }
- }
|