Skip to content

Commit

Permalink
calculating and updating the streak each day
Browse files Browse the repository at this point in the history
  • Loading branch information
WelldoneM committed Nov 5, 2024
1 parent d003808 commit 7f1067e
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 12 deletions.
32 changes: 20 additions & 12 deletions src/contexts/UserContext.jsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import LoadingCircle from '@components/common/LoadingCircle';
import { calculateProgress } from '@utils/calculateProgress';
import { signInWithGoogle } from '@utils/firebase/authUtils';
import { fetchUserProfile, updateUserProfile } from '@utils/firebase/createUserProfile';
import { getStreakData, updateStreakData } from '@utils/firebase/streakUtils';
import { auth } from '@utils/firebaseConfig';
import { getCompletedDates } from '@utils/taskCompletion';
import { onAuthStateChanged, signOut } from 'firebase/auth';
import { createContext, useContext, useEffect, useState } from 'react';

Expand All @@ -19,8 +19,6 @@ export const UserProvider = ({ children }) => {
const [completedDays, setCompletedDays] = useState([]);
const [streakCount, setStreakCount] = useState(0);

const today = new Date().toISOString().split('T')[0];

// handle Sign-In
const handleSignIn = async () => {
const userData = await signInWithGoogle();
Expand Down Expand Up @@ -64,7 +62,7 @@ export const UserProvider = ({ children }) => {
return () => unsubscribe();
}, []);

// Fetch streak data
// Fetch streak data and initialize completedDays and streakCount
const fetchStreakData = async (userId) => {
const { completedDays, streakCount } = await getStreakData(userId);
setCompletedDays(completedDays || []);
Expand All @@ -73,11 +71,14 @@ export const UserProvider = ({ children }) => {

// Calculate streak based on consecutive days
const calculateStreak = (days) => {
const sortedDates = days.sort((a, b) => new Date(b) - new Date(a));
let streak = 0;
for (let i = 0; i < sortedDates.length; i++) {
const dayDiff = (new Date(today) - new Date(sortedDates[i])) / (1000 * 60 * 60 * 24);
if (dayDiff === streak) {
if (!days.length) return 0;

const sortedDates = days.map((date) => new Date(date)).sort((a, b) => b - a);

let streak = 1;
for (let i = 1; i < sortedDates.length; i++) {
const diff = (sortedDates[i - 1] - sortedDates[i]) / (1000 * 60 * 60 * 24);
if (diff === 1) {
streak++;
} else {
break;
Expand All @@ -88,10 +89,10 @@ export const UserProvider = ({ children }) => {

// Check for progress on goals and tasks today
const checkDailyProgress = async (goals) => {
const { completedDates } = calculateProgress(goals);
const progressMadeToday = completedDates.includes(today);
const today = new Date().toISOString().split('T')[0];
const completedDates = getCompletedDates(goals);

if (progressMadeToday && !completedDays.includes(today)) {
if (completedDates.includes(today) && !completedDays.includes(today)) {
const updatedDays = [...completedDays, today];
const newStreakCount = calculateStreak(updatedDays);

Expand All @@ -112,6 +113,13 @@ export const UserProvider = ({ children }) => {
}
};

// Call `checkDailyProgress` once `user.goals` is loaded
useEffect(() => {
if (user && user.goals) {
checkDailyProgress(user.goals); // Call with `user.goals` once available
}
}, [user]);

return (
<UserContext.Provider
value={{
Expand Down
5 changes: 5 additions & 0 deletions src/hooks/useGoalsUpdater.js
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,12 @@ const useGoalsUpdater = () => {
console.error('Specified goal, microgoal, or task does not exist');
return;
}
// Toggle the task completion status
task.completed = !task.completed;

// Set the completion date when the task is completed, clear if uncompleted
task.completionDate = task.completed ? new Date().toISOString().split('T')[0] : null;
// Update the user profile with updated goals
await updateGoals(updatedGoals, 'Task completion status toggled successfully.');
};

Expand Down
30 changes: 30 additions & 0 deletions src/utils/taskCompletion.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
/**
* Get unique dates on which tasks have been completed
* @param {Array} goals - List of goal objects, each containing microgoals and tasks
* @returns {Array} - Unique dates when tasks were marked as completed
*/
export const getCompletedDates = (goals) => {
const completedDates = new Set();

// Check if goals is an array and iterate only if it exists
if (Array.isArray(goals)) {
goals.forEach((goal) => {
// Ensure microgoals is defined and an array
if (Array.isArray(goal.microgoals)) {
goal.microgoals.forEach((microGoal) => {
// Ensure tasks is defined and an array
if (Array.isArray(microGoal.tasks)) {
microGoal.tasks.forEach((task) => {
// Check for both task completion and valid completion date
if (task.completed && task.completionDate) {
completedDates.add(task.completionDate);
}
});
}
});
}
});
}

return Array.from(completedDates);
};

0 comments on commit 7f1067e

Please sign in to comment.