WebSocket API
Websocket连接概述
accountSubscribe:订阅账号事件
accountUnsubscribe:取消订阅账号事件
logsSubscribe:订阅日志事件
logsUnsubscribe:取消订阅日志事件
programSubscribe:订阅程序事件
programUnsubscribe:取消订阅程序事件
signatureSubscribe:订阅签名事件
signatureUnsubscribe:取消订阅签名事件
slotSubscribe:订阅槽位事件
slotUnsubscribe:取消订阅槽位事件
安装包:
下载包
npm install --save express
npm install websocket
如果下载这监听的话:reconnecting 就会自带心跳机制不需从新加
(缺点只能TypeScript中使用)
npm install --save reconnecting-websocket
[reconnecting 具体使用方式](https://blog.csdn.net/m1s2q3l4/article/details/121556091?spm=1001.2014.3001.5501)
HTML页面实现方式:(获取的数据都是实时监听到的长链接)
<html>
<head>
<!--加入下面这行代码避免出现中文乱码-->
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
</head>
<body>
<div id="result"></div>
</body>
<script type="text/javascript">
//想要监听的地址
var socketUrl = `ws://api.devnet`;
var socket = new WebSocket(socketUrl);
//连接打开事件
//订阅日志事件logsSubscribe
//mentions这个参数相当于(交易号)
socket.onopen = function() {
console.log("Socket 已打开");
let rpc = {
jsonrpc: "2.0",
id: 1,
method: "logsSubscribe",
"params": [
{
"mentions": [ "Ef2FSTK4Jk7Yc3AiKoWhDrhdPdATTxPAngRRNSgDTdEY" ]
},
{
"commitment": "finalized"
}
]
//这个属于监听全部信息
//"params": [ "all" ]
}
socket.send(JSON.stringify(rpc));
};
//收到消息事件
socket.onmessage = function(msg) {
console.log("接受到消息:" + msg.data);
var result = document.getElementById("result").innerHTML;
result = result + "<br/>接收消息:" + msg.data;
document.getElementById("result").innerHTML = result;
};
//连接关闭事件
socket.onclose = function() {};
//发生了错误事件
socket.onerror = function() {
console.log("发生错误!");
}
</script>
</html>
TypeScript:中的监听(加入了心跳检查(防止断联))
执行的方式是:node 文件名,执行成功效果
const W3CWebSocket = require('websocket').w3cwebsocket;
/**
* https://docs.solana.com/developing/clients/jsonrpc-api
*
* websocket心跳重连机制
* https://www.cnblogs.com/tugenhua0707/p/8648044.html
*/
//建立w3c标准的websocket对象,传入wss地址
// let client = new W3CWebSocket('ws://solana.com')
// client.onerror = (e) =>{
// console.log('回调函数');
// console.log(e)
// };
// //收到消息的处理函数
// client.onmessage = (e)=> {
// if (typeof e.data === 'string') {
// var jsonData = JSON.parse(e.data)
// // console.log(jsonData) //打印全部信息
// if (jsonData.params){
// console.log("logs",jsonData.params.result.value.logs);
// }
// // if (jsonData.params){
// // console.log(jsonData.params.value.logs[1]);
// // }
//
// }
// };
// //链接打开的回调函数
// client.onopen = () => {
//
// console.log("发送订阅账号事件")
//
// var str2 ={
// "jsonrpc": "2.0",
// "id": 1,
// "method": "logsSubscribe",
// "params": [ "all" ]
// }
// console.log("发送信息订阅日志信息")
// client.send(JSON.stringify(str2));
// };
// //链接关闭的回调函数
// client.onclose = () =>{
// console.log('关闭回调函数');
// };
var lockReconnect = false;//避免重复连接
var wsUrl = "ws://api.devne.com";
var ws;
var tt;
function createWebSocket(wsUrl) {
try {
ws = new W3CWebSocket(wsUrl)
init();
} catch(e) {
console.log('catch');
reconnect(wsUrl);
}
}
function init() {
ws.onclose = function () {
console.log('链接关闭');
reconnect(wsUrl);
};
ws.onerror = function() {
console.log('发生异常了');
reconnect(wsUrl);
};
ws.onopen = function () {
//心跳检测重置
heartCheck.start();
};
ws.onmessage = function (e) {
//拿到任何消息都说明当前连接是正常的
console.log('接收到消息');
if (typeof e.data === 'string') {
var jsonData = JSON.parse(e.data)
// console.log(jsonData) //打印全部信息
if (jsonData.params){
console.log("logs",jsonData.params.result.value.logs);
}
// if (jsonData.params){
// console.log(jsonData.params.value.logs[1]);
// }
}
heartCheck.start();
}
}
function reconnect(url) {
if(lockReconnect) {
return;
};
lockReconnect = true;
console.log("重连中...")
//没连接上会一直重连,设置延迟避免请求过多
tt && clearTimeout(tt);
tt = setTimeout(function () {
createWebSocket(wsUrl);
lockReconnect = false;
}, 4000);
}
//心跳检测
var heartCheck = {
timeout: 3000,
timeoutObj: null,
serverTimeoutObj: null,
start: function(){
console.log('start');
var self = this;
this.timeoutObj && clearTimeout(this.timeoutObj);
this.serverTimeoutObj && clearTimeout(this.serverTimeoutObj);
this.timeoutObj = setTimeout(function(){
//这里发送一个心跳,后端收到后,返回一个心跳消息,
console.log("发送订阅账号事件")
var str2 ={
"jsonrpc": "2.0",
"id": 1,
"method": "logsSubscribe",
"params": [ "all" ]
}
console.log("发送信息订阅日志信息")
ws.send(JSON.stringify(str2));
self.serverTimeoutObj = setTimeout(function() {
console.log(ws);
ws.close();
// createWebSocket();
}, self.timeout);
}, this.timeout)
}
}
createWebSocket(wsUrl);