Compare commits

..

5 commits

Author SHA1 Message Date
libraryupgrader
836871b041 build: Updating npm dependencies
* i: 0.3.6 → 0.3.7
  * https://npmjs.com/advisories/1002379 (CVE-2021-3820)
* ansi-regex: 2.1.1 → 5.0.1
  * https://npmjs.com/advisories/1002401 (CVE-2021-3807)

Additional changes:
* composer.json: Updated phpcs command in composer test (T280592).
* composer.json: Added phpcs command to scripts (T280592).

Change-Id: Ie0d55562573ddfd839c010a4c620e79b25994df9
2021-10-07 11:56:43 +00:00
libraryupgrader
7c11156848 build: Updating path-parse to 1.0.7
* https://npmjs.com/advisories/1773 (CVE-2021-23343)

Change-Id: I3dfa881e6d3a9d14a419d34b59431c2dba8a8e4a
2021-09-02 16:31:02 +00:00
libraryupgrader
c1b20d560d build: Updating dependencies
composer:
* mediawiki/mediawiki-codesniffer: 19.1.0 → 19.4.0

npm:
* grunt: 1.3.0 → 1.4.0

Change-Id: I0b75f416bf27cfc4ff2361cb8e128dc99c5b6a36
2021-05-09 10:15:05 +00:00
libraryupgrader
790ef209bc build: Updating y18n to 3.2.2
* https://npmjs.com/advisories/1654 (CVE-2020-7774)

Change-Id: Ia923fae56073cc2e3bf2c77fc34258ff689a4006
2021-03-30 00:00:47 +00:00
libraryupgrader
0fecfab673 build: Updating dependencies
composer:
* mediawiki/mediawiki-codesniffer: 18.0.0 → 19.1.0

npm:
* grunt: 1.0.1 → 1.3.0
  * https://npmjs.com/advisories/577 (CVE-2018-3721)
  * https://npmjs.com/advisories/745
  * https://npmjs.com/advisories/782 (CVE-2018-16487)
  * https://npmjs.com/advisories/788
  * https://npmjs.com/advisories/813
  * https://npmjs.com/advisories/1065 (CVE-2019-10744)
  * https://npmjs.com/advisories/1523 (CVE-2019-10744)

Additional changes:
* Replaced "jakub-onderka" packages with "php-parallel-lint".
* Committed package-lock.json (T179229) too.
* And updating CoC link to use Special:MyLanguage (T202047).
* Dropped .php5 and .inc files from .phpcs.xml (T200956).
* Also sorted "composer fix" command to run phpcbf last.

Change-Id: I5bc68d9d819496e5ce7c6384615b15ef2e8515f9
2021-01-01 05:00:22 +00:00
74 changed files with 3255 additions and 6636 deletions

View file

@ -1,8 +0,0 @@
{
"root": true,
"extends": [
"wikimedia/client-es5",
"wikimedia/jquery",
"wikimedia/mediawiki"
]
}

1
.gitignore vendored
View file

@ -5,4 +5,3 @@
node_modules/
/composer.lock
/vendor/
/.eslintcache

2
.jshintignore Normal file
View file

@ -0,0 +1,2 @@
node_modules
vendor

View file

@ -1,9 +1,10 @@
<?xml version="1.0"?>
<ruleset>
<rule ref="./vendor/mediawiki/mediawiki-codesniffer/MediaWiki">
<exclude name="MediaWiki.Files.ClassMatchesFilename.NotMatch" />
<exclude name="MediaWiki.Commenting.FunctionComment.MissingDocumentationProtected" />
<exclude name="MediaWiki.Commenting.FunctionComment.MissingDocumentationPublic" />
<exclude name="MediaWiki.Usage.ExtendClassUsage.FunctionConfigUsage" />
<exclude name="PSR12.Properties.ConstantVisibility.NotFound" />
<exclude name="MediaWiki.Usage.DbrQueryUsage.DbrQueryFound" />
<exclude name="Squiz.Scope.MethodScope.Missing" />
</rule>
<file>.</file>

View file

@ -5,275 +5,266 @@
* @file
* @ingroup Extensions
*/
// @codingStandardsIgnoreFile
$specialPageAliases = [];
$specialPageAliases = array();
/** English (English) */
$specialPageAliases['en'] = [
'ContributionScores' => [ 'ContributionScores' ],
];
$specialPageAliases['en'] = array(
'ContributionScores' => array( 'ContributionScores' ),
);
/** Arabic (العربية) */
$specialPageAliases['ar'] = [
'ContributionScores' => [ 'نتائج_المساهمة' ],
];
$specialPageAliases['ar'] = array(
'ContributionScores' => array( 'نتائج_المساهمة' ),
);
/** Aramaic (ܐܪܡܝܐ) */
$specialPageAliases['arc'] = [
'ContributionScores' => [ 'ܦܠܛ̈ܐ_ܕܫܘܬܦܘ̈ܬܐ' ],
];
$specialPageAliases['arc'] = array(
'ContributionScores' => array( 'ܦܠܛ̈ܐ_ܕܫܘܬܦܘ̈ܬܐ' ),
);
/** Egyptian Arabic (مصرى) */
$specialPageAliases['arz'] = [
'ContributionScores' => [ 'نتايج_المساهمه' ],
];
$specialPageAliases['arz'] = array(
'ContributionScores' => array( 'نتايج_المساهمه' ),
);
/** Assamese (অসমীয়া) */
$specialPageAliases['as'] = [
'ContributionScores' => [ 'বৰঙনিৰ_মূল্যায়ন' ],
];
$specialPageAliases['as'] = array(
'ContributionScores' => array( 'বৰঙনিৰ_মূল্যায়ন' ),
);
/** Avaric (авар) */
$specialPageAliases['av'] = [
'ContributionScores' => [ 'Очки_вклада' ],
];
$specialPageAliases['av'] = array(
'ContributionScores' => array( 'Очки_вклада' ),
);
/** Bashkir (башҡортса) */
$specialPageAliases['ba'] = [
'ContributionScores' => [ 'Өлөш_мәрәйҙәре' ],
];
$specialPageAliases['ba'] = array(
'ContributionScores' => array( 'Өлөш_мәрәйҙәре' ),
);
/** Western Balochi (بلوچی رخشانی) */
$specialPageAliases['bgn'] = [
'ContributionScores' => [ 'شراکتانی_امتیاز_ئان' ],
];
$specialPageAliases['bgn'] = array(
'ContributionScores' => array( 'شراکتانی_امتیاز_ئان' ),
);
/** Banjar (Bahasa Banjar) */
$specialPageAliases['bjn'] = [
'ContributionScores' => [ 'Skor_sumbangan' ],
];
$specialPageAliases['bjn'] = array(
'ContributionScores' => array( 'Skor_sumbangan' ),
);
/** Bengali (বাংলা) */
$specialPageAliases['bn'] = [
'ContributionScores' => [ 'অবদানের_স্কোর' ],
];
$specialPageAliases['bn'] = array(
'ContributionScores' => array( 'অবদানের_স্কোর' ),
);
/** Breton (brezhoneg) */
$specialPageAliases['br'] = [
'ContributionScores' => [ 'Skor_Degasadennoù' ],
];
$specialPageAliases['br'] = array(
'ContributionScores' => array( 'Skor_Degasadennoù' ),
);
/** Bosnian (bosanski) */
$specialPageAliases['bs'] = [
'ContributionScores' => [ 'DoprinosiBodovi' ],
];
$specialPageAliases['bs'] = array(
'ContributionScores' => array( 'DoprinosiBodovi' ),
);
/** Min Dong Chinese (Mìng-dĕ̤ng-ngṳ̄) */
$specialPageAliases['cdo'] = [
'ContributionScores' => [ '貢獻分數' ],
];
$specialPageAliases['cdo'] = array(
'ContributionScores' => array( '貢獻分數' ),
);
/** German (Deutsch) */
$specialPageAliases['de'] = [
'ContributionScores' => [ 'Beitragspunkte' ],
];
$specialPageAliases['de'] = array(
'ContributionScores' => array( 'Beitragspunkte' ),
);
/** Zazaki (Zazaki) */
$specialPageAliases['diq'] = [
'ContributionScores' => [ 'SqoréDekerdışan' ],
];
$specialPageAliases['diq'] = array(
'ContributionScores' => array( 'SqoréDekerdışan' ),
);
/** Esperanto (Esperanto) */
$specialPageAliases['eo'] = [
'ContributionScores' => [ 'Poentaro_de_kontribuoj', 'Kontribuatingoj' ],
];
$specialPageAliases['eo'] = array(
'ContributionScores' => array( 'Poentaro_de_kontribuoj', 'Kontribuatingoj' ),
);
/** Estonian (eesti) */
$specialPageAliases['et'] = [
'ContributionScores' => [ 'Kaastööpunktid' ],
];
$specialPageAliases['et'] = array(
'ContributionScores' => array( 'Kaastööpunktid' ),
);
/** Persian (فارسی) */
$specialPageAliases['fa'] = [
'ContributionScores' => [ 'امتیازهای_مشارکت' ],
];
$specialPageAliases['fa'] = array(
'ContributionScores' => array( 'امتیازهای_مشارکت' ),
);
/** Finnish (suomi) */
$specialPageAliases['fi'] = [
'ContributionScores' => [ 'Muokkauspisteet' ],
];
$specialPageAliases['fi'] = array(
'ContributionScores' => array( 'Muokkauspisteet' ),
);
/** Galician (galego) */
$specialPageAliases['gl'] = [
'ContributionScores' => [ 'Puntuación_das_contribucións' ],
];
$specialPageAliases['gl'] = array(
'ContributionScores' => array( 'Puntuación_das_contribucións' ),
);
/** Hebrew (עברית) */
$specialPageAliases['he'] = [
'ContributionScores' => [ ירוג_תרומות' ],
];
$specialPageAliases['he'] = array(
'ContributionScores' => array( ירוג_תרומות' ),
);
/** Haitian (Kreyòl ayisyen) */
$specialPageAliases['ht'] = [
'ContributionScores' => [ 'PwentajKontribisyon' ],
];
$specialPageAliases['ht'] = array(
'ContributionScores' => array( 'PwentajKontribisyon' ),
);
/** Hungarian (magyar) */
$specialPageAliases['hu'] = [
'ContributionScores' => [ 'Szerkesztési_pontok' ],
];
$specialPageAliases['hu'] = array(
'ContributionScores' => array( 'Szerkesztési_pontok' ),
);
/** Interlingua (interlingua) */
$specialPageAliases['ia'] = [
'ContributionScores' => [ 'Scores_de_contributiones' ],
];
$specialPageAliases['ia'] = array(
'ContributionScores' => array( 'Scores_de_contributiones' ),
);
/** Indonesian (Bahasa Indonesia) */
$specialPageAliases['id'] = [
'ContributionScores' => [ 'Skor_kontribusi', 'SkorKontribusi' ],
];
$specialPageAliases['id'] = array(
'ContributionScores' => array( 'Skor_kontribusi', 'SkorKontribusi' ),
);
/** Italian (italiano) */
$specialPageAliases['it'] = [
'ContributionScores' => [ 'PunteggiContributi' ],
];
$specialPageAliases['it'] = array(
'ContributionScores' => array( 'PunteggiContributi' ),
);
/** Japanese (日本語) */
$specialPageAliases['ja'] = [
'ContributionScores' => [ '貢献スコア', '貢献得点' ],
];
$specialPageAliases['ja'] = array(
'ContributionScores' => array( '貢献スコア', '貢献得点' ),
);
/** Khmer (ភាសាខ្មែរ) */
$specialPageAliases['km'] = [
'ContributionScores' => [ 'ពិន្ទុអ្នករួមចំណែក' ],
];
$specialPageAliases['km'] = array(
'ContributionScores' => array( 'ពិន្ទុអ្នករួមចំណែក' ),
);
/** Korean (한국어) */
$specialPageAliases['ko'] = [
'ContributionScores' => [ '기여점수' ],
];
$specialPageAliases['ko'] = array(
'ContributionScores' => array( '기여점수' ),
);
/** Colognian (Ripoarisch) */
$specialPageAliases['ksh'] = [
'ContributionScores' => [ 'MetmaacherZahle' ],
];
$specialPageAliases['ksh'] = array(
'ContributionScores' => array( 'MetmaacherZahle' ),
);
/** Ladino (Ladino) */
$specialPageAliases['lad'] = [
'ContributionScores' => [ 'Resultados_de_ajustamientos' ],
];
$specialPageAliases['lad'] = array(
'ContributionScores' => array( 'Resultados_de_ajustamientos' ),
);
/** Luxembourgish (Lëtzebuergesch) */
$specialPageAliases['lb'] = [
'ContributionScores' => [ 'Score_vun_de_Kontributiounen' ],
];
$specialPageAliases['lb'] = array(
'ContributionScores' => array( 'Score_vun_de_Kontributiounen' ),
);
/** Northern Luri (لۊری شومالی) */
$specialPageAliases['lrc'] = [
'ContributionScores' => [ 'نئرخ_ھومیاری' ],
];
$specialPageAliases['lrc'] = array(
'ContributionScores' => array( 'نئرخ_ھومیاری' ),
);
/** Minangkabau (Baso Minangkabau) */
$specialPageAliases['min'] = [
'ContributionScores' => [ 'SkorJariah' ],
];
$specialPageAliases['min'] = array(
'ContributionScores' => array( 'SkorJariah' ),
);
/** Macedonian (македонски) */
$specialPageAliases['mk'] = [
'ContributionScores' => [ 'БодувањеНаПридонесите' ],
];
$specialPageAliases['mk'] = array(
'ContributionScores' => array( 'БодувањеНаПридонесите' ),
);
/** Malayalam (മലയാളം) */
$specialPageAliases['ml'] = [
'ContributionScores' => [ 'സേവനസ്കോറുകൾ' ],
];
$specialPageAliases['ml'] = array(
'ContributionScores' => array( 'സേവനസ്കോറുകൾ' ),
);
/** Marathi (मराठी) */
$specialPageAliases['mr'] = [
'ContributionScores' => [ 'योगदानप्राविण्य' ],
];
$specialPageAliases['mr'] = array(
'ContributionScores' => array( 'योगदानप्राविण्य' ),
);
/** Norwegian Bokmål (norsk bokmål) */
$specialPageAliases['nb'] = [
'ContributionScores' => [ 'Bidragspoeng' ],
];
$specialPageAliases['nb'] = array(
'ContributionScores' => array( 'Bidragspoeng' ),
);
/** Low Saxon (Netherlands) (Nedersaksies) */
$specialPageAliases['nds-nl'] = [
'ContributionScores' => [ 'Biedragentelling' ],
];
$specialPageAliases['nds-nl'] = array(
'ContributionScores' => array( 'Biedragentelling' ),
);
/** Dutch (Nederlands) */
$specialPageAliases['nl'] = [
'ContributionScores' => [ 'Gebruikersscores', 'Bijdragenscores' ],
];
$specialPageAliases['nl'] = array(
'ContributionScores' => array( 'Gebruikersscores', 'Bijdragenscores' ),
);
/** Polish (polski) */
$specialPageAliases['pl'] = [
'ContributionScores' => [ 'Punkty_za_edycje' ],
];
$specialPageAliases['pl'] = array(
'ContributionScores' => array( 'Punkty_za_edycje' ),
);
/** Russian (русский) */
$specialPageAliases['ru'] = [
'ContributionScores' => [ 'Очки_вклада' ],
];
$specialPageAliases['ru'] = array(
'ContributionScores' => array( 'Очки_вклада' ),
);
/** Sanskrit (संस्कृतम्) */
$specialPageAliases['sa'] = [
'ContributionScores' => [ 'योगदानप्राप्ताङ्क' ],
];
$specialPageAliases['sa'] = array(
'ContributionScores' => array( 'योगदानप्राप्ताङ्क' ),
);
/** Sicilian (sicilianu) */
$specialPageAliases['scn'] = [
'ContributionScores' => [ 'PunteggiContribuzione' ],
];
$specialPageAliases['scn'] = array(
'ContributionScores' => array( 'PunteggiContribuzione' ),
);
/** Slovak (slovenčina) */
$specialPageAliases['sk'] = [
'ContributionScores' => [ 'SkórePríspevkov' ],
];
/** Serbian Cyrillic (српски (ћирилица)) */
$specialPageAliases['sr-ec'] = [
'ContributionScores' => [ 'ОценеДоприноса' ],
];
/** Serbian Latin (srpski (latinica)) */
$specialPageAliases['sr-el'] = [
'ContributionScores' => [ 'OceneDoprinosa' ],
];
$specialPageAliases['sk'] = array(
'ContributionScores' => array( 'SkórePríspevkov' ),
);
/** Swedish (svenska) */
$specialPageAliases['sv'] = [
'ContributionScores' => [ 'Bidragspoäng' ],
];
$specialPageAliases['sv'] = array(
'ContributionScores' => array( 'Bidragspoäng' ),
);
/** Thai (ไทย) */
$specialPageAliases['th'] = [
'ContributionScores' => [ 'คะแนนการเขียน' ],
];
$specialPageAliases['th'] = array(
'ContributionScores' => array( 'คะแนนการเขียน' ),
);
/** Tagalog (Tagalog) */
$specialPageAliases['tl'] = [
'ContributionScores' => [ 'Mga_puntos_ng_ambag' ],
];
$specialPageAliases['tl'] = array(
'ContributionScores' => array( 'Mga_puntos_ng_ambag' ),
);
/** Turkish (Türkçe) */
$specialPageAliases['tr'] = [
'ContributionScores' => [ 'KatkıSkorları', 'KatkıPuanları' ],
];
$specialPageAliases['tr'] = array(
'ContributionScores' => array( 'KatkıSkorları', 'KatkıPuanları' ),
);
/** Ukrainian (українська) */
$specialPageAliases['uk'] = [
'ContributionScores' => [ 'Очки_внеску', 'Очки_вклада' ],
];
$specialPageAliases['uk'] = array(
'ContributionScores' => array( 'Очки_внеску', 'Очки_вклада' ),
);
/** Simplified Chinese (中文(简体)‎) */
$specialPageAliases['zh-hans'] = [
'ContributionScores' => [ '贡献得分' ],
];
$specialPageAliases['zh-hans'] = array(
'ContributionScores' => array( '贡献得分' ),
);
/** Traditional Chinese (中文(繁體)‎) */
$specialPageAliases['zh-hant'] = [
'ContributionScores' => [ '貢獻分數' ],
];
$specialPageAliases['zh-hant'] = array(
'ContributionScores' => array( '貢獻分數' ),
);

93
ContributionScores.php Normal file
View file

@ -0,0 +1,93 @@
<?php
/** \file
* \brief Contains setup code for the Contribution Scores Extension.
*/
# Not a valid entry point, skip unless MEDIAWIKI is defined
if ( !defined( 'MEDIAWIKI' ) ) {
echo 'Contribution Scores extension';
exit( 1 );
}
$wgExtensionCredits['specialpage'][] = [
'path' => __FILE__,
'name' => 'Contribution Scores',
'url' => 'https://www.mediawiki.org/wiki/Extension:Contribution_Scores',
'author' => 'Tim Laqua',
'descriptionmsg' => 'contributionscores-desc',
'version' => '1.25.0'
];
define( 'CONTRIBUTIONSCORES_MAXINCLUDELIMIT', 50 );
$wgContribScoreReports = null;
// These settings can be overridden in LocalSettings.php.
// Set to true to exclude bots from the reporting.
$wgContribScoreIgnoreBlockedUsers = false;
// Set to true to exclude blocked users from the reporting.
$wgContribScoreIgnoreBots = false;
// Set to true to use real user names when available. Only for MediaWiki 1.19 and later.
$wgContribScoresUseRealName = false;
// Set to true to disable cache for parser function and inclusion of table.
$wgContribScoreDisableCache = false;
$wgAutoloadClasses['ContributionScores'] = __DIR__ . '/ContributionScores_body.php';
$wgSpecialPages['ContributionScores'] = 'ContributionScores';
$wgMessagesDirs['ContributionScores'] = __DIR__ . '/i18n';
$wgExtensionMessagesFiles['ContributionScoresAlias'] = __DIR__ . '/ContributionScores.alias.php';
$wgExtensionMessagesFiles['ContributionScoresMagic'] =
__DIR__ . '/ContributionScores.i18n.magic.php';
$wgHooks['ParserFirstCallInit'][] = 'efContributionScores_Setup';
function efContributionScores_Setup( &$parser ) {
$parser->setFunctionHook( 'cscore', 'efContributionScores_Render' );
return true;
}
function efContributionScores_Render( &$parser, $usertext, $metric = 'score' ) {
global $wgContribScoreDisableCache;
if ( $wgContribScoreDisableCache ) {
$parser->disableCache();
}
$user = User::newFromName( $usertext );
$dbr = wfGetDB( DB_REPLICA );
if ( $user instanceof User && $user->isLoggedIn() ) {
global $wgLang;
if ( $metric == 'score' ) {
$res = $dbr->select( 'revision',
'COUNT(DISTINCT rev_page)+SQRT(COUNT(rev_id)-COUNT(DISTINCT rev_page))*2 AS wiki_rank',
[ 'rev_user' => $user->getID() ] );
$row = $dbr->fetchObject( $res );
$output = $wgLang->formatNum( round( $row->wiki_rank, 0 ) );
} elseif ( $metric == 'changes' ) {
$res = $dbr->select( 'revision',
'COUNT(rev_id) AS rev_count',
[ 'rev_user' => $user->getID() ] );
$row = $dbr->fetchObject( $res );
$output = $wgLang->formatNum( $row->rev_count );
} elseif ( $metric == 'pages' ) {
$res = $dbr->select( 'revision',
'COUNT(DISTINCT rev_page) AS page_count',
[ 'rev_user' => $user->getID() ] );
$row = $dbr->fetchObject( $res );
$output = $wgLang->formatNum( $row->page_count );
} else {
$output = wfMessage( 'contributionscores-invalidmetric' )->text();
}
} else {
$output = wfMessage( 'contributionscores-invalidusername' )->text();
}
return $parser->insertStripItem( $output, $parser->mStripState );
}

274
ContributionScores_body.php Normal file
View file

@ -0,0 +1,274 @@
<?php
/** \file
* \brief Contains code for the ContributionScores Class (extends SpecialPage).
*/
/// Special page class for the Contribution Scores extension
/**
* Special page that generates a list of wiki contributors based
* on edit diversity (unique pages edited) and edit volume (total
* number of edits.
*
* @ingroup Extensions
* @author Tim Laqua <t.laqua@gmail.com>
*/
class ContributionScores extends IncludableSpecialPage {
public function __construct() {
parent::__construct( 'ContributionScores' );
}
/// Generates a "Contribution Scores" table for a given LIMIT and date range
/**
* Function generates Contribution Scores tables in HTML format (not wikiText)
*
* @param int $days Days in the past to run report for
* @param int $limit Maximum number of users to return (default 50)
* @param string|null $title The title of the table
* @param array $options array of options (default none; nosort/notools)
* @return string Html Table representing the requested Contribution Scores.
*/
function genContributionScoreTable( $days, $limit, $title = null, $options = 'none' ) {
global $wgContribScoreIgnoreBots, $wgContribScoreIgnoreBlockedUsers, $wgContribScoresUseRealName;
$opts = explode( ',', strtolower( $options ) );
$dbr = wfGetDB( DB_REPLICA );
$userTable = $dbr->tableName( 'user' );
$userGroupTable = $dbr->tableName( 'user_groups' );
$revTable = $dbr->tableName( 'revision' );
$ipBlocksTable = $dbr->tableName( 'ipblocks' );
$sqlWhere = "";
$nextPrefix = "WHERE";
if ( $days > 0 ) {
$date = time() - ( 60 * 60 * 24 * $days );
$dateString = $dbr->timestamp( $date );
$sqlWhere .= " {$nextPrefix} rev_timestamp > '$dateString'";
$nextPrefix = "AND";
}
if ( $wgContribScoreIgnoreBlockedUsers ) {
$sqlWhere .= " {$nextPrefix} rev_user NOT IN " .
"(SELECT ipb_user FROM {$ipBlocksTable} WHERE ipb_user <> 0)";
$nextPrefix = "AND";
}
if ( $wgContribScoreIgnoreBots ) {
$sqlWhere .= " {$nextPrefix} rev_user NOT IN " .
"(SELECT ug_user FROM {$userGroupTable} WHERE ug_group='bot')";
}
$sqlMostPages = "SELECT rev_user,
COUNT(DISTINCT rev_page) AS page_count,
COUNT(rev_id) AS rev_count
FROM {$revTable}
{$sqlWhere}
GROUP BY rev_user
ORDER BY page_count DESC
LIMIT {$limit}";
$sqlMostRevs = "SELECT rev_user,
COUNT(DISTINCT rev_page) AS page_count,
COUNT(rev_id) AS rev_count
FROM {$revTable}
{$sqlWhere}
GROUP BY rev_user
ORDER BY rev_count DESC
LIMIT {$limit}";
$sql = "SELECT user_id, " .
"user_name, " .
"user_real_name, " .
"page_count, " .
"rev_count, " .
"page_count+SQRT(rev_count-page_count)*2 AS wiki_rank " .
"FROM $userTable u JOIN (($sqlMostPages) UNION ($sqlMostRevs)) s ON (user_id=rev_user) " .
"ORDER BY wiki_rank DESC " .
"LIMIT $limit";
$res = $dbr->query( $sql );
$sortable = in_array( 'nosort', $opts ) ? '' : ' sortable';
$output = "<table class=\"wikitable contributionscores plainlinks{$sortable}\" >\n" .
"<tr class='header'>\n" .
Html::element( 'th', [], $this->msg( 'contributionscores-rank' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-score' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-pages' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-changes' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-username' )->text() );
$altrow = '';
$user_rank = 1;
$lang = $this->getLanguage();
foreach ( $res as $row ) {
// Use real name if option used and real name present.
if ( $wgContribScoresUseRealName && $row->user_real_name !== '' ) {
$userLink = Linker::userLink(
$row->user_id,
$row->user_name,
$row->user_real_name
);
} else {
$userLink = Linker::userLink(
$row->user_id,
$row->user_name
);
}
$output .= Html::closeElement( 'tr' );
$output .= "<tr class='{$altrow}'>\n" .
"<td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( round( $user_rank, 0 ) ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( round( $row->wiki_rank, 0 ) ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( $row->page_count ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( $row->rev_count ) .
"\n</td><td class='content'>" .
$userLink;
# Option to not display user tools
if ( !in_array( 'notools', $opts ) ) {
$output .= Linker::userToolLinks( $row->user_id, $row->user_name );
}
$output .= Html::closeElement( 'td' ) . "\n";
if ( $altrow == '' && empty( $sortable ) ) {
$altrow = 'odd ';
} else {
$altrow = '';
}
$user_rank++;
}
$output .= Html::closeElement( 'tr' );
$output .= Html::closeElement( 'table' );
$dbr->freeResult( $res );
if ( !empty( $title ) ) {
$output = Html::rawElement( 'table',
[
'style' => 'border-spacing: 0; padding: 0',
'class' => 'contributionscores-wrapper',
'lang' => htmlspecialchars( $lang->getCode() ),
'dir' => $lang->getDir()
],
"\n" .
"<tr>\n" .
"<td style='padding: 0px;'>{$title}</td>\n" .
"</tr>\n" .
"<tr>\n" .
"<td style='padding: 0px;'>{$output}</td>\n" .
"</tr>\n"
);
}
return $output;
}
function execute( $par ) {
$this->setHeaders();
if ( $this->including() ) {
$this->showInclude( $par );
} else {
$this->showPage();
}
return true;
}
/**
* Called when being included on a normal wiki page.
* Cache is disabled so it can depend on the user language.
* @param string|null $par A subpage give to the special page
*/
function showInclude( $par ) {
$days = null;
$limit = null;
$options = 'none';
if ( !empty( $par ) ) {
$params = explode( '/', $par );
$limit = intval( $params[0] );
if ( isset( $params[1] ) ) {
$days = intval( $params[1] );
}
if ( isset( $params[2] ) ) {
$options = $params[2];
}
}
if ( empty( $limit ) || $limit < 1 || $limit > CONTRIBUTIONSCORES_MAXINCLUDELIMIT ) {
$limit = 10;
}
if ( is_null( $days ) || $days < 0 ) {
$days = 7;
}
if ( $days > 0 ) {
$reportTitle = $this->msg( 'contributionscores-days' )->numParams( $days )->text();
} else {
$reportTitle = $this->msg( 'contributionscores-allrevisions' )->text();
}
$reportTitle .= ' ' . $this->msg( 'contributionscores-top' )->numParams( $limit )->text();
$title = Xml::element( 'h4',
[ 'class' => 'contributionscores-title' ],
$reportTitle
) . "\n";
$this->getOutput()->addHTML( $this->genContributionScoreTable(
$days,
$limit,
$title,
$options
) );
}
/**
* Show the special page
*/
function showPage() {
global $wgContribScoreReports;
if ( !is_array( $wgContribScoreReports ) ) {
$wgContribScoreReports = [
[ 7, 50 ],
[ 30, 50 ],
[ 0, 50 ]
];
}
$out = $this->getOutput();
$out->addWikiMsg( 'contributionscores-info' );
foreach ( $wgContribScoreReports as $scoreReport ) {
list( $days, $revs ) = $scoreReport;
if ( $days > 0 ) {
$reportTitle = $this->msg( 'contributionscores-days' )->numParams( $days )->text();
} else {
$reportTitle = $this->msg( 'contributionscores-allrevisions' )->text();
}
$reportTitle .= ' ' . $this->msg( 'contributionscores-top' )->numParams( $revs )->text();
$title = Xml::element( 'h2',
[ 'class' => 'contributionscores-title' ],
$reportTitle
) . "\n";
$out->addHTML( $title );
$out->addHTML( $this->genContributionScoreTable( $days, $revs ) );
}
}
protected function getGroupName() {
return 'wiki';
}
}

View file

@ -1,26 +1,29 @@
/* eslint-env node, es6 */
/*jshint node:true */
module.exports = function ( grunt ) {
'use strict';
grunt.loadNpmTasks( 'grunt-contrib-jshint' );
grunt.loadNpmTasks( 'grunt-banana-checker' );
grunt.loadNpmTasks( 'grunt-eslint' );
grunt.loadNpmTasks( 'grunt-jsonlint' );
grunt.initConfig( {
jshint: {
all: [
'*.js'
]
},
banana: {
all: 'i18n'
},
eslint: {
options: {
cache: true
},
jsonlint: {
all: [
'**/*.{js,json}',
'**/*.json',
'!node_modules/**',
'!vendor/**'
]
}
} );
grunt.registerTask( 'test', [ 'eslint', 'banana' ] );
grunt.registerTask( 'test', [ 'jshint', 'jsonlint', 'banana' ] );
grunt.registerTask( 'default', 'test' );
};

View file

@ -1,9 +1,9 @@
{
"require-dev": {
"mediawiki/mediawiki-codesniffer": "45.0.0",
"mediawiki/minus-x": "1.1.3",
"php-parallel-lint/php-console-highlighter": "1.0.0",
"php-parallel-lint/php-parallel-lint": "1.4.0"
"mediawiki/mediawiki-codesniffer": "19.4.0",
"mediawiki/minus-x": "0.3.1",
"php-parallel-lint/php-console-highlighter": "0.3.2",
"php-parallel-lint/php-parallel-lint": "1.0.0"
},
"scripts": {
"fix": [
@ -16,10 +16,5 @@
"minus-x check ."
],
"phpcs": "phpcs -sp --cache"
},
"config": {
"allow-plugins": {
"dealerdirect/phpcodesniffer-composer-installer": true
}
}
}

View file

@ -1,64 +0,0 @@
{
"name": "ContributionScores",
"author": "Tim Laqua",
"url": "https://www.mediawiki.org/wiki/Extension:Contribution_Scores",
"descriptionmsg": "contributionscores-desc",
"version": "1.26.1",
"type": "specialpage",
"requires": {
"MediaWiki": ">= 1.34.0"
},
"SpecialPages": {
"ContributionScores": "ContributionScores"
},
"AutoloadClasses": {
"ContributionScores": "src/ContributionScores.php"
},
"Hooks": {
"ParserFirstCallInit": "ContributionScores::onParserFirstCallInit"
},
"MessagesDirs": {
"ContributionScores": [
"i18n"
]
},
"ExtensionMessagesFiles": {
"ContribScoreAlias": "ContributionScores.alias.php",
"ContribScoreMagic": "ContributionScores.i18n.magic.php"
},
"config": {
"ContribScoreReports": {
"value": null,
"description": "Each array defines a report - 7,50 is \"past 7 days \" and \"LIMIT 50 \" - Can be omitted."
},
"ContribScoreIgnoreBlockedUsers": {
"value": false,
"description": "Set to true to exclude blocked users from the reporting."
},
"ContribScoreIgnoreBots": {
"value": false,
"description": "Set to true to exclude bots users from the reporting."
},
"ContribScoreIgnoreUsernames": {
"value": [],
"description": "Array of usernames to exclude from the reporting."
},
"ContribScoresUseRealName": {
"value": false,
"description": "Set to true to use real user names when available."
},
"ContribScoreDisableCache": {
"value": false,
"description": "Set to true to disable cache for parser function and inclusion of table."
},
"ContribScoreUseRoughEditCount": {
"value": false,
"description": "Set to true to use the rough number of edits in user table, for performance issue."
},
"ContribScoreCacheTTL": {
"value": 30,
"description": "Cache the contribution scores data, in minutes."
}
},
"manifest_version": 2
}

View file

@ -4,8 +4,7 @@
"Meno25",
"Mido",
"OsamaK",
"ترجمان05",
"ديفيد"
"ترجمان05"
]
},
"contributionscores": "نتائج المساهمات",
@ -15,7 +14,6 @@
"contributionscores-days": "{{PLURAL:$1||اليوم الماضي|اليومان الماضيان|ال$1 أيام الماضية|ال$1 يومًا الماضية|ال$1 يوم الماضية}}",
"contributionscores-allrevisions": "كل الوقت",
"contributionscores-score": "النتيجة",
"contributionscores-rank": "الرتبة",
"contributionscores-pages": "الصفحات",
"contributionscores-changes": "تغييرات",
"contributionscores-username": "اسم المستخدم",

View file

@ -1,8 +1,8 @@
{
"@metadata": {
"authors": [
"Alp Er Tunqa",
"Mousa"
"Mousa",
"Alp Er Tunqa"
]
},
"contributionscores": "چالیشماق امتیازلاری",

View file

@ -1,11 +1,10 @@
{
"@metadata": {
"authors": [
"Aftab1995",
"Aftabuzzaman",
"Bellayet",
"Wikitanvir",
"আফতাবুজ্জামান"
"Aftab1995",
"Aftabuzzaman"
]
},
"contributionscores": "অনুদানের স্কোর",

View file

@ -3,8 +3,7 @@
"authors": [
"CERminator",
"KWiki",
"Srdjan m",
"Srđan"
"Srdjan m"
]
},
"contributionscores": "Rezultat doprinosa",

View file

@ -1,9 +0,0 @@
{
"@metadata": {
"authors": [
"Robin Owain"
]
},
"contributionscores-score": "Sgor",
"contributionscores-changes": "Newidiadau"
}

View file

@ -4,8 +4,7 @@
"Byrial",
"Christian List",
"Kaare",
"Peter Alberti",
"Saederup92"
"Peter Alberti"
]
},
"contributionscores": "Bidragspoint",
@ -15,7 +14,6 @@
"contributionscores-days": "Sidste {{PLURAL:$1|dag|$1 dage}}",
"contributionscores-allrevisions": "Gennem tiden",
"contributionscores-score": "Point",
"contributionscores-rank": "Rang",
"contributionscores-pages": "Sider",
"contributionscores-changes": "Ændringer",
"contributionscores-username": "Brugernavn",

