hosseinhezami/laravel-gemini
Laravel package for integrating Google Gemini into your app. Send prompts, manage chats and responses, and work with text generation via a clean, developer-friendly API. Ideal for quickly adding AI features to Laravel projects.
Installation
composer require hosseinhezami/laravel-gemini
php artisan vendor:publish --tag=gemini-config
Add GEMINI_API_KEY to .env.
First Use Case: Text Generation
use HosseinHezami\LaravelGemini\Facades\Gemini;
$response = Gemini::text()
->prompt('Hello Gemini!')
->generate();
echo $response->content();
Key Files to Review
config/gemini.php (default models, API settings)app/Providers/GeminiServiceProvider.php (service binding)vendor/hosseinhezami/laravel-gemini/src/ (core logic)Builder Pattern for API Calls Chain methods for clarity and reusability:
Gemini::text()
->model('gemini-2.5-flash')
->system('You are a helpful assistant.')
->prompt('Explain Laravel Eloquent.')
->temperature(0.5)
->generate();
Multimodal Requests Combine text + files (e.g., document analysis):
Gemini::text()
->upload('document', storage_path('docs/report.pdf'))
->prompt('Summarize this document.')
->generate();
Streaming Responses For real-time UI updates:
return response()->stream(function () {
Gemini::text()
->prompt('Tell a story about AI.')
->stream(function ($chunk) {
echo "data: " . json_encode($chunk) . "\n\n";
});
}, 200, ['Content-Type' => 'text/event-stream']);
Caching Strategy Cache frequent queries to reduce API calls:
// Cache a prompt configuration
$cacheName = Gemini::text()
->prompt('Frequent question.')
->cache(ttl: '3600s');
// Reuse cached config
$response = Gemini::text()
->cachedContent($cacheName)
->generate();
Dynamic API Key Management Switch keys per request (e.g., for multi-tenancy):
Gemini::setApiKey('tenant-specific-key');
$response = Gemini::text()->prompt('...')->generate();
Gemini::video()
->prompt('Generate a 10-second clip.')
->generate(); // Returns a job ID; poll later
try-catch for HosseinHezami\LaravelGemini\Exceptions\GeminiException.throttle middleware for API key protection.Gemini facade in unit tests:
$this->mock(Gemini::class)->shouldReceive('text')->andReturnSelf();
API Key Priority:
setApiKey() overrides .env/config. Verify keys dynamically if using multi-tenancy.\Log::debug('API Key Source:', [
'env' => config('gemini.api_key'),
'runtime' => Gemini::getApiKey(),
]);
File Upload Limits:
$allowedTypes = ['image/png', 'application/pdf'];
if (!in_array($mime, $allowedTypes)) {
throw new \InvalidArgumentException('Unsupported file type.');
}
Streaming Quirks:
config/gemini.stream.chunk_size) affects latency/performance. Test with 1024 (default) and adjust.Gemini::text()->stream(function($chunk) { \Log::debug($chunk); }) to inspect chunks.Caching Caveats:
displayName for consistency:
$cacheName = Gemini::text()->prompt('...')->cache(displayName: 'user_guide_summary');
Gemini::caches()->delete($cacheName);
Model Compatibility:
gemini-2.5-flash lacks video generation). Check Gemini docs for model capabilities.Gemini::text()->model('gemini-2.5-flash-lite') for cost-sensitive operations.Enable Logging:
Set logging: true in config/gemini.php to log requests/responses to storage/logs/gemini.log.
Request Validation: Validate payloads before sending:
$builder = Gemini::text()->prompt('...');
\Log::debug('Request Payload:', $builder->getPayload());
Rate Limit Headers:
Check response->headers() for X-RateLimit-* headers to diagnose throttling.
File Upload Debugging: Verify file URIs with:
$fileId = Gemini::files()->upload('document', $path);
\Log::debug('Uploaded File:', Gemini::files()->get($fileId));
Custom Providers:
Extend the HosseinHezami\LaravelGemini\Contracts\Provider interface to support non-Gemini APIs:
class CustomProvider implements Provider {
public function generateContent(array $payload) { ... }
}
Register in config/gemini.php:
'providers' => [
'custom' => [
'class' => \App\Providers\CustomProvider::class,
],
],
Response Transformers: Override response handling in a service provider:
Gemini::extend(function ($app) {
$app->singleton('gemini.response', function () {
return new \App\Services\CustomResponseTransformer();
});
});
Middleware for API Keys: Add middleware to validate keys per request:
namespace App\Http\Middleware;
use Closure;
use HosseinHezami\LaravelGemini\Facades\Gemini;
class ValidateGeminiKey {
public function handle($request, Closure $next) {
if (!$request->hasValidGeminiKey()) {
Gemini::setApiKey($request->validated('api_key'));
}
return $next($request);
}
}
Event Listeners:
Listen for gemini.generated events to process responses:
event(new \HosseinHezami\LaravelGemini\Events\ContentGenerated($response));
How can I help you explore Laravel packages today?