blob: 6cbbf876822e2f6f2afd715965d9321bfcb4b631 [file] [log] [blame]
/**
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { createElement } from 'react';
import dynamic from 'dva/dynamic';
import pathToRegexp from 'path-to-regexp';
import { getMenuData } from './menu';
let routerDataCache;
const modelNotExisted = (app, model) => (
// eslint-disable-next-line
!app._models.some(({ namespace }) => {
return namespace === model.substring(model.lastIndexOf('/') + 1);
})
);
// wrapper of dynamic
const dynamicWrapper = (app, models, component) => {
// () => require('module')
// transformed by babel-plugin-dynamic-import-node-sync
if (component.toString().indexOf('.then(') < 0) {
models.forEach((model) => {
if (modelNotExisted(app, model)) {
// eslint-disable-next-line
app.model(require(`../models/${model}`).default);
}
});
return (props) => {
if (!routerDataCache) {
routerDataCache = getRouterData(app);
}
return createElement(component().default, {
...props,
routerData: routerDataCache,
});
};
}
// () => import('module')
return dynamic({
app,
models: () => models.filter(
model => modelNotExisted(app, model)).map(m => import(`../models/${m}.js`)
),
// add routerData prop
component: () => {
if (!routerDataCache) {
routerDataCache = getRouterData(app);
}
return component().then((raw) => {
const Component = raw.default || raw;
return props => createElement(Component, {
...props,
routerData: routerDataCache,
});
});
},
});
};
function getFlatMenuData(menus) {
let keys = {};
menus.forEach((item) => {
if (item.children) {
keys[item.path] = { ...item };
keys = { ...keys, ...getFlatMenuData(item.children) };
} else {
keys[item.path] = { ...item };
}
});
return keys;
}
export const getRouterData = (app) => {
const routerConfig = {
'/': {
component: dynamicWrapper(app, ['user', 'login'], () => import('../layouts/BasicLayout')),
},
'/monitor/dashboard': {
component: dynamicWrapper(app, ['dashboard'], () => import('../routes/Dashboard/Dashboard')),
},
'/monitor/topology': {
component: dynamicWrapper(app, ['topology'], () => import('../routes/Topology/Topology')),
},
'/monitor/service': {
component: dynamicWrapper(app, ['service'], () => import('../routes/Service/Service')),
},
'/monitor/endpoint': {
component: dynamicWrapper(app, ['endpoint'], () => import('../routes/Endpoint/Endpoint')),
},
'/trace': {
component: dynamicWrapper(app, ['trace'], () => import('../routes/Trace/Trace')),
},
'/monitor/alarm': {
component: dynamicWrapper(app, ['alarm'], () => import('../routes/Alarm/Alarm')),
},
'/user': {
component: dynamicWrapper(app, [], () => import('../layouts/UserLayout')),
},
'/user/login': {
component: dynamicWrapper(app, ['login'], () => import('../routes/User/Login')),
},
'/exception/403': {
component: dynamicWrapper(app, [], () => import('../routes/Exception/403')),
},
'/exception/404': {
component: dynamicWrapper(app, [], () => import('../routes/Exception/404')),
},
'/exception/500': {
component: dynamicWrapper(app, [], () => import('../routes/Exception/500')),
},
};
// Get name from ./menu.js or just set it in the router data.
const menuData = getFlatMenuData(getMenuData());
// Route configuration data
// eg. {name,authority ...routerConfig }
const routerData = {};
// The route matches the menu
Object.keys(routerConfig).forEach((path) => {
// Regular match item name
// eg. router /user/:id === /user/chen
const pathRegexp = pathToRegexp(path);
const menuKey = Object.keys(menuData).find(key => pathRegexp.test(`/${key}`));
let menuItem = {};
// If menuKey is not empty
if (menuKey) {
menuItem = menuData[menuKey];
}
let router = routerConfig[path];
// If you need to configure complex parameter routing,
// https://github.com/ant-design/ant-design-pro-site/blob/master/docs/router-and-nav.md#%E5%B8%A6%E5%8F%82%E6%95%B0%E7%9A%84%E8%B7%AF%E7%94%B1%E8%8F%9C%E5%8D%95
// eg . /list/:type/user/info/:id
router = {
...router,
name: router.name || menuItem.name,
authority: router.authority || menuItem.authority,
};
routerData[path] = router;
});
return routerData;
};