block-employee-directory/EmployeeDirectory/Services/EmployeeService.swift
Matt Bruce 67b2163134 Merge branch 'develop' into requestBuilder
# Conflicts:
#	EmployeeDirectory/Protocols/EmployeeServiceProtocol.swift
#	EmployeeDirectory/ViewControllers/EmployeesViewController.swift
#	EmployeeDirectory/ViewModels/EmployeesViewModel.swift

Signed-off-by: Matt Bruce <mbrucedogs@gmail.com>
2025-01-21 14:30:22 -06:00

144 lines
4.8 KiB
Swift

//
// EmployeeService.swift
// EmployeeDirectory
//
// Created by Matt Bruce on 1/20/25.
//
import Foundation
public enum EmployeeSortField: String {
case fullName
case team
case employeeType
}
public enum EmployeeSortOrder: String {
case ascending = "asc"
case descending = "desc"
}
/// These are the testing URL Endpoints for different states
internal enum EmployeeServiceMode: String, CaseIterable {
case production
case malformed
case empty
public var service: EmployeeServiceProtocol {
switch self {
case .production:
return MockEmployeeService.shared
//return EmployeeService.shared
case .malformed:
return EmployeeMalformedService.shared
case .empty:
return EmployeeEmptyService.shared
}
}
/// Enpoint in which to grabe employees from.
public var endpoint: String {
switch self {
case .production:
return "https://s3.amazonaws.com/sq-mobile-interview/employees.json"
case .malformed:
return "https://s3.amazonaws.com/sq-mobile-interview/employees_malformed.json"
case .empty:
return "https://s3.amazonaws.com/sq-mobile-interview/employees_empty.json"
}
}
}
/// Service Layer for Employees
public class EmployeeService: EmployeeServiceProtocol {
// MARK: - Properties
public static let shared = EmployeeService() // Default shared instance
// MARK: - Initializer
public init() {}
// MARK: - Public Methods
/// This will get a list of all employees
/// - Parameter serviceMode: Mode in which to hit.
/// - Returns: An Employees struct
public func getEmployees() async throws -> Employees {
return try await NetworkService.shared.fetchData(from: EmployeeServiceMode.production.endpoint, as: Employees.self)
}
/// Fetch employees with pagination support
/// - Parameters:
/// - page: The page number to fetch.
/// - perPage: The number of employees per page.
/// - Returns: A paginated Employees object.
public func getEmployees(page: Int, perPage: Int,
sortField: EmployeeSortField = .fullName,
sortOrder: EmployeeSortOrder = .ascending) async throws -> Employees {
guard var urlComponents = URLComponents(string: EmployeeServiceMode.production.endpoint) else {
throw NetworkServiceError.invalidURL
}
urlComponents.queryItems = [
URLQueryItem(name: "page", value: "\(page)"),
URLQueryItem(name: "perPage", value: "\(perPage)"),
URLQueryItem(name: "sortField", value: "\(sortField.rawValue)"),
URLQueryItem(name: "sortOrder", value: "\(sortOrder.rawValue)")
]
guard let url = urlComponents.url else {
throw NetworkServiceError.invalidURL
}
let request = RequestBuilder(url: url, method: .get).build()
return try await NetworkService.shared.fetchData(with: request, as: Employees.self)
}
}
/// Service Layer for Employees
public class EmployeeMalformedService: EmployeeServiceProtocol {
// MARK: - Properties
public static let shared = EmployeeMalformedService() // Default shared instance
// MARK: - Initializer
public init() {}
// MARK: - Public Methods
/// This will get a list of all employees
/// - Parameter serviceMode: Mode in which to hit.
/// - Returns: An Employees struct
public func getEmployees() async throws -> Employees {
return try await NetworkService.shared.fetchData(from: EmployeeServiceMode.malformed.endpoint, as: Employees.self)
}
public func getEmployees(page: Int, perPage: Int, sortField: EmployeeSortField, sortOrder: EmployeeSortOrder) async throws -> Employees {
return try await NetworkService.shared.fetchData(from: EmployeeServiceMode.malformed.endpoint, as: Employees.self)
}
}
/// Service Layer for Employees
public class EmployeeEmptyService: EmployeeServiceProtocol {
// MARK: - Properties
public static let shared = EmployeeEmptyService() // Default shared instance
// MARK: - Initializer
public init() {}
// MARK: - Public Methods
/// This will get a list of all employees
/// - Parameter serviceMode: Mode in which to hit.
/// - Returns: An Employees struct
public func getEmployees() async throws -> Employees {
return try await NetworkService.shared.fetchData(from: EmployeeServiceMode.empty.endpoint, as: Employees.self)
}
public func getEmployees(page: Int, perPage: Int, sortField: EmployeeSortField, sortOrder: EmployeeSortOrder) async throws -> Employees {
return try await NetworkService.shared.fetchData(from: EmployeeServiceMode.empty.endpoint, as: Employees.self)
}
}