Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: route preload with Link tag #12792

Merged
merged 3 commits into from
Nov 20, 2024
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/docs/docs/api/api.en-US.md
Original file line number Diff line number Diff line change
@@ -207,7 +207,7 @@ function IndexPage({ user }) {

`<Link to>` supports relative path navigation; `<Link reloadDocument>` does not do routing navigation and is equivalent to the jump behavior of `<a href>`.

If `prefetch` is enabled, then when the user hovers over the component, Umi will automatically start preloading the component js files and data for the routing jump.
If `prefetch` is enabled, then when the user hovers over the component, Umi will automatically start preloading the component js files and data for the routing jump. (Note: Use this feature when `routePrefetch` and `manifest` are enabled)

### matchPath

2 changes: 1 addition & 1 deletion docs/docs/docs/api/api.md
Original file line number Diff line number Diff line change
@@ -206,7 +206,7 @@ function IndexPage({ user }) {

`<Link to>` 支持相对路径跳转;`<Link reloadDocument>` 不做路由跳转,等同于 `<a href>` 的跳转行为。

若开启了 `prefetch` 则当用户将鼠标放到该组件上方时,Umi 就会自动开始进行跳转路由的组件 js 文件和数据预加载。
若开启了 `prefetch` 则当用户将鼠标放到该组件上方时,Umi 就会自动开始进行跳转路由的组件 js 文件和数据预加载。(注:使用此功能请同时开启 `routePrefetch` 和 `manifest` 配置)

### matchPath

43 changes: 9 additions & 34 deletions packages/renderer-react/src/browser.tsx
Original file line number Diff line number Diff line change
@@ -249,42 +249,17 @@ const getBrowser = (
) || []
).filter(Boolean);
matchedRouteIds.forEach((id) => {
// preload
// @ts-ignore
const manifest = window.__umi_manifest__;
if (manifest) {
const routeIdReplaced = id.replace(/[\/\-]/g, '_');
const preloadId = `preload-${routeIdReplaced}.js`;
if (!document.getElementById(preloadId)) {
const keys = Object.keys(manifest).filter((k) =>
k.startsWith(routeIdReplaced + '.'),
);
keys.forEach((key) => {
if (!/\.(js|css)$/.test(key)) {
throw Error(`preload not support ${key} file`);
}
let file = manifest[key];
const link = document.createElement('link');
link.rel = 'preload';
link.as = 'style';
if (key.endsWith('.js')) {
link.as = 'script';
link.id = preloadId;
}
// publicPath already in the manifest,
// but if runtimePublicPath is true, we need to replace it
if (opts.runtimePublicPath) {
file = file.replace(
new RegExp(`^${opts.publicPath}`),
// @ts-ignore
window.publicPath,
);
}
link.href = file;
document.head.appendChild(link);
});
// preload lazy component
// window.__umi_manifest__ is available when routePrefetch and manifest config is enabled
// __umi_manifest__ is not needed for preload, keep this is for compatibility and minimal change
if ((window as any).__umi_manifest__) {
// ref: https://github.com/facebook/react/blob/0940414/packages/react/src/ReactLazy.js#L135
const lazyCtor = opts.routeComponents[id]?._payload?._result;
if (typeof lazyCtor == 'function') {
lazyCtor();
}
}

const clientLoader = opts.routes[id]?.clientLoader;
const hasClientLoader = !!clientLoader;
const hasServerLoader = opts.routes[id]?.hasServerLoader;
Loading