> ## Documentation Index
> Fetch the complete documentation index at: https://mintlify.com/getzep/graphiti/llms.txt
> Use this file to discover all available pages before exploring further.

# Search

> Search functionality and configuration for querying knowledge graphs

## Overview

The search module provides powerful hybrid search capabilities for querying knowledge graphs. It supports multiple search methods (vector similarity, BM25 full-text search, breadth-first search) and various reranking strategies.

## SearchConfig

The `SearchConfig` class defines search behavior across different graph layers (edges, nodes, episodes, communities).

```python theme={null}
class SearchConfig(BaseModel):
    edge_config: EdgeSearchConfig | None = None
    node_config: NodeSearchConfig | None = None
    episode_config: EpisodeSearchConfig | None = None
    community_config: CommunitySearchConfig | None = None
    limit: int = 10
    reranker_min_score: float = 0
```

<ParamField path="edge_config" type="EdgeSearchConfig | None">
  Configuration for searching edges.
</ParamField>

<ParamField path="node_config" type="NodeSearchConfig | None">
  Configuration for searching nodes.
</ParamField>

<ParamField path="episode_config" type="EpisodeSearchConfig | None">
  Configuration for searching episodes.
</ParamField>

<ParamField path="community_config" type="CommunitySearchConfig | None">
  Configuration for searching communities.
</ParamField>

<ParamField path="limit" type="int" default="10">
  Maximum number of results to return.
</ParamField>

<ParamField path="reranker_min_score" type="float" default="0">
  Minimum score threshold for reranked results.
</ParamField>

## EdgeSearchConfig

Configuration for edge search operations.

```python theme={null}
class EdgeSearchConfig(BaseModel):
    search_methods: list[EdgeSearchMethod]
    reranker: EdgeReranker = EdgeReranker.rrf
    sim_min_score: float = DEFAULT_MIN_SCORE
    mmr_lambda: float = DEFAULT_MMR_LAMBDA
    bfs_max_depth: int = MAX_SEARCH_DEPTH
```

<ParamField path="search_methods" type="list[EdgeSearchMethod]" required>
  List of search methods to use. Options: `EdgeSearchMethod.cosine_similarity`, `EdgeSearchMethod.bm25`, `EdgeSearchMethod.bfs`.
</ParamField>

<ParamField path="reranker" type="EdgeReranker" default="EdgeReranker.rrf">
  Reranking strategy. Options: `rrf` (reciprocal rank fusion), `node_distance`, `episode_mentions`, `mmr` (maximal marginal relevance), `cross_encoder`.
</ParamField>

<ParamField path="sim_min_score" type="float">
  Minimum similarity score for vector search results.
</ParamField>

<ParamField path="mmr_lambda" type="float">
  Lambda parameter for MMR reranking (diversity vs relevance tradeoff).
</ParamField>

<ParamField path="bfs_max_depth" type="int">
  Maximum depth for breadth-first search.
</ParamField>

## NodeSearchConfig

Configuration for node search operations.

```python theme={null}
class NodeSearchConfig(BaseModel):
    search_methods: list[NodeSearchMethod]
    reranker: NodeReranker = NodeReranker.rrf
    sim_min_score: float = DEFAULT_MIN_SCORE
    mmr_lambda: float = DEFAULT_MMR_LAMBDA
    bfs_max_depth: int = MAX_SEARCH_DEPTH
```

<ParamField path="search_methods" type="list[NodeSearchMethod]" required>
  List of search methods to use. Options: `NodeSearchMethod.cosine_similarity`, `NodeSearchMethod.bm25`, `NodeSearchMethod.bfs`.
</ParamField>

<ParamField path="reranker" type="NodeReranker" default="NodeReranker.rrf">
  Reranking strategy. Options: `rrf`, `node_distance`, `episode_mentions`, `mmr`, `cross_encoder`.
</ParamField>

<ParamField path="sim_min_score" type="float">
  Minimum similarity score for vector search results.
</ParamField>

<ParamField path="mmr_lambda" type="float">
  Lambda parameter for MMR reranking.
</ParamField>

<ParamField path="bfs_max_depth" type="int">
  Maximum depth for breadth-first search.
</ParamField>

## EpisodeSearchConfig

Configuration for episode search operations.

```python theme={null}
class EpisodeSearchConfig(BaseModel):
    search_methods: list[EpisodeSearchMethod]
    reranker: EpisodeReranker = EpisodeReranker.rrf
    sim_min_score: float = DEFAULT_MIN_SCORE
    mmr_lambda: float = DEFAULT_MMR_LAMBDA
    bfs_max_depth: int = MAX_SEARCH_DEPTH
```

<ParamField path="search_methods" type="list[EpisodeSearchMethod]" required>
  List of search methods to use. Options: `EpisodeSearchMethod.bm25`.
</ParamField>

<ParamField path="reranker" type="EpisodeReranker" default="EpisodeReranker.rrf">
  Reranking strategy. Options: `rrf`, `cross_encoder`.
</ParamField>

## CommunitySearchConfig

Configuration for community search operations.

```python theme={null}
class CommunitySearchConfig(BaseModel):
    search_methods: list[CommunitySearchMethod]
    reranker: CommunityReranker = CommunityReranker.rrf
    sim_min_score: float = DEFAULT_MIN_SCORE
    mmr_lambda: float = DEFAULT_MMR_LAMBDA
    bfs_max_depth: int = MAX_SEARCH_DEPTH
```

<ParamField path="search_methods" type="list[CommunitySearchMethod]" required>
  List of search methods to use. Options: `CommunitySearchMethod.cosine_similarity`, `CommunitySearchMethod.bm25`.
</ParamField>

<ParamField path="reranker" type="CommunityReranker" default="CommunityReranker.rrf">
  Reranking strategy. Options: `rrf`, `mmr`, `cross_encoder`.
</ParamField>

## SearchResults

Container for search results across different graph layers.

```python theme={null}
class SearchResults(BaseModel):
    edges: list[EntityEdge] = []
    edge_reranker_scores: list[float] = []
    nodes: list[EntityNode] = []
    node_reranker_scores: list[float] = []
    episodes: list[EpisodicNode] = []
    episode_reranker_scores: list[float] = []
    communities: list[CommunityNode] = []
    community_reranker_scores: list[float] = []
```

<ResponseField name="edges" type="list[EntityEdge]">
  List of relevant entity edges.
</ResponseField>

<ResponseField name="edge_reranker_scores" type="list[float]">
  Reranker scores for edges (parallel to edges list).
</ResponseField>

<ResponseField name="nodes" type="list[EntityNode]">
  List of relevant entity nodes.
</ResponseField>

<ResponseField name="node_reranker_scores" type="list[float]">
  Reranker scores for nodes (parallel to nodes list).
</ResponseField>

<ResponseField name="episodes" type="list[EpisodicNode]">
  List of relevant episodes.
</ResponseField>

<ResponseField name="episode_reranker_scores" type="list[float]">
  Reranker scores for episodes (parallel to episodes list).
</ResponseField>

<ResponseField name="communities" type="list[CommunityNode]">
  List of relevant communities.
</ResponseField>

<ResponseField name="community_reranker_scores" type="list[float]">
  Reranker scores for communities (parallel to communities list).
</ResponseField>

### merge

```python theme={null}
@classmethod
def merge(cls, results_list: list[SearchResults]) -> SearchResults
```

Merge multiple SearchResults objects into a single SearchResults object.

<ParamField path="results_list" type="list[SearchResults]" required>
  List of SearchResults objects to merge.
</ParamField>

## SearchFilters

Filters to apply when searching the graph.

```python theme={null}
class SearchFilters(BaseModel):
    node_labels: list[str] | None = None
    edge_types: list[str] | None = None
    valid_at: list[list[DateFilter]] | None = None
    invalid_at: list[list[DateFilter]] | None = None
    created_at: list[list[DateFilter]] | None = None
    expired_at: list[list[DateFilter]] | None = None
    edge_uuids: list[str] | None = None
    property_filters: list[PropertyFilter] | None = None
```

<ParamField path="node_labels" type="list[str] | None">
  Filter nodes by labels.
</ParamField>

<ParamField path="edge_types" type="list[str] | None">
  Filter edges by type names.
</ParamField>

<ParamField path="valid_at" type="list[list[DateFilter]] | None">
  Filter by valid\_at timestamp (list of OR conditions, each containing AND conditions).
</ParamField>

<ParamField path="invalid_at" type="list[list[DateFilter]] | None">
  Filter by invalid\_at timestamp.
</ParamField>

<ParamField path="created_at" type="list[list[DateFilter]] | None">
  Filter by created\_at timestamp.
</ParamField>

<ParamField path="expired_at" type="list[list[DateFilter]] | None">
  Filter by expired\_at timestamp.
</ParamField>

<ParamField path="edge_uuids" type="list[str] | None">
  Filter to specific edge UUIDs.
</ParamField>