View file

@ -8,7 +8,7 @@
]
},
"contributionscores": "Statistik zu Benutzern",
"contributionscores-desc": "Erweitert das Wiki um eine [[Special:ContributionScores|Spezialseite]] zum Ermitteln der Benutzer mit den meisten Beiträgen",
"contributionscores-desc": "Ergänzt eine [[Special:ContributionScores|Spezialseite]] zum Abfragen der Datenbank des Wikis bezüglich der Benutzer mit den meisten Beiträgen",
"contributionscores-info": "In die Bewertung fließen hauptsächlich einmalig bearbeitete Seiten unter Berücksichtigung einer hohen Bearbeitungszahl ein.",
"contributionscores-top": "(Top $1)",
"contributionscores-days": "{{PLURAL:$1|Letzter Tag|Letzte $1 Tage}}",

View file

@ -2,8 +2,8 @@
"@metadata": {
"authors": [
"Erdemaslancan",
"Marmase",
"Mirzali"
"Mirzali",
"Marmase"
]
},
"contributionscores": "Skorê iştıraqan",
@ -11,9 +11,9 @@
"contributionscores-info": "Ebe pawıtışê hecmê tedqiqê berzi ra, puwan raveri pelanê bêemsalanê vurniyayeyan senceno.",
"contributionscores-top": "(Tewr Gırde $1)",
"contributionscores-days": "{{PLURAL:$1|Roca peyêne|$1 Rocê peyêni}}",
"contributionscores-allrevisions": "Her dem",
"contributionscores-score": "Puwan",
"contributionscores-rank": "Rêze",
"contributionscores-allrevisions": "Çaxan de hemi",
"contributionscores-score": "Skor",
"contributionscores-rank": "Rate",
"contributionscores-pages": "Peli",
"contributionscores-changes": "Vurnayışi",
"contributionscores-username": "Nameyê karberi",

