@occollective/recommendations
v1.3.1
Published
A lightweight, flexible recommendation engine for React applications. Define and manage product recommendations with custom display rules, priorities, and fallback options.
Readme
Recommendation Engine SDK
A lightweight, flexible recommendation engine for React applications. Define and manage product recommendations with custom display rules, priorities, and fallback options.
Features
- 🚀 Lightweight and performant
- 🎯 Component-based targeting
- 🔄 Priority-based recommendations
- ⚡️ Built-in caching
- 🎨 Flexible display conditions
- 📦 Fallback support
- 🛡️ TypeScript support
Installation
npm install @occollective/recommendationsQuick Start
import { engine, useRecommendations } from '@occollective/recommendations';
// 1. Define your recommendations
engine.define(
'holiday-sale',
[
{ id: '1', name: 'Holiday Bundle', price: 99.99 },
{ id: '2', name: 'Gift Set', price: 49.99 },
],
() => true,
{
component: 'product-slider',
}
);
// 2. Use in your components
function ProductSlider() {
const { recommendations, loading } = useRecommendations('product-slider');
if (loading) return <div>Loading...</div>;
if (!recommendations) return null;
return (
<div>
{recommendations.map((product) => (
<div key={product.id}>
{product.name} - ${product.price}
</div>
))}
</div>
);
}Advanced Configuration
Custom Engine Instance
Create a configured engine instance for more control:
import {
createEngine,
RecommendationProvider,
} from '@occollective/recommendations';
const engine = createEngine({
cache: {
ttl: 5 * 60 * 1000, // 5 minutes
maxSize: 1000, // Maximum cache entries
},
});
function App() {
return (
<RecommendationProvider engine={engine}>
<YourApp />
</RecommendationProvider>
);
}Priority-Based Recommendations
Define multiple recommendations for the same component with different priorities:
// High priority - Flash Sale
engine.define(
'flash-sale',
flashSaleProducts,
(context) => isFlashSaleActive(),
{
component: 'home-recommendations',
priority: 3,
}
);
// Medium priority - Personalized
engine.define(
'personalized',
personalizedProducts,
(context) => hasUserPreferences(context),
{
component: 'home-recommendations',
priority: 2,
}
);
// Low priority - Default
engine.define('default', defaultProducts, () => true, {
component: 'home-recommendations',
priority: 1,
});Fallback Support
Add fallback options for when primary recommendations don't match:
engine.define(
'premium-products',
premiumProducts,
(context) => isPremiumUser(context),
{
component: 'product-recommendations',
fallbackProducts: standardProducts, // Show these if user isn't premium
priority: 2,
}
);Context-Aware Conditions
Pass context to your display conditions:
engine.define(
'geo-specific',
usProducts,
(context) => {
const userRegion = (context as { region?: string })?.region;
return userRegion === 'US';
},
{
component: 'regional-offers',
}
);
// In your component:
function RegionalOffers() {
const { recommendations } = useRecommendations('regional-offers', {
region: 'US',
});
// ...
}Performance Optimization
Caching
The engine includes built-in caching with configurable TTL and size limits:
const engine = createEngine({
cache: {
ttl: 5 * 60 * 1000, // 5 minutes
maxSize: 1000, // Maximum entries
},
});Efficient Conditions
Write performant display conditions:
// ❌ Bad: Expensive operation on every check
engine.define('expensive', products, async (context) => {
const data = await fetchLargeDataset();
return processData(data);
});
// ✅ Good: Cache expensive operations
const dataCache = new Map();
engine.define('optimized', products, async (context) => {
const cached = dataCache.get('key');
if (cached) return cached;
const result = await fetchLargeDataset();
dataCache.set('key', result);
return result;
});TypeScript Support
The package includes comprehensive TypeScript definitions:
import type {
Product,
RecommendationOptions,
} from '@occollective/recommendations';
interface MyProduct extends Product {
category: string;
inStock: boolean;
}
const options: RecommendationOptions = {
component: 'product-slider',
priority: 2,
fallbackProducts: defaultProducts,
};Error Handling
Use error boundaries for robust error handling:
import { ErrorBoundary } from 'react-error-boundary';
function RecommendationsErrorBoundary({ children }) {
return (
<ErrorBoundary
fallback={<DefaultRecommendations />}
onError={(error) => {
console.error('Recommendations failed:', error);
}}
>
{children}
</ErrorBoundary>
);
}Best Practices
- Component Organization: Group recommendations by component
- Priority Levels: Use consistent priority levels (1-3 recommended)
- Fallbacks: Always provide fallback options for critical components
- Performance: Cache expensive operations outside the display condition
- TypeScript: Utilize type definitions for better development experience
License
This project is licensed under the MIT License - see the LICENSE file for details.
