Cache Updated

This commit is contained in:
Sharon Dcruz 2025-09-23 12:46:33 +05:30
parent 7438431c11
commit 1896b3fb44

View File

@ -5,6 +5,7 @@ import * as admin from "firebase-admin";
const app = getAdmin();
const logger = getLogger();
const kTrainerRole = "Trainer";
const CACHE_FOLDER = "gym_member_cache";
interface MembershipData {
id?: string;
@ -44,6 +45,183 @@ interface PersonalTrainerAssign {
gymId: string;
}
interface MinimalCacheEntry {
membershipId: string;
userId: string;
status: string;
displayName: string;
email?: string | null;
phoneNumber?: string | null;
alternateContact?: string | null;
renewalDate?: string | null;
expirationDate?: string | null;
createdAt?: string | null;
daysUntilExpiry?: number | null;
hasPersonalTraining: boolean;
hasPartialPayment: boolean;
remainingAmount: number;
subscriptionId?: string | null;
lastUpdated: string;
}
interface MinimalJsonCacheData {
gymId: string;
members: MinimalCacheEntry[];
totalMembers: number;
lastUpdated: string;
cacheVersion: string;
}
async function updateCacheForMembership(gymId: string, membershipId: string): Promise<void> {
try {
const fileName = `${CACHE_FOLDER}/${gymId}.json`;
const file = app.storage().bucket().file(fileName);
let existingData: MinimalJsonCacheData | null = null;
try {
const [fileBuffer] = await file.download();
existingData = JSON.parse(fileBuffer.toString());
} catch (error) {
logger.warn(`Could not load existing cache for gym ${gymId}, skipping cache update: ${error}`);
return;
}
if (!existingData || !existingData.members) {
logger.warn(`Invalid cache data for gym ${gymId}, skipping cache update`);
return;
}
const membershipDoc = await app
.firestore()
.collection("memberships")
.doc(membershipId)
.get();
if (!membershipDoc.exists) {
logger.warn(`Membership ${membershipId} not found, skipping cache update`);
return;
}
const membershipData = membershipDoc.data();
const updatedEntry = await generateMinimalCacheEntry(
membershipData!.userId,
membershipId,
membershipData!,
gymId
);
const memberIndex = existingData.members.findIndex(
member => member.membershipId === membershipId
);
if (memberIndex >= 0) {
existingData.members[memberIndex] = updatedEntry;
} else {
existingData.members.push(updatedEntry);
}
existingData.lastUpdated = new Date().toISOString();
existingData.totalMembers = existingData.members.length;
await file.save(JSON.stringify(existingData, null, 2), {
metadata: {
contentType: "application/json",
metadata: {
gymId: gymId,
totalMembers: existingData.totalMembers.toString(),
generatedAt: existingData.lastUpdated,
cacheVersion: existingData.cacheVersion,
},
},
});
logger.info(`Cache updated for membership ${membershipId} in gym ${gymId}`);
} catch (error) {
logger.error(`Error updating cache for membership ${membershipId}:`, error);
}
}
async function generateMinimalCacheEntry(
userId: string,
membershipId: string,
membershipData: any,
gymId: string
): Promise<MinimalCacheEntry> {
try {
let firstName = "";
let lastName = "";
let email = "";
let phoneNumber = "";
let alternateContact = "";
try {
const clientFieldsSnapshot = await app
.firestore()
.collection("client_profiles")
.where("uid", "==", userId)
.get();
if (!clientFieldsSnapshot.empty) {
const fieldDoc = clientFieldsSnapshot.docs[0];
const fieldData = fieldDoc.data();
const fields = fieldData.fields || {};
firstName = fields["first-name"] || fieldData["first-name"] || "";
lastName = fields["last-name"] || fieldData["last-name"] || "";
email = fields["email"] || fieldData["email"] || "";
phoneNumber = fields["phone-number"] || fieldData["phone-number"] || "";
alternateContact =
fields["alternate-contact"] || fieldData["alternate-contact"] || "";
}
} catch (error) {
logger.error(`Error getting fields for user ${userId}:`, error);
}
const daysUntilExpiry = membershipData.daysUntilExpiry || null;
const displayName =
firstName.length === 0
? "Unknown"
: lastName.length === 0
? firstName
: `${firstName} ${lastName}`;
const isPartial = membershipData.isPartialPayment === true;
const remaining = membershipData.remainingAmount || 0;
const hasPartialPayment = isPartial && remaining > 0;
const minimalEntry: MinimalCacheEntry = {
membershipId,
userId,
status: membershipData.status || "N/A",
displayName,
email: email || null,
phoneNumber: phoneNumber || null,
alternateContact: alternateContact || null,
renewalDate: null,
expirationDate: membershipData.expirationDate
? membershipData.expirationDate.toDate().toISOString()
: null,
createdAt: membershipData.createdAt
? membershipData.createdAt.toDate().toISOString()
: null,
daysUntilExpiry,
hasPersonalTraining:
membershipData.subscription?.hasPersonalTraining === true,
hasPartialPayment,
remainingAmount: remaining,
subscriptionId: membershipData.subscriptionId || null,
lastUpdated: new Date().toISOString(),
};
return minimalEntry;
} catch (error) {
logger.error("Error generating minimal cache entry:", error);
throw error;
}
}
export const checkExpiredMemberships = onSchedule(
{
schedule: "0 8,14,20 * * *",
@ -150,6 +328,7 @@ async function findExpiredMembershipsWithoutExpiryDate(): Promise<
throw error;
}
}
async function updateExpiryDateForExpiredMembership(
membershipId: string,
membershipData: MembershipData
@ -184,6 +363,8 @@ async function updateExpiryDateForExpiredMembership(
updatedAt: admin.firestore.FieldValue.serverTimestamp(),
});
await updateCacheForMembership(membershipData.gymId, membershipId);
logger.info(
`Updated expiry date for expired membership ${membershipId}: ${expiryDate.toISOString()}`
);
@ -513,6 +694,8 @@ async function updateDaysUntilExpiryForAllMemberships(): Promise<void> {
.doc(doc.id)
.update(updateData);
await updateCacheForMembership(data.gymId, doc.id);
logger.info(
`Updated membership ${doc.id} with daysUntilExpiry: ${daysUntilExpiry}`
);
@ -665,6 +848,8 @@ async function processExpiredMembership(
});
}
await updateCacheForMembership(membershipData.gymId, membershipId);
logger.info(`Marked membership ${membershipId} as EXPIRED`);
await sendPlanExpiredNotification(membershipId, membershipData);
@ -697,6 +882,8 @@ async function processExpiringMembership(
expirationDate: admin.firestore.Timestamp.fromDate(expiryDate),
updatedAt: admin.firestore.FieldValue.serverTimestamp(),
});
await updateCacheForMembership(membershipData.gymId, membershipId);
}
await sendPlanExpiringNotification(membershipId, membershipData);
@ -1067,4 +1254,4 @@ async function getGymName(gymId: string): Promise<string> {
logger.error(`Error getting gym name for gym ${gymId}:`, error);
return "Unknown Gym";
}
}
}