Skip to content

Commit 8e4a768

Browse files
committed
[feat][#29] network 연결 확인 및 상태별 처리
1 parent 1bba44c commit 8e4a768

File tree

5 files changed

+59
-13
lines changed

5 files changed

+59
-13
lines changed

DontForget.xcodeproj/project.pbxproj

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@
4848
AD147F322B57FFB500561846 /* AppIntent.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD147F312B57FFB500561846 /* AppIntent.swift */; };
4949
AD147F342B57FFB600561846 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = AD147F332B57FFB600561846 /* Assets.xcassets */; };
5050
AD147F382B57FFB600561846 /* DontForgetWidgetExtension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = AD147F262B57FFB500561846 /* DontForgetWidgetExtension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
51+
AD1D31F92B9589A700ECCBFD /* NetworkMonitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD1D31F82B9589A700ECCBFD /* NetworkMonitor.swift */; };
5152
AD36D44B2B8DD37D00250705 /* DeletionRepository.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD36D44A2B8DD37D00250705 /* DeletionRepository.swift */; };
5253
AD36D44D2B8DD39500250705 /* DeletionInterface.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD36D44C2B8DD39500250705 /* DeletionInterface.swift */; };
5354
AD3B45852B68B634009529DE /* AnniversaryDetailView.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD3B45842B68B634009529DE /* AnniversaryDetailView.swift */; };
@@ -152,6 +153,7 @@
152153
AD147F312B57FFB500561846 /* AppIntent.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppIntent.swift; sourceTree = "<group>"; };
153154
AD147F332B57FFB600561846 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
154155
AD147F352B57FFB600561846 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
156+
AD1D31F82B9589A700ECCBFD /* NetworkMonitor.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NetworkMonitor.swift; sourceTree = "<group>"; };
155157
AD36D44A2B8DD37D00250705 /* DeletionRepository.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DeletionRepository.swift; sourceTree = "<group>"; };
156158
AD36D44C2B8DD39500250705 /* DeletionInterface.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DeletionInterface.swift; sourceTree = "<group>"; };
157159
AD3B45842B68B634009529DE /* AnniversaryDetailView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AnniversaryDetailView.swift; sourceTree = "<group>"; };
@@ -251,6 +253,7 @@
251253
children = (
252254
09642C3A2B649B260015220E /* EndPoint.swift */,
253255
09642C3C2B649B2D0015220E /* APIConstant.swift */,
256+
AD1D31F82B9589A700ECCBFD /* NetworkMonitor.swift */,
254257
);
255258
path = Network;
256259
sourceTree = "<group>";
@@ -756,6 +759,7 @@
756759
09642C462B649FD00015220E /* DTO.swift in Sources */,
757760
AD0F99332B7C523200E2A915 /* AlarmView.swift in Sources */,
758761
09642C582B67C8730015220E /* ViewModelType.swift in Sources */,
762+
AD1D31F92B9589A700ECCBFD /* NetworkMonitor.swift in Sources */,
759763
);
760764
runOnlyForDeploymentPostprocessing = 0;
761765
};
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
//
2+
// NetworkMonitor.swift
3+
// DontForget
4+
//
5+
// Created by 제나 on 3/4/24.
6+
//
7+
8+
import Foundation
9+
import Network
10+
11+
@Observable
12+
final class NetworkMonitor: ObservableObject {
13+
static let shared = NetworkMonitor()
14+
private let networkMonitor = NWPathMonitor()
15+
private let workerQueue = DispatchQueue(label: "Monitor")
16+
var isConnected = false
17+
18+
init() {
19+
networkMonitor.pathUpdateHandler = { path in
20+
self.isConnected = path.status == .satisfied
21+
}
22+
networkMonitor.start(queue: workerQueue)
23+
}
24+
}