View file

@ -4,8 +4,8 @@
"Consta",
"Crazymadlover",
"Omnipaedista",
"Protnet",
"ZaDiak"
"ZaDiak",
"Protnet"
]
},
"contributionscores": "Βαθμολογίες συνεισφοράς",

View file

@ -15,4 +15,4 @@
"contributionscores-username": "Username",
"contributionscores-invalidusername": "Invalid username",
"contributionscores-invalidmetric": "Invalid metric"
}
}

View file

@ -2,22 +2,20 @@
"@metadata": {
"authors": [
"Michawiki",
"Mirin",
"Robin van der Vliet",
"Yekrats"
"Yekrats",
"Robin van der Vliet"
]
},
"contributionscores": "Poentaro de Kontribuoj",
"contributionscores-desc": "Informmendas la vikian datumbazon por la plej [[Special:ContributionScores|oftaj kontribuantoj]]",
"contributionscores-info": "La poentaroj precipe mezuras la nombrojn de unikaj redaktitaj paĝoj, kun konsiderado pri grandega kvanto de redaktoj.",
"contributionscores-info": "Poentaroj estas donataj jene:\n*Unu (1) poento por ĉiu unika paĝo redaktata\n*Kvadrata Radiko de (Tutaj Faritaj Redaktoj) - (Tutaj Unikaj Paĝoj) * 2\nPoentaroj kalkulitaj laŭ ĉi tiu maniero pezos redaktan diversecon super redaktan volumon.\nBaze, ĉi tiu poentaro mezuras ĉefe unikajn paĝojn redaktitajn, kun konsidero por altaj redakto-volumon - supozita esti pli altkvalita paĝo.",
"contributionscores-top": "(Plej alta $1)",
"contributionscores-days": "{{PLURAL:$1|Lasta tago|Lastaj $1 tagoj}}",
"contributionscores-allrevisions": "Ĉiame",
"contributionscores-score": "Poentaro",
"contributionscores-rank": "Rango",
"contributionscores-pages": "Paĝoj",
"contributionscores-changes": "Ŝanĝoj",
"contributionscores-username": "Uzantnomo",
"contributionscores-invalidusername": "Nevalida uzantnomo",
"contributionscores-invalidusername": "Nevalida salutnomo",
"contributionscores-invalidmetric": "Nevalida parametro"
}

View file

@ -6,8 +6,8 @@
"Fitoschido",
"Ihojose",
"Imre",
"Macofe",
"Sanbec"
"Sanbec",
"Macofe"
]
},
"contributionscores": "Puntuaciones de contribuciones",

8
i18n/ext.json Normal file
View file

@ -0,0 +1,8 @@
{
"@metadata": {
"authors": [
"Better"
]
},
"contributionscores-days": "Úrtimus $1 dias"
}

View file

@ -1,13 +1,13 @@
{
"@metadata": {
"authors": [
"Alirezaaa",
"Ebraminio",
"Huji",
"Mjbmr",
"Reza1615",
"Tofighi",
"ZxxZxxZ"
"ZxxZxxZ",
"Alirezaaa"
]
},
"contributionscores": "امتیاز مشارکت",

View file

@ -1,13 +1,12 @@
{
"@metadata": {
"authors": [
"01miki10",
"Crt",
"Nike",
"Pxos",
"Pyscowicz",
"Str4nd",
"Stryn"
"Stryn",
"Pxos",
"Pyscowicz"
]
},
"contributionscores": "Muokkauspisteet",
@ -19,7 +18,7 @@
"contributionscores-rank": "Sija",
"contributionscores-pages": "Sivuja",
"contributionscores-changes": "Muutoksia",
"contributionscores-username": "Käyttäjänimi",
"contributionscores-invalidusername": "Virheellinen käyttäjänimi",
"contributionscores-username": "Käyttäjätunnus",
"contributionscores-invalidusername": "Virheellinen käyttäjätunnus",
"contributionscores-invalidmetric": "Virheellinen muuttuja"
}

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"Pyscowicz"
]
},
"contributionscores": "Mookkauspisteet"
}

View file

@ -21,6 +21,6 @@
"contributionscores-pages": "Pages",
"contributionscores-changes": "Changements",
"contributionscores-username": "Nom dutilisateur",
"contributionscores-invalidusername": "Nom dutilisateur incorrect",
"contributionscores-invalidusername": "Nom dutilisateur invalide",
"contributionscores-invalidmetric": "Métrique incorrecte"
}

View file

@ -1,11 +1,10 @@
{
"@metadata": {
"authors": [
"PiefPafPier",
"Robin van der Vliet",
"Snakesteuben",
"Robin0van0der0vliet",
"Snakesteuben"
"Robin van der Vliet"
]
},
"contributionscores-username": "Meidochnamme"
"contributionscores-username": "Brûkersnamme"
}

View file

@ -3,8 +3,8 @@
"authors": [
"Ansumang",
"Kaustubh",
"Sfic",
"Siddhartha Ghai"
"Siddhartha Ghai",
"Sfic"
]
},
"contributionscores": "योगदान संख्या",

View file

@ -3,21 +3,19 @@
"authors": [
"Dalibor Bosits",
"Ex13",
"MaGa",
"SpeedyGonsales"
]
},
"contributionscores": "Najbolji suradnici",
"contributionscores-desc": "Šalje upit bazi podataka za najveći [[Special:ContributionScores|broj suradničkih doprinosa]]",
"contributionscores-info": "U prvom planu rezultat mjeri jedinstvene izmijenjene stranice, uzimajući u obzir veliku količinu uređivanja.",
"contributionscores-top": "(najboljih $1)",
"contributionscores-info": "Rezultat se dobiva kao suma slijedećih stavki:\n*1 bod za svaku stranicu koju ste uređivali\n* (kvadratni) korijen iz (broja ukupnih uređivanja) - (broja stranica koje ste uređivali) * 2\n\nRezultat dobiven na ovaj način daje veću težinu broju uređivanja različitih stranica nego ukupnom broju uređivanja. U osnovi, ovakav rezultat mjeri prvenstveno broj različitih stranica koje ste uređivali, uzimajući u obzir broj uređivanja, jer veći broj uređivanja na nekom članku daje kvalitetniji članak.",
"contributionscores-top": "(Najboljih $1)",
"contributionscores-days": "{{PLURAL:$1|Zadnji dan|Zadnjih $1 dana}}",
"contributionscores-allrevisions": "Sve vrijeme",
"contributionscores-allrevisions": "Sva uređivanja",
"contributionscores-score": "Rezultat",
"contributionscores-rank": "Mjesto",
"contributionscores-pages": "Stranica",
"contributionscores-changes": "Uređivanja",
"contributionscores-username": "Suradničko ime",
"contributionscores-username": "Ime suradnika",
"contributionscores-invalidusername": "Nevaljano suradničko ime",
"contributionscores-invalidmetric": "Nevaljana metrika"
}

