mediawiki-extensions-Cite/lib/ext.Cite.js

549 lines
16 KiB
JavaScript
Raw Normal View History

Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
/* ----------------------------------------------------------------------
* This file implements <ref> and <references> extension tag handling
* natively in Parsoid.
* ---------------------------------------------------------------------- */
'use strict';
require('./core-upgrade.js');
var Util = require('./mediawiki.Util.js').Util;
var DU = require('./mediawiki.DOMUtils.js').DOMUtils;
var coreutil = require('util');
var defines = require('./mediawiki.parser.defines.js');
var entities = require('entities');
// define some constructor shortcuts
var KV = defines.KV;
var EOFTk = defines.EOFTk;
var SelfclosingTagTk = defines.SelfclosingTagTk;
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
// FIXME: Move out to some common helper file?
// Helper function to process extension source
function processExtSource(manager, extToken, opts) {
var extSrc = extToken.getAttribute('source');
var tagWidths = extToken.dataAttribs.tagWidths;
var content = extSrc.substring(tagWidths[0], extSrc.length - tagWidths[1]);
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
// FIXME: Should this be specific to the extension
// Or is it okay to do this unconditionally for all?
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
// Right now, this code is run only for ref and references,
// so not a real problem, but if this is used on other extensions,
// requires addressing.
//
// FIXME: SSS: This stripping maybe be unnecessary after all.
//
// Strip all leading white-space
var wsMatch = content.match(/^(\s*)([^]*)$/);
var leadingWS = wsMatch[1];
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
// Update content to normalized form
content = wsMatch[2];
if (!content || content.length === 0) {
opts.emptyContentCB(opts.res);
} else {
// Pass an async signal since the ext-content is not processed completely.
opts.parentCB({tokens: opts.res, async: true});
// Wrap templates always
opts.pipelineOpts = Util.extendProps({}, opts.pipelineOpts, { wrapTemplates: true });
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
var tsr = extToken.dataAttribs.tsr;
opts.srcOffsets = [ tsr[0] + tagWidths[0] + leadingWS.length, tsr[1] - tagWidths[1] ];
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
// Process ref content
Util.processContentInPipeline(manager.env, manager.frame, content, opts);
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
}
}
/**
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
* Simple token transform version of the Ref extension tag
*
* @class
* @constructor
*/
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
function Ref(cite) {
this.cite = cite;
}
function hasRef(node) {
var c = node.firstChild;
while (c) {
if (DU.isElt(c)) {
var typeOf = c.getAttribute('typeof');
if ((/(?:^|\s)mw:Extension\/ref\/Marker(?=$|\s)/).test(typeOf)) {
return true;
}
if (hasRef(c)) {
return true;
}
}
c = c.nextSibling;
}
return false;
}
/**
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
* Handle ref tokens
*/
Ref.prototype.handleRef = function(manager, pipelineOpts, refTok, cb) {
// Nested <ref> tags at the top level are considered errors
// But, inside templates, they are supported
if (!pipelineOpts.inTemplate && pipelineOpts.extTag === "ref") {
cb({ tokens: [refTok.getAttribute("source")] });
return;
}
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
var refOpts = Object.assign({
name: null,
group: null,
}, Util.KVtoHash(refTok.getAttribute("options"), true));
var about = manager.env.newAboutId();
var finalCB = function(toks, contentBody) {
// Marker meta with ref content
var da = Util.clone(refTok.dataAttribs);
// Clear stx='html' so that sanitizer doesn't barf
da.stx = undefined;
da.group = refOpts.group || '';
da.name = refOpts.name || '';
da.content = contentBody ? DU.serializeChildren(contentBody) : '';
da.hasRefInRef = contentBody ? hasRef(contentBody) : false;
toks.push(new SelfclosingTagTk('meta', [
new KV('typeof', 'mw:Extension/ref/Marker'),
new KV('about', about)
], da));
// All done!
cb({ tokens: toks, async: false });
};
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
processExtSource(manager, refTok, {
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
// Full pipeline for processing ref-content
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
pipelineType: 'text/x-mediawiki/full',
pipelineOpts: {
(Bug 64901) Fix paragraph-wrapping to match PHP parser + Tidy combo General changes --------------- * Replaced the hacky 'inBlockNode' parser pipeline option with a cleaner 'noPWrapping' option that suppresses paragraph wrapping in sub-pipelines (ex: recursive link content, ref tags, attribute content, etc.). Changes to wt2html pipeline --------------------------- * Fixed paragraph-wrapping code to ensure that there are no bare text nodes left behind, but without removing the line-based block-tag influences on p-wrapping. Some simplifications as well. TODO: There are still some discrepancies around <blockquote> p-wrapping behavior. These will be investigated and addressed in a future patch. * Fixed foster parenting code to ensure that fostered content is added in p-tags where necessary rather than span-tags. Changes to html2wt/selser pipeline ---------------------------------- * Fixed DOMDiff to tag mw:DiffMarker nodes with a is-block-node attribute when the deleted node is a block node. This is used during selective serialization to discard original separators between adjacent p-nodes if either of their neighbors is a deleted block node. * Fixed serialization to account for changes to p-wrapping. - Updated tag handlers for the <p> tag. - Updated separator handling to deal with deleted block tags and their influence on separators around adjacent p-tags. - Updated selser output code to test whether a deleted block tag forces nowiki escaping on unedited content from adjacent p-tags. Changes to parser tests / test setup ------------------------------------ * Tweaked selser test generation to ensure that text nodes are always inserted in p-wrappers where necessary. * Updated parser test output for several tests to introduce p-tags instead of span-tags or missing p-tags, add html/parsoid section, or in one case, add missing HTML output. Parser Test Result changes -------------------------- Newly passing - 12 wt2html - 1 wt2wt - 3 html2html - 3 html2wt Newly failing - 1 html2wt "3. Leading whitespace in indent-pre suppressing contexts should not be escaped" This is just normalization of output where multiple HTML forms serialize to the same wikitext with a newline difference. It is not worth the complexity to fix this. - 1 wt2wt ""Trailing newlines in a deep dom-subtree that ends a wikitext line" This is again normalization during serialization where an extra unnecessary newline is introduced. - A bunch of selser test changes. 182 +add, 188 -add => 6 fewer selser failures - That is a lot of changes to sift through, and I didn't look at every one of those, but a number of changes seem to be harmless, and just a change to previously "failing" tests. - "Media link with nasty text" test seems to have a lot of selser changes, but the HTML generated by Parsoid seems to be "buggy" with interesting DSR values as well. That needs investigation separately. - "HTML nested bullet list, closed tags (bug 5497) [[3,3,4,[0,1,4],3]]" has seen a degradation where a dirty diff got introduced. Haven't investigated carefully why that is so. Change-Id: Ia9c9950717120fbcd03abfe4e09168e787669ac4
2014-08-29 05:59:20 +00:00
extTag: "ref",
inTemplate: pipelineOpts.inTemplate,
Introduce Parsing/DOM scopes for content fragments * Added mechanism to parse a set of tokens in its own parsing scope all the way to DOM (which in turn restricts token transformations to just that scope). This is equivalent to enforcing well-balanced requirements in restricted contexts (Ex: link content, image captions for starters). This also provides an option of enforcing balanced templates in certain contexts. This patch applies it to link content and image captions. Deleted the hacky closeUnclosedBlockTags code for dealing with bad HTML in captions. * Refactored common/duplicate code out of Cite handler and Template handler. * Updated DSR handling for dom-fragments which eliminates the warnings about cs/s dsr mismatches seen on image reuse. it:Dalmine used to get a bunch of DSR inconsistency warnings when dom-fragments were reused (reported in bug 53071) and are now fixed with this patch. * There is still one big hole in DOM fragment unpacking that has to be fixed. This pertains to improper tag nesting that will be broken up by the tree builder. The DOM fragment unpacker has to recognize these scenarios and fix up the DOM (either by fixing up the final DOM or by stripping mis-nested tags in the DOM fragment being unpacked). This patch has an incomplete hack for this that addresses the common-use case of nested a-tags generated by wikitext of this form: "[http://foo.bar a [[Wikilink] here]". Bug: 54454 Bug: 49942 Bug: 44476 Bug: 47326 Change-Id: I33ee38bc43743125b705ac821b339586593dbef7
2013-09-24 01:07:29 +00:00
noPre: true,
(Bug 64901) Fix paragraph-wrapping to match PHP parser + Tidy combo General changes --------------- * Replaced the hacky 'inBlockNode' parser pipeline option with a cleaner 'noPWrapping' option that suppresses paragraph wrapping in sub-pipelines (ex: recursive link content, ref tags, attribute content, etc.). Changes to wt2html pipeline --------------------------- * Fixed paragraph-wrapping code to ensure that there are no bare text nodes left behind, but without removing the line-based block-tag influences on p-wrapping. Some simplifications as well. TODO: There are still some discrepancies around <blockquote> p-wrapping behavior. These will be investigated and addressed in a future patch. * Fixed foster parenting code to ensure that fostered content is added in p-tags where necessary rather than span-tags. Changes to html2wt/selser pipeline ---------------------------------- * Fixed DOMDiff to tag mw:DiffMarker nodes with a is-block-node attribute when the deleted node is a block node. This is used during selective serialization to discard original separators between adjacent p-nodes if either of their neighbors is a deleted block node. * Fixed serialization to account for changes to p-wrapping. - Updated tag handlers for the <p> tag. - Updated separator handling to deal with deleted block tags and their influence on separators around adjacent p-tags. - Updated selser output code to test whether a deleted block tag forces nowiki escaping on unedited content from adjacent p-tags. Changes to parser tests / test setup ------------------------------------ * Tweaked selser test generation to ensure that text nodes are always inserted in p-wrappers where necessary. * Updated parser test output for several tests to introduce p-tags instead of span-tags or missing p-tags, add html/parsoid section, or in one case, add missing HTML output. Parser Test Result changes -------------------------- Newly passing - 12 wt2html - 1 wt2wt - 3 html2html - 3 html2wt Newly failing - 1 html2wt "3. Leading whitespace in indent-pre suppressing contexts should not be escaped" This is just normalization of output where multiple HTML forms serialize to the same wikitext with a newline difference. It is not worth the complexity to fix this. - 1 wt2wt ""Trailing newlines in a deep dom-subtree that ends a wikitext line" This is again normalization during serialization where an extra unnecessary newline is introduced. - A bunch of selser test changes. 182 +add, 188 -add => 6 fewer selser failures - That is a lot of changes to sift through, and I didn't look at every one of those, but a number of changes seem to be harmless, and just a change to previously "failing" tests. - "Media link with nasty text" test seems to have a lot of selser changes, but the HTML generated by Parsoid seems to be "buggy" with interesting DSR values as well. That needs investigation separately. - "HTML nested bullet list, closed tags (bug 5497) [[3,3,4,[0,1,4],3]]" has seen a degradation where a dirty diff got introduced. Haven't investigated carefully why that is so. Change-Id: Ia9c9950717120fbcd03abfe4e09168e787669ac4
2014-08-29 05:59:20 +00:00
noPWrapping: true
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
},
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
res: [],
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
parentCB: cb,
emptyContentCB: finalCB,
documentCB: function(refContentDoc) {
finalCB([], refContentDoc.body);
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
}
});
};
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
/**
* Helper class used by <references> implementation
*/
function RefGroup(group) {
this.name = group || '';
this.refs = [];
this.indexByName = new Map();
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
}
function makeValidIdAttr(val) {
// Looks like Cite.php doesn't try to fix ids that already have
// a "_" in them. Ex: name="a b" and name="a_b" are considered
// identical. Not sure if this is a feature or a bug.
// It also considers entities equal to their encoding (i.e. '&' === '&amp;')
// and then substitutes % with .
var v = entities.decodeHTML(val).replace(/\s/g, '_');
return encodeURIComponent(v).replace(/%/g, ".");
}
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
RefGroup.prototype.renderLine = function(refsList, ref) {
var ownerDoc = refsList.ownerDocument;
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// Generate the li and set ref content first, so the HTML gets parsed.
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// We then append the rest of the ref nodes before the first node
var li = ownerDoc.createElement('li');
DU.addAttributes(li, {
'about': "#" + ref.target,
'id': ref.target
});
var reftextSpan = ownerDoc.createElement('span');
DU.addAttributes(reftextSpan, {
'id': "mw-reference-text-" + ref.target,
'class': "mw-reference-text"
});
reftextSpan.innerHTML = ref.content;
li.appendChild(reftextSpan);
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// Generate leading linkbacks
var createLinkback = function(href, group, text) {
var a = ownerDoc.createElement('a');
var span = ownerDoc.createElement('span');
var textNode = ownerDoc.createTextNode(text + " ");
a.setAttribute('href', href);
span.setAttribute('class', 'mw-linkback-text');
if (group) {
a.setAttribute('data-mw-group', group);
}
span.appendChild(textNode);
a.appendChild(span);
return a;
};
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
if (ref.linkbacks.length === 1) {
var linkback = createLinkback('#' + ref.id, ref.group, '↑');
linkback.setAttribute('rel', 'mw:referencedBy');
li.insertBefore(linkback, reftextSpan);
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
} else {
// 'mw:referencedBy' span wrapper
var span = ownerDoc.createElement('span');
span.setAttribute('rel', 'mw:referencedBy');
li.insertBefore(span, reftextSpan);
ref.linkbacks.forEach(function(lb, i) {
var linkback = createLinkback('#' + lb, ref.group, i + 1);
span.appendChild(linkback);
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
});
}
// Space before content node
li.insertBefore(ownerDoc.createTextNode(' '), reftextSpan);
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// Add it to the ref list
refsList.appendChild(li);
};
function ReferencesData() {
this.index = 0;
this.refGroups = new Map();
}
ReferencesData.prototype.getRefGroup = function(groupName, allocIfMissing) {
groupName = groupName || '';
if (!this.refGroups.has(groupName) && allocIfMissing) {
this.refGroups.set(groupName, new RefGroup(groupName));
}
return this.refGroups.get(groupName);
};
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
ReferencesData.prototype.removeRefGroup = function(groupName) {
if (groupName !== null && groupName !== undefined) {
// '' is a valid group (the default group)
this.refGroups.delete(groupName);
}
};
ReferencesData.prototype.add = function(groupName, refName, about, skipLinkback) {
var group = this.getRefGroup(groupName, true);
var ref;
refName = makeValidIdAttr(refName);
if (refName && group.indexByName.has(refName)) {
ref = group.indexByName.get(refName);
if (ref.content) {
ref.hasMultiples = true;
}
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
} else {
// The ids produced Cite.php have some particulars:
// Simple refs get 'cite_ref-' + index
// Refs with names get 'cite_ref-' + name + '_' + index + (backlink num || 0)
// Notes (references) whose ref doesn't have a name are 'cite_note-' + index
// Notes whose ref has a name are 'cite_note-' + name + '-' + index
var n = this.index;
var refKey = (1 + n) + '';
var refIdBase = 'cite_ref-' + (refName ? refName + '_' + refKey : refKey);
var noteId = 'cite_note-' + (refName ? refName + '-' + refKey : refKey);
// bump index
this.index += 1;
ref = {
about: about,
content: null,
group: group.name,
groupIndex: group.refs.length + 1,
index: n,
key: refIdBase,
id: (refName ? refIdBase + '-0' : refIdBase),
linkbacks: [],
name: refName,
target: noteId
};
group.refs.push(ref);
if (refName) {
group.indexByName.set(refName, ref);
}
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
}
if (!skipLinkback) {
ref.linkbacks.push(ref.key + '-' + ref.linkbacks.length);
}
return ref;
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
};
function References(cite) {
this.cite = cite;
}
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
/**
* Sanitize the references tag and convert it into a meta-token
*/
References.prototype.handleReferences = function(manager, pipelineOpts, refsTok, cb) {
var env = manager.env;
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
// group is the only recognized option?
var refsOpts = Object.assign({
group: null
}, Util.KVtoHash(refsTok.getAttribute("options"), true));
// Assign an about id and intialize the nested refs html
var referencesId = env.newAboutId();
// Emit a marker mw:DOMFragment for the references
// token so that the dom post processor can generate
// and emit references at this point in the DOM.
var emitReferencesFragment = function(toks, refsBody) {
var type = refsTok.getAttribute('typeof');
var olHTML = "<ol class='mw-references'" +
" typeof='mw:Extension/references'" +
" about='" + referencesId + "'" + ">" + (refsBody || "") + "</ol>";
var olProcessor = function(ol) {
var dp = DU.getDataParsoid(ol);
dp.src = refsTok.getAttribute('source');
if (refsOpts.group) {
dp.group = refsOpts.group;
ol.setAttribute('data-mw-group', refsOpts.group);
}
DU.storeDataParsoid(ol, dp);
};
cb({
async: false,
tokens: DU.buildDOMFragmentTokens(
manager.env,
refsTok,
olHTML,
olProcessor,
// The <ol> HTML above is wrapper HTML added on and doesn't
// have any DSR on it. We want DSR added to it.
{ aboutId: referencesId, setDSR: true, isForeignContent: true }
)
});
};
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
processExtSource(manager, refsTok, {
// Partial pipeline for processing ref-content
// Expand till stage 2 so that all embedded
// ref tags get processed
pipelineType: 'text/x-mediawiki/full',
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
pipelineOpts: {
// In order to associated ref-tags nested here with this references
// object, we have to pass along the references id.
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
extTag: "references",
extTagId: referencesId,
wrapTemplates: pipelineOpts.wrapTemplates,
inTemplate: pipelineOpts.inTemplate
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
},
res: [],
parentCB: cb,
emptyContentCB: emitReferencesFragment,
endCB: emitReferencesFragment,
documentCB: function(refsDoc) {
emitReferencesFragment([], DU.serializeChildren(refsDoc.body));
}
Updated native <ref> and <references> tag implementations. * Updated native implementations of the <ref> and <references> tag implementations of the cite extension. * <references> tag was not being processed properly by Parsoid. This led to lost references on the BO page. This patch fixes it which fills out references and more closely matches output en:WP. * Extracted extension content processing code into a helper and reused it for both <ref> and <references> handler. - Leading ws-only lines are unconditionally stripped. Is this accurate or is this extension-specific? Given that this code is right now tied to <ref> and <references> tag, this is not yet a problem, but if made more generic, this issue has to be addressed. * PreHandler should not run when processing the refs-tag. Right now, this is a hard check in the pre-handler. Probably worth making this more generic by letting every stage in the pipeline get a chance at turning themselves on/off based on the extension being processed by the pipeline (can use the _applyToStage fn. on ParserPipeline). TO BE DONE. * <ref> extension needs to be reset after each <references> tag is processed to duplicate behavior of existing cite extension. TO BE DONE. * Updated refs group index to start at 1. * No change in parser tests. References section output on the en:Barack Obama page now more closely matches the refs output on enwp. * In addition to the en:BO page, the following wikitext was used to fix bugs and test the implementation. CMD: "node parse --extensions ref,references < /tmp/test" ---------------------------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> ---------------------------------------------- Change-Id: I2d243656e9e903d8dadb55ee7c0630824c65cc01
2013-03-26 00:40:20 +00:00
});
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
};
References.prototype.extractRefFromNode = function(node, refsData,
refInRefProcessor, referencesAboutId, referencesGroup, refsInReferencesHTML) {
var nestedInReferences = referencesAboutId !== undefined;
var dp = DU.getDataParsoid(node);
// SSS FIXME: Need to clarify semantics here.
// If both the containing <references> elt as well as the nested <ref>
// elt has a group attribute, what takes precedence?
var group = dp.group || referencesGroup || '';
var refName = dp.name;
var about = node.getAttribute("about");
var ref = refsData.add(group, refName, about, nestedInReferences);
var nodeType = (node.getAttribute("typeof") || '').replace(/mw:Extension\/ref\/Marker/, '');
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// Add ref-index linkback
var doc = node.ownerDocument;
var span = doc.createElement('span');
var content = dp.content;
var dataMW = Util.clone(DU.getDataMw(node));
var body;
if (dp.hasRefInRef) {
var html = DU.parseHTML(content).body;
refInRefProcessor(html);
content = DU.serializeChildren(html);
}
if (content) {
// If there are multiple <ref>s with the same name, but different
// content, we need to record this one's content instead of
// linking to <references>.
if (ref.hasMultiples && content !== ref.content) {
body = {'html': content};
} else {
body = {'id': "mw-reference-text-" + ref.target};
}
}
if (!Object.keys(dataMW).length) {
dataMW = {
'name': 'ref',
// Dont set body if this is a reused reference
// like <ref name='..' /> with empty content.
'body': body,
'attrs': {
// 1. Use 'dp.group' (which is the group attribute that the ref node had)
// rather than use 'group' (which could be the group from an enclosing
// <references> tag).
// 2. Dont emit empty keys
'group': dp.group || undefined,
'name': refName || undefined
Add capability for DOM-based template expansion, and use DOM fragments for extensions This patch adds the capability to expand individual transclusions all the way to DOM, which enforces properly nested templates. This is also needed for DOM-based template re-expansion, which the VE folks would like to use for template editing. In normal parsing, DOM-based expansion is currently disabled by default for transclusions, and enabled by default for extensions. The decision whether to balance a particular transclusion can be based on a statistics-based classification of templates into balanced and unbalanced ones. The advantage of this approach is consistency in behavior for old revisions. Another alternative is to wrap unbalanced transclusions into <domparse> tags which disable DOM-based parsing for all transclusions in its content. This has the advantage that all special cases can be handled after tag insertion, and that balancing could also be enforced in the PHP parser using an extension. Other major changes: * Renamed transclusion content typeof from mw:Object/Template to mw:Transclusion * Renamed extension typeof from mw:Object/Extensions/foo to mw:Extension/foo and switched Cite to use lower-case ref/references too Other minor changes: * Only apply template encapsulation algorithm on DOM to mw:Transclusion and mw:Param objects, and no longer to all mw:Object/* elements. We should probably switch to a more explicit encapsulation type instead. Maybe something like mw:EncapStart/Transclusion and mw:EncapEnd/Transclusion instead of the current mw:Transclusion and mw:Transclusion/End, so that stripping those metas out selectively is easy? * Changed the DOMTraverser logic to let handlers explicitly return the next element to handle. Useful when several siblings are handled, as is the case for the fragment unwrapper for example, and avoids some cases where deleted nodes were still being processed. * Changed Cite to use mw:Extension/Ref{,erences} as all other extensions. * Make sure we round-trip gallery when the PHP preprocessor is not used Five parsoid-specific wt2html tests are failing due to the typeof change. They will be fine once those tests are adjusted. For now, adding them to parser tests blacklist. TODO: * Switch the Cite extension to the generic DOMFragment mechanism instead of marker tokens. Change-Id: I64b560a12695256915d2196d0646347381400e80
2013-05-16 22:23:05 +00:00
}
};
}
DU.addAttributes(span, {
'about': about,
'class': 'mw-ref',
'id': nestedInReferences ? undefined :
(ref.name ? ref.linkbacks[ref.linkbacks.length - 1] : ref.id),
'rel': 'dc:references',
'typeof': nodeType
});
DU.addTypeOf(span, "mw:Extension/ref");
var dataParsoid = {
src: dp.src,
dsr: dp.dsr
};
DU.setDataParsoid(span, dataParsoid);
DU.setDataMw(span, dataMW);
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
// refLink is the link to the citation
var refLink = doc.createElement('a');
DU.addAttributes(refLink, {
'href': '#' + ref.target,
'style': 'counter-reset: mw-Ref ' + ref.groupIndex + ';'
});
if (ref.group) {
refLink.setAttribute('data-mw-group', ref.group);
}
// refLink-span which will contain a default rendering of the cite link
// for browsers that don't support counters
var refLinkSpan = doc.createElement('span');
refLinkSpan.setAttribute('class', 'mw-reflink-text');
refLinkSpan.appendChild(doc.createTextNode("[" +
(ref.group? ref.group + " " : "") + ref.groupIndex + "]"));
refLink.appendChild(refLinkSpan);
span.appendChild(refLink);
if (!nestedInReferences) {
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
node.parentNode.insertBefore(span, node);
} else {
DU.storeDataParsoid(span, dataParsoid);
DU.storeDataMw(span, dataMW);
refsInReferencesHTML.push(DU.serializeNode(span).str, '\n');
Moved ref-index generation to DOM post-pass * When I last fixed Cite in commit 0164b846, I didn't take it all the way through. I was assigning ref indexes in the async pipeline which is incorrect since ref-tokens and references-tokens should be processed in the same order as they show up in the input. * I now moved ref-index assignment to the DOM post processor phase where they always belonged. * Fixed references and cite reset functions to only reset a specific group, if necessary. * Pipelines processing template transclusions should propagate the extension tag if the transclusion showed up in the context of extension source so that any extension-specific constraints are respected. (Ex: ref-tags in reference-extension context are handled differently -- and this should continue to be true even when the tags show up via transcluded content) * These fixes were tested on the following snippet from 0164b846. Where this snippet was generating buggy output earlier, it is now being handled correctly. --------------------------- X1<ref name="x" /> X2<ref name="x" /> <references> <ref name="x">x</ref> </references> Y<ref name="y">{{echo|y}}</ref> Z<ref name="z" /> <references> {{echo|<ref name="z">z</ref>}} </references> A<ref name="a">a</ref> B<ref name="b" /> <references> {{echo|<ref name="b">b</ref>}} </references> C<ref name="c">c</ref> D<ref name="d" /> <references> <ref name="d">{{echo|d}}</ref> </references> --------------------------- X1<ref name="x" /> X2<ref name="x" /> Change-Id: I838d188c90b526878a72e4baf1e54cac644aadfc
2013-04-24 19:09:08 +00:00
}
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
// Keep the first content to compare multiple <ref>s with the same name.
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
if (!ref.content) {
ref.content = content;
}
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
};
References.prototype.insertReferencesIntoDOM = function(refsNode, refsData, refsInReferencesHTML) {
var about = refsNode.getAttribute('about');
var dp = DU.getDataParsoid(refsNode);
var group = dp.group || '';
var src = dp.src || '<references/>'; // fall back so we don't crash
// Extract ext-source for <references>..</references> usage
var body = Util.extractExtBody("references", src).trim();
var refGroup = refsData.getRefGroup(group);
var dataMW = DU.getDataMw(refsNode);
if (!Object.keys(dataMW).length) {
var datamwBody;
// We'll have to output data-mw.body.extsrc in
// scenarios where original wikitext was of the form:
// "<references> lot of refs here </references>"
// Ex: See [[en:Barack Obama]]
if (body.length > 0) {
datamwBody = {
'extsrc': body,
'html': refsInReferencesHTML.join('')
};
}
dataMW = {
'name': 'references',
'body': datamwBody,
'attrs': {
// Dont emit empty keys
'group': group || undefined
}
};
DU.setDataMw(refsNode, dataMW);
}
// Remove all children from the references node
//
// Ex: When {{Reflist}} is reused from the cache, it comes with
// a bunch of references as well. We have to remove all those cached
// references before generating fresh references.
while (refsNode.firstChild) {
refsNode.removeChild(refsNode.firstChild);
}
if (refGroup) {
refGroup.refs.forEach(refGroup.renderLine.bind(refGroup, refsNode));
Extension handling rewrite + cite extension refactoring. Tokenization ------------ * Fixed tokenizer to correctly parse extension tags in different contexts: with start and end tags, in self-closing tag mode, and to correctly handle scenarios when the exension end-tag is followed by a '#' (the special char used to skip over extension content). * Removed the distinction in the tokenizer between installed extensions and natively supported extension tags (<ref> and <references> for ex.). They all tokenize and get processed identically and get handled by different paths in the extension handler. * Template and TemplateArg tokens now carry tpl. transclusion source alongwith them since tsr information will not be accurate when they show up in extension contexts that in turn showed up in template context that were expanded by the php preprocessor. Ex: {{echo|<ref>{{echo|foo}}</ref>}} The tsr for the ref-tag will correspond to the template-source of the echo-template, NOT the original top-level page. So, env.page.src.substring(..) will return incorrect source for the innermost {{echo|foo}}. This fix of carrying along tpl transclusion source in the token itself eliminates this problem. Knowledge of native extensions ------------------------------ * Natively implemented extension tags (<ref> and <references>) are hardcoded in env.conf.parsoid. At some point, it would be good to have a registration mechanism for parsoid-native extensions. Extension handling ------------------ * Extracted extension handling out of the template handler into its own handler class. Right now, this class inherits from the template handler in order to be able to reuse a lot of the expansion and encapsulation functionality currently in the Template Handler. * This handler now handles extensions that are: (a) natively implemented and registered with Parsoid. (b) implemented as a PHP extension and expanded by relying on the PHP preprocessor. For (a), it uses information from env.conf.parsoid to find ext-handlers for natively implemented ext-tags. However, this can be cleaned up at some point by making available a registration mechanism. Cite/Ref/References ------------------- * Reworked the cite handler to split up ref-token processing and references token processing. * The handler now processes ref-tokens, parses content all the way to html output and encapsulates the html in an attribute of a meta-token that serves as a placeholder for where the ref-token occured. * References are handled as a DOM post-pass where these meta placeholder tokens are collected, content extracted from the attribute and spit out at the site of a references tag. The DOM walking is in DOMPostProcessor.js, but the actual processing is part of the Cite.js to keep all cite extension handling code in one place. Parser pipeline --------------- * Restructured parser pipeline recipes based on changes to Cite, TemplateHandler, and ExtensionHandler. * Added a couple functions to the parser pipeline: 1. resetState to reset state before starting a new top-level parse when pipelines are reused across top-level parses (ex: parser tests) 2. setSourceOffsets to set start/end offsets of the source being handled by the pipeline. This is required to correctly set tsr values when extension content (which is a substring of original top-level text) is parsed in its own pipeline. Other fixes ----------- * Removed env parameter from the Params object since it was not being used and seemed like unnecessary state propagation. * Removed a FIXME in DOMUtils.buildTokensFromDOM by reusing code in the tokenizer that converts "\n" in text to NlTks. * Cleanup of Util.shiftTokenTSR. * ext.util.TokenCollection is now no longer used by anything. Added a FIXME and left around in case we are able to improve tokenizing and handling of *include* tags that can eliminate the need for the messy TokenAndAttrCollector. Test results ------------ * No change in parser tests results. * Tested with a few different files. - en:BO page seems to be parsed about 10% faster than before (needs verification). - Referencs on the en:BO page seem to be more accurate than before. Change-Id: I8a095fa9fa976c7b3a2a4bd968dc9db4270b105f
2013-03-09 00:07:59 +00:00
}
// Remove the group from refsData
refsData.removeRefGroup(group);
};
References.prototype.insertMissingReferencesIntoDOM = function(env, refsData, node) {
var doc = node.ownerDocument;
var self = this;
refsData.refGroups.forEach(function(refsValue, refsGroup) {
var ol = doc.createElement('ol');
var dp = DU.getDataParsoid(ol);
DU.addAttributes(ol, {
'class': 'mw-references',
typeof: 'mw:Extension/references',
about: env.newAboutId()
});
// The new references come out of "nowhere", so to make selser work
// propertly, add a zero-sized DSR pointing to the end of the document.
dp.dsr = [env.page.src.length, env.page.src.length, 0, 0];
if (refsGroup) {
ol.setAttribute('data-mw-group', refsGroup);
dp.group = refsGroup;
}
DU.storeDataParsoid(ol, dp);
// Add a \n before the <ol> so that when serialized to wikitext,
// each <references /> tag appears on its own line.
node.appendChild(doc.createTextNode("\n"));
node.appendChild(ol);
self.insertReferencesIntoDOM(ol, refsData, [""]);
});
};
/**
* Native Parsoid implementation of the Cite extension
* that ties together <ref> and <references>
*/
var Cite = function() {
this.ref = new Ref(this);
this.references = new References(this);
};
if (typeof module === "object") {
module.exports.Cite = Cite;
module.exports.ReferencesData = ReferencesData;
}