193 lines
5.6 KiB
Dart
193 lines
5.6 KiB
Dart
import 'package:get/get.dart';
|
|
import 'package:marco/helpers/services/app_logger.dart';
|
|
import 'package:marco/helpers/services/api_service.dart';
|
|
import 'package:marco/model/attendance_model.dart';
|
|
import 'package:marco/model/project_model.dart';
|
|
import 'package:marco/model/employee_model.dart';
|
|
import 'package:marco/model/employees/employee_details_model.dart';
|
|
import 'package:marco/controller/project_controller.dart';
|
|
|
|
class EmployeesScreenController extends GetxController {
|
|
List<AttendanceModel> attendances = [];
|
|
List<ProjectModel> projects = [];
|
|
String? selectedProjectId;
|
|
List<EmployeeDetailsModel> employeeDetails = [];
|
|
RxBool isAllEmployeeSelected = false.obs;
|
|
RxList<EmployeeModel> employees = <EmployeeModel>[].obs;
|
|
|
|
RxBool isLoading = false.obs;
|
|
RxMap<String, RxBool> uploadingStates = <String, RxBool>{}.obs;
|
|
Rxn<EmployeeDetailsModel> selectedEmployeeDetails = Rxn<EmployeeDetailsModel>();
|
|
RxBool isLoadingEmployeeDetails = false.obs;
|
|
|
|
@override
|
|
void onInit() {
|
|
super.onInit();
|
|
fetchAllProjects();
|
|
|
|
final projectId = Get.find<ProjectController>().selectedProject?.id;
|
|
|
|
if (projectId != null) {
|
|
selectedProjectId = projectId;
|
|
fetchEmployeesByProject(projectId);
|
|
} else if (isAllEmployeeSelected.value) {
|
|
fetchAllEmployees();
|
|
} else {
|
|
clearEmployees();
|
|
}
|
|
}
|
|
|
|
Future<void> fetchAllProjects() async {
|
|
isLoading.value = true;
|
|
|
|
await _handleApiCall(
|
|
ApiService.getProjects,
|
|
onSuccess: (data) {
|
|
projects = data.map((json) => ProjectModel.fromJson(json)).toList();
|
|
logSafe(
|
|
"Projects fetched: ${projects.length} projects loaded.",
|
|
level: LogLevel.info,
|
|
);
|
|
},
|
|
onEmpty: () {
|
|
logSafe("No project data found or API call failed.", level: LogLevel.warning);
|
|
},
|
|
);
|
|
|
|
isLoading.value = false;
|
|
update();
|
|
}
|
|
|
|
void clearEmployees() {
|
|
employees.clear();
|
|
logSafe("Employees cleared", level: LogLevel.info);
|
|
update(['employee_screen_controller']);
|
|
}
|
|
|
|
Future<void> fetchAllEmployees() async {
|
|
isLoading.value = true;
|
|
|
|
await _handleApiCall(
|
|
ApiService.getAllEmployees,
|
|
onSuccess: (data) {
|
|
employees.assignAll(data.map((json) => EmployeeModel.fromJson(json)));
|
|
logSafe(
|
|
"All Employees fetched: ${employees.length} employees loaded.",
|
|
level: LogLevel.info,
|
|
);
|
|
},
|
|
onEmpty: () {
|
|
employees.clear();
|
|
logSafe("No Employee data found or API call failed.", level: LogLevel.warning);
|
|
},
|
|
);
|
|
|
|
isLoading.value = false;
|
|
update(['employee_screen_controller']);
|
|
}
|
|
|
|
Future<void> fetchEmployeesByProject(String? projectId) async {
|
|
if (projectId == null || projectId.isEmpty) {
|
|
logSafe("Project ID is required but was null or empty.", level: LogLevel.error);
|
|
return;
|
|
}
|
|
|
|
isLoading.value = true;
|
|
|
|
await _handleApiCall(
|
|
() => ApiService.getAllEmployeesByProject(projectId),
|
|
onSuccess: (data) {
|
|
employees.assignAll(data.map((json) => EmployeeModel.fromJson(json)));
|
|
|
|
for (var emp in employees) {
|
|
uploadingStates[emp.id] = false.obs;
|
|
}
|
|
|
|
logSafe(
|
|
"Employees fetched: ${employees.length} for project $projectId",
|
|
level: LogLevel.info,
|
|
|
|
);
|
|
},
|
|
onEmpty: () {
|
|
employees.clear();
|
|
logSafe("No employees found for project $projectId.", level: LogLevel.warning, );
|
|
},
|
|
onError: (e) {
|
|
logSafe("Error fetching employees for project $projectId", level: LogLevel.error, error: e, );
|
|
},
|
|
);
|
|
|
|
isLoading.value = false;
|
|
update(['employee_screen_controller']);
|
|
}
|
|
|
|
Future<void> fetchEmployeeDetails(String? employeeId) async {
|
|
if (employeeId == null || employeeId.isEmpty) return;
|
|
|
|
isLoadingEmployeeDetails.value = true;
|
|
|
|
await _handleSingleApiCall(
|
|
() => ApiService.getEmployeeDetails(employeeId),
|
|
onSuccess: (data) {
|
|
selectedEmployeeDetails.value = EmployeeDetailsModel.fromJson(data);
|
|
logSafe("Employee details loaded for $employeeId", level: LogLevel.info, );
|
|
},
|
|
onEmpty: () {
|
|
selectedEmployeeDetails.value = null;
|
|
logSafe("No employee details found for $employeeId", level: LogLevel.warning, );
|
|
},
|
|
onError: (e) {
|
|
selectedEmployeeDetails.value = null;
|
|
logSafe("Error fetching employee details for $employeeId", level: LogLevel.error, error: e, );
|
|
},
|
|
);
|
|
|
|
isLoadingEmployeeDetails.value = false;
|
|
}
|
|
|
|
Future<void> _handleApiCall(
|
|
Future<List<dynamic>?> Function() apiCall, {
|
|
required Function(List<dynamic>) onSuccess,
|
|
required Function() onEmpty,
|
|
Function(dynamic error)? onError,
|
|
}) async {
|
|
try {
|
|
final response = await apiCall();
|
|
if (response != null && response.isNotEmpty) {
|
|
onSuccess(response);
|
|
} else {
|
|
onEmpty();
|
|
}
|
|
} catch (e) {
|
|
if (onError != null) {
|
|
onError(e);
|
|
} else {
|
|
logSafe("API call error", level: LogLevel.error, error: e);
|
|
}
|
|
}
|
|
}
|
|
|
|
Future<void> _handleSingleApiCall(
|
|
Future<Map<String, dynamic>?> Function() apiCall, {
|
|
required Function(Map<String, dynamic>) onSuccess,
|
|
required Function() onEmpty,
|
|
Function(dynamic error)? onError,
|
|
}) async {
|
|
try {
|
|
final response = await apiCall();
|
|
if (response != null && response.isNotEmpty) {
|
|
onSuccess(response);
|
|
} else {
|
|
onEmpty();
|
|
}
|
|
} catch (e) {
|
|
if (onError != null) {
|
|
onError(e);
|
|
} else {
|
|
logSafe("API call error", level: LogLevel.error, error: e);
|
|
}
|
|
}
|
|
}
|
|
}
|