Comparing version 0.21.0-dev.0 to 0.21.0-dev.1
@@ -7,3 +7,3 @@ var e=require("../../library/common/error") | ||
var a=require("../../library/node/server/Responder/Router") | ||
var s=require("../../library/node/server/WebSocket/type") | ||
var s=require("../../library/node/server/WebSocket/function") | ||
var i=require("../../library/node/server/WebSocket/WebSocketServer") | ||
@@ -26,3 +26,3 @@ var l=require("../../library/node/server/WebSocket/WebSocketUpgradeRequest") | ||
e.forEach(e=>e.webSocket.sendBuffer(t))} | ||
r.on(s.WEB_SOCKET_EVENT_MAP.OPEN,()=>{const e=((e,t,o)=>{void 0===u[e]&&(u[e]=new Set) | ||
r.on(s.WEBSOCKET_EVENT.OPEN,()=>{const e=((e,t,o)=>{void 0===u[e]&&(u[e]=new Set) | ||
const r=u[e] | ||
@@ -36,3 +36,3 @@ r.add(t) | ||
i(e)}) | ||
r.on(s.WEB_SOCKET_EVENT_MAP.CLOSE,()=>{const e=((e,t)=>{const o=u[e] | ||
r.on(s.WEBSOCKET_EVENT.CLOSE,()=>{const e=((e,t)=>{const o=u[e] | ||
o&&o.delete(t) | ||
@@ -45,3 +45,3 @@ o&&0===o.size&&delete u[e] | ||
i(e)}) | ||
r.on(s.WEB_SOCKET_EVENT_MAP.FRAME,((t,r)=>async({dataType:n,dataBuffer:a})=>{if(n!==s.DATA_TYPE_MAP.OPCODE_BINARY)return t.close(1e3,"expect OPCODE_BINARY") | ||
r.on(s.WEBSOCKET_EVENT.FRAME,((t,r)=>async({dataType:n,dataBuffer:a})=>{if(n!==s.OPCODE_TYPE.BINARY)return t.close(1e3,"expect BINARY") | ||
const{error:i}=await(0,e.catchAsync)(r,(0,o.parseBufferPacket)(a)) | ||
@@ -69,6 +69,6 @@ i&&t.close(1e3,i.toString())})(r,([e,t])=>{const{type:s,payload:i,targetId:l}=JSON.parse(e) | ||
const k='\n<div id="setup" class="flex-column">\n <input id="group-path" class="auto-height" type="text" placeholder="group-path" autofocus />\n <input id="id" class="auto-height" type="text" placeholder="id" />\n</div>\n<button id="button-toggle"></button>\n<div id="log" style="overflow-y: auto; flex: 1; min-height: 0;"></div>\n<button id="button-log-clear" class="non-flex">Clear Log [Ctrl+l]</button>\n<div id="main" class="flex-column non-flex">\n <label for="payload-text">Message Text: </label>\n <textarea id="payload-text" style="min-height: 6em;"></textarea>\n <label>Message File: <input id="payload-file" class="auto-height" type="file" /></label>\n <button id="button-send"></button>\n</div>\n' | ||
const E=()=>{const{alert:e,getSelection:t,location:o,Blob:r,WebSocket:n,qS:a,cE:s,TYPE_CLOSE:i,TYPE_INFO_GROUP:l,TYPE_INFO_USER:c,TYPE_BUFFER_GROUP:d,TYPE_BUFFER_SINGLE:p,FRAME_LENGTH_LIMIT:u,Dr:{Common:{Time:{setTimeoutAsync:f},Function:{lossyAsync:y},Math:{getRandomInt:g,getRandomId:b},Format:{binary:m}},Browser:{Data:{BlobPacket:{packBlobPacket:S,parseBlobPacket:k}},Resource:{createDownloadWithBlob:E},DOM:{applyDragFileListListener:h},Input:{KeyCommand:{createKeyCommandHub:O}}}}}=window | ||
const N=(e,t="")=>s("span",{innerText:`[${e}]`,className:`id-tag ${t}`}) | ||
const E=()=>{const{alert:e,getSelection:t,location:o,Blob:r,WebSocket:n,qS:a,cE:s,TYPE_CLOSE:i,TYPE_INFO_GROUP:l,TYPE_INFO_USER:c,TYPE_BUFFER_GROUP:d,TYPE_BUFFER_SINGLE:p,FRAME_LENGTH_LIMIT:u,Dr:{Common:{Time:{setTimeoutAsync:f},Function:{lossyAsync:y},Math:{getRandomInt:g,getRandomId:b},Format:{binary:m}},Browser:{Data:{BlobPacket:{packBlobPacket:S,parseBlobPacket:k}},Resource:{createDownloadWithBlob:E},DOM:{applyDragFileListListener:h},Input:{KeyCommand:{createKeyCommandHub:N}}}}}=window | ||
const O=(e,t="")=>s("span",{innerText:`[${e}]`,className:`id-tag ${t}`}) | ||
const v=()=>s("span",{innerText:(new Date).toLocaleString(),className:"time-tag"}) | ||
const _=(...e)=>{const t=a("#log") | ||
const x=(...e)=>{const t=a("#log") | ||
const o=s("p",{id:b()},e) | ||
@@ -78,8 +78,8 @@ t.appendChild(o) | ||
return o} | ||
const x=({id:e,text:o,className:r})=>_(s("pre",{innerText:o,ondblclick:e=>t().selectAllChildren(e.currentTarget.parentNode.querySelector("pre"))}),N(e,r),v()) | ||
const P=({isSend:e,id:t,fileName:o,fileSize:r,fileId:n,className:a})=>_(s("pre",{innerText:e?"sharing: ":"share: "}),s(e?"b":"button",{innerText:`📄 ${o} (${m(r)}B)`,onclick:e?null:()=>B(t,n)}),N(t,a),v()) | ||
const w=e=>_(s("pre",{innerText:e,className:"color-system"}),N("System","color-system"),v()) | ||
const T=()=>a("#log","") | ||
const I={fileWeakMap:new WeakMap,retryCount:0} | ||
const R=()=>{w(`Left group: ${I.groupPath}`) | ||
const w=({id:e,text:o,className:r})=>x(s("pre",{innerText:o,ondblclick:e=>t().selectAllChildren(e.currentTarget.parentNode.querySelector("pre"))}),O(e,r),v()) | ||
const T=({isSend:e,id:t,fileName:o,fileSize:r,fileId:n,className:a})=>x(s("pre",{innerText:e?"sharing: ":"share: "}),s(e?"b":"button",{innerText:`📄 ${o} (${m(r)}B)`,onclick:e?null:()=>_(t,n)}),O(t,a),v()) | ||
const I=e=>x(s("pre",{innerText:e,className:"color-system"}),O("System","color-system"),v()) | ||
const R=()=>a("#log","") | ||
const P={fileWeakMap:new WeakMap,retryCount:0} | ||
const C=()=>{I(`Left group: ${P.groupPath}`) | ||
a("#setup").style.display="" | ||
@@ -90,17 +90,17 @@ a("#main").style.display="none" | ||
document.title="WebSocket Group" | ||
I.websocket=null | ||
I.groupPath=null | ||
I.id=null | ||
I.groupInfo=[]} | ||
const C=y(async e=>{R() | ||
await f(200*I.retryCount) | ||
I.retryCount++ | ||
I.retryCount<=10&&w(`(${I.retryCount}) connection dropped, try re-connect... [${e.message||e.type||e}]`) | ||
I.retryCount<=10&&M()}).trigger | ||
P.websocket=null | ||
P.groupPath=null | ||
P.id=null | ||
P.groupInfo=[]} | ||
const B=y(async e=>{C() | ||
await f(200*P.retryCount) | ||
P.retryCount++ | ||
P.retryCount<=10&&I(`(${P.retryCount}) connection dropped, try re-connect... [${e.message||e.type||e}]`) | ||
P.retryCount<=10&&$()}).trigger | ||
C() | ||
R() | ||
T() | ||
const B=(e,t)=>{I.websocket.send(S(JSON.stringify({type:p,targetId:e,payload:{fileId:t,intent:"request"}})))} | ||
const M=()=>{if(I.websocket){I.websocket.send(S(JSON.stringify({type:i}))) | ||
const _=(e,t)=>{P.websocket.send(S(JSON.stringify({type:p,targetId:e,payload:{fileId:t,intent:"request"}})))} | ||
const $=()=>{if(P.websocket){P.websocket.send(S(JSON.stringify({type:i}))) | ||
return}const e=a("#group-path").value.trim()||"public" | ||
const t=a("#id").value.trim()||$() | ||
const t=a("#id").value.trim()||M() | ||
const r=new n(((e,t)=>{const{protocol:r,host:n}=o | ||
@@ -110,3 +110,3 @@ return`${"https:"===r?"wss:":"ws:"}//${n}/websocket-group/${encodeURIComponent(e)}?id=${encodeURIComponent(t)}`})(e,t),"group-binary-packet") | ||
const s=t=>{a("#group-path").value=e | ||
a("#id").value=t;(({websocket:e,groupPath:t,id:o})=>{w(`Join group: ${t}, as: ${o}`) | ||
a("#id").value=t;(({websocket:e,groupPath:t,id:o})=>{I(`Join group: ${t}, as: ${o}`) | ||
a("#setup").style.display="none" | ||
@@ -117,11 +117,11 @@ a("#main").style.display="" | ||
document.title=`[${t}/${o}]` | ||
I.websocket=e | ||
I.groupPath=t | ||
I.id=o | ||
I.groupInfo=[] | ||
I.retryCount=0})({websocket:r,groupPath:e,id:t})} | ||
r.addEventListener("error",C) | ||
r.addEventListener("close",({code:e})=>1e3===e?R():C(new Error(`server close with code: ${e}`))) | ||
P.websocket=e | ||
P.groupPath=t | ||
P.id=o | ||
P.groupInfo=[] | ||
P.retryCount=0})({websocket:r,groupPath:e,id:t})} | ||
r.addEventListener("error",B) | ||
r.addEventListener("close",({code:e})=>1e3===e?C():B(new Error(`server close with code: ${e}`))) | ||
r.addEventListener("message",({data:e})=>F(e,s))} | ||
const $=()=>{const e=Object.keys(window) | ||
const M=()=>{const e=Object.keys(window) | ||
return`User-${e[g(e.length-1)]}`} | ||
@@ -131,18 +131,18 @@ const F=async(e,t)=>{const[o,n]=await k(e) | ||
if(s===c)t(u.id) | ||
else if(s===l){w(`Current ${u.length} user: ${u.join(", ")}`) | ||
else if(s===l){I(`Current ${u.length} user: ${u.join(", ")}`) | ||
a("#button-send").disabled=u.length<=1 | ||
a("#button-send",`Send to ${u.length-1} User [Ctrl+Enter]`) | ||
I.groupInfo=u}else if(s===d){const{id:e,text:t,fileName:o,fileSize:r,fileId:n}=u | ||
t&&x({id:e,text:t}) | ||
o&&P({id:e,fileName:o,fileSize:r,fileId:n})}else if(s===p){if(i!==I.id)throw new Error("Strange mismatch") | ||
P.groupInfo=u}else if(s===d){const{id:e,text:t,fileName:o,fileSize:r,fileId:n}=u | ||
t&&w({id:e,text:t}) | ||
o&&T({id:e,fileName:o,fileSize:r,fileId:n})}else if(s===p){if(i!==P.id)throw new Error("Strange mismatch") | ||
const{id:e,intent:t}=u | ||
if("request"===t){const{fileId:t}=u | ||
const o=I.fileWeakMap.get(a(`#${t}`)) | ||
const o=P.fileWeakMap.get(a(`#${t}`)) | ||
const r=o&&o.name | ||
const n=o&&o.type | ||
I.websocket.send(S(JSON.stringify({type:p,targetId:e,payload:{intent:"response",ok:Boolean(o),fileName:r,fileType:n}}),o)) | ||
w(o?`Send file: ${r} to ${e}`:`Miss file request from ${e}`)}else if("response"===t){const{ok:t,fileName:o,fileType:a}=u | ||
P.websocket.send(S(JSON.stringify({type:p,targetId:e,payload:{intent:"response",ok:Boolean(o),fileName:r,fileType:n}}),o)) | ||
I(o?`Send file: ${r} to ${e}`:`Miss file request from ${e}`)}else if("response"===t){const{ok:t,fileName:o,fileType:a}=u | ||
t&&E(o,new r([n],{type:a})) | ||
w(t?`Get file: ${o} from ${e}`:`Miss file response from ${e}`)}}} | ||
const L=()=>{if(!I.websocket||I.groupInfo.length<=1||!a("#payload-text"))return | ||
I(t?`Get file: ${o} from ${e}`:`Miss file response from ${e}`)}}} | ||
const L=()=>{if(!P.websocket||P.groupInfo.length<=1||!a("#payload-text"))return | ||
const t=a("#payload-text").value.trim() | ||
@@ -156,17 +156,17 @@ const o=a("#payload-file").files[0] | ||
if(n>u)return e(`fill size too big! max: ${m(u)}B, get ${m(n)}B`) | ||
t&&x({id:I.id,text:t,className:"color-self"}) | ||
const s=r&&P({isSend:!0,id:I.id,fileName:r,fileSize:n,className:"color-self"}) | ||
I.websocket.send(S(JSON.stringify({type:d,payload:{text:t,fileName:r,fileSize:n,fileId:s&&s.id}}))) | ||
r&&I.fileWeakMap.set(s,o)} | ||
a("#button-log-clear").onclick=T | ||
a("#button-toggle").onclick=M | ||
t&&w({id:P.id,text:t,className:"color-self"}) | ||
const s=r&&T({isSend:!0,id:P.id,fileName:r,fileSize:n,className:"color-self"}) | ||
P.websocket.send(S(JSON.stringify({type:d,payload:{text:t,fileName:r,fileSize:n,fileId:s&&s.id}}))) | ||
r&&P.fileWeakMap.set(s,o)} | ||
a("#button-log-clear").onclick=R | ||
a("#button-toggle").onclick=$ | ||
a("#button-send").onclick=L | ||
const{start:U,addKeyCommand:G}=O({}) | ||
G({checkMap:{ctrlKey:!0,key:"d"},callback:M}) | ||
G({checkMap:{ctrlKey:!0,key:"l"},callback:T}) | ||
const{start:U,addKeyCommand:G}=N({}) | ||
G({checkMap:{ctrlKey:!0,key:"d"},callback:$}) | ||
G({checkMap:{ctrlKey:!0,key:"l"},callback:R}) | ||
G({checkMap:{ctrlKey:!0,key:"Enter"},callback:L}) | ||
G({target:a("#group-path"),checkMap:{key:"Enter"},callback:M}) | ||
G({target:a("#id"),checkMap:{key:"Enter"},callback:M}) | ||
G({target:a("#group-path"),checkMap:{key:"Enter"},callback:$}) | ||
G({target:a("#id"),checkMap:{key:"Enter"},callback:$}) | ||
U() | ||
h(document,e=>{const t=a("#payload-file") | ||
t&&(t.files=e)})} |
exports.rethrowError=(r=>{console.warn(r) | ||
throw r}) | ||
exports.throwInfo=((r,t=r.type)=>{const e=new Error(t) | ||
e.info=r | ||
throw e}) | ||
exports.tryCall=((r,t,...e)=>{try{return r[t](...e)}catch(r){}}) | ||
exports.catchSync=((r,...t)=>{let e,o | ||
try{e=r(...t)}catch(r){o=r||new Error}return{result:e,error:o}}) | ||
exports.catchAsync=(async(r,...t)=>{let e,o | ||
try{e=await r(...t)}catch(r){o=r||new Error}return{result:e,error:o}}) | ||
exports.catchSync=((r,...t)=>{let e,c | ||
try{e=r(...t)}catch(r){c=r||new Error}return{result:e,error:c}}) | ||
exports.catchAsync=(async(r,...t)=>{let e,c | ||
try{e=await r(...t)}catch(r){c=r||new Error}return{result:e,error:c}}) |
@@ -1,22 +0,5 @@ | ||
var t=require("./check") | ||
exports.transformCache=(n=>{let s=null | ||
let u=null | ||
return(...o)=>{if(!u||!(0,t.isCompactArrayShallowEqual)(u,o)){s=n.apply(null,o) | ||
u=o}return s}}) | ||
exports.createTransformCacheWithInfo=((u=s,o=n)=>{const i=[] | ||
return n=>{let s=null | ||
let C=null | ||
const r={id:`#${i.length}`,stackInfo:new Error("GET STACK").stack.toString().split("\n")[2].trim(),sumHitCount:0,sumMissCount:0,hitCount:0,missCount:0} | ||
i.push(r,i) | ||
return(...l)=>{if(C&&(0,t.isCompactArrayShallowEqual)(C,l))r.hitCount++ | ||
else{s=n.apply(null,l) | ||
C=l | ||
r.missCount++}(t=>{if(o(t,i)){u(t,i) | ||
t.sumHitCount+=t.hitCount | ||
t.sumMissCount+=t.missCount | ||
t.hitCount=0 | ||
t.missCount=0}})(r) | ||
return s}}}) | ||
const n=(t,n)=>t.hitCount+t.missCount>=10&&t.hitCount<=t.missCount||t.hitCount+t.missCount>=Math.max(t.sumHitCount,t.sumMissCount,200) | ||
const s=(t,n)=>{const s=t.hitCount<=t.missCount&&t.sumHitCount<=t.sumMissCount | ||
console[s?"warn":"log"](`[DEBUG][transformCache] ${s?"bad":"good"} cache with`+` HIT[${t.hitCount}/${t.hitCount+t.missCount}]`+` SUM[${t.sumHitCount}/${t.sumHitCount+t.sumMissCount}]`+`\n[${t.id} of ${n.length}] ${t.stackInfo}`)} | ||
var l=require("./check") | ||
exports.transformCache=(r=>{let e=null | ||
let a=null | ||
return(...t)=>{if(!a||!(0,l.isCompactArrayShallowEqual)(a,t)){e=r.apply(null,t) | ||
a=t}return e}}) |
var e=require("../../../common/module/Event") | ||
var t=require("./type") | ||
var r=require("./Frame") | ||
const n=e=>{} | ||
const o=Buffer.from("Dr") | ||
exports.createWebSocket=(({socket:a,frameLengthLimit:s,sendFrameMaskType:c,shouldActivePing:d=!1})=>{const i=(0,e.createEventEmitter)() | ||
const u=(0,r.createFrameSender)(s) | ||
const l=(0,r.createFrameReceiver)(s) | ||
let f=null | ||
var r=require("./function") | ||
var t=require("./frameSender") | ||
var n=require("./frameReceiver") | ||
const o=e=>{} | ||
const a=Buffer.from("Dr") | ||
exports.createWebSocket=(({socket:s,frameLengthLimit:c=8388608,isMask:d=!1,shouldPing:i=!1})=>{const u=(0,e.createEventEmitter)() | ||
const f=(0,t.createFrameSenderStore)(c) | ||
const l=(0,n.createFrameReceiverStore)(c) | ||
let E=null | ||
let m=null | ||
let E=null | ||
let T=0 | ||
const P=e=>{if(3!==T){0===T&&a.writable&&a.write("HTTP/1.1 400 Bad Request\r\nconnection: close\r\n\r\n") | ||
T=3 | ||
f&&clearTimeout(f) | ||
let T=null | ||
let O=0 | ||
const P=e=>{if(3!==O){0===O&&s.writable&&s.write(["HTTP/1.1 400 Bad Request","connection: close","\r\n"].join("\r\n")) | ||
O=3 | ||
E&&clearTimeout(E) | ||
m&&clearTimeout(m) | ||
E&&clearTimeout(E) | ||
f=null | ||
T&&clearTimeout(T) | ||
E=null | ||
m=null | ||
E=null | ||
u.queuePromise(n,n) | ||
l.queuePromise(n,n) | ||
u.clear() | ||
l.clear() | ||
a.off("error",g) | ||
a.off("end",g) | ||
a.on("error",n) | ||
a.destroyed||a.destroy() | ||
i.emit(t.WEB_SOCKET_EVENT_MAP.CLOSE)}} | ||
let F=null | ||
let _=[] | ||
let A=0 | ||
const O=e=>{switch(e.dataType){case t.DATA_TYPE_MAP.OPCODE_CLOSE:{const t=e.dataBufferLength>=2&&e.dataBuffer.readUInt16BE(0,!0)||1e3 | ||
const r=e.dataBufferLength>=3&&e.dataBuffer.slice(2,e.dataBufferLength).toString()||"" | ||
return g(t,r)}case t.DATA_TYPE_MAP.OPCODE_PING:return L(e.dataBuffer) | ||
case t.DATA_TYPE_MAP.OPCODE_PONG:return M()}const r=(e=>{F||(F=e.dataType) | ||
_.push(e.dataBuffer) | ||
if((A+=e.dataBuffer.length)>s)throw new Error(`[WebSocket] frameBufferList length ${A} exceeds limit: ${s}`) | ||
T=null | ||
f.dispose() | ||
l.dispose() | ||
s.off("error",S) | ||
s.off("end",S) | ||
s.on("error",o) | ||
s.destroyed||s.destroy() | ||
u.emit(r.WEBSOCKET_EVENT.CLOSE)}} | ||
let B=null | ||
let C=[] | ||
let F=0 | ||
const g=e=>{switch(e.dataType){case r.OPCODE_TYPE.CLOSE:{const r=e.dataBufferLength>=2&&e.dataBuffer.readUInt16BE(0,!0)||1e3 | ||
const t=e.dataBufferLength>=3&&e.dataBuffer.slice(2,e.dataBufferLength).toString()||"" | ||
return S(r,t)}case r.OPCODE_TYPE.PING:return y(e.dataBuffer) | ||
case r.OPCODE_TYPE.PONG:return p()}const t=(e=>{B||(B=e.dataType) | ||
C.push(e.dataBuffer) | ||
if((F+=e.dataBuffer.length)>c)throw new Error(`[WebSocket] frameBufferList length ${F} exceeds limit: ${c}`) | ||
if(!e.isFIN)return null | ||
const t=F | ||
const r=1===_.length?_[0]:Buffer.concat(_,A) | ||
F=null | ||
_=[] | ||
A=0 | ||
return{dataType:t,dataBuffer:r}})(e) | ||
r&&i.emit(t.WEB_SOCKET_EVENT_MAP.FRAME,r) | ||
d&&B()} | ||
const g=(e=1e3,t="")=>{if(3!==T){if(2===T)return P() | ||
if(1!==T&&2!==T)throw new Error(`[close] error readyState = ${T}`) | ||
T=2 | ||
f=setTimeout(P,5e3) | ||
u.encodeCloseFrame(e,t,c) | ||
1e3===e?u.sendEncodedFrame(a).catch(P):u.sendEncodedFrame(a).then(P,P)}} | ||
const B=()=>{m&&clearTimeout(m) | ||
m=setTimeout(C,6e4)} | ||
const h=()=>{E&&clearTimeout(E) | ||
E=setTimeout(()=>g(1006,"pong timeout"),6e4)} | ||
const C=(e=o)=>{if(1===T){h() | ||
u.encodePingFrame(e,c) | ||
return u.sendEncodedFrame(a)}} | ||
const L=(e=o)=>{if(1===T){u.encodePongFrame(e,c) | ||
return u.sendEncodedFrame(a)}} | ||
const M=()=>{E&&clearTimeout(E) | ||
E=null | ||
if(d)B() | ||
const r=B | ||
const t=1===C.length?C[0]:Buffer.concat(C,F) | ||
B=null | ||
C=[] | ||
F=0 | ||
return{dataType:r,dataBuffer:t}})(e) | ||
t&&u.emit(r.WEBSOCKET_EVENT.FRAME,t) | ||
i&&h()} | ||
const S=(e=1e3,r="")=>{if(3!==O){if(2===O)return P() | ||
if(1!==O&&2!==O)throw new Error(`[close] error readyState = ${O}`) | ||
O=2 | ||
E=setTimeout(P,5e3);(0,t.encodeCloseFrame)(f,e,r,d) | ||
1e3===e?(0,t.sendEncodedFrame)(f,s).catch(P):(0,t.sendEncodedFrame)(f,s).then(P,P)}} | ||
const h=()=>{m&&clearTimeout(m) | ||
m=setTimeout(L,6e4)} | ||
const N=()=>{T&&clearTimeout(T) | ||
T=setTimeout(()=>S(1006,"pong timeout"),6e4)} | ||
const L=(e=a)=>{if(1===O){N();(0,t.encodePingFrame)(f,e,d) | ||
return(0,t.sendEncodedFrame)(f,s)}} | ||
const y=(e=a)=>{if(1===O){(0,t.encodePongFrame)(f,e,d) | ||
return(0,t.sendEncodedFrame)(f,s)}} | ||
const p=()=>{T&&clearTimeout(T) | ||
T=null | ||
if(i)h() | ||
else{m&&clearTimeout(m) | ||
m=null}} | ||
return Object.assign({CONNECTING:0,OPEN:1,CLOSING:2,CLOSED:3},i,{socket:a,frameLengthLimit:s,sendFrameMaskType:c,getReadyState:()=>T,setReadyState:e=>{T=e},setFrameLengthLimit:e=>{u.setFrameLengthLimit(e) | ||
l.setFrameLengthLimit(e) | ||
s=e},isClosed:()=>3===T||!a||a.destroyed,doCloseSocket:P,listenAndReceiveFrame:()=>l.listenAndReceiveFrame(a,O,e=>g(1006,"Frame Error")),close:g,sendText:e=>{if(1!==T)throw new Error(`[sendBuffer] not open yet: readyState = ${T}`) | ||
u.encodeFrame(t.FRAME_TYPE_CONFIG_MAP.FRAME_COMPLETE,t.DATA_TYPE_MAP.OPCODE_TEXT,Buffer.from(e),c) | ||
return u.sendEncodedFrame(a)},sendBuffer:e=>{if(1!==T)throw new Error(`[sendBuffer] not open yet: readyState = ${T}`) | ||
u.encodeFrame(t.FRAME_TYPE_CONFIG_MAP.FRAME_COMPLETE,t.DATA_TYPE_MAP.OPCODE_BINARY,e,c) | ||
return u.sendEncodedFrame(a)},setNextPing:B,setNextPong:h,sendPing:C,sendPong:L})}) | ||
return Object.assign({CONNECTING:0,OPEN:1,CLOSING:2,CLOSED:3},u,{socket:s,frameLengthLimit:c,isMask:d,getReadyState:()=>O,isClosed:()=>3===O||!s||s.destroyed,doCloseSocket:P,open:()=>{s.on("error",S) | ||
s.on("end",S);(0,n.listenAndReceiveFrame)(l,s,g,e=>S(1006,"Frame Error")) | ||
O=1 | ||
u.emit(r.WEBSOCKET_EVENT.OPEN)},close:S,sendText:e=>{if(1!==O)throw new Error(`[sendBuffer] not open yet: readyState = ${O}`);(0,t.encodeFrame)(f,r.FRAME_CONFIG.COMPLETE,r.OPCODE_TYPE.TEXT,Buffer.from(e),d) | ||
return(0,t.sendEncodedFrame)(f,s)},sendBuffer:e=>{if(1!==O)throw new Error(`[sendBuffer] not open yet: readyState = ${O}`);(0,t.encodeFrame)(f,r.FRAME_CONFIG.COMPLETE,r.OPCODE_TYPE.BINARY,e,d) | ||
return(0,t.sendEncodedFrame)(f,s)},setNextPing:h,setNextPong:N,sendPing:L,sendPong:y})}) |
@@ -5,3 +5,3 @@ var e=require("url") | ||
var r=require("../../net") | ||
var s=require("./type") | ||
var s=require("./function") | ||
var c=require("./WebSocket") | ||
@@ -11,27 +11,23 @@ const n=new Set(["wss:","ws:","https:","http:"]) | ||
const a=(e,o,t)=>e.doCloseSocket() | ||
exports.createWebSocketClient=(({urlString:p,option:l={},onError:S,onUpgradeResponse:d=a,frameLengthLimit:u=s.DEFAULT_FRAME_LENGTH_LIMIT})=>{const g=new e.URL(p) | ||
exports.createWebSocketClient=(({urlString:p,option:l={},onError:u,onUpgradeResponse:S=a,frameLengthLimit:d})=>{const g=new e.URL(p) | ||
if(!n.has(g.protocol))throw new Error(`[WebSocketClient] invalid url protocol: ${g.protocol}`) | ||
if(!g.host)throw new Error(`[WebSocketClient] invalid url host: ${g.host}`) | ||
l.isSecure=i.has(g.protocol) | ||
const{requestOption:k,requestProtocolString:w,responseKey:b}=((e,{key:o,isSecure:t,headers:c,origin:n="",requestProtocolString:i=""})=>{const a=o||(0,s.getRequestKey)() | ||
const{requestOption:w,requestProtocolString:k,responseKey:b}=((e,{key:o,isSecure:t,headers:c,origin:n="",requestProtocolString:i=""})=>{const a=o||(0,s.getRequestKey)() | ||
const p=(0,s.getRespondKey)(a) | ||
return{requestOption:Object.assign({},(0,r.urlToOption)(e),{protocol:void 0,port:""!==e.port?e.port:t?443:80,headers:Object.assign({},c,{origin:n,upgrade:"websocket",connection:"upgrade","sec-websocket-version":s.WEB_SOCKET_VERSION,"sec-websocket-key":a,"sec-websocket-protocol":i})}),requestProtocolString:i,responseKey:p}})(g,l) | ||
const h=(l.isSecure?t.get:o.get)(k) | ||
return{requestOption:Object.assign({},(0,r.urlToOption)(e),{protocol:void 0,port:""!==e.port?e.port:t?443:80,headers:Object.assign({},c,{origin:n,upgrade:"websocket",connection:"upgrade","sec-websocket-version":s.WEBSOCKET_VERSION,"sec-websocket-key":a,"sec-websocket-protocol":i})}),requestProtocolString:i,responseKey:p}})(g,l) | ||
const h=(l.isSecure?t.get:o.get)(w) | ||
h.on("error",e=>{if(!h.aborted){h.abort() | ||
S(e)}}) | ||
u(e)}}) | ||
h.on("response",e=>{h.abort() | ||
S(new Error("[WebSocketClient] unexpected response"))}) | ||
h.on("upgrade",async(e,o,t)=>{const r=(0,c.createWebSocket)({socket:o,frameLengthLimit:u,sendFrameMaskType:s.DO_MASK_DATA}) | ||
u(new Error("[WebSocketClient] unexpected response"))}) | ||
h.on("upgrade",async(e,o,t)=>{const r=(0,c.createWebSocket)({socket:o,frameLengthLimit:d,isMask:!0}) | ||
r.origin=l.origin | ||
r.isSecure=l.isSecure | ||
await d(r,e,t) | ||
await S(r,e,t) | ||
r.isClosed()||((e,o,t,r)=>{if(e.getReadyState()!==e.CONNECTING)throw new Error(`[WebSocketClient][doUpgradeSocket] error readyState ${e.getReadyState()}`) | ||
if(t!==o.headers["sec-websocket-accept"])throw new Error("[WebSocketClient][doUpgradeSocket] wrong sec-websocket-accept") | ||
const c=o.headers["sec-websocket-protocol"] | ||
if(!r.split(/, */).includes(c))throw new Error(`[WebSocketClient][doUpgradeSocket] unexpected protocol ${c}`) | ||
e.socket.on("error",e.close) | ||
e.socket.on("end",e.close) | ||
e.listenAndReceiveFrame() | ||
e.protocol=c | ||
e.setReadyState(e.OPEN) | ||
e.emit(s.WEB_SOCKET_EVENT_MAP.OPEN)})(r,e,b,w)})}) | ||
const s=o.headers["sec-websocket-protocol"] | ||
if(!r.split(/, */).includes(s))throw new Error(`[WebSocketClient][doUpgradeSocket] unexpected protocol ${s}`) | ||
e.protocol=s | ||
e.open()})(r,e,b,k)})}) |
@@ -1,26 +0,22 @@ | ||
var e=require("./type") | ||
var e=require("./function") | ||
var o=require("./WebSocket") | ||
const r=(e,o,r)=>e.doCloseSocket() | ||
exports.enableWebSocketServer=(({server:t,onUpgradeRequest:s=r,frameLengthLimit:c=e.DEFAULT_FRAME_LENGTH_LIMIT})=>{const n=new Set | ||
t.on("upgrade",async(r,t,a)=>{const d=(0,o.createWebSocket)({socket:t,frameLengthLimit:c,sendFrameMaskType:e.DO_NOT_MASK_DATA,shouldActivePing:!0}) | ||
const{responseKey:i}=((o,r)=>{const t=r.headers["sec-websocket-key"] | ||
exports.enableWebSocketServer=(({server:t,onUpgradeRequest:s=r,frameLengthLimit:c})=>{const n=new Set | ||
t.on("upgrade",async(r,t,i)=>{const a=(0,o.createWebSocket)({socket:t,frameLengthLimit:c,isMask:!1,shouldPing:!0}) | ||
const{responseKey:d}=((o,r)=>{const t=r.headers["sec-websocket-key"] | ||
const s=parseInt(r.headers["sec-websocket-version"]) | ||
if(!t||s!==e.WEB_SOCKET_VERSION||"GET"!==r.method||"websocket"!==r.headers.upgrade.toLowerCase())return o.doCloseSocket(new Error("invalid upgrade request")) | ||
if(!t||s!==e.WEBSOCKET_VERSION||"GET"!==r.method||"websocket"!==r.headers.upgrade.toLowerCase())return o.doCloseSocket(new Error("invalid upgrade request")) | ||
o.origin=r.headers.origin | ||
o.isSecure=Boolean(r.socket.authorized||r.socket.encrypted) | ||
o.protocolList=(r.headers["sec-websocket-protocol"]||"").split(/, */) | ||
return{responseKey:(0,e.getRespondKey)(t)}})(d,r) | ||
if(d.isClosed())return | ||
const p=await s(d,r,a) | ||
if(!d.isClosed()){if(!p)return d.doCloseSocket(new Error("no selected protocol"));((o,r,t)=>{if(o.getReadyState()!==o.CONNECTING)throw new Error(`[WebSocketServer][doUpgradeSocket] error readyState ${o.getReadyState()}`) | ||
if(r&&!o.protocolList.includes(r))throw new Error(`[WebSocketServer][doUpgradeSocket] unexpected protocol ${r}`) | ||
o.socket.on("error",o.close) | ||
o.socket.on("end",o.close) | ||
o.socket.write(`HTTP/1.1 101 Switching Protocols\r\nupgrade: websocket\r\nconnection: upgrade\r\nsec-websocket-accept: ${t}\r\n${r?`sec-websocket-protocol: ${r}\r\n`:""}\r\n`) | ||
o.listenAndReceiveFrame() | ||
o.protocol=r | ||
o.setReadyState(o.OPEN) | ||
o.emit(e.WEB_SOCKET_EVENT_MAP.OPEN)})(d,p,i) | ||
if(!d.isClosed()){n.add(d) | ||
d.on(e.WEB_SOCKET_EVENT_MAP.CLOSE,()=>{n.delete(d)})}}}) | ||
return{responseKey:(0,e.getRespondKey)(t)}})(a,r) | ||
if(a.isClosed())return | ||
const p=await s(a,r,i) | ||
if(!a.isClosed()){if(!p)return a.doCloseSocket(new Error("no selected protocol"));((e,o,r)=>{if(e.getReadyState()!==e.CONNECTING)throw new Error(`[WebSocketServer][doUpgradeSocket] error readyState ${e.getReadyState()}`) | ||
if(o&&!e.protocolList.includes(o))throw new Error(`[WebSocketServer][doUpgradeSocket] unexpected protocol ${o}`) | ||
e.protocol=o | ||
e.open() | ||
e.socket.write(["HTTP/1.1 101 Switching Protocols","upgrade: websocket","connection: upgrade",`sec-websocket-accept: ${r}`,o&&`sec-websocket-protocol: ${o}`,"\r\n"].filter(Boolean).join("\r\n"))})(a,p,d) | ||
if(!a.isClosed()){n.add(a) | ||
a.on(e.WEBSOCKET_EVENT.CLOSE,()=>{n.delete(a)})}}}) | ||
return n}) |
@@ -5,7 +5,2 @@ const rethrowError = error => { | ||
}; | ||
const throwInfo = (info, message = info.type) => { | ||
const error = new Error(message); | ||
error.info = info; | ||
throw error; | ||
}; | ||
const tryCall = (thisArg, name, ...args) => { | ||
@@ -40,2 +35,2 @@ try { | ||
}; | ||
export { rethrowError, throwInfo, tryCall, catchSync, catchAsync }; | ||
export { rethrowError, tryCall, catchSync, catchAsync }; |
@@ -13,40 +13,2 @@ import { isCompactArrayShallowEqual } from "./check"; | ||
}; | ||
const createTransformCacheWithInfo = (outputInfo = DEFAULT_OUTPUT_INFO, shouldOutputInfo = DEFAULT_SHOULD_OUTPUT_INFO) => { | ||
const infoArray = []; | ||
return transformFunc => { | ||
let cacheResult = null; | ||
let cacheArgs = null; | ||
const info = { | ||
id: `#${infoArray.length}`, | ||
stackInfo: new Error("GET STACK").stack.toString().split("\n")[2].trim(), | ||
sumHitCount: 0, | ||
sumMissCount: 0, | ||
hitCount: 0, | ||
missCount: 0 | ||
}; | ||
infoArray.push(info, infoArray); | ||
return (...args) => { | ||
if (cacheArgs && isCompactArrayShallowEqual(cacheArgs, args)) info.hitCount++; else { | ||
cacheResult = transformFunc.apply(null, args); | ||
cacheArgs = args; | ||
info.missCount++; | ||
} | ||
(info => { | ||
if (shouldOutputInfo(info, infoArray)) { | ||
outputInfo(info, infoArray); | ||
info.sumHitCount += info.hitCount; | ||
info.sumMissCount += info.missCount; | ||
info.hitCount = 0; | ||
info.missCount = 0; | ||
} | ||
})(info); | ||
return cacheResult; | ||
}; | ||
}; | ||
}; | ||
const DEFAULT_SHOULD_OUTPUT_INFO = (info, infoArray) => info.hitCount + info.missCount >= 10 && info.hitCount <= info.missCount || info.hitCount + info.missCount >= Math.max(info.sumHitCount, info.sumMissCount, 200); | ||
const DEFAULT_OUTPUT_INFO = (info, infoArray) => { | ||
const isBadCache = info.hitCount <= info.missCount && info.sumHitCount <= info.sumMissCount; | ||
console[isBadCache ? "warn" : "log"](`[DEBUG][transformCache] ${isBadCache ? "bad" : "good"} cache with` + ` HIT[${info.hitCount}/${info.hitCount + info.missCount}]` + ` SUM[${info.sumHitCount}/${info.sumHitCount + info.sumMissCount}]` + `\n[${info.id} of ${infoArray.length}] ${info.stackInfo}`); | ||
}; | ||
export { transformCache, createTransformCacheWithInfo }; | ||
export { transformCache }; |
import { createEventEmitter } from "../../../common/module/Event"; | ||
import { FRAME_TYPE_CONFIG_MAP, DATA_TYPE_MAP, WEB_SOCKET_EVENT_MAP } from "./type"; | ||
import { createFrameSender, createFrameReceiver } from "./Frame"; | ||
import { FRAME_CONFIG, OPCODE_TYPE, WEBSOCKET_EVENT } from "./function"; | ||
import { createFrameSenderStore, encodeFrame, encodeCloseFrame, encodePingFrame, encodePongFrame, sendEncodedFrame } from "./frameSender"; | ||
import { createFrameReceiverStore, listenAndReceiveFrame } from "./frameReceiver"; | ||
const NULL_ERROR_LISTENER = error => {}; | ||
const DEFAULT_BUFFER = Buffer.from("Dr"); | ||
const createWebSocket = ({socket, frameLengthLimit, sendFrameMaskType, shouldActivePing = !1}) => { | ||
const createWebSocket = ({socket, frameLengthLimit = 8388608, isMask = !1, shouldPing = !1}) => { | ||
const eventEmitter = createEventEmitter(); | ||
const frameSender = createFrameSender(frameLengthLimit); | ||
const frameReceiver = createFrameReceiver(frameLengthLimit); | ||
const frameSenderStore = createFrameSenderStore(frameLengthLimit); | ||
const frameReceiverStore = createFrameReceiverStore(frameLengthLimit); | ||
let closeTimeoutToken = null; | ||
@@ -16,3 +17,3 @@ let pingTimeoutToken = null; | ||
if (3 !== readyState) { | ||
0 === readyState && socket.writable && socket.write("HTTP/1.1 400 Bad Request\r\nconnection: close\r\n\r\n"); | ||
0 === readyState && socket.writable && socket.write([ "HTTP/1.1 400 Bad Request", "connection: close", "\r\n" ].join("\r\n")); | ||
readyState = 3; | ||
@@ -25,6 +26,4 @@ closeTimeoutToken && clearTimeout(closeTimeoutToken); | ||
pongTimeoutToken = null; | ||
frameSender.queuePromise(NULL_ERROR_LISTENER, NULL_ERROR_LISTENER); | ||
frameReceiver.queuePromise(NULL_ERROR_LISTENER, NULL_ERROR_LISTENER); | ||
frameSender.clear(); | ||
frameReceiver.clear(); | ||
frameSenderStore.dispose(); | ||
frameReceiverStore.dispose(); | ||
socket.off("error", close); | ||
@@ -34,3 +33,3 @@ socket.off("end", close); | ||
socket.destroyed || socket.destroy(); | ||
eventEmitter.emit(WEB_SOCKET_EVENT_MAP.CLOSE); | ||
eventEmitter.emit(WEBSOCKET_EVENT.CLOSE); | ||
} | ||
@@ -43,3 +42,3 @@ }; | ||
switch (frame.dataType) { | ||
case DATA_TYPE_MAP.OPCODE_CLOSE: | ||
case OPCODE_TYPE.CLOSE: | ||
{ | ||
@@ -50,5 +49,5 @@ const code = frame.dataBufferLength >= 2 && frame.dataBuffer.readUInt16BE(0, !0) || 1e3; | ||
} | ||
case DATA_TYPE_MAP.OPCODE_PING: | ||
case OPCODE_TYPE.PING: | ||
return sendPong(frame.dataBuffer); | ||
case DATA_TYPE_MAP.OPCODE_PONG: | ||
case OPCODE_TYPE.PONG: | ||
return receivePong(); | ||
@@ -71,4 +70,4 @@ } | ||
})(frame); | ||
completeFrameData && eventEmitter.emit(WEB_SOCKET_EVENT_MAP.FRAME, completeFrameData); | ||
shouldActivePing && setNextPing(); | ||
completeFrameData && eventEmitter.emit(WEBSOCKET_EVENT.FRAME, completeFrameData); | ||
shouldPing && setNextPing(); | ||
}; | ||
@@ -81,4 +80,4 @@ const close = (code = 1e3, reason = "") => { | ||
closeTimeoutToken = setTimeout(doCloseSocket, 5e3); | ||
frameSender.encodeCloseFrame(code, reason, sendFrameMaskType); | ||
1e3 === code ? frameSender.sendEncodedFrame(socket).catch(doCloseSocket) : frameSender.sendEncodedFrame(socket).then(doCloseSocket, doCloseSocket); | ||
encodeCloseFrame(frameSenderStore, code, reason, isMask); | ||
1e3 === code ? sendEncodedFrame(frameSenderStore, socket).catch(doCloseSocket) : sendEncodedFrame(frameSenderStore, socket).then(doCloseSocket, doCloseSocket); | ||
} | ||
@@ -97,4 +96,4 @@ }; | ||
setNextPong(); | ||
frameSender.encodePingFrame(dataBuffer, sendFrameMaskType); | ||
return frameSender.sendEncodedFrame(socket); | ||
encodePingFrame(frameSenderStore, dataBuffer, isMask); | ||
return sendEncodedFrame(frameSenderStore, socket); | ||
} | ||
@@ -104,4 +103,4 @@ }; | ||
if (1 === readyState) { | ||
frameSender.encodePongFrame(dataBuffer, sendFrameMaskType); | ||
return frameSender.sendEncodedFrame(socket); | ||
encodePongFrame(frameSenderStore, dataBuffer, isMask); | ||
return sendEncodedFrame(frameSenderStore, socket); | ||
} | ||
@@ -112,3 +111,3 @@ }; | ||
pongTimeoutToken = null; | ||
if (shouldActivePing) setNextPing(); else { | ||
if (shouldPing) setNextPing(); else { | ||
pingTimeoutToken && clearTimeout(pingTimeoutToken); | ||
@@ -126,25 +125,23 @@ pingTimeoutToken = null; | ||
frameLengthLimit, | ||
sendFrameMaskType, | ||
isMask, | ||
getReadyState: () => readyState, | ||
setReadyState: nextReadyState => { | ||
readyState = nextReadyState; | ||
}, | ||
setFrameLengthLimit: nextFrameLengthLimit => { | ||
frameSender.setFrameLengthLimit(nextFrameLengthLimit); | ||
frameReceiver.setFrameLengthLimit(nextFrameLengthLimit); | ||
frameLengthLimit = nextFrameLengthLimit; | ||
}, | ||
isClosed: () => 3 === readyState || !socket || socket.destroyed, | ||
doCloseSocket, | ||
listenAndReceiveFrame: () => frameReceiver.listenAndReceiveFrame(socket, onReceiveFrame, error => close(1006, "Frame Error")), | ||
open: () => { | ||
socket.on("error", close); | ||
socket.on("end", close); | ||
listenAndReceiveFrame(frameReceiverStore, socket, onReceiveFrame, error => close(1006, "Frame Error")); | ||
readyState = 1; | ||
eventEmitter.emit(WEBSOCKET_EVENT.OPEN); | ||
}, | ||
close, | ||
sendText: text => { | ||
if (1 !== readyState) throw new Error(`[sendBuffer] not open yet: readyState = ${readyState}`); | ||
frameSender.encodeFrame(FRAME_TYPE_CONFIG_MAP.FRAME_COMPLETE, DATA_TYPE_MAP.OPCODE_TEXT, Buffer.from(text), sendFrameMaskType); | ||
return frameSender.sendEncodedFrame(socket); | ||
encodeFrame(frameSenderStore, FRAME_CONFIG.COMPLETE, OPCODE_TYPE.TEXT, Buffer.from(text), isMask); | ||
return sendEncodedFrame(frameSenderStore, socket); | ||
}, | ||
sendBuffer: buffer => { | ||
if (1 !== readyState) throw new Error(`[sendBuffer] not open yet: readyState = ${readyState}`); | ||
frameSender.encodeFrame(FRAME_TYPE_CONFIG_MAP.FRAME_COMPLETE, DATA_TYPE_MAP.OPCODE_BINARY, buffer, sendFrameMaskType); | ||
return frameSender.sendEncodedFrame(socket); | ||
encodeFrame(frameSenderStore, FRAME_CONFIG.COMPLETE, OPCODE_TYPE.BINARY, buffer, isMask); | ||
return sendEncodedFrame(frameSenderStore, socket); | ||
}, | ||
@@ -151,0 +148,0 @@ setNextPing, |
@@ -5,12 +5,12 @@ import { URL } from "url"; | ||
import { urlToOption } from "../../net"; | ||
import { DO_MASK_DATA, DEFAULT_FRAME_LENGTH_LIMIT, WEB_SOCKET_VERSION, WEB_SOCKET_EVENT_MAP, getRequestKey, getRespondKey } from "./type"; | ||
import { WEBSOCKET_VERSION, WEBSOCKET_EVENT, getRequestKey, getRespondKey } from "./function"; | ||
import { createWebSocket } from "./WebSocket"; | ||
const VALID_WEB_SOCKET_PROTOCOL_SET = new Set([ "wss:", "ws:", "https:", "http:" ]); | ||
const SECURE_WEB_SOCKET_PROTOCOL_SET = new Set([ "wss:", "https:" ]); | ||
const VALID_WEBSOCKET_PROTOCOL_SET = new Set([ "wss:", "ws:", "https:", "http:" ]); | ||
const SECURE_WEBSOCKET_PROTOCOL_SET = new Set([ "wss:", "https:" ]); | ||
const DEFAULT_ON_UPGRADE_RESPONSE = (webSocket, response, bodyHeadBuffer) => webSocket.doCloseSocket(); | ||
const createWebSocketClient = ({urlString, option = {}, onError, onUpgradeResponse = DEFAULT_ON_UPGRADE_RESPONSE, frameLengthLimit = DEFAULT_FRAME_LENGTH_LIMIT}) => { | ||
const createWebSocketClient = ({urlString, option = {}, onError, onUpgradeResponse = DEFAULT_ON_UPGRADE_RESPONSE, frameLengthLimit}) => { | ||
const url = new URL(urlString); | ||
if (!VALID_WEB_SOCKET_PROTOCOL_SET.has(url.protocol)) throw new Error(`[WebSocketClient] invalid url protocol: ${url.protocol}`); | ||
if (!VALID_WEBSOCKET_PROTOCOL_SET.has(url.protocol)) throw new Error(`[WebSocketClient] invalid url protocol: ${url.protocol}`); | ||
if (!url.host) throw new Error(`[WebSocketClient] invalid url host: ${url.host}`); | ||
option.isSecure = SECURE_WEB_SOCKET_PROTOCOL_SET.has(url.protocol); | ||
option.isSecure = SECURE_WEBSOCKET_PROTOCOL_SET.has(url.protocol); | ||
const {requestOption, requestProtocolString, responseKey} = ((url, {key, isSecure, headers, origin = "", requestProtocolString = ""}) => { | ||
@@ -29,3 +29,3 @@ const requestKey = key || getRequestKey(); | ||
connection: "upgrade", | ||
"sec-websocket-version": WEB_SOCKET_VERSION, | ||
"sec-websocket-version": WEBSOCKET_VERSION, | ||
"sec-websocket-key": requestKey, | ||
@@ -54,3 +54,3 @@ "sec-websocket-protocol": requestProtocolString | ||
frameLengthLimit, | ||
sendFrameMaskType: DO_MASK_DATA | ||
isMask: !0 | ||
}); | ||
@@ -65,8 +65,4 @@ webSocket.origin = option.origin; | ||
if (!requestProtocolString.split(/, */).includes(protocol)) throw new Error(`[WebSocketClient][doUpgradeSocket] unexpected protocol ${protocol}`); | ||
webSocket.socket.on("error", webSocket.close); | ||
webSocket.socket.on("end", webSocket.close); | ||
webSocket.listenAndReceiveFrame(); | ||
webSocket.protocol = protocol; | ||
webSocket.setReadyState(webSocket.OPEN); | ||
webSocket.emit(WEB_SOCKET_EVENT_MAP.OPEN); | ||
webSocket.open(); | ||
})(webSocket, response, responseKey, requestProtocolString); | ||
@@ -73,0 +69,0 @@ }); |
@@ -1,5 +0,5 @@ | ||
import { DO_NOT_MASK_DATA, DEFAULT_FRAME_LENGTH_LIMIT, WEB_SOCKET_VERSION, WEB_SOCKET_EVENT_MAP, getRespondKey } from "./type"; | ||
import { WEBSOCKET_VERSION, WEBSOCKET_EVENT, getRespondKey } from "./function"; | ||
import { createWebSocket } from "./WebSocket"; | ||
const DEFAULT_ON_UPGRADE_REQUEST = (webSocket, request, bodyHeadBuffer) => webSocket.doCloseSocket(); | ||
const enableWebSocketServer = ({server, onUpgradeRequest = DEFAULT_ON_UPGRADE_REQUEST, frameLengthLimit = DEFAULT_FRAME_LENGTH_LIMIT}) => { | ||
const enableWebSocketServer = ({server, onUpgradeRequest = DEFAULT_ON_UPGRADE_REQUEST, frameLengthLimit}) => { | ||
const webSocketSet = new Set(); | ||
@@ -10,4 +10,4 @@ server.on("upgrade", async (request, socket, bodyHeadBuffer) => { | ||
frameLengthLimit, | ||
sendFrameMaskType: DO_NOT_MASK_DATA, | ||
shouldActivePing: !0 | ||
isMask: !1, | ||
shouldPing: !0 | ||
}); | ||
@@ -17,3 +17,3 @@ const {responseKey} = ((webSocket, request) => { | ||
const version = parseInt(request.headers["sec-websocket-version"]); | ||
if (!requestKey || version !== WEB_SOCKET_VERSION || "GET" !== request.method || "websocket" !== request.headers.upgrade.toLowerCase()) return webSocket.doCloseSocket(new Error("invalid upgrade request")); | ||
if (!requestKey || version !== WEBSOCKET_VERSION || "GET" !== request.method || "websocket" !== request.headers.upgrade.toLowerCase()) return webSocket.doCloseSocket(new Error("invalid upgrade request")); | ||
webSocket.origin = request.headers.origin; | ||
@@ -33,13 +33,9 @@ webSocket.isSecure = Boolean(request.socket.authorized || request.socket.encrypted); | ||
if (protocol && !webSocket.protocolList.includes(protocol)) throw new Error(`[WebSocketServer][doUpgradeSocket] unexpected protocol ${protocol}`); | ||
webSocket.socket.on("error", webSocket.close); | ||
webSocket.socket.on("end", webSocket.close); | ||
webSocket.socket.write(`HTTP/1.1 101 Switching Protocols\r\nupgrade: websocket\r\nconnection: upgrade\r\nsec-websocket-accept: ${responseKey}\r\n${protocol ? `sec-websocket-protocol: ${protocol}\r\n` : ""}\r\n`); | ||
webSocket.listenAndReceiveFrame(); | ||
webSocket.protocol = protocol; | ||
webSocket.setReadyState(webSocket.OPEN); | ||
webSocket.emit(WEB_SOCKET_EVENT_MAP.OPEN); | ||
webSocket.open(); | ||
webSocket.socket.write([ "HTTP/1.1 101 Switching Protocols", "upgrade: websocket", "connection: upgrade", `sec-websocket-accept: ${responseKey}`, protocol && `sec-websocket-protocol: ${protocol}`, "\r\n" ].filter(Boolean).join("\r\n")); | ||
})(webSocket, protocol, responseKey); | ||
if (!webSocket.isClosed()) { | ||
webSocketSet.add(webSocket); | ||
webSocket.on(WEB_SOCKET_EVENT_MAP.CLOSE, () => { | ||
webSocket.on(WEBSOCKET_EVENT.CLOSE, () => { | ||
webSocketSet.delete(webSocket); | ||
@@ -46,0 +42,0 @@ }); |
@@ -1,1 +0,1 @@ | ||
{"name":"dr-js","version":"0.21.0-dev.0","description":"A collection of strange functions","author":"dr-js","license":"MIT","keywords":["Dr","Dr-js","JavaScript"],"repository":"github:dr-js/dr-js","bin":"bin/index.js","browser":"library/Dr.browser.js","engines":{"node":">=10.15","npm":">=6"},"sideEffects":false} | ||
{"name":"dr-js","version":"0.21.0-dev.1","description":"A collection of strange functions","author":"dr-js","license":"MIT","keywords":["Dr","Dr-js","JavaScript"],"repository":"github:dr-js/dr-js","bin":"bin/index.js","browser":"library/Dr.browser.js","engines":{"node":">=10.15","npm":">=6"},"sideEffects":false} |
Sorry, the diff of this file is too big to display
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 3 instances in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 3 instances in 1 package
209
448034
10409