从JavaScript运行MongoDB命令时会执行注释代码

时间:2016-07-06 16:59:54

标签: node.js mongodb

Mongo.exe尝试在我的JavaScript文件中执行注释行?

我在JavaScript文件中有一组MongoDB Shell命令。

 use test;
    /*
     var categories = [];
     var sum = 0;

     var category = {
       _id: "",
       num: 0
     };

     var cur = db.itemdata.aggregate( [   
        { $group: { _id: "$category"  ,
            num : {$sum: 1 }
            }},
        { $sort: {"_id":1 }}
     ]).toArray();
       for(var i=0; i < cur.length; i++){
        sum += cur[i].num;
        categories.push(cur[i]);
       }

     category.num = sum;
     categories.unshift(category);

     */


     /* Example 2 */
     var category = 'Books';
     var cnt = db.itemdata.find({"category" : category}).count()
     print(cnt);

我在Exampe2下得到了代码的预期结果。但是,我在终端看到一些警告/信息。

  

2016-07-06T11:44:35.886-0500 E QUERY [thread1] SyntaxError:unterminated comment @(shell):3:0
  2016-07-06T11:44:35.889-0500 E QUERY [thread1] ReferenceError:categories is   未定义:@(shell):3:2
  2016-07-06T11:44:35.891-0500 E QUERY [thread1] ReferenceError:categories is   未定义:@(shell):1:1
  3
  再见

我使用以下命令/语法在Windows机器中执行了JavaScript文件:

mongo.exe < script.js

为什么我看到这些错误,即使categories变量在评论区块内。

这不是一个表明,想了解它为什么会发生?

3 个答案:

答案 0 :(得分:7)

这可能是由于mongo shell处理多行操作的方式。 shell会逐个评估行,除非它看到它认为会跨越多行的东西,在这种情况下它会启动“多行操作”。

使用mongo命令(不管道输入文件),它可能如下所示:

> 40 + 2;
> 42
> for(var i = 0; i < 2; i++) {
> ...

其中40 + 2被立即评估,但{将告诉mongo在评估for循环之前等待其结束对应}

此行为记录在案here

问题是/*不是这样的符号,因此mongo不会等待其朋友*/。它会等待一个更多的行,或者直到你给它认为可以评估它的东西。

/*
    var categories = []; *
*/
 ...

以上内容不会引发错误,并会继续等待进一步说明,因为*/都是二进制运算符,所以mongo知道评估不会带来什么好处以这些结尾的一条线。所以它会等待,然后如果你添加,比如40 + 2,那么它会屈服于42就好了,因为现在整个评估的代码段从/*到{{1}是有效的JavaScript。

也许这不是决定是否评估输入线的最优雅的方式,但现在它的工作方式。 同样地,

40 + 2

会起作用,因为mongo会在评估之前等待结束/* { var categories = []; var sum = 0; ...other commented stuff.. }*/ 。但是,这可能不是你每次写评论时都想做的事情,而是让下一个开发人员想知道这是否是编写文档的新方法。

解决方案1 ​​

您可以使用}的单行评论。至少那些应该是好的,无论是批量评估还是逐一评估。但这会使您的代码对其他一些相关问题开放。例如,

//

解决方案2

如果您不想经常担心shell中是否有效(我知道我没有),您可以改变执行脚本的方式。

使用“script.js”作为参数运行mongo命令,而不是管道var template = ` Awesome multi-line template string... ...or error? `; 那样的mongo命令。{/ p>

这将以“脚本”模式而不是“交互式”模式评估代码,因此它将解决这些问题。有些事情需要改变才能实现。像mongo.exe < script.js这样的助手无法在脚本模式下工作,您需要将其更改为JavaScript对应mongo.exe script.js

这些差异记录在案here

答案 1 :(得分:3)

避免在javascript中使用块注释/ * * /。仅使用单行注释//。

资料来源:Douglas Crockford-JavaScript_ The Good Parts(2008)

  

JavaScript提供两种形式的注释,用/ * * /和形成块注释   以//开头的行尾注释评论应该自由使用   提高程序的可读性。注意评论总是准确 -   率地描述代码。过时的评论比没有评论更糟糕。

     

块评论的/ * * /形式来自一种叫做PL / I的语言。   PL / I选择那些奇怪的对作为评论的符号,因为   它们不太可能出现在那种语言的程序中,除了   也许在字符串文字中。在JavaScript中,这些对也可以发生   在正则表达式文字中,所以块注释不安全   注释掉代码块。例如:

/*
var rm_a = /a*/.match(s);
*/
  

导致语法错误。因此,建议使用/ * * / comments   避免使用//注释代替。在本书中,//将被使用   独占。

答案 2 :(得分:0)

可以在JS中运行注释的代码

let code = ((function () {
/* 
  alert('Run commented code'); 
  let a=3; 
  alert(a+5); 
*/})+'').match(/[^]*\/\*([^]*)\*\/\}$/)[1];

eval(code);