[#499] Refactor Route to Destination (#500)

- Route -> Destination refactor done
- test working
- cleanup of URLRouting usage
This commit is contained in:
Lukas Korba 2022-12-01 15:31:30 +01:00 committed by GitHub
parent a591ee93ce
commit 8e3544b732
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
31 changed files with 272 additions and 272 deletions

View File

@ -11,12 +11,12 @@ import ComposableArchitecture
import ZcashLightClientKit
struct Deeplink {
enum Route: Equatable {
enum Destination: Equatable {
case home
case send(amount: Int64, address: String, memo: String)
}
func resolveDeeplinkURL(_ url: URL, isValidZcashAddress: (String) throws -> Bool) throws -> Route {
func resolveDeeplinkURL(_ url: URL, isValidZcashAddress: (String) throws -> Bool) throws -> Destination {
// simplified format zcash:<address>
// TODO [#109]: simplified for now until ZIP-321 is implememnted (https://github.com/zcash/secant-ios-wallet/issues/109)
let address = url.absoluteString.replacingOccurrences(of: "zcash:", with: "")
@ -29,12 +29,12 @@ struct Deeplink {
// regular URL format zcash://
let appRouter = OneOf {
// GET /home
URLRouting.Route(.case(Route.home)) {
Route(.case(Destination.home)) {
Path { "home" }
}
// GET /home/send?amount=:amount&address=:address&memo=:memo
URLRouting.Route(.case(Route.send(amount:address:memo:))) {
Route(.case(Destination.send(amount:address:memo:))) {
Path { "home"; "send" }
Query {
Field("amount", default: 0) { Int64.parser() }

View File

@ -17,5 +17,5 @@ extension DependencyValues {
}
struct DeeplinkClient {
let resolveDeeplinkURL: (URL, DerivationToolClient) throws -> Deeplink.Route
let resolveDeeplinkURL: (URL, DerivationToolClient) throws -> Deeplink.Destination
}

View File

@ -10,7 +10,7 @@ struct AppReducer: ReducerProtocol {
private enum CancelId {}
struct State: Equatable {
enum Route: Equatable {
enum Destination: Equatable {
case welcome
case startup
case onboarding
@ -25,17 +25,17 @@ struct AppReducer: ReducerProtocol {
var onboardingState: OnboardingFlowReducer.State
var phraseValidationState: RecoveryPhraseValidationFlowReducer.State
var phraseDisplayState: RecoveryPhraseDisplayReducer.State
var prevRoute: Route?
var internalRoute: Route = .welcome
var prevDestination: Destination?
var internalDestination: Destination = .welcome
var sandboxState: SandboxReducer.State
var storedWallet: StoredWallet?
var welcomeState: WelcomeReducer.State
var route: Route {
get { internalRoute }
var destination: Destination {
get { internalDestination }
set {
prevRoute = internalRoute
internalRoute = newValue
prevDestination = internalDestination
internalDestination = newValue
}
}
}
@ -56,7 +56,7 @@ struct AppReducer: ReducerProtocol {
case phraseValidation(RecoveryPhraseValidationFlowReducer.Action)
case respondToWalletInitializationState(InitializationState)
case sandbox(SandboxReducer.Action)
case updateRoute(AppReducer.State.Route)
case updateDestination(AppReducer.State.Destination)
case welcome(WelcomeReducer.Action)
}
@ -93,29 +93,29 @@ struct AppReducer: ReducerProtocol {
Reduce { state, action in
switch action {
case let .updateRoute(route):
state.route = route
case let .updateDestination(destination):
state.destination = destination
case .sandbox(.reset):
state.route = .startup
state.destination = .startup
case .onboarding(.createNewWallet):
return Effect(value: .createNewWallet)
case .phraseValidation(.proceedToHome):
state.route = .home
state.destination = .home
case .phraseValidation(.displayBackedUpPhrase):
state.route = .phraseDisplay
state.destination = .phraseDisplay
case .phraseDisplay(.finishedPressed):
// user is still supposed to do the backup phrase validation test
if state.prevRoute == .welcome || state.prevRoute == .onboarding {
state.route = .phraseValidation
if state.prevDestination == .welcome || state.prevDestination == .onboarding {
state.destination = .phraseValidation
}
// user wanted to see the backup phrase once again (at validation finished screen)
if state.prevRoute == .phraseValidation {
state.route = .home
if state.prevDestination == .phraseValidation {
state.destination = .home
}
case .deeplink(let url):
@ -144,13 +144,13 @@ struct AppReducer: ReducerProtocol {
}
case .deeplinkHome:
state.route = .home
state.homeState.route = nil
state.destination = .home
state.homeState.destination = nil
return .none
case let .deeplinkSend(amount, address, memo):
state.route = .home
state.homeState.route = .send
state.destination = .home
state.homeState.destination = .send
state.homeState.sendState.amount = amount
state.homeState.sendState.address = address
state.homeState.sendState.memoState.text = memo
@ -162,7 +162,7 @@ struct AppReducer: ReducerProtocol {
}
return Effect(value: .deeplink(url))
/// Default is meaningful here because there's `appReducer` handling actions and this reducer is handling only routes. We don't here plenty of unused cases.
/// Default is meaningful here because there's `appReducer` handling actions and this reducer is handling only destinations. We don't here plenty of unused cases.
default:
break
}
@ -206,7 +206,7 @@ struct AppReducer: ReducerProtocol {
)
case .uninitialized:
state.appInitializationState = .uninitialized
return Effect(value: .updateRoute(.onboarding))
return Effect(value: .updateDestination(.onboarding))
.delay(for: 3, scheduler: mainQueue)
.eraseToEffect()
.cancellable(id: CancelId.self, cancelInFlight: true)
@ -257,7 +257,7 @@ struct AppReducer: ReducerProtocol {
return .none
}
var landingRoute: AppReducer.State.Route = .home
var landingDestination: AppReducer.State.Destination = .home
if !storedWallet.hasUserPassedPhraseBackupTest {
do {
@ -266,7 +266,7 @@ struct AppReducer: ReducerProtocol {
let recoveryPhrase = RecoveryPhrase(words: phraseWords)
state.phraseDisplayState.phrase = recoveryPhrase
state.phraseValidationState = randomRecoveryPhrase.random(recoveryPhrase)
landingRoute = .phraseDisplay
landingDestination = .phraseDisplay
} catch {
// TODO [#201]: - merge with issue 201 (https://github.com/zcash/secant-ios-wallet/issues/201) and its Error States
return .none
@ -275,7 +275,7 @@ struct AppReducer: ReducerProtocol {
state.appInitializationState = .initialized
return Effect(value: .updateRoute(landingRoute))
return Effect(value: .updateDestination(landingDestination))
.delay(for: 3, scheduler: mainQueue)
.eraseToEffect()
.cancellable(id: CancelId.self, cancelInFlight: true)
@ -325,16 +325,16 @@ struct AppReducer: ReducerProtocol {
case .welcome(.debugMenuStartup), .home(.debugMenuStartup):
return .concatenate(
Effect.cancel(id: CancelId.self),
Effect(value: .updateRoute(.startup))
Effect(value: .updateDestination(.startup))
)
case .onboarding(.importWallet(.successfullyRecovered)):
return Effect(value: .updateRoute(.home))
return Effect(value: .updateDestination(.home))
case .onboarding(.importWallet(.initializeSDK)):
return Effect(value: .initializeSDK)
/// Default is meaningful here because there's `routeReducer` handling routes and this reducer is handling only actions. We don't here plenty of unused cases.
/// Default is meaningful here because there's `destinationReducer` handling destinations and this reducer is handling only actions. We don't here plenty of unused cases.
default:
return .none
}

View File

@ -8,7 +8,7 @@ struct AppView: View {
var body: some View {
WithViewStore(store) { viewStore in
Group {
switch viewStore.route {
switch viewStore.destination {
case .home:
NavigationView {
HomeView(
@ -86,21 +86,21 @@ struct AppView: View {
private extension AppView {
@ViewBuilder func debugView(_ viewStore: AppViewStore) -> some View {
List {
Section(header: Text("Navigation Stack Routes")) {
Section(header: Text("Navigation Stack Destinations")) {
Button("Go To Sandbox (navigation proof)") {
viewStore.send(.updateRoute(.sandbox))
viewStore.send(.updateDestination(.sandbox))
}
Button("Go To Onboarding") {
viewStore.send(.updateRoute(.onboarding))
viewStore.send(.updateDestination(.onboarding))
}
Button("Go To Phrase Validation Demo") {
viewStore.send(.updateRoute(.phraseValidation))
viewStore.send(.updateDestination(.phraseValidation))
}
Button("Restart the app") {
viewStore.send(.updateRoute(.welcome))
viewStore.send(.updateDestination(.welcome))
}
Button("[Be careful] Nuke Wallet") {

View File

@ -12,7 +12,7 @@ struct HomeReducer: ReducerProtocol {
private enum CancelId {}
struct State: Equatable {
enum Route: Equatable {
enum Destination: Equatable {
case notEnoughFreeDiskSpace
case profile
case request
@ -21,7 +21,7 @@ struct HomeReducer: ReducerProtocol {
case balanceBreakdown
}
var route: Route?
var destination: Destination?
var balanceBreakdownState: BalanceBreakdownReducer.State
var drawerOverlay: DrawerOverlay
@ -68,7 +68,7 @@ struct HomeReducer: ReducerProtocol {
case synchronizerStateChanged(SDKSynchronizerState)
case walletEvents(WalletEventsFlowReducer.Action)
case updateDrawer(DrawerOverlay)
case updateRoute(HomeReducer.State.Route?)
case updateDestination(HomeReducer.State.Destination?)
case updateSynchronizerStatus
case updateWalletEvents([WalletEvent])
}
@ -110,9 +110,9 @@ struct HomeReducer: ReducerProtocol {
.map(HomeReducer.Action.synchronizerStateChanged)
.eraseToEffect()
.cancellable(id: CancelId.self, cancelInFlight: true)
return .concatenate(Effect(value: .updateRoute(nil)), syncEffect)
return .concatenate(Effect(value: .updateDestination(nil)), syncEffect)
} else {
return Effect(value: .updateRoute(.notEnoughFreeDiskSpace))
return Effect(value: .updateDestination(.notEnoughFreeDiskSpace))
}
case .onDisappear:
@ -145,16 +145,16 @@ struct HomeReducer: ReducerProtocol {
}
return .none
case .updateRoute(let route):
state.route = route
case .updateDestination(let destination):
state.destination = destination
return .none
case .profile(.back):
state.route = nil
state.destination = nil
return .none
case .profile(.settings(.quickRescan)):
state.route = nil
state.destination = nil
return Effect.task {
do {
try await sdkSynchronizer.rewind(.quick)
@ -165,7 +165,7 @@ struct HomeReducer: ReducerProtocol {
}
case .profile(.settings(.fullRescan)):
state.route = nil
state.destination = nil
return Effect.task {
do {
try await sdkSynchronizer.rewind(.birthday)
@ -185,30 +185,30 @@ struct HomeReducer: ReducerProtocol {
// TODO [#221]: error we need to handle (https://github.com/zcash/secant-ios-wallet/issues/221)
return .none
case .walletEvents(.updateRoute(.all)):
case .walletEvents(.updateDestination(.all)):
return state.drawerOverlay != .full ? Effect(value: .updateDrawer(.full)) : .none
case .walletEvents(.updateRoute(.latest)):
case .walletEvents(.updateDestination(.latest)):
return state.drawerOverlay != .partial ? Effect(value: .updateDrawer(.partial)) : .none
case .walletEvents:
return .none
case .send(.updateRoute(.done)):
return Effect(value: .updateRoute(nil))
case .send(.updateDestination(.done)):
return Effect(value: .updateDestination(nil))
case .send:
return .none
case .scan(.found):
audioServices.systemSoundVibrate()
return Effect(value: .updateRoute(nil))
return Effect(value: .updateDestination(nil))
case .scan:
return .none
case .balanceBreakdown(.onDisappear):
state.route = nil
state.destination = nil
return .none
case .balanceBreakdown:
@ -270,11 +270,11 @@ extension HomeStore {
// MARK: - ViewStore
extension HomeViewStore {
func bindingForRoute(_ route: HomeReducer.State.Route) -> Binding<Bool> {
func bindingForDestination(_ destination: HomeReducer.State.Destination) -> Binding<Bool> {
self.binding(
get: { $0.route == route },
get: { $0.destination == destination },
send: { isActive in
return .updateRoute(isActive ? route : nil)
return .updateDestination(isActive ? destination : nil)
}
)
}

View File

@ -27,12 +27,12 @@ struct HomeView: View {
.navigationBarHidden(true)
.onAppear(perform: { viewStore.send(.onAppear) })
.onDisappear(perform: { viewStore.send(.onDisappear) })
.fullScreenCover(isPresented: viewStore.bindingForRoute(.balanceBreakdown)) {
.fullScreenCover(isPresented: viewStore.bindingForDestination(.balanceBreakdown)) {
BalanceBreakdownView(store: store.balanceBreakdownStore())
}
}
.navigationLinkEmpty(
isActive: viewStore.bindingForRoute(.notEnoughFreeDiskSpace),
isActive: viewStore.bindingForDestination(.notEnoughFreeDiskSpace),
destination: { NotEnoughFreeSpaceView(viewStore: viewStore) }
)
}
@ -52,7 +52,7 @@ extension HomeView {
.frame(width: 60, height: 60)
.padding(.trailing, 15)
.navigationLink(
isActive: viewStore.bindingForRoute(.profile),
isActive: viewStore.bindingForDestination(.profile),
destination: {
ProfileView(store: store.profileStore())
}
@ -82,7 +82,7 @@ extension HomeView {
.padding(.horizontal, 50)
.neumorphicButton()
.navigationLink(
isActive: viewStore.bindingForRoute(.send),
isActive: viewStore.bindingForDestination(.send),
destination: {
SendFlowView(store: store.sendStore())
}
@ -101,7 +101,7 @@ extension HomeView {
.padding(.top, 7)
.padding(.leading, 22)
.navigationLink(
isActive: viewStore.bindingForRoute(.scan),
isActive: viewStore.bindingForDestination(.scan),
destination: {
ScanView(store: store.scanStore())
}
@ -128,7 +128,7 @@ extension HomeView {
VStack {
Button {
viewStore.send(.updateRoute(.balanceBreakdown))
viewStore.send(.updateDestination(.balanceBreakdown))
} label: {
Text("$\(viewStore.shieldedBalance.total.decimalString())")
.font(.custom(FontFamily.Zboto.regular.name, size: 40))

View File

@ -14,7 +14,7 @@ typealias OnboardingFlowViewStore = ViewStore<OnboardingFlowReducer.State, Onboa
struct OnboardingFlowReducer: ReducerProtocol {
struct State: Equatable {
enum Route: Equatable, CaseIterable {
enum Destination: Equatable, CaseIterable {
case createNewWallet
case importExistingWallet
}
@ -30,7 +30,7 @@ struct OnboardingFlowReducer: ReducerProtocol {
var steps: IdentifiedArrayOf<Step> = Self.onboardingSteps
var index = 0
var skippedAtindex: Int?
var route: Route?
var destination: Destination?
var currentStep: Step { steps[index] }
var isFinalStep: Bool { steps.count == index + 1 }
@ -51,7 +51,7 @@ struct OnboardingFlowReducer: ReducerProtocol {
case next
case back
case skip
case updateRoute(OnboardingFlowReducer.State.Route?)
case updateDestination(OnboardingFlowReducer.State.Destination?)
case createNewWallet
case importExistingWallet
case importWallet(ImportWalletReducer.Action)
@ -85,16 +85,16 @@ struct OnboardingFlowReducer: ReducerProtocol {
state.index = state.steps.count - 1
return .none
case .updateRoute(let route):
state.route = route
case .updateDestination(let destination):
state.destination = destination
return .none
case .createNewWallet:
state.route = .createNewWallet
state.destination = .createNewWallet
return .none
case .importExistingWallet:
state.route = .importExistingWallet
state.destination = .importExistingWallet
return .none
case .importWallet:
@ -142,11 +142,11 @@ extension OnboardingFlowReducer.State {
// MARK: - ViewStore
extension OnboardingFlowViewStore {
func bindingForRoute(_ route: OnboardingFlowReducer.State.Route) -> Binding<Bool> {
func bindingForDestination(_ destination: OnboardingFlowReducer.State.Destination) -> Binding<Bool> {
self.binding(
get: { $0.route == route },
get: { $0.destination == destination },
send: { isActive in
return .updateRoute(isActive ? route : nil)
return .updateDestination(isActive ? destination : nil)
}
)
}

View File

@ -47,7 +47,7 @@ struct OnboardingFooterView: View {
}
}
.navigationLinkEmpty(
isActive: viewStore.bindingForRoute(.importExistingWallet),
isActive: viewStore.bindingForDestination(.importExistingWallet),
destination: {
ImportWalletView(
store: store.scope(

View File

@ -6,7 +6,7 @@ typealias ProfileViewStore = ViewStore<ProfileReducer.State, ProfileReducer.Acti
struct ProfileReducer: ReducerProtocol {
struct State: Equatable {
enum Route {
enum Destination {
case addressDetails
case settings
}
@ -15,7 +15,7 @@ struct ProfileReducer: ReducerProtocol {
var addressDetailsState: AddressDetailsReducer.State
var appBuild = ""
var appVersion = ""
var route: Route?
var destination: Destination?
var sdkVersion = ""
var settingsState: SettingsReducer.State
}
@ -26,7 +26,7 @@ struct ProfileReducer: ReducerProtocol {
case onAppear
case onAppearFinished(String)
case settings(SettingsReducer.Action)
case updateRoute(ProfileReducer.State.Route?)
case updateDestination(ProfileReducer.State.Destination?)
}
@Dependency(\.appVersion) var appVersion
@ -60,8 +60,8 @@ struct ProfileReducer: ReducerProtocol {
case .back:
return .none
case let .updateRoute(route):
state.route = route
case let .updateDestination(destination):
state.destination = destination
return .none
case .addressDetails:
@ -88,22 +88,22 @@ extension ProfileStore {
// MARK: - ViewStore
extension ProfileViewStore {
var routeBinding: Binding<ProfileReducer.State.Route?> {
var destinationBinding: Binding<ProfileReducer.State.Destination?> {
self.binding(
get: \.route,
send: ProfileReducer.Action.updateRoute
get: \.destination,
send: ProfileReducer.Action.updateDestination
)
}
var bindingForAddressDetails: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: { $0 == .addressDetails },
embed: { $0 ? .addressDetails : nil }
)
}
var bindingForSettings: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: { $0 == .settings },
embed: { $0 ? .settings : nil }
)
@ -116,7 +116,7 @@ extension ProfileReducer.State {
static var placeholder: Self {
.init(
addressDetailsState: .placeholder,
route: nil,
destination: nil,
settingsState: .placeholder
)
}

View File

@ -17,7 +17,7 @@ struct ProfileView: View {
.padding(30)
Button(
action: { viewStore.send(.updateRoute(.addressDetails)) },
action: { viewStore.send(.updateDestination(.addressDetails)) },
label: { Text("See address details") }
)
.activeButtonStyle
@ -30,7 +30,7 @@ struct ProfileView: View {
.foregroundColor(Asset.Colors.TextField.Underline.purple.color)
Button(
action: { viewStore.send(.updateRoute(.settings)) },
action: { viewStore.send(.updateDestination(.settings)) },
label: { Text("Settings") }
)
.primaryButtonStyle

View File

@ -14,7 +14,7 @@ typealias RecoveryPhraseValidationFlowViewStore = ViewStore<RecoveryPhraseValida
struct RecoveryPhraseValidationFlowReducer: ReducerProtocol {
struct State: Equatable {
enum Route: Equatable, CaseIterable {
enum Destination: Equatable, CaseIterable {
case validation
case success
case failure
@ -27,7 +27,7 @@ struct RecoveryPhraseValidationFlowReducer: ReducerProtocol {
var missingIndices: [Int]
var missingWordChips: [PhraseChip.Kind]
var validationWords: [ValidationWord]
var route: Route?
var destination: Destination?
var isComplete: Bool {
!validationWords.isEmpty && validationWords.count == missingIndices.count
@ -40,7 +40,7 @@ struct RecoveryPhraseValidationFlowReducer: ReducerProtocol {
}
enum Action: Equatable {
case updateRoute(RecoveryPhraseValidationFlowReducer.State.Route?)
case updateDestination(RecoveryPhraseValidationFlowReducer.State.Destination?)
case reset
case move(wordChip: PhraseChip.Kind, intoGroup: Int)
case succeed
@ -60,8 +60,8 @@ struct RecoveryPhraseValidationFlowReducer: ReducerProtocol {
switch action {
case .reset:
state = randomRecoveryPhrase.random(state.phrase)
state.route = .validation
// FIXME [#186]: Resetting causes route to be nil = preamble screen, hence setting the .validation. The transition back is not animated
state.destination = .validation
// FIXME [#186]: Resetting causes destination to be nil = preamble screen, hence setting the .validation. The transition back is not animated
// though
case let .move(wordChip, group):
@ -91,20 +91,20 @@ struct RecoveryPhraseValidationFlowReducer: ReducerProtocol {
return .none
case .succeed:
state.route = .success
state.destination = .success
case .fail:
state.route = .failure
state.destination = .failure
case .failureFeedback:
feedbackGenerator.generateErrorFeedback()
case .updateRoute(let route):
guard let route = route else {
case .updateDestination(let destination):
guard let destination = destination else {
state = randomRecoveryPhrase.random(state.phrase)
return .none
}
state.route = route
state.destination = destination
case .proceedToHome:
break
@ -169,11 +169,11 @@ extension RecoveryPhrase.Group {
// MARK: - ViewStore
extension RecoveryPhraseValidationFlowViewStore {
func bindingForRoute(_ route: RecoveryPhraseValidationFlowReducer.State.Route) -> Binding<Bool> {
func bindingForDestination(_ destination: RecoveryPhraseValidationFlowReducer.State.Destination) -> Binding<Bool> {
self.binding(
get: { $0.route == route },
get: { $0.destination == destination },
send: { isActive in
return .updateRoute(isActive ? route : nil)
return .updateDestination(isActive ? destination : nil)
}
)
}
@ -182,27 +182,27 @@ extension RecoveryPhraseValidationFlowViewStore {
extension RecoveryPhraseValidationFlowViewStore {
var bindingForValidation: Binding<Bool> {
self.binding(
get: { $0.route != nil },
get: { $0.destination != nil },
send: { isActive in
return .updateRoute(isActive ? .validation : nil)
return .updateDestination(isActive ? .validation : nil)
}
)
}
var bindingForSuccess: Binding<Bool> {
self.binding(
get: { $0.route == .success },
get: { $0.destination == .success },
send: { isActive in
return .updateRoute(isActive ? .success : .validation)
return .updateDestination(isActive ? .success : .validation)
}
)
}
var bindingForFailure: Binding<Bool> {
self.binding(
get: { $0.route == .failure },
get: { $0.destination == .failure },
send: { isActive in
return .updateRoute(isActive ? .failure : .validation)
return .updateDestination(isActive ? .failure : .validation)
}
)
}
@ -221,7 +221,7 @@ extension RecoveryPhraseValidationFlowReducer.State {
.unassigned(word: "garlic")
],
validationWords: [],
route: nil
destination: nil
)
static let placeholderStep1 = RecoveryPhraseValidationFlowReducer.State(
@ -236,7 +236,7 @@ extension RecoveryPhraseValidationFlowReducer.State {
validationWords: [
.init(groupIndex: 2, word: "morning")
],
route: nil
destination: nil
)
static let placeholderStep2 = RecoveryPhraseValidationFlowReducer.State(
@ -252,7 +252,7 @@ extension RecoveryPhraseValidationFlowReducer.State {
.init(groupIndex: 2, word: "morning"),
.init(groupIndex: 0, word: "thank")
],
route: nil
destination: nil
)
static let placeholderStep3 = RecoveryPhraseValidationFlowReducer.State(
@ -269,7 +269,7 @@ extension RecoveryPhraseValidationFlowReducer.State {
.init(groupIndex: 0, word: "thank"),
.init(groupIndex: 3, word: "garlic")
],
route: nil
destination: nil
)
static let placeholderStep4 = RecoveryPhraseValidationFlowReducer.State(
@ -287,7 +287,7 @@ extension RecoveryPhraseValidationFlowReducer.State {
.init(groupIndex: 3, word: "garlic"),
.init(groupIndex: 1, word: "boil")
],
route: nil
destination: nil
)
}

View File

@ -51,7 +51,7 @@ struct RecoveryPhraseValidationFlowView: View {
}
Button(
action: { viewStore.send(.updateRoute(.validation)) },
action: { viewStore.send(.updateDestination(.validation)) },
label: { Text("recoveryPhraseTestPreamble.button.goNext") }
)
.activeButtonStyle

View File

@ -6,7 +6,7 @@ typealias SandboxViewStore = ViewStore<SandboxReducer.State, SandboxReducer.Acti
struct SandboxReducer: ReducerProtocol {
struct State: Equatable {
enum Route: Equatable, CaseIterable {
enum Destination: Equatable, CaseIterable {
case history
case send
case recoveryPhraseDisplay
@ -16,11 +16,11 @@ struct SandboxReducer: ReducerProtocol {
}
var walletEventsState: WalletEventsFlowReducer.State
var profileState: ProfileReducer.State
var route: Route?
var destination: Destination?
}
enum Action: Equatable {
case updateRoute(SandboxReducer.State.Route?)
case updateDestination(SandboxReducer.State.Destination?)
case walletEvents(WalletEventsFlowReducer.Action)
case profile(ProfileReducer.Action)
case reset
@ -28,8 +28,8 @@ struct SandboxReducer: ReducerProtocol {
func reduce(into state: inout State, action: Action) -> ComposableArchitecture.EffectTask<Action> {
switch action {
case let .updateRoute(route):
state.route = route
case let .updateDestination(destination):
state.destination = destination
return .none
case let .walletEvents(walletEventsAction):
@ -73,22 +73,22 @@ extension SandboxViewStore {
func toggleSelectedTransaction() {
let isAlreadySelected = (self.selectedTranactionID != nil)
let walletEvent = self.walletEventsState.walletEvents[5]
let newRoute = isAlreadySelected ? nil : WalletEventsFlowReducer.State.Route.showWalletEvent(walletEvent)
send(.walletEvents(.updateRoute(newRoute)))
let newDestination = isAlreadySelected ? nil : WalletEventsFlowReducer.State.Destination.showWalletEvent(walletEvent)
send(.walletEvents(.updateDestination(newDestination)))
}
var selectedTranactionID: String? {
self.walletEventsState
.route
.flatMap(/WalletEventsFlowReducer.State.Route.showWalletEvent)
.destination
.flatMap(/WalletEventsFlowReducer.State.Destination.showWalletEvent)
.map(\.id)
}
func bindingForRoute(_ route: SandboxReducer.State.Route) -> Binding<Bool> {
func bindingForDestination(_ destination: SandboxReducer.State.Destination) -> Binding<Bool> {
self.binding(
get: { $0.route == route },
get: { $0.destination == destination },
send: { isActive in
return .updateRoute(isActive ? route : nil)
return .updateDestination(isActive ? destination : nil)
}
)
}
@ -101,7 +101,7 @@ extension SandboxReducer.State {
.init(
walletEventsState: .placeHolder,
profileState: .placeholder,
route: nil
destination: nil
)
}
}
@ -112,7 +112,7 @@ extension SandboxStore {
initialState: SandboxReducer.State(
walletEventsState: .placeHolder,
profileState: .placeholder,
route: nil
destination: nil
),
reducer: SandboxReducer()
)

View File

@ -2,25 +2,25 @@ import SwiftUI
import ComposableArchitecture
struct SandboxView: View {
struct SandboxRouteValue: Identifiable {
struct SandboxDestinationValue: Identifiable {
let id: Int
let route: SandboxReducer.State.Route
let destination: SandboxReducer.State.Destination
}
let store: SandboxStore
var navigationRouteValues: [SandboxRouteValue] = SandboxReducer.State.Route.allCases
var navigationDestinationValues: [SandboxDestinationValue] = SandboxReducer.State.Destination.allCases
.enumerated()
.filter { $0.1 != .history }
.map { SandboxRouteValue(id: $0.0, route: $0.1) }
.map { SandboxDestinationValue(id: $0.0, destination: $0.1) }
var modalRoutes: [SandboxRouteValue] = SandboxReducer.State.Route.allCases
var modalDestinations: [SandboxDestinationValue] = SandboxReducer.State.Destination.allCases
.enumerated()
.filter { $0.1 == .history }
.map { SandboxRouteValue(id: $0.0, route: $0.1) }
.map { SandboxDestinationValue(id: $0.0, destination: $0.1) }
@ViewBuilder func view(for route: SandboxReducer.State.Route) -> some View {
switch route {
@ViewBuilder func view(for destination: SandboxReducer.State.Destination) -> some View {
switch destination {
case .history:
WalletEventsFlowView(store: store.historyStore())
case .send:
@ -45,23 +45,23 @@ struct SandboxView: View {
WithViewStore(store) { viewStore in
VStack {
List {
Section(header: Text("Navigation Stack Routes")) {
ForEach(navigationRouteValues) { routeValue in
Text("\(String(describing: routeValue.route))")
Section(header: Text("Navigation Stack Destinations")) {
ForEach(navigationDestinationValues) { destinationValue in
Text("\(String(describing: destinationValue.destination))")
.navigationLink(
isActive: viewStore.bindingForRoute(routeValue.route),
isActive: viewStore.bindingForDestination(destinationValue.destination),
destination: {
view(for: routeValue.route)
view(for: destinationValue.destination)
}
)
}
}
Section(header: Text("Modal Routes")) {
ForEach(modalRoutes) { routeValue in
Section(header: Text("Modal Destinations")) {
ForEach(modalDestinations) { destinationValue in
Button(
action: { viewStore.send(.updateRoute(routeValue.route)) },
label: { Text("\(String(describing: routeValue.route))") }
action: { viewStore.send(.updateDestination(destinationValue.destination)) },
label: { Text("\(String(describing: destinationValue.destination))") }
)
}
}
@ -80,13 +80,13 @@ struct SandboxView: View {
}
}
.fullScreenCover(
isPresented: viewStore.bindingForRoute(.history),
isPresented: viewStore.bindingForDestination(.history),
content: {
NavigationView {
WalletEventsFlowView(store: store.historyStore())
.toolbar {
ToolbarItem {
Button("Done") { viewStore.send(.updateRoute(nil)) }
Button("Done") { viewStore.send(.updateDestination(nil)) }
}
}
}

View File

@ -16,7 +16,7 @@ struct SendFlowReducer: ReducerProtocol {
private enum SyncStatusUpdatesID {}
struct State: Equatable {
enum Route: Equatable {
enum Destination: Equatable {
case confirmation
case inProgress
case success
@ -27,7 +27,7 @@ struct SendFlowReducer: ReducerProtocol {
var addMemoState: Bool
var isSendingTransaction = false
var memoState: MultiLineTextFieldReducer.State
var route: Route?
var destination: Destination?
var shieldedBalance = WalletBalance.zero
var transactionAddressInputState: TransactionAddressTextFieldReducer.State
var transactionAmountInputState: TransactionAmountTextFieldReducer.State
@ -83,7 +83,7 @@ struct SendFlowReducer: ReducerProtocol {
case synchronizerStateChanged(SDKSynchronizerState)
case transactionAddressInput(TransactionAddressTextFieldReducer.Action)
case transactionAmountInput(TransactionAmountTextFieldReducer.Action)
case updateRoute(SendFlowReducer.State.Route?)
case updateDestination(SendFlowReducer.State.Destination?)
}
@Dependency(\.derivationTool) var derivationTool
@ -115,27 +115,27 @@ struct SendFlowReducer: ReducerProtocol {
case .addMemo:
return .none
case .updateRoute(.done):
state.route = nil
case .updateDestination(.done):
state.destination = nil
state.memoState.text = ""
state.transactionAmountInputState.textFieldState.text = ""
state.transactionAmountInputState.amount = 0
state.transactionAddressInputState.textFieldState.text = ""
return .none
case .updateRoute(.failure):
state.route = .failure
case .updateDestination(.failure):
state.destination = .failure
state.isSendingTransaction = false
return .none
case .updateRoute(.confirmation):
case .updateDestination(.confirmation):
state.amount = Zatoshi(state.transactionAmountInputState.amount)
state.address = state.transactionAddressInputState.textFieldState.text
state.route = .confirmation
state.destination = .confirmation
return .none
case let .updateRoute(route):
state.route = route
case let .updateDestination(destination):
state.destination = destination
return .none
case .sendConfirmationPressed:
@ -169,20 +169,20 @@ struct SendFlowReducer: ReducerProtocol {
.eraseToEffect()
return .concatenate(
Effect(value: .updateRoute(.inProgress)),
Effect(value: .updateDestination(.inProgress)),
sendTransActionEffect
)
} catch {
return Effect(value: .updateRoute(.failure))
return Effect(value: .updateDestination(.failure))
}
case .sendTransactionResult(let result):
state.isSendingTransaction = false
do {
_ = try result.get()
return Effect(value: .updateRoute(.success))
return Effect(value: .updateDestination(.success))
} catch {
return Effect(value: .updateRoute(.failure))
return Effect(value: .updateDestination(.failure))
}
case .transactionAmountInput:
@ -239,47 +239,47 @@ extension SendFlowStore {
// MARK: - ViewStore
extension SendFlowViewStore {
var routeBinding: Binding<SendFlowReducer.State.Route?> {
var destinationBinding: Binding<SendFlowReducer.State.Destination?> {
self.binding(
get: \.route,
send: SendFlowReducer.Action.updateRoute
get: \.destination,
send: SendFlowReducer.Action.updateDestination
)
}
var bindingForConfirmation: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: {
$0 == .confirmation ||
$0 == .inProgress ||
$0 == .success ||
$0 == .failure
},
embed: { $0 ? SendFlowReducer.State.Route.confirmation : nil }
embed: { $0 ? SendFlowReducer.State.Destination.confirmation : nil }
)
}
var bindingForInProgress: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: {
$0 == .inProgress ||
$0 == .success ||
$0 == .failure
},
embed: { $0 ? SendFlowReducer.State.Route.inProgress : SendFlowReducer.State.Route.confirmation }
embed: { $0 ? SendFlowReducer.State.Destination.inProgress : SendFlowReducer.State.Destination.confirmation }
)
}
var bindingForSuccess: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: { $0 == .success },
embed: { _ in SendFlowReducer.State.Route.success }
embed: { _ in SendFlowReducer.State.Destination.success }
)
}
var bindingForFailure: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: { $0 == .failure },
embed: { _ in SendFlowReducer.State.Route.failure }
embed: { _ in SendFlowReducer.State.Destination.failure }
)
}
}
@ -291,7 +291,7 @@ extension SendFlowReducer.State {
.init(
addMemoState: true,
memoState: .placeholder,
route: nil,
destination: nil,
transactionAddressInputState: .placeholder,
transactionAmountInputState: .amount
)
@ -301,7 +301,7 @@ extension SendFlowReducer.State {
.init(
addMemoState: true,
memoState: .placeholder,
route: nil,
destination: nil,
transactionAddressInputState: .placeholder,
transactionAmountInputState: .placeholder
)

View File

@ -36,7 +36,7 @@ struct SendFLowView_Previews: PreviewProvider {
initialState: .init(
addMemoState: true,
memoState: .placeholder,
route: nil,
destination: nil,
transactionAddressInputState: .placeholder,
transactionAmountInputState: .placeholder
),

View File

@ -71,7 +71,7 @@ struct CreateTransaction: View {
.padding()
Button(
action: { viewStore.send(.updateRoute(.confirmation)) },
action: { viewStore.send(.updateDestination(.confirmation)) },
label: { Text("Send") }
)
.activeButtonStyle

View File

@ -10,7 +10,7 @@ struct TransactionFailed: View {
Button(
action: {
viewStore.send(.updateRoute(.done))
viewStore.send(.updateDestination(.done))
},
label: { Text("Close") }
)

View File

@ -10,7 +10,7 @@ struct TransactionSent: View {
Button(
action: {
viewStore.send(.updateRoute(.done))
viewStore.send(.updateDestination(.done))
},
label: { Text("Close") }
)

View File

@ -6,13 +6,13 @@ typealias SettingsViewStore = ViewStore<SettingsReducer.State, SettingsReducer.A
struct SettingsReducer: ReducerProtocol {
struct State: Equatable {
enum Route {
enum Destination {
case backupPhrase
}
var phraseDisplayState: RecoveryPhraseDisplayReducer.State
var rescanDialog: ConfirmationDialogState<SettingsReducer.Action>?
var route: Route?
var destination: Destination?
}
enum Action: Equatable {
@ -23,7 +23,7 @@ struct SettingsReducer: ReducerProtocol {
case phraseDisplay(RecoveryPhraseDisplayReducer.Action)
case quickRescan
case rescanBlockchain
case updateRoute(SettingsReducer.State.Route?)
case updateDestination(SettingsReducer.State.Destination?)
}
@Dependency(\.localAuthentication) var localAuthentication
@ -47,7 +47,7 @@ struct SettingsReducer: ReducerProtocol {
let phraseWords = try mnemonic.asWords(storedWallet.seedPhrase)
let recoveryPhrase = RecoveryPhrase(words: phraseWords)
state.phraseDisplayState.phrase = recoveryPhrase
return Effect(value: .updateRoute(.backupPhrase))
return Effect(value: .updateDestination(.backupPhrase))
} catch {
// TODO [#201]: - merge with issue 201 (https://github.com/zcash/secant-ios-wallet/issues/201) and its Error States
return .none
@ -70,11 +70,11 @@ struct SettingsReducer: ReducerProtocol {
return .none
case .phraseDisplay:
state.route = nil
state.destination = nil
return .none
case .updateRoute(let route):
state.route = route
case .updateDestination(let destination):
state.destination = destination
return .none
}
}
@ -88,15 +88,15 @@ struct SettingsReducer: ReducerProtocol {
// MARK: - ViewStore
extension SettingsViewStore {
var routeBinding: Binding<SettingsReducer.State.Route?> {
var destinationBinding: Binding<SettingsReducer.State.Destination?> {
self.binding(
get: \.route,
send: SettingsReducer.Action.updateRoute
get: \.destination,
send: SettingsReducer.Action.updateDestination
)
}
var bindingForBackupPhrase: Binding<Bool> {
self.routeBinding.map(
self.destinationBinding.map(
extract: { $0 == .backupPhrase },
embed: { $0 ? .backupPhrase : nil }
)

View File

@ -9,13 +9,13 @@ struct WalletEventsFlowReducer: ReducerProtocol {
private enum CancelId {}
struct State: Equatable {
enum Route: Equatable {
enum Destination: Equatable {
case latest
case all
case showWalletEvent(WalletEvent)
}
var route: Route?
var destination: Destination?
@BindableState var alert: AlertState<WalletEventsFlowReducer.Action>?
var latestMinedHeight: BlockHeight?
@ -31,7 +31,7 @@ struct WalletEventsFlowReducer: ReducerProtocol {
case onAppear
case onDisappear
case openBlockExplorer(URL?)
case updateRoute(WalletEventsFlowReducer.State.Route?)
case updateDestination(WalletEventsFlowReducer.State.Destination?)
case replyTo(String)
case synchronizerStateChanged(SDKSynchronizerState)
case updateWalletEvents([WalletEvent])
@ -76,14 +76,14 @@ struct WalletEventsFlowReducer: ReducerProtocol {
state.walletEvents = IdentifiedArrayOf(uniqueElements: sortedWalletEvents)
return .none
case .updateRoute(.showWalletEvent(let walletEvent)):
case .updateDestination(.showWalletEvent(let walletEvent)):
state.selectedWalletEvent = walletEvent
state.route = .showWalletEvent(walletEvent)
state.destination = .showWalletEvent(walletEvent)
return .none
case .updateRoute(let route):
state.route = route
if route == nil {
case .updateDestination(let destination):
state.destination = destination
if destination == nil {
state.selectedWalletEvent = nil
}
return .none
@ -130,7 +130,7 @@ struct WalletEventsFlowReducer: ReducerProtocol {
// MARK: - ViewStore
extension WalletEventsFlowViewStore {
private typealias Route = WalletEventsFlowReducer.State.Route
private typealias Destination = WalletEventsFlowReducer.State.Destination
func bindingForSelectedWalletEvent(_ walletEvent: WalletEvent?) -> Binding<Bool> {
self.binding(
@ -139,14 +139,14 @@ extension WalletEventsFlowViewStore {
return false
}
return $0.route.map(/WalletEventsFlowReducer.State.Route.showWalletEvent) == walletEvent
return $0.destination.map(/WalletEventsFlowReducer.State.Destination.showWalletEvent) == walletEvent
},
send: { isActive in
guard let walletEvent = walletEvent else {
return WalletEventsFlowReducer.Action.updateRoute(nil)
return WalletEventsFlowReducer.Action.updateDestination(nil)
}
return WalletEventsFlowReducer.Action.updateRoute( isActive ? WalletEventsFlowReducer.State.Route.showWalletEvent(walletEvent) : nil)
return WalletEventsFlowReducer.Action.updateDestination( isActive ? WalletEventsFlowReducer.State.Destination.showWalletEvent(walletEvent) : nil)
}
)
}

View File

@ -42,7 +42,7 @@ extension WalletEventsFlowView {
ForEach(viewStore.walletEvents) { walletEvent in
walletEvent.rowView(viewStore)
.onTapGesture {
viewStore.send(.updateRoute(.showWalletEvent(walletEvent)))
viewStore.send(.updateDestination(.showWalletEvent(walletEvent)))
}
.listRowInsets(EdgeInsets())
.foregroundColor(Asset.Colors.Text.body.color)
@ -54,7 +54,7 @@ extension WalletEventsFlowView {
HStack(spacing: 0) {
VStack {
Button {
viewStore.send(.updateRoute(.latest))
viewStore.send(.updateDestination(.latest))
} label: {
Text("Latest")
.font(.custom(FontFamily.Rubik.regular.name, size: 18))
@ -70,7 +70,7 @@ extension WalletEventsFlowView {
VStack {
Button {
viewStore.send(.updateRoute(.all))
viewStore.send(.updateDestination(.all))
} label: {
Text("All")
.font(.custom(FontFamily.Rubik.regular.name, size: 18))

View File

@ -34,7 +34,7 @@ class AppInitializationTests: XCTestCase {
validationWords: [
.init(groupIndex: 2, word: "dizzy")
],
route: nil
destination: nil
)
let recoveryPhraseRandomizer = RecoveryPhraseRandomizerClient(
@ -122,9 +122,9 @@ class AppInitializationTests: XCTestCase {
await testScheduler.advance(by: 3.00)
// ad 5.
await store.receive(.updateRoute(.phraseDisplay)) { state in
state.prevRoute = .welcome
state.internalRoute = .phraseDisplay
await store.receive(.updateDestination(.phraseDisplay)) { state in
state.prevDestination = .welcome
state.internalDestination = .phraseDisplay
}
}
@ -191,9 +191,9 @@ class AppInitializationTests: XCTestCase {
store.receive(.respondToWalletInitializationState(.uninitialized))
// ad 3.
store.receive(.updateRoute(.onboarding)) { state in
state.prevRoute = .welcome
state.internalRoute = .onboarding
store.receive(.updateDestination(.onboarding)) { state in
state.prevDestination = .welcome
state.internalDestination = .onboarding
}
}
}

View File

@ -70,8 +70,8 @@ class AppTests: XCTestCase {
Self.testScheduler.advance(by: 3)
store.receive(.updateRoute(.onboarding)) {
$0.route = .onboarding
store.receive(.updateDestination(.onboarding)) {
$0.destination = .onboarding
$0.appInitializationState = .uninitialized
}
}

View File

@ -12,9 +12,9 @@ import ZcashLightClientKit
@MainActor
class DeeplinkTests: XCTestCase {
func testActionDeeplinkHome_SameRouteLevel() throws {
func testActionDeeplinkHome_SameDestinationLevel() throws {
var appState = AppReducer.State.placeholder
appState.route = .welcome
appState.destination = .welcome
let store = TestStore(
initialState: appState,
@ -22,14 +22,14 @@ class DeeplinkTests: XCTestCase {
)
store.send(.deeplinkHome) { state in
state.route = .home
state.destination = .home
}
}
func testActionDeeplinkHome_GeetingBack() throws {
var appState = AppReducer.State.placeholder
appState.route = .home
appState.homeState.route = .send
appState.destination = .home
appState.homeState.destination = .send
let store = TestStore(
initialState: appState,
@ -37,14 +37,14 @@ class DeeplinkTests: XCTestCase {
)
store.send(.deeplinkHome) { state in
state.route = .home
state.homeState.route = nil
state.destination = .home
state.homeState.destination = nil
}
}
func testActionDeeplinkSend() throws {
var appState = AppReducer.State.placeholder
appState.route = .welcome
appState.destination = .welcome
let store = TestStore(
initialState: appState,
@ -56,8 +56,8 @@ class DeeplinkTests: XCTestCase {
let memo = "testing some memo"
store.send(.deeplinkSend(amount, address, memo)) { state in
state.route = .home
state.homeState.route = .send
state.destination = .home
state.homeState.destination = .send
state.homeState.sendState.amount = amount
state.homeState.sendState.address = address
state.homeState.sendState.memoState.text = memo
@ -71,12 +71,12 @@ class DeeplinkTests: XCTestCase {
let result = try Deeplink().resolveDeeplinkURL(url, isValidZcashAddress: { _ in false })
XCTAssertEqual(result, Deeplink.Route.home)
XCTAssertEqual(result, Deeplink.Destination.home)
}
func testDeeplinkRequest_Received_Home() async throws {
var appState = AppReducer.State.placeholder
appState.route = .welcome
appState.destination = .welcome
appState.appInitializationState = .initialized
let store = TestStore(
@ -84,7 +84,7 @@ class DeeplinkTests: XCTestCase {
reducer: AppReducer()
) { dependencies in
dependencies.deeplink = DeeplinkClient(
resolveDeeplinkURL: { _, _ in Deeplink.Route.home }
resolveDeeplinkURL: { _, _ in Deeplink.Destination.home }
)
let synchronizer = NoopSDKSynchronizer()
synchronizer.updateStateChanged(.synced)
@ -98,7 +98,7 @@ class DeeplinkTests: XCTestCase {
_ = await store.send(.deeplink(url))
await store.receive(.deeplinkHome) { state in
state.route = .home
state.destination = .home
}
await store.finish()
@ -111,7 +111,7 @@ class DeeplinkTests: XCTestCase {
let result = try Deeplink().resolveDeeplinkURL(url, isValidZcashAddress: { _ in false })
XCTAssertEqual(result, Deeplink.Route.send(amount: 123_000_000, address: "address", memo: "some text"))
XCTAssertEqual(result, Deeplink.Destination.send(amount: 123_000_000, address: "address", memo: "some text"))
}
func testDeeplinkRequest_Received_Send() async throws {
@ -119,7 +119,7 @@ class DeeplinkTests: XCTestCase {
synchronizer.updateStateChanged(.synced)
var appState = AppReducer.State.placeholder
appState.route = .welcome
appState.destination = .welcome
appState.appInitializationState = .initialized
let store = TestStore(
@ -127,7 +127,7 @@ class DeeplinkTests: XCTestCase {
reducer: AppReducer()
) { dependencies in
dependencies.deeplink = DeeplinkClient(
resolveDeeplinkURL: { _, _ in Deeplink.Route.send(amount: 123_000_000, address: "address", memo: "some text") }
resolveDeeplinkURL: { _, _ in Deeplink.Destination.send(amount: 123_000_000, address: "address", memo: "some text") }
)
dependencies.sdkSynchronizer = synchronizer
}
@ -143,8 +143,8 @@ class DeeplinkTests: XCTestCase {
let memo = "some text"
await store.receive(.deeplinkSend(amount, address, memo)) { state in
state.route = .home
state.homeState.route = .send
state.destination = .home
state.homeState.destination = .send
state.homeState.sendState.amount = amount
state.homeState.sendState.address = address
state.homeState.sendState.memoState.text = memo

View File

@ -85,8 +85,8 @@ class HomeTests: XCTestCase {
reducer: HomeReducer()
)
store.send(.walletEvents(.updateRoute(.all))) { state in
state.walletEventsState.route = .all
store.send(.walletEvents(.updateDestination(.all))) { state in
state.walletEventsState.destination = .all
}
store.receive(.updateDrawer(.full)) { state in
@ -113,8 +113,8 @@ class HomeTests: XCTestCase {
reducer: HomeReducer()
)
store.send(.walletEvents(.updateRoute(.latest))) { state in
state.walletEventsState.route = .latest
store.send(.walletEvents(.updateDestination(.latest))) { state in
state.walletEventsState.destination = .latest
}
store.receive(.updateDrawer(.partial)) { state in
@ -138,7 +138,7 @@ class HomeTests: XCTestCase {
}
// expected side effects as a result of .onAppear registration
store.receive(.updateRoute(nil))
store.receive(.updateDestination(nil))
store.receive(.synchronizerStateChanged(.unknown))
store.receive(.updateSynchronizerStatus)
@ -160,8 +160,8 @@ class HomeTests: XCTestCase {
}
// expected side effects as a result of .onAppear registration
store.receive(.updateRoute(.notEnoughFreeDiskSpace)) { state in
state.route = .notEnoughFreeDiskSpace
store.receive(.updateDestination(.notEnoughFreeDiskSpace)) { state in
state.destination = .notEnoughFreeDiskSpace
}
// long-living (cancelable) effects need to be properly canceled.
@ -171,7 +171,7 @@ class HomeTests: XCTestCase {
@MainActor func testQuickRescan_ResetToHomeScreen() async throws {
let homeState = HomeReducer.State(
route: .profile,
destination: .profile,
balanceBreakdownState: .placeholder,
drawerOverlay: .full,
profileState: .placeholder,
@ -189,7 +189,7 @@ class HomeTests: XCTestCase {
)
_ = await store.send(.profile(.settings(.quickRescan))) { state in
state.route = nil
state.destination = nil
}
await store.receive(.rewindDone(true, .quickRescan))
@ -197,7 +197,7 @@ class HomeTests: XCTestCase {
@MainActor func testFullRescan_ResetToHomeScreen() async throws {
let homeState = HomeReducer.State(
route: .profile,
destination: .profile,
balanceBreakdownState: .placeholder,
drawerOverlay: .full,
profileState: .placeholder,
@ -215,7 +215,7 @@ class HomeTests: XCTestCase {
)
_ = await store.send(.profile(.settings(.fullRescan))) { state in
state.route = nil
state.destination = nil
}
await store.receive(.rewindDone(true, .fullRescan))

View File

@ -321,7 +321,7 @@ class RecoveryPhraseValidationTests: XCTestCase {
store.receive(.succeed) {
XCTAssertTrue($0.isComplete)
$0.route = .success
$0.destination = .success
}
}
@ -394,7 +394,7 @@ class RecoveryPhraseValidationTests: XCTestCase {
store.receive(.failureFeedback)
store.receive(.fail) {
$0.route = .failure
$0.destination = .failure
XCTAssertFalse($0.isValid)
}
}
@ -612,7 +612,7 @@ class RecoveryPhraseValidationTests: XCTestCase {
missingIndices: missingIndices,
missingWordChips: phrase.words(fromMissingIndices: missingIndices),
validationWords: completion,
route: nil
destination: nil
)
XCTAssertTrue(result.isValid)
@ -651,7 +651,7 @@ class RecoveryPhraseValidationTests: XCTestCase {
missingIndices: missingIndices,
missingWordChips: phrase.words(fromMissingIndices: missingIndices),
validationWords: completion,
route: nil
destination: nil
)
XCTAssertFalse(result.isValid)

View File

@ -77,8 +77,8 @@ class SendTests: XCTestCase {
)
// first it's expected that progress screen is showed
await store.receive(.updateRoute(.inProgress)) { state in
state.route = .inProgress
await store.receive(.updateDestination(.inProgress)) { state in
state.destination = .inProgress
}
// check the success transaction to be received back
@ -89,8 +89,8 @@ class SendTests: XCTestCase {
}
// all went well, the success screen is triggered
await store.receive(.updateRoute(.success)) { state in
state.route = .success
await store.receive(.updateDestination(.success)) { state in
state.destination = .success
}
}
@ -145,8 +145,8 @@ class SendTests: XCTestCase {
)
// first it's expected that progress screen is showed
await store.receive(.updateRoute(.inProgress)) { state in
state.route = .inProgress
await store.receive(.updateDestination(.inProgress)) { state in
state.destination = .inProgress
}
// check the success transaction to be received back
@ -157,8 +157,8 @@ class SendTests: XCTestCase {
}
// all went well, the success screen is triggered
await store.receive(.updateRoute(.success)) { state in
state.route = .success
await store.receive(.updateDestination(.success)) { state in
state.destination = .success
}
}
@ -198,8 +198,8 @@ class SendTests: XCTestCase {
await testScheduler.advance(by: 0.01)
// first it's expected that progress screen is showed
await store.receive(.updateRoute(.inProgress)) { state in
state.route = .inProgress
await store.receive(.updateDestination(.inProgress)) { state in
state.destination = .inProgress
}
// check the failure transaction to be received back
@ -210,8 +210,8 @@ class SendTests: XCTestCase {
}
// the failure screen is triggered as expected
await store.receive(.updateRoute(.failure)) { state in
state.route = .failure
await store.receive(.updateDestination(.failure)) { state in
state.destination = .failure
}
}

View File

@ -59,8 +59,8 @@ class SettingsTests: XCTestCase {
await store.receive(.backupWallet) { state in
state.phraseDisplayState.phrase = RecoveryPhrase(words: mnemonic.components(separatedBy: " "))
}
await store.receive(.updateRoute(.backupPhrase)) { state in
state.route = .backupPhrase
await store.receive(.updateDestination(.backupPhrase)) { state in
state.destination = .backupPhrase
}
}
@ -109,7 +109,7 @@ class SettingsTests: XCTestCase {
.cancel(TextState("Cancel"))
]
),
route: nil
destination: nil
),
reducer: SettingsReducer()
)
@ -132,7 +132,7 @@ class SettingsTests: XCTestCase {
.cancel(TextState("Cancel"))
]
),
route: nil
destination: nil
),
reducer: SettingsReducer()
)
@ -155,7 +155,7 @@ class SettingsTests: XCTestCase {
.cancel(TextState("Cancel"))
]
),
route: nil
destination: nil
),
reducer: SettingsReducer()
)

View File

@ -97,7 +97,7 @@ class WalletEventsSnapshotTests: XCTestCase {
reducer: HomeReducer()
)
ViewStore(store).send(.walletEvents(.updateRoute(.showWalletEvent(walletEvent))))
ViewStore(store).send(.walletEvents(.updateDestination(.showWalletEvent(walletEvent))))
let walletEventsStore = WalletEventsFlowStore(
initialState: .placeHolder,
reducer: WalletEventsFlowReducer()
@ -144,7 +144,7 @@ class WalletEventsSnapshotTests: XCTestCase {
reducer: HomeReducer()
)
ViewStore(store).send(.walletEvents(.updateRoute(.showWalletEvent(walletEvent))))
ViewStore(store).send(.walletEvents(.updateDestination(.showWalletEvent(walletEvent))))
let walletEventsStore = WalletEventsFlowStore(
initialState: .placeHolder,
reducer: WalletEventsFlowReducer()
@ -196,7 +196,7 @@ class WalletEventsSnapshotTests: XCTestCase {
walletEvents: .placeholder
)
ViewStore(store).send(.walletEvents(.updateRoute(.showWalletEvent(walletEvent))))
ViewStore(store).send(.walletEvents(.updateDestination(.showWalletEvent(walletEvent))))
let walletEventsStore = WalletEventsFlowStore(
initialState: walletEventsState,
reducer: WalletEventsFlowReducer()
@ -244,7 +244,7 @@ class WalletEventsSnapshotTests: XCTestCase {
reducer: HomeReducer()
)
ViewStore(store).send(.walletEvents(.updateRoute(.showWalletEvent(walletEvent))))
ViewStore(store).send(.walletEvents(.updateDestination(.showWalletEvent(walletEvent))))
let walletEventsStore = WalletEventsFlowStore(
initialState: .placeHolder,
reducer: WalletEventsFlowReducer()

View File

@ -16,7 +16,7 @@ class WalletEventsTests: XCTestCase {
func testSynchronizerSubscription() throws {
let store = TestStore(
initialState: WalletEventsFlowReducer.State(
route: .latest,
destination: .latest,
isScrollable: true,
walletEvents: []
),
@ -71,7 +71,7 @@ class WalletEventsTests: XCTestCase {
let store = TestStore(
initialState: WalletEventsFlowReducer.State(
route: .latest,
destination: .latest,
isScrollable: true,
walletEvents: identifiedWalletEvents
),
@ -103,7 +103,7 @@ class WalletEventsTests: XCTestCase {
let store = TestStore(
initialState: WalletEventsFlowReducer.State(
route: .latest,
destination: .latest,
isScrollable: true,
walletEvents: []
),