Reusable SearchQuery
One of the most powerful concepts behind RushDB is its "fractal" API architecture with a self-aware design that's exposed through a consistent, easy-to-understand interface. This design philosophy allows you to use the same query structure across different aspects of your graph database, creating a highly flexible and intuitive developer experience.
The Power of Consistency
At the heart of RushDB's API design is the SearchQuery pattern - a standardized way to query your data that remains consistent regardless of what entity you're working with: records, relationships, labels, or properties. This consistent approach brings several powerful benefits:
- Reduced learning curve: Learn the query pattern once, apply it everywhere
- Predictable API usage: No need to learn different filtering paradigms for different entity types
- Code reusability: Reuse query logic across different parts of your application
- Self-discoverability: The graph intrinsically knows its structure and exposes it consistently
SearchQuery Structure
The SearchQuery object provides a standardized way to filter, sort, and paginate results:
interface SearchQuery {
// Filter by record labels
labels?: string[];
// Filter by property values and relationships
where?: WhereClause;
// Maximum number of records to return (default: 100)
limit?: number;
// Number of records to skip (for pagination)
skip?: number;
// Sorting configuration
orderBy?: OrderByClause;
// Data aggregation and transformation
aggregate?: AggregateClause;
}
Fractal API in Action
The power of RushDB's fractal API design becomes apparent when you see the same query structure used across different endpoints:
1. Searching Records
- TypeScript
- Python
- REST API
// Find all active PRODUCT records with price between $10-$50
const products = await db.records.find({
labels: ['PRODUCT'],
where: {
active: true,
price: { $gte: 10, $lte: 50 }
},
orderBy: { price: 'asc' },
limit: 20
});
# Find all active PRODUCT records with price between $10-$50
result = db.records.find({
"labels": ["PRODUCT"],
"where": {
"active": True,
"price": {"$gte": 10, "$lte": 50}
},
"orderBy": {"price": "asc"},
"limit": 20
})
products = result.data
# Find all active PRODUCT records with price between $10-$50
curl -X POST "https://api.rushdb.com/api/v1/records/search" \
-H "Authorization: Bearer $RUSHDB_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"labels": ["PRODUCT"],
"where": {
"active": true,
"price": {
"$gte": 10,
"$lte": 50
}
},
"orderBy": {"price": "asc"},
"limit": 20
}'
2. Deleting Records with the Same Query Structure
- TypeScript
- Python
- REST API
// Delete discontinued products with zero inventory
await db.records.delete({
labels: ['PRODUCT'],
where: {
discontinued: true,
inventory: 0
}
});
# Delete discontinued products with zero inventory
db.records.delete({
"labels": ["PRODUCT"],
"where": {
"discontinued": True,
"inventory": 0
}
})
# Delete discontinued products with zero inventory
curl -X PUT "https://api.rushdb.com/api/v1/records/delete" \
-H "Authorization: Bearer $RUSHDB_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"labels": ["PRODUCT"],
"where": {
"discontinued": true,
"inventory": 0
}
}'
3. Searching Relationships
- TypeScript
- Python
- REST API
// Find all CREATED relationships by users in the admin group
const createdRelationships = await db.relationships.find({
where: {
groups: { $in: ["admin"] },
$relation: {
type: "CREATED"
}
},
limit: 50
});
# Find all CREATED relationships by users in the admin group
created_relationships = db.relationships.find({
"where": {
"groups": { "$in": ["admin"] },
"$relation": {
"type": "CREATED"
}
},
"limit": 50
})
# Find all CREATED relationships by users in the admin group
curl -X POST "https://api.rushdb.com/api/v1/relationships/search" \
-H "Authorization: Bearer $RUSHDB_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"where": {
"groups": { "$in": ["admin"] },
"$relation": {
"type": "CREATED"
}
},
"limit": 50
}'
4. Discovering Labels
- TypeScript
- Python
- REST API
// Find all labels used on records in North America region
const labels = await db.labels.find({
where: {
region: { $in: ["US", "CA", "MX"] }
}
});
# Find all labels used on records in North America region
labels = db.labels.find({
"where": {
"region": {"$in": ["US", "CA", "MX"]}
}
})
# Find all labels used on records in North America region
curl -X POST "https://api.rushdb.com/api/v1/labels/search" \
-H "Authorization: Bearer $RUSHDB_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"where": {
"region": {"$in": ["US", "CA", "MX"]}
}
}'
5. Exploring Properties
- TypeScript
- Python
- REST API
// Get all string properties used on PRODUCT records
const productProps = await db.properties.find({
labels: ["PRODUCT"],
where: {
// ...
}
});
# Get all string properties used on PRODUCT records
product_props = db.properties.find({
"labels": ["PRODUCT"],
"where": {
// ...
}
})
# Get all string properties used on PRODUCT records
curl -X POST "https://api.rushdb.com/api/v1/properties/search" \
-H "Authorization: Bearer $RUSHDB_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"labels": ["PRODUCT"],
"where": {
// ...
}
}'
APIs Supporting SearchQuery
RushDB provides consistent SearchQuery capabilities across multiple API endpoints:
API Endpoint | Description | Documentation |
---|---|---|
/api/v1/records/search | Search for records | Records API |
/api/v1/records/delete | Delete records using search criteria | Delete Records |
/api/v1/relationships/search | Search for relationships | Relationships API |
/api/v1/labels/search | Search for labels | Labels API |
/api/v1/properties/search | Search for properties | Properties API |
/api/v1/properties/:id/values | Get property values with filtering | Properties API |
Powerful Use Cases
Dynamic Filtering in Catalog Applications
With RushDB's fractal API design, building dynamic filtering interfaces for catalog or marketplace applications becomes dramatically simplified. The more you filter records (and simultaneously filter properties), the more precise your results become.
To implement this pattern:
- Fetch all records and all available properties (no filters applied)
- As users select filters, apply the same SearchQuery to both the records and properties endpoints
- The filtered properties API will return only properties that exist in the remaining record set
- Update your UI to display only filter options that are still relevant
- TypeScript
- Python
// User selects a category filter
const filterQuery = {
where: { category: "electronics" }
};
// Get filtered products
const products = await db.records.find({
labels: ["PRODUCT"],
...filterQuery
});
// Get available properties for the remaining product set
const availableProperties = await db.properties.find(filterQuery);
// Generate dynamic filters based on available properties
const dynamicFilters = generateFiltersFromProperties(availableProperties);
# User selects a category filter
filter_query = {
"where": {"category": "electronics"}
}
# Get filtered products
result = db.records.find({
"labels": ["PRODUCT"],
**filter_query
})
products = result.data
# Get available properties for the remaining product set
available_properties = db.properties.find(filter_query)
# Generate dynamic filters based on available properties
dynamic_filters = generate_filters_from_properties(available_properties)
AI-Powered Data Analytics Without ETL
RushDB's fractal API design makes it exceptionally well-suited for AI workflows and RAG (Retrieval Augmented Generation) systems. By importing raw JSON data and allowing RushDB to automatically recognize and index structures, you can eliminate traditional ETL processes.
This allows AI agents to:
- Explore available data structure without predefined schemas
- Dynamically generate queries based on discovered patterns
- Refetch and recalculate results on-the-fly as new insights emerge
- Perform complex aggregations without manual data preparation
For example, an AI agent could:
- TypeScript
- Python
// Discovery phase: Explore available labels
const availableLabels = await db.labels.find({});
console.log("Discovered entity types:", Object.keys(availableLabels));
// Explore properties of a specific label
const personProperties = await db.properties.find({
labels: ["PERSON"],
where: {
// ...
}
});
// Generate insights based on discovered structure
const insightQuery = generateQueryFromDiscoveredStructure(personProperties);
const results = await db.records.find(insightQuery);
# Discovery phase: Explore available labels
available_labels = db.labels.find({})
print("Discovered entity types:", list(available_labels.keys()))
# Explore properties of a specific label
person_properties = db.properties.find({
"labels": ["PERSON"],
"where": {
// ...
}
})
# Generate insights based on discovered structure
insight_query = generate_query_from_discovered_structure(person_properties)
result = db.records.find(insight_query)
results = result.data
Conclusion
RushDB's fractal API design with the reusable SearchQuery pattern represents a significant advancement in database interaction. By maintaining a consistent query structure across different entities and operations, RushDB enables developers to build more intuitive, flexible, and powerful applications with less code and cognitive overhead.
This design philosophy reflects a deep understanding of how developers work with data, ensuring that once you learn the SearchQuery pattern, you can apply that knowledge universally throughout your application's interaction with RushDB.