Android シミュレーション サーバーがメッセージを送信するためのソケット通信ツール
1. 背景
背景の紹介:
PowerMsg などの一部のシナリオでは、サーバーに依存してクライアントにメッセージを送信する必要があり、サーバーはメッセージ タイプを送信し、クライアントはそのタイプを解析して対応するアクションを実行します。たとえば、ライブで質問に回答するには、サーバーに依存してメッセージを送信する必要があり、クライアントはルールに従って質問を表示するためにメッセージを取得する必要があります。
2. 問題点の説明
サーバーからのメッセージの送信に依存しているため、クライアントは非常に受動的であり、対応するメッセージを積極的に構築することはできません。したがって、サーバー側のメッセージ配信をシミュレートできるツールが緊急に必要とされており、ソケット ツールはそこから生まれました。
3. ツールの原理
コンピューターはソケット サーバーをシミュレートし、Android アプリケーションはソケット クライアントをシミュレートし、ソケット ツールを通じてクライアントにメッセージを送信します。
4. ソケットクライアントコード
if (ConfigHelper.getInstance().getAppConfig().isDebug()
&& PreferenceCommon.getInstance().getBoolean("is_xx_socket_enable", false)) {
Socket2PowerMsgTool.getInstance().setLiveMessageParserCallBack(this)
Socket2PowerMsgTool.getInstance().startSocket()
}
Socket2PowerMsgTool.java
public class Socket2PowerMsgTool {
private static final String SocketIP = "30.5.195.154";
private static final int SocketPort = 7654;
Socket socket = null;
private String recv_buff = null;
private static Socket2PowerMsgTool instance = new Socket2PowerMsgTool();
private Socket2PowerMsgTool(){
}
public static Socket2PowerMsgTool getInstance(){
return instance;
}
private ILiveMessageParserCallBack mLiveMessageParserCallBack;
public void setLiveMessageParserCallBack(ILiveMessageParserCallBack mLiveMessageParserCallBack) {
this.mLiveMessageParserCallBack = mLiveMessageParserCallBack;
}
public void startSocket() {
String ip = PreferenceCommon.getInstance().getString("live_mock_socket_ip", "");
String portString = PreferenceCommon.getInstance().getString("live_mock_socket_port", "");
if (TextUtils.isEmpty(ip) || TextUtils.isEmpty(portString)) {
return;
}
int port = Integer.parseInt(portString);
new Thread(new Runnable() {
@Override
public void run() {
try {
//连接到指定的IP和端口号,并指定10s的超时时间
socket = new Socket();
socket.connect(new InetSocketAddress(ip, port), 10000);
if (socket != null && socket.isConnected()) {
while(true) {
recv();
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}).start();
}
private void recv() {
InputStream inputStream = null;
try {
inputStream = socket.getInputStream();
} catch (IOException e) {
e.printStackTrace();
}
if (inputStream != null){
try {
byte[] buffer = new byte[1024];
int count = inputStream.read(buffer);//count是传输的字节数
recv_buff = new String(buffer);//socket通信传输的是byte类型,需要转为String类型
recv_buff = recv_buff.substring(0, count);
String regex="^[A-Fa-f0-9]+$";
if (recv_buff.matches(regex)) {
recv_buff = hexStringToString(recv_buff);
}
Log.i("ruihan-test", recv_buff);
if (!TextUtils.isEmpty(recv_buff) && isJSONString(recv_buff)) {
MockPowerMsgEntity mockPowerMsgEntity = FastJsonUtil.json2pojo(recv_buff, MockPowerMsgEntity.class);
if(mockPowerMsgEntity != null) {
if (mockPowerMsgEntity.type == 1) {
if (mLiveMessageParserCallBack != null) {
mLiveMessageParserCallBack
.msgLiveOriginalJsonPaserCallBack(FastJsonUtil.pojo2json(mockPowerMsgEntity.data));
}
} else if (mockPowerMsgEntity.type == 2) {
if (mLiveMessageParserCallBack != null) {
mLiveMessageParserCallBack
.msgLikeParserCallback(JSONObject.toJavaObject(mockPowerMsgEntity.data, MsgLike.class));
}
} else if (mockPowerMsgEntity.type == 3) {
if (mLiveMessageParserCallBack != null) {
mLiveMessageParserCallBack
.msgLiveStatusParserCallback(FastJsonUtil.pojo2json(mockPowerMsgEntity.data),
JSONObject.toJavaObject(mockPowerMsgEntity.data, MsgLiveStatus.class));
}
}
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
private String hexStringToString(String s) {
if (s == null || s.equals("")) {
return null;
}
s = s.replace(" ", "");
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, "UTF-8");
new String();
} catch (Exception e1) {
e1.printStackTrace();
}
return s;
}
public boolean isJSONString(String str) {
boolean result = false;
try {
Object obj = JSONObject.parse(str);
result = true;
} catch (Exception e) {
result = false;
}
return result;
}
public void closeSocket() {
try {
if (socket!= null) {
socket.close();
socket = null;
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
インターフェイス コールバックの実装:
override fun msgLiveOriginalJsonPaserCallBack(jsonString: String?) {
val isBenefitType = LiveRoomUtils.isBenefitCoupon(jsonString)
if (isBenefitType) {
// TODO
return
}
val isOldHighLightType = LiveRoomUtils.isOldHighLightType(jsonString)
if (isOldHighLightType) {
return
}
val isNativeHighLight = LiveRoomUtils.isNativeHighLight(jsonString, mLiveId)
if (isNativeHighLight) {
// TODO
}
val isAnswerType = LiveRoomUtils.isAnswerType(jsonString)
if (isAnswerType) {
// TODO
}
eventBusFire(WeexEventConstants.WEEX_EVENT_BIND_POWER_MESSAGE_CALLBACK,
JSONObject.parse(jsonString))
}
MockPowerMsgEntity.java
public class MockPowerMsgEntity implements Serializable {
/**
* type 1 2 3 分别对应下列3个回调
* fun msgLiveOriginalJsonPaserCallBack(jsonString: String?)
* fun msgLikeParserCallback(msgLike: MsgLike)
* fun msgLiveStatusParserCallback(jsonString: String?, msgLiveStatus: MsgLiveStatus?)
*
*/
public int type; // 对应 PowerMsg 三种回调类型
public JSONObject data; // 数据类型
}
5. ソケットサーバーツール
1. ソフトウェアをインストールする
ソフトウェアのインストール: SSokit
SSokit アドレス
2. 手順の参考
1. ソフトウェアを開き、現在のコンピュータ アドレスを自動的に識別し、ポート番号を手動で入力します (例: 7653) 2.
電話を振り、IP とポート番号を入力し、ボタンをクリックしてシミュレートされた PowerMsg を設定し、スイッチをオンにします。
3. 接続されていると表示します。
4. 右側の入力ボックスにテキストを送信します。フォーマット参照:
{
"type": 1,
"data": {
"uniqueKey":"1629428186122:-875441502",
"type":1304,
"body":{
"questionId":12312312312312
}
}
携帯端末設定参考: