oa-navigate-back.js 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. /**
  2. * H5 上 uni.navigateBack 偶发既不成功也不进 fail;离开 OA web-view 时做兜底。
  3. * @param {{ fallbackUrl?: string, onStuck?: () => void }} [opts]
  4. */
  5. export function isOaHostWebviewRoute(route) {
  6. const value = String(route || '')
  7. return (
  8. value.indexOf('oa/start/webview') !== -1 ||
  9. value.indexOf('oa/webview/') !== -1 ||
  10. value.indexOf('market/webview/') !== -1
  11. )
  12. }
  13. export function navigateBackFromOaHost(opts) {
  14. const onStuck = opts && opts.onStuck
  15. const pageRoute = (page) => {
  16. return String(
  17. (page && (page.route || (page.$page && page.$page.fullPath))) || ''
  18. )
  19. }
  20. const samePageStillOnTop = (start) => {
  21. try {
  22. const pages = getCurrentPages()
  23. const current = pages && pages[pages.length - 1]
  24. return (
  25. !!current &&
  26. pages.length === start.depth &&
  27. current === start.page &&
  28. pageRoute(current) === start.route &&
  29. isOaHostWebviewRoute(start.route)
  30. )
  31. } catch (_) {
  32. return false
  33. }
  34. }
  35. const resolveFallbackUrl = () => {
  36. const explicit = String((opts && opts.fallbackUrl) || '').trim()
  37. if (explicit) return explicit
  38. try {
  39. const pages = getCurrentPages()
  40. if (pages && pages.length >= 2) {
  41. const prev = pages[pages.length - 2]
  42. const route = prev && prev.route
  43. if (route) return '/' + String(route).replace(/^\//, '')
  44. }
  45. } catch (_) {
  46. /* ignore */
  47. }
  48. return '/pages/oa/start/index'
  49. }
  50. let fallbackStarted = false
  51. const fallback = () => {
  52. if (fallbackStarted) return
  53. fallbackStarted = true
  54. const fallbackUrl = resolveFallbackUrl()
  55. if (!fallbackUrl) {
  56. if (onStuck) onStuck()
  57. return
  58. }
  59. uni.redirectTo({
  60. url: fallbackUrl,
  61. fail: () => {
  62. uni.reLaunch({
  63. url: fallbackUrl,
  64. fail: () => {
  65. if (onStuck) onStuck()
  66. }
  67. })
  68. }
  69. })
  70. }
  71. try {
  72. const pages = getCurrentPages()
  73. if (pages && pages.length > 1) {
  74. const startPage = pages[pages.length - 1]
  75. const start = {
  76. page: startPage,
  77. route: pageRoute(startPage),
  78. depth: pages.length
  79. }
  80. uni.navigateBack({
  81. delta: 1,
  82. fail: () => fallback()
  83. })
  84. // H5:navigateBack 偶发静默失败
  85. setTimeout(() => {
  86. if (samePageStillOnTop(start)) fallback()
  87. }, 280)
  88. return
  89. }
  90. } catch (_) {
  91. /* fall through */
  92. }
  93. fallback()
  94. }