<ParamField path="property_filters" type="list[PropertyFilter] | None">
  Filter by custom properties.
</ParamField>

### Example

```python theme={null}
from graphiti_core.search.search_filters import SearchFilters, DateFilter, ComparisonOperator
from datetime import datetime

filters = SearchFilters(
    node_labels=["Person", "Organization"],
    created_at=[
        [
            DateFilter(
                date=datetime(2024, 1, 1),
                comparison_operator=ComparisonOperator.greater_than
            )
        ]
    ]
)

results = await graphiti.search_(query="AI research", search_filter=filters)
```

## DateFilter

Filter for date-based queries.

```python theme={null}
class DateFilter(BaseModel):
    date: datetime | None = None
    comparison_operator: ComparisonOperator
```

<ParamField path="date" type="datetime | None">
  The datetime to filter on.
</ParamField>

<ParamField path="comparison_operator" type="ComparisonOperator" required>
  Comparison operator: `equals`, `not_equals`, `greater_than`, `less_than`, `greater_than_equal`, `less_than_equal`, `is_null`, `is_not_null`.
</ParamField>

## PropertyFilter

Filter for custom property queries.

```python theme={null}
class PropertyFilter(BaseModel):
    property_name: str
    property_value: str | int | float | None = None
    comparison_operator: ComparisonOperator
```

<ParamField path="property_name" type="str" required>
  Name of the property to filter on.
</ParamField>

<ParamField path="property_value" type="str | int | float | None">
  Value to match on for the property.
</ParamField>

<ParamField path="comparison_operator" type="ComparisonOperator" required>
  Comparison operator for the property.
</ParamField>

## Search Config Recipes

Pre-configured search configurations for common use cases.

### COMBINED\_HYBRID\_SEARCH\_CROSS\_ENCODER

```python theme={null}
from graphiti_core.search.search_config_recipes import COMBINED_HYBRID_SEARCH_CROSS_ENCODER
```

Performs a full-text search, similarity search, and BFS with cross\_encoder reranking over edges, nodes, episodes, and communities. Best for high-accuracy results.

### COMBINED\_HYBRID\_SEARCH\_RRF

```python theme={null}
from graphiti_core.search.search_config_recipes import COMBINED_HYBRID_SEARCH_RRF
```

Performs a hybrid search with RRF (reciprocal rank fusion) reranking over all graph layers. Good balance of speed and accuracy.

### COMBINED\_HYBRID\_SEARCH\_MMR

```python theme={null}
from graphiti_core.search.search_config_recipes import COMBINED_HYBRID_SEARCH_MMR
```

Performs a hybrid search with MMR (maximal marginal relevance) reranking for diverse results.

### EDGE\_HYBRID\_SEARCH\_RRF

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_RRF
```

Performs a hybrid search over edges only with RRF reranking.

### EDGE\_HYBRID\_SEARCH\_MMR

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_MMR
```

Performs a hybrid search over edges with MMR reranking for diverse edge results.

### EDGE\_HYBRID\_SEARCH\_NODE\_DISTANCE

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_NODE_DISTANCE
```

Performs a hybrid search over edges with node distance reranking. Requires `center_node_uuid` parameter.

### EDGE\_HYBRID\_SEARCH\_EPISODE\_MENTIONS

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_EPISODE_MENTIONS
```

Performs a hybrid search over edges with reranking by episode mention count.

