@@ -23,11 +23,42 @@ export interface IAttachment {
2323 body : NodeJS . ReadableStream ;
2424}
2525
26- function getPortFromUrl ( url : URL ) : string {
27- if ( url . port ) return url . port ;
28- if ( url . protocol . toLowerCase ( ) === 'https:' ) return '443' ;
29- if ( url . protocol . toLowerCase ( ) === 'http:' ) return '80' ;
30- return '' ;
26+ // The URL API normalizes away default ports (:80 on http, :443 on https),
27+ // so parse the port from the raw URL string to preserve ports.
28+ function getPortFromUrl ( url : string ) : string {
29+ // Capture the authority section (everything between :// and the first /?#)
30+ const authorityMatch = / ^ [ a - z ] [ a - z 0 - 9 + . - ] * : \/ \/ ( [ ^ / ? # ] + ) / i. exec ( url ) ;
31+ if ( ! authorityMatch ) {
32+ return '' ;
33+ }
34+
35+ const hostPort = authorityMatch [ 1 ] ;
36+
37+ // IPv6 address: [::1] or [::1]:port
38+ if ( hostPort . startsWith ( '[' ) ) {
39+ const bracketEnd = hostPort . indexOf ( ']' ) ;
40+ if ( bracketEnd !== - 1 && hostPort [ bracketEnd + 1 ] === ':' ) {
41+ const port = hostPort . slice ( bracketEnd + 2 ) ;
42+ return / ^ \d + $ / . test ( port ) ? port : '' ;
43+ }
44+ return '' ;
45+ }
46+
47+ // IPv4 / hostname: host or host:port
48+ const colonIndex = hostPort . lastIndexOf ( ':' ) ;
49+ if ( colonIndex === - 1 ) {
50+ return '' ;
51+ }
52+ const port = hostPort . slice ( colonIndex + 1 ) ;
53+ return / ^ \d + $ / . test ( port ) ? port : '' ;
54+ }
55+
56+ // Add brackets to IPv6 addresses
57+ function bracketIPv6 ( hostname : string ) : string {
58+ if ( hostname . startsWith ( '[' ) || hostname . indexOf ( ':' ) === - 1 ) {
59+ return hostname ;
60+ }
61+ return `[${ hostname } ]` ;
3162}
3263
3364/**
@@ -59,16 +90,15 @@ export class HttpClient implements IHttpClient {
5990 const curl = new URL ( rurl ) ;
6091 const method = data ? 'POST' : 'GET' ;
6192
62- const host = curl . hostname ;
63-
64- const port = getPortFromUrl ( curl ) ;
93+ const port = getPortFromUrl ( rurl ) ;
94+ const host = port ? `${ bracketIPv6 ( curl . hostname ) } :${ port } ` : curl . host || curl . hostname ;
6595 const headers : IHeaders = {
6696 'User-Agent' : 'node-soap/' + version ,
6797 'Accept' : 'text/html,application/xhtml+xml,application/xml,text/xml;q=0.9,*/*;q=0.8' ,
6898 'Accept-Encoding' : 'none' ,
6999 'Accept-Charset' : 'utf-8' ,
70100 ...( exoptions . forever && { Connection : 'keep-alive' } ) ,
71- 'Host' : host + ( port ? ':' + port : '' ) ,
101+ 'Host' : host ,
72102 } ;
73103 const mergeOptions = [ 'headers' ] ;
74104
0 commit comments