Skip to content

Commit 0e9d0a4

Browse files
committed
add DemoShopRepositoryTest
1 parent a4a09e0 commit 0e9d0a4

12 files changed

Lines changed: 575 additions & 6 deletions

NativeAppTemplate/Login/SignUpService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ import Foundation
99
import SwiftyJSON
1010

1111
struct SignUpsService {
12-
var networkClient: NativeAppTemplateAPI
12+
var networkClient = NativeAppTemplateAPI()
1313
var session = URLSession(configuration: .default)
1414
}
1515

NativeAppTemplate/Networking/Services/AccountPasswordService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
import class Foundation.URLSession
99

1010
struct AccountPasswordService: Service {
11-
let networkClient: NativeAppTemplateAPI
11+
var networkClient = NativeAppTemplateAPI()
1212
let session = URLSession(configuration: .default)
1313
}
1414

NativeAppTemplate/Networking/Services/ItemTagsService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
import class Foundation.URLSession
99

1010
struct ItemTagsService: Service {
11-
let networkClient: NativeAppTemplateAPI
11+
var networkClient = NativeAppTemplateAPI()
1212
let session = URLSession(configuration: .default)
1313
}
1414

NativeAppTemplate/Networking/Services/MeService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
import class Foundation.URLSession
99

1010
struct MeService: Service {
11-
let networkClient: NativeAppTemplateAPI
11+
var networkClient = NativeAppTemplateAPI()
1212
let session = URLSession(configuration: .default)
1313
}
1414

NativeAppTemplate/Networking/Services/PermissionsService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
import class Foundation.URLSession
3030

3131
struct PermissionsService: Service {
32-
let networkClient: NativeAppTemplateAPI
32+
var networkClient = NativeAppTemplateAPI()
3333
let session = URLSession(configuration: .default)
3434
}
3535

NativeAppTemplate/Networking/Services/ShopsService.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
import class Foundation.URLSession
3030