View file

@ -2,18 +2,16 @@
"@metadata": {
"authors": [
"IvanLanin",
"Rex",
"William Surya Permana"
"Rex"
]
},
"contributionscores": "Nilai kontribusi",
"contributionscores-desc": "Menghitung [[Special:ContributionScores|volume kontribusi pengguna]] terbanyak di basis data wiki",
"contributionscores-info": "Nilai ini secara garis besar mengukur halaman unik yang disunting, dengan pertimbangan volume suntingan yang tinggi.",
"contributionscores-top": "($1 teratas)",
"contributionscores": "Skor kontribusi",
"contributionscores-desc": "Menghitung [[Special:ContributionScores|jumlah kontribusi pengguna]] terbanyak di basis data wiki",
"contributionscores-info": "Skor dihitung dengan cara berikut:\n* Satu (1) poin untuk setiap halaman tunggal yang disunting\n* Akar kuadrat dari (total suntingan) - (total halaman tunggal) * 2\nSkor dihitung dengan cara ini untuk menghasilkan jumlah tertimbang penyuntingan berbanding volume suntingan.\nPada dasarnya, skor ini menghitung jumlah halaman tunggal yang disunting, dengan pertimbangan di mana volume suntingan yang tinggi - diasumsikan sebagai halaman dengan kualitas lebih tinggi.",
"contributionscores-top": "($1 tertinggi)",
"contributionscores-days": "{{PLURAL:$1|Hari|$1 hari}} terakhir",
"contributionscores-allrevisions": "Sepanjang masa",
"contributionscores-score": "Nilai",
"contributionscores-rank": "Peringkat",
"contributionscores-score": "Skor",
"contributionscores-pages": "Halaman",
"contributionscores-changes": "Perubahan",
"contributionscores-username": "Nama pengguna",

View file

@ -6,12 +6,11 @@
},
"contributionscores": "Contes de contribution",
"contributionscores-desc": "Calcula li funde de data del wiki por max alt [[Special:ContributionScores|volúmine de contribution de usator]]",
"contributionscores-info": "Li calcul primarimen mesura págines unic redactet, considerant li alt volume de redactiones.",
"contributionscores-info": "Contes es calculat quam seque:\n*Un (1) punctu por chascun págine unic redactet\n*Fonte de quadrat de (total de redactiones fat) - (total unique pages) * 2\nContes calculat in ti diversitá de redaction in pesa maniere súper de volúmine de redaction.\nBasicmen, ti conte mesura primarimen págines unic redactet, che consideration por alt volúmine de redaction - suposit esser un págine de alt qualitá.",
"contributionscores-top": "(Prim $1)",
"contributionscores-days": "Ultim {{PLURAL:$1|die|$1 dies}}",
"contributionscores-allrevisions": "Omni témpor",
"contributionscores-score": "Conte",
"contributionscores-rank": "Classification",
"contributionscores-pages": "Págines",
"contributionscores-changes": "Changes",
"contributionscores-username": "Nómine de usator",

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"Ukabia"
]
},
"contributionscores-username": "Ahàǹjìème"
}

View file

@ -4,9 +4,5 @@
"Joao Xavier"
]
},
"contributionscores-days": "Lasta {{PLURAL:$1|dio|$1 dii}}",
"contributionscores-score": "Nombro di punti",
"contributionscores-pages": "Pagini",
"contributionscores-changes": "Modifikuri",
"contributionscores-username": "Uzeronomo"
"contributionscores-days": "Lasta {{PLURAL:$1|dio|$1 dii}}"
}

View file

@ -16,7 +16,5 @@
"contributionscores-rank": "Sæti",
"contributionscores-pages": "Síður",
"contributionscores-changes": "Breytingar",
"contributionscores-username": "Notandanafn",
"contributionscores-invalidusername": "Ógilt notandanafn",
"contributionscores-invalidmetric": "Ógild mæling"
"contributionscores-username": "Notandanafn"
}

View file

@ -1,15 +1,13 @@
{
"@metadata": {
"authors": [
"Diki Ananta",
"Meursault2004",
"NoiX180",
"Pras",
"Sumbukompor"
"NoiX180"
]
},
"contributionscores": "Bijining pasumbang",
"contributionscores-desc": "Nglakokaké polling (angkèt) ing basis data kanggo [[Special:ContributionScores|volume kontribusi naraguna]]",
"contributionscores-desc": "Nglakokaké polling (angkèt) ing basis data kanggo [[Special:ContributionScores|volume kontribusi panganggo]]",
"contributionscores-info": "Skoré diétung kaya mangkéné:\n* Biji siji (1) per kaca unik sing disunting\n* Oyot (bs. Indonesia ''akar'') saka (Gunggungé Suntingan) - (Gunggungé Kaca-KAca Unik) * 2\nSkor sing diétung miturut cara iki bisa nyerminaké divèrsitas suntingan sadhuwuring volume suntingan.\nSacara dhasar, skor iki utamané ngétung kaca-kaca unik sing disunting, karo mélu nimbangaké volume suntingan dhuwur - diasumsèkaké kwalitas kacané luwih dhuwur.",
"contributionscores-top": "(Top $1)",
"contributionscores-days": "{{PLURAL:$1|dina|$1 dina}} pungkasan",
@ -18,7 +16,7 @@
"contributionscores-rank": "Rangking",
"contributionscores-pages": "Kaca",
"contributionscores-changes": "Owah-owahan",
"contributionscores-username": "Jeneng naraguna",
"contributionscores-invalidusername": "Jeneng naraguna ora sah",
"contributionscores-username": "Jeneng panganggo",
"contributionscores-invalidusername": "Jeneng panganggo ora sah",
"contributionscores-invalidmetric": "Metrik ora sah"
}

View file

@ -1,12 +0,0 @@
{
"@metadata": {
"authors": [
"Mirzali"
]
},
"contributionscores-score": "Puwan",
"contributionscores-rank": "Rêze",
"contributionscores-pages": "Peli",
"contributionscores-changes": "Vurnayışi",
"contributionscores-username": "Namê karberi"
}

View file

@ -1,12 +0,0 @@
{
"@metadata": {
"authors": [
"Rul1902"
]
},
"contributionscores-score": "အ်ုဏါင်းဏေဝ်ႋ",
"contributionscores-rank": "အ်ုထေါဟ်",
"contributionscores-pages": "လိက်မေံၜၠါ်လ်ုဖး",
"contributionscores-changes": "မ်ုအင်းလယ်လ်ုဖး",
"contributionscores-username": "ဆ်ုသုံႋဆာႋမိင်"
}

View file

@ -1,7 +1,5 @@
{
"@metadata": {
"authors": []
},
"@metadata": [],
"contributionscores": "Üles berw esepteri",
"contributionscores-info": "Esepter kelesi deý sanaladı:\n*1 upaý ärbir tüzetilgen biregeý bet üşin\n*Mınanıñ şarşı tübiri (Barlıq İstelingen Tüzetwler) (Barlıq Biregeý Better) * 2\nOsı täsilmen sanalğan esepter tüzetw awqımındağı öñdew ärkelkiliginiñ salmağın ölşeýdi. Negizinde, bul esep aldımen tüzetilgen birkelki betterdi ölşeýdi, joğarğı öñdew awqımımen birge — joğarı sapalı bet jağdaýımen eseptep.",
"contributionscores-top": "(Joğarğı $1)",

View file

@ -3,9 +3,9 @@
"authors": [
"Hym411",
"Priviet",
"Revi",
"Shirayuki",
"아라"
"아라",
"Revi"
]
},
"contributionscores": "기여 점수",

View file

@ -1,12 +1,10 @@
{
"@metadata": {
"authors": [
"Balyozxane",
"George Animal"
]
},
"contributionscores-allrevisions": "Hemû dem",
"contributionscores-pages": "Rûpel",
"contributionscores-changes": "Guhartin",
"contributionscores-username": "Navê bikarhêner"
}

View file

@ -6,7 +6,7 @@
]
},
"contributionscores": "Bewäertung vun den Ännerungen",
"contributionscores-desc": "Ufro un d'Wiki-Datebank no den héchste [[Special:ContributionScores|Benotzerscoren]]",
"contributionscores-desc": "Ufro un d'Wiki-Datebank no den héichste [[Special:ContributionScores|Benotzerscoren]]",
"contributionscores-info": "D'Bewäertung moosst Zuel vu geännerte Säite a consideréiert d'Zuel vun den Ännerungen.",
"contributionscores-top": "(Top $1)",
"contributionscores-days": "{{PLURAL:$1|Leschten Dag|Lescht $1 Deeg}}",

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"Giromin Cangiaxo"
]
},
"contributionscores": "Pontezzi contributi"
}

View file

@ -6,7 +6,7 @@
},
"contributionscores": "Оцени за придонеси",
"contributionscores-desc": "Презема податоци од викибазата за [[Special:ContributionScores|корисници со највеќе придонеси]]",
"contributionscores-info": "Салдото е мерка што изразува уредувања на одделни страници, со оглед на големиот број на уредувања.",
"contributionscores-info": "Салдото е мерка што изразува уредувања на засебни страници, со оглед на големиот број на уредувања.",
"contributionscores-top": "(Најдобри $1)",
"contributionscores-days": "{{PLURAL:$1|Последниот ден|Последните $1 дена}}",
"contributionscores-allrevisions": "На сите времиња",
@ -16,5 +16,5 @@
"contributionscores-changes": "Измени",
"contributionscores-username": "Корисничко име",
"contributionscores-invalidusername": "Неправилно корисничко име",
"contributionscores-invalidmetric": "Грешно мерило"
"contributionscores-invalidmetric": "Грешна метрика"
}

View file

@ -1,13 +0,0 @@
{
"@metadata": {
"authors": [
"Awangba Mangang"
]
},
"contributionscores-allrevisions": "ꯃꯇꯝ ꯄꯨꯂꯞ",
"contributionscores-rank": "ꯊꯥꯛ",
"contributionscores-pages": "ꯂꯃꯥꯏꯁꯤꯡ",
"contributionscores-changes": "ꯑꯍꯣꯡꯕꯁꯤꯡ",
"contributionscores-username": "ꯁꯤꯖꯤꯟꯅꯔꯤꯕ ꯃꯃꯤꯡ",
"contributionscores-invalidusername": "ꯁꯤꯖꯤꯟꯅꯔꯤꯕ ꯃꯃꯤꯡ ꯌꯥꯎꯗꯦ"
}

