From edb1be2a0dd3aa47f347888fcca29b3301c758bc Mon Sep 17 00:00:00 2001 From: mathematicalcoffee Date: Mon, 26 Nov 2012 17:17:21 +1000 Subject: [PATCH] first attempt at adding cleverLinks and monospaceLinks features; needs testing --- rhino_modules/jsdoc/config.js | 4 +- rhino_modules/jsdoc/util/templateHelper.js | 36 ++++++- test/specs/jsdoc/util/templateHelper.js | 104 +++++++++++++++++++++ 3 files changed, 139 insertions(+), 5 deletions(-) diff --git a/rhino_modules/jsdoc/config.js b/rhino_modules/jsdoc/config.js index 8cc6c61c..b70933b1 100644 --- a/rhino_modules/jsdoc/config.js +++ b/rhino_modules/jsdoc/config.js @@ -15,7 +15,9 @@ var util = require('common/util'); // required config values, override these defaults in your config.json if necessary const defaults = { "tags": { - "allowUnknownTags": true + "allowUnknownTags": true, + "monospaceLinks": false, + "cleverLinks": false }, "source": { "includePattern": ".+\\.js(doc)?$", diff --git a/rhino_modules/jsdoc/util/templateHelper.js b/rhino_modules/jsdoc/util/templateHelper.js index 3c19f32b..294fcc99 100644 --- a/rhino_modules/jsdoc/util/templateHelper.js +++ b/rhino_modules/jsdoc/util/templateHelper.js @@ -425,11 +425,16 @@ exports.registerLink = function(longname, url) { linkMap.urlToLongname[url] = longname; }; -function toLink(longname, content) { +function toLink(longname, content, monospace) { if (!longname) { // if this happens, there's something wrong with the caller itself; the user can't fix this throw new Error('Missing required parameter: url'); } + var monospaceLinks = env.conf.tags.monospaceLinks; + var cleverLinks = env.conf.tags.cleverLinks; + //console.log('monospaceLinks: ' + monospaceLinks); + //console.log('cleverLinks: ' + cleverLinks); + // Split into URL and content. // Has link text been specified {@link link|content}, e.g. @@ -448,8 +453,10 @@ function toLink(longname, content) { } var url; + var isURL = false; // Has link been specified manually? if (/^(http|ftp)s?:/.test(longname)) { + isURL = true; url = longname; } else { @@ -463,6 +470,20 @@ function toLink(longname, content) { return content; } else { + if (monospace === undefined) { + // cleverLinks takes precedence. if cleverLinks is true + // we ignore monospaceLinks. + // If it's a symbol we use monospace font. + // Otherwise if cleverLinks is `false` we use monospaceLinks. + if (cleverLinks) { + monospace = !isURL; + } else { + monospace = monospaceLinks; + } + } + if (monospace) { + content = '' + content + ''; + } return ''+content+''; } } @@ -530,9 +551,16 @@ var toTutorial = exports.toTutorial = function(tutorial, content, missingOpts) { /** Find symbol {@link ...} and {@tutorial ...} strings in text and turn into html links */ exports.resolveLinks = function(str) { - str = str.replace(/(?:\[(.+?)\])?\{@link +(.+?)\}/gi, - function(match, content, longname) { - return toLink(longname, content); + str = str.replace(/(?:\[(.+?)\])?\{@link(plain|code)? +(.+?)\}/gi, + function(match, content, monospace, longname) { + if (monospace === 'plain') { + monospace = false; + } else if (monospace === 'code') { + monospace = true; + } else { + monospace = undefined; + } + return toLink(longname, content, monospace); } ); diff --git a/test/specs/jsdoc/util/templateHelper.js b/test/specs/jsdoc/util/templateHelper.js index 3a87954d..2afea5d8 100644 --- a/test/specs/jsdoc/util/templateHelper.js +++ b/test/specs/jsdoc/util/templateHelper.js @@ -1,5 +1,24 @@ /*global afterEach: true, beforeEach: true, describe: true, expect: true, env: true, it: true, xdescribe: true, xit: true */ + +function setConfTagsVariables(hash) { + var keys = Object.keys(hash); + var storage = {}; + for (var i = 0; i < keys.length; ++i) { + storage[keys[i]] = env.conf.tags[keys[i]]; + // works because hash[key] is a scalar not an array/object + env.conf.tags[keys[i]] = hash[keys[i]]; + console.log(keys[i] + ': ' + env.conf.tags.keys[i] + ' (' + hash[keys[i]] + ')'); + } + return storage; +} + +function restoreConfTags(storage) { + var keys = Object.keys(hash); + for (var i = 0; i < keys.length; ++i) { + env.conf.tags[keys[i]] = storage[keys[i]]; + } +} describe("jsdoc/util/templateHelper", function() { var helper = require('jsdoc/util/templateHelper'); helper.registerLink('test', 'path/to/test.html'); @@ -468,6 +487,91 @@ describe("jsdoc/util/templateHelper", function() { expect(output).toEqual('Link to My Caption'); }); + it('Test of {@linkcode } which should be in monospace', function() { + var input = 'Link to {@linkcode test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + }); + + it('Test of {@linkplain } which should be in normal font', function() { + var input = 'Link to {@linkplain test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + }); + + // conf.monospaceLinks. check that + // a) it works + it('if conf.monospaceLinks is true, all {@link} should be monospace', function () { + var storage = setConfTagsVariables({monospaceLinks: true}); + env.conf.tags.monospaceLinks = true; + var input = 'Link to {@link test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + // b) linkcode and linkplain are still respected + it('if conf.monospaceLinks is true, all {@linkcode} should still be monospace', function () { + var storage = setConfTagsVariables({monospaceLinks: true}); + var input = 'Link to {@linkcode test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + it('if conf.monospaceLinks is true, all {@linkplain} should still be plain', function () { + var storage = setConfTagsVariables({monospaceLinks: true}); + var input = 'Link to {@linkplain test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + // conf.cleverLinks. check that + // a) it works + it('if conf.cleverLinks is true, {@link symbol} should be in monospace', function () { + var storage = setConfTagsVariables({cleverLinks: true}); + var input = 'Link to {@link test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + it('if conf.cleverLinks is true, {@link URL} should be in plain text', function () { + var storage = setConfTagsVariables({cleverLinks: true}); + var input = 'Link to {@link http://github.com}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to http://github.com'); + restoreConfTags(storage); + }); + + // b) linkcode and linkplain are still respected + it('if conf.cleverLinks is true, all {@linkcode} should still be clever', function () { + var storage = setConfTagsVariables({cleverLinks: true}); + var input = 'Link to {@linkcode test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + it('if conf.cleverLinks is true, all {@linkplain} should still be plain', function () { + var storage = setConfTagsVariables({cleverLinks: true}); + var input = 'Link to {@linkplain test}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test'); + restoreConfTags(storage); + }); + + // c) if monospaceLinks is additionally `true` it is ignored in favour + // of cleverLinks + it('if conf.cleverLinks is true and so is conf.monospaceLinks, cleverLinks overrides', function () { + var storage = setConfTagsVariables({cleverLinks: true, monospaceLinks: true}); + var input = 'Link to {@link test} and {@link http://github.com}', + output = helper.resolveLinks(input); + expect(output).toEqual('Link to test and http://github.com'); + restoreConfTags(storage); + }); + }); // disabled because Jasmine appears to execute this code twice, which causes createLink to