243 lines
6.8 KiB
JavaScript
243 lines
6.8 KiB
JavaScript
/** @constructor */
|
|
JSDOC.SymbolSet = function() {
|
|
this.init();
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.init = function() {
|
|
this._index = new Hash();
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.keys = function() {
|
|
return this._index.keys();
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.hasSymbol = function(alias) {
|
|
return this._index.hasKey(alias);
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.addSymbol = function(symbol) {
|
|
if (this.hasSymbol(symbol.alias)) {
|
|
LOG.warn("Overwriting symbol documentation for: "+symbol.alias + ".");
|
|
}
|
|
this._index.set(symbol.alias, symbol);
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.getSymbol = function(alias) {
|
|
if (this.hasSymbol(alias)) return this._index.get(alias);
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.getSymbolByName = function(name) {
|
|
for (var p = this._index.first(); p; p = this._index.next()) {
|
|
var symbol = p.value;
|
|
if (symbol.name == name) return symbol;
|
|
}
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.toArray = function() {
|
|
return this._index.values();
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.deleteSymbol = function(alias) {
|
|
if (!this.hasSymbol(alias)) return;
|
|
this._index.drop(alias);
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.renameSymbol = function(oldName, newName) {
|
|
// todo: should check if oldname or newname already exist
|
|
this._index.replace(oldName, newName);
|
|
this._index.get(newName).alias = newName;
|
|
return newName;
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.relate = function() {
|
|
this.resolveBorrows();
|
|
this.resolveMemberOf();
|
|
this.resolveAugments();
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.resolveBorrows = function() {
|
|
for (var p = this._index.first(); p; p = this._index.next()) {
|
|
var symbol = p.value;
|
|
if (symbol.is("FILE") || symbol.is("GLOBAL")) continue;
|
|
|
|
var borrows = symbol.inherits;
|
|
for (var i = 0; i < borrows.length; i++) {
|
|
|
|
if (/#$/.test(borrows[i].alias)) {
|
|
LOG.warn("Attempted to borrow entire instance of "+borrows[i].alias+" but that feature is not yet implemented.");
|
|
return;
|
|
}
|
|
var borrowed = this.getSymbol(borrows[i].alias);
|
|
|
|
if (!borrowed) {
|
|
LOG.warn("Can't borrow undocumented "+borrows[i].alias+".");
|
|
continue;
|
|
}
|
|
|
|
if (borrows[i].as == borrowed.alias) {
|
|
var assumedName = borrowed.name.split(/([#.-])/).pop();
|
|
borrows[i].as = symbol.name+RegExp.$1+assumedName;
|
|
LOG.inform("Assuming borrowed as name is "+borrows[i].as+" but that feature is experimental.");
|
|
}
|
|
|
|
var borrowAsName = borrows[i].as;
|
|
var borrowAsAlias = borrowAsName;
|
|
if (!borrowAsName) {
|
|
LOG.warn("Malformed @borrow, 'as' is required.");
|
|
continue;
|
|
}
|
|
|
|
if (borrowAsName.length > symbol.alias.length && borrowAsName.indexOf(symbol.alias) == 0) {
|
|
borrowAsName = borrowAsName.replace(borrowed.alias, "")
|
|
}
|
|
else {
|
|
var joiner = "";
|
|
if (borrowAsName.charAt(0) != "#") joiner = ".";
|
|
borrowAsAlias = borrowed.alias + joiner + borrowAsName;
|
|
}
|
|
|
|
borrowAsName = borrowAsName.replace(/^[#.]/, "");
|
|
|
|
if (this.hasSymbol(borrowAsAlias)) continue;
|
|
|
|
var clone = borrowed.clone();
|
|
clone.name = borrowAsName;
|
|
clone.alias = borrowAsAlias;
|
|
this.addSymbol(clone);
|
|
}
|
|
}
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.resolveMemberOf = function() {
|
|
for (var p = this._index.first(); p; p = this._index.next()) {
|
|
var symbol = p.value;
|
|
|
|
if (symbol.is("FILE") || symbol.is("GLOBAL")) continue;
|
|
|
|
// the memberOf value was provided in the @memberOf tag
|
|
else if (symbol.memberOf) {
|
|
// like foo.bar is a memberOf foo
|
|
if (symbol.alias.indexOf(symbol.memberOf) == 0) {
|
|
var memberMatch = new RegExp("^("+symbol.memberOf+")[.#-]?(.+)$");
|
|
var aliasParts = symbol.alias.match(memberMatch);
|
|
|
|
if (aliasParts) {
|
|
symbol.memberOf = aliasParts[1];
|
|
symbol.name = aliasParts[2];
|
|
}
|
|
|
|
var nameParts = symbol.name.match(memberMatch);
|
|
|
|
if (nameParts) {
|
|
symbol.name = nameParts[2];
|
|
}
|
|
}
|
|
// like bar is a memberOf foo
|
|
else {
|
|
var joiner = symbol.memberOf.charAt(symbol.memberOf.length-1);
|
|
if (!/[.#-]/.test(joiner)) symbol.memberOf += ".";
|
|
this.renameSymbol(symbol.alias, symbol.memberOf + symbol.name);
|
|
}
|
|
}
|
|
// the memberOf must be calculated
|
|
else {
|
|
var parts = symbol.alias.match(/^(.*[.#-])([^.#-]+)$/);
|
|
|
|
if (parts) {
|
|
symbol.memberOf = parts[1];
|
|
symbol.name = parts[2];
|
|
}
|
|
}
|
|
|
|
// set isStatic, isInner
|
|
if (symbol.memberOf) {
|
|
switch (symbol.memberOf.charAt(symbol.memberOf.length-1)) {
|
|
case '#' :
|
|
symbol.isStatic = false;
|
|
symbol.isInner = false;
|
|
break;
|
|
case '.' :
|
|
symbol.isStatic = true;
|
|
symbol.isInner = false;
|
|
break;
|
|
case '-' :
|
|
symbol.isStatic = false;
|
|
symbol.isInner = true;
|
|
break;
|
|
default: // memberOf ends in none of the above
|
|
symbol.isStatic = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
// unowned methods and fields belong to the global object
|
|
if (!symbol.is("CONSTRUCTOR") && !symbol.isNamespace && symbol.memberOf == "") {
|
|
symbol.memberOf = "_global_";
|
|
}
|
|
|
|
// clean up
|
|
if (symbol.memberOf.match(/[.#-]$/)) {
|
|
symbol.memberOf = symbol.memberOf.substr(0, symbol.memberOf.length-1);
|
|
}
|
|
// add to parent's methods or properties list
|
|
if (symbol.memberOf) {
|
|
|
|
var container = this.getSymbol(symbol.memberOf);
|
|
if (!container) {
|
|
if (JSDOC.Lang.isBuiltin(symbol.memberOf)) container = JSDOC.Parser.addBuiltin(symbol.memberOf);
|
|
else {
|
|
LOG.warn("Trying to document "+symbol.name +" as a member of undocumented symbol "+symbol.memberOf+".");
|
|
}
|
|
}
|
|
|
|
if (container) container.addMember(symbol);
|
|
}
|
|
}
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.resolveAugments = function() {
|
|
for (var p = this._index.first(); p; p = this._index.next()) {
|
|
var symbol = p.value;
|
|
|
|
if (symbol.alias == "_global_" || symbol.is("FILE")) continue;
|
|
JSDOC.SymbolSet.prototype.walk.apply(this, [symbol]);
|
|
}
|
|
}
|
|
|
|
JSDOC.SymbolSet.prototype.walk = function(symbol) {
|
|
var augments = symbol.augments;
|
|
for(var i = 0; i < augments.length; i++) {
|
|
var contributer = this.getSymbol(augments[i]);
|
|
if (!contributer && JSDOC.Lang.isBuiltin(''+augments[i])) {
|
|
contributer = new JSDOC.Symbol("_global_."+augments[i], [], augments[i], new JSDOC.DocComment("Built in."));
|
|
contributer.isNamespace = true;
|
|
contributer.srcFile = "";
|
|
contributer.isPrivate = false;
|
|
JSDOC.Parser.addSymbol(contributer);
|
|
}
|
|
|
|
if (contributer) {
|
|
if (contributer.augments.length) {
|
|
JSDOC.SymbolSet.prototype.walk.apply(this, [contributer]);
|
|
}
|
|
|
|
symbol.inheritsFrom.push(contributer.alias);
|
|
//if (!isUnique(symbol.inheritsFrom)) {
|
|
// LOG.warn("Can't resolve augments: Circular reference: "+symbol.alias+" inherits from "+contributer.alias+" more than once.");
|
|
//}
|
|
//else {
|
|
var cmethods = contributer.methods;
|
|
var cproperties = contributer.properties;
|
|
|
|
for (var ci = 0, cl = cmethods.length; ci < cl; ci++) {
|
|
if (!cmethods[ci].isStatic) symbol.inherit(cmethods[ci]);
|
|
}
|
|
for (var ci = 0, cl = cproperties.length; ci < cl; ci++) {
|
|
if (!cproperties[ci].isStatic) symbol.inherit(cproperties[ci]);
|
|
}
|
|
//}
|
|
}
|
|
else LOG.warn("Can't augment contributer: "+augments[i]+", not found.");
|
|
}
|
|
}
|