3131
struct ShopsService: Service {
32-
let networkClient: NativeAppTemplateAPI
32+
var networkClient = NativeAppTemplateAPI()
3333
let session = URLSession(configuration: .default)
3434
}
3535

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
//
2+
// DemoAccountPasswordRepository.swift
3+
// NativeAppTemplate
4+
//
5+
// Created by Daisuke Adachi on 2025/06/16.
6+
//
7+
8+
@testable import NativeAppTemplate
9+
import Foundation
10+
11+
@MainActor
12+
final class DemoAccountPasswordRepository: AccountPasswordRepositoryProtocol {
13+
var lastUpdatePassword: UpdatePassword?
14+
var shouldThrowError = false
15+
var errorMessage = "Invalid current password"
16+
17+
required init(accountPasswordService: AccountPasswordService) {
18+
}
19+
20+
func update(updatePassword: UpdatePassword) async throws {
21+
lastUpdatePassword = updatePassword
22+
23+
if shouldThrowError {
24+
throw NativeAppTemplateAPIError.requestFailed(nil, 422, errorMessage)
25+
}
26+
27+
// Simulate validation
28+
if updatePassword.currentPassword.isEmpty {
29+
throw NativeAppTemplateAPIError.requestFailed(nil, 422, "Current password is required")
30+
}
31+
32+
if updatePassword.password.isEmpty {
33+
throw NativeAppTemplateAPIError.requestFailed(nil, 422, "New password is required")
34+
}
35+
36+
if updatePassword.password != updatePassword.passwordConfirmation {
37+
throw NativeAppTemplateAPIError.requestFailed(nil, 422, "Password confirmation does not match")
38+
}
39+
40+
if updatePassword.password.count < 8 {
41+
throw NativeAppTemplateAPIError.requestFailed(nil, 422, "Password must be at least 8 characters long")
42+
}
43+
44+
// Success case - password updated
45+
}
46+
47+
// MARK: - Test Helpers
48+
func resetState() {
49+
lastUpdatePassword = nil
50+
shouldThrowError = false
51+
errorMessage = "Invalid current password"
52+
}
53+
}
Lines changed: 113 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
//
2+
// DemoAccountPasswordRepositoryTest.swift
3+
// NativeAppTemplate
4+
//
5+
// Created by Daisuke Adachi on 2025/06/16.
6+
//
7+
8+
import Testing
9+
@testable import NativeAppTemplate
10+
11+
@Suite
12+
struct DemoAccountPasswordRepositoryTest {
13+
@MainActor
14+
struct Tests {
15+
let repository = DemoAccountPasswordRepository(accountPasswordService: AccountPasswordService())
16+
17+
@Test
18+
func updatePasswordSuccess() async throws {
19+
repository.resetState()
20+
21+
let updatePassword = UpdatePassword(
22+
currentPassword: "currentPassword123",
23+
password: "newPassword123",
24+
passwordConfirmation: "newPassword123"
25+
)
26+
27+
await #expect(throws: Never.self) {
28+
try await repository.update(updatePassword: updatePassword)
29+
}
30+
31+
#expect(repository.lastUpdatePassword?.currentPassword == "currentPassword123")
32+
#expect(repository.lastUpdatePassword?.password == "newPassword123")
33+
#expect(repository.lastUpdatePassword?.passwordConfirmation == "newPassword123")
34+
}
35+
36+
@Test
37+
func updatePasswordWithEmptyCurrentPassword() async throws {
38+
repository.resetState()
39+
40+
let updatePassword = UpdatePassword(
41+
currentPassword: "",
42+
password: "newPassword123",
43+
passwordConfirmation: "newPassword123"
44+
)
45+
46+
await #expect(throws: NativeAppTemplateAPIError.self) {
47+
try await repository.update(updatePassword: updatePassword)
48+
}
49+
}
50+
51+
@Test
52+
func updatePasswordWithEmptyNewPassword() async throws {
53+
repository.resetState()
54+
55+
let updatePassword = UpdatePassword(
56+
currentPassword: "currentPassword123",
57+
password: "",
58+
passwordConfirmation: ""
59+
)
60+
61+
await #expect(throws: NativeAppTemplateAPIError.self) {
62+
try await repository.update(updatePassword: updatePassword)
63+
}
64+
}
65+
66+
@Test
67+
func updatePasswordWithMismatchedConfirmation() async throws {
68+
repository.resetState()
69+
70+
let updatePassword = UpdatePassword(
71+
currentPassword: "currentPassword123",
72+
password: "newPassword123",
73+
passwordConfirmation: "differentPassword123"
74+
)
75+
76+
await #expect(throws: NativeAppTemplateAPIError.self) {
77+
try await repository.update(updatePassword: updatePassword)
78+
}
79+
}
80+
81+
@Test
82+
func updatePasswordWithShortPassword() async throws {
83+
repository.resetState()
84+
85+
let updatePassword = UpdatePassword(
86+
currentPassword: "currentPassword123",
87+
password: "short",
88+
passwordConfirmation: "short"
89+
)
90+
91+
await #expect(throws: NativeAppTemplateAPIError.self) {
92+
try await repository.update(updatePassword: updatePassword)
93+
}
94+
}
95+
96+
@Test
97+
func updatePasswordWithForcedError() async throws {
98+
repository.resetState()
99+
repository.shouldThrowError = true
100+
repository.errorMessage = "Custom error message"
101+
102+
let updatePassword = UpdatePassword(
103+
currentPassword: "currentPassword123",
104+
password: "newPassword123",
105+
passwordConfirmation: "newPassword123"
106+
)
107+
108+
await #expect(throws: NativeAppTemplateAPIError.self) {
109+
try await repository.update(updatePassword: updatePassword)
110+
}
111+
}
112+
}
113+
}
Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
//
2+
// DemoItemTagRepository.swift
3+
// NativeAppTemplate
4+
//
5+
// Created by Daisuke Adachi on 2025/05/17.
6+
//
7+
8+
import Testing
9+
@testable import NativeAppTemplate
10+
import Foundation
11+
12+
@MainActor
13+
final class DemoItemTagRepository: ItemTagRepositoryProtocol {
14+
var itemTags: [ItemTag] = []
15+
var state: DataState = .initial
16+
var isEmpty: Bool { itemTags.isEmpty }
17+
18+
required init(itemTagsService: ItemTagsService) {
19+
}
20+
21+
func findBy(id: String) -> ItemTag {
22+
itemTags.first { $0.id == id }!
23+
}
24+
25+
func reload(shopId: String) {
26+
state = .loading
27+
28+
let allItemTags = fetchAll()
29+
itemTags = allItemTags.filter { $0.shopId == shopId }
30+
31+
state = .hasData
32+
}
33+
34+
func fetchAll(shopId: String) async throws -> [ItemTag] {
35+
let allItemTags = fetchAll()
36+
let itemTags = allItemTags.filter { $0.shopId == shopId }
37+
38+
return itemTags
39+
}
40+
41+
func fetchDetail(id: String) async throws -> ItemTag {
42+
return itemTags.first { $0.id == id }!
43+
}
44+
45+
func create(shopId: String, itemTag: ItemTag) async throws -> ItemTag {
46+
itemTags.append(itemTag)
47+
return itemTag
48+
}
49+
50+
func update(id: String, itemTag: ItemTag) async throws -> ItemTag {
51+
let index = itemTags.firstIndex { $0.id == id }!
52+
itemTags[index] = itemTag
53+
54+
return itemTag
55+
}
56+
57+
func destroy(id: String) async throws {
58+
itemTags.removeAll { $0.id == id }
59+
}
60+
61+
func complete(id: String) async throws -> ItemTag {
62+
var itemTag = itemTags.first { $0.id == id }!
63+
itemTag.state = .completed
64+
itemTag.completedAt = .now
65+
66+
let index = itemTags.firstIndex { $0.id == id }!
67+
itemTags[index] = itemTag
68+
69+
return itemTag
70+
}
71+
72+
func reset(id: String) async throws -> ItemTag {
73+
var itemTag = itemTags.first { $0.id == id }!
74+
itemTag.state = .idled
75+
itemTag.scanState = .unscanned
76+
itemTag.completedAt = nil
77+
itemTag.customerReadAt = nil
78+
79+
let index = itemTags.firstIndex { $0.id == id }!
80+
itemTags[index] = itemTag
81+
82+
return itemTag
83+
}
84+
85+
private func fetchAll() -> [ItemTag] {
86+
return [
87+
mockItemTag(id: "1", shopId: "1", queueNumber: "A001"),
88+
mockItemTag(id: "2", shopId: "1", queueNumber: "A002"),
89+
mockItemTag(id: "3", shopId: "1", queueNumber: "A003"),
90+
mockItemTag(id: "4", shopId: "2", queueNumber: "A001"),
91+
mockItemTag(id: "5", shopId: "2", queueNumber: "A002"),
92+
mockItemTag(id: "6", shopId: "2", queueNumber: "A003"),
93+
mockItemTag(id: "7", shopId: "2", queueNumber: "A004")
94+
]
95+
}
96+
97+
// MARK: - Helpers
98+
private func mockItemTag(
99+
id: String = UUID().uuidString,
100+
shopId: String = UUID().uuidString,
101+
queueNumber: String = "Mock ItemTag"
102+
) -> ItemTag {
103+
ItemTag(
104+
id: id,
105+
shopId: shopId,
106+
queueNumber: queueNumber,
107+
state: .idled,
108+
scanState: .unscanned,
109+
createdAt: .now,
110+
customerReadAt: nil,
111+
completedAt: nil,
112+
shopName: "Mock ItemTag",
113+
alreadyCompleted: false
114+
)
115+
}
116+
}

0 commit comments

Comments
 (0)