{"id":35912191,"url":"https://github.com/marcohefti/request-network-api-client-php","last_synced_at":"2026-03-10T09:09:15.009Z","repository":{"id":328079943,"uuid":"1114143381","full_name":"marcohefti/request-network-api-client-php","owner":"marcohefti","description":"Request Network REST API client for PHP","archived":false,"fork":false,"pushed_at":"2026-02-25T11:45:46.000Z","size":9541,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-02-25T15:44:52.537Z","etag":null,"topics":["api-client","defi","payments","php","request-network","web3"],"latest_commit_sha":null,"homepage":"","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/marcohefti.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-12-11T00:50:44.000Z","updated_at":"2026-02-25T11:45:49.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/marcohefti/request-network-api-client-php","commit_stats":null,"previous_names":["marcohefti/request-network-api-client-php"],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/marcohefti/request-network-api-client-php","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/marcohefti%2Frequest-network-api-client-php","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/marcohefti%2Frequest-network-api-client-php/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/marcohefti%2Frequest-network-api-client-php/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/marcohefti%2Frequest-network-api-client-php/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/marcohefti","download_url":"https://codeload.github.com/marcohefti/request-network-api-client-php/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/marcohefti%2Frequest-network-api-client-php/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":30328306,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-03-10T05:25:20.737Z","status":"ssl_error","status_checked_at":"2026-03-10T05:25:17.430Z","response_time":106,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["api-client","defi","payments","php","request-network","web3"],"created_at":"2026-01-10T03:38:32.457Z","updated_at":"2026-03-10T09:09:14.990Z","avatar_url":"https://github.com/marcohefti.png","language":"PHP","readme":"# Request Network API Client (PHP)\n\n[![Latest Version](https://img.shields.io/packagist/v/marcohefti/request-network-api-client.svg?style=flat-square)](https://packagist.org/packages/marcohefti/request-network-api-client)\n[![Tests](https://img.shields.io/github/actions/workflow/status/marcohefti/request-network-api-client-php/tests.yml?branch=main\u0026label=tests\u0026style=flat-square)](https://github.com/marcohefti/request-network-api-client-php/actions/workflows/tests.yml)\n[![PHP Version](https://img.shields.io/packagist/php-v/marcohefti/request-network-api-client.svg?style=flat-square)](https://packagist.org/packages/marcohefti/request-network-api-client)\n[![License](https://img.shields.io/packagist/l/marcohefti/request-network-api-client.svg?style=flat-square)](LICENSE)\n[![Total Downloads](https://img.shields.io/packagist/dt/marcohefti/request-network-api-client.svg?style=flat-square)](https://packagist.org/packages/marcohefti/request-network-api-client)\n\nPHP client for the Request Network hosted REST API. It mirrors the TypeScript client's\nsurface so WooCommerce and other PHP runtimes can talk to Request without a Node bridge.\n\n## Installation\n\nInstall via Composer:\n\n```bash\ncomposer require marcohefti/request-network-api-client\n```\n\n## Quick start\n\nMinimal example using the static factory:\n\n```php\nuse RequestSuite\\RequestPhpClient\\RequestClient;\n\n$client = RequestClient::create([\n    'apiKey' =\u003e $_ENV['REQUEST_API_KEY'],\n]);\n\n// Create a new payment request\n$request = $client-\u003erequests()-\u003ecreate([\n    'amount' =\u003e '100',\n    'invoiceCurrency' =\u003e 'USD',\n    'paymentCurrency' =\u003e 'ETH-sepolia-sepolia',\n    'payee' =\u003e '0x0000000000000000000000000000000000000000',\n    'reference' =\u003e 'order-123',\n]);\n\n$requestId = $request['requestId'] ?? null;\n\n// Search for payments\n$payments = $client-\u003epayments()-\u003esearch(['requestId' =\u003e $requestId]);\n```\n\n\n## Why Use This Client?\n\nInstead of manually building HTTP requests and handling errors, this client provides:\n\n- **Type Safety**: Strict type hints and PHPDoc throughout (PHPStan level 7 clean)\n- **Automatic Retries**: Exponential backoff with jitter for transient failures\n- **Schema Validation**: Runtime validation against OpenAPI specs (optional)\n- **Webhook Security**: Timing-safe signature verification with secret rotation support\n- **Error Handling**: Rich exception hierarchy with correlation IDs and retry headers\n- **Logging**: Automatic credential redaction in PSR-3 compatible logs\n- **Testing**: Built-in FakeHttpAdapter for easy unit testing\n\n**Before vs After:** See `docs/BEFORE-AFTER.md` for side-by-side code comparisons showing how this client simplifies common Request Network API operations.\n\n## Documentation\n\n- **[Architecture](docs/ARCHITECTURE.md)** - System design and internals\n- **[Testing](docs/TESTING.md)** - Test strategy, coverage, and validation\n- **[HTTP Client](docs/HTTP-CLIENT.md)** - HTTP adapter, retry behavior, error handling\n- **[Webhooks](docs/WEBHOOKS.md)** - Signature verification, middleware, event handlers\n- **[Before/After](docs/BEFORE-AFTER.md)** - Code comparisons showing client benefits\n- **[Troubleshooting](docs/TROUBLESHOOTING.md)** - Common issues and solutions\n- **[Publishing](docs/PUBLISHING.md)** - Release checklist\n\n## What this client covers\n\n- PHP-first `RequestClient` with facades for requests (including request listing), payouts, payments,\n  secure payments, payer/compliance (v1+v2), client IDs, currencies (v1+v2), and legacy pay.\n- Shared HTTP pipeline with retry, logging, and runtime validation driven by the synced OpenAPI spec.\n- Webhook utilities: signature verifier, typed event objects, parser, dispatcher, PSR‑15 middleware, and\n  testing helpers that mirror the TypeScript webhook module.\n- Env‑based factory for backend and WooCommerce usage, with PSR‑4 autoloading under\n  `RequestSuite\\RequestPhpClient`.\n\n## Compatibility\n\n- **PHP:** \u003e= 8.2\n- **Frameworks:** Designed for PSR‑15 stacks (e.g., WooCommerce, Laravel/Symfony via adapters)\n- **HTTP Clients:** Any PSR-18 compatible client (Guzzle, Symfony HttpClient, etc.) or built-in cURL adapter\n\n## Development\n\nCommon commands:\n\n- `composer test` – PHPUnit suites.\n- `composer stan` – PHPStan analysis.\n- `composer cs` / `composer lint` – coding standards (if configured).\n- `composer update:spec` – sync OpenAPI + webhook fixtures from the contracts package.\n\nSee `docs/TESTING.md` and `docs/ARCHITECTURE.md` for the full testing strategy, spec sync flow,\nand domain layout.\n\n## Webhooks\n\nThe webhook module provides secure signature verification, typed event objects, and PSR-15 middleware:\n\n```php\nuse RequestSuite\\RequestPhpClient\\Webhooks\\Events\\PaymentConfirmedEvent;\nuse RequestSuite\\RequestPhpClient\\Webhooks\\WebhookParser;\n\n$parser = new WebhookParser();\n$parsed = $parser-\u003eparse([\n    'rawBody' =\u003e (string) $request-\u003egetBody(),\n    'headers' =\u003e $request,\n    'secret' =\u003e [$_ENV['REQUEST_WEBHOOK_SECRET']],\n]);\n\nif ($parsed-\u003eevent() instanceof PaymentConfirmedEvent) {\n    $data = $parsed-\u003eevent()-\u003edata();\n    $requestId = $data-\u003estring('requestId');\n    // Handle payment confirmation\n}\n```\n\n**Features:**\n- Timing-safe signature verification with secret rotation support\n- Typed event classes for all webhook types\n- PSR-15 middleware for framework integration\n- Event dispatcher for handler registration\n- Testing helpers for unit tests\n\nSee `docs/WEBHOOKS.md` and `examples/webhook-handler-middleware.php` for complete webhook integration examples.\n\n## Logging \u0026 redaction\n\nPass either a callable `(string $event, array $context) =\u003e void` or a PSR-3 `LoggerInterface` via\n`RequestClient::create(['logger' =\u003e ...])` to receive lifecycle events (`request:start`,\n`request:response`, `request:error`). When you supply a PSR-3 logger, the client automatically wraps it with\n`Logging\\PsrLoggerAdapter`, which redacts sensitive fields (API keys, Authorization headers, webhook signatures) via\n`Logging\\Redactor` before handing context to your logger:\n\n```php\nuse Monolog\\Handler\\StreamHandler;\nuse Monolog\\Logger;\nuse RequestSuite\\RequestPhpClient\\RequestClient;\n\n$logger = new Logger('request-network-api-client');\n$logger-\u003epushHandler(new StreamHandler('php://stdout'));\n\n$client = RequestClient::create([\n    'apiKey' =\u003e $_ENV['REQUEST_API_KEY'],\n    'logger' =\u003e $logger,\n    'logLevel' =\u003e 'info',\n]);\n```\n\n`WebhookMiddleware` shares the same logger plumbing and emits `webhook:verified`, `webhook:dispatched`, and\n`webhook:error` events so you can trace webhook flows without leaking secrets.\n\n## Testing harness\n\nUnit tests (and downstream consumers) can inject the built-in `Testing\\FakeHttpAdapter` to queue\nresponses and assert requests without rolling bespoke stubs:\n\n```php\nuse RequestSuite\\RequestPhpClient\\Testing\\FakeHttpAdapter;\n\n$fake = new FakeHttpAdapter([\n    FakeHttpAdapter::jsonResponse(['status' =\u003e 'ok']),\n]);\n\n$client = RequestClient::create([\n    'apiKey' =\u003e 'rk_test',\n    'httpAdapter' =\u003e $fake,\n]);\n\n$client-\u003erequests()-\u003ecreate([...]);\n$fake-\u003eassertSent(static fn ($pending) =\u003e $pending-\u003emethod() === 'POST');\n```\n\nSee `docs/TESTING.md` for the full harness (coverage guard, parity scripts, integration plans).\n\n## Composer scripts\n\n- `composer test` - runs PHPUnit using `phpunit.xml.dist`.\n- `composer stan` - runs PHPStan static analysis (level 7) using `phpstan.neon.dist`.\n- `composer coverage` - prints PHPUnit coverage summary to the terminal.\n- `composer cs` - runs PHPCS with PSR-12 + Slevomat rules.\n- `composer cs:fix` - auto-fixes code style issues where possible.\n- `composer md` - runs PHPMD (codesize/design/unusedcode) with configured thresholds.\n- `composer cpd` - runs PHPCPD (copy/paste detection).\n- `composer deps:rules` - runs PHPStan dependency rules (architecture contracts).\n\nThese are also invoked from the workspace validator (see root `scripts/validate.sh`).\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmarcohefti%2Frequest-network-api-client-php","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmarcohefti%2Frequest-network-api-client-php","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmarcohefti%2Frequest-network-api-client-php/lists"}