正则表达式对我想要做的事情是正确的吗?

Is the Regex right against what am I trying to do?

本文关键字:我想要 正则表达式      更新时间:2023-11-04

>我正在创建一个可重用的节点.js 导航控制器类,以便我可以在其他服务器端项目中重用它 如果我可能需要或其他人可能发现它有用。

这是用例。

var navController = new NavigationController({
    routes : {
        '/user/:action/:anything' : 'UserController',
        '/app/:action' : 'AppController',
        '/file/:action' : 'FileController',
        '/feedback/:action' : 'FeedbackController',
        '/:anything' : 'ErrorController'
    },
    ErrorController : 'ErrorController'
});
navController.init();

服务器请求时用户可以调用该对象的此函数。

navController.navigate(req, res);

现在这个和控制器被正确地调用了。navigate(req, res( 函数下的东西是基于 URL 调用适当的控制器对象的一部分,被定义为名为 getRouteByPath(path( 的函数。这个私有函数将获取路由,并允许 navigate(req, res( 函数获取要调用的控制器类名。

var getRouteByPath = function(path) {
    for(var route in config.routes) {
        var routeRegex = '';
        var routeParts = route.split('/');
        for(var rp = 0; rp < routeParts.length; rp++) {
            // checking if route part starts with :
            if(routeParts[rp].indexOf(':') === 0) {
                // this is "anything" part
                routeRegex += '[/]?([A-Za-z0-9]*)';
            } else if(routeParts[rp] != "") {
                routeRegex += '[/]?' + routeParts[rp];
            }
        }
        var routeRegexResult = path.match(routeRegex);
        if(routeRegexResult) {
            console.log(routeRegexResult);
            return route;
        }
    }
    return null;
};

我太担心这个功能了,好像这是正确的方法?

一些缺陷:

  • 为什么使用斜杠作为字符类([/](?没有必要这样做,只有在正则表达式文本中,您需要使用反斜杠(如 /'//g(对其进行转义。只需使用单个"/"代替(new RegExp("/", "g")(。

  • .indexOf(<string>)==0确实有效,但搜索整个字符串并且效率不高。更好的使用始于,在您的情况下routePart.charAt(0)==":"

  • <string>.match(<string>) - 我建议构建一个新的RegExp对象并使用 .test ,因为你不想匹配 - 我认为也没有必要构建捕获组,因为你只返回路由字符串而不返回匹配(好吧,你记录它们(。

  • 您想检查整个path是否与您的正则表达式匹配?不要忘记添加 ^$ .您当前的应用程序控制器正则表达式也与类似 /user/app/example 的路由匹配。

  • 为什么你的斜杠(而且只有斜杠(是可选的(/?(?我不仅不认为这是你想要的,而且还在构建像/'/?user'/?([A-Za-z0-9]*)'/?([A-Za-z0-9]*)/这样的正则表达式时为灾难性的回溯打开了大门

    要避免这种情况,您需要将整个组设置为可选:(?:/([^/]*))?

  • 此外,您应该只构建一次正则表达式(在初始化时(并将它们存储在缓存中,而不是每次调用 getRouteByPath 时都构建它们。RegExp的编译隐藏在代码中的某个地方,尽管它需要发生。

一些注意事项:

routeRegex += '[/]?([A-Za-z0-9]*)';

说路线可能存在也可能不存在//匹配也许+*更适合。

另外,由于我瘦_在网络路由中是允许的

您的.split('/')将从路由中删除所有/,因此它不应位于拆分列表中