Files
Krow-workspace/apps/web/src/services/workforceService.ts

438 lines
13 KiB
TypeScript

import type { Staff, User, Event } from "../features/workforce/type";
/**
* Mock Workforce Service
* Provides placeholder data for UI development
* Replace with actual API calls when backend is ready
*/
const mockUsers: Record<string, User> = {
admin: {
id: "admin-001",
email: "admin@krow.com",
role: "admin",
user_role: "admin",
name: "Admin User",
company_name: "Krow Workforce",
},
vendor: {
id: "vendor-001",
email: "vendor@staffagency.com",
role: "vendor",
user_role: "vendor",
name: "Vendor User",
company_name: "Staff Agency Pro",
},
client: {
id: "client-001",
email: "client@eventco.com",
role: "client",
user_role: "client",
name: "Client User",
company_name: "Event Co.",
},
operator: {
id: "operator-001",
email: "operator@krow.com",
role: "operator",
user_role: "operator",
name: "Operator User",
company_name: "Krow Workforce",
},
};
const mockStaff = [
{
id: "staff-001",
employee_name: "Sarah Johnson",
position: "Event Coordinator",
photo: "https://i.pravatar.cc/150?u=staff-001",
photo_url: "https://i.pravatar.cc/150?u=staff-001",
profile_type: "Senior",
email: "sarah.johnson@example.com",
contact_number: "+1 (555) 123-4567",
status: "Active",
skills: ["Event Management", "Customer Service", "Coordination"],
department: "Events",
hub_location: "New York",
averageRating: 4.8,
reliability_score: 95,
shift_coverage_percentage: 98,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 1).toISOString(),
employment_type: "Contract",
manager: "John Smith",
cancellation_count: 0,
no_show_count: 0,
total_shifts: 145,
},
{
id: "staff-002",
employee_name: "Michael Chen",
position: "Logistics Manager",
photo: "https://i.pravatar.cc/150?u=staff-002",
photo_url: "https://i.pravatar.cc/150?u=staff-002",
profile_type: "Intermediate",
email: "michael.chen@example.com",
contact_number: "+1 (555) 234-5678",
status: "Active",
skills: ["Logistics", "Operations", "Planning"],
department: "Operations",
hub_location: "Los Angeles",
averageRating: 4.6,
reliability_score: 88,
shift_coverage_percentage: 85,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 3).toISOString(),
employment_type: "Full-time",
manager: "Jane Williams",
cancellation_count: 2,
no_show_count: 1,
total_shifts: 156,
},
{
id: "staff-003",
employee_name: "Emma Rodriguez",
position: "Customer Service Rep",
photo: "https://i.pravatar.cc/150?u=staff-003",
photo_url: "https://i.pravatar.cc/150?u=staff-003",
profile_type: "Junior",
email: "emma.rodriguez@example.com",
contact_number: "+1 (555) 345-6789",
status: "Pending",
skills: ["Customer Service", "Communication"],
department: "Support",
hub_location: "Chicago",
averageRating: 4.3,
reliability_score: 72,
shift_coverage_percentage: 65,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 10).toISOString(),
employment_type: "Part-time",
manager: "Robert Brown",
cancellation_count: 5,
no_show_count: 3,
total_shifts: 89,
},
{
id: "staff-004",
employee_name: "James Wilson",
position: "Security Officer",
photo: "https://i.pravatar.cc/150?u=staff-004",
photo_url: "https://i.pravatar.cc/150?u=staff-004",
profile_type: "Senior",
email: "james.wilson@example.com",
contact_number: "+1 (555) 456-7890",
status: "Active",
skills: ["Security", "Safety"],
department: "Security",
hub_location: "Miami",
averageRating: 4.9,
reliability_score: 99,
shift_coverage_percentage: 100,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 2).toISOString(),
employment_type: "Full-time",
manager: "Patricia Davis",
cancellation_count: 0,
no_show_count: 0,
total_shifts: 198,
},
{
id: "staff-005",
employee_name: "Lisa Anderson",
position: "HR Specialist",
photo: "https://i.pravatar.cc/150?u=staff-005",
photo_url: "https://i.pravatar.cc/150?u=staff-005",
profile_type: "Intermediate",
email: "lisa.anderson@example.com",
contact_number: "+1 (555) 567-8901",
status: "Suspended",
skills: ["HR", "Recruitment"],
department: "Human Resources",
hub_location: "New York",
averageRating: 4.5,
reliability_score: 91,
shift_coverage_percentage: 92,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 30).toISOString(),
employment_type: "Full-time",
manager: "John Smith",
cancellation_count: 1,
no_show_count: 0,
total_shifts: 167,
},
{
id: "staff-006",
employee_name: "David Martinez",
position: "Data Analyst",
photo: "https://i.pravatar.cc/150?u=staff-006",
photo_url: "https://i.pravatar.cc/150?u=staff-006",
profile_type: "Senior",
email: "david.martinez@example.com",
contact_number: "+1 (555) 678-9012",
status: "Active",
skills: ["Data Analysis", "Reporting", "SQL"],
department: "Analytics",
hub_location: "San Francisco",
averageRating: 4.7,
reliability_score: 93,
shift_coverage_percentage: 87,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 5).toISOString(),
employment_type: "Contract",
manager: "Michael Thompson",
cancellation_count: 1,
no_show_count: 1,
total_shifts: 134,
},
{
id: "staff-007",
employee_name: "Jessica Lee",
position: "Project Manager",
photo: "https://i.pravatar.cc/150?u=staff-007",
photo_url: "https://i.pravatar.cc/150?u=staff-007",
profile_type: "Senior",
email: "jessica.lee@example.com",
contact_number: "+1 (555) 789-0123",
status: "Active",
skills: ["Project Management", "Agile"],
department: "Projects",
hub_location: "Boston",
averageRating: 4.4,
reliability_score: 85,
shift_coverage_percentage: 79,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 7).toISOString(),
employment_type: "Full-time",
manager: "Sarah Johnson",
cancellation_count: 3,
no_show_count: 1,
total_shifts: 142,
},
{
id: "staff-008",
employee_name: "Kevin Thompson",
position: "Business Analyst",
photo: "https://i.pravatar.cc/150?u=staff-008",
photo_url: "https://i.pravatar.cc/150?u=staff-008",
profile_type: "Intermediate",
email: "kevin.thompson@example.com",
contact_number: "+1 (555) 890-1234",
status: "Pending",
skills: ["Business Analysis", "Strategy"],
department: "Strategy",
hub_location: "Austin",
averageRating: 4.2,
reliability_score: 68,
shift_coverage_percentage: 72,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 14).toISOString(),
employment_type: "Part-time",
manager: "Robert Brown",
cancellation_count: 6,
no_show_count: 2,
total_shifts: 95,
},
{
id: "staff-009",
employee_name: "Nicole White",
position: "Marketing Manager",
photo: "https://i.pravatar.cc/150?u=staff-009",
photo_url: "https://i.pravatar.cc/150?u=staff-009",
profile_type: "Senior",
email: "nicole.white@example.com",
contact_number: "+1 (555) 901-2345",
status: "Active",
skills: ["Marketing", "Branding"],
department: "Marketing",
hub_location: "Seattle",
averageRating: 4.6,
reliability_score: 89,
shift_coverage_percentage: 86,
vendor_id: "vendor-001",
vendor_name: "Staff Agency Pro",
created_by: "vendor@staffagency.com",
created_date: new Date().toISOString(),
last_active: new Date(Date.now() - 1000 * 60 * 60 * 24 * 4).toISOString(),
employment_type: "Full-time",
manager: "Patricia Davis",
cancellation_count: 2,
no_show_count: 0,
total_shifts: 178,
},
] as unknown as Staff[];
const mockEvents: Event[] = [
{
id: "event-001",
business_name: "Event Co.",
client_email: "client@eventco.com",
created_by: "client@eventco.com",
assigned_staff: [
{ staff_id: "staff-001" },
{ staff_id: "staff-004" },
],
},
{
id: "event-002",
business_name: "Event Co.",
client_email: "client@eventco.com",
created_by: "client@eventco.com",
assigned_staff: [
{ staff_id: "staff-002" },
{ staff_id: "staff-009" },
],
},
];
/**
* Simulates API delay for realistic behavior
*/
const delay = (ms: number = 500) =>
new Promise((resolve) => setTimeout(resolve, ms));
/**
* Workforce Service - Mock implementation
*/
export const workforceService = {
auth: {
/**
* Get current user (mocked)
* In production, this would verify Firebase auth session
*/
me: async (): Promise<User> => {
await delay(800);
// Return a random user for demonstration
const users = Object.values(mockUsers);
return users[Math.floor(Math.random() * users.length)];
},
/**
* Sign out user (mocked)
*/
logout: async (): Promise<void> => {
await delay(300);
console.log("User logged out (mock)");
},
},
entities: {
Staff: {
/**
* List all staff members
* @param sortBy - Sort field (e.g., '-created_date' for descending)
*/
list: async (sortBy?: string): Promise<Staff[]> => {
await delay(1200);
const staffList = [...mockStaff];
// Simple sorting logic
if (sortBy === "-created_date") {
staffList.sort(
(a, b) =>
new Date(b.created_date || 0).getTime() -
new Date(a.created_date || 0).getTime()
);
} else if (sortBy === "created_date") {
staffList.sort(
(a, b) =>
new Date(a.created_date || 0).getTime() -
new Date(b.created_date || 0).getTime()
);
}
return staffList;
},
/**
* Get single staff member by ID
*/
get: async (id: string): Promise<Staff | null> => {
await delay(600);
return mockStaff.find((s) => s.id === id) || null;
},
/**
* Create new staff member
*/
create: async (staff: Partial<Staff>): Promise<Staff> => {
await delay(1000);
const newStaff: Staff = {
...staff,
id: `staff-${Date.now()}`,
created_date: new Date().toISOString(),
} as Staff;
mockStaff.push(newStaff);
return newStaff;
},
/**
* Update staff member
*/
update: async (id: string, updates: Partial<Staff>): Promise<Staff> => {
await delay(800);
const index = mockStaff.findIndex((s) => s.id === id);
if (index === -1) throw new Error("Staff not found");
mockStaff[index] = { ...mockStaff[index], ...updates };
return mockStaff[index];
},
/**
* Delete staff member
*/
delete: async (id: string): Promise<void> => {
await delay(600);
const index = mockStaff.findIndex((s) => s.id === id);
if (index === -1) throw new Error("Staff not found");
mockStaff.splice(index, 1);
},
},
Event: {
/**
* List all events
*/
list: async (): Promise<Event[]> => {
await delay(1000);
return [...mockEvents];
},
/**
* Get single event by ID
*/
get: async (id: string): Promise<Event | null> => {
await delay(600);
return mockEvents.find((e) => e.id === id) || null;
},
},
},
};
export default workforceService;