Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

Single line comment make trouble. #61

Merged
merged 1 commit into from

2 participants

@cbou

If there is such a comment in a file // asfasdfasdf /** ///// it causes some trouble in the output.

For example try to parse this part of c.js

/**
 * Parse tag string "@param {Array} name description" etc.
 *
 * @param {String}
 * @return {Object}
 * @api public
 */

exports.parseTag = function(str) {
  var tag = {} 
    , parts = str.split(/ +/)
    , type = tag.type = parts.shift().replace('@', '');

  /* shouldn't fail */
  switch (type) { // asfasdfasdf /** /////
    case 'param':
      tag.types = exports.parseTagTypes(parts.shift());
      tag.name = parts.shift() || '';
      tag.description = parts.join(' ');
      break;
    case 'return':
      tag.types = exports.parseTagTypes(parts.shift());
      tag.description = parts.join(' ');
      break;
    case 'see':
      if (~str.indexOf('http')) {
        tag.title = parts.length > 1
          ? parts.shift()
          : '';
        tag.url = parts.join(' ');
      } else {
        tag.local = parts.join(' ');
      }
    case 'api':
      tag.visibility = parts.shift();
      break;
    case 'type':
      tag.types = exports.parseTagTypes(parts.shift());
      break;
  }

  return tag;
}

/**
 * Parse tag type string "{Array|Object}" etc.
 *
 * @param {String} str
 * @return {Array}
 * @api public
 */

exports.parseTagTypes = function(str) {
  return str
    .replace(/[{}]/g, '')
    .split(/ *[|,\/] */);
};

You will get something like that:

    "description": {
      "full": "<p>/////<br />    case 'param':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      tag.name = parts.shift() || '';<br />      tag.description = parts.join(' ');<br />      break;<br />    case 'return':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      tag.description = parts.join(' ');<br />      break;<br />    case 'see':<br />      if (~str.indexOf('http')) {<br />        tag.title = parts.length > 1<br />          ? parts.shift()<br />          : '';<br />        tag.url = parts.join(' ');<br />      } else {<br />        tag.local = parts.join(' ');<br />      }<br />    case 'api':<br />      tag.visibility = parts.shift();<br />      break;<br />    case 'type':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      break;<br />  }</p>\n\n<p>return tag;<br />}</p>\n\n<p>/**<br />Parse tag type string \"{Array|Object}\" etc.</p>",
      "summary": "<p>/////<br />    case 'param':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      tag.name = parts.shift() || '';<br />      tag.description = parts.join(' ');<br />      break;<br />    case 'return':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      tag.description = parts.join(' ');<br />      break;<br />    case 'see':<br />      if (~str.indexOf('http')) {<br />        tag.title = parts.length > 1<br />          ? parts.shift()<br />          : '';<br />        tag.url = parts.join(' ');<br />      } else {<br />        tag.local = parts.join(' ');<br />      }<br />    case 'api':<br />      tag.visibility = parts.shift();<br />      break;<br />    case 'type':<br />      tag.types = exports.parseTagTypes(parts.shift());<br />      break;<br />  }</p>",
      "body": "<p>return tag;<br />}</p>\n\n<p>/**<br />Parse tag type string \"{Array|Object}\" etc.</p>"
    },

So I create this pull request to care about single line comment too.

I write a new test, and all current tests are green.

I hope it will help.

@cbou

I also have a question, is it normal that this line /* shouldn't fail */ is found by the parser ?
I thought that only /** and /*! can be found..

@tj
Owner
tj commented

i didn't specifically omit /**/ support but no one really uses those for single-line comments

@cbou

What do you think about my pull request ?

@tj
Owner
tj commented

looks fine to me although i wouldn't recommend using that style anyway

@tj tj merged commit 1b9e8d0 into tj:master
@cbou

Which style do you mean ? Do you mean iteration over each character and test if a comment start ? Or something else ?

@tj
Owner
tj commented

no no using /* foo */ single-line comments

@cbou

Oh yes for sure but you want to continue to parse it. People who wants to ignore it in documentation should use /*! foo */ right ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Jul 4, 2012
  1. @cbou
This page is out of date. Refresh to see the latest.
Showing with 22 additions and 5 deletions.
  1. +13 −5 lib/dox.js
  2. +9 −0 test/dox.test.js
View
18 lib/dox.js
@@ -30,12 +30,13 @@ exports.parseComments = function(js, options){
, comment
, buf = ''
, ignore
- , within
+ , withinMultiline = false
+ , withinSignle = false
, code;
for (var i = 0, len = js.length; i < len; ++i) {
// start comment
- if (!within && '/' == js[i] && '*' == js[i+1]) {
+ if (!withinMultiline && !withinSignle && '/' == js[i] && '*' == js[i+1]) {
// code following previous comment
if (buf.trim().length) {
comment = comments[comments.length - 1];
@@ -46,17 +47,24 @@ exports.parseComments = function(js, options){
buf = '';
}
i += 2;
- within = true;
+ withinMultiline = true;
ignore = '!' == js[i];
// end comment
- } else if (within && '*' == js[i] && '/' == js[i+1]) {
+ } else if (withinMultiline && !withinSignle && '*' == js[i] && '/' == js[i+1]) {
i += 2;
buf = buf.replace(/^ *\* ?/gm, '');
var comment = exports.parseComment(buf, options);
comment.ignore = ignore;
comments.push(comment);
- within = ignore = false;
+ withinMultiline = ignore = false;
buf = '';
+ } else if (!withinSignle && !withinMultiline && '/' == js[i] && '/' == js[i+1]) {
+ i += 2;
+ withinSignle = true;
+ buf += js[i];
+ } else if (withinSignle && !withinMultiline && '\n' == js[i]) {
+ withinSignle = false;
+ buf += js[i];
// buffer comment or code
} else {
buf += js[i];
View
9 test/dox.test.js
@@ -110,6 +110,15 @@ module.exports = {
parseComment.description.full.should.equal('<p>Parse the given comment <code>str</code>.</p>\n\n<h2>The comment object returned contains the following</h2>\n\n<ul>\n<li><code>tags</code> array of tag objects</li>\n<li><code>description</code> the first line of the comment</li>\n<li><code>body</code> lines following the description</li>\n<li><code>content</code> both the description and the body</li>\n<li><code>isPrivate</code> true when "@api private" is used</li>\n</ul>');
parseComment.description.body.should.equal('<h2>The comment object returned contains the following</h2>\n\n<ul>\n<li><code>tags</code> array of tag objects</li>\n<li><code>description</code> the first line of the comment</li>\n<li><code>body</code> lines following the description</li>\n<li><code>content</code> both the description and the body</li>\n<li><code>isPrivate</code> true when "@api private" is used</li>\n</ul>');
+ var parseTag = comments.shift();
+
+ // Should be the comment be parsed ?
+ var shouldNotFail = comments.shift();
+
+ var parseTagTypes = comments.shift();
+ parseTagTypes.tags.should.have.length(3);
+ parseTagTypes.description.full.should.equal('<p>Parse tag type string \"{Array|Object}\" etc.</p>');
+
var escape = comments.pop();
escape.tags.should.have.length(3);
escape.description.full.should.equal('<p>Escape the given <code>html</code>.</p>');
Something went wrong with that request. Please try again.