UNPKG

nativescript-vue-router-extended

Version:

NativeScript Vue Router Extended for NativeScript Vue hybrid Apps.

206 lines 6.95 kB
import { RouterGuardsService } from "./router-guards-service"; export class RouterService { constructor({ routes = [] }, { routeToCallback = null, routeBackCallback = null, routeBackFallbackPath = "", logger = null, frame = null, vm = null, }) { this.routes = []; this.history = []; this.routerGuardsService = null; this.defaultOptions = { transition: { duration: 100, }, meta: { props: {}, }, }; this.routes = routes; this.routeToCallback = routeToCallback; this.routeBackCallback = routeBackCallback; this.routeBackFallbackPath = routeBackFallbackPath; this.logger = logger || console.log; this.vm = vm; this.frame = frame; this.routerGuardsService = new RouterGuardsService({ to: null, from: null, }); } push(route, options = {}) { this.navigateTo(route, options); } back(options = {}, emptyRouteFallbackPath = null) { this.navigateBack(options, emptyRouteFallbackPath); } onError(callback) { this.errorCallbacks.push(callback); } beforeEach(callback) { this.routerGuardsService.addBeforeEach(callback); } beforeResolve(callback) { this.routerGuardsService.addBeforeResolve(callback); } invokeBeforeResolve() { const context = this.routerGuardsService.runBeforeResolve(); if (!this.performContextAction(context)) { this.setNavigationState(false); return false; } return true; } afterEach(callback) { this.routerGuardsService.addAfterEach(callback); this.setNavigationState(false); } invokeAfterEach() { this.routerGuardsService.runAfterEach(); } updateVm(vm) { this.vm = vm; } getRoute(route) { if (!route) { return null; } let routePath = ""; if (typeof route === "string") { routePath = route; } else if (typeof route === "object") { routePath = route.name || route.path; } return (this.routes.find(({ path, name }) => path === routePath || name === routePath) || null); } getCurrentRoute() { return this.getRoute(this.currentRoute); } setCurrentRoute(route) { this.currentRoute = route; this.vm.$route = Object.assign(this.vm.$route, route); } getNewRoute() { return this.newRoute; } getPreviousRoute() { const historyEntryNo = this.history.length - 1; if (historyEntryNo < 0) { return null; } if (!this.history[historyEntryNo]) { return null; } return this.getRoute(this.history[historyEntryNo]); } setNavigationState(toggle) { this.isNavigating = toggle; if (!this.isNavigating) { this.setNewRoute(null); } } appendRouteHistory(routePath) { this.history.push(routePath); } clearRouteHistory() { this.history.splice(0); } isRouteAvailable(route) { return Object.keys(this.getRoute(route) || {}).length > 0; } setNewRoute(route) { this.newRoute = route; } isValidRoute(route) { let logMessage = ""; if (!this.isRouteAvailable(route)) { const routePath = typeof route === "object" && route && route.path ? route.path : route.toString(); logMessage = `Route ${routePath} is missing`; } if (logMessage && this.logger) { this.logger.warn("ROUTER", logMessage); return false; } return true; } navigateTo(route, options = {}, isNavigatingBack = false) { if (!this.isValidRoute(route)) { return; } const previousRoute = this.getCurrentRoute(); const newRoute = this.getRoute(route); const routeOptions = Object.assign(Object.assign({}, this.defaultOptions), options); routeOptions.props = routeOptions.props || {}; routeOptions.context = routeOptions.props; newRoute.meta = newRoute.meta || {}; newRoute.meta.props = Object.assign(Object.assign(Object.assign({}, newRoute.meta), (newRoute.meta.props || {})), routeOptions.props); this.setNavigationState(true); this.setNewRoute(newRoute); this.routerGuardsService.setRoutes(newRoute, previousRoute); const context = this.routerGuardsService.runBeforeEach(); if (!this.performContextAction(context)) { this.setNavigationState(false); return; } if (this.vm.$modalPage) { const modal = this.vm.$modalPage; if (modal.instance && modal.data) { modal.instance.onNavigatingFrom(modal.data); } this.vm.$modalPage = null; } if (isNavigatingBack) { if (this.routeBackCallback) { this.routeBackCallback(newRoute, routeOptions); } this.vm.$navigateBack(routeOptions); } else { if (this.routeToCallback) { this.routeToCallback(newRoute, routeOptions); } this.vm.$navigateTo(newRoute.component, routeOptions); } this.setCurrentRoute(newRoute); if (routeOptions.clearHistory) { this.clearRouteHistory(); } if (!isNavigatingBack && previousRoute) { this.appendRouteHistory(previousRoute.path); } if (isNavigatingBack && this.history.length > 0) { this.history.pop(); } } navigateBack(options = {}, emptyRouteFallbackPath = null) { let newRoute = this.getPreviousRoute(); if (!newRoute || (this.frame.topmost() && this.frame.topmost().backStack.length < 1)) { const alternativePath = emptyRouteFallbackPath || this.routeBackFallbackPath; if (alternativePath) { newRoute = this.getRoute(alternativePath); options.clearHistory = true; this.navigateTo(newRoute, options); } if (!newRoute && this.logger) { this.logger.warn("ROUTER", "No route to go back to"); } return; } this.navigateTo(newRoute, options, true); } performContextAction(context) { if (context === false) { return false; } if (context instanceof Error) { this.onError(context); return false; } if (typeof context === "object" || typeof context === "string") { this.navigateTo(context); return false; } return true; } } //# sourceMappingURL=router-service.js.map