Skip to content

Commit 3108a8a

Browse files
authored
Fix refresh for alternatives routes (#9382)
1 parent 05f1c59 commit 3108a8a

File tree

17 files changed

+369
-59
lines changed

17 files changed

+369
-59
lines changed

CHANGELOG.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,17 @@
11
# Changes to the Mapbox Navigation SDK for iOS
22

3+
## 3.10.0-rc.1
4+
5+
### Packaging
6+
7+
* MapboxNavigationCore now requires [MapboxMaps v11.13.0-rc.1](https://github.com/mapbox/mapbox-maps-ios/releases/tag/v11.13.0-rc.1)
8+
* MapboxNavigationCore now requires [MapboxNavigationNative v324.13.0-rc.1](https://github.com/mapbox/mapbox-navigation-native-ios/releases/tag/v324.13.0-rc.1)
9+
10+
### Routing
11+
12+
* Fixed re-enabling route refresh after leg change.
13+
* Fixed route refresh of alternative routes.
14+
315
## 3.10.0-beta.1
416

517
### Packaging

Package.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33

44
import PackageDescription
55

6-
let (navNativeVersion, navNativeChecksum, navNativeRevision) = ("324.13.0-beta.1", "6de7358d694f7bdc1f120478c207e94a01971f2cb5cba81262d597bbb694f712", "15464003bfad533303ad25d2e1c7860cfaf47abe")
7-
let mapsVersion: Version = "11.13.0-beta.1"
6+
let (navNativeVersion, navNativeChecksum, navNativeRevision) = ("324.13.0-rc.1", "0a8e40363cea0b41476c0da9c9d2c4614b3460ff06f6aa79396bfc786aac54ee", "398baac89e32466f799b350b2d560e843452ed04")
7+
let mapsVersion: Version = "11.13.0-rc.1"
88

99
let package = Package(
1010
name: "MapboxNavigation",

Sources/MapboxNavigationCore/MapboxNavigationProvider.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -114,7 +114,8 @@ public final class MapboxNavigationProvider {
114114
///
115115
/// It is intended to be used when creating off-line tile packs.
116116
public func getLatestNavigationTilesetDescriptor() -> TilesetDescriptor {
117-
TilesetDescriptorFactory.getLatestForCache(nativeHandlersFactory.cacheHandle)
117+
// TODO: (NAVIOS-2231) Add support for adas tiles
118+
TilesetDescriptorFactory.getLatestForCache(nativeHandlersFactory.cacheHandle, includeAdas: false)
118119
}
119120

120121
// MARK: - Instance Lifecycle control

Sources/MapboxNavigationCore/Navigator/Internals/CoreNavigator/CoreNavigator.swift

Lines changed: 24 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -296,15 +296,24 @@ final class NativeNavigator: CoreNavigator, @unchecked Sendable {
296296
return
297297
}
298298

299-
let refreshObserver = NavigatorRouteRefreshObserver(refreshCallback: { [weak self] in
300-
guard let self else { return nil }
299+
let refreshObserver = NavigatorRouteRefreshObserver(
300+
refreshCallback: { [weak self] routeIdPrefix, routeIndex, _ in
301+
guard let self else { return nil }
301302

302-
guard let primaryRoute = navigator.native.getPrimaryRoute() else { return nil }
303-
return RouteRefreshResult(
304-
updatedRoute: primaryRoute,
305-
alternativeRoutes: navigator.native.getAlternativeRoutes()
306-
)
307-
})
303+
guard let primaryRoute = navigator.native.getPrimaryRoute() else { return nil }
304+
let alternativeRoutes = navigator.native.getAlternativeRoutes()
305+
306+
if primaryRoute.matching(routeIdPrefix: routeIdPrefix, routeIndex: routeIndex) {
307+
return .mainRoute(primaryRoute)
308+
}
309+
if let refreshedAlternative = alternativeRoutes.first(where: {
310+
$0.route.matching(routeIdPrefix: routeIdPrefix, routeIndex: routeIndex)
311+
}) {
312+
return .alternativeRoute(alternative: refreshedAlternative)
313+
}
314+
return nil
315+
}
316+
)
308317
navigator.native.addRouteRefreshObserver(for: refreshObserver)
309318
navigator.native.startRoutesRefresh(
310319
forDefaultRefreshPeriodMs: UInt64(refreshPeriod * 1000),
@@ -512,3 +521,10 @@ enum NativeNavigatorError: Swift.Error {
512521
case failedToUpdateRoutes(reason: String)
513522
case failedToUpdateAlternativeRoutes(reason: String)
514523
}
524+
525+
extension RouteInterface {
526+
fileprivate func matching(routeIdPrefix: String, routeIndex: UInt32) -> Bool {
527+
// TODO: (NN-3674) use full routeId instead of just prefix.
528+
getRouteId().starts(with: routeIdPrefix) && getRouteIndex() == routeIndex
529+
}
530+
}

Sources/MapboxNavigationCore/Navigator/Internals/CoreNavigator/NavigatorRouteRefreshObserver.swift

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,13 @@ import _MapboxNavigationHelpers
22
import Foundation
33
@preconcurrency import MapboxNavigationNative
44

5-
struct RouteRefreshResult: @unchecked Sendable {
6-
let updatedRoute: RouteInterface
7-
let alternativeRoutes: [RouteAlternative]
5+
enum RouteRefreshResult: @unchecked Sendable {
6+
case mainRoute(RouteInterface)
7+
case alternativeRoute(alternative: RouteAlternative)
88
}
99

1010
class NavigatorRouteRefreshObserver: RouteRefreshObserver, @unchecked Sendable {
11-
typealias RefreshCallback = () -> RouteRefreshResult?
11+
typealias RefreshCallback = (String, UInt32, UInt32) -> RouteRefreshResult?
1212
private var refreshCallback: RefreshCallback
1313

1414
init(refreshCallback: @escaping RefreshCallback) {
@@ -22,7 +22,7 @@ class NavigatorRouteRefreshObserver: RouteRefreshObserver, @unchecked Sendable {
2222
legIndex: UInt32,
2323
routeGeometryIndex: UInt32
2424
) {
25-
guard let routeRefreshResult = refreshCallback() else {
25+
guard let routeRefreshResult = refreshCallback(routeId, routeIndex, legIndex) else {
2626
return
2727
}
2828

Sources/MapboxNavigationCore/Navigator/MapboxNavigator.swift

Lines changed: 36 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1290,32 +1290,45 @@ final class MapboxNavigator: @unchecked Sendable {
12901290
return
12911291
}
12921292

1293-
var newMainRoute = currentNavigationRoutes.mainRoute
1294-
let isMainRouteUpdate = refreshRouteResult.updatedRoute.getRouteId() ==
1295-
currentNavigationRoutes.mainRoute.routeId.rawValue
1296-
if isMainRouteUpdate {
1297-
guard let updatedMainRoute = await NavigationRoute(nativeRoute: refreshRouteResult.updatedRoute)
1298-
else { return }
1299-
newMainRoute = updatedMainRoute
1300-
}
13011293
let event = RefreshingStatus.Events.Refreshing()
13021294
await send(RefreshingStatus(event: event))
13031295

1304-
var refreshedNavigationRoutes = await NavigationRoutes(
1305-
mainRoute: newMainRoute,
1306-
alternativeRoutes: await AlternativeRoute.fromNative(
1307-
alternativeRoutes: refreshRouteResult.alternativeRoutes,
1308-
relateveTo: newMainRoute
1309-
)
1310-
)
1296+
var refreshedNavigationRoutes = currentNavigationRoutes
1297+
1298+
switch refreshRouteResult {
1299+
case .mainRoute(let refreshedMainRoute):
1300+
guard let updatedMainRoute = await NavigationRoute(nativeRoute: refreshedMainRoute)
1301+
else {
1302+
await sendFailedToRefreshEvent()
1303+
return
1304+
}
1305+
refreshedNavigationRoutes.mainRoute = updatedMainRoute
1306+
1307+
case .alternativeRoute(alternative: let refreshedAlternative):
1308+
guard let newAlternative = await AlternativeRoute(
1309+
mainRoute: currentNavigationRoutes.mainRoute.route,
1310+
alternativeRoute: refreshedAlternative
1311+
), let index = currentNavigationRoutes.allAlternativeRoutesWithIgnored
1312+
.firstIndex(where: { $0.nativeRoute.getRouteId() == refreshedAlternative.route.getRouteId() })
1313+
else {
1314+
await sendFailedToRefreshEvent()
1315+
return
1316+
}
1317+
refreshedNavigationRoutes.allAlternativeRoutesWithIgnored[index] = newAlternative
1318+
}
1319+
13111320
if let status = self.navigator.mostRecentNavigationStatus {
13121321
refreshedNavigationRoutes.updateForkPointPassed(with: status)
13131322
}
13141323
let routeProgress = await state.privateRouteProgress
1324+
let refreshedMainLegIndex: Int? = switch refreshRouteResult {
1325+
case .mainRoute: Int(legIndex)
1326+
case .alternativeRoute: nil
1327+
}
13151328
let updatedRouteProgress = routeProgress?.refreshingRoute(
13161329
with: refreshedNavigationRoutes,
1317-
legIndex: Int(legIndex),
1318-
legShapeIndex: 0, // TODO: NN should provide this value in `MBNNRouteRefreshObserver`
1330+
refreshedMainLegIndex: refreshedMainLegIndex,
1331+
// TODO: Pass legShapeIndex. NN should provide this value in `MBNNRouteRefreshObserver`
13191332
congestionConfiguration: configuration.congestionConfig
13201333
)
13211334
await state.update(privateRouteProgress: updatedRouteProgress)
@@ -1329,6 +1342,12 @@ final class MapboxNavigator: @unchecked Sendable {
13291342
}
13301343
}
13311344

1345+
private func sendFailedToRefreshEvent() async {
1346+
Log.warning("Failed to refresh the routes", category: .navigation)
1347+
let error = RefreshingStatus.Events.FailedToRefresh()
1348+
await send(RefreshingStatus(event: error))
1349+
}
1350+
13321351
func didFailToRefreshAnnotations(_ notification: Notification) {
13331352
guard let refreshRouteFailure = notification
13341353
.userInfo?[NativeNavigator.NotificationUserInfoKey.refreshRequestErrorKey] as? RouteRefreshError,

Sources/MapboxNavigationCore/Navigator/Navigator.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -291,6 +291,8 @@ public struct RefreshingStatus: Equatable, Sendable {
291291
public struct Refreshing: RefreshingEvent, Sendable {}
292292
/// The route has been refreshed.
293293
public struct Refreshed: RefreshingEvent, Sendable {}
294+
/// The route has failed to refresh.
295+
public struct FailedToRefresh: RefreshingEvent, Sendable {}
294296
/// Indicates that current route's refreshing is no longer available.
295297
///
296298
/// It is strongly recommended to request a new route. Refreshing TTL has expired and the route will no longer

Sources/MapboxNavigationCore/Navigator/RouteProgress/RouteProgress.swift

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -115,8 +115,7 @@ public struct RouteProgress: Equatable, Sendable {
115115

116116
func refreshingRoute(
117117
with refreshedRoutes: NavigationRoutes,
118-
legIndex: Int,
119-
legShapeIndex: Int,
118+
refreshedMainLegIndex: Int?,
120119
congestionConfiguration: CongestionRangesConfiguration
121120
) -> RouteProgress {
122121
var refreshedRouteProgress = self
@@ -125,8 +124,10 @@ public struct RouteProgress: Equatable, Sendable {
125124

126125
refreshedRouteProgress.navigationRoutes = refreshedRoutes
127126

128-
refreshedRouteProgress.currentLegProgress = refreshedRouteProgress.currentLegProgress
129-
.refreshingLeg(with: refreshedRouteProgress.route.legs[legIndex])
127+
if let refreshedMainLegIndex {
128+
refreshedRouteProgress.currentLegProgress = refreshedRouteProgress.currentLegProgress
129+
.refreshingLeg(with: refreshedRouteProgress.route.legs[refreshedMainLegIndex])
130+
}
130131
refreshedRouteProgress.calculateLegsCongestion(configuration: congestionConfiguration)
131132

132133
return refreshedRouteProgress
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import Foundation
22

33
extension Bundle {
4-
public static let mapboxNavigationVersion: String = "3.10.0-beta.1"
4+
public static let mapboxNavigationVersion: String = "3.10.0-rc.1"
55
public static let mapboxNavigationUXBundleIdentifier: String = "com.mapbox.navigationUX"
66
}

Sources/_MapboxNavigationTestHelpers/Core/AlternativeRouteMock.swift

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,13 @@ extension AlternativeRoute {
1010
shape: mockShape
1111
),
1212
alternativeRoute: Route = .mock(),
13-
nativeRouteAlternative: RouteAlternative = .mock()
13+
nativeRouteAlternative: RouteAlternative? = nil
1414
) -> Self {
15-
self.init(
15+
let nativeAlternative = nativeRouteAlternative ?? .mock(route: alternativeRoute)
16+
return self.init(
1617
mainRoute: mainRoute,
1718
alternativeRoute: alternativeRoute,
18-
nativeRouteAlternative: nativeRouteAlternative
19+
nativeRouteAlternative: nativeAlternative
1920
)!
2021
}
2122

@@ -33,6 +34,10 @@ extension AlternativeRoute {
3334
}
3435

3536
extension RouteAlternative {
37+
public static func mock(route: Route, routeIndex: Int = 0) -> Self {
38+
.mock(route: RouteInterfaceMock(route: route, routeIndex: routeIndex))
39+
}
40+
3641
public static func mock(
3742
id: UInt32 = 0,
3843
route: RouteInterface = RouteInterfaceMock(),

0 commit comments

Comments
 (0)