Show RFM as customer snapshot
All checks were successful
Build and Deploy / build-and-deploy (push) Successful in 49s

This commit is contained in:
Cauê Faleiros
2026-06-15 12:36:04 -03:00
parent 76b1c545f1
commit 1956e62697
2 changed files with 17 additions and 14 deletions

View File

@@ -292,7 +292,13 @@ const getRfmAnalytics = async (range = {}) => {
`, historyParams) `, historyParams)
]); ]);
const historyClients = buildRfmClients(historyResult.rows.map(row => ({ const periodByPhone = new Map(periodResult.rows.map(row => [row.phone, {
monetary: toNumber(row.monetary),
frequency: toNumber(row.frequency),
quantityPurchased: toNumber(row.quantity_purchased)
}]));
const clients = buildRfmClients(historyResult.rows.map(row => ({
name: row.name, name: row.name,
phone: row.phone, phone: row.phone,
monetary: toNumber(row.monetary), monetary: toNumber(row.monetary),
@@ -300,22 +306,16 @@ const getRfmAnalytics = async (range = {}) => {
quantityPurchased: toNumber(row.quantity_purchased), quantityPurchased: toNumber(row.quantity_purchased),
lastPurchaseDate: row.last_purchase_date, lastPurchaseDate: row.last_purchase_date,
recencyDays: toNumber(row.recency_days) recencyDays: toNumber(row.recency_days)
}))); }))).map(client => {
const rfmByPhone = new Map(historyClients.map(client => [client.phone, client])); const periodClient = periodByPhone.get(client.phone);
const clients = periodResult.rows.map(row => {
const rfmClient = rfmByPhone.get(row.phone);
return { return {
...rfmClient, ...client,
name: row.name, monetary: periodClient?.monetary || 0,
phone: row.phone, frequency: periodClient?.frequency || 0,
monetary: toNumber(row.monetary), quantityPurchased: periodClient?.quantityPurchased || 0
frequency: toNumber(row.frequency),
quantityPurchased: toNumber(row.quantity_purchased),
lastPurchaseDate: row.last_purchase_date
}; };
}).filter(client => client.segmentKey).sort((a, b) => { }).sort((a, b) => {
if (b.recencyScore !== a.recencyScore) return b.recencyScore - a.recencyScore; if (b.recencyScore !== a.recencyScore) return b.recencyScore - a.recencyScore;
if (b.valueScore !== a.valueScore) return b.valueScore - a.valueScore; if (b.valueScore !== a.valueScore) return b.valueScore - a.valueScore;
return b.monetary - a.monetary; return b.monetary - a.monetary;

View File

@@ -256,6 +256,9 @@ test('getRfmAnalytics calculates recency against selected range end date', async
assert.equal(yesterday.clients[0].recencyDays, 0); assert.equal(yesterday.clients[0].recencyDays, 0);
assert.equal(yesterday.clients[0].frequency, 1); assert.equal(yesterday.clients[0].frequency, 1);
assert.equal(yesterday.clients[0].monetary, 100); assert.equal(yesterday.clients[0].monetary, 100);
assert.equal(yesterday.clients.length, 3);
assert.ok(yesterday.clients.some(client => client.recencyScore === 1));
assert.ok(yesterday.clients.some(client => client.phone === '2' && client.monetary === 0 && client.frequency === 0));
} finally { } finally {
pool.query = originalQuery; pool.query = originalQuery;
} }