### EDGE\_HYBRID\_SEARCH\_CROSS\_ENCODER

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_CROSS_ENCODER
```

Performs a hybrid search over edges with cross encoder reranking for highest accuracy.

### NODE\_HYBRID\_SEARCH\_RRF

```python theme={null}
from graphiti_core.search.search_config_recipes import NODE_HYBRID_SEARCH_RRF
```

Performs a hybrid search over nodes with RRF reranking.

### NODE\_HYBRID\_SEARCH\_MMR

```python theme={null}
from graphiti_core.search.search_config_recipes import NODE_HYBRID_SEARCH_MMR
```

Performs a hybrid search over nodes with MMR reranking.

### NODE\_HYBRID\_SEARCH\_NODE\_DISTANCE

```python theme={null}
from graphiti_core.search.search_config_recipes import NODE_HYBRID_SEARCH_NODE_DISTANCE
```

Performs a hybrid search over nodes with node distance reranking.

### NODE\_HYBRID\_SEARCH\_EPISODE\_MENTIONS

```python theme={null}
from graphiti_core.search.search_config_recipes import NODE_HYBRID_SEARCH_EPISODE_MENTIONS
```

Performs a hybrid search over nodes with episode mention count reranking.

### NODE\_HYBRID\_SEARCH\_CROSS\_ENCODER

```python theme={null}
from graphiti_core.search.search_config_recipes import NODE_HYBRID_SEARCH_CROSS_ENCODER
```

Performs a hybrid search over nodes with cross encoder reranking.

### COMMUNITY\_HYBRID\_SEARCH\_RRF

```python theme={null}
from graphiti_core.search.search_config_recipes import COMMUNITY_HYBRID_SEARCH_RRF
```

Performs a hybrid search over communities with RRF reranking.

### COMMUNITY\_HYBRID\_SEARCH\_MMR

```python theme={null}
from graphiti_core.search.search_config_recipes import COMMUNITY_HYBRID_SEARCH_MMR
```

Performs a hybrid search over communities with MMR reranking.

### COMMUNITY\_HYBRID\_SEARCH\_CROSS\_ENCODER

```python theme={null}
from graphiti_core.search.search_config_recipes import COMMUNITY_HYBRID_SEARCH_CROSS_ENCODER
```

Performs a hybrid search over communities with cross encoder reranking.

## Examples

### Basic Search

```python theme={null}
from graphiti_core import Graphiti

graphiti = Graphiti(uri="bolt://localhost:7687", user="neo4j", password="password")

# Simple search
edges = await graphiti.search(
    query="What are the user's interests?",
    group_ids=["user_123"],
    num_results=10
)

for edge in edges:
    print(f"Fact: {edge.fact}")
```

### Advanced Search with Custom Config

```python theme={null}
from graphiti_core.search.search_config import (
    SearchConfig,
    EdgeSearchConfig,
    EdgeSearchMethod,
    EdgeReranker,
    NodeSearchConfig,
    NodeSearchMethod,
    NodeReranker
)

# Create custom search config
config = SearchConfig(
    edge_config=EdgeSearchConfig(
        search_methods=[EdgeSearchMethod.bm25, EdgeSearchMethod.cosine_similarity],
        reranker=EdgeReranker.cross_encoder
    ),
    node_config=NodeSearchConfig(
        search_methods=[NodeSearchMethod.cosine_similarity],
        reranker=NodeReranker.rrf
    ),
    limit=20
)

results = await graphiti.search_(
    query="AI research projects",
    config=config,
    group_ids=["user_123"]
)

print(f"Found {len(results.edges)} edges and {len(results.nodes)} nodes")
```

### Search with Filters

```python theme={null}
from graphiti_core.search.search_filters import (
    SearchFilters,
    DateFilter,
    ComparisonOperator,
    PropertyFilter
)
from datetime import datetime, timedelta

# Filter for recent data
recent_date = datetime.now() - timedelta(days=30)

filters = SearchFilters(
    node_labels=["Person", "Organization"],
    edge_types=["WORKS_AT", "COLLABORATES_WITH"],
    created_at=[
        [
            DateFilter(
                date=recent_date,
                comparison_operator=ComparisonOperator.greater_than
            )
        ]
    ],
    property_filters=[
        PropertyFilter(
            property_name="status",
            property_value="active",
            comparison_operator=ComparisonOperator.equals
        )
    ]
)

results = await graphiti.search_(
    query="active collaborations",
    search_filter=filters,
    group_ids=["user_123"]
)
```

### Node Distance Reranking

```python theme={null}
from graphiti_core.search.search_config_recipes import EDGE_HYBRID_SEARCH_NODE_DISTANCE

# Search with results reranked by proximity to a center node
edges = await graphiti.search(
    query="related information",
    center_node_uuid="node-uuid-123",
    group_ids=["user_123"],
    num_results=10
)

# Or with advanced search
results = await graphiti.search_(
    query="related information",
    config=EDGE_HYBRID_SEARCH_NODE_DISTANCE,
    center_node_uuid="node-uuid-123",
    group_ids=["user_123"]
)
```

### Breadth-First Search

```python theme={null}
from graphiti_core.search.search_config import (
    SearchConfig,
    EdgeSearchConfig,
    EdgeSearchMethod,
    EdgeReranker
)

config = SearchConfig(
    edge_config=EdgeSearchConfig(
        search_methods=[EdgeSearchMethod.bfs],
        reranker=EdgeReranker.rrf,
        bfs_max_depth=3
    )
)

results = await graphiti.search_(
    query="expand from these nodes",
    config=config,
    bfs_origin_node_uuids=["node-1", "node-2"],
    group_ids=["user_123"]
)
```
