Skip to main content
C SDK / API reference The libmoss API is split across two opaque handles, MossClient and MossSession. Every fallible function returns a MossResult code and writes its output through an out-parameter. See Getting started for build and link instructions. Include the header and link against libmoss:
#include "libmoss.h"

MossClient

The entry point. Construct it with your project credentials, then manage cloud indexes, load an index for querying, or open sessions.
FunctionDescription
moss_client_newCreate a client with project credentials.
moss_client_freeDestroy a client.
moss_client_sessionOpen a local session (auto-loads from the cloud if the index exists).
moss_client_create_indexCreate a cloud index.
moss_client_add_docsAdd documents to a cloud index.
moss_client_delete_docsDelete documents from a cloud index.
moss_client_delete_indexDelete a cloud index.
moss_client_get_indexGet index metadata.
moss_client_list_indexesList all indexes.
moss_client_get_docsFetch documents from a cloud index.
moss_client_get_job_statusPoll a mutation job.
moss_client_load_indexLoad a cloud index into memory for local queries.
moss_client_unload_indexUnload a loaded index.
moss_client_queryQuery a loaded index.
moss_client_refresh_indexRefresh a loaded index from the cloud.

Signatures

MossResult moss_client_new(const char *project_id,
                           const char *project_key,
                           MossClient **out);

void moss_client_free(MossClient *client);

MossResult moss_client_session(MossClient *client,
                               const char *name,
                               const MossSessionOptions *opts,
                               MossSession **out);

MossResult moss_client_create_index(MossClient *client,
                                    const char *name,
                                    const MossDocumentInfo *docs,
                                    uintptr_t doc_count,
                                    const char *model_id,
                                    MossMutationResult **out);

MossResult moss_client_add_docs(MossClient *client,
                                const char *name,
                                const MossDocumentInfo *docs,
                                uintptr_t doc_count,
                                const MossMutationOptions *opts,
                                MossMutationResult **out);

MossResult moss_client_delete_docs(MossClient *client,
                                   const char *name,
                                   const char *const *doc_ids,
                                   uintptr_t count,
                                   MossMutationResult **out);

MossResult moss_client_delete_index(MossClient *client,
                                    const char *name,
                                    bool *out_deleted);

MossResult moss_client_get_index(MossClient *client,
                                 const char *name,
                                 MossIndexInfo **out);

MossResult moss_client_list_indexes(MossClient *client,
                                    MossIndexInfo **out,
                                    uintptr_t *out_count);

MossResult moss_client_get_docs(MossClient *client,
                                const char *name,
                                const char *const *doc_ids,
                                uintptr_t id_count,
                                MossDocumentInfo **out_docs,
                                uintptr_t *out_count);

MossResult moss_client_get_job_status(MossClient *client,
                                      const char *job_id,
                                      MossJobStatusResponse **out);

MossResult moss_client_load_index(MossClient *client,
                                  const char *name,
                                  const MossLoadIndexOptions *opts,
                                  MossIndexInfo **out);

MossResult moss_client_unload_index(MossClient *client, const char *name);

MossResult moss_client_query(MossClient *client,
                             const char *name,
                             const char *query,
                             const MossQueryOptions *opts,
                             MossSearchResult **out);

MossResult moss_client_refresh_index(MossClient *client,
                                     const char *name,
                                     MossRefreshResult **out);
Load before you query. moss_client_query runs against an index that is already loaded into memory. Call moss_client_load_index first, then moss_client_query. Querying a cloud index that has not been loaded is not supported.
When you no longer need a loaded index, free its memory with moss_client_unload_index. To pick up changes pushed since the index was loaded, call moss_client_refresh_index.

model_id on create

moss_client_create_index takes a model_id argument. Pass NULL for the default model, or a model id such as "moss-mediumlm". The "custom" model is not supported for cloud index creation.

MossSession

A local index. Add and query documents on the same machine, persist them, and sync with the cloud. Session queries run locally on the session, so no load step is needed before querying.
FunctionDescription
moss_session_freeDestroy a session.
moss_session_nameGet the session name.
moss_session_doc_countGet the document count.
moss_session_add_docsAdd documents (auto-embeds for built-in models).
moss_session_delete_docsDelete documents by id.
moss_session_get_docsFetch documents (NULL ids = all).
moss_session_queryHybrid search, run locally.
moss_session_load_indexLoad an existing cloud index into the session.
moss_session_push_indexPush the session to the cloud.

Signatures

void moss_session_free(MossSession *session);

const char *moss_session_name(const MossSession *session);

uintptr_t moss_session_doc_count(const MossSession *session);

MossResult moss_session_add_docs(MossSession *session,
                                 const MossDocumentInfo *docs,
                                 uintptr_t doc_count,
                                 const MossAddDocsOptions *opts,
                                 uintptr_t *out_added,
                                 uintptr_t *out_updated);

MossResult moss_session_delete_docs(MossSession *session,
                                    const char *const *doc_ids,
                                    uintptr_t count,
                                    uintptr_t *out_deleted);

MossResult moss_session_get_docs(MossSession *session,
                                 const char *const *doc_ids,
                                 uintptr_t id_count,
                                 MossDocumentInfo **out_docs,
                                 uintptr_t *out_count);

