You're Invited: Meet the Socket team at BSidesSF and RSAC - April 27 - May 1.RSVP
Socket
Sign inDemoInstall
Socket

xprezzo-on-finished

Package Overview
Dependencies
Maintainers
1
Versions
4
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

xprezzo-on-finished - npm Package Compare versions

Comparing version

to
1.1.2

10

HISTORY.md

@@ -5,6 +5,16 @@ 1.0.0 / 2020-10-05

* depds updated
* depds eslint updated to 8.15.0
* depds eslint-config-standard to 17.0.0
* depds eslint-plugin-import to 2.26.0
* depds mocha to 10.0.0
1.0.0 / 2020-10-05
==================
* depds updated
1.0.0 / 2020-10-05
==================
* Initial release

219

index.js
/*!
* xprezzo-on-finished
* Copyright(c) 2020 Ben Ajenoui <info@seohero.io>
* Copyright(c) 2022 Cloudgen Wong <cloudgen.wong@gmail.com>
* MIT Licensed

@@ -33,18 +33,17 @@ */

*/
let isFinished = (msg) => {
const socket = msg.socket
function isFinished (msg) {
const socket = msg.socket
if (typeof msg.finished === 'boolean') {
// OutgoingMessage
return Boolean(msg.finished || (socket && !socket.writable))
}
if (typeof msg.finished === 'boolean') {
// OutgoingMessage
return Boolean(msg.finished || (socket && !socket.writable))
}
if (typeof msg.complete === 'boolean') {
// IncomingMessage
return Boolean(msg.upgrade || !socket || !socket.readable || (msg.complete && !msg.readable))
}
if (typeof msg.complete === 'boolean') {
// IncomingMessage
return Boolean(msg.upgrade || !socket || !socket.readable || (msg.complete && !msg.readable))
}
// don't know
return undefined
// don't know
return undefined
}

@@ -60,110 +59,63 @@

function attachFinishedListener (msg, callback) {
let eeSocket
let finished = false
let attachFinishedListener =(msg, callback) => {
let eeSocket
let finished = false
let onFinish = (error) => {
eeMsg.cancel()
eeSocket.cancel()
function onFinish (error) {
eeMsg.cancel()
eeSocket.cancel()
finished = true
callback(error)
}
finished = true
callback(error)
}
// finished on first message event
const eeMsg = eeSocket = first([[msg, 'end', 'finish']], onFinish)
// finished on first message event
const eeMsg = eeSocket = first([[msg, 'end', 'finish']], onFinish)
let onSocket = (socket) => {
// remove listener
msg.removeListener('socket', onSocket)
function onSocket (socket) {
// remove listener
msg.removeListener('socket', onSocket)
if (finished) return
if (eeMsg !== eeSocket) return
if (finished) return
if (eeMsg !== eeSocket) return
// finished on first socket event
eeSocket = first([[socket, 'error', 'close']], onFinish)
}
// finished on first socket event
eeSocket = first([[socket, 'error', 'close']], onFinish)
}
if (msg.socket) {
// socket already assigned
onSocket(msg.socket)
return
}
if (msg.socket) {
// socket already assigned
onSocket(msg.socket)
return
}
// wait for socket to be assigned
msg.on('socket', onSocket)
// wait for socket to be assigned
msg.on('socket', onSocket)
if (msg.socket === undefined) {
// istanbul ignore next: node.js 0.8 patch
patchAssignSocket(msg, onSocket)
}
if (msg.socket === undefined) {
// to be remove soon:
// Patch ServerResponse.prototype.assignSocket for node.js 0.8.
// istanbul ignore next: node.js 0.8 patch
((res, callback) => {
const assignSocket = res.assignSocket
if (typeof assignSocket !== 'function') return
// res.on('socket', callback) is broken in 0.8
res.assignSocket = (socket) => {
assignSocket.call(this, socket)
callback(socket)
}
})(msg, onSocket)
}
}
/**
* Attach the listener to the message.
*
* @param {object} msg
* @return {function}
* @private
*/
function attachListener (msg, listener) {
let attached = msg.__onFinished
// create a private single listener with queue
if (!attached || !attached.queue) {
attached = msg.__onFinished = createListener(msg)
attachFinishedListener(msg, attached)
}
const queue = __queue__.get(attached)
queue.push(listener)
__queue__.set(attached, queue)
}
/**
* Create listener on message.
*
* @param {object} msg
* @return {function}
* @private
*/
function createListener (msg) {
function listener (err) {
const queue = __queue__.get(listener)
if (msg.__onFinished === listener) msg.__onFinished = null
if (!queue) return
__queue__.set(listener, null)
for (let i = 0; i < queue.length; i++) {
queue[i](err, msg)
let asyncHooks = (() => {
try {
return require('async_hooks')
} catch (e) {
return {}
}
}
__queue__.set(listener, [])
})()
return listener
}
/**
* Patch ServerResponse.prototype.assignSocket for node.js 0.8.
*
* @param {ServerResponse} res
* @param {function} callback
* @private
*/
// istanbul ignore next: node.js 0.8 patch
function patchAssignSocket (res, callback) {
const assignSocket = res.assignSocket
if (typeof assignSocket !== 'function') return
// res.on('socket', callback) is broken in 0.8
res.assignSocket = function _assignSocket (socket) {
assignSocket.call(this, socket)
callback(socket)
}
}
/**
* Module exports.

@@ -183,13 +135,48 @@ * @public

module.exports = (msg, listener) => {
if (isFinished(msg) !== false) {
defer(listener, null, msg)
return msg
}
if (isFinished(msg) !== false) {
defer(listener, null, msg)
return msg
}
// attach the listener to the message
attachListener(msg, listener)
// attach the listener to the message
((msg, listener) => {
let attached = msg.__onFinishe
let res
return msg
// create anonymous resource
if (asyncHooks.AsyncResource) {
res = new asyncHooks.AsyncResource(listener.name || 'bound-anonymous-fn')
}
// apply to compatible node.js on
if (res && res.runInAsyncScope) {
listener = res.runInAsyncScope.bind(res, listener, null)
}
// create a private single listener with queue
if (!attached || !attached.queue) {
// Create listener on message
attached = msg.__onFinished = ((msg) =>{
let listener = (err) => {
const queue = __queue__.get(listener)
if (msg.__onFinished === listener) msg.__onFinished = null
if (!queue) return
__queue__.set(listener, null)
for (let i = 0; i < queue.length; i++) {
queue[i](err, msg)
}
}
__queue__.set(listener, [])
return listener
})(msg)
attachFinishedListener(msg, attached)
}
const queue = __queue__.get(attached)
queue.push(listener)
__queue__.set(attached, queue)
})(msg, listener)
return msg
}
module.exports.isFinished = isFinished
{
"name": "xprezzo-on-finished",
"description": "Execute a callback when a request closes, finishes, or errors",
"version": "1.1.1",
"author": "Ben Ajenoui <info@seohero.io>",
"version": "1.1.2",
"author": "Cloudgen Wong <cloudgen.wong@gmail.com>",
"license": "MIT",

@@ -10,10 +10,9 @@ "repository": "xprezzo/xprezzo-on-finished",

"devDependencies": {
"eslint": "7.11.0",
"eslint-config-standard": "14.1.1",
"eslint-plugin-import": "2.22.1",
"eslint": "8.15.0",
"eslint-config-standard": "17.0.0",
"eslint-plugin-import": "2.26.0",
"eslint-plugin-markdown": "1.0.2",
"eslint-plugin-node": "11.1.0",
"eslint-plugin-promise": "4.2.1",
"eslint-plugin-standard": "4.0.1",
"mocha": "8.2.0",
"eslint-plugin-promise": "6.0.0",
"mocha": "10.0.0",
"nyc": "15.1.0"

@@ -20,0 +19,0 @@ },

@@ -5,16 +5,3 @@ # xprezzo-on-finished

## Philosophy of Xprezzo
Problems faced:
* Too many requires which creates problem when project grow
* The dependencies update are slow
* Test cases of difficult to design
How Xprezzo try to tackle those problems:
* Useful internal libraries/packages are exposed
* Merge small libraries into a larger one.
* Provide easy to use test framework
## Install

@@ -163,3 +150,3 @@

Xprezzo and related projects are maintained by [Ben Ajenoui](mailto:info@seohero.io) and sponsored by [SEO Hero](https://www.seohero.io).
Xprezzo and related projects are maintained by [Cloudgen Wong](mailto:cloudgen.wong@gmail.com).

@@ -166,0 +153,0 @@ ## License

Sorry, the diff of this file is not supported yet