stats update
This commit is contained in:
parent
19f360e3f0
commit
addfb479b1
3 changed files with 115 additions and 7 deletions
|
@ -201,6 +201,7 @@ const EventCheckIn = () => {
|
||||||
const update = Update.getInstance();
|
const update = Update.getInstance();
|
||||||
const logger = SendLog.getInstance();
|
const logger = SendLog.getInstance();
|
||||||
const dataSync = DataSyncService.getInstance();
|
const dataSync = DataSyncService.getInstance();
|
||||||
|
const get = Get.getInstance();
|
||||||
|
|
||||||
const currentUser = auth.getCurrentUser();
|
const currentUser = auth.getCurrentUser();
|
||||||
if (!currentUser) {
|
if (!currentUser) {
|
||||||
|
@ -211,7 +212,6 @@ const EventCheckIn = () => {
|
||||||
const eventId = event.id;
|
const eventId = event.id;
|
||||||
|
|
||||||
// Check if user is already checked in
|
// Check if user is already checked in
|
||||||
const get = Get.getInstance();
|
|
||||||
const existingAttendees = await get.getList<EventAttendee>(
|
const existingAttendees = await get.getList<EventAttendee>(
|
||||||
Collections.EVENT_ATTENDEES,
|
Collections.EVENT_ATTENDEES,
|
||||||
1,
|
1,
|
||||||
|
@ -241,6 +241,32 @@ const EventCheckIn = () => {
|
||||||
await update.create(Collections.EVENT_ATTENDEES, attendeeData);
|
await update.create(Collections.EVENT_ATTENDEES, attendeeData);
|
||||||
|
|
||||||
console.log("Successfully created attendance record");
|
console.log("Successfully created attendance record");
|
||||||
|
|
||||||
|
// Update user's total points
|
||||||
|
// First, get all the user's attendance records to calculate total points
|
||||||
|
const userAttendance = await get.getList<EventAttendee>(
|
||||||
|
Collections.EVENT_ATTENDEES,
|
||||||
|
1,
|
||||||
|
1000,
|
||||||
|
`user="${userId}"`
|
||||||
|
);
|
||||||
|
|
||||||
|
// Calculate total points
|
||||||
|
let totalPoints = 0;
|
||||||
|
userAttendance.items.forEach(attendee => {
|
||||||
|
totalPoints += attendee.points_earned || 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
// Log the points update
|
||||||
|
console.log(`Updating user points to: ${totalPoints}`);
|
||||||
|
|
||||||
|
// Update the user record with the new total points
|
||||||
|
await update.updateFields(Collections.USERS, userId, {
|
||||||
|
points: totalPoints
|
||||||
|
});
|
||||||
|
|
||||||
|
// Sync the updated user data
|
||||||
|
await dataSync.syncCollection(Collections.USERS);
|
||||||
} catch (createError: any) {
|
} catch (createError: any) {
|
||||||
console.error("Error creating attendance record:", createError);
|
console.error("Error creating attendance record:", createError);
|
||||||
|
|
||||||
|
|
|
@ -5,6 +5,7 @@ import { Collections } from "../../../schemas/pocketbase/schema";
|
||||||
import type { Event, Log, User } from "../../../schemas/pocketbase";
|
import type { Event, Log, User } from "../../../schemas/pocketbase";
|
||||||
import { Get } from "../../../scripts/pocketbase/Get";
|
import { Get } from "../../../scripts/pocketbase/Get";
|
||||||
import type { EventAttendee } from "../../../schemas/pocketbase";
|
import type { EventAttendee } from "../../../schemas/pocketbase";
|
||||||
|
import { Update } from "../../../scripts/pocketbase/Update";
|
||||||
|
|
||||||
// Extended User interface with points property
|
// Extended User interface with points property
|
||||||
interface ExtendedUser extends User {
|
interface ExtendedUser extends User {
|
||||||
|
@ -16,6 +17,7 @@ export function Stats() {
|
||||||
const [eventsAttended, setEventsAttended] = useState(0);
|
const [eventsAttended, setEventsAttended] = useState(0);
|
||||||
const [loyaltyPoints, setLoyaltyPoints] = useState(0);
|
const [loyaltyPoints, setLoyaltyPoints] = useState(0);
|
||||||
const [pointsChange, setPointsChange] = useState("No activity");
|
const [pointsChange, setPointsChange] = useState("No activity");
|
||||||
|
const [quarterlyPoints, setQuarterlyPoints] = useState(0); // Points earned this quarter
|
||||||
const [membershipStatus, setMembershipStatus] = useState("Member");
|
const [membershipStatus, setMembershipStatus] = useState("Member");
|
||||||
const [memberSince, setMemberSince] = useState<string | null>(null);
|
const [memberSince, setMemberSince] = useState<string | null>(null);
|
||||||
const [upcomingEvents, setUpcomingEvents] = useState(0);
|
const [upcomingEvents, setUpcomingEvents] = useState(0);
|
||||||
|
@ -25,6 +27,26 @@ export function Stats() {
|
||||||
const [pointsEarned, setPointsEarned] = useState(0);
|
const [pointsEarned, setPointsEarned] = useState(0);
|
||||||
const [attendancePercentage, setAttendancePercentage] = useState(0);
|
const [attendancePercentage, setAttendancePercentage] = useState(0);
|
||||||
|
|
||||||
|
// Helper function to get the start date of the current quarter
|
||||||
|
const getCurrentQuarterStartDate = (): Date => {
|
||||||
|
const now = new Date();
|
||||||
|
const currentMonth = now.getMonth();
|
||||||
|
let quarterStartMonth = 0;
|
||||||
|
|
||||||
|
// Determine the start month of the current quarter
|
||||||
|
if (currentMonth >= 0 && currentMonth <= 2) {
|
||||||
|
quarterStartMonth = 0; // Q1: Jan-Mar
|
||||||
|
} else if (currentMonth >= 3 && currentMonth <= 5) {
|
||||||
|
quarterStartMonth = 3; // Q2: Apr-Jun
|
||||||
|
} else if (currentMonth >= 6 && currentMonth <= 8) {
|
||||||
|
quarterStartMonth = 6; // Q3: Jul-Sep
|
||||||
|
} else {
|
||||||
|
quarterStartMonth = 9; // Q4: Oct-Dec
|
||||||
|
}
|
||||||
|
|
||||||
|
return new Date(now.getFullYear(), quarterStartMonth, 1);
|
||||||
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const fetchStats = async () => {
|
const fetchStats = async () => {
|
||||||
try {
|
try {
|
||||||
|
@ -62,13 +84,69 @@ export function Stats() {
|
||||||
|
|
||||||
setEventsAttended(attendedEvents.totalItems);
|
setEventsAttended(attendedEvents.totalItems);
|
||||||
|
|
||||||
// Calculate total points earned
|
// Get user points - either from the user record or calculate from attendees
|
||||||
let totalPoints = 0;
|
let totalPoints = 0;
|
||||||
attendedEvents.items.forEach(attendee => {
|
|
||||||
totalPoints += attendee.points_earned || 0;
|
// Calculate quarterly points
|
||||||
});
|
const quarterStartDate = getCurrentQuarterStartDate();
|
||||||
|
let pointsThisQuarter = 0;
|
||||||
|
|
||||||
|
// If user has points field, use that for total points
|
||||||
|
if (currentUser && currentUser.points !== undefined) {
|
||||||
|
totalPoints = currentUser.points;
|
||||||
|
|
||||||
|
// Still need to calculate quarterly points from attendees
|
||||||
|
attendedEvents.items.forEach(attendee => {
|
||||||
|
const checkinDate = new Date(attendee.time_checked_in);
|
||||||
|
if (checkinDate >= quarterStartDate) {
|
||||||
|
pointsThisQuarter += attendee.points_earned || 0;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
// Calculate both total and quarterly points from attendees
|
||||||
|
attendedEvents.items.forEach(attendee => {
|
||||||
|
const points = attendee.points_earned || 0;
|
||||||
|
totalPoints += points;
|
||||||
|
|
||||||
|
const checkinDate = new Date(attendee.time_checked_in);
|
||||||
|
if (checkinDate >= quarterStartDate) {
|
||||||
|
pointsThisQuarter += points;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// Update the user record with calculated points if needed
|
||||||
|
if (currentUser) {
|
||||||
|
try {
|
||||||
|
const update = Update.getInstance();
|
||||||
|
await update.updateFields(Collections.USERS, currentUser.id, {
|
||||||
|
points: totalPoints
|
||||||
|
});
|
||||||
|
} catch (error) {
|
||||||
|
console.error("Error updating user points:", error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
setPointsEarned(totalPoints);
|
setPointsEarned(totalPoints);
|
||||||
|
setLoyaltyPoints(totalPoints);
|
||||||
|
setQuarterlyPoints(pointsThisQuarter);
|
||||||
|
|
||||||
|
// Get current quarter name
|
||||||
|
const now = new Date();
|
||||||
|
const currentMonth = now.getMonth();
|
||||||
|
let quarterName = "";
|
||||||
|
|
||||||
|
if (currentMonth >= 0 && currentMonth <= 2) {
|
||||||
|
quarterName = "Q1";
|
||||||
|
} else if (currentMonth >= 3 && currentMonth <= 5) {
|
||||||
|
quarterName = "Q2";
|
||||||
|
} else if (currentMonth >= 6 && currentMonth <= 8) {
|
||||||
|
quarterName = "Q3";
|
||||||
|
} else {
|
||||||
|
quarterName = "Q4";
|
||||||
|
}
|
||||||
|
|
||||||
|
setPointsChange(`${pointsThisQuarter} pts in ${quarterName}`);
|
||||||
|
|
||||||
// Get all events to calculate percentage
|
// Get all events to calculate percentage
|
||||||
const allEvents = await get.getList<Event>("events", 1, 1000);
|
const allEvents = await get.getList<Event>("events", 1, 1000);
|
||||||
|
@ -123,8 +201,11 @@ export function Stats() {
|
||||||
<div className="stat">
|
<div className="stat">
|
||||||
<div className="stat-title font-medium opacity-80">Loyalty Points</div>
|
<div className="stat-title font-medium opacity-80">Loyalty Points</div>
|
||||||
<div className="stat-value text-secondary">{loyaltyPoints}</div>
|
<div className="stat-value text-secondary">{loyaltyPoints}</div>
|
||||||
<div className="stat-desc flex items-center gap-2 mt-1">
|
<div className="stat-desc flex flex-col items-start gap-1 mt-1">
|
||||||
<div className="badge badge-secondary badge-sm">{pointsChange}</div>
|
<div className="flex items-center justify-between w-full">
|
||||||
|
<div className="badge badge-secondary badge-sm">{quarterlyPoints} pts this quarter</div>
|
||||||
|
<div className="text-xs opacity-70">Total points</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -31,6 +31,7 @@ export interface User extends BaseRecord {
|
||||||
major?: string;
|
major?: string;
|
||||||
zelle_information?: string;
|
zelle_information?: string;
|
||||||
last_login?: string;
|
last_login?: string;
|
||||||
|
points?: number; // Total points earned from events
|
||||||
notification_preferences?: string; // JSON string of notification settings
|
notification_preferences?: string; // JSON string of notification settings
|
||||||
display_preferences?: string; // JSON string of display settings (theme, font size, etc.)
|
display_preferences?: string; // JSON string of display settings (theme, font size, etc.)
|
||||||
accessibility_settings?: string; // JSON string of accessibility settings (color blind mode, reduced motion)
|
accessibility_settings?: string; // JSON string of accessibility settings (color blind mode, reduced motion)
|
||||||
|
|
Loading…
Reference in a new issue