Newer
Older
XinYang_SanWei+RongYun / static / js / vue-auto.js
@张强云笔记本 张强云笔记本 on 17 Dec 2021 7 KB 融云通话接入
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
// 所生成的所有路由数组
var Routers = [];
/**
 * rc:require.context 传入的文件
 * redirect:需要将根路由(/)重定向到的路由
 * rootFile:页面级别的.vue存放的文件名称
 */
exports.default = (function (config) {
    var defaultConfig = {
        rc: null,
        redirect: '',
        rootFile: 'views'
    };
    var _a = Object.assign({}, defaultConfig, config), rc = _a.rc, redirect = _a.redirect, rootFile = _a.rootFile;
    if (rc === null)
        return Routers;
    // allRouters[object]:存储所有路由的变量:先将所有的路由生成,然后放在该变量里面
    var allRouters = {};
    // 通过循环RC(传入的文件)
    var routerFileAndLen = rc
        .keys()
        .map(function (fileName) {
        // 因为得到的filename格式是: './baseButton.vue', 所以这里我们去掉头和尾,只保留真正的文件名
        var realFileName = fileName
            .replace(/^\.\//, '')
            .replace(/\.\w+$/, '');
        return {
            fileName: realFileName,
            // routerName(路由名称):将 / 转为 - 并去掉 _
            routerName: realFileName.replace(/\//g, '-').replace(/_/g, ''),
            // routerComponent(路由异步component的文件路径):将 ./baseButton.vue 从 . 之后截取
            routerComponent: fileName.substr(1),
            // fileLen(文件的层级深度):通过 / 的数量来判断当前文件的深度
            fileLen: fileName.match(/\//g).length
        };
    })
        .sort(function (i, j) { return i.fileLen - j.fileLen; }); // 通过文件深度 升序排序
    // 传入文件中最大深度
    var maxLen = 0;
    routerFileAndLen.map(function (r) {
        var name = r.routerName;
        // 生成一块路由对象,包含:name、fileName(用于后续处理真正path的依据)、path、needDelectName(用于后续处理,判断是否删除name的依据)、component
        var obj = {
            name: name,
            fileName: r.fileName,
            // path:只是以name命名的path,还不是真正的路由path
            path: '/' + (name === 'index' ? '' : name),
            // needDelectName: name === 'index',
            needDelectName: false,
            component: resolve => require.ensure([], () => resolve(require("@/" + rootFile + r.routerComponent)))
        };
        maxLen = r.fileLen;
        // allRouters的key:以 'len'加当前的文件深度 作为key
        var key = 'len' + maxLen;
        if (Array.isArray(allRouters[key]))
            allRouters[key].push(obj);
        else
            allRouters[key] = [obj];
    });
    // 将根目录层的路由放入Routers中
    Routers.push.apply(Routers, allRouters.len1);
    // 截取名称方法:从开始到最后一个'-'之间的字符串
    var substrName = function (name) { return name.substr(0, name.lastIndexOf('-')); };
    /**
     * 正式生成路由:1、将相应的路由放在对应的路由下,形成子路由;2、生成同级路由
     * index:当前文件深度,为maxlen的倒序循环
     * nofindnum:未找到路由的次数
     * newcurr:当前新的深度下的路由数据
     */
    var ceateRouter = function (index, nofindnum, newcurr) {
        if (nofindnum === void 0) { nofindnum = 0; }
        if (newcurr === void 0) { newcurr = null; }
        // 当前深度下的路由数据:优先使用传入的newcurr,其次获取当前深度对应的路由数据
        var curr = newcurr || allRouters['len' + index];
        // 当前深度上一层的路由数据
        var pre = allRouters['len' + (index - 1)];
        // 若 没有上一层的数据了
        if (!pre) {
            // 则表明是属于顶层的路由
            curr.map(function (c) {
                var path = '/' + c.fileName.replace('/index', '');
                if (path.match('_'))
                    path = path.replace('/_', '/:');
                // 将真正的路由path赋值给当前路由
                c.path = path;
                // 将当前路由放到Routers里面
                Routers.push(c);
            });
            return;
        }
        // 在上一层中 未找到的 当前深度路由数据
        var noFind = [];
        // 循环当前深度路由数据
        curr.map(function (c) {
            // 在 上一层深度 的路由数据里面查找
            var fobj = pre.find(function (p) {
                // 生成 当前深度 当前项 路由的name
                var name = substrName(c.name);
                // 循环nofindnum,当nofindnum>0,则表示已经出现:在上一层中未找到对应的父路由,则需要将 当前深度 当前项 路由的name 再次生成
                for (var i = 0; i < nofindnum; i++) {
                    name = substrName(name);
                }
                return name === p.name;
            });
            // 如果 找到了 对应的 父路由数据(fobj)
            if (fobj) {
                // 生成 当前路由的path:1、去掉当前路由中与父路由重复的;2、去掉/;3、将 _ 转为 :;
                var path = c.fileName
                    .replace(fobj.fileName, '')
                    .substr(1)
                    .replace('_', ':');
                if (path.match('/') && !path.match('/:')) {
                    path = path.replace('/index', '');
                }
                if (path === undefined) {
                    throw new Error("\u627E\u5230\u4E86\u5BF9\u5E94\u7684\u7236\u8DEF\u7531\uFF0C\u4F46\u662F\u751F\u6210\u5B50\u8DEF\u7531\u7684path\u4E3A\u3010undefined\u3011\u4E86");
                }
                // 将真正的路由path赋值给当前路由
                c.path = path;
                // 若:当前路由为 index
                if (path === 'index') {
                    // 1、转为 '' path,'':表明是默认子路由,那父路由就不能存在name属性
                    c.path = '';
                    // 2、将父路由的needDelectName标记为true,表明需要删除它的name
                    fobj.needDelectName = fobj.needDelectName || true;
                }
                // 将当前路由放到父路由的children里面
                if (Array.isArray(fobj.children))
                    fobj.children.push(c);
                else
                    fobj.children = [c];
            }
            else
                noFind.push(c); // 表明未找到父路由,则先将当前路由的数据放入noFind中存储起来
        });
        // 若存在:未找到的路由数据,则再次向上一个层级寻找
        if (noFind.length)
            ceateRouter(index - 1, ++nofindnum, noFind);
    };
    // 倒序循环 最大深度,然后调用生成路由方法
    for (var i = maxLen; i > 1; i--)
        ceateRouter(i);
    // 路由生成完毕了,应该删除 有默认子路由的父路由的name属性
    var deleteNameFun = function (arr) {
        arr.map(function (r) {
            // 删除多余的fileName属性
            delete r.fileName;
            // 判断是否需要删除name属性
            if (r.needDelectName)
                delete r.name;
            // 判断完毕了,则要删除needDelectName属性
            delete r.needDelectName;
            // 若 存在子路由 则继续调用deleteNameFun,删除name
            if (Array.isArray(r.children))
                deleteNameFun(r.children);
        });
    };
    // 调用deleteNameFun,先删除Routers的一级路由的name
    deleteNameFun(Routers);
    // 若存在重定向的路由,则加入重定向
    if (redirect)
        Routers.unshift({ path: '/', redirect: redirect });
    // 返回正儿八经的的路由数据
    return Routers;
});