Samwilson has uploaded a new change for review. https://gerrit.wikimedia.org/r/321223
Change subject: Templates for list items ...................................................................... Templates for list items Change-Id: I7197fc93abad50dc2fc7309bc32a96be52cc47e2 --- M Genealogy.i18n.php M README.md M src/Hooks.php M src/Person.php M tests/phpunit/PersonTest.php 5 files changed, 105 insertions(+), 34 deletions(-) git pull ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/Genealogy refs/changes/23/321223/1 diff --git a/Genealogy.i18n.php b/Genealogy.i18n.php index 9df2339..9d63d97 100644 --- a/Genealogy.i18n.php +++ b/Genealogy.i18n.php @@ -25,4 +25,5 @@ 'genealogy-parser-function-not-found' => 'Genealogy parser function type not recognised: $1', 'genealogy-existing-partners' => 'This person already has the following ' .'{{PLURAL:$1|partner|partners}}: ', + 'genealogy-person-list-item' => 'Person/list-item' ]; diff --git a/README.md b/README.md index 131e546..c86cfd7 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,7 @@ All details: [mediawiki.org/wiki/Extension:Genealogy](https://mediawiki.org/wiki/Extension:Genealogy) + ## Usage summary This extension creates one parser function: `{{#genealogy: … }}`. @@ -25,6 +26,7 @@ `{{#genealogy:tree|ancestors=List|descendants=List}}`<br /> where each `List` is a newline-separated list of page titles. + ## Templates **Example:** @@ -35,20 +37,40 @@ When this extension creates a link to a page that doesn't yet exist, the text of `[[Template:Person/preload]]` is preloaded. The location of this preload text can be customised -by modifying the `[[MediaWiki:genealogy-person-preload]]` system message. +by modifying the `genealogy-person-preload` system message. + +**Person list-item:** +Three types of lists of people can be generated: `siblings`, `partners`, and `children`. +The default behaviour is a simple bulleted list, +but this can be overridden by a template, `Template:Person/list-item` +(the template name is specified by the `genealogy-person-list-item` system message). +For example, to get a comma-separated one-line list of people, the following template code could be used: + +``` +{{{link}}}{{#ifeq:{{{index}}}|{{{count}}}|.|,}} +``` + +There are four parameters that are available for use in the list-item template: +* `link` — A wikitext link. +* `title` — The page title. +* `index` — The index of this list-item in the full list, starting from 1. +* `count` — The total number of items in the full list. ## Installation -1. Clone into your extensions directory: +1. Clone the *Genealogy* and *GraphViz* extensions into your extensions directory: ``` $ cd extensions $ git clone https://github.com/samwilson/Genealogy.git + $ git clone https://gerrit.wikimedia.org/r/p/mediawiki/extensions/GraphViz.git ``` -2. Enable it in your `LocalSettings.php` file: +2. Enable them in your `LocalSettings.php` file: ``` wfLoadExtension( 'Genealogy' ); + wfLoadExtension( 'GraphViz' ); ``` + ## Development The *Genealogy* extension is developed by Sam Wilson and released under version diff --git a/src/Hooks.php b/src/Hooks.php index 9c2e888..f7d7e88 100644 --- a/src/Hooks.php +++ b/src/Hooks.php @@ -84,7 +84,7 @@ $params[] = $arg; } } - $out = ''; // "<pre>".print_r($params, true)."</pre>"; + $out = ''; $isHtml = false; switch ( $type ) { case 'person': @@ -99,30 +99,31 @@ break; case 'parent': $parentTitle = Title::newFromText( $params[0] ); - if ( $parentTitle && $parentTitle->exists() ) { - $parent = new Person( $parentTitle ); - $out .= $parent->getWikiLink(); - } else { - $query = [ 'preload' => wfMessage( 'genealogy-person-preload' ) ]; - $out .= Linker::link( $parentTitle, null, [], $query ); - $isHtml = true; - } + $parent = new Person( $parentTitle ); + $out .= $parent->getWikiLink(); +// if ( $parentTitle && $parentTitle->exists() ) { +// $out .= $parent->getWikiLink(); +// } else { +// $query = [ 'preload' => wfMessage( 'genealogy-person-preload' ) ]; +// $out .= Linker::link( $parentTitle, null, [], $query ); +// $isHtml = true; +// } self::saveProp( $parser, 'parent', $params[0] ); break; case 'siblings': $person = new Person( $parser->getTitle() ); - $out .= self::peopleList( $person->getSiblings() ); + $out .= self::peopleList( $parser, $person->getSiblings() ); break; case 'partner': self::saveProp( $parser, 'partner', $params[0] ); break; case 'partners': $person = new Person( $parser->getTitle() ); - $out .= self::peopleList( $person->getPartners() ); + $out .= self::peopleList( $parser, $person->getPartners() ); break; case 'children': $person = new Person( $parser->getTitle() ); - $out .= self::peopleList( $person->getChildren() ); + $out .= self::peopleList( $parser, $person->getChildren() ); break; case 'tree': $tree = new Tree(); @@ -154,7 +155,7 @@ /** * Save a page property. * @param Parser $parser The parser object. - * @param string $prop The property name; it will be prefxed with 'genealogy '. + * @param string $prop The property name; it will be prefixed with 'genealogy '. * @param string $val The property value. * @param boolean $multi Whether this property can have multiple values (will be stored as * multiple properties, with an integer appended to their name. @@ -178,15 +179,30 @@ } /** - * Get a wikitext list of people. - * @todo Replace with a proper templating system. + * Get a wikitext list of siblings, partners, or children. + * @param Parser $parser The parser to use to render each line. * @param Person[] $people * @return string Wikitext list of people. */ - public static function peopleList( $people ) { + public static function peopleList( Parser $parser, $people ) { + $templateName = wfMessage( 'genealogy-person-list-item' ); $out = ''; + $index = 1; + $peopleCount = count( $people ); foreach ( $people as $person ) { - $out .= "* " . $person->getWikiLink() . "\n"; + $exists = Title::newFromText( 'Template:' . $templateName->toString() )->exists(); + if ( $exists ) { + $template = '{{' . $templateName + . '|title=' . $person->getTitle()->getFullText() + . '|link=' . $person->getWikiLink() + . '|index=' . $index + . '|count=' . $peopleCount + . '}}'; + $out .= $parser->recursivePreprocess( $template ); + $index ++; + } else { + $out .= "* " . $person->getWikiLink() . "\n"; + } } return $out; } diff --git a/src/Person.php b/src/Person.php index 5e58f38..b22dbdb 100644 --- a/src/Person.php +++ b/src/Person.php @@ -60,12 +60,13 @@ /** * Get all Titles that refer to this Person (i.e. all redirects both inward and outward, and * the actual Title). - * @return Title[] The Titles, some of which might not actually exist. + * @return Title[] An array of the Titles, some of which might not actually exist, keyed by the + * prefixed DB key. */ public function getTitles() { - $page = WikiPage::factory( $this->title ); $titles = [ $this->title->getPrefixedDBkey() => $this->title ]; // Find all the outgoing redirects that leave from here. + $page = WikiPage::factory( $this->title ); while ( $page->isRedirect() ) { $title = $page->getRedirectTarget(); $titles[$title->getPrefixedDBkey()] = $title; @@ -78,6 +79,11 @@ return $titles; } + /** + * Get wikitext for a link to this Person; non-existant people will have the preload + * parameter added. + * @return string The wikitext. + */ public function getWikiLink() { $birthYear = $this->getDateYear( $this->getBirthDate() ); $deathYear = $this->getDateYear( $this->getDeathDate() ); @@ -90,7 +96,16 @@ $dateString = "(".wfMessage( 'genealogy-died' )." $deathYear)"; } $date = ( $this->hasDates() ) ? " $dateString" : ""; - return "[[" . $this->getTitle()->getPrefixedText() . "]]$date"; + if ( $this->getTitle()->exists() ) { + return "[[" . $this->getTitle()->getFullText() . "]]$date"; + } else { + $query = [ + 'action' => 'edit', + 'preload' => wfMessage( 'genealogy-person-preload' ), + ]; + $url = $this->getTitle()->getFullURL( $query ); + return '[' . $url . ' ' . $this->getTitle()->getFullText() . ']'; + } } /** @@ -188,21 +203,23 @@ /** * Get all children. - * - * @return Person[] An array of children, possibly empty. + * @return Person[] An array of children, possibly empty, keyed by the prefixed DB key. */ public function getChildren() { - if ( is_array( $this->children ) ) { - return $this->children; - } $this->children = $this->getPropInbound( 'parent' ); return $this->children; } + /** + * Find people with properties that are equal to one of this page's titles. + * @param string $type + * @return Person[] Keyed by the prefixed DB key. + */ protected function getPropInbound( $type ) { $dbr = wfGetDB( DB_SLAVE ); $tables = [ 'pp'=>'page_props', 'p'=>'page' ]; $columns = [ 'pp_value', 'page_title' ]; + $where = [ 'pp_value' => $this->getTitles(), "pp_propname LIKE 'genealogy $type %'", diff --git a/tests/phpunit/PersonTest.php b/tests/phpunit/PersonTest.php index d214556..cb6cde6 100644 --- a/tests/phpunit/PersonTest.php +++ b/tests/phpunit/PersonTest.php @@ -24,16 +24,31 @@ public function testCreatePerson() { $charlesTitle = Title::newFromText( 'Charles' ); - $page = new WikiPage( $charlesTitle ); - $wikiText = '{{#genealogy:parent|Elizabeth}}{{#genealogy:partner|Dianna}}'; - $page->doEditContent( new WikitextContent( $wikiText ), '' ); + $wikiText1 = '{{#genealogy:parent|Elizabeth}}{{#genealogy:partner|Dianna}}'; + $this->setPageContent( 'Charles', $wikiText1 ); $charles = new Person( $charlesTitle ); $this->assertCount( 1, $charles->getPartners() ); + + // Create the partner page, and check that all's as it should be. + $this->setPageContent( 'Dianna', 'Lorem' ); + $dianna = new Person( Title::newFromText( 'Dianna' ) ); + $this->assertEquals( [ 'Charles' ], array_keys( $dianna->getPartners() ) ); + $elizabeth = new Person( Title::newFromText( 'Elizabeth' ) ); + $this->assertEquals( [ 'Charles' ], array_keys( $elizabeth->getChildren() ) ); + + // Then edit the first page to remove the partner. + $wikiText2 = '{{#genealogy:parent|Elizabeth}}{{#genealogy:partner|Bob}}'; + $this->setPageContent( 'Charles', $wikiText2 ); + $this->assertEquals( [ 'Bob' ], array_keys( $charles->getPartners() ) ); + $this->assertEmpty( $dianna->getPartners() ); } - public function testName() { - $person = new Person( Title::newFromText( 'Will' ) ); - $this->assertEquals( 'Will', $person->getTitle() ); + public function testChildren() { + $wikiText = '{{#genealogy:parent|Alice}}'; + $this->setPageContent( 'Bob', $wikiText ); + $this->setPageContent( 'Carly', $wikiText ); + $alice = new Person( Title::newFromText( 'Alice' ) ); + $this->assertEquals( ['Bob', 'Carly'], array_keys( $alice->getChildren() ) ); } public function testDates() { -- To view, visit https://gerrit.wikimedia.org/r/321223 To unsubscribe, visit https://gerrit.wikimedia.org/r/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I7197fc93abad50dc2fc7309bc32a96be52cc47e2 Gerrit-PatchSet: 1 Gerrit-Project: mediawiki/extensions/Genealogy Gerrit-Branch: master Gerrit-Owner: Samwilson <s...@samwilson.id.au> _______________________________________________ MediaWiki-commits mailing list MediaWiki-commits@lists.wikimedia.org https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits