import Foundation import SaplingCore public protocol GitProvider: Sendable { var displayName: String { get } func initRepository(at path: URL) async throws -> GitRepository func clone(remoteURL: URL, to destinationURL: URL) async throws -> GitRepository func repository(at path: URL) -> any Repository } public protocol Repository: Sendable { var rootURL: URL { get } func status() async throws -> [GitFileStatus] func add(paths: [String]) async throws func commit(message: String) async throws -> GitCommit func push(remote: String?, branch: String?) async throws func pull(remote: String?, branch: String?) async throws func createBranch(named name: String) async throws -> GitBranch func switchBranch(named name: String) async throws -> GitBranch func merge(branch name: String) async throws func addSubmodule(remoteURL: URL, path: String) async throws -> Subproject func removeSubmodule(path: String) async throws func updateSubmodules(initSubmodules: Bool, recursive: Bool) async throws func syncSubmodules(recursive: Bool) async throws } public protocol Branch: Sendable { var name: String { get } var isCurrent: Bool { get } var upstreamName: String? { get } } public protocol Commit: Sendable { var id: String { get } var message: String { get } var authoredAt: Date { get } } public protocol Remote: Sendable { var name: String { get } var url: URL { get } } extension GitBranch: Branch {} extension GitCommit: Commit {} extension GitRemote: Remote {} public enum GitProviderError: Error, Equatable, Sendable { case unsupportedOnCurrentPlatform case commandFailed(command: String, exitCode: Int32, output: String) case invalidRepository(URL) case notImplemented(String) }