import { createBrowserHistory , History } from 'history' ; import { matchPath } from 'react-router' ; import cfg from 'teleport/config' ; let _inst = null ; const history = { original ( ) { return _inst ; } , init ( history ? ) { _inst = history || createBrowserHistory ( ) ; } , replace ( route = '' ) { route = this . ensureKnownRoute ( route ) ; _inst . replace ( route ) ; } , push ( route , withRefresh = false ) { route = this . ensureKnownRoute ( route ) ; if ( withRefresh ) { this . _pageRefresh ( route ) ; } else { _inst . push ( route ) ; } } , reload ( ) { window . location . reload ( ) ; } , goToLogin ( rememberLocation = false ) { let url = cfg . routes . login ; if ( rememberLocation ) { const { search , pathname } = _inst . location ; const knownRoute = this . ensureKnownRoute ( pathname ) ; const knownRedirect = this . ensureBaseUrl ( knownRoute ) ; const query = search ? encodeURIComponent ( search ) : '' ; url = `${ url }?redirect_uri=${ knownRedirect }${ query }` ; } this . _pageRefresh ( url ) ; } , getRedirectParam ( ) { return getUrlParameter ( 'redirect_uri' , this . original ( ) . location . search ) ; } , ensureKnownRoute ( route = '' ) { return this . _canPush ( route ) ? route : cfg . routes . root ; } , ensureBaseUrl ( url ) { url = url || '' ; if ( url . indexOf ( cfg . baseUrl ) !== 0 ) { if ( url . startsWith ( '/' ) ) { url = `${ cfg . baseUrl }${ url }` ; } else { url = `${ cfg . baseUrl }/${ url }` ; } } return url ; } , getRoutes ( ) { return Object . getOwnPropertyNames ( cfg . routes ) . map ( p => cfg . routes [ p ] ) ; } , getLocation ( ) { return this . original ( ) . location ; } , _canPush ( route ) { const knownRoutes = this . getRoutes ( ) ; const { pathname } = new URL ( this . ensureBaseUrl ( route ) ) ; const match = ( known ) => matchPath ( pathname , { path : known , exact : true , } ) ; return knownRoutes . some ( match ) ; } , _pageRefresh ( route ) { window . location . href = this . ensureBaseUrl ( route ) ; } , } ; export default history ; export function getUrlParameter ( name = '' , path = '' ) { const params = new URLSearchParams ( path ) ; const value = params . get ( name ) ; return value || '' ; }