diff --git a/api/README.runserver.txt b/api/README.runserver.txt new file mode 100644 index 0000000000..7b04917f01 --- /dev/null +++ b/api/README.runserver.txt @@ -0,0 +1,11 @@ +== Installation on Ubuntu VM == + +apt-get update +apt-get install nodejs npm git build-essential +npm install -g express html5 lru-cache jquery pegjs async jshashes +adduser --system --home /var/lib/parsoid parsoid +cd /var/lib/parsoid +git clone +https://gerrit.wikimedia.org/r/p/mediawiki/extensions/VisualEditor.git +cd VisualEditor/api +./runserver.sh diff --git a/api/runserver.sh b/api/runserver.sh new file mode 100755 index 0000000000..21826a6f00 --- /dev/null +++ b/api/runserver.sh @@ -0,0 +1,6 @@ +#!/bin/sh +# redirect port 80 to unprivileged port 8000 +iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-ports 8000 + +# run the server as non-privileged user +nohup sudo -u nobody node server.js & diff --git a/modules/parser/ext.core.LinkHandler.js b/modules/parser/ext.core.LinkHandler.js index fa5f3f7404..2f4d43b67a 100644 --- a/modules/parser/ext.core.LinkHandler.js +++ b/modules/parser/ext.core.LinkHandler.js @@ -343,9 +343,13 @@ function ExternalLinkHandler( manager, isInclude ) { // img_options production only. ExternalLinkHandler.prototype.imageParser = new PegTokenizer(); } - this.onEnd(); + this._reset(); } +ExternalLinkHandler.prototype._reset = function () { + this.linkCount = 1; +}; + ExternalLinkHandler.prototype.rank = 1.15; ExternalLinkHandler.prototype._imageExtensions = { 'jpg': true, @@ -403,6 +407,10 @@ ExternalLinkHandler.prototype.onExtLink = function ( token, manager, cb ) { //console.warn('extlink href: ' + href ); //console.warn( 'content: ' + JSON.stringify( content, null, 2 ) ); // validate the href + if ( ! content.length ) { + content = ['[' + this.linkCount + ']']; + this.linkCount++; + } if ( this.imageParser.tokenizeURL( href ) ) { if ( content.length === 1 && content[0].constructor === String && @@ -433,10 +441,6 @@ ExternalLinkHandler.prototype.onExtLink = function ( token, manager, cb ) { ].concat( content, [ new EndTagTk( 'a' )]) } ); } else { - if ( content === '' ) { - content = ['[' + this.linkCount + ']']; - this.linkCount++; - } cb( { tokens: ['[', href, ' ' ].concat( content, [']'] ) } ); @@ -444,8 +448,8 @@ ExternalLinkHandler.prototype.onExtLink = function ( token, manager, cb ) { }; ExternalLinkHandler.prototype.onEnd = function ( token, manager, cb ) { - this.linkCount = 1; - return { tokens: token }; + this._reset(); + cb( { tokens: [ token ] } ); }; diff --git a/modules/parser/mediawiki.TokenTransformManager.js b/modules/parser/mediawiki.TokenTransformManager.js index 66bafad9bf..0a792b1a6f 100644 --- a/modules/parser/mediawiki.TokenTransformManager.js +++ b/modules/parser/mediawiki.TokenTransformManager.js @@ -435,6 +435,12 @@ AsyncTokenTransformManager.prototype.transformTokens = function ( tokens, parent // maybeSyncReturn callback if ( resTokens && resTokens.length ) { if ( resTokens.length === 1 ) { + if ( resTokens[0] === undefined ) { + console.warn('transformer ' + transformer + + ' returned undefined token!'); + resTokens.shift(); + break; + } if ( token === resTokens[0] && ! resTokens.rank ) { // token not modified, continue with // transforms.