### Custom Class Definition and Usage Example Source: https://github.com/palaxo/es-odm/blob/master/README.md Provides a practical example of defining a custom class inheriting from a base class, including custom methods and overriding static search functionality. It demonstrates how to use the `in` method to create an indexed class and perform bulk deletion. ```javascript class Counter extends createClass('counter', Joi.object()) { async customFunction() { return 666; } static customStatic() { return new this({ a: 4 }, `myId`); } static async search(...args) { const results = await super.search(...args); if (results.length <= 0) { throw Error(`Nothing`); } else { return results; } } } const MyCounter = Counter.in('default'); const allCounters = await MyCounter.findAll(); await allCounters.delete(); const instanceCounter = new MyCounter({ counter: 15 }, 'myId'); await instanceCounter.save(); ``` -------------------------------- ### Count and Check Document Existence in JavaScript Source: https://context7.com/palaxo/es-odm/llms.txt Provides JavaScript examples for counting documents matching various query criteria and checking the existence of single or multiple documents by their IDs. It also demonstrates using the `head` method to retrieve existence information along with metadata like version. ```javascript const User = createClass('users').in('production'); // Count all documents const total = await User.count(); console.log(`Total users: ${total}`); // Count with query const activeCount = await User.count({ query: { term: { status: 'active' } } }); // Count with complex query const recentActive = await User.count({ query: { bool: { must: [ { term: { status: 'active' } }, { range: { lastLogin: { gte: 'now-7d' } } } ] } } }); // Check if single document exists const exists = await User.exists('user123'); if (exists) { console.log('User exists'); } // Check multiple documents const existsArray = await User.exists(['user1', 'user2', 'user3']); existsArray.forEach((exists, index) => { const id = ['user1', 'user2', 'user3'][index]; console.log(`${id}: ${exists ? 'exists' : 'not found'}`); }); // Use head to check existence with metadata try { const head = await User.head('user123'); console.log(`Exists with version ${head._version}`); } catch (error) { console.log('Document not found'); } ``` -------------------------------- ### Find and Get Documents by ID using JavaScript Source: https://context7.com/palaxo/es-odm/llms.txt Retrieves documents using either the search API (find) for flexible searching or the mget API (get) for direct ID-based retrieval. 'find' returns a BulkArray with status tracking for not found IDs, while 'get' throws an error if an ID is not found. Both can handle single or multiple IDs and support specifying source fields for 'find'. ```javascript const User = createClass('users').in('production'); // Find by single ID using search const user = await User.find('user123'); console.log(user.length); // 1 or 0 if not found // Find multiple IDs const users = await User.find(['user1', 'user2', 'user3']); console.log(users.notFound); // Tracks which IDs were not found // Get by single ID (throws if not found) try { const user = await User.get('user123'); console.log(user._id, user._version); // Direct instance access } catch (error) { if (error.statusCode === 404) { console.log('User not found'); } } // Get multiple IDs as BulkArray const userBulk = await User.get(['user1', 'user2', 'user3']); // Throws error if any ID is not found // Get with specific source fields const users = await User.find(['user1', 'user2'], ['name', 'email']); ``` -------------------------------- ### Find and Get Documents Source: https://context7.com/palaxo/es-odm/llms.txt Retrieve documents by their IDs. 'find' supports single or multiple IDs and returns a BulkArray with notFound tracking. 'get' retrieves directly and throws an error if an ID is not found, also supporting single or multiple IDs. ```APIDOC ## FIND AND GET DOCUMENTS ### Description Retrieve documents by their IDs. `find` supports single or multiple IDs and returns a BulkArray with `notFound` tracking. `get` retrieves directly and throws an error if an ID is not found, also supporting single or multiple IDs. ### Method GET (Implicit) ### Endpoint `/users/_find` (for `find`) `/users/_mget` (for `get`) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **ids** (array of string) - Required - The IDs of the documents to retrieve. - **source** (array of string) - Optional - Specific fields to retrieve from the documents. ### Request Example ```javascript // Find by single ID using search const user = await User.find('user123'); // Find multiple IDs const users = await User.find(['user1', 'user2', 'user3']); // Get by single ID (throws if not found) try { const user = await User.get('user123'); } catch (error) { // handle error } // Get multiple IDs as BulkArray const userBulk = await User.get(['user1', 'user2', 'user3']); // Find with specific source fields const users = await User.find(['user1', 'user2'], ['name', 'email']); ``` ### Response #### Success Response (200) - **document** (object) - The retrieved document(s). - **notFound** (array of string) - For `find` operations, lists IDs that were not found. #### Response Example ```json // Example for find(['user1', 'user2']) { "user1": {"_id": "user1", "name": "John Doe"}, "user2": {"_id": "user2", "name": "Jane Smith"} } // Example for find(['user1', 'nonexistent']) { "user1": {"_id": "user1", "name": "John Doe"} } // notFound: ["nonexistent"] ``` ``` -------------------------------- ### Instantiate Class Manually Source: https://github.com/palaxo/es-odm/blob/master/README.md Demonstrates manual instantiation of class instances, allowing direct provision of data, ES _id, _version, and other metadata. This is useful for creating new records or explicitly setting known values for existing ones. ```javascript const instance = new MyClass({ field1: 'value1', field2: 123 }, '_id', '_version', '_highlight', '_primary_term', '_seq_no', '_score', '_sort'); ``` -------------------------------- ### Create a New ODM Class with Schema and Tenant (Node.js) Source: https://github.com/palaxo/es-odm/blob/master/README.md Demonstrates how to create a new ODM class using the `createClass` function. It shows how to specify the class name, an optional Joi schema for validation, and an initial tenant which forms part of the index alias. The `in()` method can be used to create inherited classes with different tenants. ```javascript const Joi = require('joi'); // Define a schema for validation const userSchema = Joi.object({ name: Joi.string().required(), email: Joi.string().email().required() }); // Create a class named 'User' with the defined schema and a tenant 'myTenant' const User = createClass('User', userSchema, 'myTenant'); // Create an inherited class with a different tenant const AdminUser = User.in('adminTenant'); // Example of creating an instance (requires specifying tenant if not default) // const newUser = new User({ name: 'John Doe', email: 'john@example.com' }); // const admin = new AdminUser({ name: 'Admin User', email: 'admin@example.com' }); ``` -------------------------------- ### Get Class Alias Source: https://github.com/palaxo/es-odm/blob/master/README.md Retrieves the full alias for a class, which is composed of the tenant and the class name. This alias is essential for constructing Elasticsearch queries. ```javascript const alias = MyClass.alias; // e.g., 'default_myclass' ``` -------------------------------- ### Configure Elasticsearch Client and Logger (Node.js) Source: https://github.com/palaxo/es-odm/blob/master/README.md Shows how to configure the underlying Elasticsearch client and the library's logger. `setClient` replaces the default singleton ES client, which should be called once at application startup. `setLoggerConfig` and `setLoggerUidFunction` allow customization of logging behavior and the generation of unique IDs for logs. ```javascript const elasticsearch = require('@elastic/elasticsearch'); // Initialize a new ES client instance const esClientInstance = new elasticsearch.Client({ node: 'http://localhost:9200' }); // Set the custom ES client for the ODM library setClient(esClientInstance); // Configure logger settings (example) setLoggerConfig({ logLevel: 'info', logColor: true }); // Set a custom function to generate unique IDs for logs setLoggerUidFunction(() => `custom-id-${Date.now()}`); // Now, all subsequent operations will use the configured client and logger. ``` -------------------------------- ### setClient - Configure ElasticSearch Client Source: https://context7.com/palaxo/es-odm/llms.txt Replaces the default ElasticSearch client singleton with a custom configured client for the application. This should be called once at application startup. ```APIDOC ## setClient - Configure ElasticSearch Client ### Description Replaces the default ElasticSearch client singleton with a custom configured client for the application. This ensures all ODM operations use the specified client configuration. ### Method `setClient(client)` ### Parameters #### Path Parameters - `client` (Client) - Required - An instance of the ElasticSearch Client. ### Request Example ```javascript const { Client } = require('@elastic/elasticsearch'); const { setClient } = require('es-odm'); // Create and configure custom ES client const client = new Client({ node: 'https://localhost:9200', auth: { username: 'elastic', password: 'changeme' }, tls: { rejectUnauthorized: false }, maxRetries: 3, requestTimeout: 60000 }); // Set as the ODM client (call once at startup) setClient(client); // All subsequent ODM operations use this client const User = createClass('users'); await User.createIndex(); ``` ### Response (No direct response, modifies internal client singleton) ### Response Example ```json // No direct response example ``` ``` -------------------------------- ### Configure ElasticSearch Client with es-odm Source: https://context7.com/palaxo/es-odm/llms.txt Replaces the default ElasticSearch client singleton with a custom configured client. This allows applications to specify connection details, authentication, and other client-level configurations. Call this function once at application startup. ```javascript const { Client } = require('@elastic/elasticsearch'); const { setClient } = require('es-odm'); // Create and configure custom ES client const client = new Client({ node: 'https://localhost:9200', auth: { username: 'elastic', password: 'changeme' }, tls: { rejectUnauthorized: false }, maxRetries: 3, requestTimeout: 60000 }); // Set as the ODM client (call once at startup) setClient(client); // All subsequent ODM operations use this client const User = createClass('users'); await User.createIndex(); ``` -------------------------------- ### Implement Custom Data Transformation Hooks in JavaScript Source: https://context7.com/palaxo/es-odm/llms.txt Demonstrates how to extend ODM classes to override internal methods for data transformation. Examples include encrypting sensitive fields before saving (`_packData`), decrypting them upon loading (`_unpackData`), adding default filters to searches (`_alterSearch`), and enriching search results after loading (`_afterSearch`). ```javascript const User = createClass('users').in('production'); // Override _packData to transform before save class EncryptedUser extends User { async _packData(cache) { const data = await super._packData(cache); // Encrypt sensitive fields if (data.ssn) { data.ssn = await encrypt(data.ssn); } // Add metadata data.lastModified = new Date().toISOString(); data.version = (data.version || 0) + 1; return data; } static _unpackData(source) { const data = super._unpackData(source); // Decrypt on load if (data.ssn) { data.ssn = decrypt(data.ssn); } return data; } static _alterSearch(body) { // Add default filters to all searches if (!body.query) { body.query = { match_all: {} }; } body.query = { bool: { must: [body.query], filter: [ { term: { deleted: false } } ] } }; return body; } static async _afterSearch(instances, cache) { // Enrich instances after search const userIds = instances.map(i => i._id); const permissions = await fetchPermissions(userIds); instances.forEach(instance => { instance.permissions = permissions[instance._id] || []; }); } } // Use customized model const user = new EncryptedUser({ name: 'John', ssn: '123-45-6789' }); await user.save(); // SSN encrypted before save const loaded = await EncryptedUser.get(user._id); console.log(loaded.ssn); // Decrypted automatically function encrypt(data) { return Buffer.from(data).toString('base64'); } function decrypt(data) { return Buffer.from(data, 'base64').toString(); } async function fetchPermissions(ids) { return {}; } ``` -------------------------------- ### Manage Tenant Aliases for ODM Models (Node.js) Source: https://github.com/palaxo/es-odm/blob/master/README.md Illustrates how to manage index aliases with specific tenants using the `createClass` and `in` methods. It shows how the tenant (prefix) and name combine to form the final alias, and how the `in()` method creates a new ODM model instance with an updated tenant alias without altering the original. ```javascript // Create a class with default tenant ('*') const MyClass = createClass('myIndex'); // Create a class with a specific tenant ('default') const DefaultTenantClass = createClass('myIndex', void 0, 'default'); // Create a class with a specific tenant ('tenant') const SpecificTenantClass = createClass('myIndex', void 0, 'tenant'); // Inherit from an existing class to change tenant const ChangedTenantClass = SpecificTenantClass.in('changedTenant'); // The resulting aliases would be: // MyClass -> *_myIndex // DefaultTenantClass -> default_myIndex // SpecificTenantClass -> tenant_myIndex // ChangedTenantClass -> changedTenant_myIndex // Note: When creating instances or performing operations requiring a specific index, // the alias must not contain wildcards, meaning the tenant must be fully specified. ``` -------------------------------- ### Configure es-odm Warning Thresholds in JavaScript Source: https://context7.com/palaxo/es-odm/llms.txt Demonstrates how to configure warning thresholds for downloaded data size and search call complexity using `setConfiguration`. This helps in monitoring performance by logging warnings when certain limits are exceeded during data retrieval or search operations. ```javascript const { setConfiguration } = require('es-odm'); // Configure warning thresholds setConfiguration({ warning: { downloadedMiB: 100, // Warn when single request downloads > 100 MiB searchCalls: 50 // Warn when single search requires > 50 internal calls } }); // These will trigger warnings in logs if exceeded const User = createClass('users').in('production'); // This might trigger downloadedMiB warning const largeResult = await User.search({ query: { match_all: {} } }); // If result > 100 MiB // This might trigger searchCalls warning const allResults = await User.search({ query: { match_all: {} } }); // If requires > 50 internal pagination calls ``` -------------------------------- ### Import Core ODM Functions and Classes (Node.js) Source: https://github.com/palaxo/es-odm/blob/master/README.md Imports essential functions and classes from the ODM library, including class creation, bulk operations, base models, and client/logger configuration utilities. This is typically done once at the application's startup. ```javascript const { createClass, BulkArray, BaseModel, JointModel, esClient, setClient, esErrors, setLoggerConfig, setLoggerUidFunction } = require('odm'); ``` -------------------------------- ### Instance Level API Source: https://github.com/palaxo/es-odm/blob/master/README.md Provides methods for interacting with individual Elasticsearch document instances, including saving, reloading, deleting, cloning, and validation. ```APIDOC ## async save(?useVersion) ### Description Saves or re-saves an instance to Elasticsearch. It uses the specified `_id` or generates a new one if not provided. Internally, it utilizes the ES 'index' function. ### Method ASYNC ### Endpoint Not applicable (instance method) ### Parameters #### Query Parameters - **useVersion** (boolean) - Optional - If true, checks if the version matches. `_id` and `_version` must be specified. The sequence number will be fetched automatically if not presented. ### Request Example (Instance method, no explicit request body) ### Response #### Success Response (200) (Instance saved successfully) #### Response Example (No specific response body defined, typically indicates success) ## async reload() ### Description Reloads the instance data from Elasticsearch. It internally uses the 'get' method and creates a new instance of the same constructor. ### Method ASYNC ### Endpoint Not applicable (instance method) ### Parameters (None) ### Request Example (Instance method, no explicit request body) ### Response #### Success Response (200) (Instance data reloaded successfully) #### Response Example (No specific response body defined, typically indicates success) ## async delete(?useVersion) ### Description Deletes an instance from Elasticsearch. The `_id` must be specified, and the entry must exist in Elasticsearch. If `useVersion` is true, it checks for version matching, and `_version` must be specified. ### Method ASYNC ### Endpoint Not applicable (instance method) ### Parameters #### Query Parameters - **useVersion** (boolean) - Optional - If true, checks if the version matches. `_version` must be specified. The sequence number will be fetched automatically if not presented. ### Request Example (Instance method, no explicit request body) ### Response #### Success Response (200) (Instance deleted successfully) #### Response Example (No specific response body defined, typically indicates success) ## clone(?_preserveAttributes) ### Description Returns a clone of the current instance. This performs a deep copy. The cloned instance is created from the same class. The `preserveAttributes` option (defaults to true) can be used to preserve attributes like `_id` and `_version`. ### Method (Instance method) ### Endpoint Not applicable (instance method) ### Parameters #### Query Parameters - **_preserveAttributes** (boolean) - Optional - Defaults to true. If true, preserves attributes like `_id` and `_version`. ### Request Example (Instance method, no explicit request body) ### Response #### Success Response (200) - **clonedInstance** (object) - A deep copy of the current instance. #### Response Example { "clonedInstance": { ... cloned object ... } } ## async validate() ### Description Validates the instance data using Joi. Throws an error in case of invalid data. ### Method ASYNC ### Endpoint Not applicable (instance method) ### Parameters (None) ### Request Example (Instance method, no explicit request body) ### Response #### Success Response (200) (Instance validated successfully) #### Error Response (Throws an error if validation fails) #### Response Example (No specific response body defined on success, errors are thrown) ``` -------------------------------- ### putMapping and getMapping: Schema Management Source: https://context7.com/palaxo/es-odm/llms.txt This section covers schema management for Elasticsearch indices using `putMapping` and `getMapping`. `putMapping` allows you to add or update field definitions in an existing index, supporting nested objects and dynamic fields. `getMapping` retrieves the current mapping definitions for an index. It also includes functions for managing index settings (`getSettings`, `putSettings`). ```javascript const User = createClass('users').in('production'); // Add new field mapping await User.putMapping({ properties: { phoneNumber: { type: 'text', fields: { keyword: { type: 'keyword' } } }, preferences: { type: 'object', properties: { newsletter: { type: 'boolean' }, notifications: { type: 'boolean' } } } } }); // Get current mapping const mapping = await User.getMapping(); console.log(JSON.stringify(mapping, null, 2)); // Get settings const settings = await User.getSettings(); console.log(settings); // Get settings with defaults const allSettings = await User.getSettings(true); // Update settings (requires closing index first) await User.putSettings({ number_of_replicas: 3, refresh_interval: '30s' }); ``` -------------------------------- ### Model Customization with clone and in in ES-ODM Source: https://context7.com/palaxo/es-odm/llms.txt Provides methods to create customized model classes. The `in` method allows creating models for different tenants, automatically managing aliases. The `clone` method enables deep copying of models with modifications to properties like tenant or refresh behavior. Supports extending models with custom static and instance methods. ```javascript const User = createClass('users', Joi.object()); // Clone to different tenant const ProdUsers = User.in('production'); const DevUsers = User.in('development'); const TestUsers = User.in('test'); // Each has different alias console.log(ProdUsers.alias); // production_users console.log(DevUsers.alias); // development_users console.log(TestUsers.alias); // test_users // Change refresh behavior const NoRefreshUser = User.immediateRefresh(false); const user = new NoRefreshUser({ name: 'John' }); await user.save(); // Doesn't refresh immediately const RefreshUser = User.immediateRefresh(true); const user2 = new RefreshUser({ name: 'Jane' }); await user2.save(); // Refreshes immediately // Clone with custom changes const CustomUser = User.clone({ _tenant: 'custom', _immediateRefresh: 'wait_for', customProperty: 'value' }); // Extend with custom methods class AdvancedUser extends User.in('production') { static async findByEmail(email) { return this.search({ query: { term: { email } } }); } async activate() { this.status = 'active'; this.activatedAt = new Date().toISOString(); await this.save(); } } const users = await AdvancedUser.findByEmail('test@example.com'); ``` -------------------------------- ### Elasticsearch ODM - Indices API Source: https://github.com/palaxo/es-odm/blob/master/README.md APIs for managing Elasticsearch indices, including creation, deletion, aliasing, mapping, and settings. ```APIDOC ## POST /{index} (Implied) - Create Index ### Description Creates a new Elasticsearch index for the current model. Allows specifying custom settings. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters - **setAlias** (boolean) - Optional - Defaults to `true`. If true, the ODM alias is automatically set to the newly created index. #### Request Body - **body** (object) - Optional - Settings and mappings for the new index. ### Request Example ```json { "settings": { "number_of_shards": 1 }, "mappings": { "properties": { "field1": {"type": "text"} } } } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch create index API. #### Response Example ```json { "acknowledged": true, "shards_acknowledged": true, "index": "my-index-2023-10-27" } ``` ## GET /{index}/_alias (Implied) - Get Index ### Description Retrieves the name of the Elasticsearch index associated with the current ODM alias. Returns the index name as a string. ### Method GET ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **string** - The name of the index currently pointed to by the ODM alias. #### Response Example ```json "my-index-2023-10-27" ``` ## POST /{index}/_alias (Implied) - Alias Index ### Description Assigns the current ODM alias to a specified existing index. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **index** (string) - Required - The name of the index to alias. ### Request Example ```json { "index": "target-index-name" } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch alias API. #### Response Example ```json { "acknowledged": true } ``` ## DELETE /{index}/_alias (Implied) - Delete Alias ### Description Deletes the ODM alias from Elasticsearch. The underlying index remains unchanged. ### Method DELETE ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **object** - The response from the Elasticsearch delete alias API. #### Response Example ```json { "acknowledged": true } ``` ## HEAD /{index}/_alias (Implied) - Alias Exists ### Description Checks if the ODM alias exists in Elasticsearch. ### Method HEAD ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **boolean** - True if the alias exists, false otherwise. #### Response Example ```json true ``` ## HEAD /{index} (Implied) - Index Exists ### Description Checks if the index associated with the ODM alias exists in Elasticsearch. ### Method HEAD ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **boolean** - True if the index exists, false otherwise. #### Response Example ```json true ``` ## DELETE /{index} (Implied) - Delete Index ### Description Deletes the alias and the corresponding index in Elasticsearch. ### Method DELETE ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **object** - The response from the Elasticsearch delete index API. #### Response Example ```json { "acknowledged": true } ``` ## GET /{index}/_mapping (Implied) - Get Mapping ### Description Retrieves the mapping definition for the index associated with the current ODM alias. ### Method GET ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **object** - The mapping definition of the index. #### Response Example ```json { "my-index-2023-10-27": { "mappings": { "properties": { "field1": {"type": "text"} } } } } ``` ## PUT /{index}/_mapping (Implied) - Put Mapping ### Description Applies a new mapping definition to the index associated with the current ODM alias. ### Method PUT ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **mapping** (object) - Required - The mapping definition to apply. ### Request Example ```json { "properties": { "new_field": {"type": "keyword"} } } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch put mapping API. #### Response Example ```json { "acknowledged": true } ``` ## GET /{index}/_settings (Implied) - Get Settings ### Description Retrieves the settings for the index associated with the current ODM alias. ### Method GET ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Query Parameters - **includeDefaults** (boolean) - Optional - Defaults to `false`. If true, includes default settings. ### Request Example None ### Response #### Success Response (200) - **object** - The settings definition of the index. #### Response Example ```json { "my-index-2023-10-27": { "settings": { "index": { "number_of_shards": "1", "number_of_replicas": "1" } } } } ``` ## PUT /{index}/_settings (Implied) - Put Settings ### Description Applies new settings to the index associated with the current ODM alias. ### Method PUT ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **settings** (object) - Required - The settings definition to apply. ### Request Example ```json { "index": { "number_of_replicas": 2 } } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch put settings API. #### Response Example ```json { "acknowledged": true } ``` ## POST /{index}/_reindex (Implied) - Reindex ### Description Reindexes documents from the current model's index to a specified destination index. Can optionally use a painless script for transformations. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters - **script** (object) - Optional - A painless script to transform documents during reindexing. #### Request Body - **destinationModel** (string | object) - Required - The destination index or model alias. Can be a string representing an alias/index name or an ODM model object. ### Request Example ```json { "destinationModel": "another-model-alias", "script": { "source": "ctx._source.new_field = 'value'" } } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch reindex API. #### Response Example ```json { "took": 500, "timed_out": false, "total": 1000, "updated": 0, "created": 1000, "deleted": 0, "batches": 5, "version_conflicts": 0, "noops": 0, "retries": {"bulk": 0, "search": 0}, "throttled_millis": 0, "requests_per_second": -1, "throttled_task_duration_millis": 0, "failures": [] } ``` ## POST /{index}/_clone (Implied) - Clone Index ### Description Creates a clone of the current ODM index. The source index must be blocked for writes before cloning. Allows specifying optional settings for the new index. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **settings** (object) - Optional - Settings for the newly created cloned index. ### Request Example ```json { "settings": { "index": { "number_of_replicas": 0 } } } ``` ### Response #### Success Response (200) - **string** - The name of the newly created cloned index. #### Response Example ```json "my-index-clone-2023-10-27" ``` ## POST /{index}/_refresh (Implied) - Refresh ### Description Refreshes the index or indices associated with the current ODM alias, making pending changes visible. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **object** - The response from the Elasticsearch refresh API. #### Response Example ```json { "_shards": { "total": 2, "successful": 1, "failed": 0 } } ``` ## POST /{index}/_pit (Implied) - Open PIT ### Description Opens a Point in Time (PIT) for the specified index, allowing for consistent deep pagination. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters None ### Request Example None ### Response #### Success Response (200) - **object** - The response containing the PIT ID and creation time. #### Response Example ```json { "id": "", "kept_alive": "1m" } ``` ## POST /{index}/_close_point_in_time (Implied) - Close PIT ### Description Closes a previously opened Point in Time (PIT) using its ID. ### Method POST ### Endpoint (Implied by the context of the ODM class) ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body - **id** (string) - Required - The ID of the Point in Time to close. ### Request Example ```json { "id": "" } ``` ### Response #### Success Response (200) - **object** - The response from the Elasticsearch close PIT API. #### Response Example ```json { "succeeded": true, "evidence": "delete_by_query" } ``` ``` -------------------------------- ### createClass - Create ODM Model Class Source: https://context7.com/palaxo/es-odm/llms.txt Creates a new ODM model class that represents an ElasticSearch index with optional schema validation and tenant support for multi-tenancy. Models can also be extended with custom methods. ```APIDOC ## createClass - Create ODM Model Class ### Description Creates a new ODM model class that represents an ElasticSearch index with optional schema validation and tenant support for multi-tenancy. ### Method `createClass(indexName, [schema], [tenant])` ### Parameters #### Path Parameters - `indexName` (string) - Required - The name of the ElasticSearch index. - `schema` (Joi.Schema) - Optional - A Joi schema object for validation. - `tenant` (string) - Optional - The tenant identifier for multi-tenancy. ### Request Example ```javascript const { createClass } = require('es-odm'); const Joi = require('@hapi/joi'); // Basic model const User = createClass('users'); // Model with Joi schema validation const Product = createClass('products', Joi.object({ name: Joi.string().required(), price: Joi.number().min(0).required(), category: Joi.string().required(), inStock: Joi.boolean().default(true) })); // Model with tenant for multi-tenancy const TenantModel = createClass('documents', Joi.object(), 'company_a'); // Extend model with custom methods class Counter extends createClass('counter', Joi.object({ value: Joi.number().required() })) { async increment() { this.value += 1; await this.save(); return this.value; } static async createWithValue(value) { const counter = new this({ value }); await counter.save(); return counter; } } // Use the extended model const MyCounter = Counter.in('default'); const counter = await MyCounter.createWithValue(10); await counter.increment(); // Returns 11 ``` ### Response (Returns an ODM model class) ### Response Example ```json // No direct response example, as it returns a class constructor ``` ``` -------------------------------- ### createIndex: Index Creation with Alias Support Source: https://context7.com/palaxo/es-odm/llms.txt This code snippet demonstrates how to create new Elasticsearch indices using the `createIndex` method. It supports defining index settings, mappings, and automatically managing aliases for zero-downtime operations. The function returns the name of the created index, which by default includes an alias pointing to it. You can also opt out of automatic alias creation. ```javascript const User = createClass('users', Joi.object()).in('production'); // Create index with automatic alias const indexName = await User.createIndex({ settings: { number_of_shards: 3, number_of_replicas: 2, analysis: { analyzer: { email_analyzer: { type: 'custom', tokenizer: 'uax_url_email', filter: ['lowercase'] } } } }, mappings: { properties: { email: { type: 'text', analyzer: 'email_analyzer' }, name: { type: 'text' }, created: { type: 'date' }, status: { type: 'keyword' } } } }); console.log(`Created index: ${indexName}`); // e.g., production_users-abc123 // Create index without setting alias const newIndex = await User.createIndex({ settings: { number_of_shards: 1 } }, false); // Get current index const currentIndex = await User.getIndex(); console.log(currentIndex); // Check if alias exists if (await User.aliasExists()) { console.log('Alias exists'); } // Alias existing index await User.aliasIndex(newIndex); // Delete alias (keeps underlying index) await User.deleteAlias(); // Delete index and alias await User.deleteIndex(); ``` -------------------------------- ### search - Query Documents Source: https://context7.com/palaxo/es-odm/llms.txt Performs ElasticSearch search with optional pagination and Point-in-Time support. It can return either ODM instances or raw source data. ```APIDOC ## search - Query Documents ### Description Performs ElasticSearch search queries, supporting basic queries, pagination, deep pagination with `searchAfter`, and consistent results using Point-in-Time (PIT). It can return ODM model instances or raw source data. ### Method `Model.search(query, [from], [size], [options])` ### Parameters #### Path Parameters - `query` (object) - Required - The ElasticSearch query object. - `from` (number) - Optional - The offset from the start of the result set (for basic pagination). - `size` (number) - Optional - The number of hits to return (for basic pagination). - `options` (object) - Optional - Additional options for the search. - `searchAfter` (array) - Used for deep pagination. - `pitId` (string) - The Point-in-Time ID to use for consistent results. - `refresh` (string) - The refresh interval for PIT queries. - `source` (array) - An array of fields to include in the returned source data. ### Request Example ```javascript const User = createClass('users').in('production'); // Basic search with match query const results = await User.search({ query: { match: { email: 'john@example.com' } } }); // Search with pagination const page1 = await User.search({ query: { match_all: {} } }, 0, 10); // from=0, size=10 // Search with searchAfter for deep pagination const firstPage = await User.search({ query: { match_all: {} }, sort: [{ created: 'desc' }] }, 0, 100); const lastItem = firstPage[firstPage.length - 1]; const nextPage = await User.search({ query: { match_all: {} }, sort: [{ created: 'desc' }] }, undefined, 100, { searchAfter: lastItem._sort }); // Point-in-Time search for consistent results const pitId = await User.openPIT(); const pitResults = await User.search({ query: { match: { status: 'active' } }, sort: [{ _shard_doc: 'desc' }] }, undefined, 1000, { pitId: pitId, refresh: '1m' }); await User.closePIT(pitId); // Return raw source data instead of instances const rawData = await User.search({ query: { term: { role: 'admin' } } }, undefined, undefined, { source: ['email', 'name', 'role'] }); ``` ### Response #### Success Response (200) - `hits` (array) - An array of search results (ODM instances or raw objects). - `total` (object) - Information about the total number of hits. - `took` (number) - The time in ms the search took. #### Response Example ```json { "hits": [ { "_id": "doc1", "_source": { "name": "John Doe", "email": "john@example.com" } } ], "total": { "value": 1, "relation": "eq" }, "took": 10 } ``` ```