7 dox
property

version

exports.version

Library version.

    exports.version = '0.3.1';
    method

    parseComments

    exports.parseComments()

    Parse comments in the given string of js.

    • @param: {String} js
    • @param: {Object} options
    • @return: {Array}
    • @see: exports.parseComment
    exports.parseComments = function(js, options){
      options = options || {};
    
      var comments = []
        , raw = options.raw
        , comment
        , buf = ''
        , ignore
        , within
        , code;
    
      for (var i = 0, len = js.length; i < len; ++i) {
        // start comment
        if (!within && '/' == js[i] && '*' == js[i+1]) {
          // code following previous comment
          if (buf.trim().length) {
            comment = comments[comments.length - 1];
            if(comment) {
              comment.code = code = buf.trim();
              comment.ctx = exports.parseCodeContext(code);
            }
            buf = '';
          }
          i += 2;
          within = true;
          ignore = '!' == js[i];
        // end comment
        } else if (within && '*' == 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;
          buf = '';
        // buffer comment or code
        } else {
          buf += js[i];
        }
      }
    
      // trailing code
      if (buf.trim().length) {
        console.log(comments.length);
        comment = comments[comments.length - 1];
        code = buf.trim();
        comment.code = code;
        comment.ctx = exports.parseCodeContext(code);
      }
    
      return comments;
    };
    method

    parseComment

    exports.parseComment()

    Parse the given comment str.

    The comment object returned contains the following

    • tags array of tag objects
    • description the first line of the comment
    • body lines following the description
    • content both the description and the body
    • isPrivate true when "@api private" is used
    • @param: {String} str
    • @param: {Object} options
    • @return: {Object}
    • @see: exports.parseTag
    exports.parseComment = function(str, options) {
      str = str.trim();
      options = options || {};
    
      var comment = { tags: [] }
        , raw = options.raw
        , description = {};
    
      // parse comment body
      description.full = str.split('\n@')[0].replace(/^([A-Z][\w ]+):$/gm, '## $1');
      description.summary = description.full.split('\n\n')[0];
      description.body = description.full.split('\n\n').slice(1).join('\n\n');
      comment.description = description;
    
      // parse tags
      if (~str.indexOf('\n@')) {
        var tags = '@' + str.split('\n@').slice(1).join('\n@');
        comment.tags = tags.split('\n').map(exports.parseTag);
        comment.isPrivate = comment.tags.some(function(tag){
          return 'api' == tag.type && 'private' == tag.visibility;
        })
      }
    
      // markdown
      if (!raw) {
        description.full = markdown(description.full);
        description.summary = markdown(description.summary);
        description.body = markdown(description.body);
      }
    
      return comment;
    }
    method

    parseTag

    exports.parseTag()

    Parse tag string "@param {Array} name description" etc.

    • @param: {String}
    • @return: {Object}
    exports.parseTag = function(str) {
      var tag = {} 
        , parts = str.split(/ +/)
        , type = tag.type = parts.shift().replace('@', '');
    
      switch (type) {
        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;
        case 'memberOf':
          tag.parent = parts.shift();
          break;
        case 'augments':
          tag.otherClass = parts.shift();
          break;
        case 'borrows':
          tag.otherMemberName = parts.join(' ').split(' as ')[0];
          tag.thisMemberName = parts.join(' ').split(' as ')[1];
          break;
        default:
          tag.string = parts.join(' ');
          break;
      }
    
      return tag;
    }
    method

    parseTagTypes

    exports.parseTagTypes()

    Parse tag type string "{Array|Object}" etc.

    • @param: {String} str
    • @return: {Array}
    exports.parseTagTypes = function(str) {
      return str
        .replace(/[{}]/g, '')
        .split(/ *[|,\/] */);
    };
    method

    parseCodeContext

    exports.parseCodeContext()

    Parse the context from the given str of js.

    This method attempts to discover the context
    for the comment based on it's code. Currently
    supports:

    • function statements
    • function expressions
    • prototype methods
    • prototype properties
    • methods
    • properties
    • declarations
    • @param: {String} str
    • @return: {Object}
    exports.parseCodeContext = function(str){
      var str = str.split('\n')[0];
    
      // function statement
      if (/^function (\w+) *\(/.exec(str)) {
        return {
            type: 'function'
          , name: RegExp.$1
          , string: RegExp.$1 + '()'
        };
      // function expression
      } else if (/^var *(\w+) *= *function/.exec(str)) {
        return {
            type: 'function'
          , name: RegExp.$1
          , string: RegExp.$1 + '()'
        };
      // prototype method
      } else if (/^(\w+)\.prototype\.(\w+) *= *function/.exec(str)) {
        return {
            type: 'method'
          , constructor: RegExp.$1
          , name: RegExp.$2
          , string: RegExp.$1 + '.prototype.' + RegExp.$2 + '()'
        };
      // prototype property
      } else if (/^(\w+)\.prototype\.(\w+) *= *([^\n;]+)/.exec(str)) {
        return {
            type: 'property'
          , constructor: RegExp.$1
          , name: RegExp.$2
          , value: RegExp.$3
          , string: RegExp.$1 + '.prototype' + RegExp.$2
        };
      // method
      } else if (/^(\w+)\.(\w+) *= *function/.exec(str)) {
        return {
            type: 'method'
          , receiver: RegExp.$1
          , name: RegExp.$2
          , string: RegExp.$1 + '.' + RegExp.$2 + '()'
        };
      // property
      } else if (/^(\w+)\.(\w+) *= *([^\n;]+)/.exec(str)) {
        return {
            type: 'property'
          , receiver: RegExp.$1
          , name: RegExp.$2
          , value: RegExp.$3
          , string: RegExp.$1 + '.' + RegExp.$2
        };
      // declaration
      } else if (/^var +(\w+) *= *([^\n;]+)/.exec(str)) {
        return {
            type: 'declaration'
          , name: RegExp.$1
          , value: RegExp.$2
          , string: RegExp.$1
        };
      }
    };