PHPackages                             meabed/php-parallel-soap - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [HTTP &amp; Networking](/categories/http)
4. /
5. meabed/php-parallel-soap

ActiveLibrary[HTTP &amp; Networking](/categories/http)

meabed/php-parallel-soap
========================

Parallel, multi-curl PHP SoapClient that performs many SOAP requests concurrently

4.0.0(2w ago)4393.5k↓55.8%18[1 issues](https://github.com/Meabed/php-parallel-soap/issues)[1 PRs](https://github.com/Meabed/php-parallel-soap/pulls)MITPHPPHP &gt;=8.0CI passing

Since Jun 17Pushed 2w ago4 watchersCompare

[ Source](https://github.com/Meabed/php-parallel-soap)[ Packagist](https://packagist.org/packages/meabed/php-parallel-soap)[ Docs](https://github.com/meabed/php-parallel-soap)[ RSS](/packages/meabed-php-parallel-soap/feed)WikiDiscussions master Synced 2d ago

READMEChangelog (1)Dependencies (10)Versions (15)Used By (0)

Parallel, Multi-Curl PHP SoapClient
===================================

[](#parallel-multi-curl-php-soapclient)

 [ ![CI Status](https://github.com/meabed/php-parallel-soap/actions/workflows/ci.yml/badge.svg) ](https://github.com/meabed/php-parallel-soap/actions/workflows/ci.yml) [ ![Latest Version](https://camo.githubusercontent.com/d36e9d19a46458f712384f53461d80b467df2b40b8d1f328abccba79276de033/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f762f6d65616265642f7068702d706172616c6c656c2d736f61702e7376673f7374796c653d666c61742d737175617265) ](https://packagist.org/packages/meabed/php-parallel-soap) [ ![PHP Version](https://camo.githubusercontent.com/38262028e51a5a588004713d08254f2c20d7854a78faab7e47e8630ae4a53967/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f7068702d762f6d65616265642f7068702d706172616c6c656c2d736f61702e7376673f7374796c653d666c61742d737175617265) ](https://packagist.org/packages/meabed/php-parallel-soap) [ ![Total Downloads](https://camo.githubusercontent.com/f8ab6e9b9242e3736e4f520decf010f86a6ba64be64538a1bb17cc69174993c8/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f646d2f6d65616265642f7068702d706172616c6c656c2d736f61702e7376673f7374796c653d666c61742d737175617265) ](https://packagist.org/packages/meabed/php-parallel-soap) [ ![Software License](https://camo.githubusercontent.com/55c0218c8f8009f06ad4ddae837ddd05301481fcf0dff8e0ed9dadda8780713e/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f6c6963656e73652d4d49542d627269676874677265656e2e7376673f7374796c653d666c61742d737175617265) ](LICENSE.md)

A drop-in replacement for PHP's native `SoapClient` that can fire **many SOAP requests in parallel** using curl's multi handle, while keeping the familiar synchronous SoapClient API when you need it.

Working with SOAP is often painful:

- SOAP messages are verbose and obscure.
- Performance suffers because the native client has no connection pooling, TLS session reuse, or low-level TCP tuning.
- A list of calls can only be sent sequentially — you loop and wait for each response.
- Debugging the underlying HTTP (headers / payloads / errors) is hard.

`ParallelSoapClient` lets you send requests concurrently and gives you hooks for a PSR-3 logger, response parsing, custom `SOAPAction` headers, XML formatting and arbitrary curl options (such as TLS session sharing and connection reuse).

Features
--------

[](#features)

- **Single and parallel modes** — switch with `setMulti(true|false)`.
- **True concurrency** via `curl_multi_exec` — consecutive calls no longer block each other.
- **TLS / DNS / cookie session sharing** through a shared curl handle per endpoint.
- **Per-request curl metadata** captured in `$client->curlInfo`.
- **Deterministic request ids** — identical payloads hash to the same id, so duplicate calls are sent only once.
- **First-class exception handling** in both single and parallel modes.
- **Pluggable hooks** — logger, result parser, `SOAPAction` builder, XML formatter, debug callback.

Requirements
------------

[](#requirements)

- PHP **8.0+**
- `ext-soap`, `ext-curl`, `ext-libxml`

The library is tested in CI against PHP **8.1, 8.2, 8.3, 8.4 and 8.5** (including a TLS suite).

> **Upgrading from 3.x?** 4.0 moves the client out of the now-reserved `Soap\` namespace into `Meabed\ParallelSoap\`. Change `use Soap\ParallelSoapClient;` to `use Meabed\ParallelSoap\ParallelSoapClient;` — the API is otherwise unchanged. 3.x also fatal-errors on PHP 8.4/8.5, so upgrading is required there. See [UPGRADING.md](UPGRADING.md)and the [CHANGELOG](CHANGELOG.md).

Installation
------------

[](#installation)

```
composer require meabed/php-parallel-soap
```

Usage
-----

[](#usage)

### Synchronous (single) call

[](#synchronous-single-call)

Behaves exactly like the native `SoapClient`, but the transport is curl:

```
use Meabed\ParallelSoap\ParallelSoapClient;

$client = new ParallelSoapClient($wsdl, [
    'trace' => true,
    'exceptions' => true,
    'soap_version' => SOAP_1_1,
    // Optional: unwrap the "" envelope into a scalar value.
    'resFn' => fn ($method, $res) => $res->{$method . 'Result'} ?? $res,
]);

$client->setMulti(false); // default

$sum = $client->Add(['intA' => 4, 'intB' => 3]); // 7
```

### Parallel (multi) call

[](#parallel-multi-call)

Queue any number of calls, then execute them all at once with `run()`:

```
$client->setMulti(true);
$client->setCurlOptions([
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_SSL_VERIFYPEER => true,
]);

// Each call returns a request id instead of a result while in parallel mode.
$id1 = $client->Add(['intA' => 4,  'intB' => 3]);
$id2 = $client->Add(['intA' => 10, 'intB' => 20]);
$id3 = $client->Add(['intA' => 10, 'intB' => 20]); // identical payload => same id as $id2

// Fire every queued request concurrently. The client resets to single mode afterwards.
$responses = $client->run();

echo $responses[$id1]; // 7
echo $responses[$id2]; // 30
```

### Handling errors in parallel mode

[](#handling-errors-in-parallel-mode)

In parallel mode exceptions are **not** thrown; instead each result is either the parsed response or a `SoapFault` object, so you inspect the result type:

```
$responses = $client->run();

foreach ($responses as $id => $response) {
    if ($response instanceof SoapFault) {
        // Network error, malformed response, server fault, ...
        echo "Error for {$id}: {$response->getMessage()}\n";
        continue;
    }
    echo "OK {$id}: {$response}\n";
}
```

Calling a method that does not exist in the WSDL short-circuits before any HTTP request and returns a string prefixed with `ParallelSoapClient::ERROR_STR` (`*ERROR*`).

### Running a subset of queued requests

[](#running-a-subset-of-queued-requests)

```
$responses = $client->run([$id1, $id3]); // only execute these two
```

Configuration
-------------

[](#configuration)

All hooks are passed through the constructor `$options` array (and are removed before being handed to the native `SoapClient`):

OptionTypePurpose`logger``Psr\Log\LoggerInterface`PSR-3 logger; defaults to `NullLogger`.`resFn``callable($method, $res)`Transform/unwrap each parsed response.`soapActionFn``callable($action, $headers)`Build the outgoing `SOAPAction` header(s).`formatXmlFn``callable($xml)`Format the request XML before it is logged.`debugFn``callable($res, $id)`Receive each response/exception for debugging or metadata capture.Plus the runtime setters:

- `setMulti(bool)` — toggle parallel mode.
- `setCurlOptions(array)` — any `CURLOPT_*` options (TLS, timeouts, proxies, verbosity…).
- `setLogSoapRequest(bool)` — log every request payload through the PSR-3 logger.

See the [`example/`](example) directory for complete, runnable scripts.

How it works
------------

[](#how-it-works)

`__doRequest()` is overridden to build a curl handle per call instead of sending the request immediately. In parallel mode the handles are accumulated and executed together through `curl_multi_*`; the raw responses are then fed back through the native SOAP parser so you get ordinary PHP objects (or `SoapFault`s) out the other end. A shared curl handle per endpoint enables TLS session, DNS and cookie reuse across the batch.

For a deeper walkthrough — the request lifecycle, the local SOAP server used by the tests, and diagrams — see [docs/development.md](docs/development.md).

Testing
-------

[](#testing)

The test suite has two layers:

- **Hermetic tests** (`tests/Hermetic`) run against a local SOAP server started on a free port — over both **HTTP** and **TLS** (with a generated self-signed certificate). They need no network access and run by default.
- **External integration tests** (`tests/Crcind`, `tests/Dne`) hit public demo SOAP services. They are tagged with the `external` group, excluded from the default run, and skip automatically when the host is unreachable.

```
composer install

composer test          # hermetic suite only (default)
composer check-style   # PSR-2 coding standard
composer stan          # PHPStan static analysis
composer lint          # php-l syntax lint
composer ci            # lint + style + stan + tests

vendor/bin/phpunit --group external   # opt into the external integration tests
```

You can also run the local SOAP server on its own with `composer dev-server` and call it directly — see [docs/development.md](docs/development.md) for a worked example.

Contributing
------------

[](#contributing)

Contributions are welcome — please review the [guidelines](CONTRIBUTING.md):

- [One feature or change per pull request](CONTRIBUTING.md#only-one-feature-or-change-per-pull-request)
- [Write meaningful commit messages](CONTRIBUTING.md#write-meaningful-commit-messages)
- [Follow the existing coding standards](CONTRIBUTING.md#follow-the-existing-coding-standards)

Changelog
---------

[](#changelog)

See [CHANGELOG.md](CHANGELOG.md) for a list of notable changes.

Acknowledgements
----------------

[](#acknowledgements)

Thanks to everyone who has reported issues and contributed fixes, including [@c266](https://github.com/c266) for independently diagnosing the PHP 8.5 `__doRequest()`signature break ([\#180](https://github.com/meabed/php-parallel-soap/pull/180), [\#179](https://github.com/meabed/php-parallel-soap/issues/179)).

License
-------

[](#license)

Released under the [MIT license](LICENSE.md).

###  Health Score

63

—

FairBetter than 99% of packages

Maintenance96

Actively maintained with recent releases

Popularity45

Moderate usage in the ecosystem

Community18

Small or concentrated contributor base

Maturity76

Established project with proven stability

 Bus Factor1

Top contributor holds 62.3% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~584 days

Recently: every ~703 days

Total

6

Last Release

16d ago

Major Versions

1.0.1 → 2.02019-02-12

2.0 → 3.0.02023-07-24

3.0.1 → 4.0.02026-06-17

PHP version history (4 changes)1.0.0PHP &gt;=7.0

2.0PHP &gt;=7.2

3.0.0PHP &gt;=8

4.0.0PHP &gt;=8.0

### Community

Maintainers

![](https://www.gravatar.com/avatar/e0688fa386c5dbcbb27c78b325cf9a957ddf8b07c3bf53271060e2a32aa91975?d=identicon)[meabed](/maintainers/meabed)

---

Top Contributors

[![meabed](https://avatars.githubusercontent.com/u/45731?v=4)](https://github.com/meabed "meabed (251 commits)")[![renovate[bot]](https://avatars.githubusercontent.com/in/2740?v=4)](https://github.com/renovate[bot] "renovate[bot] (97 commits)")[![renovate-bot](https://avatars.githubusercontent.com/u/25180681?v=4)](https://github.com/renovate-bot "renovate-bot (53 commits)")[![rstrong-pica9](https://avatars.githubusercontent.com/u/3339806?v=4)](https://github.com/rstrong-pica9 "rstrong-pica9 (2 commits)")

---

Tags

asynchronouscurlcurl-multiparallelsoapsoap-clientsoap-serverasyncasynchronouscurlconcurrentparallelsoapwsdlphp8soap-clientmulticurlcurl\_multi

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/meabed-php-parallel-soap/health.svg)

```
[![Health](https://phpackages.com/badges/meabed-php-parallel-soap/health.svg)](https://phpackages.com/packages/meabed-php-parallel-soap)
```

###  Alternatives

[meabed/asynchronous-soap

Parallel, multi-curl PHP SoapClient that performs many SOAP requests concurrently

4411.7k](/packages/meabed-asynchronous-soap)[api-platform/metadata

API Resource-oriented metadata attributes and factories

275.0M219](/packages/api-platform-metadata)[chuyskywalker/rolling-curl

Rolling-Curl: A non-blocking, non-dos multi-curl library for PHP

213461.0k6](/packages/chuyskywalker-rolling-curl)[phpgt/fetch

Asynchronous HTTP client with promises.

3726.1k5](/packages/phpgt-fetch)[khr/php-mcurl-client

wrap curl client (http client) for PHP 5.3; using php multi curl, parallel request and write asynchronous code

71230.4k6](/packages/khr-php-mcurl-client)[aalfiann/parallel-request-php

A PHP class to create multiple request in parallel (non-blocking).

1219.8k3](/packages/aalfiann-parallel-request-php)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
