Bug #81029 [Opn]: SOAP HTTP socket not closing on object destruction

From: Date: Mon, 17 May 2021 14:43:09 +0000
Subject: Bug #81029 [Opn]: SOAP HTTP socket not closing on object destruction
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-233873@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=81029&edit=1

 ID:                 81029
 Updated by:         nikic@php.net
 Reported by:        kdonaldson at staff dot nexigen dot digital
 Summary:            SOAP HTTP socket not closing on object destruction
 Status:             Open
 Type:               Bug
 Package:            SOAP related
 Operating System:   macOS and Cent OS 7
 PHP Version:        7.4.19
 Block user comment: N
 Private report:     N

 New Comment:

@cmb: As it's stored in a property, shouldn't that happen automatically when the object
(and thus also its properties) are destroyed?


Previous Comments:
------------------------------------------------------------------------
[2021-05-11 11:27:24] cmb@php.net

It seems to me we're missing to undo the refcount increment[1]
when the object is destroyed.

[1] <https://github.com/php/php-src/blob/php-7.4.19/ext/soap/php_http.c#L523>

------------------------------------------------------------------------
[2021-05-11 10:32:30] kdonaldson at staff dot nexigen dot digital

Description:
------------
If a SoapClient object is constructed without specifying the 'keep_alive' option to false,
the socket never appears to be closed if it falls out of scope

The provided script should be able to reproduce this, you can check the open sockets by running the
script like: "php /path/to/script.php &" and using the resulting PID on "lsof -a
-p {pid}"

You should slowly see a list of TCP connections slowly build up over time similar to this:

php     4396 vagrant    3u  IPv4  53416      0t0     TCP
homestead:57814->ec2-52-7-155-169.compute-1.amazonaws.com:https (ESTABLISHED)
php     4396 vagrant    4u  IPv4  53447      0t0     TCP
homestead:57816->ec2-52-7-155-169.compute-1.amazonaws.com:https (ESTABLISHED)
php     4396 vagrant    5u  IPv4  54451      0t0     TCP
homestead:57818->ec2-52-7-155-169.compute-1.amazonaws.com:https (ESTABLISHED)

If instead you were to add ['keep_alive' => false] as the options parameter on the
SoapClient you'll see that the TCP connections don't appear to build up.

While I do understand the purpose of Keep Alive to keep a single connection open, I would assume
this is still a bug as the SoapClient has gone out of scope and new SoapClient objects don't
appear to reuse the existing connection and simply ignore it creating a new one.

Test script:
---------------
<?php

function call(int $number) {
    $client = new SoapClient('https://www.dataaccess.com/webservicesserver/NumberConversion.wso?WSDL');
    $response = $client->NumberToWords(['ubiNum' => $number]);
    return $response->NumberToWordsResult;
}

$numbers = array_fill(0, 10000, 1);

foreach ($numbers as $number) {
    call($number);
}

Expected result:
----------------
The socket to be closed when the SoapClient object falls out of scope or destructs

Actual result:
--------------
The socket stays open and contributes to the open file limit / file descriptor limit


------------------------------------------------------------------------



--
Edit this bug report at https://bugs.php.net/bug.php?id=81029&edit=1


Thread (20 messages)

« previous php.bugs (#233873) next »