Skip to content

Commit 5e15d94

Browse files
committed
Wire up custom collections view model
1 parent dc896ac commit 5e15d94

File tree

7 files changed

+40
-16
lines changed

7 files changed

+40
-16
lines changed

Sources/App/Controllers/API/API+PackageController+GetRoute+Model.swift

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ extension API.PackageController.GetRoute {
5151
var fundingLinks: [FundingLink]
5252
var swift6Readiness: Swift6Readiness?
5353
var forkedFromInfo: ForkedFromInfo?
54+
var customCollections: [CustomCollection.Details]
5455

5556
internal init(packageId: Package.Id,
5657
repositoryOwner: String,
@@ -83,7 +84,8 @@ extension API.PackageController.GetRoute {
8384
preReleaseReference: App.Reference?,
8485
fundingLinks: [FundingLink] = [],
8586
swift6Readiness: Swift6Readiness?,
86-
forkedFromInfo: ForkedFromInfo?
87+
forkedFromInfo: ForkedFromInfo?,
88+
customCollections: [CustomCollection.Details]
8789
) {
8890
self.packageId = packageId
8991
self.repositoryOwner = repositoryOwner
@@ -126,6 +128,7 @@ extension API.PackageController.GetRoute {
126128
self.fundingLinks = fundingLinks
127129
self.swift6Readiness = swift6Readiness
128130
self.forkedFromInfo = forkedFromInfo
131+
self.customCollections = customCollections
129132
}
130133

131134
init?(result: API.PackageController.PackageResult,
@@ -136,7 +139,8 @@ extension API.PackageController.GetRoute {
136139
platformBuildInfo: BuildInfo<CompatibilityMatrix.PlatformCompatibility>?,
137140
weightedKeywords: [WeightedKeyword] = [],
138141
swift6Readiness: Swift6Readiness?,
139-
forkedFromInfo: ForkedFromInfo?) {
142+
forkedFromInfo: ForkedFromInfo?,
143+
customCollections: [CustomCollection.Details]) {
140144
// we consider certain attributes as essential and return nil (raising .notFound)
141145
let repository = result.repository
142146
guard
@@ -182,7 +186,8 @@ extension API.PackageController.GetRoute {
182186
preReleaseReference: result.preReleaseVersion?.reference,
183187
fundingLinks: result.repository.fundingLinks,
184188
swift6Readiness: swift6Readiness,
185-
forkedFromInfo: forkedFromInfo
189+
forkedFromInfo: forkedFromInfo,
190+
customCollections: customCollections
186191
)
187192

188193
}

Sources/App/Controllers/API/API+PackageController+GetRoute.swift

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,8 @@ extension API.PackageController {
4747
repository: repository)
4848
async let forkedFromInfo = forkedFromInfo(on: database, fork: packageResult.repository.forkedFrom)
4949

50+
let customCollections = await customCollections(on: database, package: packageResult.package)
51+
5052
guard
5153
let model = try await Self.Model(
5254
result: packageResult,
@@ -57,7 +59,8 @@ extension API.PackageController {
5759
platformBuildInfo: buildInfo.platform,
5860
weightedKeywords: weightedKeywords,
5961
swift6Readiness: buildInfo.swift6Readiness,
60-
forkedFromInfo: forkedFromInfo
62+
forkedFromInfo: forkedFromInfo,
63+
customCollections: customCollections
6164
),
6265
let schema = API.PackageSchema(result: packageResult)
6366
else {
@@ -96,6 +99,15 @@ extension API.PackageController.GetRoute {
9699
return .fromGitHub(url: url)
97100
}
98101
}
102+
103+
static func customCollections(on database: Database, package: Package) async -> [CustomCollection.Details] {
104+
do {
105+
try await package.$customCollections.load(on: database)
106+
return package.customCollections.map(\.details)
107+
} catch {
108+
return []
109+
}
110+
}
99111
}
100112

101113

Sources/App/Controllers/API/Types+WithExample.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -248,7 +248,8 @@ extension API.PackageController.GetRoute.Model: WithExample {
248248
releaseReference: .tag(1, 2, 3, "1.2.3"),
249249
preReleaseReference: nil,
250250
swift6Readiness: nil,
251-
forkedFromInfo: nil)
251+
forkedFromInfo: nil,
252+
customCollections: [])
252253
}
253254
}
254255

Sources/App/Models/CustomCollection.swift

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ final class CustomCollection: @unchecked Sendable, Model, Content {
6767

6868

6969
extension CustomCollection {
70-
struct Details: Codable {
70+
struct Details: Codable, Equatable {
7171
var name: String
7272
var description: String?
7373
var badge: String?
@@ -99,6 +99,10 @@ extension CustomCollection {
9999
let removedIDs = Set(existing.keys).subtracting(Set(incoming.keys))
100100
try await $packages.detach(existing[removedIDs], on: database)
101101
}
102+
103+
var details: Details {
104+
.init(name: name, description: description, badge: badge, url: url)
105+
}
102106
}
103107

104108

Sources/App/Views/PackageController/GetRoute.Model+ext.swift

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -399,13 +399,10 @@ extension API.PackageController.GetRoute.Model {
399399
}
400400

401401
func customCollectionsItem() -> Node<HTML.ListContext> {
402-
let collections: [CustomCollection.Details] = [
403-
.init(name: "Collection 1", url: URL(string: "https://github.com/foo/bar/list1.json")!),
404-
.init(name: "Collection 2", url: URL(string: "https://github.com/foo/bar/list2.json")!)
405-
]
402+
guard !customCollections.isEmpty else { return .empty }
406403
return .li(
407404
.class("custom-collections"),
408-
.forEach(collections, { collection in
405+
.forEach(customCollections, { collection in
409406
.a(
410407
.href(collection.url), // FIXME: link to custom collection page
411408
.text("\(collection.name)")

Tests/AppTests/API+PackageController+GetRoute+ModelTests.swift

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,8 @@ class API_PackageController_GetRoute_ModelTests: SnapshotTestCase {
4343
platformBuildInfo: nil,
4444
weightedKeywords: [],
4545
swift6Readiness: nil,
46-
forkedFromInfo: nil)
46+
forkedFromInfo: nil,
47+
customCollections: [])
4748

4849
// validate
4950
XCTAssertNotNil(m)
@@ -66,7 +67,8 @@ class API_PackageController_GetRoute_ModelTests: SnapshotTestCase {
6667
platformBuildInfo: nil,
6768
weightedKeywords: [],
6869
swift6Readiness: nil,
69-
forkedFromInfo: nil))
70+
forkedFromInfo: nil,
71+
customCollections: []))
7072

7173
// validate
7274
XCTAssertEqual(model.packageIdentity, "swift-bar")
@@ -89,7 +91,8 @@ class API_PackageController_GetRoute_ModelTests: SnapshotTestCase {
8991
platformBuildInfo: nil,
9092
weightedKeywords: [],
9193
swift6Readiness: nil,
92-
forkedFromInfo: nil))
94+
forkedFromInfo: nil,
95+
customCollections: []))
9396

9497
// validate
9598
XCTAssertEqual(model.documentationTarget, .internal(docVersion: .reference("main"), archive: "archive1"))
@@ -116,7 +119,8 @@ class API_PackageController_GetRoute_ModelTests: SnapshotTestCase {
116119
platformBuildInfo: nil,
117120
weightedKeywords: [],
118121
swift6Readiness: nil,
119-
forkedFromInfo: nil))
122+
forkedFromInfo: nil,
123+
customCollections: []))
120124

121125
// validate
122126
XCTAssertEqual(model.documentationTarget, .external(url: "https://example.com/package/documentation"))

Tests/AppTests/Mocks/API.PackageController.GetRoute.Model+mock.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,8 @@ extension API.PackageController.GetRoute.Model {
129129
releaseReference: .tag(5, 2, 0),
130130
preReleaseReference: .tag(5, 3, 0, "beta.1"),
131131
swift6Readiness: nil,
132-
forkedFromInfo: nil
132+
forkedFromInfo: nil,
133+
customCollections: []
133134
)
134135
}
135136
}

0 commit comments

Comments
 (0)