registerRoute.js 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293
  1. /*
  2. Copyright 2019 Google LLC
  3. Use of this source code is governed by an MIT-style
  4. license that can be found in the LICENSE file or at
  5. https://opensource.org/licenses/MIT.
  6. */
  7. import { logger } from 'workbox-core/_private/logger.js';
  8. import { WorkboxError } from 'workbox-core/_private/WorkboxError.js';
  9. import { Route } from './Route.js';
  10. import { RegExpRoute } from './RegExpRoute.js';
  11. import { getOrCreateDefaultRouter } from './utils/getOrCreateDefaultRouter.js';
  12. import './_version.js';
  13. /**
  14. * Easily register a RegExp, string, or function with a caching
  15. * strategy to a singleton Router instance.
  16. *
  17. * This method will generate a Route for you if needed and
  18. * call [registerRoute()]{@link module:workbox-routing.Router#registerRoute}.
  19. *
  20. * @param {RegExp|string|module:workbox-routing.Route~matchCallback|module:workbox-routing.Route} capture
  21. * If the capture param is a `Route`, all other arguments will be ignored.
  22. * @param {module:workbox-routing~handlerCallback} [handler] A callback
  23. * function that returns a Promise resulting in a Response. This parameter
  24. * is required if `capture` is not a `Route` object.
  25. * @param {string} [method='GET'] The HTTP method to match the Route
  26. * against.
  27. * @return {module:workbox-routing.Route} The generated `Route`(Useful for
  28. * unregistering).
  29. *
  30. * @memberof module:workbox-routing
  31. */
  32. function registerRoute(capture, handler, method) {
  33. let route;
  34. if (typeof capture === 'string') {
  35. const captureUrl = new URL(capture, location.href);
  36. if (process.env.NODE_ENV !== 'production') {
  37. if (!(capture.startsWith('/') || capture.startsWith('http'))) {
  38. throw new WorkboxError('invalid-string', {
  39. moduleName: 'workbox-routing',
  40. funcName: 'registerRoute',
  41. paramName: 'capture',
  42. });
  43. }
  44. // We want to check if Express-style wildcards are in the pathname only.
  45. // TODO: Remove this log message in v4.
  46. const valueToCheck = capture.startsWith('http') ?
  47. captureUrl.pathname : capture;
  48. // See https://github.com/pillarjs/path-to-regexp#parameters
  49. const wildcards = '[*:?+]';
  50. if ((new RegExp(`${wildcards}`)).exec(valueToCheck)) {
  51. logger.debug(`The '$capture' parameter contains an Express-style wildcard ` +
  52. `character (${wildcards}). Strings are now always interpreted as ` +
  53. `exact matches; use a RegExp for partial or wildcard matches.`);
  54. }
  55. }
  56. const matchCallback = ({ url }) => {
  57. if (process.env.NODE_ENV !== 'production') {
  58. if ((url.pathname === captureUrl.pathname) &&
  59. (url.origin !== captureUrl.origin)) {
  60. logger.debug(`${capture} only partially matches the cross-origin URL ` +
  61. `${url}. This route will only handle cross-origin requests ` +
  62. `if they match the entire URL.`);
  63. }
  64. }
  65. return url.href === captureUrl.href;
  66. };
  67. // If `capture` is a string then `handler` and `method` must be present.
  68. route = new Route(matchCallback, handler, method);
  69. }
  70. else if (capture instanceof RegExp) {
  71. // If `capture` is a `RegExp` then `handler` and `method` must be present.
  72. route = new RegExpRoute(capture, handler, method);
  73. }
  74. else if (typeof capture === 'function') {
  75. // If `capture` is a function then `handler` and `method` must be present.
  76. route = new Route(capture, handler, method);
  77. }
  78. else if (capture instanceof Route) {
  79. route = capture;
  80. }
  81. else {
  82. throw new WorkboxError('unsupported-route-type', {
  83. moduleName: 'workbox-routing',
  84. funcName: 'registerRoute',
  85. paramName: 'capture',
  86. });
  87. }
  88. const defaultRouter = getOrCreateDefaultRouter();
  89. defaultRouter.registerRoute(route);
  90. return route;
  91. }
  92. export { registerRoute };