Skip to content

Latest commit

 

History

History
430 lines (312 loc) · 10.5 KB

File metadata and controls

430 lines (312 loc) · 10.5 KB
hlquery logo

A modular Perl client library for hlquery, designed with a familiar and intuitive API structure.

Twitter Follow Commit Activity GitHub stars License

DocumentationhlqueryDiscord

Features

  • Modular Architecture: Clean separation of concerns with organized classes
  • Intuitive API: Familiar and easy-to-use structure
  • Authentication Support: Bearer token and X-API-Key authentication
  • Flexible Parameters: Support for multiple parameter formats
  • Auto-detection: Automatically detects searchable fields when not specified
  • Type-safe Responses: Response objects with helper methods
  • Comprehensive Validation: Input validation for all operations
  • Minimal Dependencies: Uses standard Perl modules (LWP, JSON, URI)

Installation

Prerequisites

Install required Perl modules:

cpanm LWP::UserAgent JSON URI URI::Escape Digest::MD5

Or using cpanfile:

cpanm --installdeps .

Manual Installation

Add the lib directory to your Perl path:

$ use lib '/path/to/hlquery/etc/api/perl/lib';
$ use Hlquery::Client;

Use the canonical Hlquery::Client, Hlquery::Collections, Hlquery::Documents, Hlquery::Request, Hlquery::Response, and Hlquery::Search module names. Lowercase imports such as Hlquery::client are no longer supported as direct file-based imports because they create release tarball collisions on case-insensitive filesystems.

Quick Start

Basic Usage

use Hlquery::Client;

# Initialize client
my $client = Hlquery::Client->new('http://localhost:9200');

# Health check
my $health = $client->Health();
print "Status: " . $health->GetStatusCode() . "\n";

# List collections
my $collections = $client->ListCollections(0, 10);
if ($collections->IsSuccess()) {
    my $body = $collections->GetBody();
    print "Found " . scalar(@{$body->{collections}}) . " collections\n";
}

With Authentication

# Method 1: Set token in constructor
my $client = Hlquery::Client->new('http://localhost:9200', {
    token => 'your_token_here',
    auth_method => 'bearer'  # or 'api-key'
});

# Method 2: Set token dynamically
my $client = Hlquery::Client->new('http://localhost:9200');
$client->SetAuthToken('your_token_here', 'bearer');

# Method 3: Use X-API-Key
$client->SetAuthToken('your_token_here', 'api-key');

Reduce Text Example

If the ai_search module is enabled, you can use the raw request helper to summarize a stored document:

my $summary = $client->ExecuteRequest(
    'GET',
    '/modules/ai_search/talk',
    undef,
    {
        q   => 'summarize onboarding guide in docs',
        run => 'true',
    }
);

print $summary->GetRawBody() . "\n";

Architecture

Core Classes

Hlquery::Client

Main client class that provides access to all API operations.

Hlquery::Request

Handles HTTP requests, authentication, and error handling using LWP::UserAgent.

Hlquery::Response

Response wrapper with helper methods:

  • GetStatusCode() - Get HTTP status code
  • GetBody() - Get response body
  • GetData() - Get 'data' field from response body
  • IsSuccess() - Check if request was successful
  • IsError() - Check if request failed
  • GetError() - Get error message
  • ToHash() - Convert to hash format (for backward compatibility)

API Classes

Hlquery::Collections manages collections (List, Get, Create, Delete, Update). Hlquery::Documents handles document CRUD plus ImportDocuments. Hlquery::Search covers search requests and parameter normalization.

Utilities

Hlquery::Utils::Auth handles token helpers and validation. Hlquery::Utils::Config provides defaults and URL/config parsing. Hlquery::Utils::Validator validates client input before requests are sent.

Exceptions

Hlquery::Exception is the base type. Use Hlquery::AuthenticationException, Hlquery::RequestException, Hlquery::ValidationException, Hlquery::CollectionException, Hlquery::DocumentException, and Hlquery::SearchException for more specific failures.

API Methods

System APIs

Health()

Check server health status.

my $health = $client->Health();
if ($health->IsSuccess()) {
    my $body = $health->GetBody();
    print "Status: " . $body->{status} . "\n";
}

Stats()

Get server statistics.

my $stats = $client->Stats();

Info()

Get server information.

my $info = $client->Info();

Collections API

Using the Collections API Object

my $collections = $client->Collections();

# List collections
my $result = $collections->List(0, 10);

# Get collection
$result = $collections->Get('my_collection');

# Create collection
$result = $collections->Create('new_collection', $schema);

# Delete collection
$result = $collections->Delete('collection_name');

# Get formatted fields
$result = $collections->GetFields('my_collection');

