tibor-src / xai-sdk-laravel
Unofficial Laravel integration for tibor-src/xai-sdk-php.
Requires
- php: ^8.2.0
- illuminate/support: ^11.48.0 || ^12.56.0 || ^13.23.0
- tibor-src/xai-sdk-php: ^0.2.8
Requires (Dev)
- larastan/larastan: ^3.10.0
- laravel/pint: ^1.30.3
- orchestra/testbench: ^9.12.0 || ^10.8.0 || ^11.3.0
- pestphp/pest: ^3.8.5 || ^4.7.5
- pestphp/pest-plugin-type-coverage: ^3.0 || ^4.0
Suggests
None
Provides
None
Conflicts
- laravel/framework: <11.48.0 || >=14.0.0
Replaces
None
README
Unofficial Laravel package for tibor-src/xai-sdk-php.
This package is not published or maintained by xAI. It registers that PHP client's SpaceXSI class in the Laravel container. SpaceXAI remains a deprecated alias of the same binding. Request and response behavior comes from tibor-src/xai-sdk-php.
Install
composer require tibor-src/xai-sdk-laravel
Requires PHP 8.2 or newer and tibor-src/xai-sdk-php 0.2.8 or newer. Set XAI_API_KEY in the environment, then publish the config if you want to override the client's constructor options:
php artisan vendor:publish --tag=xai-config
The published config/xai.php reads XAI_API_KEY. Leave the other values null to keep the PHP client's defaults.
Usage
use TiborSrc\XaiSdkPhp\SpaceXSI; $client = app(SpaceXSI::class); $response = $client->responses->create([ 'model' => 'grok-4.7', 'input' => 'Explain why the sky is blue in one sentence.', ]); echo $response->toText();
The client sends store as false unless you opt in. That differs from the API wire default. With storage disabled, it requests encrypted reasoning content so $response->toInput() can preserve context between turns. A create call that omits stream is sent as a stream and returned as the finished response. Pass 'stream' => false for one JSON response, or 'stream' => true for a ResponseStream.
TiborSrc\XaiSdkLaravel\Facades\SpaceXSI resolves the same container binding. TiborSrc\XaiSdkLaravel\Facades\SpaceXAI still resolves that binding and is deprecated. Resources are public properties on the client, so call them on the resolved instance: SpaceXSI::getFacadeRoot()->responses->create(...).
config/xai.php passes timeout and idle_timeout through to the PHP client. Null keeps the client's default. 0, a negative value, or anything longer than 24 hours becomes 24 hours. The same 24-hour cap applies to videos->wait() and batches->wait(): a timeout or interval longer than 24 hours means 24 hours. A wait() timeout of 0 or less still expires at once, and an interval of 0 or less still polls again without a pause.
retry_before_output still defaults to off. When it is true, the PHP client retries a dropped connection before the first response byte. That includes a streamed responses->create() whose connection drops after the 200 headers and before the first byte of the event stream.
Resources
The binding is the PHP client. It exposes:
responses(create,compact,get,delete,inputItems->list)models(list,get, pluslanguage,image, andvideo)images(generate,edit)videos(generate,edit,extend,get,wait)files(upload,list,get,delete,content,createPublicUrl,revokePublicUrl)batches(create,list,get,cancel,results,wait,requests)voice(speak,transcribe,list,get,custom,clientSecrets)tokenizer(encode)account(apiKey)
xai-sdk-php 0.2.8
The resolved client forwards request bodies to tibor-src/xai-sdk-php 0.2.8. This package does not validate aspect ratios, guidelines, model ids, or transcription formats.
responses->create()acceptsguidelines. Each entry is['type' => 'policy', 'category' => ..., 'behavior' => ...].categoryisnsfw,violence,profanity, orcyber.behaviorisdeclinefornsfw,violence, andprofanity, andallowforcyberonly. The API rejects other pairs with400, and it rejects the oldsexual,self_harm,illicit, andoffer_supportvalues with422.cybermust be enabled for the API key. Each category may appear at most once.$response->watermarkedand$stream->watermarkedare true when the response has the headerx-watermark: true. Watermarking is on by default for supported models from November 7, 2026.incomplete_details.reasoncan becontent_filter.temperatureandtop_pare sent as given. The API samplestemperatureabove 1 at 1, andtop_pabove the model's default at that default.voice->transcribe()acceptsaudio_formatwebm,avi, andmov. ABlobwithout a name is sent asaudio.webm,audio.avi, oraudio.movwhen its MIME type or first bytes say so.videos->generate()acceptsaspect_ratio21:9and5:2, along with1:1,16:9,9:16,4:3,3:4,3:2, and2:3.voice->clientSecrets->create()accepts the realtime models inTiborSrc\XaiSdkPhp\KNOWN_REALTIME_MODEL_IDS:grok-voice-latest(which points togrok-voice-3.0),grok-voice-3.0,grok-voice-2.0, andgrok-voice-think-fast-2.0. A session that asks forgrok-voice-think-fast-2.0reportsgrok-voice-2.0.- Live search is removed. The API returns HTTP 410 for
search_parametersand rejects a tool withtypelive_search. UsewebSearch()andxSearch().web_search_optionsis the chat-completions form of that removal; this client has no chat-completions resource. - A request may include up to 1000 tools.
xSearch()allowed_x_handlesandexcluded_x_handleseach take up to 20 handles. The client does not enforce either limit.
use TiborSrc\XaiSdkPhp\SpaceXSI; use function TiborSrc\XaiSdkPhp\webSearch; use function TiborSrc\XaiSdkPhp\xSearch; $response = app(SpaceXSI::class)->responses->create([ 'model' => 'grok-4.7', 'input' => 'Hello', 'guidelines' => [ ['type' => 'policy', 'category' => 'violence', 'behavior' => 'decline'], ['type' => 'policy', 'category' => 'cyber', 'behavior' => 'allow'], ], 'tools' => [webSearch(), xSearch()], ]);
Tests
composer test
That runs Pint, PHPStan at the maximum level, Pest's type coverage at 100%, and the test suite. Tests mock the PHP client's HTTP layer and do not call the live API.
License
Apache License 2.0. See LICENSE and NOTICE.