instantpage.js 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. /*! instant.page v0.0.0 - (C) 2019 Alexandre Dieulot - https://instant.page/license */
  2. let urlBeingPreloaded
  3. const prefetcher = document.createElement('link')
  4. const useAjaxFallback = !(prefetcher.relList && prefetcher.relList.supports && prefetcher.relList.supports('prefetch'))
  5. if (!useAjaxFallback) {
  6. prefetcher.rel = 'prefetch'
  7. document.head.appendChild(prefetcher)
  8. }
  9. document.addEventListener('mouseover', mouseoverListener, true)
  10. function mouseoverListener(event) {
  11. const linkElement = event.target.closest('a')
  12. if (!linkElement) {
  13. return
  14. }
  15. if (!isPreloadable(linkElement)) {
  16. return
  17. }
  18. linkElement.addEventListener('mouseout', mouseoutListener)
  19. preload(linkElement.href)
  20. }
  21. function mouseoutListener(event) {
  22. if (event.relatedTarget && event.target.closest('a') == event.relatedTarget.closest('a')) {
  23. return
  24. }
  25. stopPreloading()
  26. }
  27. function isPreloadable(linkElement) {
  28. if (urlBeingPreloaded == linkElement.href) {
  29. return false
  30. }
  31. const urlObject = new URL(linkElement.href)
  32. if (urlObject.origin != location.origin) {
  33. return false
  34. }
  35. if ('noInstant' in linkElement.dataset) {
  36. return false
  37. }
  38. return true
  39. }
  40. function preload(url) {
  41. urlBeingPreloaded = url
  42. if (!useAjaxFallback) {
  43. prefetcher.href = url
  44. console.log(`Preloading ${url}`)
  45. }
  46. else {
  47. console.log(`Todo: preload with Ajax ${url}`)
  48. }
  49. }
  50. function stopPreloading() {
  51. if (!urlBeingPreloaded) {
  52. return
  53. }
  54. urlBeingPreloaded = undefined
  55. if (!useAjaxFallback) {
  56. /* The spec says an empty string should abort the prefetching
  57. * but Firefox 64 interprets it as a relative URL to prefetch. */
  58. prefetcher.removeAttribute('href')
  59. console.log(`Stopped preloading`)
  60. }
  61. else {
  62. console.log(`Todo: stop preloading with xhr.abort()`)
  63. }
  64. }