Convenience Methods

# List collections
my $collections = $client->ListCollections(0, 10);

# Get collection details
my $collection = $client->GetCollection('my_collection');

# Get collection fields (formatted)
my $fields = $client->GetCollectionFields('my_collection');

Documents API

Using the Documents API Object

my $documents = $client->Documents();

# List documents
my $result = $documents->List('collection', { offset => 0, limit => 10 });

# Get document
$result = $documents->Get('collection', 'doc_id');

# Add document
$result = $documents->Add('collection', $document);

# Update document
$result = $documents->Update('collection', 'doc_id', $document);

# Delete document
$result = $documents->Delete('collection', 'doc_id');

# Bulk import
$result = $documents->ImportDocuments('collection', [$doc1, $doc2, $doc3]);

Convenience Methods

# List documents
my $docs = $client->ListDocuments('collection', { offset => 0, limit => 10 });

# Get document
my $doc = $client->GetDocument('collection', 'doc_id');

Search API

Using the Search API Object

my $search = $client->SearchAPI();

# Simple search
my $results = $search->Search('collection', {
    q => 'search query',
    query_by => 'title,content',
    limit => 10
});

# Multi-search
$results = $search->MultiSearch([
    { collection => 'col1', q => 'query1' },
    { collection => 'col2', q => 'query2' }
]);

# Vector search (POST body)
my $vector_results = $search->VectorSearch('collection', {
    body => {
        vector => [0.1, 0.2, 0.3],
        field_name => 'embedding',
        topk => 5,
        include_distance => JSON::true,
        query_params => { ef => 128, nprobe => 8, is_linear => JSON::true }
    }
});

Convenience Method

# Search documents
my $results = $client->Search('collection', {
    q => 'search query',
    query_by => 'title,content',
    limit => 10
});

Search Parameters

The Search() method accepts flexible parameters:

Query String (q)

The q parameter supports the current lexical query syntax:

  • FIELD: q => 'title:laptop'
  • NOT: q => 'title:laptop NOT title:refurbished' or q => 'NOT apple'
  • Boolean: q => 'title:laptop OR title:notebook'
  • WILDCARD: q => 'laptop*', q => '*laptop', q => 'lap*top'
  • Phrase: q => '"exact phrase"'

Use filter_by for field filters and numeric comparisons, for example:

  • filter_by => 'price:>100&&category:electronics'
  • filter_by => 'category:food||category:nature'

Other Parameters

  • query_by - Fields to search in (comma-separated string or array reference)
  • query - Structured query object

Pagination

  • from / offset - Starting offset
  • size / limit - Number of results
  • page - Page number (alternative to offset)
  • per_page - Results per page

Filtering & Sorting

  • filter_by - Filter conditions (string)
  • filter - Filter object
  • sort_by - Sort fields (string or array reference)
  • sort - Sort specification

Faceting

  • facet_by - Facet fields (string or array reference)
  • facets - Facet specification

API Aliases

Indices($params)

Alias for ListCollections().

my $collections = $client->Indices({ offset => 0, limit => 10 });

Get($params)

Alias for GetCollection() or GetDocument().

# Get document
my $doc = $client->Get({ index => 'collection', id => 'doc_id' });

# Get collection
my $collection = $client->Get({ index => 'collection' });

Cat($type, $params)

Cat API for listing collections and system information.

my $indices = $client->Cat('indices', { limit => 10 });

Response Handling

All methods return a Hlquery::Response object:

my $response = $client->Health();

# Check status
if ($response->IsSuccess()) {
    # Handle success
    my $body = $response->GetBody();
}

# Or check status code
if ($response->GetStatusCode() == 200) {
    # Handle success
}

# Get error
if ($response->IsError()) {
    my $error = $response->GetError();
    print "Error: $error\n";
}

# Convert to hash (for backward compatibility)
my $hash = $response->ToHash();
# Returns: { status => 200, body => {...} }

Examples

Complete Example

See example.pl for a complete example demonstrating:

  • Health checks
  • Authentication (with and without token)
  • Listing collections
  • Getting collection fields
  • Listing documents with pagination
  • Multiple search methods
  • Dynamic authentication

Run the example:

# Without authentication
perl example.pl

# With authentication
perl example.pl your_token_here

Organized Examples

Check the examples/ directory for organized examples:

  • basic_usage.pl - Basic operations
  • search.pl - Search patterns
  • collections.pl - Collection management
  • documents.pl - Document CRUD

Requirements

  • Perl >= 5.10
  • LWP::UserAgent - For HTTP requests
  • JSON - For JSON encoding/decoding
  • URI - For URL handling
  • URI::Escape - For URL encoding
  • Digest::MD5 - For token generation