API docs¶
Functions¶
-
elasticutils.get_es(urls=None, timeout=5, force_new=False, **settings)¶ Create an elasticsearch Elasticsearch object and return it.
This will aggressively re-use Elasticsearch objects with the following rules:
- if you pass the same argument values to get_es(), then it will return the same Elasticsearch object
- if you pass different argument values to get_es(), then it will return different Elasticsearch object
- it caches each Elasticsearch object that gets created
- if you pass in force_new=True, then you are guaranteed to get a fresh Elasticsearch object AND that object will not be cached
Parameters: - urls – list of uris; Elasticsearch hosts to connect to,
defaults to
['http://localhost:9200'] - timeout – int; the timeout in seconds, defaults to 5
- force_new – Forces get_es() to generate a new Elasticsearch object rather than pulling it from cache.
- settings – other settings to pass into Elasticsearch constructor; See http://elasticsearch-py.readthedocs.org/ for more details.
Examples:
# Returns cached Elasticsearch object es = get_es() # Returns a new Elasticsearch object es = get_es(force_new=True) es = get_es(urls=['localhost']) es = get_es(urls=['localhost:9200'], timeout=10, max_retries=3)
The S class¶
-
class
elasticutils.S(type_=None)¶ Represents a lazy Elasticsearch Search API request.
The API for S takes inspiration from Django’s QuerySet.
S can be either typed or untyped. An untyped S returns results as an iterable of
elasticutils.DefaultMappingTypeinstances.An S is lazy in the sense that it doesn’t do an Elasticsearch search request until it’s forced to evaluate by:
- use the
elasticutils.Sin an iterable context - call
len()on aelasticutils.S - call the
elasticutils.S.execute(),elasticutils.S.everything(),elasticutils.S.count(),elasticutils.S.suggestions()orelasticutils.S.facet_counts()methods
Adding support for other queries
You can add support for queries that S doesn’t have support for by subclassing S with a method called
process_query_<ACTION>. This method takes a key, value and an action.For example:
claass FunkyS(S): def process_query_funkyquery(self, key, val, action): return {'funkyquery': {'field': key, 'value': val}}Then you can use that just like other actions:
s = FunkyS().query(Q(foo__funkyquery='bar')) s = FunkyS().query(foo__funkyquery='bar')
Many Elasticsearch queries take other arguments. This is a good way of using different arguments. For example, if you wanted to write a handler for fuzzy for dates, you could do:
claass FunkyS(S): def process_query_fuzzy(self, key, val, action): # val here is a (value, min_similarity) tuple return { 'funkyquery': { key: { 'value': val[0], 'min_similarity': val[1] } } }Used:
s = FunkyS().query(created__fuzzy=(created_dte, '1d'))
Adding support for other filters
You can add support for filters that S doesn’t have support for by subclassing S with a method called
process_filter_<ACTION>. This method takes a key, value and an action.For example:
claass FunkyS(S): def process_filter_funkyfilter(self, key, val, action): return {'funkyfilter': {'field': key, 'value': val}}Then you can use that just like other actions:
s = FunkyS().filter(F(foo__funkyfilter='bar')) s = FunkyS().filter(foo__funkyfilter='bar')
-
__init__(type_=None)¶ Create and return an S.
Parameters: type – class; the MappingType for this S
Chaining transforms
-
query(*queries, **kw)¶ Return a new S instance with query args combined with existing set in a must boolean query.
Parameters: - queries – instances of Q
- kw – queries in the form of
field__action=value
There are three special flags you can use:
must=True: Specifies that the queries and kw queries must match in order for a document to be in the result.If you don’t specify a special flag, this is the default.
should=True: Specifies that the queries and kw queries should match in order for a document to be in the result.must_not=True: Specifies the queries and kw queries must not match in order for a document to be in the result.
These flags work by putting those queries in the appropriate clause of an Elasticsearch boolean query.
Examples:
>>> s = S().query(foo='bar') >>> s = S().query(Q(foo='bar')) >>> s = S().query(foo='bar', bat__match='baz') >>> s = S().query(foo='bar', should=True) >>> s = S().query(foo='bar', should=True).query(baz='bat', must=True)
Notes:
- Don’t specify multiple special flags, but if you did, should takes precedence.
- If you don’t specify any, it defaults to must.
- You can specify special flags in the
elasticutils.Q, too. If you’re building your query incrementally, usingelasticutils.Qhelps a lot.
See the documentation on
elasticutils.Qfor more details on composing queries with Q.See the documentation on
elasticutils.Sfor more details on adding support for more query types.
-
query_raw(query)¶ Return a new S instance with a query_raw.
Parameters: query – Python dict specifying the complete query to send to Elasticsearch Example:
S().query_raw({'match': {'title': 'example'}})
Note
If there’s a query_raw in your S, then that’s your query. All
.query(),.demote(),.boost()and anything else that affects the query clause is ignored.
-
filter(*filters, **kw)¶ Return a new S instance with filter args combined with existing set with AND.
Parameters: - filters – this will be instances of F
- kw – this will be in the form of
field__action=value
Examples:
>>> s = S().filter(foo='bar') >>> s = S().filter(F(foo='bar')) >>> s = S().filter(foo='bar', bat='baz') >>> s = S().filter(foo='bar').filter(bat='baz')
By default, everything is combined using AND. If you provide multiple filters in a single filter call, those are ANDed together. If you provide multiple filters in multiple filter calls, those are ANDed together.
If you want something different, use the F class which supports
&(and),|(or) and~(not) operators. Then call filter once with the resulting F instance.See the documentation on
elasticutils.Ffor more details on composing filters with F.See the documentation on
elasticutils.Sfor more details on adding support for new filter types.
-
filter_raw(filter_)¶ Return a new S instance with a filter_raw.
Parameters: filter – Python dict specifying the complete filter to send to Elasticsearch Example:
S().filter_raw({'term': {'title': 'example'}})
Note
If there’s a filter_raw in your S, then that’s your filter. All
.filter()and anything else that affects the filter clause is ignored.
-
order_by(*fields)¶ Return a new S instance with results ordered as specified
You can change the order search results by specified fields:
q = (S().query(title='trucks') .order_by('title')This orders search results by the title field in ascending order.
If you want to sort by descending order, prepend a
-:q = (S().query(title='trucks') .order_by('-title')You can also sort by the computed field
_scoreor pass a dict as a sort field in order to use more advanced sort options. Read the Elasticsearch documentation for details.Note
Calling this again will overwrite previous
.order_by()calls.
-
boost(**kw)¶ Return a new S instance with field boosts.
ElasticUtils allows you to specify query-time field boosts with
.boost(). It takes a set of arguments where the keys are either field names or field name +__+ field action.Examples:
q = (S().query(title='taco trucks', description__match='awesome') .boost(title=4.0, description__match=2.0))
If the key is a field name, then the boost will apply to all query bits that have that field name. For example:
q = (S().query(title='trucks', title__prefix='trucks', title__fuzzy='trucks') .boost(title=4.0))
applies a 4.0 boost to all three query bits because all three query bits are for the title field name.
If the key is a field name and field action, then the boost will apply only to that field name and field action. For example:
q = (S().query(title='trucks', title__prefix='trucks', title__fuzzy='trucks') .boost(title__prefix=4.0))
will only apply the 4.0 boost to title__prefix.
Boosts are relative to one another and all boosts default to 1.0.
For example, if you had:
qs = (S().boost(title=4.0, summary=2.0) .query(title__match=value, summary__match=value, content__match=value, should=True))
title__matchwould be boosted twice as much assummary__matchandsummary__matchtwice as much ascontent__match.
-
demote(amount_, *queries, **kw)¶ Returns a new S instance with boosting query and demotion.
You can demote documents that match query criteria:
q = (S().query(title='trucks') .demote(0.5, description__match='gross')) q = (S().query(title='trucks') .demote(0.5, Q(description__match='gross')))
This is implemented using the boosting query in Elasticsearch. Anything you specify with
.query()goes into the positive section. The negative query and negative boost portions are specified as the first and second arguments to.demote().Note
Calling this again will overwrite previous
.demote()calls.
-
facet(*args, **kw)¶ Return a new S instance with facet args combined with existing set.
Parameters: args – The list of facets to return. Additional keyword options:
size– Maximum number of terms to return for each facet.
-
facet_raw(**kw)¶ Return a new S instance with raw facet args combined with existing set.
-
highlight(*fields, **kwargs)¶ Set highlight/excerpting with specified options.
Parameters: fields – The list of fields to highlight. If the field is None, then the highlight is cleared. Additional keyword options:
pre_tags– List of tags before highlighted portionpost_tags– List of tags after highlighted portion
Results will have a
highlightattribute on thees_metaobject which contains the highlighted field excerpts.For example:
q = (S().query(title__match='crash', content__match='crash') .highlight('title', 'content')) for result in q: print result.es_meta.highlight['title'] print result.es_meta.highlight['content']
If you pass in
None, it will clear the highlight.For example, this search won’t highlight anything:
q = (S().query(title__match='crash') .highlight('title') # highlights 'title' field .highlight(None)) # clears highlight
Note
Calling this again will overwrite previous
.highlight()calls.Note
Make sure the fields you’re highlighting are indexed correctly. Read the Elasticsearch documentation for details.
-
search_type(search_type)¶ Set Elasticsearch search type for distributed search behaviour.
Parameters: search_type – The search type to set. The search type affects how much results are fetched from each shard, and how are they then merged back. This can affect the accuracy of the results and the execution speed.
For the list of possible values and additional documentation, consult the Elasticsearch reference: http://www.elasticsearch.org/guide/en/elasticsearch/reference/current/search-request-search-type.html
If called multiple times, the last search type will be in effect.
-
suggest(name, term, **kwargs)¶ Set suggestion options.
Parameters: - name – The name to use for the suggestions.
- term – The term to suggest similar looking terms for.
Additional keyword options:
field– The field to base suggestions upon, defaults to _all
Results will have a
_suggestionsproperty containing the suggestions for all terms.Note
Suggestions are only supported since Elasticsearch 0.90.
Calling this multiple times will add multiple suggest clauses to the query.
-
values_list(*fields)¶ Return a new S instance that returns ListSearchResults.
Parameters: fields – the list of fields to have in the results.
With no arguments, passes
fields=*and returns values for any fields you have marked as “stored = True” for that mapping.With arguments, passes those field arguments via
fieldsand returns a list of tuples with values in the order specified.For example (assume id, name and age are stored fields):
>>> list(S().values_list()) [([1], ['fred'], [40]), ([2], ['brian'], [30]), ...] >>> list(S().values_list('id', 'name')) [([1], ['fred']), ([2], ['brian']), ([3], ['james'])] >>> list(S().values_list('name', 'id')) [(['fred'], [1]), (['brian'], [2]), (['james'], [3])]
Note
If you do not specify any fields and you have no fields marked as stored, then you will get back the
_idand_typeof each result and that’s it.
-
values_dict(*fields)¶ Return a new S instance that returns DictSearchResults.
Parameters: fields – the list of fields to have in the results.
With no arguments, passes
fields=*and returns values for any fields you have marked as “stored = True” for that mapping.With arguments, passes those field arguments via
fieldsand returns a list of dicts with the specified fields.For example (assuming id, name and age are stored):
>>> list(S().values_dict()) [{'id': [1], 'name': ['fred'], 'age': [40]}, ...] >>> list(S().values_dict('id', 'name')) [{'id': [1], 'name': ['fred']}, ...]
Note
If you do not specify any fields and you have no fields marked as stored, then you will get back the
_idand_typeof each result and that’s it.
-
es(**settings)¶ Return a new S with specified Elasticsearch settings.
This allows you to configure the Elasticsearch object that gets used to execute the search.
Parameters: settings – the settings you’d use to build the Elasticsearch—same as what you’d pass to get_es().
-
indexes(*indexes)¶ Return a new S instance that will search specified indexes.
-
doctypes(*doctypes)¶ Return a new S instance that will search specified doctypes.
Note
Elasticsearch calls these “mapping types”. It’s the name associated with a mapping.
-
explain(value=True)¶ Return a new S instance with explain set.
Methods to override if you need different behavior
-
get_es(default_builder=<function get_es>)¶ Returns the Elasticsearch object to use.
Parameters: default_builder – The function that takes a bunch of arguments and generates a elasticsearch Elasticsearch object. Note
If you desire special behavior regarding building the Elasticsearch object for this S, subclass S and override this method.
-
get_indexes(default_indexes=None)¶ Returns the list of indexes to act on.
-
get_doctypes(default_doctypes=None)¶ Returns the list of doctypes to use.
-
to_python(obj)¶ Converts strings in a data structure to Python types
It converts datetime-ish things to Python datetimes.
Override if you want something different.
Parameters: obj – Python datastructure Returns: Python datastructure with strings converted to Python types Note
This does the conversion in-place!
Methods that force evaluation
-
__iter__()¶ Executes search and returns an iterator of results.
Returns: iterator of results For example:
>>> s = S().query(name__prefix='Jimmy') >>> for obj in s.execute(): ... print obj['id'] ...
-
__len__()¶ Executes search and returns the number of results you’d get.
Executes search and returns number of results returned as an integer.
Returns: integer For example:
>>> some_s = S().query(name__prefix='Jimmy') >>> length = len(some_s)
This is very different than calling
elasticutils.S.count(). If you callelasticutils.S.count()you get the total number of results that Elasticsearch thinks matches your search. If you calllen(), then you get the number of results you got from the search which factors in slices and default from and size values.
-
all()¶ No-op that returns a clone of self
This is here to make it more Django QuerySet-like and work with better with things that accept QuerySets.
-
count()¶ Returns the total number of results Elasticsearch thinks will match this search.
Returns: integer For example:
>>> all_jimmies = S().query(name__prefix='Jimmy').count()
-
execute()¶ Executes search and returns a SearchResults object.
Returns: SearchResults instance For example:
>>> s = S().query(name__prefix='Jimmy') >>> results = s.execute()
-
facet_counts()¶ Executes search and returns facet counts.
Example:
>>> s = S().query(name__prefix='Jimmy') >>> facet_counts = s.facet_counts()
- use the
The F class¶
-
class
elasticutils.F(**filters)¶ Filter objects.
Makes it easier to create filters cumulatively using
&(and),|(or) and~(not) operations.For example:
f = F() f &= F(price='Free') f |= F(style='Mexican')
creates a filter “price = ‘Free’ or style = ‘Mexican’”.
The Q class¶
-
class
elasticutils.Q(**queries)¶ Query objects.
Makes it easier to create queries cumulatively.
If there’s more than one query part, they’re combined under a BooleanQuery. By default, they’re combined in the must clause.
You can combine two Q classes using the
+operator. For example:q = Q() q += Q(title__match='shoes') q += Q(summary__match='shoes')
creates a BooleanQuery with two must clauses.
Example 2:
q = Q() q += Q(title__match='shoes', should=True) q += Q(summary__match='shoes') q += Q(description__match='shoes', must=True)
creates a BooleanQuery with one should clause (title) and two must clauses (summary and description).
The SearchResults class¶
-
class
elasticutils.SearchResults(type, response, results, fields)¶ After executing a search, this is the class that manages the results.
Property type: the mapping type of the S that created this SearchResults instance Property took: the amount of time the search took Property count: the total results Property response: the raw Elasticsearch search response Property results: the search results from the response if any Property fields: the list of fields specified by values_list or values_dict When you iterate over this object, it returns the individual search results in the shape you asked for (object, tuple, dict, etc) in the order returned by Elasticsearch.
Example:
s = S().query(bio__match='archaeologist') results = s.execute() # Shows how long the search took print results.took # Shows the raw Elasticsearch response print results.results
The MappingType class¶
-
class
elasticutils.MappingType¶ Base class for mapping types.
To extend this class:
- implement
get_index(). - implement
get_mapping_type_name(). - if this ties back to a model, implement
get_model()and possibly alsoget_object().
For example:
class ContactType(MappingType): @classmethod def get_index(cls): return 'contacts_index' @classmethod def get_mapping_type_name(cls): return 'contact_type' @classmethod def get_model(cls): return ContactModel def get_object(self): return self.get_model().get(id=self._id)
-
classmethod
from_results(results_dict)¶
-
get_object()¶ Returns the model instance
This gets called when someone uses the
.objectattribute which triggers lazy-loading of the object this document is based on.By default, this calls:
self.get_model().get(id=self._id)
where
self._idis the Elasticsearch document id.Override it to do something different.
-
classmethod
get_index()¶ Returns the index to use for this mapping type.
You can specify the index to use for this mapping type. This affects
Sbuilt with this type.By default, raises NotImplementedError.
Override this to return the index this mapping type should be indexed and searched in.
-
classmethod
get_mapping_type_name()¶ Returns the mapping type name.
You can specify the mapping type name (also sometimes called the document type) with this method.
By default, raises NotImplementedError.
Override this to return the mapping type name.
-
classmethod
get_model()¶ Return the model class related to this MappingType.
This can be any class that has an instance related to this MappingType by id.
For example, if you’re using Django and your MappingType is related to a Django model–this should return the Django model.
By default, raises NoModelError.
Override this to return a class that works with
.get_object()to return the instance of the model that is related to this document.
- implement
The Indexable class¶
-
class
elasticutils.Indexable¶ Mixin for mapping types with all the indexing hoo-hah.
Add this mixin to your DjangoMappingType subclass and it gives you super indexing power.
-
classmethod
bulk_index(documents, id_field='id', es=None, index=None)¶ Adds or updates a batch of documents.
Parameters: - documents –
List of Python dicts representing individual documents to be added to the index
Note
This must be serializable into JSON.
- id_field – The name of the field to use as the document id. This defaults to ‘id’.
- es – The Elasticsearch to use. If you don’t specify an Elasticsearch, it’ll use cls.get_es().
- index – The name of the index to use. If you don’t specify one it’ll use cls.get_index().
Note
If you need the documents available for searches immediately, make sure to refresh the index by calling
refresh_index().- documents –
-
classmethod
extract_document(obj_id, obj=None)¶ Extracts the Elasticsearch index document for this instance
This must be implemented.
Note
The resulting dict must be JSON serializable.
Parameters: - obj_id – the object id for the object to extract from
- obj – if this is not None, use this as the object to extract from; this allows you to fetch a bunch of items at once and extract them one at a time
Returns: dict of key/value pairs representing the document
-
classmethod
get_es()¶ Returns an Elasticsearch object
Override this if you need special functionality.
Returns: a elasticsearch Elasticsearch instance
-
classmethod
get_indexable()¶ Returns an iterable of things to index.
Returns: iterable of things to index
-
classmethod
get_mapping()¶ Returns the mapping for this mapping type.
Example:
@classmethod def get_mapping(cls): return { 'properties': { 'id': {'type': 'integer'}, 'name': {'type': 'string'} } }
See the docs for more details on how to specify a mapping.
Override this to return a mapping for this doctype.
Returns: dict representing the Elasticsearch mapping or None if you want Elasticsearch to infer it. defaults to None.
-
classmethod
index(document, id_=None, overwrite_existing=True, es=None, index=None)¶ Adds or updates a document to the index
Parameters: - document –
Python dict of key/value pairs representing the document
Note
This must be serializable into JSON.
- id –
the id of the document
Note
If you don’t provide an
id_, then Elasticsearch will make up an id for your document and it’ll look like a character name from a Lovecraft novel. - overwrite_existing – if
Trueoverwrites existing documents of the same ID and doctype - es – The Elasticsearch to use. If you don’t specify an Elasticsearch, it’ll use cls.get_es().
- index – The name of the index to use. If you don’t specify one it’ll use cls.get_index().
Note
If you need the documents available for searches immediately, make sure to refresh the index by calling
refresh_index().- document –
-
classmethod
refresh_index(es=None, index=None)¶ Refreshes the index.
Elasticsearch will update the index periodically automatically. If you need to see the documents you just indexed in your search results right now, you should call refresh_index as soon as you’re done indexing. This is particularly helpful for unit tests.
Parameters: - es – The Elasticsearch to use. If you don’t specify an Elasticsearch, it’ll use cls.get_es().
- index – The name of the index to use. If you don’t specify one it’ll use cls.get_index().
-
classmethod
unindex(id_, es=None, index=None)¶ Removes a particular item from the search index.
Parameters: - id – The Elasticsearch id for the document to remove from the index.
- es – The Elasticsearch to use. If you don’t specify an Elasticsearch, it’ll use cls.get_es().
- index – The name of the index to use. If you don’t specify one it’ll use cls.get_index().
-
classmethod
The DefaultMappingType class¶
-
class
elasticutils.DefaultMappingType¶ This is the default mapping type for S.
The MLT class¶
-
class
elasticutils.MLT(id_, s=None, mlt_fields=None, index=None, doctype=None, es=None, **query_params)¶ Represents a lazy Elasticsearch More Like This API request.
This is lazy in the sense that it doesn’t evaluate and execute the Elasticsearch request unless you force it to by iterating over it or getting the length of the search results.
For example:
>>> mlt = MLT(2034, index='addons_index', doctype='addon') >>> num_related_documents = len(mlt) >>> num_related_documents = list(mlt)
-
__init__(id_, s=None, mlt_fields=None, index=None, doctype=None, es=None, **query_params)¶ When the MLT is evaluated, it generates a list of dict results.
Parameters: - id – The id of the document we want to find more like.
- s – An instance of an S. Allows you to pass in a query which will be used as the body of the more-like-this request.
- mlt_fields – A list of fields to look at for more like this.
- index – The index to use. Falls back to the first index listed in s.get_indexes().
- doctype – The doctype to use. Falls back to the first doctype listed in s.get_doctypes().
- es – The Elasticsearch object to use. If you don’t provide one, then it will create one for you.
- query_params – Any additional query parameters for the more like this call.
Note
You must specify either an s or the index and doctype arguments. Omitting them will result in a ValueError.
-
to_python(obj)¶ Converts strings in a data structure to Python types
It converts datetime-ish things to Python datetimes.
Override if you want something different.
Parameters: obj – Python datastructure Returns: Python datastructure with strings converted to Python types Note
This does the conversion in-place!
-
get_es()¶ Returns an Elasticsearch.
- If there’s an s, then it returns that Elasticsearch.
- If the es was provided in the constructor, then it returns that Elasticsearch.
- Otherwise, it creates a new Elasticsearch and returns that.
Override this if that behavior isn’t correct for you.
-
raw()¶ Build query and passes to Elasticsearch, then returns the raw format returned.
-
The ESTestCase class¶
-
class
elasticutils.estestcase.ESTestCase(methodName='runTest')¶ Superclass for Elasticsearch-using test cases.
Property es_settings: settings to use to build a elasticsearch Elasticsearch object Property index_name: Name of the index to use for theses tests Property mapping_type_name: The mapping type name for the mapping you want created Property mapping: The mapping to use when creating the index Property data: Any documents to index during setup_class()For examples of usage, see
tests/test_*.pyfiles.You probably want to subclass this and at least set relevant class properties. Then use that subclass as the superclass for your tests.
-
classmethod
cleanup_index()¶ Cleans up the index
This deletes the index named by
cls.index_name.
-
classmethod
create_index(**kwargs)¶ Creates an index with specified settings
Uses
cls.index_nameas the index to create.Parameters: kwargs – Any additional args to put in the body like “settings”, “mappings”, etc.
-
classmethod
get_es()¶ Returns the Elasticsearch object specified by
cls.es_settings
-
classmethod
get_s(mapping_type=None)¶ Returns an S for the settings on this class
Uses
cls.es_settingsto configure the Elasticsearch object. Usescls.index_namefor the index andcls.mapping_type_namefor the MappingType to search.Parameters: mapping_type – The MappingType class to use to create the S
-
classmethod
index_data(documents, id_field='id')¶ Indexes specified data
Uses
cls.index_nameas the index to index into. Usescls.mapping_type_nameas the doctype to index these documents as.Parameters: - documents – List of documents as Python dicts
- id_field – The field of the document that represents the id
-
classmethod
refresh()¶ Refresh index after indexing
This refreshes the index specified by
cls.index_name.
-
classmethod
setup_class()¶ Sets up the index specified by
cls.index_nameThis will create the index named
cls.index_namewith the mapping specified incls.mappingand indexes any data specified incls.data.If you need something different, then override this.
-
classmethod
teardown_class()¶ Removes the index specified by
cls.index_nameThis should clean up anything created in
cls.setup_class()and anything created by the tests.
-
classmethod
Helper utilites¶
-
elasticutils.utils.chunked(iterable, n)¶ Returns chunks of n length of iterable
If len(iterable) % n != 0, then the last chunk will have length less than n.
Example:
>>> chunked([1, 2, 3, 4, 5], 2) [(1, 2), (3, 4), (5,)]
-
elasticutils.utils.format_explanation(explanation, indent=' ', indent_level=0)¶ Return explanation in an easier to read format
Easier to read for me, at least.
-
elasticutils.utils.to_json(data)¶ Convert Python structure to JSON used by Elasticsearch
This is a helper method that uses the elasticsearch-py JSONSerializer to serialize the structure. This is the serializer that elasticsearch-py uses to serialize data for Elasticsearch and handles dates.
Parameters: data – Python structure (e.g. dict, list, ...) Returns: string Examples:
>>> to_json({'query': {'match': {'message': 'test message'}}}) '{"query": {"match": {"message": "test message"}}}'
>>> from elasticutils import S >>> some_s = S().query(message__match='test message') >>> to_json(some_s.build_search()) '{"query": {"match": {"message": "test message"}}}'