MossResult moss_session_query(MossSession *session,
                              const char *query,
                              const MossQueryOptions *opts,
                              MossSearchResult **out);

MossResult moss_session_load_index(MossSession *session,
                                   const char *index_name,
                                   const MossLoadIndexOptions *opts,
                                   uintptr_t *out_doc_count);

MossResult moss_session_push_index(MossSession *session,
                                   MossPushIndexResult **out);
moss_session_name returns a pointer owned by the session - it is valid for the lifetime of the session and must not be freed. moss_session_load_index accepts an optional MossLoadIndexOptions. When opts.auto_refresh is set, the session polls the cloud index every opts.polling_interval_secs and pulls newer versions in on the next moss_session_query, moss_session_get_docs, or moss_session_doc_count. Auto-refresh pauses while the session has un-pushed local edits (after moss_session_add_docs / moss_session_delete_docs, until moss_session_push_index), so it never clobbers local work. Pass NULL for the default behavior (no auto-refresh).

Memory management

These rules govern literal C memory (malloc / free) ownership across the C ABI. Rule: every pointer returned by libmoss through an out-parameter must be freed with the matching moss_free_*() function.
Allocated byFree with
moss_session_query, moss_client_querymoss_free_search_result
moss_session_get_docs, moss_client_get_docsmoss_free_documents
moss_client_get_indexmoss_free_index_info
moss_client_list_indexesmoss_free_index_info_list
moss_client_create_index, moss_client_add_docs, moss_client_delete_docsmoss_free_mutation_result
moss_session_push_indexmoss_free_push_index_result
moss_client_get_job_statusmoss_free_job_status_response
moss_client_refresh_indexmoss_free_refresh_result
Free signatures:
void moss_free_string(char *s);
void moss_free_documents(MossDocumentInfo *docs, uintptr_t count);
void moss_free_search_result(MossSearchResult *result);
void moss_free_index_info(MossIndexInfo *info);
void moss_free_index_info_list(MossIndexInfo *infos, uintptr_t count);
void moss_free_mutation_result(MossMutationResult *result);
void moss_free_push_index_result(MossPushIndexResult *result);
void moss_free_job_status_response(MossJobStatusResponse *resp);
void moss_free_refresh_result(MossRefreshResult *result);
Input data (documents, strings, id arrays) is copied during the call, so the caller owns and frees its own input buffers. The MossClient and MossSession handles themselves are freed with moss_client_free and moss_session_free.

Error handling

Every fallible function returns a MossResult (int32_t):
  • OK (0) means success.
  • Negative values are errors.
enum MossResult {
    OK                  =  0,
    ERR_NULL_POINTER    = -1,
    ERR_INVALID_ARG     = -2,
    ERR_CLOUD           = -3,
    ERR_INDEX_NOT_FOUND = -4,
    ERR_MODEL           = -5,
    ERR_IO              = -6,
    ERR_INTERNAL        = -7,
};
Call moss_last_error() to get a human-readable message for the most recent failed moss_* call on the current thread. The returned pointer is valid until the next moss_* call on the same thread, and is NULL if no error is stored. Do not free it.
MossResult r = moss_client_new(id, key, &client);
if (r != OK) {
    const char *err = moss_last_error();
    fprintf(stderr, "Error: %s\n", err ? err : "(no details)");
}

Thread safety

MossClient and MossSession handles are internally mutex-protected and may be shared across threads safely. Concurrent calls on the same handle serialize. Do not free a MossClient or MossSession handle while another thread is still using it.

Metadata filters

Pass filters as a JSON string through MossQueryOptions.filter_json. A single-field filter has the shape:
{ "field": "<name>", "condition": { "<operator>": <value> } }
Combine clauses with $and / $or:
{ "$and": [ { "field": "...", "condition": { ... } }, { "field": "...", "condition": { ... } } ] }
In C, the JSON quotes have to be escaped inside the string literal:
MossQueryOptions opts = {
    .top_k       = 5,
    .alpha       = 0.8f,
    .filter_json = "{\"field\": \"type\", \"condition\": {\"$eq\": \"billing\"}}",
};

Operators

OperatorMeaningExample value
$eq / $neequals / not equals"billing"
$gt / $gte / $lt / $ltenumeric comparisons (values are strings)"100"
$in / $ninin / not in a list["new-york", "seattle"]
$nearwithin a radius of a point, "lat,lng,radiusMeters""40.7580,-73.9855,5000"
$and / $orcombine clausesarray of clauses
The same filter format applies to moss_session_query and moss_client_query. See Examples for runnable filter usage.

Query options

MossQueryOptions controls result count, the semantic/keyword blend, and filtering:
typedef struct MossQueryOptions {
    uintptr_t   top_k;          // number of results to return
    float       alpha;          // hybrid blend: 1.0 = semantic, 0.0 = keyword
    const char *filter_json;    // optional metadata filter (NULL = none)
    const float *embedding;     // optional query embedding (custom model)
    uintptr_t   embedding_dim;  // length of `embedding`, 0 when NULL
} MossQueryOptions;
Pass NULL for the whole options struct to use defaults. alpha blends dense (semantic) and sparse (keyword) scoring; 1.0 is pure semantic, 0.0 is pure keyword. Set embedding / embedding_dim only when the session or index uses the custom model.