DontForget/Sources/Presentations/Application/Detail/View/AnniversaryDetailView.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,7 @@ struct AnniversaryDetailView: View {
164164
coordinateSpace: .local
165165
)
166166
.onEnded({ value in
167-
if value.translation.width > 200 {
167+
if value.translation.width > 100 {
168168
withAnimation {
169169
dismiss()
170170
}

DontForget/Sources/Presentations/Application/Detail/ViewModel/AnniversaryDetailViewModel.swift

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ final class DefaultAnniversaryDetailViewModel: ViewModelType {
1313
// MARK: - Properties
1414
let anniversaryId: Int
1515
private var cancellables = Set<AnyCancellable>()
16-
@Published var state: State
16+
@Published var state: State = .idle
1717
@Published var anniversaryDetail: AnniversaryDetailDTO?
1818
private let anniversaryDetailRepository: AnniversaryDetailRepository
1919
private let deletionRepository: DeletionRepository
@@ -44,7 +44,6 @@ final class DefaultAnniversaryDetailViewModel: ViewModelType {
4444
anniversaryDetailRepository: AnniversaryDetailRepository,
4545
deletionRepository: DeletionRepository
4646
) {
47-
self.state = .loading
4847
self.anniversaryId = anniversaryId
4948
self.anniversaryDetailRepository = anniversaryDetailRepository
5049
self.fetchAnniversaryDetailUseCase = DefaultFetchAnniversaryDetailUseCase(
@@ -82,15 +81,13 @@ final class DefaultAnniversaryDetailViewModel: ViewModelType {
8281
} catch {
8382
print("=== DEBUG: \(error)")
8483
promise(.failure(error))
85-
self.state = .failed("failed fetchAnniversaryDetail()")
8684
}
8785
}
8886
}
8987
.receive(on: DispatchQueue.main)
9088
.sink { _ in } receiveValue: { [weak self] response in
9189
if let response = response {
9290
self?.anniversaryDetail = response.anniversaryDetail
93-
self?.state = .success
9491
}
9592
}
9693
.store(in: &cancellables)

DontForget/Sources/Presentations/Application/Home/View/HomeView.swift

Lines changed: 29 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ struct HomeView: View {
2727
@State private var navigateToCreationView = false
2828
@State private var isNavigate = false
2929
@State private var id = -1
30+
private var networkConnected: Bool { NetworkMonitor.shared.isConnected }
3031

3132
var body: some View {
3233
NavigationView {
@@ -81,7 +82,8 @@ struct HomeView: View {
8182
}
8283
.clipShape(RoundedRectangle(cornerRadius: 32))
8384
.onTapGesture {
84-
if let firstAnniversaryDetail = viewModel.firstAnniversaryDetail {
85+
if let firstAnniversaryDetail = viewModel.firstAnniversaryDetail,
86+
networkConnected {
8587
id = firstAnniversaryDetail.anniversaryId
8688
isNavigate = true
8789
}
@@ -109,9 +111,11 @@ struct HomeView: View {
109111
.simultaneousGesture(
110112
TapGesture()
111113
.onEnded({
112-
DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) {
113-
id = anniversaries[index].anniversaryId
114-
isNavigate = true
114+
if networkConnected {
115+
DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) {
116+
id = anniversaries[index].anniversaryId
117+
isNavigate = true
118+
}
115119
}
116120
})
117121
)
@@ -129,10 +133,7 @@ struct HomeView: View {
129133
#endif
130134
}
131135
.offset(y: anniversaries.isEmpty ? 0 : -140)
132-
.onAppear {
133-
viewModel.action(.readAnniversaries)
134-
viewModel.action(.changePushState)
135-
}
136+
.onAppear(perform: actionOnAppear)
136137
.id(Self.scrollTopView)
137138
}
138139
.scrollDisabled(anniversaries.isEmpty)
@@ -150,6 +151,20 @@ struct HomeView: View {
150151
}
151152
}
152153
}
154+
.onChange(of: networkConnected) { _, status in
155+
if status {
156+
actionOnAppear()
157+
}
158+
}
159+
.toolbar {
160+
if !networkConnected {
161+
ToolbarItem(placement: .status) {
162+
Text("네트워크 연결이 없어요")
163+
.font(.pretendard(size: 15))
164+
.foregroundStyle(.white)
165+
}
166+
}
167+
}
153168
}
154169
}
155170
}
@@ -204,5 +219,11 @@ extension HomeView {
204219
isActive: $navigateToCreationView,
205220
label: { AddNewAnniversaryView() }
206221
)
222+
.disabled(!networkConnected)
223+
}
224+
225+
private func actionOnAppear() {
226+
viewModel.action(.readAnniversaries)
227+
viewModel.action(.changePushState)
207228
}
208229
}

0 commit comments

Comments
 (0)