Resolve providers correctly

This commit is contained in:
2025-07-07 20:12:57 +10:00
parent 1953c00f17
commit 80c063b3c2
3 changed files with 60 additions and 18 deletions

View File

@ -1,5 +1,5 @@
/*
* darwin-apk © 2024 Gay Pizza Specifications
* darwin-apk © 2024, 2025 Gay Pizza Specifications
* SPDX-License-Identifier: Apache-2.0
*/
@ -25,21 +25,15 @@ public extension ApkIndex {
func resolve(requirement: ApkVersionRequirement) -> ApkIndexPackage? {
self.packages.first { pkg in
guard pkg.name == requirement.name ||
pkg.provides.contains(where: { $0.name == requirement.name }) else {
return false
}
return requirement.versionSpec.satisfied(by: pkg.version)
return (pkg.name == requirement.name && requirement.versionSpec.satisfied(by: pkg.version))
|| pkg.provides.contains(where: { $0.satisfies(requirement) })
}
}
func resolveIndex(requirement: ApkVersionRequirement) -> Index? {
self.packages.firstIndex { pkg in
guard pkg.name == requirement.name ||
pkg.provides.contains(where: { $0.name == requirement.name }) else {
return false
}
return requirement.versionSpec.satisfied(by: pkg.version)
return (pkg.name == requirement.name && requirement.versionSpec.satisfied(by: pkg.version))
|| pkg.provides.contains(where: { $0.satisfies(requirement) })
}
}
}

View File

@ -93,7 +93,7 @@ extension ApkIndexPackage {
case "p":
do {
provides = try record.value.split(separator: " ")
.map { .init(requirement: try .init(extract: $0)) }
.map { try .init(requirement: try .init(extract: $0)) }
} catch { throw .badValue(key: record.key, cause: error.localizedDescription) }
case "i":
do {
@ -207,7 +207,7 @@ extension ApkIndexPackage: CustomStringConvertible {
s += "dependencies: - \(self.dependencies.map(\.requirement.description).joined(separator: " "))\n"
}
if !self.provides.isEmpty {
s += "provides: ----- \(self.provides.map(\.name).joined(separator: " "))\n"
s += "provides: ----- \(self.provides.map(\.description).joined(separator: " "))\n"
}
if !self.installIf.isEmpty {
s += "install if: --- \(self.installIf.map(\.requirement.description).joined(separator: " "))\n"

View File

@ -1,12 +1,60 @@
/*
* darwin-apk © 2024 Gay Pizza Specifications
* darwin-apk © 2024, 2025 Gay Pizza Specifications
* SPDX-License-Identifier: Apache-2.0
*/
public struct ApkIndexProvides: Hashable, Sendable {
let name: String
import Foundation
init(requirement: ApkVersionRequirement) {
self.name = requirement.name
public enum ApkIndexProvides: Hashable, Sendable {
case any(name: String)
case specific(name: String, version: String)
}
extension ApkIndexProvides {
init(requirement: ApkVersionRequirement) throws(ProvidesError) {
self = switch requirement.versionSpec {
case .any(invert: false):
.any(name: requirement.name)
case .constraint(invert: false, op: .equals, let version):
.specific(name: requirement.name, version: version)
default:
throw .badConstraint
}
}
func satisfies(_ requirement: ApkVersionRequirement) -> Bool {
switch self {
case .any(let name):
return requirement.name == name
case .specific(let name, let version):
return requirement.name == name &&
requirement.versionSpec.satisfied(by: version)
}
}
enum ProvidesError: Error, LocalizedError {
case badConstraint
var errorDescription: String? {
switch self {
case .badConstraint: "Invalid constraint type, must only be equals"
}
}
}
}
extension ApkIndexProvides: CustomStringConvertible {
public var description: String {
switch self {
case .any(let name): name
case .specific(let name, let version): "\(name)=\(version)"
}
}
public var name: String {
switch self {
case .any(let name): name
case .specific(let name, _): name
}
}
}