View file

@ -1,18 +1,8 @@
{
"@metadata": {
"authors": [
"Dr Lotus Black",
"Ninjastrikers"
]
},
"contributionscores": "ပံ့ပို့မှု ရမှတ်များ",
"contributionscores-top": "(ထိပ်ဆုံး $1)",
"contributionscores-days": "နောက်ဆုံး {{PLURAL:$1|ရက်|$1 ရက်}}",
"contributionscores-allrevisions": "တချိန်လုံး",
"contributionscores-score": "ရမှတ်",
"contributionscores-rank": "အဆင့်",
"contributionscores-pages": "စာမျက်နှာများ",
"contributionscores-changes": "အပြောင်းအလဲများ",
"contributionscores-username": "အသုံးပြုသူအမည်",
"contributionscores-invalidusername": "အသုံးပြုသူအမည် မမှန်ကန်ပါ"
"contributionscores-pages": "စာမျက်နှာများ"
}

View file

@ -1,10 +1,9 @@
{
"@metadata": {
"authors": [
"Akapochtli",
"Fluence"
]
},
"contributionscores-changes": "Tlapatlaliztli",
"contributionscores-username": "Tequitiuhcatocaitll"
"contributionscores-username": "Tlatequitiltilīltōcāitl"
}

View file

@ -1,10 +1,10 @@
{
"@metadata": {
"authors": [
"Danmichaelo",
"Nghtwlkr",
"Helland",
"Jon Harald Søby",
"Nghtwlkr"
"Danmichaelo",
"Jon Harald Søby"
]
},
"contributionscores": "Bidragspoeng",

View file

@ -1,17 +1,8 @@
{
"@metadata": {
"authors": [
"RajeshPandey",
"पर्वत सुबेदी"
"RajeshPandey"
]
},
"contributionscores": "योगदान प्राप्ताङ्कहरू",
"contributionscores-days": "अन्तिम {{PLURAL:$1|दिन|$1 दिनहरू}}",
"contributionscores-allrevisions": "सबै समय",
"contributionscores-score": "प्राप्ताङ्क",
"contributionscores-rank": "क्रम",
"contributionscores-pages": "पृष्ठहरू",
"contributionscores-changes": "परिवर्तनहरू",
"contributionscores-username": "प्रयोगकर्ता नाम",
"contributionscores-invalidusername": "अबैध प्रयोगकर्ता नाम"
"contributionscores-username": "प्रयोगकर्ता नाम"
}

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"BukhariSaeed"
]
},
"contributionscores-changes": "ਤਬਦੀਲੀਆਂ"
}

View file

@ -5,15 +5,13 @@
"Derbeth",
"Equadus",
"McMonster",
"Rail",
"Railfail536",
"Sp5uhe",
"Wpedzich"
]
},
"contributionscores": "Punkty za edycje",
"contributionscores-desc": "Wylicza [[Special:ContributionScores|punkty za edycje]] dla użytkowników",
"contributionscores-info": "Wynik jest uzależniony przede wszystkim od liczby edytowanych unikalnych stron z uwzględnieniem dużej liczby edycji zakładając wyższą wartość tworzenia nowych artykułów.",
"contributionscores-info": "Punkty za edycje naliczane są następującą metodą:\n*1 punkt za każdą edytowaną unikalną stronę\n*pierwiastek kwadratowy z (ogólna liczba edycji) - (wszystkich unikalnych stron) * 2\nTaki sposób naliczania pozwala wyważyć różnorodność edycji względem liczby edycji. Zasadniczo wynik uzależniony jest od liczby edytowanych unikalnych stron z uwzględnieniem dużej liczby edycji zakładając wyższą wartość tworzenia nowych artykułów.",
"contributionscores-top": "($1 najlepszych)",
"contributionscores-days": "{{PLURAL:$1|Ostatni 1 dzień|Ostatnie $1 dni|Ostatnich $1 dni}}",
"contributionscores-allrevisions": "Cała aktywność",

View file

@ -1,11 +1,8 @@
{
"@metadata": {
"authors": [
"Abbas dhothar",
"BukhariSaeed"
]
},
"contributionscores-days": "پچھلے{{PLURAL:$1|دن|$1 دناں}}",
"contributionscores-changes": "تبدیلیاں",
"contributionscores-username": "ورتن آلے دا ناں"
}

View file

@ -2,7 +2,6 @@
"@metadata": {
"authors": [
"Ahmed-Najib-Biabani-Ibrahimkhel",
"Amjad Khan",
"Baloch Khan"
]
},

View file

@ -1,13 +1,13 @@
{
"@metadata": {
"authors": [
"!Silent",
"Brunoy Anastasiya Seryozhenko",
"Crazymadlover",
"Eduardo.mps",
"Giro720",
"HenriqueCrang",
"Luckas",
"HenriqueCrang",
"!Silent",
"Opraco"
]
},

View file

@ -1,12 +1,11 @@
{
"@metadata": {
"authors": [
"Fúlvio",
"Hamilton Abreu",
"Malafaya",
"Vitorvicentevalente",
"Waldir",
"Waldyrious"
"Vitorvicentevalente",
"Fúlvio"
]
},
"contributionscores": "Pontuação de contribuições",

View file

@ -4,11 +4,11 @@
"Jon Harald Søby",
"JtFuruhata",
"Kalan",
"Liuxinyu970226",
"Mormegil",
"Purodha",
"Raymond",
"Shirayuki",
"Liuxinyu970226",
"Tacsipacsi"
]
},

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"AlimanRuna"
]
},
"contributionscores-days": "Qayna {{PLURAL:$1|p'unchaw|$1 p'unchawkuna}}"
}

View file

@ -2,12 +2,12 @@
"@metadata": {
"authors": [
"Ahonc",
"Kaganer",
"Kalan",
"Lockal",
"Okras",
"Ole Yves",
"Александр Сигачёв"
"Александр Сигачёв",
"Kaganer"
]
},
"contributionscores": "Оценка вклада",

View file

@ -1,12 +1,9 @@
{
"@metadata": {
"authors": [
"Mehtab ahmed",
"Tweety"
"Mehtab ahmed"
]
},
"contributionscores-days": "گذريل {{PLURAL:$1|ڏينھن|$1 ڏينھن}}",
"contributionscores-pages": "صفحا",
"contributionscores-changes": "بدلاءَ",
"contributionscores-username": "واپرائيندڙ-نانءُ"
"contributionscores-changes": "تبديليون"
}

View file

@ -1,20 +0,0 @@
{
"@metadata": {
"authors": [
"Vlad5250"
]
},
"contributionscores": "Ocjene za doprinose",
"contributionscores-desc": "Preuzima podatke s wikibaze podataka za [[Special:ContributionScores|korisnike s najviše doprinosa]]",
"contributionscores-info": "Saldo je mjera koja izražava uređivanja pojedinačnih stranica, uzimajući u obzir velike količine uređivanja.",
"contributionscores-top": "(Najboljih $1)",
"contributionscores-days": "{{PLURAL:$1|Posljednji $1 dan|Posljednja $1 dana|Posljednjih $1 dana}}",
"contributionscores-allrevisions": "Svih vremena",
"contributionscores-score": "Ocjena",
"contributionscores-rank": "Rang",
"contributionscores-pages": "Stranice",
"contributionscores-changes": "Izmjene",
"contributionscores-username": "Korisničko ime",
"contributionscores-invalidusername": "Nevaljano korisničko ime",
"contributionscores-invalidmetric": "Nevaljana metrika"
}

View file

@ -2,19 +2,16 @@
"@metadata": {
"authors": [
"Helix84",
"Luky001",
"Teslaton",
"Yardom78"
"Teslaton"
]
},
"contributionscores": "Skóre príspevkov",
"contributionscores-desc": "Získava údaje z databázy wiki o [[Special:ContributionScores|množstve používateľských príspevkov]]",
"contributionscores-info": "Skóre primárne meria jedinečné editované stránky s ohľadom na veľké množstvo úprav.",
"contributionscores-desc": "Zisťuje naväčší [[Special:ContributionScores|objem používateľských príspevkov]] z databázy wiki",
"contributionscores-info": "Skóre sa počíta nasledovne:\n*1 bod za každú jedinečnú stránku, ktorú používateľ upravoval\n*Odmocnina z (celkom úprav) - (celkom jedinečných stránok) * 2\nSkóre vypočítané týmto spôsobom vážia diverzitu úprav viac ako objem úprav. V podstate toto skóre meria najmä počet upravovaných jedinečných stránok s prihliadnutím na vysoký objem úprav; čo sa pokladá za stránku vyššej kvality.",
"contributionscores-top": "(Najlepších $1)",
"contributionscores-days": "{{PLURAL:$1|Posledný $1 deň|Posledné $1 dni|Posledných $1 dní}}",
"contributionscores-allrevisions": "Celkom",
"contributionscores-allrevisions": "Celá história",
"contributionscores-score": "Skóre",
"contributionscores-rank": "Poradie",
"contributionscores-pages": "Stránky",
"contributionscores-changes": "Zmeny",
"contributionscores-username": "Používateľské meno",

View file

