Documentation Index
Fetch the complete documentation index at: https://docs.cocobase.buzz/llms.txt
Use this file to discover all available pages before exploring further.
Relationships
Build relational data structures by linking documents and users together with automatic population support across all platforms.Relationships enable you to structure complex data models like social
networks, e-commerce systems, and collaborative applications.
Overview
Cocobase supports powerful relationship features:- Document references - Store IDs to link documents
- Population - Automatically fetch related data
- Nested population - Multi-level relationship resolution
- User-to-user relationships - Followers, friends, referrals
- User-to-document relationships - Bookmarks, favorites, ownership
- Document-to-document relationships - Comments, reviews, hierarchies
Relationship Types
One-to-One
A single reference to another entity.{
"id": "user_123",
"email": "john@example.com",
"data": {
"username": "johndoe",
"referred_by": "user_456"
}
}
One-to-Many / Many-to-Many
Arrays of references for multiple relationships.{
"id": "user_123",
"email": "john@example.com",
"data": {
"username": "johndoe",
"followers_ids": ["user_456", "user_789", "user_012"],
"following_ids": ["user_456", "user_999"]
}
}
Creating Relationships
User to User
- JavaScript
- Dart
- Go
- Python
- HTTP
import { Cocobase } from 'cocobase';
const db = new Cocobase({ apiKey: 'your-api-key' });
// User signs up with referral
await db.auth.signup({
email: 'bob@example.com',
password: 'password123',
data: {
username: 'bob',
referred_by: 'user_abc123'
}
});
// Follow a user
const currentUser = await db.auth.getUser();
const currentFollowing = currentUser.data.following_ids || [];
await db.auth.updateUser({
data: {
following_ids: [...currentFollowing, 'user_to_follow']
}
});
// Unfollow a user
await db.auth.updateUser({
data: {
following_ids: currentFollowing.filter(id => id !== 'user_to_unfollow')
}
});
import 'package:cocobase/cocobase.dart';
final db = Cocobase(CocobaseConfig(apiKey: 'your-api-key'));
// User signs up with referral
await db.auth.signup(
email: 'bob@example.com',
password: 'password123',
data: {
'username': 'bob',
'referred_by': 'user_abc123',
},
);
// Follow a user
final currentUser = await db.auth.getUser();
final currentFollowing = List<String>.from(
currentUser.data['following_ids'] ?? []
);
await db.auth.updateUser({
'data': {
'following_ids': [...currentFollowing, 'user_to_follow'],
}
});
// Unfollow a user
await db.auth.updateUser({
'data': {
'following_ids': currentFollowing.where((id) => id != 'user_to_unfollow').toList(),
}
});
package main
import (
"context"
"github.com/lordace-coder/cocobase-go/cocobase"
)
func main() {
client := cocobase.NewClient(cocobase.Config{
APIKey: "your-api-key",
})
ctx := context.Background()
// User signs up with referral
_, err := client.Signup(ctx, cocobase.SignupRequest{
Email: "bob@example.com",
Password: "password123",
Data: map[string]interface{}{
"username": "bob",
"referred_by": "user_abc123",
},
})
// Update user relationships
updates := map[string]interface{}{
"data": map[string]interface{}{
"following_ids": []string{"user_456", "user_789"},
},
}
_, err = client.UpdateUser(ctx, updates)
}
import requests
API_KEY = 'your-api-key'
BASE_URL = 'https://api.cocobase.cc'
headers = {'X-API-Key': API_KEY, 'Content-Type': 'application/json'}
# User signs up with referral
signup_data = {
'email': 'bob@example.com',
'password': 'password123',
'data': {
'username': 'bob',
'referred_by': 'user_abc123'
}
}
response = requests.post(
f'{BASE_URL}/auth-collections/signup',
headers=headers,
json=signup_data
)
token = response.json()['access_token']
# Follow a user
auth_headers = {
'Authorization': f'Bearer {token}',
'Content-Type': 'application/json'
}
# Get current user
user_response = requests.get(
f'{BASE_URL}/auth-collections/user',
headers=auth_headers
)
current_user = user_response.json()
# Update following list
current_following = current_user.get('data', {}).get('following_ids', [])
new_following = current_following + ['user_to_follow']
requests.patch(
f'{BASE_URL}/auth-collections/user',
headers=auth_headers,
json={'data': {'following_ids': new_following}}
)
# User signs up with referral
curl -X POST https://api.cocobase.cc/auth-collections/signup \
-H "X-API-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"email": "bob@example.com",
"password": "password123",
"data": {
"username": "bob",
"referred_by": "user_abc123"
}
}'
# Follow a user (update following list)
curl -X PATCH https://api.cocobase.cc/auth-collections/user \
-H "Authorization: Bearer YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"data": {
"following_ids": ["user_456", "user_789", "user_to_follow"]
}
}'
User to Document
- JavaScript
- Dart
- Go
- Python
- HTTP
// User bookmarks a post
const currentUser = await db.auth.getUser();
const bookmarks = currentUser.data.bookmarked_posts || [];
await db.auth.updateUser({
data: {
bookmarked_posts: [...bookmarks, 'post_123']
}
});
// Remove bookmark
await db.auth.updateUser({
data: {
bookmarked_posts: bookmarks.filter(id => id !== 'post_123')
}
});
// User bookmarks a post
final currentUser = await db.auth.getUser();
final bookmarks = List<String>.from(
currentUser.data['bookmarked_posts'] ?? []
);
await db.auth.updateUser({
'data': {
'bookmarked_posts': [...bookmarks, 'post_123'],
}
});
// Remove bookmark
await db.auth.updateUser({
'data': {
'bookmarked_posts': bookmarks.where((id) => id != 'post_123').toList(),
}
});
// Update user bookmarks
updates := map[string]interface{}{
"data": map[string]interface{}{
"bookmarked_posts": []string{"post_123", "post_456"},
},
}
_, err := client.UpdateUser(ctx, updates)
# User bookmarks a post
user_response = requests.get(
f'{BASE_URL}/auth-collections/user',
headers=auth_headers
)
current_user = user_response.json()
bookmarks = current_user.get('data', {}).get('bookmarked_posts', [])
new_bookmarks = bookmarks + ['post_123']
requests.patch(
f'{BASE_URL}/auth-collections/user',
headers=auth_headers,
json={'data': {'bookmarked_posts': new_bookmarks}}
)
# User bookmarks a post
curl -X PATCH https://api.cocobase.cc/auth-collections/user \
-H "Authorization: Bearer YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"data": {
"bookmarked_posts": ["post_123", "post_456", "post_789"]
}
}'
Document to Document
- JavaScript
- Dart
- Go
- Python
- HTTP
// Create a post
const post = await db.createDocument('posts', {
title: 'My first post',
content: 'Hello world!',
author_id: 'user_123'
});
// Create a comment on the post
const comment = await db.createDocument('comments', {
post_id: post.id,
author_id: 'user_456',
text: 'Great post!',
created_at: new Date().toISOString()
});
// Create a post
final post = await db.createDocument('posts', {
'title': 'My first post',
'content': 'Hello world!',
'author_id': 'user_123',
});
// Create a comment on the post
final comment = await db.createDocument('comments', {
'post_id': post.id,
'author_id': 'user_456',
'text': 'Great post!',
'created_at': DateTime.now().toIso8601String(),
});
// Create a post
postData := map[string]interface{}{
"title": "My first post",
"content": "Hello world!",
"author_id": "user_123",
}
post, err := client.CreateDocument(ctx, "posts", postData)
// Create a comment on the post
commentData := map[string]interface{}{
"post_id": post.ID,
"author_id": "user_456",
"text": "Great post!",
"created_at": time.Now().Format(time.RFC3339),
}
comment, err := client.CreateDocument(ctx, "comments", commentData)
# Create a post
post_data = {
'title': 'My first post',
'content': 'Hello world!',
'author_id': 'user_123'
}
post_response = requests.post(
f'{BASE_URL}/collections/posts/documents',
headers=headers,
json=post_data
)
post = post_response.json()
# Create a comment on the post
comment_data = {
'post_id': post['id'],
'author_id': 'user_456',
'text': 'Great post!',
'created_at': datetime.utcnow().isoformat()
}
requests.post(
f'{BASE_URL}/collections/comments/documents',
headers=headers,
json=comment_data
)
# Create a post
curl -X POST https://api.cocobase.cc/collections/posts/documents \
-H "X-API-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"title": "My first post",
"content": "Hello world!",
"author_id": "user_123"
}'
# Create a comment (using post ID from response)
curl -X POST https://api.cocobase.cc/collections/comments/documents \
-H "X-API-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"post_id": "doc_post123",
"author_id": "user_456",
"text": "Great post!"
}'
Populating Relationships
Automatically fetch related data instead of just IDs.Basic Population
- JavaScript
- Dart
- Go
- Python
- HTTP
// Without population (just IDs)
const users = await db.listDocuments('users');
console.log(users[0].data.referred_by); // "user_456"
// With population (full data)
const usersWithReferrer = await db.listDocuments('users', {
populate: ['referred_by']
});
console.log(usersWithReferrer[0].data.referred_by);
// { id: "user_456", email: "alice@example.com", data: { username: "alice" } }
// Without population (just IDs)
final users = await db.listDocuments('users');
print(users[0].data['referred_by']); // "user_456"
// With population (full data)
final usersWithReferrer = await db.listDocuments('users',
queryBuilder: QueryBuilder().populate('referred_by')
);
print(usersWithReferrer[0].data['referred_by']);
// { id: "user_456", email: "alice@example.com", data: { username: "alice" } }
// Basic query (just IDs)
users, _ := client.ListDocuments(ctx, "users", nil)
fmt.Printf("Referred by: %v\n", users[0].Data["referred_by"]) // "user_456"
// With population (via URL parameter)
// Note: Use HTTP endpoint with populate parameter
// /collections/users/documents?populate=referred_by
# Without population (just IDs)
users = requests.get(
f'{BASE_URL}/auth-collections/users',
headers=headers
).json()
print(users['data'][0]['data']['referred_by']) # "user_456"
# With population (full data)
params = {'populate': 'referred_by'}
users_with_referrer = requests.get(
f'{BASE_URL}/auth-collections/users',
headers=headers,
params=params
).json()
print(users_with_referrer['data'][0]['data']['referred_by'])
# { id: "user_456", email: "alice@example.com", data: { username: "alice" } }
# Without population (just IDs)
curl "https://api.cocobase.cc/auth-collections/users" \
-H "X-API-Key: your-api-key"
# With population (full data)
curl "https://api.cocobase.cc/auth-collections/users?populate=referred_by" \
-H "X-API-Key: your-api-key"
Populate Multiple Fields
- JavaScript
- Dart
- Go
- Python
- HTTP
const users = await db.listDocuments('users', {
populate: ['referred_by', 'followers_ids', 'following_ids']
});
console.log(users[0].data.referred_by); // Full user object
console.log(users[0].data.followers_ids); // Array of full user objects
console.log(users[0].data.following_ids); // Array of full user objects
final users = await db.listDocuments('users',
queryBuilder: QueryBuilder().populateAll(['referred_by', 'followers_ids', 'following_ids'])
);
print(users[0].data['referred_by']); // Full user object
print(users[0].data['followers_ids']); // Array of full user objects
print(users[0].data['following_ids']); // Array of full user objects
// Use HTTP endpoint with multiple populate parameters
// /collections/users/documents?populate=referred_by&populate=followers_ids&populate=following_ids
# Multiple populate parameters
params = {
'populate': ['referred_by', 'followers_ids', 'following_ids']
}
users = requests.get(
f'{BASE_URL}/auth-collections/users',
headers=headers,
params=params
).json()
print(users['data'][0]['data']['referred_by']) # Full user object
print(users['data'][0]['data']['followers_ids']) # Array of full user objects
# Populate multiple fields
curl "https://api.cocobase.cc/auth-collections/users?populate=referred_by&populate=followers_ids&populate=following_ids" \
-H "X-API-Key: your-api-key"
Explicit Source Specification
Force population from specific collections or AppUser model.- JavaScript
- Dart
- Go
- Python
- HTTP
// Force fetch from AppUser model
const posts = await db.listDocuments('posts', {
populate: ['author:appuser']
});
// Force fetch from specific collection
const projects = await db.listDocuments('projects', {
populate: ['owner:team_members']
});
// Force fetch from AppUser model
final posts = await db.listDocuments('posts',
queryBuilder: QueryBuilder().populate('author:appuser')
);
// Force fetch from specific collection
final projects = await db.listDocuments('projects',
queryBuilder: QueryBuilder().populate('owner:team_members')
);
// Use HTTP endpoint with explicit source
// /collections/posts/documents?populate=author:appuser
// /collections/projects/documents?populate=owner:team_members
# Force fetch from AppUser model
params = {'populate': 'author:appuser'}
posts = requests.get(
f'{BASE_URL}/collections/posts/documents',
headers=headers,
params=params
).json()
# Force fetch from specific collection
params = {'populate': 'owner:team_members'}
projects = requests.get(
f'{BASE_URL}/collections/projects/documents',
headers=headers,
params=params
).json()
# Force fetch from AppUser model
curl "https://api.cocobase.cc/collections/posts/documents?populate=author:appuser" \
-H "X-API-Key: your-api-key"
# Force fetch from specific collection
curl "https://api.cocobase.cc/collections/projects/documents?populate=owner:team_members" \
-H "X-API-Key: your-api-key"
Social Features
Follow System
- JavaScript
- Dart
- Go
- Python
- HTTP
class FollowSystem {
constructor(db, token) {
this.db = db;
this.token = token;
}
async follow(userIdToFollow) {
const currentUser = await this.db.auth.getUser();
const following = currentUser.data.following_ids || [];
if (following.includes(userIdToFollow)) {
console.log('Already following');
return;
}
await this.db.auth.updateUser({
data: {
following_ids: [...following, userIdToFollow]
}
});
}
async unfollow(userIdToUnfollow) {
const currentUser = await this.db.auth.getUser();
const following = currentUser.data.following_ids || [];
await this.db.auth.updateUser({
data: {
following_ids: following.filter(id => id !== userIdToUnfollow)
}
});
}
async getFollowers(userId) {
const response = await this.db.listDocuments('users', {
filters: { id: userId },
populate: ['followers_ids']
});
return response[0]?.data.followers_ids || [];
}
async getFollowing(userId) {
const response = await this.db.listDocuments('users', {
filters: { id: userId },
populate: ['following_ids']
});
return response[0]?.data.following_ids || [];
}
}
// Usage
const followSystem = new FollowSystem(db, userToken);
await followSystem.follow('user_456');
const followers = await followSystem.getFollowers('user_123');
class FollowSystem {
final Cocobase db;
FollowSystem(this.db);
Future<void> follow(String userIdToFollow) async {
final currentUser = await db.auth.getUser();
final following = List<String>.from(
currentUser.data['following_ids'] ?? []
);
if (following.contains(userIdToFollow)) {
print('Already following');
return;
}
await db.auth.updateUser({
'data': {
'following_ids': [...following, userIdToFollow],
}
});
}
Future<void> unfollow(String userIdToUnfollow) async {
final currentUser = await db.auth.getUser();
final following = List<String>.from(
currentUser.data['following_ids'] ?? []
);
await db.auth.updateUser({
'data': {
'following_ids': following.where((id) => id != userIdToUnfollow).toList(),
}
});
}
Future<List<dynamic>> getFollowers(String userId) async {
final users = await db.listDocuments('users',
queryBuilder: QueryBuilder()
.where('id', userId)
.populate('followers_ids')
);
return users.first.data['followers_ids'] ?? [];
}
Future<List<dynamic>> getFollowing(String userId) async {
final users = await db.listDocuments('users',
queryBuilder: QueryBuilder()
.where('id', userId)
.populate('following_ids')
);
return users.first.data['following_ids'] ?? [];
}
}
// Usage
final followSystem = FollowSystem(db);
await followSystem.follow('user_456');
final followers = await followSystem.getFollowers('user_123');
type FollowSystem struct {
client *cocobase.Client
}
func NewFollowSystem(client *cocobase.Client) *FollowSystem {
return &FollowSystem{client: client}
}
func (f *FollowSystem) Follow(ctx context.Context, userIDToFollow string) error {
// Get current user
currentUser, err := f.client.GetCurrentUser(ctx)
if err != nil {
return err
}
// Get current following list
following := []string{}
if followingData, ok := currentUser.Data["following_ids"].([]interface{}); ok {
for _, id := range followingData {
if idStr, ok := id.(string); ok {
following = append(following, idStr)
}
}
}
// Check if already following
for _, id := range following {
if id == userIDToFollow {
fmt.Println("Already following")
return nil
}
}
// Add to following list
following = append(following, userIDToFollow)
// Update user
updates := map[string]interface{}{
"data": map[string]interface{}{
"following_ids": following,
},
}
_, err = f.client.UpdateUser(ctx, updates)
return err
}
func (f *FollowSystem) Unfollow(ctx context.Context, userIDToUnfollow string) error {
currentUser, err := f.client.GetCurrentUser(ctx)
if err != nil {
return err
}
following := []string{}
if followingData, ok := currentUser.Data["following_ids"].([]interface{}); ok {
for _, id := range followingData {
if idStr, ok := id.(string); ok {
if idStr != userIDToUnfollow {
following = append(following, idStr)
}
}
}
}
updates := map[string]interface{}{
"data": map[string]interface{}{
"following_ids": following,
},
}
_, err = f.client.UpdateUser(ctx, updates)
return err
}
// Usage
followSystem := NewFollowSystem(client)
err := followSystem.Follow(ctx, "user_456")
class FollowSystem:
def __init__(self, api_key, token):
self.api_key = api_key
self.token = token
self.headers = {
'Authorization': f'Bearer {token}',
'Content-Type': 'application/json'
}
def follow(self, user_id_to_follow):
# Get current user
response = requests.get(
f'{BASE_URL}/auth-collections/user',
headers=self.headers
)
current_user = response.json()
following = current_user.get('data', {}).get('following_ids', [])
if user_id_to_follow in following:
print('Already following')
return
new_following = following + [user_id_to_follow]
requests.patch(
f'{BASE_URL}/auth-collections/user',
headers=self.headers,
json={'data': {'following_ids': new_following}}
)
def unfollow(self, user_id_to_unfollow):
response = requests.get(
f'{BASE_URL}/auth-collections/user',
headers=self.headers
)
current_user = response.json()
following = current_user.get('data', {}).get('following_ids', [])
new_following = [id for id in following if id != user_id_to_unfollow]
requests.patch(
f'{BASE_URL}/auth-collections/user',
headers=self.headers,
json={'data': {'following_ids': new_following}}
)
def get_followers(self, user_id):
params = {'populate': 'followers_ids'}
response = requests.get(
f'{BASE_URL}/auth-collections/users/{user_id}',
headers={'X-API-Key': self.api_key},
params=params
)
user = response.json()
return user.get('data', {}).get('followers_ids', [])
# Usage
follow_system = FollowSystem('your-api-key', user_token)
follow_system.follow('user_456')
followers = follow_system.get_followers('user_123')
# Follow a user
# First, get current user
curl https://api.cocobase.cc/auth-collections/user \
-H "Authorization: Bearer YOUR_TOKEN"
# Update following list (add new user)
curl -X PATCH https://api.cocobase.cc/auth-collections/user \
-H "Authorization: Bearer YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"data": {
"following_ids": ["user_456", "user_789", "user_new"]
}
}'
# Get user with populated followers
curl "https://api.cocobase.cc/auth-collections/users/user_123?populate=followers_ids" \
-H "X-API-Key: your-api-key"
Referral System
- JavaScript
- Dart
- Go
- Python
- HTTP
async function getReferralStats(db, userId) {
// Get this user with populated referrer
const users = await db.listDocuments('users', {
filters: { id: userId },
populate: ['referred_by'],
limit: 1
});
const user = users[0];
// Get users referred by this user
const referrals = await db.listDocuments('users', {
filters: { referred_by: userId }
});
return {
referredBy: user?.data?.referred_by,
referralCount: referrals.length,
referrals
};
}
// Usage
const stats = await getReferralStats(db, 'user_123');
console.log('Referred by:', stats.referredBy?.data?.username);
console.log('Total referrals:', stats.referralCount);
Future<Map<String, dynamic>> getReferralStats(Cocobase db, String userId) async {
// Get the user who referred this user
final users = await db.listDocuments('users',
queryBuilder: QueryBuilder()
.where('id', userId)
.populate('referred_by')
);
final user = users.first;
// Get all users this user referred
final referrals = await db.listDocuments('users', filters: {
'data.referred_by': userId,
});
return {
'referredBy': user.data['referred_by'],
'referralCount': referrals.length,
'referrals': referrals,
};
}
// Usage
final stats = await getReferralStats(db, 'user_123');
print('Referred by: ${stats['referredBy']?['data']?['username']}');
print('Total referrals: ${stats['referralCount']}');
func getReferralStats(client *cocobase.Client, ctx context.Context, userID string) (map[string]interface{}, error) {
// Get the user who referred this user
query := cocobase.NewQuery().Where("id", userID)
users, err := client.ListDocuments(ctx, "users", query)
if err != nil || len(users) == 0 {
return nil, err
}
user := users[0]
// Get all users this user referred
query = cocobase.NewQuery().Where("data.referred_by", userID)
referrals, err := client.ListDocuments(ctx, "users", query)
if err != nil {
return nil, err
}
return map[string]interface{}{
"referredBy": user.Data["referred_by"],
"referralCount": len(referrals),
"referrals": referrals,
}, nil
}
// Usage
stats, _ := getReferralStats(client, ctx, "user_123")
fmt.Printf("Total referrals: %v\n", stats["referralCount"])
def get_referral_stats(api_key, user_id):
headers = {'X-API-Key': api_key}
# Get the user who referred this user
params = {'populate': 'referred_by'}
user_response = requests.get(
f'{BASE_URL}/auth-collections/users/{user_id}',
headers=headers,
params=params
)
user = user_response.json()
# Get all users this user referred
params = {'data.referred_by': user_id}
referrals_response = requests.get(
f'{BASE_URL}/auth-collections/users',
headers=headers,
params=params
)
referrals = referrals_response.json()
return {
'referredBy': user.get('data', {}).get('referred_by'),
'referralCount': referrals.get('total', 0),
'referrals': referrals.get('data', [])
}
# Usage
stats = get_referral_stats('your-api-key', 'user_123')
print(f"Referred by: {stats['referredBy'].get('data', {}).get('username')}")
print(f"Total referrals: {stats['referralCount']}")
# Get user who referred this user
curl "https://api.cocobase.cc/auth-collections/users/user_123?populate=referred_by" \
-H "X-API-Key: your-api-key"
# Get all users this user referred
curl "https://api.cocobase.cc/auth-collections/users?data.referred_by=user_123" \
-H "X-API-Key: your-api-key"
Best Practices
1. Use Batch Queries with Population
1. Use Batch Queries with Population
Population uses optimized batch queries to avoid N+1 problems.
// ✓ Good: Single query with populate
const users = await db.listDocuments('users', {
populate: ['followers_ids', 'following_ids']
});
// ✗ Bad: Multiple individual queries
for (const user of users) {
const follower = await db.getDocument('users', user.data.followers_ids[0]);
}
2. Only Populate What You Need
2. Only Populate What You Need
Avoid over-populating to reduce response size and improve performance.
// ✓ Good: Only populate what's needed
const users = await db.listDocuments('users', {
populate: ['referred_by']
});
// ✗ Bad: Populating unnecessary relationships
const users = await db.listDocuments('users', {
populate: ['followers_ids', 'following_ids', 'referred_by', 'friends_ids']
});
3. Keep Relationship Arrays Reasonable
3. Keep Relationship Arrays Reasonable
Don’t store thousands of IDs in a single array field.
// ✓ Good: Reasonable array size (< 1000 items)
followers_ids: ['user_1', 'user_2', ..., 'user_500']
// ✗ Bad: Massive arrays (> 10,000 items)
// Consider a separate junction collection for this
4. Use Filters with Population
4. Use Filters with Population
Combine filters and population for efficient queries.
// ✓ Good: Filter and populate together
const activeUsers = await db.listDocuments('users', {
filters: { status: 'active' },
populate: ['referred_by']
});
5. Cache Populated Results
5. Cache Populated Results
Cache frequently accessed relationships to reduce API calls.
const cache = new Map();
async function getUserWithRelationships(userId, populate) {
const cacheKey = `${userId}:${populate.join(',')}`;
if (cache.has(cacheKey)) {
return cache.get(cacheKey);
}
const data = await db.getDocument('users', userId, { populate });
cache.set(cacheKey, data);
return data;
}
Next Steps
CRUD Operations
Create and manage related documents
Query & Filtering
Filter documents by relationships
Real-time Updates
Watch relationship changes live
Authentication
Manage user relationships
