From f3261f94e6d5f0ed72fe994176ea20a715283be6 Mon Sep 17 00:00:00 2001 From: KONFeature Date: Wed, 6 Nov 2024 10:42:22 +0100 Subject: [PATCH] =?UTF-8?q?=E2=9C=A8=20Global=20stats=20endpoint?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- packages/ponder/src/api/stats.ts | 72 ++++++++++++++++++++++++++++++++ 1 file changed, 72 insertions(+) create mode 100644 packages/ponder/src/api/stats.ts diff --git a/packages/ponder/src/api/stats.ts b/packages/ponder/src/api/stats.ts new file mode 100644 index 0000000..e856c01 --- /dev/null +++ b/packages/ponder/src/api/stats.ts @@ -0,0 +1,72 @@ +import { ponder } from "@/generated"; +import { count, countDistinct, eq, gte } from "@ponder/core"; + +/** + * Get the overall system stats + */ +ponder.get("/stats/overall", async (ctx) => { + // Get all the product ids for this admin + const { InteractionEvent, ProductInteractionContract, Product } = + ctx.tables; + + // Get the total nbr of user who performed an interaction + const totalInteractions = await ctx.db + .select({ + count: countDistinct(InteractionEvent.user), + }) + .from(InteractionEvent); + const totalPerType = await ctx.db + .select({ + name: InteractionEvent.type, + count: countDistinct(InteractionEvent.user), + }) + .from(InteractionEvent) + .groupBy(InteractionEvent.type); + const totalPerProduct = await ctx.db + .select({ + name: Product.name, + count: countDistinct(InteractionEvent.user), + }) + .from(InteractionEvent) + .innerJoin( + ProductInteractionContract, + eq(InteractionEvent.interactionId, ProductInteractionContract.id) + ) + .innerJoin( + Product, + eq(ProductInteractionContract.productId, Product.id) + ) + .groupBy(Product.id); + + // Get the min time for the WAU and DAU + const wauMinTime = BigInt(Date.now() - 7 * 24 * 60 * 60 * 1000) / 1000n; + const dauMinTime = BigInt(Date.now() - 30 * 60 * 60 * 1000) / 1000n; + + // Get the WAU and DAU + const wauInteractions = await ctx.db + .select({ + count: countDistinct(InteractionEvent.user), + }) + .from(InteractionEvent) + .where(gte(InteractionEvent.timestamp, wauMinTime)); + const dauInteractions = await ctx.db + .select({ + count: countDistinct(InteractionEvent.user), + }) + .from(InteractionEvent) + .where(gte(InteractionEvent.timestamp, dauMinTime)); + + // Total number of product registered + const totalProducts = await ctx.db.select({ count: count() }).from(Product); + + return ctx.json({ + interactions: { + total: totalInteractions[0]?.count, + wau: wauInteractions[0]?.count, + dau: dauInteractions[0]?.count, + totalPerType, + totalPerProduct, + }, + products: totalProducts[0]?.count, + }); +});