Testing / Mocking the Client
BioTime::__construct() accepts an optional Guzzle ClientInterface as its second argument, so you can inject a mock HTTP handler in tests without ever contacting a real device:
use BioTime\BioTime;
use BioTime\Config;
use GuzzleHttp\Client;
use GuzzleHttp\Handler\MockHandler;
use GuzzleHttp\Handler\HandlerStack;
use GuzzleHttp\Psr7\Response;
$mock = new MockHandler([
// First call: TokenManager's POST /api-token-auth/
new Response(200, [], json_encode(['token' => 'fake-token'])),
// Second call: the actual resource request
new Response(200, [], json_encode([
'count' => 0,
'next' => null,
'previous' => null,
'data' => [],
])),
]);
$httpClient = new Client([
'handler' => HandlerStack::create($mock),
]);
$biotime = new BioTime(
Config::fromArray([
'ip' => 'test',
'username' => 'x',
'password' => 'y',
]),
$httpClient
);
$biotime->employees()->all();Queue one response per HTTP call
Each real request the SDK makes needs its own queued Response in the MockHandler. A first call to any resource method typically needs two responses: one for the token request, and one for the actual endpoint. If you call another resource method afterward in the same test, and the in-memory token cache is still valid, you'll only need to queue one more response (the token isn't re-requested) — unless you use a fresh Config/TokenManager per test, or force a 401, which triggers a second auth call plus a retry.
Simulating errors
Queue an error status to exercise ApiException/AuthenticationException handling:
$mock = new MockHandler([
new Response(200, [], json_encode(['token' => 'fake-token'])),
new Response(404, [], json_encode(['detail' => 'Not found'])),
]);Running the package's own test suite
The package declares PHPUnit as a dev dependency and a Composer test script:
"require-dev": {
"phpunit/phpunit": "^10.0"
},
"scripts": {
"test": "phpunit"
}If you're contributing to the SDK itself, clone the repository, run composer install, and run:
composer testSee Contributing for the full contributor workflow.