Malvineous has uploaded a new change for review.
https://gerrit.wikimedia.org/r/189169
Change subject: Add #foreach to iterate over articles in a category
......................................................................
Add #foreach to iterate over articles in a category
Change-Id: Ia68384bb737838d1c19cd73e4bd37c169b8aeb3d
---
M ParserFunctions.i18n.magic.php
M ParserFunctions.php
M ParserFunctions_body.php
M funcsParserTests.txt
4 files changed, 95 insertions(+), 0 deletions(-)
git pull
ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/ParserFunctions
refs/changes/69/189169/1
diff --git a/ParserFunctions.i18n.magic.php b/ParserFunctions.i18n.magic.php
index d4e1b0f..da98bd6 100644
--- a/ParserFunctions.i18n.magic.php
+++ b/ParserFunctions.i18n.magic.php
@@ -20,6 +20,8 @@
'ifexist' => array( 0, 'ifexist' ),
'time' => array( 0, 'time' ),
'timel' => array( 0, 'timel' ),
+ 'foreach' => array( 0, 'foreach' ),
+ 'i' => array( 0, 'i' ),
'rel2abs' => array( 0, 'rel2abs' ),
'titleparts' => array( 0, 'titleparts' ),
'len' => array( 0, 'len' ),
diff --git a/ParserFunctions.php b/ParserFunctions.php
index 06d8d79..06f9166 100644
--- a/ParserFunctions.php
+++ b/ParserFunctions.php
@@ -39,6 +39,12 @@
$wgPFEnableStringFunctions = true;
}
+/**
+ * Maximum number of #foreach iterations. Set to 0 to effectively disable
+ * #foreach.
+ */
+$wgPFForeachLimit = 250;
+
/** REGISTRATION */
$wgExtensionCredits['parserhook'][] = array(
'path' => __FILE__,
@@ -79,6 +85,8 @@
$parser->setFunctionHook( 'iferror', 'ExtParserFunctions::iferrorObj',
Parser::SFH_OBJECT_ARGS );
$parser->setFunctionHook( 'time', 'ExtParserFunctions::timeObj',
Parser::SFH_OBJECT_ARGS );
$parser->setFunctionHook( 'timel', 'ExtParserFunctions::localTimeObj',
Parser::SFH_OBJECT_ARGS );
+ $parser->setFunctionHook( 'foreach', 'ExtParserFunctions::foreachObj',
Parser::SFH_OBJECT_ARGS );
+ $parser->setFunctionHook( 'i', 'ExtParserFunctions::foreachParamObj',
Parser::SFH_OBJECT_ARGS );
$parser->setFunctionHook( 'expr', 'ExtParserFunctions::expr' );
$parser->setFunctionHook( 'rel2abs', 'ExtParserFunctions::rel2abs' );
diff --git a/ParserFunctions_body.php b/ParserFunctions_body.php
index 7e462bc..bb7f4bf 100644
--- a/ParserFunctions_body.php
+++ b/ParserFunctions_body.php
@@ -527,6 +527,73 @@
}
/**
+ * @param $parser Parser
+ * @param $frame PPFrame
+ * @param $titletext string Name of category to iterate through
+ * @param $rep string Content to be repeated
+ * @param $zero string Content to return if the category has no members
+ * @return string
+ */
+ public static function foreachF( $parser, $frame, $titletext = '', $rep
= '', $zero = '' ) {
+ global $wgContLang, $wgPFForeachLimit;
+ $cat = Category::newFromName( $titletext );
+ $wgContLang->findVariantLink( $titletext, $cat, true );
+ if ( !$cat ) return trim( $frame->expand( $zero ) ); // invalid
category
+ $titleArray = $cat->getMembers( $wgPFForeachLimit );
+ if ( sizeof( $titleArray ) == 0 ) {
+ // Empty category
+ return trim( $frame->expand( $zero ) );
+ }
+ $output = '';
+ $index = 1;
+ $pp = new Preprocessor_DOM( $parser );
+ foreach ( $titleArray as $target ) {
+ $customFrame = $pp->newCustomFrame( array( $target,
$index ) );
+ $output .= trim( $customFrame->expand( $rep ) );
+ $index++;
+ }
+ return $output;
+ }
+
+ /**
+ * Handle {{#foreach}}
+ *
+ * @param $parser Parser
+ * @param $frame PPFrame
+ * @param $args array
+ * @return string
+ */
+ public static function foreachObj( $parser, $frame, $args ) {
+ $titletext = isset( $args[0] ) ? trim( $frame->expand( $args[0]
) ) : '';
+ $rep = isset( $args[1] ) ? $args[1] : '';
+ $zero = isset( $args[2] ) ? $args[2] : '';
+ $result = self::foreachF( $parser, $frame, $titletext, $rep,
$zero );
+ return $result;
+ }
+
+ /**
+ * Handle {{#i}}, replacing it with whatever text we have been given in
the
+ * supplied frame.
+ *
+ * @param $parser Parser
+ * @param $frame PPFrame Usually PP_CustomFrame_DOM
+ * @param $args array
+ * @return string
+ */
+ public static function foreachParamObj( $parser, $frame, $args ) {
+ $flag = isset( $args[0] ) ? trim( $args[0] ) : '';
+ $content = $frame->getArgument( 0 );
+ $index = $frame->getArgument( 1 );
+
+ if ( $flag == '#' ) return intval( $index );
+ if ( empty( $content ) ) {
+ // Default content
+ $content = isset( $args[1] ) ? trim( $frame->expand(
$args[1] ) ) : '';
+ }
+ return $content;
+ }
+
+ /**
* Obtain a specified number of slash-separated parts of a title,
* e.g. {{#titleparts:Hello/World|1}} => "Hello"
*
diff --git a/funcsParserTests.txt b/funcsParserTests.txt
index 06224ba..8f12524 100644
--- a/funcsParserTests.txt
+++ b/funcsParserTests.txt
@@ -13,6 +13,8 @@
This used to be a Main Page, but that caused duplicate article
warnings when running the normal tests at the same time.
+
+[[Category:ParserFunctions foreach test]]
!! endarticle
!! article
@@ -320,3 +322,19 @@
<>
</p>
!! end
+
+!! test
+#foreach
+!! input
+{{#foreach:ParserFunctions foreach test|{{#i:#}}={{#i:}}}}
+!! result
+1=ParserFunctions page
+!! end
+
+!! test
+#i outside #foreach
+!! input
+{{#i:#}}={{#i:|Default}}
+!! result
+0=Default
+!! end
--
To view, visit https://gerrit.wikimedia.org/r/189169
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings
Gerrit-MessageType: newchange
Gerrit-Change-Id: Ia68384bb737838d1c19cd73e4bd37c169b8aeb3d
Gerrit-PatchSet: 1
Gerrit-Project: mediawiki/extensions/ParserFunctions
Gerrit-Branch: master
Gerrit-Owner: Malvineous <[email protected]>
_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits