mirror of
https://github.com/solidtime-io/solidtime.git
synced 2026-10-15 09:13:16 +01:00
Add goals feature for personal goals with filters
This commit is contained in:
126
resources/js/utils/useGoals.ts
Normal file
126
resources/js/utils/useGoals.ts
Normal file
@@ -0,0 +1,126 @@
|
||||
import { defineStore } from 'pinia';
|
||||
import { api } from '@/packages/api/src';
|
||||
import type { CreateGoalBody, Goal, UpdateGoalBody } from '@/packages/api/src';
|
||||
import { getCurrentOrganizationId } from '@/utils/useUser';
|
||||
import { useNotificationsStore } from '@/utils/notification';
|
||||
import { useQueryClient } from '@tanstack/vue-query';
|
||||
import { isApiValidationError } from '@/utils/apiValidation';
|
||||
|
||||
export const useGoalsStore = defineStore('goals', () => {
|
||||
const { addNotification, handleApiRequestNotifications } = useNotificationsStore();
|
||||
const queryClient = useQueryClient();
|
||||
|
||||
/**
|
||||
* Like handleApiRequestNotifications, but a 422 response is rethrown as the AxiosError
|
||||
* without a toast, so that the goal form can show the errors next to its fields.
|
||||
*/
|
||||
async function handleGoalFormRequest<T>(
|
||||
apiRequest: () => Promise<T>,
|
||||
successMessage: string,
|
||||
errorMessage: string
|
||||
): Promise<T | undefined> {
|
||||
let validationError: unknown = null;
|
||||
const response = await handleApiRequestNotifications(
|
||||
async () => {
|
||||
try {
|
||||
return await apiRequest();
|
||||
} catch (error) {
|
||||
if (isApiValidationError(error)) {
|
||||
validationError = error;
|
||||
return undefined;
|
||||
}
|
||||
throw error;
|
||||
}
|
||||
},
|
||||
undefined,
|
||||
errorMessage
|
||||
);
|
||||
if (validationError !== null) {
|
||||
throw validationError;
|
||||
}
|
||||
addNotification('success', successMessage);
|
||||
return response;
|
||||
}
|
||||
|
||||
async function createGoal(goalBody: CreateGoalBody): Promise<Goal | undefined> {
|
||||
const organization = getCurrentOrganizationId();
|
||||
if (organization) {
|
||||
const response = await handleGoalFormRequest(
|
||||
() =>
|
||||
api.createGoal(goalBody, {
|
||||
params: {
|
||||
organization: organization,
|
||||
},
|
||||
}),
|
||||
'Goal created successfully',
|
||||
'Failed to create goal'
|
||||
);
|
||||
queryClient.invalidateQueries({ queryKey: ['goals'] });
|
||||
return response?.data;
|
||||
}
|
||||
}
|
||||
|
||||
async function updateGoal(goalId: string, goalBody: UpdateGoalBody): Promise<Goal | undefined> {
|
||||
const organization = getCurrentOrganizationId();
|
||||
if (organization) {
|
||||
const response = await handleGoalFormRequest(
|
||||
() =>
|
||||
api.updateGoal(goalBody, {
|
||||
params: {
|
||||
organization: organization,
|
||||
goal: goalId,
|
||||
},
|
||||
}),
|
||||
'Goal updated successfully',
|
||||
'Failed to update goal'
|
||||
);
|
||||
queryClient.invalidateQueries({ queryKey: ['goals'] });
|
||||
return response?.data;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Archived goals are hidden from the goal list by default, archiving is not deleting.
|
||||
*/
|
||||
async function setGoalArchived(goalId: string, isArchived: boolean): Promise<Goal | undefined> {
|
||||
const organization = getCurrentOrganizationId();
|
||||
if (organization) {
|
||||
const response = await handleApiRequestNotifications(
|
||||
() =>
|
||||
api.updateGoal(
|
||||
{ is_archived: isArchived },
|
||||
{
|
||||
params: {
|
||||
organization: organization,
|
||||
goal: goalId,
|
||||
},
|
||||
}
|
||||
),
|
||||
isArchived ? 'Goal archived successfully' : 'Goal unarchived successfully',
|
||||
isArchived ? 'Failed to archive goal' : 'Failed to unarchive goal'
|
||||
);
|
||||
queryClient.invalidateQueries({ queryKey: ['goals'] });
|
||||
return response?.data;
|
||||
}
|
||||
}
|
||||
|
||||
async function deleteGoal(goalId: string) {
|
||||
const organization = getCurrentOrganizationId();
|
||||
if (organization) {
|
||||
await handleApiRequestNotifications(
|
||||
() =>
|
||||
api.deleteGoal(undefined, {
|
||||
params: {
|
||||
organization: organization,
|
||||
goal: goalId,
|
||||
},
|
||||
}),
|
||||
'Goal deleted successfully',
|
||||
'Failed to delete goal'
|
||||
);
|
||||
queryClient.invalidateQueries({ queryKey: ['goals'] });
|
||||
}
|
||||
}
|
||||
|
||||
return { createGoal, updateGoal, setGoalArchived, deleteGoal };
|
||||
});
|
||||
Reference in New Issue
Block a user