PHP SDK
Official PHP SDK for Venym Search APIs. Built with modern PHP practices, supporting PHP 8+ features and seamless framework integration.
Quick Start
1. Installation
2. Basic Usage
<?php
require_once 'vendor/autoload.php';
use Venym Search\VenymSearchClient;
use Venym Search\Exceptions\VenymSearchException;
// Initialize the client
$client = new VenymSearchClient([
'api_key' => $_ENV['VENYM_SEARCH_API_KEY'],
// 'base_url' => 'https://www.search.venym.io/api/v1', // optional
// 'timeout' => 30, // optional, default 30 seconds
// 'retries' => 3, // optional, default 3
]);
try {
// Perform a search
$result = $client->search([
'query' => 'latest PHP frameworks 2025',
'max_results' => 10
]);
echo "Found " . count($result['search_results']) . " results\n";
echo "Credits used: " . $result['credits_used'] . "\n";
echo "Credits remaining: " . $result['remaining_credits'] . "\n";
// Display results
foreach ($result['search_results'] as $index => $item) {
echo ($index + 1) . ". " . $item['title'] . "\n";
echo " URL: " . $item['link'] . "\n";
echo " Snippet: " . $item['snippet'] . "\n";
echo " Date: " . $item['date'] . "\n\n";
}
} catch (VenymSearchException $e) {
echo "Search failed: " . $e->getMessage() . "\n";
echo "Error code: " . $e->getCode() . "\n";
if ($e->hasRequestId()) {
echo "Request ID: " . $e->getRequestId() . "\n";
}
}Key Features
Built with modern PHP practices, optimized for speed and memory efficiency
Strong typing with PHP 8+ features including union types and attributes
Seamless integration with Laravel, Symfony, and other PHP frameworks
Enterprise-grade error handling, logging, and monitoring capabilities
Core Methods
| Method | Description | Returns |
|---|---|---|
| search($options) | Perform real-time web search with advanced filtering options | array |
| scrape($options) | Extract content from single webpage with advanced parsing | array |
| scrapeBulk($options) | Scrape multiple URLs concurrently with progress tracking | array |
| research($options) | AI-powered research across multiple sources with summarization | array |
| getUsage() | Get current API usage statistics and remaining credits | array |
| validateKey() | Validate API key and check account status | boolean |
Web Scraping Examples
Extract content from any webpage with advanced parsing and bulk operations:
<?php
require_once 'vendor/autoload.php';
use Venym Search\VenymSearchClient;
$client = new VenymSearchClient([
'api_key' => $_ENV['VENYM_SEARCH_API_KEY']
]);
// Single page scraping
function scrapeWebpage($client) {
try {
$result = $client->scrape([
'url' => 'https://example.com/article',
'extract_options' => ['title', 'text', 'links', 'images'],
'follow_redirects' => true,
'wait_for_selector' => '.content', // optional
'remove_selectors' => ['.ads', '.popup'] // optional
]);
echo "Page title: " . $result['primary_content']['title'] . "\n";
echo "Content length: " . strlen($result['primary_content']['text']) . " characters\n";
echo "Found links: " . count($result['extracted_data']['links']) . "\n";
echo "Found images: " . count($result['extracted_data']['images']) . "\n";
} catch (Exception $e) {
echo "Scraping failed: " . $e->getMessage() . "\n";
}
}
// Bulk scraping
function bulkScrape($client) {
$urls = [
'https://example.com/page1',
'https://example.com/page2',
'https://example.com/page3'
];
try {
$results = $client->scrapeBulk([
'urls' => $urls,
'extract_options' => ['title', 'text'],
'concurrent' => 2 // Process 2 URLs at once
]);
foreach ($results as $index => $result) {
if ($result['success']) {
echo $urls[$index] . ": " . $result['data']['primary_content']['title'] . "\n";
} else {
echo $urls[$index] . " failed: " . $result['error'] . "\n";
}
}
} catch (Exception $e) {
echo "Bulk scraping failed: " . $e->getMessage() . "\n";
}
}
scrapeWebpage($client);
bulkScrape($client);AI-Powered Research
Leverage AI to research topics across multiple sources with automatic summarization:
<?php
require_once 'vendor/autoload.php';
use Venym Search\VenymSearchClient;
$client = new VenymSearchClient([
'api_key' => $_ENV['VENYM_SEARCH_API_KEY']
]);
// AI-powered research
function researchTopic($client) {
try {
$result = $client->research([
'topic' => 'sustainable energy solutions 2025',
'max_sources' => 10,
'include_images' => true,
'language' => 'en'
]);
echo "Research summary:\n";
echo $result['summary'] . "\n\n";
echo "Key insights:\n";
foreach ($result['key_insights'] as $index => $insight) {
echo ($index + 1) . ". " . $insight . "\n";
}
echo "\nSources analyzed:\n";
foreach ($result['sources'] as $index => $source) {
echo ($index + 1) . ". " . $source['title'] . "\n";
echo " URL: " . $source['url'] . "\n";
echo " Credibility: " . $source['credibility_score'] . "\n\n";
}
} catch (Exception $e) {
echo "Research failed: " . $e->getMessage() . "\n";
}
}
researchTopic($client);Advanced Configuration
Customize the SDK behavior with advanced configuration options:
<?php
require_once 'vendor/autoload.php';
use Venym Search\VenymSearchClient;
use Venym Search\Http\GuzzleHttpClient;
// Advanced configuration with custom HTTP client
$httpClient = new GuzzleHttpClient([
'timeout' => 60,
'connect_timeout' => 10,
'verify' => false, // Disable SSL verification if needed
'proxy' => [
'http' => 'http://proxy.example.com:8080',
'https' => 'http://proxy.example.com:8080'
]
]);
$client = new VenymSearchClient([
'api_key' => $_ENV['VENYM_SEARCH_API_KEY'],
'base_url' => 'https://www.search.venym.io/api/v1',
'http_client' => $httpClient,
'timeout' => 60,
'retries' => 5,
'retry_delay' => 1, // seconds
// Rate limiting
'rate_limit' => [
'requests_per_minute' => 100,
'burst_limit' => 10
],
// Custom headers
'headers' => [
'User-Agent' => 'MyApp/1.0.0',
'X-Custom-Header' => 'value'
],
// Response format
'response_format' => 'detailed', // 'simple' or 'detailed'
// Error handling
'throw_on_error' => true,
// Debug mode
'debug' => $_ENV['APP_ENV'] === 'development'
]);
// Override settings per request
try {
$result = $client->search([
'query' => 'test query',
'max_results' => 5
], [
'timeout' => 10, // Override timeout for this request
'retries' => 1 // Override retries for this request
]);
echo "Search completed: " . count($result['search_results']) . " results\n";
} catch (Exception $e) {
echo "Search failed: " . $e->getMessage() . "\n";
}Error Handling
Robust error handling with specific exception types and retry logic:
<?php
require_once 'vendor/autoload.php';
use Venym Search\VenymSearchClient;
use Venym Search\Exceptions\{
VenymSearchException,
RateLimitException,
AuthenticationException,
InsufficientCreditsException,
ValidationException
};
$client = new VenymSearchClient([
'api_key' => $_ENV['VENYM_SEARCH_API_KEY']
]);
function robustApiCall($client) {
$maxRetries = 3;
$retryDelay = 1; // seconds
for ($attempt = 1; $attempt <= $maxRetries; $attempt++) {
try {
$result = $client->search([
'query' => 'example query',
'max_results' => 10
]);
return $result;
} catch (RateLimitException $e) {
echo "Rate limited. Retry after " . $e->getRetryAfter() . " seconds\n";
if ($attempt < $maxRetries) {
sleep($e->getRetryAfter() ?: $retryDelay);
$retryDelay *= 2; // Exponential backoff
continue;
}
throw $e;
} catch (AuthenticationException $e) {
echo "Authentication failed: " . $e->getMessage() . "\n";
throw new Exception("Check your API key", 401, $e);
} catch (InsufficientCreditsException $e) {
echo "No credits remaining: " . $e->getMessage() . "\n";
throw new Exception("Upgrade your plan", 402, $e);
} catch (ValidationException $e) {
echo "Invalid request: " . $e->getMessage() . "\n";
echo "Validation errors:\n";
foreach ($e->getValidationErrors() as $field => $errors) {
echo " $field: " . implode(', ', $errors) . "\n";
}
throw $e;
} catch (VenymSearchException $e) {
echo "API error ({$e->getStatusCode()}): " . $e->getMessage() . "\n";
// Log additional context
echo "Request ID: " . $e->getRequestId() . "\n";
echo "Response: " . $e->getResponseBody() . "\n";
if ($attempt < $maxRetries && $e->getStatusCode() >= 500) {
echo "Retrying in $retryDelay seconds...\n";
sleep($retryDelay);
$retryDelay *= 2;
continue;
}
throw $e;
} catch (Exception $e) {
echo "Unexpected error: " . $e->getMessage() . "\n";
throw $e;
}
}
throw new Exception("Max retries exceeded");
}
try {
$result = robustApiCall($client);
echo "Success: Found " . count($result['search_results']) . " results\n";
} catch (Exception $e) {
echo "API call failed: " . $e->getMessage() . "\n";
}Framework Integration
Laravel Integration
<?php
// Laravel Integration Example
// config/services.php
return [
'VENYM_SEARCH' => [
'api_key' => env('VENYM_SEARCH_API_KEY'),
'timeout' => 30,
'retries' => 3,
]
];
// app/Services/SearchService.php
<?php
namespace App\Services;
use Venym Search\VenymSearchClient;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Log;
class SearchService
{
protected $client;
public function __construct()
{
$this->client = new VenymSearchClient(config('services.VENYM_SEARCH'));
}
public function search(string $query, int $maxResults = 10): array
{
$cacheKey = 'search:' . md5($query . $maxResults);
return Cache::remember($cacheKey, 300, function () use ($query, $maxResults) {
try {
return $this->client->search([
'query' => $query,
'max_results' => $maxResults
]);
} catch (Exception $e) {
Log::error('Search failed', [
'query' => $query,
'error' => $e->getMessage(),
'trace' => $e->getTraceAsString()
]);
throw $e;
}
});
}
public function scrapeUrl(string $url): array
{
try {
return $this->client->scrape([
'url' => $url,
'extract_options' => ['title', 'text', 'metadata']
]);
} catch (Exception $e) {
Log::error('Scraping failed', [
'url' => $url,
'error' => $e->getMessage()
]);
throw $e;
}
}
}
// app/Http/Controllers/SearchController.php
<?php
namespace App\Http\Controllers;
use App\Services\SearchService;
use Illuminate\Http\Request;
use Illuminate\Http\JsonResponse;
class SearchController extends Controller
{
protected $searchService;
public function __construct(SearchService $searchService)
{
$this->searchService = $searchService;
}
public function search(Request $request): JsonResponse
{
$request->validate([
'query' => 'required|string|min:2|max:500',
'max_results' => 'integer|min:1|max:100'
]);
try {
$results = $this->searchService->search(
$request->input('query'),
$request->input('max_results', 10)
);
return response()->json([
'success' => true,
'data' => $results
]);
} catch (Exception $e) {
return response()->json([
'success' => false,
'error' => $e->getMessage()
], 500);
}
}
public function scrape(Request $request): JsonResponse
{
$request->validate([
'url' => 'required|url'
]);
try {
$result = $this->searchService->scrapeUrl($request->input('url'));
return response()->json([
'success' => true,
'data' => $result
]);
} catch (Exception $e) {
return response()->json([
'success' => false,
'error' => $e->getMessage()
], 500);
}
}
}Symfony Integration
<?php
// Symfony Integration Example
// config/packages/VENYM_SEARCH.yaml
parameters:
VENYM_SEARCH.api_key: '%env(VENYM_SEARCH_API_KEY)%'
// src/Service/VenymSearchService.php
<?php
namespace App\Service;
use Venym Search\VenymSearchClient;
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBagInterface;
use Psr\Log\LoggerInterface;
class VenymSearchService
{
private $client;
private $logger;
public function __construct(ParameterBagInterface $params, LoggerInterface $logger)
{
$this->client = new VenymSearchClient([
'api_key' => $params->get('VENYM_SEARCH.api_key')
]);
$this->logger = $logger;
}
public function search(string $query, int $maxResults = 10): array
{
try {
$result = $this->client->search([
'query' => $query,
'max_results' => $maxResults
]);
$this->logger->info('Search completed', [
'query' => $query,
'results_count' => count($result['search_results'])
]);
return $result;
} catch (\Exception $e) {
$this->logger->error('Search failed', [
'query' => $query,
'error' => $e->getMessage()
]);
throw $e;
}
}
}
// src/Controller/ApiController.php
<?php
namespace App\Controller;
use App\Service\VenymSearchService;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Component\Validator\Constraints as Assert;
use Symfony\Component\Validator\Validator\ValidatorInterface;
class ApiController extends AbstractController
{
private $searchService;
public function __construct(VenymSearchService $searchService)
{
$this->searchService = $searchService;
}
#[Route('/api/search', name: 'api_search', methods: ['POST'])]
public function search(Request $request, ValidatorInterface $validator): JsonResponse
{
$data = json_decode($request->getContent(), true);
$constraints = new Assert\Collection([
'query' => [new Assert\NotBlank(), new Assert\Length(['min' => 2, 'max' => 500])],
'max_results' => [new Assert\Type('integer'), new Assert\Range(['min' => 1, 'max' => 100])]
]);
$violations = $validator->validate($data, $constraints);
if (count($violations) > 0) {
$errors = [];
foreach ($violations as $violation) {
$errors[] = $violation->getMessage();
}
return $this->json(['error' => 'Validation failed', 'details' => $errors], 400);
}
try {
$results = $this->searchService->search(
$data['query'],
$data['max_results'] ?? 10
);
return $this->json(['success' => true, 'data' => $results]);
} catch (\Exception $e) {
return $this->json(['success' => false, 'error' => $e->getMessage()], 500);
}
}
}Version Support
Full support for PHP 8.0+ with modern language features.
- • Union types
- • Named arguments
- • Attributes
- • Match expressions
Installed via Composer with automatic dependency management.
- • PSR-4 autoloading
- • Semantic versioning
- • Development tools
- • Testing framework
Compatible with common PHP extensions and libraries.
- • cURL extension
- • JSON extension
- • OpenSSL extension
- • Mbstring extension
Examples & Resources
Ready to Build?
Start building with the Venym Search PHP SDK and explore our comprehensive API documentation.
Need Help?
Get support, report issues, or contribute to the Venym Search PHP SDK development.