@ -1,18 +1,14 @@
{
"@metadata": {
"authors": [
"Acamicamacaraca",
"Kizule",
"Milicevic01",
"Rancher",
"Sasa Stefanovic",
"Михајло Анђелковић",
"Zoranzoki21",
"Михајло Анђелковић"
"Acamicamacaraca"
]
},
"contributionscores": "Оцене доприноса",
"contributionscores-desc": "Анкетира вики базу података за највиши [[Special:ContributionScores|волумен доприноса корисника]]",
"contributionscores-info": "Резултат првенствено мери јединствене измењене странице, узимајући у обзир велику количину уређивања.",
"contributionscores-top": "(првих $1)",
"contributionscores-days": "{{PLURAL:$1|1=Последњег дана|Последњих $1 дана}}",
"contributionscores-allrevisions": "Свих времена",

View file

@ -1,22 +1,18 @@
{
"@metadata": {
"authors": [
"Aefgh39622",
"Ans",
"Woraponboonkerd"
"Woraponboonkerd",
"Ans"
]
},
"contributionscores": "คะแนนการแก้ไข",
"contributionscores-desc": "จัดอันดับฐานข้อมูลของวิกิสำหรับ[[Special:ContributionScores|ผู้ใ้ช้ที่มีจำนวนการแก้ไขสูงสุด]]",
"contributionscores-info": "คะแนนคิดจากจำนวนหน้าที่เข้าร่วมแก้ไข พร้อมพิจารณาปริมาณการแก้ไขเป็นหลัก",
"contributionscores-top": "($1 อันดับแรก)",
"contributionscores-info": "วิธีการคิดคะแนนเป็นดังต่อไปนี้:\n* หนึ่ง (1) คะแนนต่อจำนวนหน้าที่เข้าร่วมแก้ไข (ชื่อของหน้าไม่ซ้ำกัน)\n* รากที่สองของจำนวนการแก้ไขทั้งหมด - จำนวนหน้าทั้งหมดที่ร่วมแก้ไข * 2\nคะแนนจะถูกคิดโดยให้น้ำหนักของการแก้ไขที่หลากหลายมากกว่าจำนวนการแก้ไข\nโดยทั่วไป คะแนนนี้ชี้วัดถึงจำนวนหน้าต่างๆ ที่เข้าร่วมแก้ไข โดยคำนึงถึงจำนวนการแก้ไขทั้งหมดด้วย จึงคาดการณ์ได้ว่าจะทำให้มีหน้าที่มีคุณภาพสูงขึ้น",
"contributionscores-days": "$1 {{PLURAL:$1|วัน|วัน}} ที่แล้ว",
"contributionscores-allrevisions": "ตลอดเวลา",
"contributionscores-score": "คะแนน",
"contributionscores-rank": "การจัดอันดับ",
"contributionscores-pages": "จำนวนหน้า",
"contributionscores-changes": "การเปลี่ยนแปลง",
"contributionscores-changes": "จำนวนการเปลี่ยนแปลง",
"contributionscores-username": "ชื่อผู้ใช้",
"contributionscores-invalidusername": "ชื่อผู้ใช้ไม่ถูกต้อง",
"contributionscores-invalidmetric": "เกณฑ์ชี้วัดไม่ถูกต้อง"
"contributionscores-invalidusername": "ชื่อผู้ใช้ไม่ถูกต้อง"
}

View file

@ -1,10 +0,0 @@
{
"@metadata": {
"authors": [
"Joanmp17"
]
},
"contributionscores-pages": "ገጻት",
"contributionscores-changes": "ለውጥታት",
"contributionscores-username": "ስም ተጠቃሚ"
}

View file

@ -1,7 +1,6 @@
{
"@metadata": {
"authors": [
"Hedda",
"Joseph",
"Karduelis",
"Mach",
@ -9,14 +8,13 @@
"Vito Genovese"
]
},
"contributionscores": "Katkı puanları",
"contributionscores": "Katkı skorları",
"contributionscores-desc": "En yüksek [[Special:ContributionScores|kullanıcı katkı hacmi]] için viki veritabanını sorgular",
"contributionscores-info": "Puanlama, öncelikle yüksek düzenleme hacmi dikkate alınarak düzenlenmiş benzersiz sayfaları ölçer.",
"contributionscores-top": "(Zirvedeki $1 kişi)",
"contributionscores-info": "Skorlar aşağıdaki şekilde hesaplanmaktadır:\n*Değişiklik yapılan her farklı sayfa için bir (1) puan\n*(Yapılan toplam değişiklik) - (toplam farklı sayfa) * 2 işleminin karekökü\nBu şekilde hesaplanan skorlar, değişiklik sayısı ile değişiklik çeşitliliği arasında ağırlık kurmaktadır.\nTemel olarak bu skor, yüksek değişiklik sayısının yüksek kaliteli bir sayfa olduğu varsayımıyla değişiklik yapılan farklı sayfa sayısını ölçmektedir.",
"contributionscores-top": "(En yüksek $1)",
"contributionscores-days": "Son $1 {{PLURAL:$1|gün|gün}}",
"contributionscores-allrevisions": "Tüm zamanlar",
"contributionscores-score": "Puan",
"contributionscores-rank": "Sıralama",
"contributionscores-pages": "Sayfalar",
"contributionscores-changes": "Değişiklikler",
"contributionscores-username": "Kullanıcı adı",

View file

@ -1,7 +1,6 @@
{
"@metadata": {
"authors": [
"Ерней",
"Ильнар"
]
},
@ -11,10 +10,10 @@
"contributionscores-top": "(Иң әйбәт $1)",
"contributionscores-days": "Соңгы {{PLURAL:$1|$1 көн өчен}}",
"contributionscores-allrevisions": "Бөтен вакыт өчен",
"contributionscores-score": әя",
"contributionscores-score": илге",
"contributionscores-rank": "Ранг",
"contributionscores-pages": "Битләр",
"contributionscores-changes": "Төзәтмәләр",
"contributionscores-pages": "Битләр саны",
"contributionscores-changes": "Үзгәртүләр",
"contributionscores-username": "Кулланучы исеме",
"contributionscores-invalidusername": "Кулланучының исеме дөрес түгел",
"contributionscores-invalidmetric": "Ялгыш билгеләү"

View file

@ -1,18 +1,17 @@
{
"@metadata": {
"authors": [
"Candalua",
"Fierodelveneto"
"Candalua"
]
},
"contributionscores": "Ponteji contribusion",
"contributionscores": "Puntegi contributi",
"contributionscores-desc": "Intèroga el database de la wiki par el pi grando [[Special:ContributionScores|volume de contributi utente]]",
"contributionscores-info": "I punti i vien calcolà come segue:\n*Un (1) punto par ogni diversa pagina modificà\n*Raìsa quadrata de (Tute le modifiche fate) - (Total de le pagine modificà) * 2\nFasendo i conti in sta maniera pesa piassè la diversità de le modifiche rispeto al nùmaro dei contributi.\nIn sostansa, sto puntegio el tien conto sopratuto de le diverse pagine modificà, tegnendo in considerazion anca un alto volume de modifiche - che fa pensar a na pi alta qualità de la pagina modificà.",
"contributionscores-top": "(Ultimi $1)",
"contributionscores-days": "{{PLURAL:$1|Ultimo zòrno|Ultimi $1 zòrni}}",
"contributionscores-allrevisions": "Tute le revision",
"contributionscores-score": "Puntegio",
"contributionscores-pages": "Pàjine",
"contributionscores-pages": "Pagine",
"contributionscores-changes": "Canbiamenti",
"contributionscores-username": "Nome utente",
"contributionscores-invalidusername": "Nome utente mia valido",

View file

@ -2,7 +2,6 @@
"@metadata": {
"authors": [
"Minh Nguyen",
"Phjtieudoc",
"Vinhtantran"
]
},
@ -14,7 +13,7 @@
"contributionscores-allrevisions": "Từ trước đến nay",
"contributionscores-score": "Điểm số",
"contributionscores-pages": "Trang",
"contributionscores-changes": "Thay đổi",
"contributionscores-changes": "Các thay đổi",
"contributionscores-username": "Tên người dùng",
"contributionscores-invalidusername": "Tên người dùng không hợp lệ",
"contributionscores-invalidmetric": "Chuẩn đo không hợp lệ"

View file

@ -1,9 +1,7 @@
{
"@metadata": {
"authors": [
"Moon0319",
"PhiLiP",
"Roy17",
"Shinjiman",
"Shirayuki",
"Yueman"
@ -14,7 +12,7 @@
"contributionscores-info": "呢個分數係會依主要嘅唯一編輯過嘅頁,同埋考慮高編輯量。",
"contributionscores-top": "(最高$1名)",
"contributionscores-days": "最近$1日",
"contributionscores-allrevisions": "有史以來",
"contributionscores-allrevisions": "全部時間",
"contributionscores-score": "分數",
"contributionscores-rank": "等級",
"contributionscores-pages": "版",

View file

@ -1,19 +1,18 @@
{
"@metadata": {
"authors": [
"Cwlin0416",
"Kly",
"LNDDYL",
"Liuxinyu970226",
"Mark85296341",
"PhiLiP",
"Shinjiman",
"Shirayuki",
"Simon Shek"
"Simon Shek",
"Cwlin0416",
"Liuxinyu970226",
"LNDDYL"
]
},
"contributionscores": "貢獻分數",
"contributionscores-desc": "調查 Wiki 資料庫中[[Special:ContributionScores|貢獻最多的使用者]]",
"contributionscores-desc": "調查 Wiki 資料庫中 [[Special:ContributionScores|貢獻最多的使用者]]",
"contributionscores-info": "此分數主要以編輯個別頁面數量計算並考慮編輯次數。",
"contributionscores-top": "(前 $1 名)",
"contributionscores-days": "最近 {{PLURAL:$1|天|$1 天}}",

View file

@ -1,8 +0,0 @@
{
"@metadata": {
"authors": [
"Liuxinyu970226"
]
},
"contributionscores-username": "用戶名稱"
}

8229
package-lock.json generated

File diff suppressed because it is too large Load diff

View file

@ -1,13 +1,13 @@
{
"name": "ContributionScores",
"private": true,
"scripts": {
"test": "grunt test"
},
"devDependencies": {
"eslint-config-wikimedia": "0.28.2",
"grunt": "1.6.1",
"grunt-banana-checker": "0.13.0",
"grunt-eslint": "24.3.0"
"grunt": "1.4.0",
"grunt-banana-checker": "0.4.0",
"grunt-contrib-jshint": "0.11.3",
"grunt-jscs": "2.5.0",
"grunt-jsonlint": "1.0.7"
}
}

View file

@ -1,436 +0,0 @@
<?php
/** \file
* \brief Contains code for the ContributionScores Class (extends SpecialPage).
*/
use MediaWiki\MediaWikiServices;
/// Special page class for the Contribution Scores extension
/**
* Special page that generates a list of wiki contributors based
* on edit diversity (unique pages edited) and edit volume (total
* number of edits.
*
* @ingroup Extensions
* @author Tim Laqua <t.laqua@gmail.com>
*/
class ContributionScores extends IncludableSpecialPage {
const CONTRIBUTIONSCORES_MAXINCLUDELIMIT = 50;
public function __construct() {
parent::__construct( 'ContributionScores' );
}
public static function onParserFirstCallInit( Parser $parser ) {
$parser->setFunctionHook( 'cscore', [ self::class, 'efContributionScoresRender' ] );
}
public static function efContributionScoresRender( $parser, $usertext, $metric = 'score' ) {
global $wgContribScoreDisableCache, $wgContribScoreUseRoughEditCount;
if ( $wgContribScoreDisableCache ) {
$parser->getOutput()->updateCacheExpiry( 0 );
}
$user = User::newFromName( $usertext );
$loadBalancer = MediaWikiServices::getInstance()->getDBLoadBalancer();
$dbr = $loadBalancer->getConnection( DB_REPLICA );
if ( $user instanceof User && $user->isRegistered() ) {
global $wgLang;
$revVar = $wgContribScoreUseRoughEditCount ? 'user_editcount' : 'COUNT(rev_id)';
$revWhere = ActorMigration::newMigration()->getWhere( $dbr, 'rev_user', $user );
if ( $metric == 'score' ) {
$row = $dbr->selectRow(
[ 'revision' ] + $revWhere['tables'],
[ 'wiki_rank' => "COUNT(DISTINCT rev_page)+SQRT($revVar-COUNT(DISTINCT rev_page))*2" ],
$revWhere['conds'],
__METHOD__,
[],
$revWhere['joins']
);
$output = $wgLang->formatNum( round( $row->wiki_rank, 0 ) );
} elseif ( $metric == 'changes' ) {
$row = $dbr->selectRow(
[ 'revision' ] + $revWhere['tables'],
[ 'rev_count' => $revVar ],
$revWhere['conds'],
__METHOD__,
[],
$revWhere['joins']
);
$output = $wgLang->formatNum( $row->rev_count );
} elseif ( $metric == 'pages' ) {
$row = $dbr->selectRow(
[ 'revision' ] + $revWhere['tables'],
[ 'page_count' => 'COUNT(DISTINCT rev_page)' ],
$revWhere['conds'],
__METHOD__,
[],
$revWhere['joins']
);
$output = $wgLang->formatNum( $row->page_count );
} else {
$output = wfMessage( 'contributionscores-invalidmetric' )->text();
}
} else {
$output = wfMessage( 'contributionscores-invalidusername' )->text();
}
return $parser->insertStripItem( $output, $parser->getStripState() );
}
/**
* Function fetch Contribution Scores data from database
*
* @param int $days Days in the past to run report for
* @param int $limit Maximum number of users to return (default 50)
* @return array Data including the requested Contribution Scores.
*/
public static function getContributionScoreData( $days, $limit ) {
global $wgContribScoreIgnoreBots, $wgContribScoreIgnoreBlockedUsers, $wgContribScoreIgnoreUsernames,
$wgContribScoreUseRoughEditCount;
$loadBalancer = MediaWikiServices::getInstance()->getDBLoadBalancer();
$dbr = $loadBalancer->getConnection( DB_REPLICA );
$revQuery = ActorMigration::newMigration()->getJoin( 'rev_user' );
$revQuery['tables'] = array_merge( [ 'revision' ], $revQuery['tables'] );
$revUser = $revQuery['fields']['rev_user'];
$revUsername = $revQuery['fields']['rev_user_text'];
$sqlWhere = [];
if ( $days > 0 ) {
$date = time() - ( 60 * 60 * 24 * $days );
$sqlWhere[] = 'rev_timestamp > ' . $dbr->addQuotes( $dbr->timestamp( $date ) );
}
$sqlVars = [
'rev_user' => $revUser,
'page_count' => 'COUNT(DISTINCT rev_page)'
];
if ( $wgContribScoreUseRoughEditCount ) {
$revQuery['tables'][] = 'user';
$revQuery['joins']['user'] = [ 'LEFT JOIN', [ "$revUser != 0", "user_id = $revUser" ] ];
$sqlVars['rev_count'] = 'user_editcount';
} else {
$sqlVars['rev_count'] = 'COUNT(rev_id)';
}
if ( $wgContribScoreIgnoreBlockedUsers ) {
$sqlWhere[] = "{$revUser} NOT IN " .
$dbr->buildSelectSubquery( [
'block',
'block_target'
],
'bt_user',
'bt_user <> 0',
__METHOD__,
[],
[
'block_target' => [ 'JOIN', [
'bl_target=bt_id'
] ]
]
);
}
if ( $wgContribScoreIgnoreBots ) {
$sqlWhere[] = "{$revUser} NOT IN " .
$dbr->buildSelectSubquery( 'user_groups', 'ug_user', [
'ug_group' => 'bot',
'ug_expiry IS NULL OR ug_expiry >= ' . $dbr->addQuotes( $dbr->timestamp() )
], __METHOD__ );
}
if ( count( $wgContribScoreIgnoreUsernames ) ) {
$listIgnoredUsernames = $dbr->makeList( $wgContribScoreIgnoreUsernames );
$sqlWhere[] = "{$revUsername} NOT IN ($listIgnoredUsernames)";
}
if ( $dbr->unionSupportsOrderAndLimit() ) {
$order = [
'GROUP BY' => 'rev_user',
'ORDER BY' => 'page_count DESC',
'LIMIT' => $limit
];
} else {
$order = [ 'GROUP BY' => 'rev_user' ];
}
$sqlMostPages = $dbr->selectSQLText(
$revQuery['tables'],
$sqlVars,
$sqlWhere,
__METHOD__,
$order,
$revQuery['joins']
);
if ( $dbr->unionSupportsOrderAndLimit() ) {
$order['ORDER BY'] = 'rev_count DESC';
}
$sqlMostRevs = $dbr->selectSQLText(
$revQuery['tables'],
$sqlVars,
$sqlWhere,
__METHOD__,
$order,
$revQuery['joins']
);
$sqlMostPagesOrRevs = $dbr->unionQueries( [ $sqlMostPages, $sqlMostRevs ], false );
$res = $dbr->select(
[
'u' => 'user',
's' => new Wikimedia\Rdbms\Subquery( $sqlMostPagesOrRevs ),
],
[
'user_id',
'user_name',
'user_real_name',
'page_count',
'rev_count',
'wiki_rank' => 'page_count+SQRT(rev_count-page_count)*2',
],
[],
__METHOD__,
[
'ORDER BY' => 'wiki_rank DESC',
'LIMIT' => $limit,
],
[
's' => [
'JOIN',
'user_id=rev_user'
]
]
);
$ret = iterator_to_array( $res );
return $ret;
}
/// Generates a "Contribution Scores" table for a given LIMIT and date range
/**
* Function generates Contribution Scores tables in HTML format (not wikiText)
*
* @param int $days Days in the past to run report for
* @param int $limit Maximum number of users to return (default 50)
* @param string|null $title The title of the table
* @param array $options array of options (default none; nosort/notools)
* @return string Html Table representing the requested Contribution Scores.
*/
function genContributionScoreTable( $days, $limit, $title = null, $options = 'none' ) {
global $wgContribScoresUseRealName, $wgContribScoreCacheTTL;
$opts = explode( ',', strtolower( $options ) );
$sortable = in_array( 'nosort', $opts ) ? '' : ' sortable';
$output = "<table class=\"wikitable contributionscores plainlinks{$sortable}\" >\n" .
"<tr class='header'>\n" .
Html::element( 'th', [], $this->msg( 'contributionscores-rank' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-score' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-pages' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-changes' )->text() ) .
Html::element( 'th', [], $this->msg( 'contributionscores-username' )->text() );
$cache = MediaWikiServices::getInstance()->getMainWANObjectCache();
$data = $cache->getWithSetCallback(
$cache->makeKey( 'contributionscores', 'data-' . (string)$days ),
$wgContribScoreCacheTTL * 60,
function () use ( $days ) {
// Use max limit, as limit doesn't matter with performance.
// Avoid purge multiple times since limit on transclusion can be vary.
return self::getContributionScoreData( $days, self::CONTRIBUTIONSCORES_MAXINCLUDELIMIT );
} );
$lang = $this->getLanguage();
$altrow = '';
$user_rank = 1;
foreach ( $data as $row ) {
if ( $user_rank > $limit ) {
break;
}
// Use real name if option used and real name present.
if ( $wgContribScoresUseRealName && $row->user_real_name !== '' ) {
$userLink = Linker::userLink(
$row->user_id,
$row->user_name,
$row->user_real_name
);
} else {
$userLink = Linker::userLink(
$row->user_id,
$row->user_name
);
}
$output .= Html::closeElement( 'tr' );
$output .= "<tr class='{$altrow}'>\n" .
"<td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( $user_rank ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( round( $row->wiki_rank, 0 ) ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( $row->page_count ) .
"\n</td><td class='content' style='padding-right:10px;text-align:right;'>" .
$lang->formatNum( $row->rev_count ) .
"\n</td><td class='content'>" .
$userLink;
# Option to not display user tools
if ( !in_array( 'notools', $opts ) ) {
$output .= Linker::userToolLinks( $row->user_id, $row->user_name );
}
$output .= Html::closeElement( 'td' ) . "\n";
if ( $altrow == '' && empty( $sortable ) ) {
$altrow = 'odd ';
} else {
$altrow = '';
}
$user_rank++;
}
$output .= Html::closeElement( 'tr' );
$output .= Html::closeElement( 'table' );
// Transcluded on a normal wiki page.
if ( !empty( $title ) ) {
$output = Html::rawElement( 'table',
[
'style' => 'border-spacing: 0; padding: 0',
'class' => 'contributionscores-wrapper',
'lang' => htmlspecialchars( $lang->getCode() ),
'dir' => $lang->getDir()
],
"\n" .
"<tr>\n" .
"<td style='padding: 0px;'>{$title}</td>\n" .
"</tr>\n" .
"<tr>\n" .
"<td style='padding: 0px;'>{$output}</td>\n" .
"</tr>\n"
);
}
return $output;
}
function execute( $par ) {
$this->setHeaders();
if ( $this->including() ) {
$this->showInclude( $par );
} else {
$this->showPage();
}
return true;
}
/**
* Called when being included on a normal wiki page.
* Cache is disabled so it can depend on the user language.
* @param string|null $par A subpage give to the special page
*/
function showInclude( $par ) {
$days = null;
$limit = null;
$options = 'none';
if ( !empty( $par ) ) {
$params = explode( '/', $par );
$limit = intval( $params[0] );
if ( isset( $params[1] ) ) {
$days = intval( $params[1] );
}
if ( isset( $params[2] ) ) {
$options = $params[2];
}
}
if ( empty( $limit ) || $limit < 1 || $limit > self::CONTRIBUTIONSCORES_MAXINCLUDELIMIT ) {
$limit = 10;
}
if ( $days === null || $days < 0 ) {
$days = 7;
}
if ( $days > 0 ) {
$reportTitle = $this->msg( 'contributionscores-days' )->numParams( $days )->text();
} else {
$reportTitle = $this->msg( 'contributionscores-allrevisions' )->text();
}
$reportTitle .= ' ' . $this->msg( 'contributionscores-top' )->numParams( $limit )->text();
$title = Xml::element( 'h4',
[ 'class' => 'contributionscores-title' ],
$reportTitle
) . "\n";
$this->getOutput()->addHTML( $this->genContributionScoreTable(
$days,
$limit,
$title,
$options
) );
}
/**
* Show the special page
*/
function showPage() {
global $wgContribScoreReports;
if ( !is_array( $wgContribScoreReports ) ) {
$wgContribScoreReports = [
[ 7, 50 ],
[ 30, 50 ],
[ 0, 50 ]
];
}
$out = $this->getOutput();
$out->addWikiMsg( 'contributionscores-info' );
foreach ( $wgContribScoreReports as $scoreReport ) {
[ $days, $revs ] = $scoreReport;
if ( $days > 0 ) {
$reportTitle = $this->msg( 'contributionscores-days' )->numParams( $days )->text();
} else {
$reportTitle = $this->msg( 'contributionscores-allrevisions' )->text();
}
$reportTitle .= ' ' . $this->msg( 'contributionscores-top' )->numParams( $revs )->text();
$title = Xml::element( 'h2',
[ 'class' => 'contributionscores-title' ],
$reportTitle
) . "\n";
$out->addHTML( $title );
$out->addHTML( $this->genContributionScoreTable( $days, $revs ) );
}
}
public function maxIncludeCacheTime() {
global $wgContribScoreDisableCache, $wgContribScoreCacheTTL;
return $wgContribScoreDisableCache ? 0 : $wgContribScoreCacheTTL;
}
/**
* @inheritDoc
*/
protected function getGroupName() {
return 'wiki';
}
}