11cb0ef41Sopenharmony_ci'use strict' 21cb0ef41Sopenharmony_ci 31cb0ef41Sopenharmony_ciconst { AsyncResource } = require('async_hooks') 41cb0ef41Sopenharmony_ciconst { InvalidArgumentError, RequestAbortedError, SocketError } = require('../core/errors') 51cb0ef41Sopenharmony_ciconst util = require('../core/util') 61cb0ef41Sopenharmony_ciconst { addSignal, removeSignal } = require('./abort-signal') 71cb0ef41Sopenharmony_ci 81cb0ef41Sopenharmony_ciclass ConnectHandler extends AsyncResource { 91cb0ef41Sopenharmony_ci constructor (opts, callback) { 101cb0ef41Sopenharmony_ci if (!opts || typeof opts !== 'object') { 111cb0ef41Sopenharmony_ci throw new InvalidArgumentError('invalid opts') 121cb0ef41Sopenharmony_ci } 131cb0ef41Sopenharmony_ci 141cb0ef41Sopenharmony_ci if (typeof callback !== 'function') { 151cb0ef41Sopenharmony_ci throw new InvalidArgumentError('invalid callback') 161cb0ef41Sopenharmony_ci } 171cb0ef41Sopenharmony_ci 181cb0ef41Sopenharmony_ci const { signal, opaque, responseHeaders } = opts 191cb0ef41Sopenharmony_ci 201cb0ef41Sopenharmony_ci if (signal && typeof signal.on !== 'function' && typeof signal.addEventListener !== 'function') { 211cb0ef41Sopenharmony_ci throw new InvalidArgumentError('signal must be an EventEmitter or EventTarget') 221cb0ef41Sopenharmony_ci } 231cb0ef41Sopenharmony_ci 241cb0ef41Sopenharmony_ci super('UNDICI_CONNECT') 251cb0ef41Sopenharmony_ci 261cb0ef41Sopenharmony_ci this.opaque = opaque || null 271cb0ef41Sopenharmony_ci this.responseHeaders = responseHeaders || null 281cb0ef41Sopenharmony_ci this.callback = callback 291cb0ef41Sopenharmony_ci this.abort = null 301cb0ef41Sopenharmony_ci 311cb0ef41Sopenharmony_ci addSignal(this, signal) 321cb0ef41Sopenharmony_ci } 331cb0ef41Sopenharmony_ci 341cb0ef41Sopenharmony_ci onConnect (abort, context) { 351cb0ef41Sopenharmony_ci if (!this.callback) { 361cb0ef41Sopenharmony_ci throw new RequestAbortedError() 371cb0ef41Sopenharmony_ci } 381cb0ef41Sopenharmony_ci 391cb0ef41Sopenharmony_ci this.abort = abort 401cb0ef41Sopenharmony_ci this.context = context 411cb0ef41Sopenharmony_ci } 421cb0ef41Sopenharmony_ci 431cb0ef41Sopenharmony_ci onHeaders () { 441cb0ef41Sopenharmony_ci throw new SocketError('bad connect', null) 451cb0ef41Sopenharmony_ci } 461cb0ef41Sopenharmony_ci 471cb0ef41Sopenharmony_ci onUpgrade (statusCode, rawHeaders, socket) { 481cb0ef41Sopenharmony_ci const { callback, opaque, context } = this 491cb0ef41Sopenharmony_ci 501cb0ef41Sopenharmony_ci removeSignal(this) 511cb0ef41Sopenharmony_ci 521cb0ef41Sopenharmony_ci this.callback = null 531cb0ef41Sopenharmony_ci 541cb0ef41Sopenharmony_ci let headers = rawHeaders 551cb0ef41Sopenharmony_ci // Indicates is an HTTP2Session 561cb0ef41Sopenharmony_ci if (headers != null) { 571cb0ef41Sopenharmony_ci headers = this.responseHeaders === 'raw' ? util.parseRawHeaders(rawHeaders) : util.parseHeaders(rawHeaders) 581cb0ef41Sopenharmony_ci } 591cb0ef41Sopenharmony_ci 601cb0ef41Sopenharmony_ci this.runInAsyncScope(callback, null, null, { 611cb0ef41Sopenharmony_ci statusCode, 621cb0ef41Sopenharmony_ci headers, 631cb0ef41Sopenharmony_ci socket, 641cb0ef41Sopenharmony_ci opaque, 651cb0ef41Sopenharmony_ci context 661cb0ef41Sopenharmony_ci }) 671cb0ef41Sopenharmony_ci } 681cb0ef41Sopenharmony_ci 691cb0ef41Sopenharmony_ci onError (err) { 701cb0ef41Sopenharmony_ci const { callback, opaque } = this 711cb0ef41Sopenharmony_ci 721cb0ef41Sopenharmony_ci removeSignal(this) 731cb0ef41Sopenharmony_ci 741cb0ef41Sopenharmony_ci if (callback) { 751cb0ef41Sopenharmony_ci this.callback = null 761cb0ef41Sopenharmony_ci queueMicrotask(() => { 771cb0ef41Sopenharmony_ci this.runInAsyncScope(callback, null, err, { opaque }) 781cb0ef41Sopenharmony_ci }) 791cb0ef41Sopenharmony_ci } 801cb0ef41Sopenharmony_ci } 811cb0ef41Sopenharmony_ci} 821cb0ef41Sopenharmony_ci 831cb0ef41Sopenharmony_cifunction connect (opts, callback) { 841cb0ef41Sopenharmony_ci if (callback === undefined) { 851cb0ef41Sopenharmony_ci return new Promise((resolve, reject) => { 861cb0ef41Sopenharmony_ci connect.call(this, opts, (err, data) => { 871cb0ef41Sopenharmony_ci return err ? reject(err) : resolve(data) 881cb0ef41Sopenharmony_ci }) 891cb0ef41Sopenharmony_ci }) 901cb0ef41Sopenharmony_ci } 911cb0ef41Sopenharmony_ci 921cb0ef41Sopenharmony_ci try { 931cb0ef41Sopenharmony_ci const connectHandler = new ConnectHandler(opts, callback) 941cb0ef41Sopenharmony_ci this.dispatch({ ...opts, method: 'CONNECT' }, connectHandler) 951cb0ef41Sopenharmony_ci } catch (err) { 961cb0ef41Sopenharmony_ci if (typeof callback !== 'function') { 971cb0ef41Sopenharmony_ci throw err 981cb0ef41Sopenharmony_ci } 991cb0ef41Sopenharmony_ci const opaque = opts && opts.opaque 1001cb0ef41Sopenharmony_ci queueMicrotask(() => callback(err, { opaque })) 1011cb0ef41Sopenharmony_ci } 1021cb0ef41Sopenharmony_ci} 1031cb0ef41Sopenharmony_ci 1041cb0ef41Sopenharmony_cimodule.exports = connect 105